/** * Copyright 2010 Google Inc. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. * */ package org.waveprotocol.wave.client.widget.toolbar.buttons; import com.google.gwt.core.client.GWT; import com.google.gwt.dom.client.Element; import com.google.gwt.dom.client.StyleInjector; import com.google.gwt.event.dom.client.ClickEvent; import com.google.gwt.event.dom.client.MouseDownEvent; import com.google.gwt.resources.client.ClientBundle; import com.google.gwt.resources.client.CssResource; import com.google.gwt.resources.client.ImageResource; import com.google.gwt.resources.client.ImageResource.ImageOptions; import com.google.gwt.resources.client.ImageResource.RepeatStyle; import com.google.gwt.uibinder.client.UiBinder; import com.google.gwt.uibinder.client.UiField; import com.google.gwt.uibinder.client.UiHandler; import com.google.gwt.user.client.ui.Composite; import com.google.gwt.user.client.ui.Widget; import org.waveprotocol.wave.client.common.webdriver.DebugClassHelper; import org.waveprotocol.wave.client.widget.common.ImplPanel; /** * Widget implementation of a {@link ToolbarButtonView} for displaying * in a horizontal toolbar. * * @author kalman@google.com (Benjamin Kalman) */ public final class HorizontalToolbarButtonWidget extends Composite implements ToolbarButtonUi { interface Resources extends ClientBundle { @Source("HorizontalToolbarButtonWidget.css") Css css(); @Source("button_down_large.png") @ImageOptions(repeatStyle = RepeatStyle.Horizontal) ImageResource buttonDown(); @Source("toolbar_divider.png") ImageResource divider(); @Source("arrow_horizontal.png") ImageResource dropdownArrow(); } interface Css extends CssResource { String self(); String wide(); String compact(); String visualElement(); String textElement(); String textElementWithVisualElement(); String divider(); String overlay(); String enabled(); String hidden(); String down(); String dropdownArrow(); } interface Binder extends UiBinder<Widget, HorizontalToolbarButtonWidget> {} private static final Binder BINDER = GWT.create(Binder.class); @UiField(provided = true) static final Resources res = GWT.create(Resources.class); static { StyleInjector.inject(res.css().getText(), true); } @UiField ImplPanel self; @UiField Element visualElement; @UiField Element textElement; @UiField Element dropdownArrow; @UiField Element divider; @UiField Element overlay; private Listener listener; private Element currentVisualElement = null; private String debugText; // For toString() debgging. public HorizontalToolbarButtonWidget() { initWidget(BINDER.createAndBindUi(this)); // By default, the button is displayed "compact" (e.g. less padding). If // text is set on the button then the button will be displayed "wide". // If this is needed by more than just the overflow and edit-mode buttons // then perhaps a view method is warranted. self.getElement().addClassName(res.css().compact()); } @UiHandler("self") void handleButtonClicked(ClickEvent e) { if (listener != null) { listener.onClick(); } } @UiHandler("self") void handleMouseDown(MouseDownEvent e) { // Prevent the editor from losing selection focus. e.preventDefault(); e.stopPropagation(); } @Override public void setState(State state) { switch (state) { case ENABLED: self.getElement().removeClassName(res.css().hidden()); self.getElement().addClassName(res.css().enabled()); removeDebugClass("disabled"); break; case DISABLED: self.getElement().removeClassName(res.css().hidden()); self.getElement().removeClassName(res.css().enabled()); addDebugClass("disabled"); break; case INVISIBLE: self.getElement().addClassName(res.css().hidden()); break; } } @Override public void setText(String text) { textElement.setInnerText(text); debugText = text; if (text.isEmpty()) { textElement.addClassName(res.css().hidden()); self.getElement().replaceClassName(res.css().wide(), res.css().compact()); } else { textElement.removeClassName(res.css().hidden()); self.getElement().replaceClassName(res.css().compact(), res.css().wide()); } } @Override public void setTooltip(String tooltip) { setTitle(tooltip); } @Override public void setVisualElement(Element element) { if (currentVisualElement != null) { currentVisualElement.removeFromParent(); } currentVisualElement = element; visualElement.removeClassName(res.css().hidden()); visualElement.appendChild(element); textElement.addClassName(res.css().textElementWithVisualElement()); } @Override public void setDown(boolean isDown) { if (isDown) { self.addStyleName(res.css().down()); } else { self.removeStyleName(res.css().down()); } } @Override public void setShowDropdownArrow(boolean showDropdownArrow) { if (showDropdownArrow) { dropdownArrow.removeClassName(res.css().hidden()); } else { dropdownArrow.addClassName(res.css().hidden()); } } @Override public void addDebugClass(String dc) { DebugClassHelper.addDebugClass(this, dc); } @Override public void removeDebugClass(String dc) { DebugClassHelper.removeDebugClass(this, dc); } @Override public void setListener(Listener listener) { this.listener = listener; } @Override public Widget hackGetWidget() { return this; } @Override public void setShowDivider(boolean showDivider) { if (showDivider) { divider.removeClassName(res.css().hidden()); } else { divider.addClassName(res.css().hidden()); } } @Override public String toString() { return debugText; } }