C++builder中的Sender到底是一种什么机制?解决方法
C++builder中的Sender到底是一种什么机制?
C++builder中的(TObject *Sender),很常见,以前我一直以为Sender 是触发器的意思,比如btn1Click(TObject *Sender)(btn1 是按钮组件),点击的时候会触发事件。
可是我在网上搜了一下热心网友的介绍后,当单击btn时,Sender其实指向了btn1,也就是说*Sender=*btn1;
但是我在这里有个疑问。我设计了一个程序,有两个按钮:btn1.btn2.
点击btn2时,令btn1Click(Sender) 也触发了, 但是在这个过程中,Sender至始至终都是等于btn2的,按理说与btn1无任何关系,那么到底是为什么会触发btn1Click(Sender)呢?
------解决方案--------------------
void __fastcall TForm1::btn2Click(TObject *Sender)
{
if (Sender==btn2)
ShowMessage("Sender==btn2") ;
btn1Click(Sender) ;// 这里调用了。Sender==btn2
if (Sender==btn1)
ShowMessage("Sender==btn1") ;
}
这些是事件函数,VCL使用简单的回调机制,函数指针为闭包指针。
------解决方案--------------------
这叫啥触发,明明就是你直接调用了btn1Click函数
------解决方案--------------------
------解决方案--------------------
其实是你概念还比较混乱
OnClick 属性是个TNotifyEvent事件类型,就是个函数指针
TNotifyEvent 的定义
typedef void __fastcall (__closure *TNotifyEvent)(System::TObject* Sender);
你在窗体山放置一个按钮,双击按钮时就为这个按钮的OnClick事件指定了个函数指针
TForm1->btn1->OnClick = TForm1::btn1Click;
当点击btn1时就触发OnClick事件,OnClick就调用上面分配给它的函数指针,掉用处理函数btn2Click
按钮只管调用事件处理函数,至于函数中做了什么btn1不管也不应该管。
而你 btn1Click(Sender); 是直接调用了该函数,这跟你点击按钮触发事件不是一回事。
------解决方案--------------------
使用 VCL 這套積木組裡有 3 個角色要搞懂 : Owner . Parent . Sender
Sender 指的就是事件的觸發者(源)......
通常我們會經由物件檢視器的 Events 頁次選取產生事件函式...事件函式名稱會依據所屬元件來命名...問題就在此!
許多程序員皆被事件函式名稱給搞混...只要事件函式參數項相同是可以被其他事件或其他元件所共用或互換的!

------解决方案--------------------
例 : Button1 與 Button2 的 OnClick 皆指向 Button1Click 事件函式而共用......
------解决方案--------------------
Sender是那个控件引起触发的吧。
你的代码里确实调用了btn1Click事件。
你可以这样把两个button的事件指向同一个代码,btn1不单独写代码了,干脆指向btn2的事件,你看看效果。
------解决方案--------------------
Sender 是在类内部调用时说明是谁触发了事件
外部执行事件函数时则与此可能无关,关键是传了的参数。
------解决方案--------------------
C++builder中的(TObject *Sender),很常见,以前我一直以为Sender 是触发器的意思,比如btn1Click(TObject *Sender)(btn1 是按钮组件),点击的时候会触发事件。
可是我在网上搜了一下热心网友的介绍后,当单击btn时,Sender其实指向了btn1,也就是说*Sender=*btn1;
但是我在这里有个疑问。我设计了一个程序,有两个按钮:btn1.btn2.
void __fastcall TForm1::btn1Click(TObject *Sender)
{
ShowMessage("OK!!!") ;
}
//---------------------------------------------------------------------------
void __fastcall TForm1::btn2Click(TObject *Sender)
{
if (Sender==btn2)
ShowMessage("Sender==btn2") ;
btn1Click(Sender) ;
if (Sender==btn1)
ShowMessage("Sender==btn1") ;
}
//----------------------------------
点击btn2时,令btn1Click(Sender) 也触发了, 但是在这个过程中,Sender至始至终都是等于btn2的,按理说与btn1无任何关系,那么到底是为什么会触发btn1Click(Sender)呢?
------解决方案--------------------
void __fastcall TForm1::btn2Click(TObject *Sender)
{
if (Sender==btn2)
ShowMessage("Sender==btn2") ;
btn1Click(Sender) ;// 这里调用了。Sender==btn2
if (Sender==btn1)
ShowMessage("Sender==btn1") ;
}
这些是事件函数,VCL使用简单的回调机制,函数指针为闭包指针。
------解决方案--------------------
这叫啥触发,明明就是你直接调用了btn1Click函数
------解决方案--------------------
void __fastcall TForm2::btn1Click(TObject *Sender)
{
if (Sender == NULL) {
ShowMessage("null");
}
else
ShowMessage(((TButton*)Sender)->Name);
}
//---------------------------------------------------------------------------
void __fastcall TForm2::btn2Click(TObject *Sender)
{
btn1Click(btn1);
btn1Click(Sender);
btn1Click(NULL);
}
------解决方案--------------------
其实是你概念还比较混乱
OnClick 属性是个TNotifyEvent事件类型,就是个函数指针
TNotifyEvent 的定义
typedef void __fastcall (__closure *TNotifyEvent)(System::TObject* Sender);
你在窗体山放置一个按钮,双击按钮时就为这个按钮的OnClick事件指定了个函数指针
TForm1->btn1->OnClick = TForm1::btn1Click;
当点击btn1时就触发OnClick事件,OnClick就调用上面分配给它的函数指针,掉用处理函数btn2Click
按钮只管调用事件处理函数,至于函数中做了什么btn1不管也不应该管。
而你 btn1Click(Sender); 是直接调用了该函数,这跟你点击按钮触发事件不是一回事。
------解决方案--------------------
使用 VCL 這套積木組裡有 3 個角色要搞懂 : Owner . Parent . Sender
Sender 指的就是事件的觸發者(源)......
通常我們會經由物件檢視器的 Events 頁次選取產生事件函式...事件函式名稱會依據所屬元件來命名...問題就在此!
許多程序員皆被事件函式名稱給搞混...只要事件函式參數項相同是可以被其他事件或其他元件所共用或互換的!
------解决方案--------------------
例 : Button1 與 Button2 的 OnClick 皆指向 Button1Click 事件函式而共用......
void __fastcall TForm1::Button1Click(TObject *Sender)
{
((TButton *)Sender)->Caption = TEXT("改變");
}
------解决方案--------------------
Sender是那个控件引起触发的吧。
你的代码里确实调用了btn1Click事件。
你可以这样把两个button的事件指向同一个代码,btn1不单独写代码了,干脆指向btn2的事件,你看看效果。
void __fastcall TForm1::btn2Click(TObject *Sender)
{
if (Sender==btn2)
ShowMessage("Sender==btn2") ;
if (Sender==btn1)
ShowMessage("Sender==btn1") ;
}
------解决方案--------------------
Sender 是在类内部调用时说明是谁触发了事件
外部执行事件函数时则与此可能无关,关键是传了的参数。
------解决方案--------------------