| OLD | NEW |
| 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "chrome/browser/ui/gtk/menu_gtk.h" | 5 #include "chrome/browser/ui/gtk/menu_gtk.h" |
| 6 | 6 |
| 7 #include <map> | 7 #include <map> |
| 8 | 8 |
| 9 #include "base/bind.h" | 9 #include "base/bind.h" |
| 10 #include "base/i18n/rtl.h" | 10 #include "base/i18n/rtl.h" |
| 11 #include "base/logging.h" | 11 #include "base/logging.h" |
| 12 #include "base/message_loop.h" | 12 #include "base/message_loop.h" |
| 13 #include "base/stl_util.h" | 13 #include "base/stl_util.h" |
| 14 #include "base/utf_string_conversions.h" | 14 #include "base/utf_string_conversions.h" |
| 15 #include "chrome/app/chrome_command_ids.h" | 15 #include "chrome/app/chrome_command_ids.h" |
| 16 #include "chrome/browser/ui/gtk/event_utils.h" | 16 #include "chrome/browser/ui/gtk/event_utils.h" |
| 17 #include "chrome/browser/ui/gtk/gtk_custom_menu.h" | 17 #include "chrome/browser/ui/gtk/gtk_custom_menu.h" |
| 18 #include "chrome/browser/ui/gtk/gtk_custom_menu_item.h" | 18 #include "chrome/browser/ui/gtk/gtk_custom_menu_item.h" |
| 19 #include "chrome/browser/ui/gtk/gtk_util.h" | 19 #include "chrome/browser/ui/gtk/gtk_util.h" |
| 20 #include "third_party/skia/include/core/SkBitmap.h" | 20 #include "third_party/skia/include/core/SkBitmap.h" |
| 21 #include "ui/base/accelerators/accelerator_gtk.h" | 21 #include "ui/base/accelerators/accelerator_gtk.h" |
| 22 #include "ui/base/gtk/menu_label_accelerator_util.h" | 22 #include "ui/base/gtk/menu_label_accelerator_util.h" |
| 23 #include "ui/base/models/button_menu_item_model.h" | 23 #include "ui/base/models/button_menu_item_model.h" |
| 24 #include "ui/base/models/menu_model.h" | 24 #include "ui/base/models/menu_model.h" |
| 25 #include "ui/gfx/gtk_util.h" | 25 #include "ui/gfx/gtk_util.h" |
| 26 #include "ui/gfx/image/image.h" |
| 26 #include "webkit/glue/window_open_disposition.h" | 27 #include "webkit/glue/window_open_disposition.h" |
| 27 | 28 |
| 28 bool MenuGtk::block_activation_ = false; | 29 bool MenuGtk::block_activation_ = false; |
| 29 | 30 |
| 30 namespace { | 31 namespace { |
| 31 | 32 |
| 32 // Sets the ID of a menu item. | 33 // Sets the ID of a menu item. |
| 33 void SetMenuItemID(GtkWidget* menu_item, int menu_id) { | 34 void SetMenuItemID(GtkWidget* menu_item, int menu_id) { |
| 34 DCHECK_GE(menu_id, 0); | 35 DCHECK_GE(menu_id, 0); |
| 35 | 36 |
| (...skipping 283 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 319 | 320 |
| 320 GtkWidget* MenuGtk::AppendMenuItemWithLabel(int command_id, | 321 GtkWidget* MenuGtk::AppendMenuItemWithLabel(int command_id, |
| 321 const std::string& label) { | 322 const std::string& label) { |
| 322 std::string converted_label = ui::ConvertAcceleratorsFromWindowsStyle(label); | 323 std::string converted_label = ui::ConvertAcceleratorsFromWindowsStyle(label); |
| 323 GtkWidget* menu_item = BuildMenuItemWithLabel(label, command_id); | 324 GtkWidget* menu_item = BuildMenuItemWithLabel(label, command_id); |
| 324 return AppendMenuItem(command_id, menu_item); | 325 return AppendMenuItem(command_id, menu_item); |
| 325 } | 326 } |
| 326 | 327 |
| 327 GtkWidget* MenuGtk::AppendMenuItemWithIcon(int command_id, | 328 GtkWidget* MenuGtk::AppendMenuItemWithIcon(int command_id, |
| 328 const std::string& label, | 329 const std::string& label, |
| 329 const SkBitmap& icon) { | 330 const gfx::Image& icon) { |
| 330 std::string converted_label = ui::ConvertAcceleratorsFromWindowsStyle(label); | 331 std::string converted_label = ui::ConvertAcceleratorsFromWindowsStyle(label); |
| 331 GtkWidget* menu_item = BuildMenuItemWithImage(converted_label, icon); | 332 GtkWidget* menu_item = BuildMenuItemWithImage(converted_label, icon); |
| 332 return AppendMenuItem(command_id, menu_item); | 333 return AppendMenuItem(command_id, menu_item); |
| 333 } | 334 } |
| 334 | 335 |
| 335 GtkWidget* MenuGtk::AppendCheckMenuItemWithLabel(int command_id, | 336 GtkWidget* MenuGtk::AppendCheckMenuItemWithLabel(int command_id, |
| 336 const std::string& label) { | 337 const std::string& label) { |
| 337 std::string converted_label = ui::ConvertAcceleratorsFromWindowsStyle(label); | 338 std::string converted_label = ui::ConvertAcceleratorsFromWindowsStyle(label); |
| 338 GtkWidget* menu_item = | 339 GtkWidget* menu_item = |
| 339 gtk_check_menu_item_new_with_mnemonic(converted_label.c_str()); | 340 gtk_check_menu_item_new_with_mnemonic(converted_label.c_str()); |
| (...skipping 79 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 419 | 420 |
| 420 GtkWidget* MenuGtk::BuildMenuItemWithImage(const std::string& label, | 421 GtkWidget* MenuGtk::BuildMenuItemWithImage(const std::string& label, |
| 421 GtkWidget* image) { | 422 GtkWidget* image) { |
| 422 GtkWidget* menu_item = | 423 GtkWidget* menu_item = |
| 423 gtk_image_menu_item_new_with_mnemonic(label.c_str()); | 424 gtk_image_menu_item_new_with_mnemonic(label.c_str()); |
| 424 gtk_image_menu_item_set_image(GTK_IMAGE_MENU_ITEM(menu_item), image); | 425 gtk_image_menu_item_set_image(GTK_IMAGE_MENU_ITEM(menu_item), image); |
| 425 return menu_item; | 426 return menu_item; |
| 426 } | 427 } |
| 427 | 428 |
| 428 GtkWidget* MenuGtk::BuildMenuItemWithImage(const std::string& label, | 429 GtkWidget* MenuGtk::BuildMenuItemWithImage(const std::string& label, |
| 429 const SkBitmap& icon) { | 430 const gfx::Image& icon) { |
| 430 GdkPixbuf* pixbuf = gfx::GdkPixbufFromSkBitmap(icon); | |
| 431 GtkWidget* menu_item = BuildMenuItemWithImage(label, | 431 GtkWidget* menu_item = BuildMenuItemWithImage(label, |
| 432 gtk_image_new_from_pixbuf(pixbuf)); | 432 gtk_image_new_from_pixbuf(icon.ToGdkPixbuf())); |
| 433 g_object_unref(pixbuf); | |
| 434 return menu_item; | 433 return menu_item; |
| 435 } | 434 } |
| 436 | 435 |
| 437 GtkWidget* MenuGtk::BuildMenuItemWithLabel(const std::string& label, | 436 GtkWidget* MenuGtk::BuildMenuItemWithLabel(const std::string& label, |
| 438 int command_id) { | 437 int command_id) { |
| 439 GtkWidget* img = | 438 GtkWidget* img = |
| 440 delegate_ ? delegate_->GetImageForCommandId(command_id) : | 439 delegate_ ? delegate_->GetImageForCommandId(command_id) : |
| 441 MenuGtk::Delegate::GetDefaultImageForCommandId(command_id); | 440 MenuGtk::Delegate::GetDefaultImageForCommandId(command_id); |
| 442 return img ? BuildMenuItemWithImage(label, img) : | 441 return img ? BuildMenuItemWithImage(label, img) : |
| 443 gtk_menu_item_new_with_mnemonic(label.c_str()); | 442 gtk_menu_item_new_with_mnemonic(label.c_str()); |
| 444 } | 443 } |
| 445 | 444 |
| 446 void MenuGtk::BuildMenuFromModel() { | 445 void MenuGtk::BuildMenuFromModel() { |
| 447 BuildSubmenuFromModel(model_, menu_); | 446 BuildSubmenuFromModel(model_, menu_); |
| 448 } | 447 } |
| 449 | 448 |
| 450 void MenuGtk::BuildSubmenuFromModel(ui::MenuModel* model, GtkWidget* menu) { | 449 void MenuGtk::BuildSubmenuFromModel(ui::MenuModel* model, GtkWidget* menu) { |
| 451 std::map<int, GtkWidget*> radio_groups; | 450 std::map<int, GtkWidget*> radio_groups; |
| 452 GtkWidget* menu_item = NULL; | 451 GtkWidget* menu_item = NULL; |
| 453 for (int i = 0; i < model->GetItemCount(); ++i) { | 452 for (int i = 0; i < model->GetItemCount(); ++i) { |
| 454 gfx::ImageSkia icon; | 453 gfx::Image icon; |
| 455 std::string label = ui::ConvertAcceleratorsFromWindowsStyle( | 454 std::string label = ui::ConvertAcceleratorsFromWindowsStyle( |
| 456 UTF16ToUTF8(model->GetLabelAt(i))); | 455 UTF16ToUTF8(model->GetLabelAt(i))); |
| 457 bool connect_to_activate = true; | 456 bool connect_to_activate = true; |
| 458 | 457 |
| 459 switch (model->GetTypeAt(i)) { | 458 switch (model->GetTypeAt(i)) { |
| 460 case ui::MenuModel::TYPE_SEPARATOR: | 459 case ui::MenuModel::TYPE_SEPARATOR: |
| 461 menu_item = gtk_separator_menu_item_new(); | 460 menu_item = gtk_separator_menu_item_new(); |
| 462 break; | 461 break; |
| 463 | 462 |
| 464 case ui::MenuModel::TYPE_CHECK: | 463 case ui::MenuModel::TYPE_CHECK: |
| (...skipping 18 matching lines...) Expand all Loading... |
| 483 ui::ButtonMenuItemModel* button_menu_item_model = | 482 ui::ButtonMenuItemModel* button_menu_item_model = |
| 484 model->GetButtonMenuItemAt(i); | 483 model->GetButtonMenuItemAt(i); |
| 485 menu_item = BuildButtonMenuItem(button_menu_item_model, menu); | 484 menu_item = BuildButtonMenuItem(button_menu_item_model, menu); |
| 486 connect_to_activate = false; | 485 connect_to_activate = false; |
| 487 break; | 486 break; |
| 488 } | 487 } |
| 489 case ui::MenuModel::TYPE_SUBMENU: | 488 case ui::MenuModel::TYPE_SUBMENU: |
| 490 case ui::MenuModel::TYPE_COMMAND: { | 489 case ui::MenuModel::TYPE_COMMAND: { |
| 491 int command_id = model->GetCommandIdAt(i); | 490 int command_id = model->GetCommandIdAt(i); |
| 492 if (model->GetIconAt(i, &icon)) | 491 if (model->GetIconAt(i, &icon)) |
| 493 menu_item = BuildMenuItemWithImage(label, *icon.bitmap()); | 492 menu_item = BuildMenuItemWithImage(label, icon); |
| 494 else | 493 else |
| 495 menu_item = BuildMenuItemWithLabel(label, command_id); | 494 menu_item = BuildMenuItemWithLabel(label, command_id); |
| 496 if (delegate_ && delegate_->AlwaysShowIconForCmd(command_id) && | 495 if (delegate_ && delegate_->AlwaysShowIconForCmd(command_id) && |
| 497 GTK_IS_IMAGE_MENU_ITEM(menu_item)) { | 496 GTK_IS_IMAGE_MENU_ITEM(menu_item)) { |
| 498 gtk_util::SetAlwaysShowImage(menu_item); | 497 gtk_util::SetAlwaysShowImage(menu_item); |
| 499 } | 498 } |
| 500 break; | 499 break; |
| 501 } | 500 } |
| 502 | 501 |
| 503 default: | 502 default: |
| (...skipping 374 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 878 gtk_widget_set_sensitive(widget, model->IsEnabledAt(id)); | 877 gtk_widget_set_sensitive(widget, model->IsEnabledAt(id)); |
| 879 | 878 |
| 880 if (model->IsVisibleAt(id)) { | 879 if (model->IsVisibleAt(id)) { |
| 881 // Update the menu item label if it is dynamic. | 880 // Update the menu item label if it is dynamic. |
| 882 if (model->IsItemDynamicAt(id)) { | 881 if (model->IsItemDynamicAt(id)) { |
| 883 std::string label = ui::ConvertAcceleratorsFromWindowsStyle( | 882 std::string label = ui::ConvertAcceleratorsFromWindowsStyle( |
| 884 UTF16ToUTF8(model->GetLabelAt(id))); | 883 UTF16ToUTF8(model->GetLabelAt(id))); |
| 885 | 884 |
| 886 gtk_menu_item_set_label(GTK_MENU_ITEM(widget), label.c_str()); | 885 gtk_menu_item_set_label(GTK_MENU_ITEM(widget), label.c_str()); |
| 887 if (GTK_IS_IMAGE_MENU_ITEM(widget)) { | 886 if (GTK_IS_IMAGE_MENU_ITEM(widget)) { |
| 888 gfx::ImageSkia icon; | 887 gfx::Image icon; |
| 889 if (model->GetIconAt(id, &icon)) { | 888 if (model->GetIconAt(id, &icon)) { |
| 890 GdkPixbuf* pixbuf = gfx::GdkPixbufFromSkBitmap(*icon.bitmap()); | |
| 891 gtk_image_menu_item_set_image(GTK_IMAGE_MENU_ITEM(widget), | 889 gtk_image_menu_item_set_image(GTK_IMAGE_MENU_ITEM(widget), |
| 892 gtk_image_new_from_pixbuf(pixbuf)); | 890 gtk_image_new_from_pixbuf( |
| 893 g_object_unref(pixbuf); | 891 icon.ToGdkPixbuf())); |
| 894 } else { | 892 } else { |
| 895 gtk_image_menu_item_set_image(GTK_IMAGE_MENU_ITEM(widget), NULL); | 893 gtk_image_menu_item_set_image(GTK_IMAGE_MENU_ITEM(widget), NULL); |
| 896 } | 894 } |
| 897 } | 895 } |
| 898 } | 896 } |
| 899 | 897 |
| 900 gtk_widget_show(widget); | 898 gtk_widget_show(widget); |
| 901 } else { | 899 } else { |
| 902 gtk_widget_hide(widget); | 900 gtk_widget_hide(widget); |
| 903 } | 901 } |
| 904 | 902 |
| 905 GtkWidget* submenu = gtk_menu_item_get_submenu(GTK_MENU_ITEM(widget)); | 903 GtkWidget* submenu = gtk_menu_item_get_submenu(GTK_MENU_ITEM(widget)); |
| 906 if (submenu) { | 904 if (submenu) { |
| 907 gtk_container_foreach(GTK_CONTAINER(submenu), &SetMenuItemInfo, | 905 gtk_container_foreach(GTK_CONTAINER(submenu), &SetMenuItemInfo, |
| 908 userdata); | 906 userdata); |
| 909 } | 907 } |
| 910 } | 908 } |
| 911 } | 909 } |
| OLD | NEW |