seo standart penceresi

2 Temmuz 2013 Salı Unknown 0 yorum

Standart Dialog Pencereleri


işletim
            Her Windows programında gördüğümüz Open, Save, Find-Replace, Color, Font, Print gibi dialog pencereleri tek bir API fonksiyonuyla oluşturulabilen standart dialog pencereleridir.

Open ve Save Dialog Pencereleri


            Open ve Save dialog pencereleri hemen hemen birbirlerinin aynısıdır. Open penceresi dosya açmak, Save penceresi saklamak amacıyla kullanılır. Open dialog penceresi GetOpenFileName API fonksiypnuyla, Save dialog penceresi ise GetSaveFileName API fonksiyonuyla yaratılır. Bu dialog pencereleri ilgili API fonksiyonlarıyla yaratıldıktan sonra kullanıcı bir dosya seçerek OK tuşuna basar(Dosya ismi klavyeyle de yazılabilir). Böylece fonksiyon sonlanır. Programcı seçilen dosyanın ismini elde eder. Bu iki API fonksiyonu da OPENFILENAME isimli bir yapı değişkeninin adresini alır. OPENFILENAME yapısının elemanları genel olarak ikisi dışında bu dialog penceresini konfigüre etmek amacıyla kullanılır. Ancak iki eleman bu API fonksiyonları tarafından doldurulur. Seçilmiş dosyanın isim ve path ifadesi bu iki elemana yazılır. Bu API fonksiyonlarının geri dönüş değerleri FALSE ise kullanıcı dialog penceresini cancel ile kapatmıştır, TRUE ise ok ile kapatmıştır. OPENFILENAME yapısının lpstrFilter elamanı Open ve Save pencerelerinde çıkan filtreleme bilgilerini barındırır. Her filtre elemanı iki parçadan oluşur. Birinci parça yazı parçasıdır, ikinci parça filtreleme bilgisini tutar.


Pencere Başlık Yazısının Değiştirilmesi

            Pencere başlığı üzerinde işlem yapan iki fonksiyon vardır: GetWindowText ve SetWindowText. SetWindowText fonksiyonu CreateWindow fonksiyonunun ikinci parametresiyle belirtilen pencere başlığı yazısının değiştirilmesini sağlar.

BOOL SetWindowText(HWND hWnd, LPCSTR lpString);

Bu fonksiyon pushbutton penceresine uygulanırsa düğme üzerindeki yazının değiştirilmesine, editbox penceresine uygulanırsa editbox içerisindeki yazının değiştirilmesine, static penceresine uygulanırsa static pencere yazısının değiştirilmesine yol açar.
            GetWindowText fonksiyonu bunun tam tersi olarak pencere başlık yazısının elde edilmesinde kullanılır.

BOOL GetWindowText(HWND hWnd, LPSTR lpString, int nMaxCount);

            Bu fonksiyonlara ek olarak üst pencerenin handle değeri ve alt pencerenin ID değerleri bilindiğinde alt pencerenin pencere başlığı üzerinde işlem yapan SetDlgItemText ve GetDlgItemText fonksiyonları da vardır. Tabii bu fonksiyonlar kendi içlerinde GetDlgItem ve SetWindowText, GetWindowText fonksiylarını kullanarak işlem yaparlar.

OPENFILENAME Yapısının Önemli Elemanları


            Bu yapının ilk elemanı olan lStructSize elemanı yapının byte uzunluğunu tutmalıdır. hwndOwner elemanı standart dialog penceresini açan üst pencerenin handle değerini tutar. hInstance elemanına programın hInstance değeri girilmelidir. Bu yapının en önemli elemanlarından birisi lpstrFilter elemanıdır. Bu eleman birden fazla yazıyı tutan bir gösterici biçimindedir. C'de char türünden bir göstericinin birden fazla yazıyı tutabilmesi şöyle mümkün olabilir: Her yazının sonu NULL karakter ile bitirilir, tüm yazının bittiği ise iki NULL karakter kullanılarak anlatılır. lpstrFilter elemanı filtre yazılarını tutar. Her filtre elemanı iki yazıdan oluşmaktadır. Bu yazının ilki filtreleme sırasında çıkacak yazıyı belirtit ve filtreleme üzerinde bir etkisi yoktur. İkinci yazı filtrelemeye ilişkin yazıdır. Birden fazla filtreleme için ; koymak gerekir. Örnek:

x.lpstrFilter = "Executable Files\0*.exe;*.com\0Text Files\*.txt\0";

Seçim yapıldıktan sonra elde edilen dosya ismi bu API fonksiyonları tarafından lpstrFileTitle elemanının gösterdiği adrese yerleştirilir. Yani fonksiyon çağırılmadan önce bu elemanın tahsis edilmiş bir diziyi göstermesi gerekir. nMaxFileTitle elemanı ise bu dizinin en büyük uzunluğunu belirtmektedir. Bu eleman dosya ismini path ifadesi olmadan yalnızca isim biçiminde tutar. Tabii dosyanın uzantısı da alınmaktadır. Yapının lpstrInitialDir elemanı dialog penceresinin default hangi dizin için açılacağını belirtir. Seçilen dosyanın ismi tüm path bilgisiyle birlikte lpstrFile elemanının gösterdiği adrese yerleştirilir. Bu elemanın gösterdiği yazının maksimum elemanın nMaxFile elemanında saklanmalıdır.



Örnek Programın Açıklaması


            Örnek programda bir menü alınmış, menüye Open, Save ve Exit elemanları yerleştirilmiştir. Sembolik sabitleri ID_FILE_OPENX, ID_FILE_SAVEX, ID_FILE_EXITX.

Checkbox ve Radiobutton Kontrolleri


            Checkbox küçük bir kare ve yanında yazı bulunan bitr konroldür. Genellikle dialog pencerelerinin içerisinde kullanılır. Üzerine click yapıldığında içi çarpılanır. Genellikle bir özelliği dahil etmek ya da kaldırmak amacıyla kullanılır. Bu kontrolden elde edilecek bilgi kontrolün çarpılanıp çarpılanmadığıdır. Checkbox kontrolü CreateWindow fonksiyonunda "button" sınıf ismi girilerek yaratılır. Ancak pencere biçimi olarak BS_CHECKBOX girilir.

hCheckBox = CreateWindow("button", "Example", WS_CHILD | WS_VISIBLE | BS_CHEKBOX.....);

CreateWindow fonksiyonunun ikinci parametresinde belirtilen pencere başlık yazısı kare görüntüsünün yanında çıkar. Checkbox'lar otomatik, normal ve üç konumlu omlak üzere üçe ayrılırlar. Checkbox kontrolüne çarpı koyabilmek için BM_SETCHECK mesajı gönderilir. Bu mesajda lParam 0 alınır, wParam 1 ya da 0 olabilir. 1 çarpılama oluşacağını, 0 oluşmayacağını belirtir.

SendMessage(hCheckBox, BM_SETCHECKBOX, 1, 0);

Checkbox kontrolünün çarpılanıp çarpılanmadığını BM_GETCHECK mesajı ile elde edebiliriz. Bu mesajda wParam ve lParam 0 girilir. Fonksiyonun geri dönüş değeri 0 ya da 1 olur. 1 çarpılı, 0 çarpısız anlamına gelir.

status = SendMessage(jhCheckBox, BM_GETCHECK, 0, 0);

Checkbox kontrolü üzerine click yapıldığında tıpkı pushbutton kontrolünde olduğu gibi checkbox kontrolü WM_COMMAND mesajı ile BN_CLICKED durum kodu ile çağırılır. Normal checkbox'larda kontrolün üzerine click yapıldığında çarpılama işlemi kontrolün kendisi tarafından değil, gönderilen mesaj ile programcı tarafından yapılır. Normal checkbox'larda çarpılama işlemi aşağıdaki gibi yapılabilir.

case WM_COMMAND:
                switch(LOWORD(wPAram)) {
                               case ID_CHECK:
                                               if (HIWORD(wParam) == BN_CLICKED) {
                                                               if (SendMessage(hCheckBox, BM_GETCHECK, 0, 0))
                                                                              SendMessage(hCheckBox, BM_SETCHECK, 0, 0);
                                                               else
                                                                              SendMessage(hCheckBox, BM_SETCHECK, 1, 0);
                                               }
                               break;
                }

Oysa otomatik checkbox kontrolünde çarpılama işlemi kontrolünden kendisi tarafından zaten yapılmaktadır. Otomatik checkbox yaratabilmek için BS_CHECKBOX yerine BS_AUTOCHECKBOX pencere biçimi kullanılır. Checkbox genellikle dialog pencerelerinde kullanılır. Dialog penceresi ilk görüntülendiğinde çarpılanmış bir görüntü elde edebilmek için WM_INITDIALOG mesajında çarpılama işleminin bilinçli bir şekilde yapılması gerekir.

case WM_INITDIALOG:
                SendDlgItemMessage(hWnd, ID_CHECK, BM_SETCHECK, 1, 0);
                return TRUE;

Üç konumlu checkbox kontrolünde checkbox'ın 3 durumu vardır: Çarpılı, çarpısız ve etkin omayan durum. Bu chackbox kontrolü pencere biçimine ek olarak BS_3STATE eklenerek yaratılırlar. Otomatik ve üç konumlu chackbox kontrolleri Win32 sistemleriyle eklenmiştir.
            Radiobutton kontrolü dairesel bir şeklin içerisine noktasal bir şeklin yerleştirilmesine olanak sağlar. Genellikle bir grup radiobutton kontrolü biçiminde kullanılır. Genellikle radiobutton kontrollerinin bir anda yalnızca bir tanesi seçili olacak biçimde kullanılır. Uygulamada birden fazla seçenekten yalnızca bir tanesinin seçilmesi gerektiği durumlarda kullanılır. Checkbox kontrolleri tek başlarına kullanılabilir, ancak radiobutton kontrolleri grup olarak kullanılmalıdır. Bu kontrolün yanında tıpkı checkbox'ta olduğu gibi betimleyici bir yazı vardır. Bir grup içerisindeki bütün radiobutton kontrolleri tek tek CreateWindow fonksiyonuyla yaratılmalıdır. Radiobutton kontrolleri normal ve otomatik olmak üzere iki kısma ayrılırlar. Otomatik radiobutton kontrolleri Win32 sistemleriyle tanımlanmıştır. Bu kontrolü yaratabilmek için CreateWindow fonksiyonu içerisinde sınıf ismi olarak "button" girmek, pencere biçimi olarak BS_RADIOBUTTON ya da BS_AUTORADIOBUTTON vermek gerekir. Pencere başlık yazısı betimleyici yazı olarak görünür. Bu kontrol ana pencerenin içerisine gömülmek yerine genellikle dialog pencerelerinde kullanılır. Radiobutton kontrolünün üzerine click yapıldığında kontrol üst pencereye BN_CLICKED durum koduyla mesaj gönderir. Radiobutton kontrolünü çarpılamak için checkbox'ta yapıldığı gibi BM_SETCHECK mesajı gönderilir.

SendMessage(hRadioButton, BM_SETCHECK, 1, 0);

Bu kontrolün çarpılanıp çarpılanmadığı BM_GETCHECK mesajı ile sorgulanabilir.

status = SendMessage(hRadioButton, BM_GETCHECK, 0, 0);


Normal radiobutton'larda bir grup kontrolden bir tanesine click yapıldığında click yapılanı çarpılamak, çarpılı olanı silmek programcının görevidir. Autoradiobutton yalnızca dialog pencerelerinde kullanılır. Bunun için bir radiobutton grubu tanımlanması gerekir. Bu grup kaynak içerisinde tanımlanabilmektedir. Autoradiobutton grubunda bir kontrole click yapıldığında click yapılan otomatik olarak çarpılanır. Çarpılanmış olan da otomatik olarak silinir. Normal radiobutton'larda çarpılama işlemi birkaç biçimde yapılabilir:






case WM_COMMAND:
                switch(LOWORD(wParam)) {
                               case ID_RADIO1:
                                               ......
                                               ......
                                               ......
                               case ID_RADIO2:
                                               ......
                                               ......
                                               ......
                               case ID_RADIO3:
                                               ......
                                               ......
                                               ......
                }
                break;

yada daha sistematik bir yöntem kullanılabilir:

struct CBOX {
                WORD id;
                int status;
} x[4] = {{ID_RADIO1, 0}, {ID_RADIO2, 1}, {ID_RADIO3, 0}, {ID_RADIO4, 0}};

switch (LOWORD(wParam)) {
                case ID_RADIO1:
                case ID_RADIO2:
                case ID_RADIO3:
                case ID_RADIO4:
                               ProcessCheck(LOWORD(wParam));
                               break;
}

void ProcessCheck(WORD id)
{
                int i;
                HWND hRadio;

                for (i = 0; i < 4; ++i) {
                               if(x[i].status == 1) {
                                               x[i].status = 0;
                                               hRadio = GetDlgItem(hWnd, x[i].id);
                                               SendMessage(hRadio, BM_SETCHECK, 0, 0);
                               }
                               if (x[i].id == id) {
                                               x[i].status = 1;
                                               hRadio = GetDlgItem(hWnd, id);
                                               SendMessage(hRadio, BM_SETCHECK, 1, 0);
                               }
                }
}

            Örnek programda iki radiobutton dialogh penceresi üzerine çıkartılmış ve durumları elde edilmiştir. İster auto, ister normal olsun bir grup içerisindeki hangi radiobutton'ın çarpılanmış olduğunu anlamak için bir sorgulama yapılması gerekir. En pratik yöntem hepsine BM_GETCHECK mesajı göndermek ve hangisi çarpılanmışsa onu tespit etmek olabilir.
            Autoradiobutton'larda radiobutton grubunun tespit edilmesi WS_GROUP pencere biçimiyle yapılmaktadır. Dialog kaynağında radiobutton kontrolü RADIOBUTTON ismiyle yaratılır. Kaynakta ilk WS_GROUP pencere biçimine sahip radiobutton grubun ilk elemanı kabul edilir. Bundan sonraki radiobutton kontrolleri grup içerisindedir. Bir sonraki WS_GROUP pencere biçimli radiobutton kontrolüne kadarki tüm radiobutton kontrolleri bu grup içinde kabul edilir.

Çizim İşlemleri


            Bir pencerenin üzerine doığrudan yazısal ya da grafiksel çizimler yapılabilir. Pencerenin üzerine yazı yazma işlemi de bir çeşit çizim işlemi olarak değerlendirilir. Aslında static kontrolünü kullanarak yazı yazılması durumunda da bir çeşit çizim işlemi yapılmaktadır. Ancak burada çizim işlemini static kontrolünün pencere fonksiyonu yapar. Oysa bir yazı yazmak için bir alt pencerenin tanımlanması gerekmez. Bir pencere içerisinde yapılan çizim Windows tarafından otomatik olarak saklanmaz. Örneğin bir pencere başka bir pencere tarafından kapatıldığında Windows kapatılan pencere içerisindeki çizim görüntüsünü saklamaz. Bu görüntünün, yani bütün pencere çizimlerinin yeniden programcı tarafından yapılması gerekir. Windows bir pencerenin bir bölümü herhangi bir biçiminde kapatıldığında ya da açıldığında o pencere için mesaj kuyruğuna WM_PAINT mesajını bırakır. Bu durumda pencere içerisindeki bütün mesajlar WM_PAINT mesajı içerisinde yapılmalıdır. WM_PAINT mesajı şu durumlarda gönderilir:

1. Pencerenin boyutları değiştirildiğinde,
2. Bir pencereyi kaplamış olan başka bir pencerenin çekilmesi durumunda,

WM_PAINT şu durumlarda gönderilmez:

1. Bir menünün açılmasıyla ve kapatılmasıyla oluşan durumda Windows pencere görüntüsünü otomatik olarak saklar, WM_PAINT mesajını göndermez.
2. Bir pencere taşındığında Windows pencere görüntüsünü otomatik olarak oluşturur.

Pencere Çizimleri Nerede Yapılamalıdır?


            Windows pencere çizim görüntülerini otomatik olarak saklamadığı için pencere görüntüsünün her değişiminde yani her WM_PAINT mesajı geldiğinde bütün çizimler yeniden yapılmalıdır. Bu durumda bütün çizimler WM_PAINT mesajı içerisinde yapılmalıdır. Eğer çizimler başka yerde yapılırsa pencere görüntüsünün değişiminde başka yerde yapılan çizimler kaybolur.

Pencere Güncelleme Alanı(Window Update Region)

            Bir pencerenin yeniden çizilmesi gereken en küçük dikdörtgensel alanına güncelleme alanı denir. Güncelleme alanı dikdörtgensel olmak zorundadır. Pencere

içerisindeki görüntüyü yeniden oluşturmak için yalnızca güncelleme alanı içerisindeki bölümün yeniden çizilmesi yeterlidir. Üçgensel bir bölge ya da dairesel bir bölge güncelleme alanı olamaz. Windows bu bölgelere ilişkin en küçük dikdörtgeni hesap ederek güncelleme alanı yapar. Windows her pencere için bir günceleme alanının koordinat bilgisini tutmaktadır. Tabii Windows her pencere için tek pencere alanı tutar ve bunu sürekli güncelleştirir. Örneğin bir pencerenin boyutu değiştirildiğinde güncelleme alanı tüm pencere olur. Bir pencerenin güncelleme alanının koordinat bilgisi bir API fonksiyonu yardımıyla sistemden alınabilir. Güncelleme alanı boş küme ise  pencerenin hiçbir bölgesinin yeniden çizilmesine gerek yoktur. Güncelleme alanının boş küme yapılması Windows tarafından otomatik bir biçimde yapılmaz. Windows güncelleme alanını gerektiğinde güncelleştirir. Örneğin daraltp genişletebilir. Ancak boş küme yapmaz. Windows bütün pencerelerin güncelleme alanlarına periyodik olarak bakar, güncelleme alanı boş küme olmayan bir pencere alanıyla karşılaştığında ona WM_PAINT mesajını gönderir. Bu mesajı göndermesiyle kendisi güncelleme alanını ototatik olarak boş küme yapmaz. Güncelleme alanı programcı tarafından boş küme yapılmalıdır. Güncelleme alanının boş küme yapılması için en iyi yer WM_PAINT mesajının içidir. Yani sonuç olarak eğer WM_PAINT içerisinde güncelleme alanı boş küme yapılmazsa pencereye sürekli WM_PAINT mesajı gönderilir, program da sürekli ,çiizm yapan bir biçimde çalışır ve performans kaybı olur(Aslında Windows yeni güncelleme alanı eski güncelleme alanının içerisinde kalıyorsa güncelleme alanını güncellemez).

0 yorum: