Megosztás:


Tudnivalók az ablakosztályokról

Minden ablakosztályhoz tartozik egy társított ablakművelet, amelyet ugyanazon osztály összes ablaka megosztott. Az ablakos eljárás az osztály összes ablakához feldolgozza az üzeneteket, így szabályozza azok viselkedését és megjelenését. További információ az ablakkezelési eljárásokról a alatt található.

A folyamatnak regisztrálnia kell egy ablakosztályt, mielőtt létrehozhat egy ablakot az adott osztályból. Az ablakosztályok regisztrálása egy ablakeljárást, osztálystílust és más osztályattribútumot társít egy osztálynévvel. Amikor egy folyamat megad egy osztálynevet a CreateWindow vagy a CreateWindowEx függvényben, a rendszer létrehoz egy ablakot az adott osztálynévhez társított ablakeljárással, stílusokkal és egyéb attribútumokkal.

Ez a szakasz a következő témaköröket ismerteti.

Ablakosztályok típusai

Az ablakosztályok három típusa létezik:

Ezek a típusok különböznek a hatókörükben, valamint abban, hogy mikor és hogyan vannak regisztrálva és megsemmisítve.

Rendszerosztályok

A rendszerosztály a rendszer által regisztrált ablakosztály. Számos rendszerosztály minden használni kívánt folyamathoz elérhető, míg mások csak belsőleg. Mivel a rendszer regisztrálja ezeket az osztályokat, egy folyamat nem tudja megsemmisíteni őket.

A rendszer regisztrálja a rendszerosztályokat egy folyamathoz, amikor az egyik szál először meghív egy felhasználót vagy egy Windows grafikuseszköz-kezelő (GDI) függvényt.

Minden alkalmazás megkapja a rendszerosztályok saját példányát. Az ugyanabban a VDM-ben található 16 bites Windows-alapú alkalmazások rendszerosztályokat osztanak meg, ugyanúgy, mint a 16 bites Windowson.

Az alábbi táblázat az összes folyamat által használható rendszerosztályokat ismerteti.

Osztály Leírás
Gomb Egy gomb osztálya.
Kombinált mező A kombinált lista osztálya.
Szerkeszt A szerkesztési vezérlő osztálya.
Listamező A listamező osztálya.
MDIClient Az MDI-ügyfélablak osztálya.
Görgetősáv A görgetősáv osztálya.
Statikus A statikus vezérlő osztálya.

 

Az alábbi táblázat azokat a rendszerosztályokat ismerteti, amelyek csak a rendszer számára érhetők el. A teljesség kedvéért itt vannak felsorolva.

Osztály Leírás
ComboLBox A kombó dobozban található lista mező osztálya.
DDEMLEvent A dinamikus adatcsere-kezelési kódtár (DDEML) eseményeinek osztálya.
Üzenet Egy csak üzenetre használható ablak osztálya.
#32768 A menü osztálya.
#32769 Az asztali ablak osztálya.
#32770 Egy párbeszédpanel osztálya.
#32771 A feladatkapcsoló ablak osztálya.
#32772 Az ikoncímek osztálya.

 

Alkalmazás globális osztályai

Az alkalmazás globális osztálya egy végrehajtható vagy DLL által regisztrált ablakosztály, amely a folyamat összes többi modulja számára elérhető. A .dll meghívhatja például a RegisterClassEx függvényt egy olyan ablakosztály regisztrálásához, amely egy egyéni vezérlőt definiál alkalmazás globális osztályként, így a .dll betöltő folyamatok létrehozhatják az egyéni vezérlő példányait.

Ha minden folyamatban használható osztályt szeretne létrehozni, hozza létre az ablakosztályt egy .dll-ban, és töltse be a .dll-et minden folyamatban. A .dll minden folyamatba való betöltéséhez adja hozzá a nevét a AppInit_DLLs értékhez a következő beállításkulcsban:

\ HKEY_LOCAL_MACHINESzoftver\Microsoft\Windows NT\CurrentVersion\Windows

Amikor egy folyamat elindul, a rendszer betölti a megadott .dll-t az újonnan elindított folyamat kontextusában, mielőtt meghívja annak belépési pontját. Az .dll az inicializálási eljárás során regisztrálnia kell az osztályt, és meg kell adnia a CS_GLOBALCLASS stílust. További információ: Osztálystílusok.

Az alkalmazás globális osztályának eltávolításához és a hozzá társított tároló felszabadításához használja a UnregisterClass függvényt.

Alkalmazás helyi osztályai

Az alkalmazás helyi osztálya minden olyan ablakosztály, amelyet egy végrehajtható vagy .dll regisztrál a kizárólagos használatára. Bár tetszőleges számú helyi osztályt regisztrálhat, általában csak egyet regisztrál. Ez az ablakosztály támogatja az alkalmazás főablakának ablakeljárását.

A rendszer megsemmisít egy helyi osztályt, amikor az azt regisztráló modul bezárul. Az alkalmazások a UnregisterClass függvénnyel is eltávolíthatnak egy helyi osztályt, és felszabadíthatják a hozzá tartozó tárterületet.

Hogyan keres a rendszer egy ablakosztályt?

A rendszer a három ablakosztálytípus mindegyikéhez fenntartja a struktúrák listáját. Amikor egy alkalmazás meghívja a CreateWindow vagy a CreateWindowEx függvényt egy adott osztályhoz tartozó ablak létrehozásához, a rendszer az alábbi eljárással keresi meg az osztályt.

  1. Keresse az alkalmazás helyi osztályainak listájában azt az osztályt, amelynek neve meg van adva és amelynek példányleírója megegyezik a modul példányleírójával. (Több modul is használhatja ugyanazt a nevet a helyi osztályok regisztrálásához ugyanabban a folyamatban.)
  2. Ha a név nem szerepel az alkalmazás helyi osztálylistájában, keressen rá az alkalmazás globális osztályainak listájára.
  3. Ha a név nem szerepel az alkalmazás globális osztálylistájában, keresse meg a rendszerosztályok listáját.

Az alkalmazás által létrehozott összes ablak ezt az eljárást használja, beleértve a rendszer által az alkalmazás nevében létrehozott ablakokat is, például a párbeszédpaneleket. A rendszerosztályok felülbírálhatók anélkül, hogy más alkalmazásokat érintenének. Vagyis egy alkalmazás regisztrálhat egy olyan helyi osztályt, amelynek neve megegyezik a rendszerosztály nevével. Ez az alkalmazás kontextusában lecseréli a rendszerosztályt, de nem akadályozza meg, hogy más alkalmazások használják a rendszerosztályt.

Ablakosztály regisztrálása

Az ablakosztály meghatározza az ablak attribútumait, például stílusát, ikonját, kurzorát, menüjét és ablakeljárását. Az ablakosztályok regisztrálásának első lépése egy WNDCLASSEX-struktúra kitöltése az ablakosztály adataival. További információ: Ablakosztály elemei. Ezután adja át a struktúrát a RegisterClassEx függvénynek. További információ: Ablakosztályok használata.

Az alkalmazás globális osztályának regisztrálásához adja meg a CS_GLOBALCLASS stílust a WNDCLASSEX struktúra stílustagjában. Alkalmazás helyi osztályának regisztrálásakor ne adja meg a CS_GLOBALCLASS stílust.

Ha a RegisterClassEx, RegisterClassExA ANSI-verziójával regisztrálja az ablakosztályt, az alkalmazás azt kéri, hogy a rendszer az ANSI-karakterkészlettel adja át az üzenetek szöveges paramétereit a létrehozott osztály ablakainak; ha az osztályt a RegisterClassEx, RegisterClassExW Unicode-verziójával regisztrálja, az alkalmazás kéri, hogy a rendszer a Unicode karakterkészlettel adja át az üzenetek szöveges paramétereit a létrehozott osztály ablakainak. Az IsWindowUnicode függvény lehetővé teszi az alkalmazások számára az egyes ablakok természetének lekérdezését. Az ANSI- és Unicode-függvényekkel kapcsolatos további információkért lásd a függvény prototípusainak konvencióit.

Az osztályt regisztráló végrehajtható vagy DLL az osztály tulajdonosa. A rendszer meghatározza az osztály tulajdonjogát a WNDCLASSEX struktúra hInstance tagjától, amelyet az osztály regisztrálásakor a RegisterClassEx függvénynek ad át. DLL-ek esetén a hInstance tagnak a .dll példány leírójának kell lennie.

Az osztályt nem semmisítik meg, amikor a tulajdonában lévő .dll kipakolják. Ezért ha a rendszer meghívja az adott osztály ablakának ablakeljárását, az hozzáférés-megsértést fog okozni, mert az ablakeljárást tartalmazó .dll már nincs a memóriában. A folyamatnak az osztályt használó összes ablakot el kell pusztítania a .dll eltávolítása előtt, és meg kell hívnia a UnregisterClass függvényt.

Ablakosztály elemei

Az ablakosztály elemei határozzák meg az osztályhoz tartozó ablakok alapértelmezett viselkedését. Az ablakosztályt regisztráló alkalmazás elemeket rendel az osztályhoz úgy, hogy beállítja a megfelelő tagokat egy WNDCLASSEX-struktúrában , és átadja a struktúrát a RegisterClassEx függvénynek. A GetClassInfoEx és a GetClassLong függvény adatokat kér le egy adott ablakosztályról. A SetClassLong függvény módosítja az alkalmazás által már regisztrált helyi vagy globális osztály elemeit.

Bár a teljes ablakosztály sok elemből áll, a rendszer csak egy osztálynevet, az ablakeljárási címet és a példánykezelőt adja meg. A többi elem használatával definiálhatja az osztály ablakainak alapértelmezett attribútumait, például a kurzor alakját és az ablak menüjének tartalmát. A WNDCLASSEX-struktúra nem használt tagjait nullára vagy NULL értékre kell inicializálnia. Az ablakosztály elemei az alábbi táblázatban láthatóak.

Elem Cél
osztálynév Megkülönbözteti az osztályt a többi regisztrált osztálytól.
Ablakeljárás címe Mutasson arra a függvényre, amely az osztály ablakaiba küldött összes üzenetet feldolgozza, és meghatározza az ablak viselkedését.
Példánykezelő Azonosítja az osztályt regisztráló alkalmazást vagy a .dll-t.
Osztálymutató Meghatározza az egérmutatót, amelyet a rendszer az osztály egy ablakához jelenít meg.
osztályikonok Meghatározza a nagy ikont és a kis ikont.
Osztály háttértisztító Meghatározza azt a színt és mintát, amely kitölti az ügyfélterületet az ablak megnyitásakor vagy festésekor.
Osztály menü Megadja az alapértelmezett menüt azokhoz a ablakokhoz, amelyek nem definiálnak explicit módon menüt.
Osztálystílusok Meghatározza, hogyan frissítheti az ablakot az áthelyezés vagy átméretezés után, hogyan dolgozhatja fel az egér dupla kattintásait, hogyan foglalhatja le a helyet az eszközkörnyezet számára, valamint az ablak egyéb aspektusait.
Extra osztálymemória Megadja, hogy a rendszer mennyi extra memóriát foglaljon le bájtban az osztály számára. Az osztály minden ablaka osztozik a többletmemórián, és bármilyen alkalmazás által meghatározott célra használhatja. A rendszer nullára inicializálja ezt a memóriát.
Extra ablakmemória Megadja, hogy a rendszer mennyi extra memóriát foglaljon le bájtban az osztályhoz tartozó minden egyes ablakhoz. A többletmemória bármilyen alkalmazás által meghatározott célra használható. A rendszer nullára inicializálja ezt a memóriát.

 

Osztály neve

Minden ablakosztálynak szüksége van egy osztálynévre , amely megkülönbözteti az egyik osztályt a másiktól. Rendeljen hozzá egy osztálynevet úgy, hogy a WNDCLASSEX struktúra lpszClassName tagját egy nullával lezárt karakterlánc címére állítja, amely megadja a nevet. Mivel az ablakosztályok folyamatspecifikusak, az ablakosztályneveknek csak ugyanazon a folyamaton belül kell egyedinek lenniük. Mivel az osztálynevek helyet foglalnak el a rendszer privát atomtáblájában, az osztálynév-sztringeket a lehető legrövidebben kell tartani.

A GetClassName függvény lekéri annak az osztálynak a nevét, amelyhez egy adott ablak tartozik.

Ablakeljárás címe

Minden osztálynak szüksége van egy ablak-eljáráscímre az osztály összes üzenetének feldolgozásához használt ablakeljárás belépési pontjának meghatározásához. A rendszer akkor továbbítja az üzeneteket az eljárásnak, ha az ablaknak el kell végeznie a feladatokat, például festeni kell az ügyfélterületét, vagy válaszolnia kell a felhasználótól érkező bemenetre. A folyamatok egy osztályhoz rendelnek egy ablakeljárást, ha a címét a WNDCLASSEX struktúra lpfnWndProc tagjára másolja. További információ az ablakkezelési eljárásokról a alatt található.

Példánykezelő

Minden ablakosztályhoz szükség van egy példányleíróra az osztályt regisztráló alkalmazás vagy .dll azonosításához. A rendszer az összes modul nyomon követéséhez példánykezelőkre van szükség. A rendszer minden futó végrehajtható vagy .dllpéldányhoz egy azonosítót rendel.

A rendszer átad egy példánykezelőt az egyes végrehajtható fájlok belépési pont függvényének (lásd : WinMain) és .dll (lásd DllMain). A végrehajtható fájl vagy .dll úgy rendeli hozzá ezt a példánykezelőt az osztályhoz, hogy azt a hInstance tagjába másolja a WNDCLASSEX struktúrában.

Osztálymutató

Az osztálykurzor határozza meg a kurzor alakját, amikor az az osztály egy ablakának ügyfélterületén van. A rendszer automatikusan az adott alakzatra állítja a kurzort, amikor a kurzor belép az ablak ügyfélterületére, és gondoskodik róla, hogy az alakzat megmaradjon, amíg az ügyfélterületen marad. Ha egy kurzoralakzatot egy ablakosztályhoz szeretne rendelni, töltse be az előre definiált kurzoralakzatot a LoadCursor függvénnyel, majd rendelje hozzá a visszaadott kurzorfogópontot a WNDCLASSEX struktúra hCursor tagjához. Másik lehetőségként adjon meg egy egyéni kurzorerőforrást, és a LoadCursor függvénnyel töltse be az alkalmazás erőforrásaiból.

A rendszernek nincs szüksége osztálykurzorra. Ha egy alkalmazás NULL értékre állítja a WNDCLASSEX struktúra hCursor tagját, akkor nincs definiálva osztálykurzor. A rendszer feltételezi, hogy az ablak minden alkalommal beállítja a kurzor alakját, amikor a kurzor az ablakba kerül. Egy ablak beállíthatja a kurzor alakzatát a SetCursor függvény meghívásával, amikor az ablak megkapja a WM_MOUSEMOVE üzenetet. A kurzorokról további információt a Kurzorok című témakörben talál.

Osztályikonok

Az osztályikon egy kép, amelyet a rendszer egy adott osztály ablakának ábrázolására használ. Egy alkalmazásnak két osztályikonja lehet – egy nagy és egy kicsi. A rendszer egy ablak nagy osztályikonját jeleníti meg a feladat-kapcsoló ablakban, amely akkor jelenik meg, amikor a felhasználó lenyomja az ALT+TAB billentyűkombinációt, valamint a tálca és a kezelő nagy ikonnézeteiben. A kis osztály ikon megjelenik egy ablak címsorában, valamint a tálca és a kezelő kis ikonnézeteiben.

Ha nagy és kis ikont szeretne hozzárendelni egy ablakosztályhoz, adja meg az ikonok fogópontját a WNDCLASSEX-struktúrahIcon és hIconSm tagjaiban. Az ikonméreteknek meg kell felelniük a nagy és kis osztályikonok szükséges méreteinek. Nagyméretű osztályikonok esetén a GetSystemMetrics függvény hívásában megadhatja a szükséges dimenziókat a SM_CXICON és SM_CYICON értékek megadásával. Kis osztályikon esetén adja meg a SM_CXSMICON és SM_CYSMICON értékeket. További információ: Ikonok.

Ha egy alkalmazás NULL értékre állítja a WNDCLASSEX struktúra hIcon és hIconSm tagjait, a rendszer az alapértelmezett alkalmazásikont használja az ablakosztály nagy és kis osztályikonjaként. Ha megad egy nagy osztályikont, de nem ad meg kicsit, a rendszer egy kis osztályikont hoz létre a nagy alapján. Ha azonban kis osztályikont ad meg, de nem nagy ikont, akkor a rendszer az alapértelmezett alkalmazásikont használja nagy osztályikonként, a megadott ikont pedig a kisosztály ikonjaként.

A WM_SETICON üzenet használatával felülbírálhatja egy adott ablak nagyméretű vagy kis osztályikonját. A WM_GETICON üzenet használatával lekérheti az aktuális nagy vagy kis osztály ikont.

Osztály háttér ecset

A háttér-ecset osztály előkészíti az ablak kliens-területét az alkalmazás által történő későbbi rajzolásra. A rendszer az kefével kitölti az ügyfélterületet egyszínű vagy mintás színnel, így eltávolítja az összes korábbi képet az adott helyről, függetlenül attól, hogy az ablakhoz tartoznak-e. A rendszer értesíti az ablakot, hogy a hátteret meg kell festeni úgy, hogy elküldi a WM_ERASEBKGND üzenetet az ablaknak. További információért lásd az Ecsetek részt.

Ha háttérkefét szeretne hozzárendelni egy osztályhoz, hozzon létre egy kefét a megfelelő GDI-függvények használatával, és rendelje hozzá a visszaadott ecsetfogópontot a WNDCLASSEX struktúra hbrBackground tagjához.

Ecset létrehozása helyett az alkalmazás beállíthatja a hbrBackground tagot a normál rendszerszínértékek egyikére. A normál rendszer színértékeinek listáját a SetSysColors című témakörben találja.

Normál rendszerszín használatához az alkalmazásnak egyenként kell növelnie a háttérszín értékét. Például COLOR_BACKGROUND + 1 a rendszer háttérszíne. Másik lehetőségként a GetSysColorBrush függvénnyel lekérheti a fogópontot egy szabványos rendszerszínnek megfelelő ecsethez, majd megadhatja a fogópontot a WNDCLASSEX struktúra hbrBackground tagjában.

A rendszer nem követeli meg, hogy egy ablakosztály rendelkezzen osztályháttér ecsettel. Ha ez a paraméter NULL értékre van állítva, az ablaknak saját hátteret kell festenie, amikor megkapja a WM_ERASEBKGND üzenetet.

Osztály menü

Az osztálymenü határozza meg az osztály ablakai által használandó alapértelmezett menüt, ha az ablakok létrehozásakor nincs explicit menü. A menü olyan parancsok listája, amelyekből a felhasználó kiválaszthatja az alkalmazás végrehajtásához szükséges műveleteket.

A WNDCLASSEX struktúra lpszMenuName tagját egy nullával lezárt sztring címére állíthatja be, amely meghatározza a menü erőforrásnevét. A menüt feltételezzük, hogy az adott alkalmazás erőforrása. A rendszer szükség esetén automatikusan betölti a menüt. Ha a menüerőforrást nem név, hanem egész szám azonosítja, az alkalmazás az lpszMenuName tagot az egész számra állíthatja úgy, hogy az érték hozzárendelése előtt alkalmazza a MAKEINTRESOURCE makrót.

A rendszernek nincs szüksége osztálymenüre. Ha egy alkalmazás null értékre állítja a WNDCLASSEX struktúra lpszMenuName tagját, az osztály ablakai nem rendelkeznek menüsávokkal. Még akkor is, ha nincs megadva osztálymenü, az alkalmazás akkor is definiálhat menüsávot egy ablakhoz, amikor létrehozza az ablakot.

Ha egy osztályhoz menüt ad meg, és létrejön az adott osztály gyermekablaka, a menü figyelmen kívül lesz hagyva. További információkért lásd: Menük.

Osztálystílusok

Az osztálystílusok az ablakosztály további elemeit határozzák meg. Két vagy több stílus kombinálható a bitenkénti OR (|) operátorral. Ha stílust szeretne hozzárendelni egy ablakosztályhoz, rendelje hozzá a stílust a WNDCLASSEX struktúra stílustaghoz. Az osztálystílusok listáját az Ablakosztálystílusok című témakörben találja.

Osztályok és eszközkörnyezetek

Az eszközkörnyezet egy speciális értékkészlet, amelyet az alkalmazások az ablakaik ügyfélterületén való rajzoláshoz használnak. A rendszernek szüksége van egy eszközkörnyezetre a kijelző minden ablakához, de némi rugalmasságot biztosít abban, hogy a rendszer hogyan tárolja és kezelje az adott eszközkörnyezetet.

Ha nincs explicit módon megadva eszközkörnyezeti stílus, a rendszer feltételezi, hogy minden ablak a rendszer által fenntartott környezetek készletéből lekért eszközkörnyezetet használ. Ilyen esetekben minden ablaknak le kell kérnie és inicializálnia kell az eszközkörnyezetet a festés előtt, és fel kell szabadítania a festés után.

Annak érdekében, hogy ne kelljen minden alkalommal beolvasni egy eszközkörnyezetet, amikor egy ablakban kell festenie, az alkalmazás megadhatja az ablakosztály CS_OWNDC stílusát. Ez az osztálystílus arra utasítja a rendszert, hogy hozzon létre egy privát eszközkörnyezetet, vagyis egy egyedi eszközkörnyezetet rendel az osztály minden egyes ablakához. Az alkalmazásnak mindössze egyszer kell lekérnie a környezetet, majd a további festésekhez használnia.

Kiváló osztálymemória

A rendszer belső WNDCLASSEX-struktúrát tart fenn a rendszer minden ablakosztályához. Amikor egy alkalmazás regisztrál egy ablakosztályt, arra utasíthatja a rendszert, hogy több további bájtnyi memóriát foglaljon le és fűzjön hozzá a WNDCLASSEX-struktúra végéhez. Ezt a memóriát extra osztálymemóriának nevezzük, és az osztályhoz tartozó összes ablak meg van osztva. A plusz osztálymemória használatával tárolhatja az osztályra vonatkozó információkat.

Mivel a rendszer lokális halmazából van lefoglalva extra memória, az alkalmazásnak takarékosan kell használnia azon osztálymemóriát. A RegisterClassEx függvény meghiúsul, ha a kért extra osztálymemória mennyisége meghaladja a 40 bájtot. Ha egy alkalmazásnak több mint 40 bájtra van szüksége, saját memóriát kell lefoglalnia, és egy mutatót kell tárolnia a memóriához az extra osztály memóriájában.

A SetClassWord és a SetClassLong függvény egy értéket másol a plusz osztálymemóriára. Az extra osztálymemória értékének lekéréséhez használja a GetClassWord és a GetClassLong függvényt. A WNDCLASSEX struktúra cbClsExtra tagja határozza meg a lefoglalni kívánt extra osztálymemória mennyiségét. Egy olyan alkalmazásnak, amely nem használ extra osztálymemóriát, nullára kell inicializálnia a cbClsExtra tagot .

Extra ablakmemória

A rendszer minden ablakhoz belső adatstruktúrát tart fenn. Az ablakosztályok regisztrálásakor az alkalmazások több további bájtnyi memóriát, úgynevezett extra ablakmemóriát adhatnak meg. Az osztály ablakának létrehozásakor a rendszer lefoglalja és hozzáfűzi a megadott mennyiségű extra ablakmemóriát az ablak szerkezetének végéhez. Az alkalmazások ezt a memóriát használhatják az ablakspecifikus adatok tárolására.

Mivel a rendszer helyi halomából extra memória van lefoglalva, az alkalmazásnak takarékosan kell extra ablakmemóriát használnia. A RegisterClassEx függvény meghiúsul, ha a kért extra ablakmemória mennyisége meghaladja a 40 bájtot. Ha egy alkalmazásnak több mint 40 bájtra van szüksége, saját memóriát kell lefoglalnia, és egy mutatót kell tárolnia a memóriához a plusz ablakmemória számára.

A SetWindowLong függvény egy értéket másol a többletmemóriára. A GetWindowLong függvény egy értéket kér le a plusz memóriából. A WNDCLASSEX struktúra cbWndExtra tagja határozza meg a lefoglalni kívánt extra ablakmemória mennyiségét. A memóriát nem használó alkalmazásoknak nullára kell inicializálnia a cbWndExtrát .