zoukankan      html  css  js  c++  java
  • Delphi中Menu设置Images属性后快捷按键下划线被隐藏解决方法

    现象:
    MainMenu设置Images属性后,看不到快捷按键的下划线,如:新建(&N)

    分析:
    VCL中Menus.pas单元的代码,看到如下语句
    procedure TMenuItem.AdvancedDrawItem(ACanvas: TCanvas; ARect: TRect;
      State: TOwnerDrawState; TopLevel: Boolean);
    //...
    if Win2K and (odNoAccel in State) then
      DrawStyle := DrawStyle or DT_HIDEPREFIX;
    //...

    DT_HIDEPREFIX就是隐藏下划线 //用DrawText()测试一下就知道

    在设置Images属性后(odNoAccel in State)为真

    看来需要自绘菜单,响应OnAdvancedDrawItem事件

    当然,自绘菜单的代码写起来就多了,还好AdvancedDrawItem()声明在protected部分
    我们可以通过继承TMenuItem来访问AdvancedDrawItem()
    type
      TMenuItemAccess = class(TMenuItem);

    现在就要想办法使那个条件不成立,先从Win2K入手
    当Images设置后"Win2K and (odNoAccel in State)"这个条件成立

    分析单元中Win2K变量是这样得到的
    Win2K := (Win32MajorVersion > 4) and (Win32Platform = VER_PLATFORM_WIN32_NT);

    那么我们就可以通过修改Win32MajorVersion或者Win32Platform常量使其不成立

    参考代码:

    type

      TForm1 = class(TForm)

        MainMenu1: TMainMenu;

        ImageList1: TImageList;

        MenuItemFile: TMenuItem;

        MenuItemNew: TMenuItem;

        MenuItemOpen: TMenuItem;

        PopupMenu1: TPopupMenu;

        MenuItemCopy: TMenuItem;

        MenuItemPaste: TMenuItem;

        procedure FormCreate(Sender: TObject);

      private

        { Private declarations }

        procedure MenuItemAdvancedDrawItem(Sender: TObject; ACanvas: TCanvas;

          ARect: TRect; State: TOwnerDrawState);

      public

        { Public declarations }

      end;

     

    var

      Form1: TForm1;

     

    implementation

     

    {$R *.dfm}

     

    type

      TMenuItemAccess = class(TMenuItem);

     

    procedure TForm1.MenuItemAdvancedDrawItem(Sender: TObject; ACanvas: TCanvas;

      ARect: TRect; State: TOwnerDrawState);

    var

      vWin32Platform: Integer;

    begin

      vWin32Platform := PInteger(@Win32Platform)^;

      PInteger(@Win32Platform)^ := -1;

      TMenuItemAccess(Sender).OnAdvancedDrawItem := nil;

      try

        TMenuItemAccess(Sender).AdvancedDrawItem(ACanvas, ARect, State,

          TMenuItemAccess(Sender).GetParentComponent is TMainMenu);

      finally

        TMenuItemAccess(Sender).OnAdvancedDrawItem := MenuItemAdvancedDrawItem;

        PInteger(@Win32Platform)^ := vWin32Platform;

      end;

    end;

     

    procedure TForm1.FormCreate(Sender: TObject);

    var

      I: Integer;

    begin

      for I := 0 to ComponentCount - 1 do

        if Components[I] is TMenuItem then

          TMenuItem(Components[I]).OnAdvancedDrawItem := MenuItemAdvancedDrawItem

        else if Components[I] is TMenu then

          TMenu(Components[I]).OwnerDraw := True;

    end;

     

    http://blog.csdn.net/zswang/article/details/1653340

  • 相关阅读:
    linux下51单片机开发解决方案
    ubuntu下virtualbox配置hostonly网络
    标准c头文件
    linux下vim和bash配置文件
    排序算法
    系统空闲一段时间后关闭指定进程
    c常用字符串函数
    lubuntu自动登录(lxde)
    开源软件发展史
    awk命令(语言)
  • 原文地址:https://www.cnblogs.com/findumars/p/6348035.html
Copyright © 2011-2022 走看看