You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

MenuBarConnector.java 6.0KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165
  1. /*
  2. @VaadinApache2LicenseForJavaFiles@
  3. */
  4. package com.vaadin.terminal.gwt.client.ui;
  5. import java.util.Iterator;
  6. import java.util.Stack;
  7. import com.google.gwt.core.client.GWT;
  8. import com.google.gwt.user.client.Command;
  9. import com.google.gwt.user.client.ui.Widget;
  10. import com.vaadin.terminal.gwt.client.ApplicationConnection;
  11. import com.vaadin.terminal.gwt.client.Paintable;
  12. import com.vaadin.terminal.gwt.client.UIDL;
  13. import com.vaadin.terminal.gwt.client.Util;
  14. import com.vaadin.terminal.gwt.client.ui.Component.LoadStyle;
  15. import com.vaadin.terminal.gwt.client.ui.VMenuBar.CustomMenuItem;
  16. @Component(value = com.vaadin.ui.MenuBar.class, loadStyle = LoadStyle.LAZY)
  17. public class MenuBarConnector extends AbstractComponentConnector implements
  18. Paintable, SimpleManagedLayout {
  19. /**
  20. * This method must be implemented to update the client-side component from
  21. * UIDL data received from server.
  22. *
  23. * This method is called when the page is loaded for the first time, and
  24. * every time UI changes in the component are received from the server.
  25. */
  26. public void updateFromUIDL(UIDL uidl, ApplicationConnection client) {
  27. if (!isRealUpdate(uidl)) {
  28. return;
  29. }
  30. getWidget().htmlContentAllowed = uidl
  31. .hasAttribute(VMenuBar.HTML_CONTENT_ALLOWED);
  32. getWidget().openRootOnHover = uidl
  33. .getBooleanAttribute(VMenuBar.OPEN_ROOT_MENU_ON_HOWER);
  34. getWidget().enabled = isEnabled();
  35. // For future connections
  36. getWidget().client = client;
  37. getWidget().uidlId = uidl.getId();
  38. // Empty the menu every time it receives new information
  39. if (!getWidget().getItems().isEmpty()) {
  40. getWidget().clearItems();
  41. }
  42. UIDL options = uidl.getChildUIDL(0);
  43. if (null != getState() && !getState().isUndefinedWidth()) {
  44. UIDL moreItemUIDL = options.getChildUIDL(0);
  45. StringBuffer itemHTML = new StringBuffer();
  46. if (moreItemUIDL.hasAttribute("icon")) {
  47. itemHTML.append("<img src=\""
  48. + Util.escapeAttribute(client
  49. .translateVaadinUri(moreItemUIDL
  50. .getStringAttribute("icon")))
  51. + "\" class=\"" + Icon.CLASSNAME + "\" alt=\"\" />");
  52. }
  53. String moreItemText = moreItemUIDL.getStringAttribute("text");
  54. if ("".equals(moreItemText)) {
  55. moreItemText = "&#x25BA;";
  56. }
  57. itemHTML.append(moreItemText);
  58. getWidget().moreItem = GWT.create(CustomMenuItem.class);
  59. getWidget().moreItem.setHTML(itemHTML.toString());
  60. getWidget().moreItem.setCommand(VMenuBar.emptyCommand);
  61. getWidget().collapsedRootItems = new VMenuBar(true, getWidget());
  62. getWidget().moreItem.setSubMenu(getWidget().collapsedRootItems);
  63. getWidget().moreItem.addStyleName(VMenuBar.CLASSNAME
  64. + "-more-menuitem");
  65. }
  66. UIDL uidlItems = uidl.getChildUIDL(1);
  67. Iterator<Object> itr = uidlItems.getChildIterator();
  68. Stack<Iterator<Object>> iteratorStack = new Stack<Iterator<Object>>();
  69. Stack<VMenuBar> menuStack = new Stack<VMenuBar>();
  70. VMenuBar currentMenu = getWidget();
  71. while (itr.hasNext()) {
  72. UIDL item = (UIDL) itr.next();
  73. CustomMenuItem currentItem = null;
  74. final int itemId = item.getIntAttribute("id");
  75. boolean itemHasCommand = item.hasAttribute("command");
  76. boolean itemIsCheckable = item
  77. .hasAttribute(VMenuBar.ATTRIBUTE_CHECKED);
  78. String itemHTML = getWidget().buildItemHTML(item);
  79. Command cmd = null;
  80. if (!item.hasAttribute("separator")) {
  81. if (itemHasCommand || itemIsCheckable) {
  82. // Construct a command that fires onMenuClick(int) with the
  83. // item's id-number
  84. cmd = new Command() {
  85. public void execute() {
  86. getWidget().hostReference.onMenuClick(itemId);
  87. }
  88. };
  89. }
  90. }
  91. currentItem = currentMenu.addItem(itemHTML.toString(), cmd);
  92. currentItem.updateFromUIDL(item, client);
  93. if (item.getChildCount() > 0) {
  94. menuStack.push(currentMenu);
  95. iteratorStack.push(itr);
  96. itr = item.getChildIterator();
  97. currentMenu = new VMenuBar(true, currentMenu);
  98. // this is the top-level style that also propagates to items -
  99. // any item specific styles are set above in
  100. // currentItem.updateFromUIDL(item, client)
  101. if (getState().hasStyles()) {
  102. for (String style : getState().getStyles()) {
  103. currentMenu.addStyleDependentName(style);
  104. }
  105. }
  106. currentItem.setSubMenu(currentMenu);
  107. }
  108. while (!itr.hasNext() && !iteratorStack.empty()) {
  109. boolean hasCheckableItem = false;
  110. for (CustomMenuItem menuItem : currentMenu.getItems()) {
  111. hasCheckableItem = hasCheckableItem
  112. || menuItem.isCheckable();
  113. }
  114. if (hasCheckableItem) {
  115. currentMenu.addStyleDependentName("check-column");
  116. } else {
  117. currentMenu.removeStyleDependentName("check-column");
  118. }
  119. itr = iteratorStack.pop();
  120. currentMenu = menuStack.pop();
  121. }
  122. }// while
  123. getLayoutManager().setWidthNeedsUpdate(this);
  124. }// updateFromUIDL
  125. @Override
  126. protected Widget createWidget() {
  127. return GWT.create(VMenuBar.class);
  128. }
  129. @Override
  130. public VMenuBar getWidget() {
  131. return (VMenuBar) super.getWidget();
  132. }
  133. public void layout() {
  134. getWidget().iLayout();
  135. }
  136. }