atom_api_menu.cc 6.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231
  1. // Copyright (c) 2013 GitHub, Inc.
  2. // Use of this source code is governed by the MIT license that can be
  3. // found in the LICENSE file.
  4. #include "atom/browser/api/atom_api_menu.h"
  5. #include "atom/browser/native_window.h"
  6. #include "atom/common/native_mate_converters/accelerator_converter.h"
  7. #include "atom/common/native_mate_converters/callback.h"
  8. #include "atom/common/native_mate_converters/image_converter.h"
  9. #include "atom/common/native_mate_converters/string16_converter.h"
  10. #include "native_mate/constructor.h"
  11. #include "native_mate/dictionary.h"
  12. #include "native_mate/object_template_builder.h"
  13. #include "atom/common/node_includes.h"
  14. namespace atom {
  15. namespace api {
  16. Menu::Menu(v8::Isolate* isolate, v8::Local<v8::Object> wrapper)
  17. : model_(new AtomMenuModel(this)) {
  18. InitWith(isolate, wrapper);
  19. model_->AddObserver(this);
  20. }
  21. Menu::~Menu() {
  22. if (model_) {
  23. model_->RemoveObserver(this);
  24. }
  25. }
  26. void Menu::AfterInit(v8::Isolate* isolate) {
  27. mate::Dictionary wrappable(isolate, GetWrapper());
  28. mate::Dictionary delegate;
  29. if (!wrappable.Get("delegate", &delegate))
  30. return;
  31. delegate.Get("isCommandIdChecked", &is_checked_);
  32. delegate.Get("isCommandIdEnabled", &is_enabled_);
  33. delegate.Get("isCommandIdVisible", &is_visible_);
  34. delegate.Get("getAcceleratorForCommandId", &get_accelerator_);
  35. delegate.Get("executeCommand", &execute_command_);
  36. delegate.Get("menuWillShow", &menu_will_show_);
  37. }
  38. bool Menu::IsCommandIdChecked(int command_id) const {
  39. v8::Locker locker(isolate());
  40. v8::HandleScope handle_scope(isolate());
  41. return is_checked_.Run(GetWrapper(), command_id);
  42. }
  43. bool Menu::IsCommandIdEnabled(int command_id) const {
  44. v8::Locker locker(isolate());
  45. v8::HandleScope handle_scope(isolate());
  46. return is_enabled_.Run(GetWrapper(), command_id);
  47. }
  48. bool Menu::IsCommandIdVisible(int command_id) const {
  49. v8::Locker locker(isolate());
  50. v8::HandleScope handle_scope(isolate());
  51. return is_visible_.Run(GetWrapper(), command_id);
  52. }
  53. bool Menu::GetAcceleratorForCommandIdWithParams(
  54. int command_id,
  55. bool use_default_accelerator,
  56. ui::Accelerator* accelerator) const {
  57. v8::Locker locker(isolate());
  58. v8::HandleScope handle_scope(isolate());
  59. v8::Local<v8::Value> val =
  60. get_accelerator_.Run(GetWrapper(), command_id, use_default_accelerator);
  61. return mate::ConvertFromV8(isolate(), val, accelerator);
  62. }
  63. void Menu::ExecuteCommand(int command_id, int flags) {
  64. v8::Locker locker(isolate());
  65. v8::HandleScope handle_scope(isolate());
  66. execute_command_.Run(GetWrapper(),
  67. mate::internal::CreateEventFromFlags(isolate(), flags),
  68. command_id);
  69. }
  70. void Menu::MenuWillShow(ui::SimpleMenuModel* source) {
  71. v8::Locker locker(isolate());
  72. v8::HandleScope handle_scope(isolate());
  73. menu_will_show_.Run(GetWrapper());
  74. }
  75. void Menu::InsertItemAt(int index,
  76. int command_id,
  77. const base::string16& label) {
  78. model_->InsertItemAt(index, command_id, label);
  79. }
  80. void Menu::InsertSeparatorAt(int index) {
  81. model_->InsertSeparatorAt(index, ui::NORMAL_SEPARATOR);
  82. }
  83. void Menu::InsertCheckItemAt(int index,
  84. int command_id,
  85. const base::string16& label) {
  86. model_->InsertCheckItemAt(index, command_id, label);
  87. }
  88. void Menu::InsertRadioItemAt(int index,
  89. int command_id,
  90. const base::string16& label,
  91. int group_id) {
  92. model_->InsertRadioItemAt(index, command_id, label, group_id);
  93. }
  94. void Menu::InsertSubMenuAt(int index,
  95. int command_id,
  96. const base::string16& label,
  97. Menu* menu) {
  98. menu->parent_ = this;
  99. model_->InsertSubMenuAt(index, command_id, label, menu->model_.get());
  100. }
  101. void Menu::SetIcon(int index, const gfx::Image& image) {
  102. model_->SetIcon(index, image);
  103. }
  104. void Menu::SetSublabel(int index, const base::string16& sublabel) {
  105. model_->SetSublabel(index, sublabel);
  106. }
  107. void Menu::SetRole(int index, const base::string16& role) {
  108. model_->SetRole(index, role);
  109. }
  110. void Menu::Clear() {
  111. model_->Clear();
  112. }
  113. int Menu::GetIndexOfCommandId(int command_id) {
  114. return model_->GetIndexOfCommandId(command_id);
  115. }
  116. int Menu::GetItemCount() const {
  117. return model_->GetItemCount();
  118. }
  119. int Menu::GetCommandIdAt(int index) const {
  120. return model_->GetCommandIdAt(index);
  121. }
  122. base::string16 Menu::GetLabelAt(int index) const {
  123. return model_->GetLabelAt(index);
  124. }
  125. base::string16 Menu::GetSublabelAt(int index) const {
  126. return model_->GetSublabelAt(index);
  127. }
  128. bool Menu::IsItemCheckedAt(int index) const {
  129. return model_->IsItemCheckedAt(index);
  130. }
  131. bool Menu::IsEnabledAt(int index) const {
  132. return model_->IsEnabledAt(index);
  133. }
  134. bool Menu::IsVisibleAt(int index) const {
  135. return model_->IsVisibleAt(index);
  136. }
  137. void Menu::OnMenuWillClose() {
  138. Emit("menu-will-close");
  139. }
  140. void Menu::OnMenuWillShow() {
  141. Emit("menu-will-show");
  142. }
  143. // static
  144. void Menu::BuildPrototype(v8::Isolate* isolate,
  145. v8::Local<v8::FunctionTemplate> prototype) {
  146. prototype->SetClassName(mate::StringToV8(isolate, "Menu"));
  147. mate::ObjectTemplateBuilder(isolate, prototype->PrototypeTemplate())
  148. .MakeDestroyable()
  149. .SetMethod("insertItem", &Menu::InsertItemAt)
  150. .SetMethod("insertCheckItem", &Menu::InsertCheckItemAt)
  151. .SetMethod("insertRadioItem", &Menu::InsertRadioItemAt)
  152. .SetMethod("insertSeparator", &Menu::InsertSeparatorAt)
  153. .SetMethod("insertSubMenu", &Menu::InsertSubMenuAt)
  154. .SetMethod("setIcon", &Menu::SetIcon)
  155. .SetMethod("setSublabel", &Menu::SetSublabel)
  156. .SetMethod("setRole", &Menu::SetRole)
  157. .SetMethod("clear", &Menu::Clear)
  158. .SetMethod("getIndexOfCommandId", &Menu::GetIndexOfCommandId)
  159. .SetMethod("getItemCount", &Menu::GetItemCount)
  160. .SetMethod("getCommandIdAt", &Menu::GetCommandIdAt)
  161. .SetMethod("getLabelAt", &Menu::GetLabelAt)
  162. .SetMethod("getSublabelAt", &Menu::GetSublabelAt)
  163. .SetMethod("isItemCheckedAt", &Menu::IsItemCheckedAt)
  164. .SetMethod("isEnabledAt", &Menu::IsEnabledAt)
  165. .SetMethod("isVisibleAt", &Menu::IsVisibleAt)
  166. .SetMethod("popupAt", &Menu::PopupAt)
  167. .SetMethod("closePopupAt", &Menu::ClosePopupAt);
  168. }
  169. } // namespace api
  170. } // namespace atom
  171. namespace {
  172. using atom::api::Menu;
  173. void Initialize(v8::Local<v8::Object> exports,
  174. v8::Local<v8::Value> unused,
  175. v8::Local<v8::Context> context,
  176. void* priv) {
  177. v8::Isolate* isolate = context->GetIsolate();
  178. Menu::SetConstructor(isolate, base::Bind(&Menu::New));
  179. mate::Dictionary dict(isolate, exports);
  180. dict.Set("Menu", Menu::GetConstructor(isolate)->GetFunction());
  181. #if defined(OS_MACOSX)
  182. dict.SetMethod("setApplicationMenu", &Menu::SetApplicationMenu);
  183. dict.SetMethod("sendActionToFirstResponder",
  184. &Menu::SendActionToFirstResponder);
  185. #endif
  186. }
  187. } // namespace
  188. NODE_BUILTIN_MODULE_CONTEXT_AWARE(atom_browser_menu, Initialize)