OT: Windows 7 und Bildschirme mit hohem Dotpitch - Erfahrungen

24/11/2009 - 15:11 von Ulrich Korndoerfer | Report spam
Hallo NG!

Für Interessierte hier eine Zusammenfassung meiner bisherigen
"Erlebnisse" / Erkenntnisse mit hohen Dotpitches unter einem
deutschsprachigem *64 bit* Windows 7.

*****
* Neue Variante: Windows 7 DPI-Skalierung
*****

Wie die früheren Versionen von Windows bietet auch Win 7 die
Möglichkeit, über den Dialog "DPI-Einstellungen anpassen" dem System die
tatsàchliche Pixeldichte des Monitors mitzuteilen.

Um den Dialog aufzurufen kann man zum Beispiel die Systemsteuerung
öffnen und zu

Systemsteuerung->Darstellung und Anpassung->Anzeige

navigieren. Dann in der linken Spalte "Benutzerdefinierte Textgröße
(DPI) festlegen" anklicken.

Im darauf erscheinendem Dialog "DPI-Einstellung anpassen" kann direkt
die Pixeldichte (in ppi) oder ein Skalierungsfaktor vorgegeben werden.
Der Skalierungsfaktor bezieht sich auf die von MS so genannte
Standardpixeldichte von 96 ppi. Für einen Bildschirm mit zB 135 ppi (das
wàre zB ein 11.6 Zoll Laptopbildschirm mit 1366*768 Pixeln) betrüge der
Skalierungsfaktor dann ca. 1.41 bzw. 141%.

Im Gegensatz zu früheren Versionen von Windows (Ausnahme Vista) hat
dieser Dialog noch eine weitere Einstellmöglichkeit: eine Checkbox
bietet an, die "DPI-Skalierung im Stil von Windows XP" zu "verwenden".
Per Default ist diese Einstellung abgewàhlt.

Über diese Checkbox kann festgelegt werden, ob das System in die
Darstellung des GUIs von Applikationen eingreift oder nicht:

a) Checkbox angewàhlt (DPI-Skalierung im Stil von Windows XP)

Das System greift nicht in die Darstellung ein. Einer Applikation werden
die real existierende Pixelanzahl und der in der Dialogbox gewàhlte
DPI-Wert übermittelt. Das ist das gleiche Verhalten wie unter früheren
Versionen von Windows (vor Vista).

Beispiel für VB6 Applikation: Bildschirm 1366x768 Pixel, 135 DPI/PPI

Screen.Width -> 1366
Screen.Height -> 768
Screen.TwipsPerPixelX -> (1/135)/(1/1440) = 10.666...
Screen.TwipsPerPixelY -> (1/135)/(1/1440) = 10.666...

b) Checkbox nicht angewàhlt (Windows 7 DPI-Skalierung)

Das System greift in die Darstellung ein. Einer Applikation wird ein
Bildschirm mit 96 dpi Auflösung und entsprechend reduzierter Pixelanzahl
vorgegaukelt.

Beispiel für VB6 Applikation: Bildschirm 1366x768 Pixel, 135 DPI/PPI

Screen.Width -> 1366*(96/135) = 971
Screen.Height -> 768*(96/135) = 546
Screen.TwipsPerPixelX -> (1/96)/(1/1440) = 15
Screen.TwipsPerPixelY -> (1/96)/(1/1440) = 15

Für die Applikation sieht es so aus, als ob sie auf einem Bildschirm mit
971x546 Pixeln bei einer Pixelauflösung von 96 DPI laufen würde.

*****
* Wie wird die Windows 7 DPI-Skalierung realisiert
*****

Im Aero-Betrieb werden alle Bildschirmausgaben nicht mehr wie früher
direkt auf den Desktop gerendert, sondern in einen Memorybuffer. Danach
wird der Buffer auf den Desktop geblittet. Das bietet ua. folgende Vorteile:

- Der Memorybuffer kann im (meistens reichlich) vorhandenem
Videokartenram gehalten werden. Das Rendern kann die
Hardwarebeschleunigungsmethoden des Videochips verwenden.
- Der Buffer ist persistent im Videokartenram, und kann jederzeit
abgerufen werden
- Alle nötigen Arbeiten für die Ausgabe auf den Schirm erfolgen nun
direkt im Videoram und können vom Videochip durchgeführt werden.

Vor allem der letzte Punkt bietet nun viele Möglichkeiten/Vorteile, da
nun die Hardwarevorteile des Videochips genutzt werden können. Der
Buffer kann zum Beispiel vor der Ausgabe transformiert werden
(durchgeführt ohne CPU-Belastung direkt in der/durch die Graphikkarte).
Dadurch ist es zB möglich, das GUI einer Applikation als "Textur" zu
behandeln und es zB auf einer der Seitenflàchen eines rotierenden
Würfels anzuzeigen.

Ebenso einfach ist es, den Buffer bei der Ausgabe zu skalieren
("StretchBlit"). Und genau das wird bei der DPI-Skalierung gemacht:

- die Applikation rendert ihre Fenster in einen maximal 971x546 großen
Buffer
- das System gibt den Buffer skaliert um den Faktor 135/96 (1.4065) auf
den Monitor aus

Positive Folgen:

- eine Applikation, die mit dem tatsàchlichen DPI-Wert des Systems nicht
zurechtkommt (da sie intern nicht berücksichtigt, daß die Applikation
auch auf Schirmen laufen könnte, die eine andere Auflösung als 96 dpi
haben), funktioniert nun problemlos. Im GUI wird nichts abgeschnitten,
alle Bedienungselemente sind sichtbar.

Negative Folgen:

- das GUI erscheint "verwaschen", da die Pixels um einen "krummen"
Faktor 1.4065 skaliert werden müssen
- die Mauskoordinaten müssen nun umgerechnet werden auf das
Koordinatensystem des Buffers, damit auch weiterhin zugeordnet werden
kann, wo zB tatsàchlich hingeklickt wurde. Das kann auch mal schief
gehen (in Grenzfàllen).

*****
* Welche Variante sollte gewàhlt werden
*****

Meiner Meinung nach sollte die "Windows 7 DPI-Skalierung" gewàhlt
werden, also die Checkbox "DPI-Skalierung im Stil von Windows XP
verwenden" abwàhlen.

Dies ist eine globale Einstellung, die erst mal für alle Anwendungen
gilt: für *alle* Applikationen wird die Win7 DPI-Skalierung *eingeschaltet*.

Windows 7 erlaubt (zumindest theoretisch, zu den Einschrànkungen kommen
wir noch) es, diese DPI-Skalierung nun wieder *individuell* für jede
einzelne Applikation *abzuschalten*:

- jede Applikation, die der Meinung ist, sie bràuchte keine besonderen
Maßnahmen auf Schirmen mit hohem DPI-Wert, kann dies dem System
mitteilen. Das System verwendet dann für diese Applikation die Win7
DPI-Skalierung nicht.

Dazu muß sie entweder ein Manifest haben und in diesem Manifest per
<dpiAware>True>/dpiAware> dem System mitteilen, daß eine DPI-Skalierung
nicht stattfinden soll. Dies ist der von MS empfohlene Weg. Oder sie
kann das auch über einen speziellen API-Call beim Programmstart tun.
Diese Möglichkeit wurde wohl unter Vista? eingeführt, wird aber
inzwischen von MS als "deprecated" eingestuft.

- zusàtzlich kann der Benutzer für jede Applikation individuell über den
Eigenschaftendialog der Applikation unter dem Reiter "Kompatibilitàt" im
Bereich "Einstellungen" mit der Checkbox "Skalierung bei hohem DPI-Wert
deaktivieren" die Win 7 DPI-Skalierung für diese Applikation abschalten.

Das Muster lautet also:

- DPI-Skalierung global einschalten

- Applikationen, die auf diese Problematik vorbereitet sind, können
diese für sich selbst abschalten, Benutzereingriff ist nicht
erforderlich. Das funktioniert immer (zumindest nach meinen bisherigen
Erfahrungen).

Ein Ratschlag für eigene VB6-Applikationen, von denen man sicher ist,
daß sie auch unter hohen Auflösungen laufen: sie sollten ein Manifest
mit auf den Weg bekommen, falls sie auch unter Win7/Vista zum Einsatz
kommen sollen. Auch aus anderen Gründen führt der Weg an einem Manifest
für VB6-Applikationen, die für einen Einsatz unter Vista/7 in Frage
kommen sollen, nicht mehr vorbei. Mit einem Manifest kann/sollte zB auch
die Rechte/Privilegien-Verwaltung feingesteuert werden (Stichwort
UA-Control).

- Für Applikationen, die zwar intrinsisch "dpi-aware" sind, dies aber
dem System nicht von sich aus mitteilen, kann per Benutzereingriff die
DPI-Skalierung abgeschaltet werden.

- Bei Applikationen, die Probleme bei der Darstellung auf Schirmen mit
hohem DPI-Wert haben, kann der Benutzer entscheiden, ob er mit den
Einschrànkungen leben kann und die DPI-Skalierung für diese App
abschaltet oder aber die DPI-Skalierung gewàhren làßt. Das GUI erscheint
dann zwar verwaschen (und es gibt möglicherweise Probleme mit dem
Erfassen von Mauspositionen in Grenzfàllen), aber immerhin gibt es nun
nicht mehr die typischen Probleme, die man mit Applikationen hat, welche
nicht auf hohe DPI-Werte vorbereitet sind.

*****
* Probleme
*****

Es wàre nicht MS, wenn es nicht auch Probleme mit der Umsetzung oben
skizziertem Konzeptes gàbe. Wie so oft bei MS: Konzeption hui, Umsetzung
pfui ;-) Vielleicht hilft ja das erste Servicepack weiter :-)

A) Programme, die per Manifest sich als DPI-Aware bezeichnen

Schön. Aber was, wenn das Programm dann doch Probleme macht? Hier wàre
es hilfreich, daß man dann für solche Programme trotzdem die
DPI-Skalierung *aktivieren* könnte. Dazu habe ich aber bis jetzt noch
keine Möglichkeit gefunden. Ok, man könnte versuchen, per Ressourcentool
in der eingebetteten Manifestdatei das dpi-aware flag zu entfernen. Habe
ich noch nicht probiert. Jedenfalls ein Weg, der für den normalen
Benutzer nicht (so einfach) gangbar wàre.

B) 64 Bit Programme

Das Verhalten, welches hier WIN7 an den Tag legt, verstehe ich ganz und
gar nicht. Es scheint so, als ob *generell* bei 64 Bit Programmen der
Bereich "Einstellungen" des Reiters "Kompatibilitàt" des
Eigenschaften-Dialoges *nicht* zur Verfügung steht (ist deaktiviert).

Konsequenzen:

- Auf ein 64 Bit Programm, welches durchaus in der Lage ist, mit hohen
DPI-Auflösungen zurechtzukommen, dies aber nicht selbst dem System
meldet, wird stets die DPI-Skalierung angewendet. Man kann das nicht
über den Eigenschaftendialog abschalten!

Was soll das? Bei 32 Bit Programmen geht das Abschalten "von Hand" doch
auch!

Beispiel bei mir ist das *Konfigurationsprogramm* FileMenuTools.exe
(nicht die Extension selber) für die Shell-Kontextmenu-Erweiterung
FileMenuTools. Das ist ein 64 Bit-Programm, welches aller
Wahrscheinlichkeit nach keine Probleme mit hohen DPI-Werten hat. Das
eingebettete Manifest hat kein dpi-aware Flag. Konsequenterweise wird
die DPI-Skalierung angewendet. Ich kann sie nicht abschalten, weil der
entsprechende Punkt im Eigenschaftendialog der Applikation nicht zur
Verfügung steht!

Oder der alternative Explorer Q-Dir. Den gibt es in einer 32 Bit und in
einer 64 Bit Version. Beide haben eine eingebettetes Manifest ohne
dpi-aware flag. Bei der 32 Bit Version habe ich die DPI-Skalierung über
den Eigenschaftendialog deaktiviert, das Programm làuft einwandfrei und
kommt mit der hohen DPI-Auflösung zurecht. Die 64 Bit Version làuft
immer mit der DPI-Skalierung, und ich kann sie nicht im
Eigenschaftendialog abschalten. Warum darf ich das bei einer 64 Bit App
nicht?

Nun könnte man im speziellen Fall von Q-Dir sagen: ok, dann nimm halt
die 32 Bit Version und verzichte auf die 64 Bit Version. Da gibt es aber
noch ein kleines Problem:

Q-Dir verwendet/bindet ein die gleichen Shell-Kontextmenuerweiterungen,
die für den Explorer installiert sind. Und hier tut sich ein weiteres
Problemfeld zumindest der 64 Bit-Version auf:

32 Bit Programme unter W7/64 laufen zwar bis jetzt (nach meiner
Erfahrung) problemlos. Verwendet das Programm aber eine
Shell-Erweiterung (COM-Server Dll, die in den Windows Explorer
eingebunden wird), ergeben sich folgende Konstellationen:

- reine 32 Bit Shell-Erweiterung

Làßt sich installieren/registrieren, wird aber im WindowsExplorer nicht
verwendet, wahrscheinlich weil dieser per Default ein 64 Bit Prozess
ist. In Q-Dir 32 Bit sichtbar, in Q-Dir 64 Bit nicht.

- 7Zip 64 Bit Shell-Erweiterung

Die ist merkwürdig. Sichtbar in Explorer 64, Q-Dir 64 und Q-Dir 32!

- Andere 64 Bit Shell Erweiterungen

Sichtbar in Explorer 64, Q-Dir 64, nicht in Q-Dir 32!?

Bin noch am Knobeln, welche Systematik dahintersteckt. Sobald ich
nàheres weiss, könnte ich ja dazu hier einen weiteren Post folgen
lassen. Hat jemand Interesse?

C) 32 Bit Programme, die sich nicht per Manifest als DPI-Aware bezeichnen

Prinzipiell problemlos. Die DPI-Skalierung ist eingeschaltet (da global
gesetzt), nach Bedarf kann sie über den Eigenschaftendialog der
Anwendung ausgeschaltet werden.

Aber:

Bei meinen anfànglichen Schritten mit W7/64 hatte ich den Eindruck, daß
es eine Rolle spielt, von welchem Ort aus ein Programm ausgeführt wird:

A) C:\Programme Ordner oder Unterordner (für 64 Bit Programme)
B) C:\Programme (x86) Ordner oder Unterordner (für 32 Bit Programme)
C) Anderer Ort

Dabei schien es so zu sein, daß bei einem Programm, welches vom Ort A)
ausgeführt wurde, es keine Rolle spielte, welche Einstellung für die
DPI-Skalierung gewàhlt wurde: sie war *immer* abgeschaltet.

Kann ich aber nicht mehr reproduzieren.

*****
* Fazit für Applikationsentwickler
*****

Da man nicht weiß, was der User auf seinem System eingestellt hat, ob er
in der Lage ist, bei Bedarf die DPI-Skalierung abzuschalten und wegen
der Spielchen, die W7 treibt:

- Programm für die Verwendung unter hohen DPI-Werten (also
auflösungsunabhàngig) programmieren (diese EMpfehlung war auch schon für
frühere Versionen von Windows richtig)

- Manifest mit dpi-aware flag einbetten!

Ulrich Korndoerfer

VB tips, helpers, solutions -> http://www.proSource.de/Downloads/
 

Lesen sie die antworten

#1 Schmidt
24/11/2009 - 15:19 | Warnen spam
"Ulrich Korndoerfer" schrieb im
Newsbeitrag news:OU%23B3$

Danke dafür - wird hier "sogleich archiviert"... :-)

Werd demnàchst wohl auch meine erste Win7-
Test-Maschine aufsetzen.

Olaf

Ähnliche fragen