Konuyu Paylaş : facebook gplus twitter

Konuyu Oyla:
  • Derecelendirme: 5/5 - 1 oy
  • 1
  • 2
  • 3
  • 4
  • 5
Thread kullanmadan veya IdThreadComponent ile AniIndicator kullanımı hk.
#1
Merhaba Arkadaşlar;

Mobil tarafta zaman alan kısımlarda AniIndicator çalıştırılmaya çalışıldığında, işlem uzun sürse bile AniIndicator  hiç ekrana gelmeden direk işlem gerçekleşiyor. Hem işlemin devam etmesi hemde AniIndicator çalışması için Thread haricinde kullanabileceğimiz basit bir yöntem var mıdır.

Kısaca Thread kullanmadan AniIndicator nasıl düzgün çalıştırılabilir.

*Konuyla ilgili olarak; IdThreadComponent tam olarak ne için kullanılıyor, bununla yapsam ne gibi sakıncaları olur. (Bu konuda birkaç test yaptım sonuçlar olumu fakat component'in amacını bilmiyorum.)

Teşekkürler.
Cevapla
#2
(05-10-2017, Saat: 11:35)pro_imaj Adlı Kullanıcıdan Alıntı: Linkleri Görebilmeniz İçin Giriş yap veya Üye OlMerhaba Arkadaşlar;

Mobil tarafta zaman alan kısımlarda AniIndicator çalıştırılmaya çalışıldığında, işlem uzun sürse bile AniIndicator  hiç ekrana gelmeden direk işlem gerçekleşiyor. Hem işlemin devam etmesi hemde AniIndicator çalışması için Thread haricinde kullanabileceğimiz basit bir yöntem var mıdır.

Kısaca Thread kullanmadan AniIndicator nasıl düzgün çalıştırılabilir.

*Konuyla ilgili olarak; IdThreadComponent tam olarak ne için kullanılıyor, bununla yapsam ne gibi sakıncaları olur. (Bu konuda birkaç test yaptım sonuçlar olumu fakat component'in amacını bilmiyorum.)

Teşekkürler.

Uygulamanın ana thread'i meşgul iken, görsel nesnelerin güncellenmesi için gönderilen mesajlar, mesaj kuyruğundan alınıp işlenemez. Dolayısı ile görsel nesneler de güncellenemezler. Amiyane tabir ile "herşey yağ gibi akıp gitsin" istiyor iseniz, ya uzun süren işleminizi bir başka thread içinde çağıracaksınız(ana thread'i bloke etmeyeceksiniz) ya da imkanınız var ise uzun süren işlem adımlarının arasına Application.ProcessMessages satırını serpiştireceksiniz. Bu sayede uygulamanın ana thread'inin mesaj kuyruğuna gönderilen mesajlar kısmen alınıp işlenebilir olacak ve görsel nesneleriniz kendilerini güncelleyebilme imkanı bulacaklardır.
Mal sahibi, mülk sahibi
Hani bunun ilk sahibi ?
Mal da yalan mülk de yalan
Var biraz da sen oyalan...
WWW
Cevapla
#3
(05-10-2017, Saat: 11:55)Tuğrul HELVACI Adlı Kullanıcıdan Alıntı: Linkleri Görebilmeniz İçin Giriş yap veya Üye Ol
(05-10-2017, Saat: 11:35)pro_imaj Adlı Kullanıcıdan Alıntı: Linkleri Görebilmeniz İçin Giriş yap veya Üye OlMerhaba Arkadaşlar;

Mobil tarafta zaman alan kısımlarda AniIndicator çalıştırılmaya çalışıldığında, işlem uzun sürse bile AniIndicator  hiç ekrana gelmeden direk işlem gerçekleşiyor. Hem işlemin devam etmesi hemde AniIndicator çalışması için Thread haricinde kullanabileceğimiz basit bir yöntem var mıdır.

Kısaca Thread kullanmadan AniIndicator nasıl düzgün çalıştırılabilir.

*Konuyla ilgili olarak; IdThreadComponent tam olarak ne için kullanılıyor, bununla yapsam ne gibi sakıncaları olur. (Bu konuda birkaç test yaptım sonuçlar olumu fakat component'in amacını bilmiyorum.)

Teşekkürler.

Uygulamanın ana thread'i meşgul iken, görsel nesnelerin güncellenmesi için gönderilen mesajlar, mesaj kuyruğundan alınıp işlenemez. Dolayısı ile görsel nesneler de güncellenemezler. Amiyane tabir ile "herşey yağ gibi akıp gitsin" istiyor iseniz, ya uzun süren işleminizi bir başka thread içinde çağıracaksınız(ana thread'i bloke etmeyeceksiniz) ya da imkanınız var ise uzun süren işlem adımlarının arasına Application.ProcessMessages satırını serpiştireceksiniz. Bu sayede uygulamanın ana thread'inin mesaj kuyruğuna gönderilen mesajlar kısmen alınıp işlenebilir olacak ve görsel nesneleriniz kendilerini güncelleyebilme imkanı bulacaklardır.

Cevap için teşekkür ederim Tuğrul Hocam;
Application.ProcessMessages bazı işlemlerde kullanıyordum fakat burada SQL kodu çalıştığı için işimi görmüyor. Thread konusundada IdThreadComponent nesnesini onRun olayını kullanarak çalışan sql kodunu olduğu procedure'yi çağırıyorum tek sorun çalışan sql kodunun verileri ekrana bağlı olan ListView'e gelmiyor. (Aynı sql kodunun olduğu procdure'yi normal şekilde çağırdığımda veriler ListView'e geliyor.)

Bunun nedeni ne olabilir.
Cevapla
#4
(05-10-2017, Saat: 13:27)pro_imaj Adlı Kullanıcıdan Alıntı: Linkleri Görebilmeniz İçin Giriş yap veya Üye Ol
(05-10-2017, Saat: 11:55)Tuğrul HELVACI Adlı Kullanıcıdan Alıntı: Linkleri Görebilmeniz İçin Giriş yap veya Üye OlUygulamanın ana thread'i meşgul iken, görsel nesnelerin güncellenmesi için gönderilen mesajlar, mesaj kuyruğundan alınıp işlenemez. Dolayısı ile görsel nesneler de güncellenemezler. Amiyane tabir ile "herşey yağ gibi akıp gitsin" istiyor iseniz, ya uzun süren işleminizi bir başka thread içinde çağıracaksınız(ana thread'i bloke etmeyeceksiniz) ya da imkanınız var ise uzun süren işlem adımlarının arasına Application.ProcessMessages satırını serpiştireceksiniz. Bu sayede uygulamanın ana thread'inin mesaj kuyruğuna gönderilen mesajlar kısmen alınıp işlenebilir olacak ve görsel nesneleriniz kendilerini güncelleyebilme imkanı bulacaklardır.

Cevap için teşekkür ederim Tuğrul Hocam;
Application.ProcessMessages bazı işlemlerde kullanıyordum fakat burada SQL kodu çalıştığı için işimi görmüyor. Thread konusundada IdThreadComponent nesnesini onRun olayını kullanarak çalışan sql kodunu olduğu procedure'yi çağırıyorum tek sorun çalışan sql kodunun verileri ekrana bağlı olan ListView'e gelmiyor. (Aynı sql kodunun olduğu procdure'yi normal şekilde çağırdığımda veriler ListView'e geliyor.)

Bunun nedeni ne olabilir.

İlgili component muhtemelen OnRun olayına yazdığınız kodu bir thread içinde çalıştırıyordur. Main thread haricindeki thread'ler içinde iken görsel nesnelere erişmeye çalışmak, onları güncellemek; her türlü hata olasılığına açıktır. Sözün özü, ListView içine ekleme yaptığınız bölümü, TThread.Synchronize ile ya da TThread.Queue ile senkronize etmelisiniz.
Mal sahibi, mülk sahibi
Hani bunun ilk sahibi ?
Mal da yalan mülk de yalan
Var biraz da sen oyalan...
WWW
Cevapla
#5
Merhaba;

Bilgilendirme için tekrar teşekkür ederim.
 
Sorunumun kaynağını buldum! Thread nesnesinin aktiflik durumunu false yapsak bile Thread çalışmaya devam ediyormuş.

Çözüm
onRun olayında Terminate diyerek çözdüm.
Sender.Terminate;


*IdThreadComponent yeni keşfetmiş birisi olarak Thread işlemlerini artık bu yolla çok kolay ve hızlı bir şekilde yapılabileceğini bu vesileyle keşfetmiş oldum, herkese tavsiye ederim.
Cevapla
#6
Merhaba,
Malum bu aralar formumuzda alternatif çözümler revaçta, bu vesile ile nesne kullanmadan, örnek bir kod paylaşımı yapayım.
TThread.CreateAnonymousThread(
 procedure ()
 begin
   TThread.Synchronize (nil,
     procedure ()
     begin
       AniIndicator1.Visible := True;
       AniIndicator1.Enabled := True;
     end
   );
   try
     //işlemleriniz;
   finally
   //  TThread.Synchronize (nil,
   //    procedure ()
   //    begin
         AniIndicator1.Enabled := False;
         AniIndicator1.Visible := False;
   //    end);
   end;
 end
).Start;

finally bölümündeki kodları opsiyonel yaptım. Smile 
Sebebi ise Android uygulamalarda AnonymousThread işlemi tamamlandıktan (örneğin, ListView dolduruluyor) hemen sonra AniIndicator'ün gizlenmesi, az da olsa zaman alıyor (1-2 sn.). Finally bölümündeki  Synchronize'ı kapatınca, thread bitimine müteakip AniIndicator gizleniyor.
While true do; Hayat döngüsü, kısır değildir! Yapılan bir yanlış, o döngünün dışına çıkmanızı sağlayacaktır.
WWW
Cevapla
#7
Fesih hocam sizin yöntemde çok şık.

Sizin yöntem ve benim uyguladığım yöntemle; Windows ve Android'te sorunsuz çalışıyorken ios tarafında  çalışmıyor.

1-İlgili tab'ı aktif etme işlemini Thread'içinde kullanırsam işlemin başladığı tuşa ikinci kez bastığımda tabRapor aktif oluyor ve verilerde geliyor.
2-İlgili tab'ı aktif etme işlemini Thread' dışında ilgili butonda kullanırsam tab aktif oluyor fakat bu seferde ListView boş gözüküyor ekranda herhangi bir yere dokunduğumda veriler geliyor
Kod:
TabControl1.ActiveTab := tabRapor;


Delphi : 10.2.1
ios : 10.0.2
Cevapla
#8
(06-10-2017, Saat: 00:25)pro_imaj Adlı Kullanıcıdan Alıntı: Linkleri Görebilmeniz İçin Giriş yap veya Üye OlFesih hocam sizin yöntemde çok şık.

Sizin yöntem ve benim uyguladığım yöntemle; Windows ve Android'te sorunsuz çalışıyorken ios tarafında  çalışmıyor.

1-İlgili tab'ı aktif etme işlemini Thread'içinde kullanırsam işlemin başladığı tuşa ikinci kez bastığımda tabRapor aktif oluyor ve verilerde geliyor.
2-İlgili tab'ı aktif etme işlemini Thread' dışında ilgili butonda kullanırsam tab aktif oluyor fakat bu seferde ListView boş gözüküyor ekranda herhangi bir yere dokunduğumda veriler geliyor
Kod:
TabControl1.ActiveTab := tabRapor;


Delphi : 10.2.1
ios : 10.0.2

En iyisi yazdığınız kodu görmemiz sanıyorum. Aksi taktirde afaki konuşmaya devam edeceğiz.
Mal sahibi, mülk sahibi
Hani bunun ilk sahibi ?
Mal da yalan mülk de yalan
Var biraz da sen oyalan...
WWW
Cevapla
#9
Haklısınız kodları yazmamışım.  Blush

procedure TfrmAna.ListBoxItem2Click(Sender: TObject);
begin
 RaporNo := 1;

 frmDM.IdThreadGenel.Active := True;
 frmAna.TabControl1.ActiveTab := frmAna.tabRapor;
//Thread aktif olunca Run, AfterRun ve Before Run işlemin durumuna göre aktif oluyor.
end;


procedure TfrmDM.IdThreadGenelAfterRun(Sender: TIdThreadComponent);
begin
 frmAna.AniIndicator1.Visible := False;
 frmAna.AniIndicator1.Enabled := False;
 frmAna.AniIndicator1.SendToBack;
end;

procedure TfrmDM.IdThreadGenelBeforeRun(Sender: TIdThreadComponent);
begin
 frmAna.AniIndicator1.Visible := True;
 frmAna.AniIndicator1.Enabled := True;
 frmAna.AniIndicator1.BringToFront;
end;

procedure TfrmDM.IdThreadGenelRun(Sender: TIdThreadComponent);
begin
 try
    TThread.Sleep(300);
   frmAna.RaporBaslik()
 except

 end;
 Sender.Terminate;
end;

procedure TfrmAna.RaporBaslik();
begin
 DatabaseBaglan();

 case RaporNo of
   1:
     begin
       frmDM.QBaslik.Close;
       frmDM.QBaslik.SQL.Clear;
       frmDM.QBaslik.SQL.Text := 'exec dbo.S01A';
       frmDM.QBaslik.Open;
     end;
   2:
     begin
       frmDM.QBaslik.Close;
       frmDM.QBaslik.SQL.Clear;
       frmDM.QBaslik.SQL.Text := 'exec dbo.S02A';
       frmDM.QBaslik.Open;
     end;

 end;
end;

procedure TfrmAna.DatabaseBaglan();
begin
 try
   if frmDM.conServer.Connected = False then
     frmDM.conServer.Connected := True;
 Except
   ShowMessage('Check Your Internet Connection');
   exit;
 end;
end;
Cevapla
#10
İlgili component'i hiç kullanmadım, kodlarını da incelemedim ama; mantıken BeforeRun ve AfterRun olaylarının main thread içinden çağrılıyor olması gerekir. Bu durumda, ilgili event'lerde görsel nesnelere erişimde bir sıkıntı yaşamazsınız. Ancak bir thread içinde veritabanı işlemleri yapıyorsanız, kullandığınız connection'ın thread'e has olması gerekir. Main thread'in kullandığı connection'ı bir başka thread içinde kullanmak sağlıklı sonuçlar vermez. Örneğin, uygulamanızın ana thread'i ilgili connection üzerinden veri çekiyor ya da veri gönderiyor olabilir, bir diğer thread'de aynı connection üzerinden veri göndermeye ya da almaya kalkarsa sonuçlar arzu ettiğiniz gibi olmayacaktır Wink 

 Ayrıca ListView'i LiveBindings ile dolduruyorsanız, bu durumda siz bir thread içinden görsel nesnelere erişimde bulunuyorsunuz demektir -ki bu hiç de tavsiye edilen bir durum değildir. Peki ne yapabilirsiniz ? Tasarım anındaki livebindings bağlantılarınızı iptal edip, thread'in bitmesine müteakip yeniden kurarsanız bir sıkıntı yaşamamalısınız.

Thread kullanmak kolaydır ama dikkat edilmesi gereken ince nüanslar vardır. Wink
Mal sahibi, mülk sahibi
Hani bunun ilk sahibi ?
Mal da yalan mülk de yalan
Var biraz da sen oyalan...
WWW
Cevapla

Konuyu Paylaş : facebook gplus twitter



Konu ile Alakalı Benzer Konular
Konular Yazar Yorumlar Okunma Son Yorum
  scrollbox kullanımı arsl01 10 351 12-07-2018, Saat: 11:34
Son Yorum: Fesih ARSLAN
  Grid veya StringGrid Hücre Renklendirme burakb44 3 420 17-03-2018, Saat: 09:22
Son Yorum: burakb44
  Delphi AVD Manager kullanımı Bay_Y 15 1.103 07-03-2018, Saat: 15:59
Son Yorum: Bay_Y
  FMX Projede idTCPClient ReadLn Komut Kullanımı Hk. Halil Han Badem 6 431 29-01-2018, Saat: 11:14
Son Yorum: Halil Han Badem
Question spinbox kullanımı BY-HAYALET 6 464 09-12-2017, Saat: 17:36
Son Yorum: serhatil



Konuyu Okuyanlar: 1 Ziyaretçi