Çok Yakında Yeni Bir Arayüzle karşınızdayız! http://yeni.delphican.com/

Konuyu Oyla:
  • Derecelendirme: 4/5 - 1 oy
  • 1
  • 2
  • 3
  • 4
  • 5
Kalıtılmış Formu Değişkende Tutarak Dinamik Create Etmek
#1
Arkadaşlar Merhaba;
Bir sorum olucak.Açıklamaya çalışayım.Ancak eğer yeterince açık olmazsa diye örnek bir küçük projeyide paylaşıyor olacağım.

Şimdi

1 Adet BaseList Formum var.
1 Adette BaseEdit Formum var.
      
Sonra bunlardan onlarca Form türeteceğim.

Örneğin 
BaseListten   CariList,KasaList,HesapHareketList,........ gibi gibi giden.
BaseEditten    CariEdit,KasaEdit,HesapHareketEdit,........ gibi gibi giden.

Şimdi türetmiş olduğum child bir form olan CariList üzerine aldığım bir butonun clickine aşağıda ki kodu yazarsam CariEdit formu create der ve gösteririm.

Application.CreateForm(TFrmCariEditForm,FrmCariEditForm);
FrmCariEditForm.ShowModal;


Ancak bunun için her türettiğim XXXListForma bu kodu yazmam gerekir.

Oysa ben ata form olan BaseList Forma bir button koymalı ve onun clickine bir kod yazmalıyım.Sonra türettiğim form hangi alanla ilgili ListForm ise o alanla ilgili EditFormu açmalı,
bu türettiğim ListFormda yukarıdaki kodu tekrar tekrar yazmamalıyım.

Bunu şu şekilde çözmeye çalıştım.

BaseList Formda public blokta şöyle bir değişken tanımladım.

  MyEditForm:TFrmBaseEditForm;


Sonra BaseList Formdaki EditFormu açtırmak istediğim butonun clcikine aşağıdaki kodu yazdım.

Application.CreateForm(TFrmBaseEditForm,MyEditForm);
MyEditForm.ShowModal;

Sonrada türettiğim her ListFormda bu yukarıda tanımladığım MyEditForm değişkenini alakalı EditFormla set ediyorum.

Örnek CariList formda şu şekilde set ediyorum.

 MyEditForm:=FrmCariEditForm;


Ancak bu atamaya rağmen CariList formdaki click eventindeki inherit cod CariEdit formu create etmek yerine BaseEdit formu create ediyor.
Aşağıdaki gibi.


M14RkM.png


Oysa olmaısnı istediğim görüntü aşağıdaki gibi:

QPGyQj.png



Hatalı kod yazdığımın farkındayım.Bu şekilde çalışmaması gayet doğal.Ancak bu yapmak istediğimi nasıl yapabilirm.
Yardımcı olacak arkadaşlara şimdiden teşekkürler....


Örnek Projeyide daha net olması açısından paylaşıyorum.

Linkleri Görebilmeniz İçin Üye Olmanız Gerekiyor. Üye Olabilmek İçin Lütfen Buraya Tıklayınız.


Ek Dosyalar
.zip   Project1.zip (Dosya Boyutu: 8,8 KB / İndirme Sayısı: 5)
Cevapla
#2
create metodu virtual tanimlanmis bir metod değildir.
o nedenle create dediğinizde MyEditForm ' un turu ne ise (örnekte TFrmBaseEditForm) o turden bir nesne oluşturur.

MyEditForm:=FrmCariEditForm; yerine  MyEditForm:=TFrmCariEditForm.create(self); derseniz istediğiniz olacaktır.

aşağıdaki makaleye gözatarsanız statik , dinamik , virtual metodların nasıl çalıştığı daha iyi anlaşılabilir.

Linkleri Görebilmeniz İçin Üye Olmanız Gerekiyor. Üye Olabilmek İçin Lütfen Buraya Tıklayınız.
WWW
Cevapla
#3
Merhaba,

İstediğiniz işlemi yapmak için aşağıdaki değişiklikleri yapmanız gerekiyor:
BaseListForm.pas dosyasına aşağıdaki tanımı ekleyin:

type
  // Aşağıdaki satır eklenecek
  TfrmBaseListFormClass = class of TFrmBaseListForm;

  TFrmBaseListForm = class(TForm)
  ...

Kullanıma örnek olsun diye de ana formdaki Button1.Click kodunu aşağıdaki gibi değiştirin:
procedure TFrmAna.Button1Click(Sender: TObject);
var
  FormClass: TfrmBaseListFormClass;
  BaseListForm: TFrmBaseListForm;
begin
  FormClass := TFrmCariListForm;

  Application.CreateForm(FormClass, BaseListForm);
  BaseListForm.ShowModal;
end;

Aynı işlemi edit sınıfları için de yapabilirsiniz.

Eğer formun sınıfını da run-time'da bulmak istiyorsanız o zaman FindClass kullanmanız gerekiyor, ama FindClass ile sınıfı bulabilmeniz için önce RegisterClass ile register etmelisiniz. Bunun için de benim tavsiyem sınıfın yazıldığı unit'in initialization kısmında yapmanızdır. Ama ben FindClass kullanmanızı tavsiye etmem, sonradan değişiklik yapması zor oluyor ve projede çalışan programcılar değiştikçe hatalar çıkmaya başlıyor.

İyi çalışmalar
Cevapla
#4
Yanlış anlamadıysam
Normal bir şekilde form oluşturun. üstüne 3 5 buton atın bişeyler yapın, adını BaseListForm koyun, kaydedin.
Daha sonra Araba listesi yapmak istiyorsanız. Editörden New Items tıklayın. Soldaki sekmelerden Inharitable Items'a gelin BaseListForm u seçin. BaseListForm türünde yeni bir form oluşacak.
Onada ArabaListeForm adını verin ozelleştirin. Daha sonra kullanacağınız yerde ArabaListeForm create edip kullanın.
Cevapla
#5
(11-10-2019, Saat: 15:32)sadettinpolat Adlı Kullanıcıdan Alıntı: Linkleri Görebilmeniz İçin Üye Olmanız Gerekiyor. Üye Olabilmek İçin Lütfen Buraya Tıklayınız.create metodu virtual tanimlanmis bir metod değildir.
o nedenle create dediğinizde MyEditForm ' un turu ne ise (örnekte TFrmBaseEditForm) o turden bir nesne oluşturur.

MyEditForm:=FrmCariEditForm; yerine  MyEditForm:=TFrmCariEditForm.create(self); derseniz istediğiniz olacaktır.

aşağıdaki makaleye gözatarsanız statik , dinamik , virtual metodların nasıl çalıştığı daha iyi anlaşılabilir.

Linkleri Görebilmeniz İçin Üye Olmanız Gerekiyor. Üye Olabilmek İçin Lütfen Buraya Tıklayınız.

Çok teşekkürler.Bu söylediğiniz şekilde yaptığımda bellekte CariEditForm un varlığını kontrol ettiğimde form açık olmasına rağmen Free ve Nil olarak görünüyor.
Tekrar şartlı create yaptığımda (Başka bir yerden) , şöyleki  Assigned(FrmCariEditForm) False veya FrmCariEditForm=nil  ise true dönüyor ve dolayısıyla bir CariEdit form daha create oluyor ve adıda FrmCariEditForm_1 oluyor. Ama tekrar bir daha bu kontrolü yaptığımda ise ancak o zaman Assigned(FrmCariEditForm) True veya FrmCariEditForm=nil  ise False dönüyor ve üçüncü kez CariEditForm create olayını, yani FrmCariEditForm_2 oluşmasını  engelleyebiliyorum.
Bunun neden olduğunu anlayamadım ancak aslında yapmak istediğim olay sanırım  Bahadır Alkaç arkadaşımız önermiş.
Deneyip bilgi vereceğim.
Çok teşekkürler....

(11-10-2019, Saat: 15:45)Bahadir.Alkac Adlı Kullanıcıdan Alıntı: Linkleri Görebilmeniz İçin Üye Olmanız Gerekiyor. Üye Olabilmek İçin Lütfen Buraya Tıklayınız.Merhaba,

İstediğiniz işlemi yapmak için aşağıdaki değişiklikleri yapmanız gerekiyor:
BaseListForm.pas dosyasına aşağıdaki tanımı ekleyin:

type
  // Aşağıdaki satır eklenecek
  TfrmBaseListFormClass = class of TFrmBaseListForm;

  TFrmBaseListForm = class(TForm)
  ...

Kullanıma örnek olsun diye de ana formdaki Button1.Click kodunu aşağıdaki gibi değiştirin:
procedure TFrmAna.Button1Click(Sender: TObject);
var
  FormClass: TfrmBaseListFormClass;
  BaseListForm: TFrmBaseListForm;
begin
  FormClass := TFrmCariListForm;

  Application.CreateForm(FormClass, BaseListForm);
  BaseListForm.ShowModal;
end;

Aynı işlemi edit sınıfları için de yapabilirsiniz.

Eğer formun sınıfını da run-time'da bulmak istiyorsanız o zaman FindClass kullanmanız gerekiyor, ama FindClass ile sınıfı bulabilmeniz için önce RegisterClass ile register etmelisiniz. Bunun için de benim tavsiyem sınıfın yazıldığı unit'in initialization kısmında yapmanızdır. Ama ben FindClass kullanmanızı tavsiye etmem, sonradan değişiklik yapması zor oluyor ve projede çalışan programcılar değiştikçe hatalar çıkmaya başlıyor.

İyi çalışmalar

Merhaba;
Maalsef yine BaseEdit Form açılıyor.CariEditForm açılmıyor.
Cevapla
#6
@sadettinpolat ;

Aşağıdaki şekilde yazmıştım.

Bu söylediğiniz şekilde yaptığımda bellekte CariEditForm un varlığını kontrol ettiğimde form açık olmasına rağmen Free ve Nil olarak görünüyor.
Tekrar şartlı create yaptığımda (Başka bir yerden) , şöyleki  Assigned(FrmCariEditForm) False veya FrmCariEditForm=nil  ise true dönüyor ve dolayısıyla bir CariEdit form daha create oluyor ve adıda FrmCariEditForm_1 oluyor. Ama tekrar bir daha bu kontrolü yaptığımda ise ancak o zaman Assigned(FrmCariEditForm) True veya FrmCariEditForm=nil  ise False dönüyor ve üçüncü kez CariEditForm create olayını, yani FrmCariEditForm_2 oluşmasını  engelleyebiliyorum.


Ancak bir şeyi gözden kaçırmışım.
Her ne kadar Name propertysi FrmCariEdit form olsa da, MyEdit form isimli referans ile revize edildiğinden, Assigned ve/veya Nil kontrolü yaparken, Form ekranda görünmesine rağmen Assigned False dönmesinin sebebi buymuş.Dolayısıyla projelerimde başka formlarda fazladan bir değişken tanımlamamak için,  formun kullanımda olup olmadığını, açık olup olmadığını  öğrenmek amaçlı yaptığım Assigned kontrolünü, Visible propertysi ile yaparsam sanırım bu sorun çözülmüş olacak.
Yani


 if Assigned(FrmXXX) then 
begin
//Şunu Yapma
//Bunu Yap
end
else
begin
//Bunu Yapma
//Şunu Yap
end;

yerine 

 if FrmXXX.Visible then 
begin
//Şunu Yapma
//Bunu Yap
end
else
begin
//Bunu Yapma
//Şunu Yap
end;

Kodu işimi çözecek.
Assigned kontrolunun gerektirdiği durumlarda da, MyEdit form üzerinden kontrol yapacağım.
İlgi ve alakanıza teşekkürler....
Cevapla
#7
create edilmiş ve visible durumda olan bir form için Assigned kontrolünün false dönmesi garip. bir yerde gözünüzden kaçan birşey vardır.

Create işleminden önce MyEditForm := nil; ataması yapmayı deneyebilirsiniz.
WWW
Cevapla


Konu ile Alakalı Benzer Konular
Konular Yazar Yorumlar Okunma Son Yorum
  Child formlarda create yordamının çalışma sırası LastCoder 16 618 20-10-2019, Saat: 18:39
Son Yorum: LastCoder
  Nesneler arasındaki ilşkiyi/bağlantıyı tespit etmek 41linea41 2 213 14-09-2019, Saat: 13:09
Son Yorum: 41linea41
  Json Free Etmek yhackup 4 626 31-07-2019, Saat: 11:17
Son Yorum: Halil Han Badem
  Fonksiyon içinde create edilenler seci20 8 587 22-07-2019, Saat: 15:38
Son Yorum: Tuğrul HELVACI
  Create edilen button olay ekleme. KUNTAY 4 507 26-05-2019, Saat: 15:19
Son Yorum: KUNTAY



Konuyu Okuyanlar: 2 Ziyaretçi