cross-platform techniques to determine screen dimensions

Viewed 68

Is there a good cross-platform way of getting the screen dimensions? Frequently I do this with PerlTk:

 use Tk;
 my $mw = MainWindow->new;
 my $screen_width  = $mw->screenwidth();   
 my $screen_height = $mw->screenheight();  

But it'd be better to not have to load all of Tk just to do this.

This looks like a good X11 specific way of doing these things (GetRootWindow should work for screen dimensions):

Perl: Getting the geometry of a window with X11 WindowID

But I think a cross-platform approach would be better.

Specifically, I'm looking for ways to determine the monitor dimensions in pixels, which is what Tk's screenwidth and screenheight return.

2 Answers

On most POSIX-y systems:

use Curses ();
my $screen_width = $Curses::COLS;
my $screen_height = $Curses::LINES;

These values don't update automatically when the screen is resized.

The best I can see for getting display/screen resolution is to use OS-specific tools.

On X11 the best bet is probably xrandr while on Windows it'd be Win32::GUI or Win32::API.

Then wrap it in a sub that checks for the OS and selects a tool to use.

(Or of course use a GUI package, like Perl/Tk that OP is using)


For example

for my $line_out ( qx(xrandr) ) { 
    #print "--> $line_out";
    if ( my ($wt, $ht) = $line_out =~ /^\s+([0-9]+)\s*x\s*([0-9]+)/ ) { 
        say "Width: $wt, height: $ht";
        last;
    }   
}

There are many ways to parse that, and in principle I recommend using libraries to manage external programs (in particular in order to get their output/errors etc); this is a quick demo.

On my system the xrandr output is like

Screen 0: minimum 8 x 8, current 5040 x 1920, maximum 32767 x 32767
DP-0 connected primary 1920x1200+3120+418 (normal left inverted right x axis y axis) 519mm x 320mm
   1920x1200     59.95*+
   1600x1200     60.00  
   1280x1024     75.02    60.02  
   1152x864      75.00  
...

and it keeps going, and then for all displays.

So I pick the top resolution for the first listed one ("primary")

Related