Forum: Ders Arası RSS
Gtkd anahtar örneği hatalı çalışıyor
erdem (Moderatör) #1
Üye Tem 2009 tarihinden beri · 959 mesaj · Konum: Eskişehir
Grup üyelikleri: Genel Moderatörler, Üyeler
Profili göster · Bu konuya bağlantı
Konu adı: Gtkd anahtar örneği hatalı çalışıyor
Gtkd ile anahtar örneği yapmaya çalışıyordum. Hatta size de göstereyim.

[Resim: http://erdem.tk/resim/resim/Anahtar örneği.png]

Basitçe anahtar açıldığı zaman

Anahtar açıldı
Anahtar kapatıldı

yazacak. Ama sorun şu ki tek anahtar varken normal çalışıyor. Ama 2 anahtar varken sağdaki doğru çalışıyor. Soldaki anahtar açıldığı zaman hep sağdaki anahtarın durumunu yazıyor. Örneğin sağdaki anahtar açıksa

Anahtar açıldı
Anahtar açıldı

şeklinde yazıyor. Normalde kendi durumunu göstermesini istiyoruz.

import gtk.Main;
import gtk.MainWindow;
import gtk.Box;
import gtk.Switch;
import gobject.ObjectG;
import gobject.ParamSpec;
 
import std.stdio;
 
class Pencere: MainWindow
{
    Box anaKutu;
    Switch anahtar;
 
    this()
    {
        super("Anahtar örneği");
        setBorderWidth(10);
        anaKutu = new Box(Orientation.HORIZONTAL, 6);
        add(anaKutu);
 
        anahtar = new Switch();
 
        // önceden anahtar.addOnNotify(&anahtarAçık) şeklinde çağırıyordum
        anahtar.addOnNotify(delegate void(ParamSpec, ObjectG)
                            {anahtarAçık(ParamSpec, ObjectG, &anahtar);}, "active");
 
        anahtar.setActive(false);
        anaKutu.packStart(anahtar, true, true, 0);
 
        anahtar = new Switch();
        anahtar.addOnNotify(delegate void(ParamSpec, ObjectG)
                            {anahtarAçık(ParamSpec, ObjectG, &anahtar);}, "active");
        anahtar.setActive(true);
        anaKutu.packStart(anahtar, true, true, 0);
 
 
        showAll();
    }
 
    //  "notify::active" olayı
    void anahtarAçık(ParamSpec parametre, ObjectG nesne, Switch * geçerliAnahtar)
    {
        if (parametre.getName() == "active")
        {
            string durum;
            if (geçerliAnahtar.getActive())
                durum = "açıldı";
            else
                durum = "kapatıldı";
           writeln ("Anahtar " ~ durum);
        }
    }
 
    //  "notify::active" olayı
    void anahtarAçık(ParamSpec parametre, ObjectG nesne)
    {
        if (parametre.getName() == "active")
        {
            string durum;
            if (anahtar.getActive())
                durum = "açıldı";
            else
                durum = "kapatıldı";
           writeln ("Anahtar " ~ durum);
        }
    }
}
 
void main(string[] args)
{
    Main.init(args);
    new Pencere();
    Main.run();
}

delegate kullanarak nesnenin adresini göndermeye çalıştım ama gene aynı hata devam ediyor.

Bir de bu şekilde takma isim kullanarak delegate'ı nasıl kullanabiliriz acaba.

alias anahtarAçıldı = delegate void(ParamSpec, ObjectG) {anahtarAçık(ParamSpec, ObjectG, &anahtar);};
erdem (Moderatör) #2
Üye Tem 2009 tarihinden beri · 959 mesaj · Konum: Eskişehir
Grup üyelikleri: Genel Moderatörler, Üyeler
Profili göster · Bu konuya bağlantı
Yeni bir anahtar tanımlayıp adresini gönderince çalıştı!  ;-)
        anahtar2 = new Switch();
        anahtar2.addOnNotify(delegate void(ParamSpec, ObjectG)
                            {anahtarAçık(ParamSpec, ObjectG, &anahtar2);}, "active");
 
        anahtar2.setActive(true);
        anaKutu.packStart(anahtar2, true, true, 0);
acehreli (Moderatör) #3
Kullanıcı başlığı: Ali Çehreli
Üye Haz 2009 tarihinden beri · 4515 mesaj
Grup üyelikleri: Genel Moderatörler, Üyeler
Profili göster · Bu konuya bağlantı
Ha ha! :)

Ben de aşağıdaki tanıma takıldım:
        anahtar.addOnNotify(delegate void(ParamSpec, ObjectG)
                            {anahtarAçık(ParamSpec, ObjectG, &anahtar);}, "active");
Nasıl oluyor da anahtarAçık(ParamSpec, ObjectG, &anahtar); derleniyor ve doğru çalışıyor? Çünkü eğer ParamSpec bir tür ismiyse anahtarAçık'ı nasıl oluyor da bir tür ile çağırabiliyorsun? Eğer oluyorsa, bir derleyici hatası olmalı...

Bence şöyle olmalıydı:
        // 'parametre' ve 'nesne' dedim ve onlarla çağırdım:
        anahtar.addOnNotify(delegate void(ParamSpec parametre, ObjectG nesne)
                            {anahtarAçık(parametre, nesne, &anahtar);}, "active");
Ali
erdem (Moderatör) #4
Üye Tem 2009 tarihinden beri · 959 mesaj · Konum: Eskişehir
Grup üyelikleri: Genel Moderatörler, Üyeler
Profili göster · Bu konuya bağlantı
Evet iki şekilde de çalışıyor. Sizin gösterdiğiniz kod yazım şekli daha temiz gözüktüğü için ben de güncelledim.

gobject.ObjectG.d kütüğündeki addOnNotify işlevinin bildirimi şu şekilde:
    /*
     * Params:
     *     dlg          = The callback.
     *     property     = Set this if you only want to receive the signal for a specific property.
     *     connectFlags = The behavior of the signal's connection.
     */
    void addOnNotify(void delegate(ParamSpec, ObjectG) dlg,
                     string property = "", ConnectFlags connectFlags=cast(ConnectFlags)0)
    {
        /* ... */
    }
acehreli (Moderatör) #5
Kullanıcı başlığı: Ali Çehreli
Üye Haz 2009 tarihinden beri · 4515 mesaj
Grup üyelikleri: Genel Moderatörler, Üyeler
Profili göster · Bu konuya bağlantı
Ah anladım! :) addOnNotify'a verdiğin delegate'in parametre listesindeki ParamSpec ve ObjectG tür ismi değil, değişken ismi çünkü delegate tanımında tür ismi yazmak isteğe bağlıdır. Derleyici ParamSpec ve ObjectG görünce onları yerel değişken isimleri olarak kabul ediyor ve sen de zaten öyle kullanıyorsun.

Okuyanın kafasını karıştırmak için süper! :)

Ali
acehreli (Moderatör) #6
Kullanıcı başlığı: Ali Çehreli
Üye Haz 2009 tarihinden beri · 4515 mesaj
Grup üyelikleri: Genel Moderatörler, Üyeler
Profili göster · Bu konuya bağlantı
Bu arada, kimse isimsiz işlevleri öyle uzun tanımıyla yazmıyor. Belki de o yüzden bu karışıklık hiç benim başıma gelmedi. Şu yeterli ve çok daha okunaklı:
        anahtar.addOnNotify((parametre, nesne)
                            {anahtarAçık(parametre, nesne, &anahtar);}, "active");

Çok hoşuma gitti ve İngilizce foruma da yazdım:

  http://forum.dlang.org/post/o50nlb$1vd6$1@digitalmars.com

Ali
erdem (Moderatör) #7
Üye Tem 2009 tarihinden beri · 959 mesaj · Konum: Eskişehir
Grup üyelikleri: Genel Moderatörler, Üyeler
Profili göster · Bu konuya bağlantı
Bu konuya benzer bir durum gene karşıma çıktı.
import gtk.Ana;
import gtk.Pencere;
import gdk.Olay;
import gtk.GörselBileşen;
 
 
bool çıkış(Olay olay, GörselBileşen görselBileşen)
{
    görselBileşen.yoket();
    Ana.çıkış();
    return false;
}
 
void main(string[] seçenekler)
{
    Ana.ilklendir(seçenekler);
    auto pencere = new Pencere("Merhaba Dünya");
    pencere.tümünüGöster();
    pencere.silindiğinde(delegate bool(Olay olay, GörselBileşen görselBileşen)
    {
        görselBileşen.yoket();
        Ana.çıkış();
        return false;
    });
 
    /*
      Bu yöntem çalışmıyor
 
    pencere.silindiğinde(&çıkış);
 
    */
 
    /*
      Bu yöntem de çalışmıyor
 
    pencere.silindiğinde( & Ana.çıkış());
 
    */
 
    /*
      Kısayol yöntemi de çalışmıyor
 
     pencere.silindiğinde((olay, görselBileşen) { çıkış(olay, görselBileşen);});
 
    */
 
 
    Ana.çalıştır();
}

Bu yöntemlerden ilk yöntem bir sınıf içinde olduğu zaman çalışıyordu. Örneğin:

class Pencere: AnaPencere
{
    /*  ... */
    this()
    {
        this.silindiğinde(&çıkış);
        /* ... */
 
    }
 
    bool çıkış(Olay olay, GörselBileşen görselBileşen)
    {
        görselBileşen.yoket();
        Ana.çıkış();
        return false;
 
    }
}
 
void main(string[] çorbalar)
{
    Ana.ilklendir(çorbalar);
    auto pencere = new Pencere();
    Ana.çalıştır();
}

Üçüncü yöntemle daha önce konuştuğumuz kısayol yöntemini denedim o da olmadı.

Basitçe ikinci yöntemle aşağıdaki gibi çağırmak istediğim zaman ise

    pencere.silindiğinde( & Ana.çıkış());

Error: quit() is not an lvalue şeklinde bir hata iletisi alıyorum.
erdem (Moderatör) #8
Üye Tem 2009 tarihinden beri · 959 mesaj · Konum: Eskişehir
Grup üyelikleri: Genel Moderatörler, Üyeler
Profili göster · Bu konuya bağlantı
erdem:
Basitçe ikinci yöntemle aşağıdaki gibi çağırmak istediğim zaman ise

    pencere.silindiğinde( & Ana.çıkış());

Error: quit() is not an lvalue şeklinde bir hata iletisi alıyorum.

Bu örneği

    pencere.silindiğinde( delegate bool(olay, görselBileşen){ Ana.çıkış(); return false;});

şeklinde çalıştırabildim. Burada normal işlev kullanabilir miydik acaba.
acehreli (Moderatör) #9
Kullanıcı başlığı: Ali Çehreli
Üye Haz 2009 tarihinden beri · 4515 mesaj
Grup üyelikleri: Genel Moderatörler, Üyeler
Profili göster · Bu konuya bağlantı
delegate istiyorlar ama senin işlev yalnızca bir function. Sanırım tam toDelegate'e göre bir durum:

  http://dlang.org/phobos/std_functional.html#toDelegate
    pencere.silindiğinde(toDelegate(&çıkış));
Ali
erdem (Moderatör) #10
Üye Tem 2009 tarihinden beri · 959 mesaj · Konum: Eskişehir
Grup üyelikleri: Genel Moderatörler, Üyeler
Profili göster · Bu konuya bağlantı
Teşekkürler şimdi kullanabildim.
import gtk.Ana;
import gtk.Pencere;
import std.functional;
import gdk.Olay;
import gtk.GörselBileşen;
 
bool çıkış(Olay olay, GörselBileşen görselBileşen)
{
    Ana.çıkış();
    return false;
}
 
void main(string[] değişkenler)
{
    Ana.ilklendir(değişkenler);
    auto pencere = new Pencere("Basit örnek");
    pencere.tümünüGöster();
    pencere.silindiğinde(toDelegate(&çıkış));
    Ana.çalıştır();
}

Herhalde bir sınıfın üye işlevini çağıramayızdır değil mi.

   pencere.silindiğinde(toDelegate(&Ana.çıkış));

Bu şekilde kullanımda derleyici olay ve görsel bileşeni değişke olarak alan ve bool döndüren bir delegate bekliyor bizden anladığım kadarıyla.
acehreli (Moderatör) #11
Kullanıcı başlığı: Ali Çehreli
Üye Haz 2009 tarihinden beri · 4515 mesaj
Grup üyelikleri: Genel Moderatörler, Üyeler
Profili göster · Bu konuya bağlantı
erdem:
Herhalde bir sınıfın üye işlevini çağıramayızdır değil mi.

Bir üye işlevi çağırabiliriz ama delegate olabilmesi için ortada öncelikle bir nesne olması gerekir. Ek olarak, tabii sen static olmayan üye işlevleri düşünerek sormuş olmalısın. Yoksa, static üye işlevler de serbest işlevler gibi kullanılabilirler (toDelegate gerekir).
import std.functional;
 
void foo(void delegate(int) dg) {
}
 
void serbestİşlev(int) {
}
 
struct S {
    void üyeİşlev(int) {
    }
 
    static void staticÜyeİşlev(int) {
    }
}
 
void main() {
    foo(toDelegate(&serbestİşlev));
    foo((i) {});
 
    S s;
    foo(&s.üyeİşlev);
    foo(toDelegate(&S.staticÜyeİşlev);
}
Ali
Doğrulama Kodu: VeriCode Lütfen resimde gördüğünüz doğrulama kodunu girin:
İfadeler: :-) ;-) :-D :-p :blush: :cool: :rolleyes: :huh: :-/ <_< :-( :'( :#: :scared: 8-( :nuts: :-O
Özel Karakterler:
Forum: Ders Arası RSS
Bağlı değilsiniz. · Şifremi unuttum · ÜYELİK
This board is powered by the Unclassified NewsBoard software, 20100516-dev, © 2003-10 by Yves Goergen
Şu an: 2017-10-23, 15:32:11 (UTC -07:00)