|
我们知道,C++Builder没有自画菜单,但可以调用API函数::SetMenuItemInfo()来改
" w% z9 C8 e$ q- V! t4 R) ?变菜单类型,达到自画菜单的目的。下面的例子演示了如何使用自画菜单。当鼠标位于菜单 8 O4 m9 D* d: o$ s/ \
上拾,菜单项将凸出来。(黑体字为添加的代码)
1 _/ o0 F$ N) W0 K& f 3 m5 \& V7 ^; i# ?- D0 b
//头文件 7 G( ]' t% w& M, Q( D2 j
//------------------------------------------
4 b6 _0 @0 x n4 M' [#ifndef TestMenuH 6 _! L9 x/ w* h# E6 d: V) f
#define TestMenuH 8 H/ {* b. L" f; D- i
//----------------------------------------- 0 _- d* q5 @: Y# G# d
#include Classes.hpp 3 s% g/ l8 q( @: L+ r* ^
#include Controls.hpp
* n. N/ q' n q#include StdCtrls.hpp
7 u& k- W4 q9 z) m#include Forms.hpp * w* Y. t$ ^9 F6 O: {( |) b) b
#include Menus.hpp//-------------------- / H" @! X$ I9 O4 |
6 `3 W+ y8 t3 i F- F: G! m( B7 Zclass TForm1 : public TForm . r' v! i9 L( h6 I6 R! `
{ % \& J' c* v) e; q# c: e
__published: // IDE-managed Components
7 ?# R9 l2 W6 a2 x1 bTMainMenu *MainMenu1; i& N) `8 F; }6 }* ~& L
TMenuItem *aaa1;
. C9 C }: P5 c \6 DTMenuItem *aaaaaaaaa1;
" X9 P0 s$ B& x" {) ]* kTMenuItem *ccc1; ) c6 ?$ A i& Q3 r, ~4 C
TMenuItem *ddd1;
# R! Y$ G8 c% q! c) dTMenuItem *eee1; 0 b) K! a. ^6 \
TMenuItem *ddsds1; + S- x7 ]4 K9 x9 z
TMenuItem *fcdfsss1; 4 e" k0 B# ` J2 T4 o3 G, ]8 i6 x
TMenuItem *dddddddd1;
7 x( ~: u4 k9 j/ K |% M* {void __fastcall FormCreate(TObject *Sender);
2 V. S( _1 I9 N; m* b* A" ]private: // User declarations * h) B" r+ X4 m* B" v' X' i; U) ]& g
void __fastcall Modify(TMenuItem *pMenuItem); ' z2 C+ M7 t& i; _
protected : 9 Z" Z8 a8 K# J, b+ H6 {
MESSAGE void __fastcall CNMeasureItem(TWMMeasureItem Msg);//增加响应消息 . W! m; j9 v. ?2 w: \, @; ]% r7 J
MESSAGE void __fastcall CNDrawItem(TWMDrawItem Msg); " N/ N3 m' b: U+ R- z/ D, u# G) c
public: // User declarations % m* | w- V3 Y: X
__fastcall TForm1(TComponent* Owner); 8 N( _. b2 k8 W! o/ A3 Z
BEGIN_MESSAGE_MAP//添加消息映射
, Z3 p) v S7 s7 g' ?VCL_MESSAGE_HANDLER(WM_MEASUREITEM, TWMMeasureItem, CNMeasureItem);
1 }2 K& d" Z1 j% @1 ^& `. U8 LVCL_MESSAGE_HANDLER( WM_DRAWITEM, TWMDrawItem, CNDrawItem);
" ]2 F6 E: x0 w' s2 u4 E3 ]END_MESSAGE_MAP(TForm); 2 T- {7 j- O6 @& ~# ]9 v
}; r; {6 s5 i7 J5 k' O% b }
//---------------------------------------------------------------------------
1 H; o! Q$ }. F0 T3 H( H9 xextern PACKAGE TForm1 *Form1; ) K: Q. U; [( w$ A+ T
//--------------------------------------------------------------------------- w; C9 |- _' f0 {
#endif 9 J! @/ c. J7 B& T5 i# D- H
/ X# E( R" \% _$ ` D/ q//实现文件
5 R' u; ^' ~! d5 k//---------------------------------------------------------------------------
1 h) ^8 O8 k; X% W* D; a4 Q9 J#include vcl.h # D# [$ w7 N; e) e
#pragma hdrstop ) x; G# @) `; ~3 {
3 @" X0 z$ C4 @& Y. ?7 p+ b/ W% m#include TestMenu.h
& ], O* s# Y7 E e& \//--------------------------------------------------------------------------- 5 W6 ^" j {5 l, S9 j
#pragma package(smart_init)
W+ P+ C5 H9 T4 T% E& Y/ ^#pragma resource *.dfm C& F; |8 e& C0 Q3 }
TForm1 *Form1;
: |% R/ U+ I9 U2 W2 U//---------------------------------------------------------------------------
9 X6 v) K: y1 n- G__fastcall TForm1::TForm1(TComponent* Owner)
7 q- k5 @& `: r2 S' c: TForm(Owner)
3 ]1 O6 ?7 n# |! l9 X0 M{ ) Z+ B! b" i) p2 @7 d' a8 s
} 8 ?: h& _- A1 c, ]3 r
//--------------------------------------------------------------------------- 4 W6 W ?/ P# p8 U+ T0 O) d7 r
) p8 S6 `$ v5 o* {& W: A& }2 @void __fastcall TForm1::Modify(TMenuItem *pMenuItem)
7 G. ^( P6 x. D, l{//修改缺省属性 + ]' p7 C5 g G1 g: y
for(int i=0;ipMenuItem-Count;i++) $ x/ A8 u( d( s0 v
{ ; o c4 i) P8 c) p6 \
MENUITEMINFO mii=
0 t6 u* Z# U/ T{ ( @' N9 o# j* m0 ?3 N: u- }9 M. d
sizeof(MENUITEMINFO),
x1 J" s% ]; q0 wMIIM_TYPE|MIIM_DATA ,//改变类型和数据 ! L# r1 o1 l% r: A% ]8 a8 z) n3 s: U
MF_OWNERDRAW,0,0,0,0,0,DWORD(pMenuItem-Items-Handle),
2 W7 ^, _# h( y//把菜单项的句柄赋给32位数据 % w) O* @ F8 P( a. w4 m! j. r
0,
, x- D/ a+ n3 P* L0,
! |$ m7 y+ X n$ s& b) _}; . n* `& y0 l. X, b& _6 U# m' ~8 k5 a
if(pMenuItem-Items-Caption!=-)//如果不是间隔线 - Q1 n- D! o: [- c
::SetMenuItemInfo(pMenuItem-Handle,i,TRUE,mii); 9 {8 c; |* U U4 ^, ]
if(pMenuItem-Items-Count)//如果含有子菜单 2 k2 G! n5 Z# y% T; T7 l
Modify(pMenuItem-Items);
+ v" u) l8 ]/ c$ B, }}
8 M4 g! v* m- v) b , I8 X. s; T6 W: |4 D
} % e( |: ~$ f$ e- C3 d5 z4 x E6 C& M
void __fastcall TForm1::FormCreate(TObject *Sender) 5 ` f ]% S* H/ N$ f% S. ^
{
0 ]4 L% z( @ c! v* Dfor(int i=0;iMainMenu1-Items-Count;i++) / D! O4 A- h4 ~
{ 1 s9 c2 c) G" ~3 k$ D
Modify(MainMenu1-Items-Items); 3 ^& K/ @1 ?8 W: S* |
}
e4 c8 j1 g3 V9 a$ UDrawMenuBar(Handle);
( n/ M: q: z+ @# h) G A: ?} - _7 h( G9 _- A! }% V( E
//---------------------------------------------------------------------------
0 m. H; a5 j! U+ Xvoid __fastcall TForm1::CNMeasureItem(TWMMeasureItem Msg)
9 X4 s4 D; Y$ _/ J3 ]- ?! ?1 P{//设置菜单大小
% ?0 s7 i( t7 O- m. a3 a5 z4 x* XTMenuItem *pItem=MainMenu1-FindItem(Msg.MeasureItemStruct-itemData,fkHandle);
0 V8 K9 w9 T f3 o; \- F4 m$ s4 eMsg.MeasureItemStruct-itemWidth =pItem-Caption.Length()*8+40; / a. I( Y& w, d: v; \7 L; V4 `
Msg.MeasureItemStruct-itemHeight = 20;
% ^" V, T' O3 {, _# P$ G2 B: N/ x) C0 L} 8 N. Z( G9 p( t2 t
void __fastcall TForm1::CNDrawItem(TWMDrawItem Msg) 8 ?+ k% w4 y! k6 h5 u& }# R9 H
{//画出菜单
Q- w3 }2 y X8 _5 R- X& WTMenuItem *pItem=MainMenu1-FindItem(Msg.DrawItemStruct-itemData,fkHandle);
. p% ] S. L! k: i: K c, OTCanvas *pCanvas=new TCanvas;
& @+ ]; K: I: j( V' A7 e* OpCanvas-Handle=Msg.DrawItemStruct-hDC; * ^1 s' L6 n' c& [
RECT r=Msg.DrawItemStruct-rcItem; 4 F! Q7 h+ d H1 b" _, H! _
pCanvas-Brush-Color=clBtnFace; + E+ U1 B3 w, ^, l$ s
RECT r1=r; . g J; ~4 `0 F; k& u# n" o9 |
r1.right+=1; 5 G0 T& _7 Z* A6 \) {( U p
r1.bottom+=1; * e% e9 L+ H E/ M C% |7 r
r1.top-=1; # l0 N m+ C9 M8 A; ^' d
r1.left-=1; : o( i8 L4 m2 J5 @
pCanvas-FillRect(r);
: ?/ M. M" T* q1 v7 z% a& r# ]- _::SetBkMode(pCanvas-Handle,TRANSPARENT); * q1 P- x A5 R3 W2 ~
pCanvas-TextOut(r.left+10,r.top+2,pItem-Caption); 1 }5 I$ W/ R Q/ @% v3 d
r.right-=1; 8 ?2 g% U7 e- i% A" d1 R; H0 Q
r.bottom-=1; + k( P' i8 o: ?. t1 ? o( l
if(Msg.DrawItemStruct-itemAction == ODA_SELECT
2 e0 g9 B! @. r# }3 aMsg.DrawItemStruct-itemStateODS_SELECTED ) * |0 C8 z" I; k8 Q" r ?( v; |
{
4 I; Q3 r4 \, C4 f9 W4 }! L1 FpCanvas-Pen-Color=(TColor)(RGB(255,255,255));
x% _4 g% m/ w* |9 `) LpCanvas-MoveTo(r.right,r.top); 6 \% \' [/ h0 ~! b' y
pCanvas-LineTo(r.left,r.top);
8 ?, Z3 V( t& @: p& jpCanvas-LineTo(r.left,r.bottom);
5 t0 j* `# I+ j$ H4 K, i2 k# RpCanvas-Pen-Color=(TColor)(RGB(128,128,128));
( ^. S# X! a1 RpCanvas-LineTo(r.right,r.bottom); ' a6 u+ ]9 z: u4 ~: z! a
pCanvas-LineTo(r.right,r.top);
2 E; Q- ?, y* f- e4 S}
/ K& N8 o2 F. P2 X4 G* o& g5 O$ m2 L5 t$ `
} |