Merhabalar,
En basit haliyle sorunumu anlatabilmek için şu kodu hazırladım.
public
{ Public declarations }
end;
var
Form1: TForm1;
Nossa: array[1..4] of TButton;
say:integer;
implementation
{$R *.dfm}
procedure TForm1.TIKLA(Sender: TObject);
begin
ShowMessage('Test OK for '+Nossa[say].Caption);
end;
procedure TForm1.FormCreate(Sender: TObject);
var DummyText:string;
begin
for say:= 1 to 4 do
BEGIN
Nossa[say]:= Tbutton.Create(nil);
Nossa[say].Parent := self;
Nossa[say].Caption:='cisss '+inttostr(say);
Nossa[say].Name:='cisss_'+inttostr(say);
Nossa[say].Top:=10*say*3;
Nossa[say].Left:=10;
DummyText:= IntToStr(say); Memo1.Lines.Add(DummyText);
Nossa[say].onClick:= TIKLA;
END;
end;
end.
Bu kodla oluşan her butonun tıklandığında kendi caption bilgisini mesaj olarak göstermesini istiyorum. Sınırlı bilgimle Delphi 7'de bir yol bulamadım. En basit nasıl yapılabilir? Bir sonraki aşamada buton tıklama event'inin içine parametre gönderilebilir mi?
Teşekkürler.
ShowMessage('Test OK for '+TButton(sender).Caption);
işinizi görür.
Buton adına koyduğunuz prefix "cisss_" temizleyip hangi butona eriştiğinizi tespit edebileceğiniz gibi bir referans property delphi tarafından sunulmuştur.
Her buttonun TAG property'sine sayısal referans verebilirsiniz ki bunu da global array olarak kullandığınız dizi eleman index nosu kullanmak isteyebilirsiniz .
örneğin button create tanımlamalarına aşağıdakini eklerseniz;
Nossa[say].Tag := say;
buton click olayında
ShowMessage('Test OK for '+TButton(sender).Caption + ' with button index ' + TButton(sender).tag );
Parametre olarak sender:tbutton gibi yanına eklemeler yaparak zenginleştirilebilir ancak tbutton sınıfını override edip ilk TButton geçen ifadenin üzerinde Type tanımı girilerek yeni özel bir TButton türetip event property üretilmesi gerekir. Diğer yandan dilerseniz Tag değeri ile index olarak kullanmak yerine parametre değeri gönderir, parametresi referans olan işi yaptırabilirsiniz.
Muharrem hocam merhabalar,
Tam aradığım gibi bir çözüm önermişsiniz. Tag değerini butona yazdırırken string'e dönüştürdüm sadece. Onun dışında verdiğiniz kod direk ne yapacağımı anlatıyor. Çok teşekkürler.
Diğer açıklamalarınıza yönelik biraz okuma yapıp deneyeceğim.
Selamlar.
TAg Kısmını şu tür durumlar için kullanırız. MEsela bir hızlı satış ekranınız var.
Buton captionuna: Ürün adı, TAg'ına ise ürünid tutarız. butona tıkladığında ise ortak bi procedure gidip satış alanına sender butonun tagi ile işlem yaptırırız. Resmen hayat kurtarıyor

(16-01-2025, Saat: 22:09)mcuyan Adlı Kullanıcıdan Alıntı: [ -> ]TAg Kısmını şu tür durumlar için kullanırız. MEsela bir hızlı satış ekranınız var.
Buton captionuna: Ürün adı, TAg'ına ise ürünid tutarız. butona tıkladığında ise ortak bi procedure gidip satış alanına sender butonun tagi ile işlem yaptırırız. Resmen hayat kurtarıyor 
Bu, çok şeyi kolaylaştıran bir ipucuymuş. Biraz daha detay ne güzel olurdu!
Nossa[say]:= Tbutton.Create(nil);
Nossa[say].Parent := self;
Nossa[say].onClick:= TIKLA;
Muharrem Bey'den gelen çözümü farklı denemelerle sıfırdan form larda uygulayıp, "tamam artık asıl koda alayım" dedim. Üstteki parenting satırı "self" için undeclared identifier hatası verip kalıyor.
Şu şekle çevirirsem butonlar oluşuyor. Ama bu kez de TIKLA için prosedür tanımlarını girmeme rağmen undeclared identifier hatası geliyor.
Nossa[say]:= Tbutton.Create(Form1);
Nossa[say].Parent := Form1;
Nossa[say].onClick:= TIKLA;
İlerleyemiyorum. Çözüm önerilerinizi alabilir miyim?
Teşekkürler.
kodu procedure bazında yazarsanız daha kolay yardımcı oluruz.
Procedure TForm1.ButonEkle();
begin
Nossa[say]:= Tbutton.Create(nil);
Nossa[say].Parent := self;
Nossa[say].onClick:= TIKLA;
end;
derseniz self burada gönderilen formu tform1'den referans alır. Tanımsız diyorsa tform1 bağlantısı vermemiş olmalısınız.
Sonra butona tıkladığınızda gönderi sahibi (Sender:tobject) bu (tform1 referanslı tikla procedure) ile butonu bildirir.
Nil olarak create ettiğiniz için de form kapanırsa buton free olmaz onun ayrıca free etme işi size kalır. nil yerine de self derdeniz form referansıyla kendi yağında kavrulur.
Farklı formlarda button oluşturmak ise maksat, o formu parametre olarak verip, self yerine o parametre atanmalı.
-- -Bilgisayar başına geçtim bir örnek hazırladım aşağıda incelemek isteyebilirsiniz. Forma bıraktığınız bir buttona her tıkladığınızda yeni buton alt alta türetilecek. Türetilen butona basılınca da kendi ID'sini beyan edecek.
var
Nossa : array of TButton;
procedure TForm1.Tikla(Sender: TObject);
begin
ShowMessage('Test OK for '+TButton(sender).Caption + ' with button index ' + IntToStr(TButton(sender).tag) );
end;
procedure TForm1.ButonEkle();
var
say : Integer;
begin
SetLength(Nossa, length(Nossa) + 1);
say := high(Nossa);
Nossa[say] := Tbutton.Create(self);
Nossa[say].Parent := self;
Nossa[say].onClick := TIKLA;
Nossa[say].Left := 300;
Nossa[say].Tag := say;
if length(Nossa) > 1
then
Nossa[say].Top := Nossa[say-1].Top + Nossa[say-1].Height + 4
else
Nossa[say].Top := 10;
end;
procedure TForm1.BitBtn1Click(Sender: TObject);
begin
ButonEkle;
end;

Hocam elinize sağlık. Okur okumaz denedim. Sonuç ekran görünümü ekte. Derli toplu kod yazma konusunda da bir iki ipucu yakalamak iyi oldu.
Bir ilave soru sorabilir miyim?
Prosedür girişi (veya başlığı mı demeli) parantezli olsa da olmasa da kod çalışıyor. Ben şu ana kadar bu tür prosedürleri parantezsiz yazdım.
procedure TForm1.ButonEkle; şeklinde yazmak yerine procedure TForm1.ButonEkle(); parantezlerini koymak nasıl bir fark yaratıyor?
Bazen yazdığım kodlarda program normal çalışıyor gibi görünürken pat diye bir hata verip çıkıveriyor. Acaba bu parantez konusu o hatalardan birinin nedeni olabilir mi diye soruyorum.
Parantezler, parametre ihtiyacı yoksa ve/veya varsayılan değer alan parametre olduğunda tercih kullanarak bilerek ve isteyerek parametre girmediğimizi beyan ettiğimiz hallerde kullanılan etkisiz elemandır.
Bu durumda olmazsa da olur, sadece etik duygularla yazma gereği duyuyorum. Unutulmuş gibi olmuyor da kasıt belirtmiş oluyorum.