VisaToHell
VisaToHell

Reputation: 508

DPI-awareness is really needed?

I am learning how to draw GUI's with GDI/GDI+, i found this http://msdn.microsoft.com/en-us/library/windows/desktop/dd756596(v=vs.85).aspx#step_2__declare_that_the_application_is_dpi-aware Does every application do that calculation so it can be displayed properly or what ?

Can someone explain how to calculate client coordinates of buttons,images and all controls on your window so they have the same align on different resolutions ?

Thanks in advance.

Upvotes: 2

Views: 2425

Answers (2)

Hans Passant
Hans Passant

Reputation: 942267

Ignoring dpi-awareness is starting to become painful pretty quickly. Display technology has been stuck at 96 dpi for a very long time, 20 years already. Vista with its automatic dpi scaling and highly accessible "ruler" applet was a game changer. Apple with its push for "retina" displays is the real driving force. Next Apple MacBook has a 2880 x 1800 display, your typical 1024x768 window is going to be a postage stamp on a display like that.

Tooling to make it automatic is readily available, XAML based class libraries (WPF, Silverlight, Metro) are entirely resolution independent. HTML and Winforms auto-scale pretty well. But of course little help with GDI. And none whatsoever in User32, firmly stuck in pixel-land. You can certainly write the code, it's just not pleasant code to write. If you are still programming the raw API for legacy reasons then the automatic scaling built into Vista and up will be attractive. Well, for reducing the effort, it isn't going to look very attractive :)

Upvotes: 2

Cory Nelson
Cory Nelson

Reputation: 30031

With GDI, you can use GetDeviceCaps function with LOGPIXELSX and LOGPIXELSY to find your DPI, and use these values to scale your sizes:

HDC hdc = GetDC(hwnd);
int ppix = GetDeviceCaps(hdc, LOGPIXELSX);
int ppiy = GetDeviceCaps(hdc, LOGPIXELSY);
ReleaseDC(hdc);

// for a control that is 1.5 inches wide and 0.5 inches high.

int ctrl_width = int(1.5 * ppix + 0.5);
int ctrl_height = int(0.5 * ppiy + 0.5);

// for a button that conforms to Microsoft's UI guidelines of 75x23 @ 96dpi.

int btn_width = (75 * ppix + 48) / 96;
int btn_height = (23 * ppiy + 48) / 96;

GDI+ makes this considerably simpler:

Graphics g;
g.SetPageUnit(UnitInch);

// now you can specify draw coordinates in inches
// and it'll figure out DPI for you.

Do note that the GDI+ solution will only affect GDI+ draw calls—not GDI calls or coordinates of controls.

Upvotes: 3

Related Questions