WinRT/UWP ICoreWindow
« | 09 Jan 2021 | »Wie kommt man von
main
zuICoreWindow
und dem restlichen UWP Schnickschnack der Windows RunTime?
Nun, wenn ich schon die C Interface Projection zerlege, dann kann ich das hiermit auch gleich mal mitdokumentieren.
WinRT Programme werden ja “anders” behandelt als reguläre
Win32
Prozesse. Ähnlich wie bei Services erwartet das System, dass der Prozess
binnen einer bestimmten Zeit sich meldet und seine Schnittstellen zum
Empfangen von “Anweisungen” bereitstellt.
Gut analysieren kann man das über die C++ DirectX
UWP Projektvorlage.
In WinRT übernimmt das die Klasse CoreApplication
,
deren statische Methode Run
eine Instanz von IFrameworkViewSource
entgegen nimmt, was wiederum nur eine Factory für eine
IFrameworkView
Instanz ist, die mit der Methode
CreateView()
genau eine solche erzeugt.
CoreApplication::Run()
ruft nach der Erzeugung von IFrameworkView
folgende Methoden auf:
Initialize()
Hier erhält man einICoreApplicationView
wo man seine eigene Ereignisbehandlung für Events wieActivated
,Suspending
oderResuming
setzen kannSetWindow()
Über denICoreWindow
Parameter erhalten wir DAS Fenster, in dem die App laufen wird. Auch hier kann man diverse Event-Handler für Fensteränderungen setzenLoad()
Dann sollten Einstellungen und Ressourcen geladen werden, was hier angestoßen werden sollte.Run()
Und wenn alles vorbereitet ist, darf gearbeitet werden … oder man wartet einfach auf einShutdown
bzw.CloseWindow
Event. Dazu lässt man in einer Schleife die MethodeProcessEvents()
vonICoreDispatcher
ausführen, welchen man vonICoreWindow
über dasDispatcher
Property erhalten hat.Uninitialize()
KehrtRun
zurück, wird die App üblicherweise beendet und eben hier tritt dieUninitialize()
Methode in Aktion.
Was muss man also tun?
Man implementiert eine IFrameworkView
Ableitung, welches die
ICoreApplicationView
und ICoreWindow
von Initialize
und SetWindow
aufbewahrt und “vorbereitet”.
Dann implementiert man eine IFrameworkViewSource
, die die zuvor
beschriebene IFrameworkView
Ableitung instanziiert.
In main
erzeugt man seine IFrameworkViewSource
Instanz und
übergibt sie an CoreApplication::Run
.
Klingt kompliziert … naja, ist eben COM.
Und wie macht man weiter?
Für DirectX/Direct3D gibt es ja ein schönes Beispiel. XAML ist mir aktuell echt zu anstrengend, um das nativ alles nachzubauen. Da ist man eben doch mit den fertigen Templates und den C++ Erweiterungen gut beraten, die die Generierung der nötigen Codes und Metadaten übernehmen.
Aber zum Herumspielen sei noch eines erwähnt:
Tief versteckt gibt es noch das Interface
ICoreWindowInterop
mit der Methode get_WindowHandle
, die ein HWND
zurückliefert.
Oh mein Gott! Ein
HWND
in jedemCoreWindow
?
Tja, sieht fast so aus. Bei Nicht-Desktop Apps deaktiviert Microsoft die
Implementierung in den Headern … aber wer das Interface selbst zusammenbaut
und per QueryInterface
auf die IID 45D64A29-A63E-4CB6-B498-5781D298CB4F
wechselt, der wird auch dort mit einer HWND
belohnt.
Da sag ich nur: NICE!