用託管c++編寫自定義web組合控制項
什麼是自定義的組合控制項
自定義的web組合控制項正如它名字說的那樣:在單個控制項中整合了乙個或多個服務端程式及html控制項。自定義的組合控制項在功能上與使用者控制項非常類似,最大的不同之處是,它只存在於它自己的程式集中(或與其他控制項共享),能被放在工具條中,並可提供它所包含控制項的所見即所得檢視方式。
另一方面,自定義web組合控制項比使用者控制項(user control)更加難建立,因為visual studio.net的設計者們並沒有提供視覺化建立它們的任何工具,因此,問題是:為什麼要用組合控制項取代使用者控制項呢?當分發控制項到多個web程式或系統中時,如果使用自定義web組合控制項,情況要好得多,而使用者控制項最好用在不重視復用的地方,例如,如果只準備在你自己的**中使用控制項,那麼使用者控制項可能會是更好的選擇。基本上來說,你不得不在建立它所花的額外努力與從中所得到的可復用次數之間,作一權衡;同時,因為自定義組合控制項只存在於它自己的程式集中,所以在每台電腦上,只需要乙份拷貝,而使用者控制項則放置於web程式集內,因此,必須儲存在每乙個使用它的web**上。
建立乙個自定義web組合控制項
建立乙個自定義web組合控制項的步驟,實質上與建立乙個自定義的超類web控制項一樣,本例中為searchcontrol,第一件要做的事,是設計控制項的外觀,完成之後,看起來大致如圖1所示。
圖1:設計器中的控制項外觀
searchcontrol,正如上面所看到的,由三個服務端控制項組成(實際上有四個,後面將會說到):乙個標籤控制項、乙個文字框控制項、乙個按鈕。另外,自定義web組合控制項中比較棘手的部分是它們並沒有乙個很好的拖放設計工具以支援建立控制項,而需要以老方式——手工編寫**來完成。但是,也不完全正確,在此不必手工編寫服務端或html控制項**,那怎樣建立searchcontrol的外觀呢?
首先,在searchcontrol類中寫出三個服務端控制項的定義:
label
*label;
textbox
*textbox;
button
*button;
接下來,在類的建構函式中建立它們的例項:
searchcontrol::searchcontrol()
最後,在類的createchildcontrols()方法中,把它們新增到乙個自定義web組合控制項的子控制項集合裡:
void searchcontrol::createchildcontrols()
createchildcontrols()方法是從control類繼承來的乙個虛方法,而webcontrol也正是從control類繼承而來。
注意,在此並不需要render()方法,因為組成組合控制項的服務端與html控制項能繪製自身,所以,你完全不用考慮此方法,或者在render()方法中呼叫基類:
void searchcontrol::render(htmltextwriter *output)
現在,有了基本的外觀了,還可以新增一些功能。首先,需要一些屬性,用於更新標籤及文字框內的值,以下是屬性的定義:
__property void set_value(string *value);
__property string *get_value();
__property void set_labeltext(string *value);
__property string *get_labeltext();
__property void set_buttontext(string *value);
__property string *get_buttontext();
**如下:
string *searchcontrol::get_labeltext()
void searchcontrol::set_labeltext(string *value)
string *searchcontrol::get_value()
void searchcontrol::set_value(string *value)
string *searchcontrol::get_buttontext()
void searchcontrol::set_buttontext(string *value)
上述**最棘手的部分就是ensurechildcontrols()方法,其保證了子控制項在之前已經被建立,如果你不新增這個,設計器將會顯示乙個空白的自定義控制項。
當你執行上述**時,將會發現一些設計上的缺陷。首先,文字框總是同樣大小,並且不能排列多於乙個searchcontrol例項的標籤。為進行修正,要新增第四個服務端控制項到自定義web組合控制項中,在此,**(table)可能是處理所有控制項布局問題最好的方法:
void searchcontrol::createchildcontrols()
為處理排列問題,需再再新增兩個屬性:labelwidth和labelalign。labelwidth保證了標籤控制項為一特定的單位長度,而labelalign允許標籤使用horizontalalign列舉進行排列:
__property void set_labelwidth(unit value);
__property unit get_labelwidth();
__property void set_labelalign(horizontalalign value);
__property horizontalalign get_labelalign();
現在問題又有些棘手了,為指定標籤的寬度與排列,可對**單元格屬性進行修改,但在單元格中並不包含標籤自身。為簡化起見,建立乙個名為celllabel的私有類變數,由其取代createchildcontrols()方法中的cell1,以下是labelwidth與labelalign屬性的實現**:
unit searchcontrol::get_labelwidth()
void searchcontrol::set_labelwidth(unit value)
horizontalalign searchcontrol::get_labelalign()
void searchcontrol::set_labelalign(horizontalalign value)
處理文字框的縮放時,可使它完全充滿包含其的單元格,這樣,當**縮放時,文字框也會跟著縮放。於是,當控制項縮放時,文字框會隨控制項變化,或者你可以指定標籤為控制項的乙個百分比,如30%,這樣一來,當控制項縮放時,標籤與文字框都會基於百分比進行調整,以下是修改後的createchildcontrols()方法:
void searchcontrol::createchildcontrols()
另外,別忘了在建構函式中建立labelcell的例項,要不然可要花點時間找出為什麼設計器會給你乙個大大的錯誤提示框了。
處理事件
現在,有關控制項的外觀已經全部完成,是時候對控制項加入一點功能了。在此,你想做的第一件事,可能就是讓按鈕控制項能處理單擊事件了,我們在此使用乙個事件處理函式,它就和普通的windows與web程式中的一樣。以下是在單擊事件中新增的事件處理函式:
button->click += new eventhandler(this, buttonclicked);
接著,建立乙個處理此事件的方法:
void searchcontrol::buttonclicked(object *sender, eventargs *e)
看到了吧,沒有多深的科學道理,很簡單。
引發事件
如果想讓控制項的使用者訪問到單擊事件,那該怎麼做呢?我們需要建立乙個公共的__event,在此之上,使用者可提供他們自己的事件處理函式:
__event eventhandler* click;
或許,你還想提供乙個受保護的onclick()方法,這樣,如果有人從searchcontrol繼承,在傳回控制項給searchcontrol自定義web組合控制項之前或之後,他可為單擊事件提供一些額外的功能。另外,如果你很專心,那一定注意到了buttonclick()事件處理函式實際上是呼叫了onclick()方法,由其把控制項從按鈕傳遞到任意事件處理函式,而事件處理函式則可被附加於控制項的單擊事件之上。
void searchcontrol::onclick(eventargs *e)
因為單擊事件是預設也是唯一的事件,也許,再新增乙個defaultevent("click")屬性,指定單擊為控制項的預設事件,會是乙個不錯的主意:
[defaultproperty("value"), defaultevent("click"),
toolboxdata("<:searchcontrol>
runat=server>")]
public __gc class searchcontrol :
public system::web::ui::webcontrols::webcontrol
請記住,如果你修改了元資料(屬性),那必須刪除並重新引用程式集,以便元資料可被重新識別。一般而言,如果要使用此控制項,只需在設計器中雙擊searchcontrol控制項,以建立乙個事件處理函式。(下面假定使用者的**為c#**):
private void searchcontrol1_click(object sender, system.eventargs e)
在本文結束時,作一下簡單的小結,在託管c++中開發自定義web控制項,涉及了一些比較有意思的事情:首先,它建立了乙個由四個服務端控制項所組成的自定義web組合控制項,並演示了怎樣使用屬性來操作控制項;其次,還說明了怎樣處理由控制項產生的事件;最後,演示了怎樣傳遞事件給使用自定義組合控制項的web應用程式。
用jQuery 編寫自定義外掛程式
一 基本的 結構 方法一 name 外掛程式名 function var opts extend defaults,options 此處options為使用者設定的引數物件 使用者傳參 實現外掛程式的 bla bla bla jquery 方法二 function name2 function 其他...
C 用for遍歷自定義類
正確的做法是像stl容器那樣,建立乙個迭代器類,然後裡面過載 比較 遞增 解引用 這幾個函式。例如 template class t class iterator bool operator const iterator that iterator operator t operator itera...
用WIN32 API編寫自定義BUTTON
用win32 api編寫自定義button下面分析一下自繪按鈕的原理,用過mfc自繪按鈕的人都知道,是通過過載了父視窗wm drawitem的響應訊息實現的。同時也要子類化按鈕來得到按鈕的其他有用的訊息,比如wm mousemove wm keydown等訊息。因為mfc的訊息迴圈都是封裝好的,所以...