首页 > 解决方案 > Gtk3:GMenu/GMenuItem:如何感知是否打开了子菜单?(子菜单的信号)

问题描述

我的应用程序在顶部栏中有一个“编辑”菜单。我想在菜单打开时更改其内容的灵敏度(启用/禁用)和可见性。

我正在使用 GMenu / GMenuItem 创建菜单。当子菜单打开时,我如何感知?

评论:

我如何创建我的菜单:

{
  GMenu * menubar = g_menu_new();

  GMenu * edit = g_menu_new();
  g_menu_append_submenu(menubar,"_Edit", G_MENU_MODEL(edit));

  g_menu_append(edit, "_Copy" ,   "edit.copy"   );    
  g_menu_append(edit, "_Paste",   "edit.paste"  );    
       
  gtk_application_set_menubar(app, G_MENU_MODEL(menubar));
}

标签: cmenugtkgtk3submenu

解决方案


您需要使用属性submenu-action。这不会给你一个“on-open”回调,而是一个“on-open”或“on-close”回调。但它可能是你能得到的最接近的。

从菜单文件中使用它:

是一个如何在 ui 文件中使用它的示例:

<submenu id="time-menu">
  <attribute name="label" translatable="yes">Time</attribute>
  <attribute name="submenu-action">app.time-active</attribute>
</submenu>

从 API 使用它

从 API 中使用它有点棘手:您需要创建一个 GMenuItem,它包含您的GMenu * editas 子菜单。

建筑学:

GMenu (menubar)
   |
   |-- GMenuItem ("Edit" (edit_item))  <-- new part
          |
          |-- GMenu (edit_content)
                 |
                 |-- GMenuItem ("Copy") 
                 |
                 |-- GMenuItem ("Paste")                                             

示例代码

{
  GMenu * menubar = g_menu_new ();

  // Container for all menu items of the "Edit" menu
  GMenu * edit_content = g_menu_new ();
  {
    g_menu_append (edit_content, "_Copy" ,   "edit.copy" );    
    g_menu_append (edit_content, "_Paste",   "edit.paste");    
  }

  // create the "Edit" menu button, that has an "on-click" event
  GMenuItem * edit_menu;
  {
    edit_menu = g_menu_item_new ("Edit", "randomAction"); // (the action will be discarded later)
    // set action, that's fired up on click
    g_menu_item_set_attribute (edit_menu,"submenu-action", "&s", 
                                "app.menu_edit_clicked", NULL);      
    // insert the content of menu
    g_menu_item_set_submenu (edit_menu, G_MENU_MODEL (edit_content));      
    // add it to window
    g_menu_append_item (menubar, edit_menu);

    // set the on-click action(s) for the submenu
    GActionEntry actions[] = {
      {.name="menu_edit_clicked", .state="false", 
       .change_state=dt_window_menu_on_click}
    };
    g_action_map_add_action_entries (G_ACTION_MAP (app), actions, G_N_ELEMENTS (actions), NULL);
  }

  gtk_application_set_menubar (app, G_MENU_MODEL (menubar));


  g_object_unref (menubar);
}

推荐阅读