|
我们知道,C++Builder没有自画菜单,但可以调用API函数::SetMenuItemInfo()来改
( |' [, @. C; A) _变菜单类型,达到自画菜单的目的。下面的例子演示了如何使用自画菜单。当鼠标位于菜单
! b$ N( \: e d4 @, F1 W3 R8 t+ O上拾,菜单项将凸出来。(黑体字为添加的代码) H5 s0 G! `8 g0 j
5 @, A- A5 d% a! G' w//头文件 4 k, ^" ~% ]5 l- ?2 p, W4 [
//------------------------------------------
) q* d% S3 v/ K" B#ifndef TestMenuH , E t x* E5 s' x- R* C' G
#define TestMenuH
8 p1 G6 c9 V/ @7 x//----------------------------------------- ) X# P7 K- P. f( T( R8 w1 G# o" U& }# n
#include Classes.hpp
9 w' \/ i2 ^; B6 }#include Controls.hpp 0 w6 X. ?* H+ h$ {- G
#include StdCtrls.hpp
S! J9 G/ B7 c3 E1 b& T! M0 V1 y9 C: B#include Forms.hpp
q6 X, X" ?1 K) G! z- S#include Menus.hpp//-------------------- 7 Z* s( @ U& n$ O) i6 a/ _
/ l% Y) h& I$ Jclass TForm1 : public TForm
: Q3 `3 Y) ~7 G7 B* c, I( L{
) u; i9 H* C% A6 `__published: // IDE-managed Components
( U6 _$ ?" d/ A! c6 t" Y# PTMainMenu *MainMenu1;
) p, B2 Y4 s D2 J4 D* C: uTMenuItem *aaa1; * W' I y/ {! ]- F' B: K
TMenuItem *aaaaaaaaa1;
& `4 t8 u3 u1 h% K' qTMenuItem *ccc1;
6 I `3 N4 m; D( h/ dTMenuItem *ddd1;
" J7 Y( Y. A" O+ H0 x% Y2 nTMenuItem *eee1; ! B! y# ]1 @/ l: U+ e4 i% N+ @5 m
TMenuItem *ddsds1;
! Y1 a/ D {8 VTMenuItem *fcdfsss1;
F1 W8 i8 m+ v" P8 FTMenuItem *dddddddd1; / k% f7 R5 r: L' U& x. W9 j) S; g
void __fastcall FormCreate(TObject *Sender); ! L* G( U. y( T+ b
private: // User declarations * ~+ L) S. U9 H1 H H) _
void __fastcall Modify(TMenuItem *pMenuItem);
3 w4 R7 M5 f5 K/ qprotected : ' ~! h6 ]. @8 _$ g8 v1 j, J* N
MESSAGE void __fastcall CNMeasureItem(TWMMeasureItem Msg);//增加响应消息 - H+ x8 o# _" Z; w! c; O
MESSAGE void __fastcall CNDrawItem(TWMDrawItem Msg); ! {* v* `7 p' |, A
public: // User declarations + a7 [. I2 Q/ t9 G( E+ b
__fastcall TForm1(TComponent* Owner); 9 I; ]5 u" o+ k0 b5 Z* X. F
BEGIN_MESSAGE_MAP//添加消息映射 9 L) ` \; Z) w. u5 p! b% @! Y& Z1 y
VCL_MESSAGE_HANDLER(WM_MEASUREITEM, TWMMeasureItem, CNMeasureItem); ; e9 }0 w8 J! X1 d- t! s6 G
VCL_MESSAGE_HANDLER( WM_DRAWITEM, TWMDrawItem, CNDrawItem);
" G7 P) l$ ]4 O/ REND_MESSAGE_MAP(TForm);
- O$ z0 ]+ g- h};
/ {4 |! R U6 G" M$ A% Y//--------------------------------------------------------------------------- * t- k$ u' p6 x; r2 v) k/ h
extern PACKAGE TForm1 *Form1;
) b* |5 G$ Y: c, M6 z0 c//---------------------------------------------------------------------------
3 h2 w2 D7 S% ~" [" Y" k#endif
7 [- [8 ?! _3 m. \ , T3 B5 j% i7 x% ?) p, F
//实现文件 ( H/ J( L4 x( x% g5 V
//---------------------------------------------------------------------------
+ `4 N+ |0 E. B8 w$ {5 ^( u/ w#include vcl.h 3 R$ P& _' V& l, e) l$ h9 h
#pragma hdrstop
6 f; Y1 P3 i$ Z/ u6 \0 F
' z! s; g; c |/ v; g1 U' v#include TestMenu.h
3 F* k3 f. S5 w6 B/ A/ N" o8 I( x5 g//--------------------------------------------------------------------------- Y7 G6 H0 g; q; w
#pragma package(smart_init) ) T: H* ~" c8 t: G w5 C
#pragma resource *.dfm 6 F# h: z# b6 ]( _# K
TForm1 *Form1;
% A5 Y2 B# i* b% t% K//---------------------------------------------------------------------------
+ [/ j# K: E& I4 v. |; q+ x__fastcall TForm1::TForm1(TComponent* Owner) 2 w" a9 G& J; W- M' I" s
: TForm(Owner) $ B$ B; ^7 ?; m }8 m# O
{ " ]/ E+ B% _- c) k' ]# Z! l
}
- g# Y! R8 [' F9 f//---------------------------------------------------------------------------
, D+ m8 y* z5 _! w3 |2 [- |! }4 o
$ u t3 O ?+ _" _7 Qvoid __fastcall TForm1::Modify(TMenuItem *pMenuItem)
5 Z% K5 G; j( y4 J' j( i' e! i; u7 c{//修改缺省属性 ; t" H/ j* ]! I+ V x: N/ w4 U
for(int i=0;ipMenuItem-Count;i++)
, g8 G4 Y/ d' k( V{ 3 n+ ^# t& c7 U! k4 e2 e# c1 N
MENUITEMINFO mii=
: p, j n3 e: n! B' v7 Z{
: H; c8 T* i$ v: [sizeof(MENUITEMINFO), - ? H" ~* R% h. G `
MIIM_TYPE|MIIM_DATA ,//改变类型和数据 - B4 M) e+ Z# F2 ~* ~1 @ ]8 a
MF_OWNERDRAW,0,0,0,0,0,DWORD(pMenuItem-Items-Handle), 5 n) I& u7 P# o( p) l- w/ A" j
//把菜单项的句柄赋给32位数据 2 |, b9 l, ~ A! F+ ?
0, : y3 W! `% U0 | \, o# Z/ ]0 M. U
0, 4 k3 P- c8 \9 i, d
}; / Y4 f9 E9 }8 }1 {3 |+ `
if(pMenuItem-Items-Caption!=-)//如果不是间隔线 5 \# k, E5 H. L8 o, q% M
::SetMenuItemInfo(pMenuItem-Handle,i,TRUE,mii); , [/ L" G! _1 ^1 a
if(pMenuItem-Items-Count)//如果含有子菜单 , }: W. p6 \& m- k& C# o) G' u/ |( ^
Modify(pMenuItem-Items);
8 C$ \2 E$ q/ s4 N} 2 U9 ^0 G# g6 H: C
& K$ c- l* D) z# F6 q
}
9 X" H8 j, M7 C- D& f( C/ Mvoid __fastcall TForm1::FormCreate(TObject *Sender) 3 \! D% O2 O* [. W9 ?; w
{
1 V/ h, M& a6 y3 F& Z# e/ Sfor(int i=0;iMainMenu1-Items-Count;i++)
* [4 ?7 L( p$ T' Z) e{ " B# }! x! V: u
Modify(MainMenu1-Items-Items); % u$ z: ]2 k/ S1 x
} ; _2 I+ X5 [( Z+ t# f
DrawMenuBar(Handle); 2 k" x/ \% e! J- w
} ' [, p; C) i9 t3 m, A- t# b O
//--------------------------------------------------------------------------- 8 I$ l9 ^3 f0 q- J/ m) h) [ w* T& E
void __fastcall TForm1::CNMeasureItem(TWMMeasureItem Msg) + e5 }/ x% ~8 |4 ?2 g4 j
{//设置菜单大小 * d& u7 [* A% ]- t
TMenuItem *pItem=MainMenu1-FindItem(Msg.MeasureItemStruct-itemData,fkHandle); 5 m, J% U6 ?2 t+ V3 B9 h
Msg.MeasureItemStruct-itemWidth =pItem-Caption.Length()*8+40; , ], H2 T$ W- V! m" T
Msg.MeasureItemStruct-itemHeight = 20; ; f P7 h4 N) S8 ?6 S# C- R. v
} - p& J8 E- y! D( U* k) i- v
void __fastcall TForm1::CNDrawItem(TWMDrawItem Msg)
' a2 _- V% E2 e- x. J{//画出菜单
" \* g" b5 [! Z" CTMenuItem *pItem=MainMenu1-FindItem(Msg.DrawItemStruct-itemData,fkHandle);
* x8 K; L" S# u/ i' R. yTCanvas *pCanvas=new TCanvas;
, a7 Y3 i8 Z; b+ c( m: upCanvas-Handle=Msg.DrawItemStruct-hDC; 5 h |& H+ p1 U" r, d
RECT r=Msg.DrawItemStruct-rcItem; 1 B, X' l1 l* j1 E# J' D
pCanvas-Brush-Color=clBtnFace;
9 \% U w5 @1 O% m( p6 P4 gRECT r1=r; 5 h5 s( a& q' s& D5 M
r1.right+=1;
' ~' v- V/ q2 Y9 xr1.bottom+=1;
& d8 m" k% \, qr1.top-=1;
, M, j; g z9 _5 ^r1.left-=1; ' D) @, d% l5 h0 n9 ~, ~
pCanvas-FillRect(r);
3 x+ k# A q% w0 q::SetBkMode(pCanvas-Handle,TRANSPARENT); 5 e! {& m, g/ t! c5 f: D2 K# D
pCanvas-TextOut(r.left+10,r.top+2,pItem-Caption); : I6 l6 c$ Z' k' s; u- ]
r.right-=1;
/ v4 s( ?" N* y$ p0 [0 ur.bottom-=1;
3 H# e9 Q! N, {1 K& hif(Msg.DrawItemStruct-itemAction == ODA_SELECT 9 @: m* p; |6 v& k/ j
Msg.DrawItemStruct-itemStateODS_SELECTED ) . ^5 V# d, H$ m \; X# J; V- F9 @
{ % q1 ^; H ?" [1 f
pCanvas-Pen-Color=(TColor)(RGB(255,255,255));
2 Y0 I( M7 L5 M" J- [' zpCanvas-MoveTo(r.right,r.top);
5 D! H# @' N/ E) \pCanvas-LineTo(r.left,r.top); 4 q, C9 o; ^/ F6 Q7 }, B1 k
pCanvas-LineTo(r.left,r.bottom);
& f f, H, |' o) Z" P* _1 XpCanvas-Pen-Color=(TColor)(RGB(128,128,128)); ( l! R3 P- x9 X5 k- K& H
pCanvas-LineTo(r.right,r.bottom);
- c* R9 i; m; B# `8 @# \pCanvas-LineTo(r.right,r.top);
" Q' Y$ t( z$ z& @# u}
% q$ L0 @/ T9 [5 t, I' L* A! f
, }- Q% T* P u( \$ J& W9 w} |