Cara mengganti acara klik pada kontrol Firemonkey khusus

Saya mencoba membuat kontrol Firemonkey khusus yang mewarisi kontrol TListView. Saya ingin menambahkan beberapa fungsi ke kontrol yang secara otomatis dijalankan ketika pengguna mengklik kontrol. Oleh karena itu, tujuan saya BUKAN untuk menentukan metode OnItemClick pada formulir kontrol saya, melainkan menambahkan fungsionalitas langsung ke dalam kontrol itu sendiri.

Saya kesulitan memahami apa yang perlu saya lakukan untuk memanfaatkan pengendali klik untuk TListView. Di kepala saya, saya membayangkan solusi saya akan terlihat mirip dengan kode semu ini:

//somewhere in the base TListView code
void __fastcall TListView::ClickHandler()
{
    //logic for handling a click on the list view
}

//somewhere in my custom list view control
void __fastcall TMyListView::ClickHandler()
{ 
    TListView::ClickHandler(); //call base click handler so all the normal stuff happens

    //my additional logic goes here
}

Namun, sepertinya saya tidak dapat menemukan apa pun dalam dokumentasi tentang metode apa yang harus saya coba timpa, atau bagaimana saya harus melakukan hal ini.

Saya menemukan informasi ini tentang memanggil pengendali 'Click-event'. Saya membuat contoh sederhana seperti ini:

void __fastcall TFmListView::Click()
{
    ShowMessage("This is the control's click");
}

Ini berfungsi dengan baik, namun menurut dokumentasi:

Jika pengguna telah menetapkan pengendali pada peristiwa OnClick suatu kontrol, mengklik kontrol tersebut akan menyebabkan metode tersebut dipanggil.

Oleh karena itu, logika tambahan apa pun yang saya tempatkan dalam metode kontrol Click() akan hilang jika salah satu properti peristiwa klik pada kontrol disetel.

Apa cara yang tepat untuk memperluas fungsionalitas dari apa yang terjadi ketika kontrol khusus diklik?


person James Hogle    schedule 29.10.2015    source sumber
comment
Oleh karena itu, logika tambahan apa pun yang saya tempatkan dalam metode kontrol Click() akan hilang jika salah satu properti peristiwa klik pada kontrol disetel.. Itu tidak benar. Anda salah membaca dokumen. Ini adalah kelas dasar Click() yang memanggil pengendali OnClick, jika ada yang ditugaskan. Jika pengguna menetapkan penangan OnClick, dan Anda mengganti Click(), penangan pengguna tidak akan dipanggil kecuali Click() Anda memanggil kelas dasar Click(). Hal ini memungkinkan Anda untuk bertindak selain kode pengguna, untuk memutuskan apakah kode Anda berjalan sebelum/sesudah kode pengguna, dan bahkan melewati kode pengguna.   -  person Remy Lebeau    schedule 31.10.2015


Jawaban (1)


Ini adalah solusi C++ Builder untuk Anda.

Berikut adalah antarmuka kelas dan implementasinya:

class TMyListView : public TListView
{
protected:
    virtual void __fastcall DoItemClick(const TListViewItem *AItem);
};

...

/* TMyListView */

void __fastcall TMyListView::DoItemClick(const TListViewItem *AItem)
{
    // write here the logic that will be  executed
    // even if the OnItemClick handler is not assigned
    ShowMessage("Internal itemclick");

    // call the OnItemClick handler, if assigned
    TListView::DoItemClick(AItem);
}

Kemudian Anda mendeklarasikan sebuah instance dari kelas TMyListView dan event handler yang diperlukan dalam deklarasi formulir:

TMyListView *LV;
void __fastcall MyOnItemClick(const TObject *Sender, const TListViewItem *AItem);

Dan berikut implementasi event handler dan pembuatan LV:

void __fastcall TForm1::Button1Click(TObject *Sender)
{
    LV = new TMyListView(this);
    LV->Parent = this;
    LV->Position->X = 1;
    LV->Position->Y = 1;
    LV->Width = 100;
    LV->Height = 100;

    LV->Items->Add()->Text = "111";

    LV->OnItemClick = &MyOnItemClick;
}

void __fastcall TForm1::MyOnItemClick(const TObject *Sender, const TListViewItem *AItem)
{
    ShowMessage("Assigned itemclick"); //or any other event handler action
}

Kedua pesan akan ditampilkan.

person asd-tm    schedule 30.10.2015
comment
TListView sudah memiliki acara OnItemClick yang dipublikasikan. Anda tidak perlu membuat deklarasi acara sendiri untuk itu. Cukup panggil metode TListView::DoItemClick() dasar ketika metode DoItemClick() Anda yang diganti siap untuk memicu pengendali OnItemClick pengguna. BTW, di Seattle, TItemEvent bukan lagi bagian dari TCustomListView, sekarang menjadi bagian dari TAppearanceListView. Dan DoItemClick() telah diubah namanya menjadi DoListItemClick(). - person Remy Lebeau; 31.10.2015
comment
@RemyLebeau Terima kasih atas komentar dan editan Anda yang bermanfaat. Tolong, jangan ragu untuk mengedit postingan saya. - person asd-tm; 31.10.2015