stroom.widget.menu.client.presenter.MenuItemCell.java Source code

Java tutorial

Introduction

Here is the source code for stroom.widget.menu.client.presenter.MenuItemCell.java

Source

/*
 * Copyright 2016 Crown Copyright
 *
 * 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 stroom.widget.menu.client.presenter;

import com.google.gwt.cell.client.AbstractCell;
import com.google.gwt.cell.client.ValueUpdater;
import com.google.gwt.core.client.GWT;
import com.google.gwt.dom.client.BrowserEvents;
import com.google.gwt.dom.client.Element;
import com.google.gwt.dom.client.NativeEvent;
import com.google.gwt.resources.client.ClientBundle;
import com.google.gwt.resources.client.CssResource;
import com.google.gwt.resources.client.CssResource.ImportedWithPrefix;
import com.google.gwt.safecss.shared.SafeStyles;
import com.google.gwt.safecss.shared.SafeStylesUtils;
import com.google.gwt.safehtml.client.SafeHtmlTemplates;
import com.google.gwt.safehtml.shared.SafeHtml;
import com.google.gwt.safehtml.shared.SafeHtmlBuilder;
import com.google.gwt.safehtml.shared.SafeHtmlUtils;
import com.google.gwt.user.client.ui.Image;
import stroom.data.table.client.CellTableViewImpl.MenuResources;
import stroom.widget.button.client.GlyphIcon;
import stroom.widget.tab.client.presenter.Icon;
import stroom.widget.tab.client.presenter.ImageIcon;

public class MenuItemCell extends AbstractCell<Item> {
    private final MenuPresenter menuPresenter;

    @ImportedWithPrefix("stroom-menu")
    public interface Style extends CssResource {
        String DEFAULT_CSS = "MenuItem.css";

        String separator();

        String outer();

        String highlight();

        String icon();

        String face();

        String disabled();

        String text();

        String shortcut();
    }

    public interface Resources extends ClientBundle {
        @Source(Style.DEFAULT_CSS)
        Style style();
    }

    public interface Appearance<I extends Item> {
        void render(MenuItemCell cell, Context context, I value, SafeHtmlBuilder sb);
    }

    public static class SeparatorAppearance implements Appearance<Separator> {
        public interface Template extends SafeHtmlTemplates {
            @Template("<div class=\"{0}\"></div>")
            SafeHtml separator(String className);
        }

        private static final Template TEMPLATE = GWT.create(Template.class);
        private static final Resources RESOURCES = GWT.create(Resources.class);

        public SeparatorAppearance() {
            // Make sure the CSS is injected.
            RESOURCES.style().ensureInjected();
        }

        @Override
        public void render(final MenuItemCell cell, final Context context, final Separator value,
                final SafeHtmlBuilder sb) {
            sb.append(TEMPLATE.separator(RESOURCES.style().separator()));
        }
    }

    public static class MenuItemAppearance implements Appearance<MenuItem> {
        @Override
        public void render(final MenuItemCell cell, final Context context, final MenuItem value,
                final SafeHtmlBuilder sb) {
            if (value.getText() != null) {
                sb.append(SafeHtmlUtils.fromTrustedString(value.getText()));
            }
        }
    }

    public static class IconMenuItemAppearance implements Appearance<IconMenuItem> {
        public interface Template extends SafeHtmlTemplates {
            @Template("<div class=\"{0}\" style=\"{1}\">{2}</div>")
            SafeHtml outer(String className, SafeStyles styles, SafeHtml inner);

            @Template("<div class=\"{0}\">{1}</div>")
            SafeHtml inner(String className, SafeHtml icon);

            @Template("<div class=\"{0}\" title=\"Filter\"><div class=\"{1}\" style=\"{2}\"><i class=\"{3}\"></i></div></div>")
            SafeHtml icon(String iconClassName, String faceClassName, SafeStyles colour, String icon);

            @Template("<div class=\"{0}\">{1}</div>")
            SafeHtml text(String className, SafeHtml text);
        }

        private static final Template TEMPLATE = GWT.create(Template.class);
        private static final SafeStyles NORMAL = SafeStylesUtils.fromTrustedString("cursor:pointer;");
        private static final SafeStyles DISABLED = SafeStylesUtils.fromTrustedString("cursor:default;color:grey;");
        private static final Resources RESOURCES = GWT.create(Resources.class);

        private final MenuPresenter menuPresenter;

        public IconMenuItemAppearance(final MenuPresenter menuPresenter) {
            this.menuPresenter = menuPresenter;

            // Make sure the CSS is injected.
            RESOURCES.style().ensureInjected();
        }

        @Override
        public void render(final MenuItemCell cell, final Context context, final IconMenuItem value,
                final SafeHtmlBuilder sb) {
            if (value.getText() != null) {
                SafeStyles styles = NORMAL;

                if (!value.isEnabled()) {
                    styles = DISABLED;
                }

                final SafeHtmlBuilder inner = new SafeHtmlBuilder();
                final Icon enabledIcon = value.getEnabledIcon();
                final Icon disabledIcon = value.getDisabledIcon();

                if (value.isEnabled()) {
                    if (enabledIcon != null && enabledIcon instanceof ImageIcon) {
                        final ImageIcon imageIcon = (ImageIcon) enabledIcon;
                        final Image image = imageIcon.getImage();
                        if (image != null) {
                            inner.append(TEMPLATE.inner(RESOURCES.style().icon(),
                                    SafeHtmlUtils.fromTrustedString(image.getElement().getString())));
                        }
                    } else if (enabledIcon != null && enabledIcon instanceof GlyphIcon) {
                        final GlyphIcon glyphIcon = (GlyphIcon) enabledIcon;
                        inner.append(TEMPLATE.icon(RESOURCES.style().icon(), RESOURCES.style().face(),
                                SafeStylesUtils.forTrustedColor(glyphIcon.getColourSet().getEnabled()),
                                glyphIcon.getGlyph()));
                    } else {
                        inner.append(TEMPLATE.inner(RESOURCES.style().icon(), SafeHtmlUtils.EMPTY_SAFE_HTML));
                    }
                } else {
                    if (disabledIcon != null && disabledIcon instanceof ImageIcon) {
                        final ImageIcon imageIcon = (ImageIcon) disabledIcon;
                        final Image image = imageIcon.getImage();
                        if (image != null) {
                            inner.append(TEMPLATE.inner(RESOURCES.style().icon(),
                                    SafeHtmlUtils.fromTrustedString(image.getElement().getString())));
                        }
                    } else if (enabledIcon != null && enabledIcon instanceof GlyphIcon) {
                        final GlyphIcon glyphIcon = (GlyphIcon) enabledIcon;
                        inner.append(TEMPLATE.icon(RESOURCES.style().icon(),
                                RESOURCES.style().face() + " " + RESOURCES.style().disabled(),
                                SafeStylesUtils.forTrustedColor(glyphIcon.getColourSet().getEnabled()),
                                glyphIcon.getGlyph()));
                    } else {
                        inner.append(TEMPLATE.inner(RESOURCES.style().icon(), SafeHtmlUtils.EMPTY_SAFE_HTML));
                    }
                }

                inner.append(
                        TEMPLATE.inner(RESOURCES.style().text(), SafeHtmlUtils.fromTrustedString(value.getText())));

                if (value.getShortcut() != null) {
                    inner.append(TEMPLATE.inner(RESOURCES.style().shortcut(),
                            SafeHtmlUtils.fromTrustedString(value.getShortcut())));
                }

                if (menuPresenter.isHighlighted(value)) {
                    sb.append(TEMPLATE.outer(RESOURCES.style().highlight(), styles, inner.toSafeHtml()));
                } else {
                    sb.append(TEMPLATE.outer(RESOURCES.style().outer(), styles, inner.toSafeHtml()));
                }
            }
        }
    }

    private static final MenuResources MENU_RESOURCES = GWT.create(MenuResources.class);

    public MenuItemCell(final MenuPresenter menuPresenter) {
        super(BrowserEvents.CLICK, BrowserEvents.MOUSEOVER, BrowserEvents.MOUSEOUT);
        this.menuPresenter = menuPresenter;
    }

    @Override
    public void onBrowserEvent(final Context context, final Element parent, final Item value,
            final NativeEvent event, final ValueUpdater<Item> valueUpdater) {
        super.onBrowserEvent(context, parent, value, event, valueUpdater);

        if (value != null) {
            final String eventType = event.getType();
            final Element element = getElement(parent);

            if (value instanceof CommandMenuItem) {
                if (BrowserEvents.MOUSEOVER.equals(eventType)) {
                    final CommandMenuItem menuItem = (CommandMenuItem) value;
                    if (menuItem.isEnabled()) {
                        menuPresenter.onMouseOver(menuItem, element);
                        if (menuPresenter.isHover(menuItem)) {
                            element.addClassName(MENU_RESOURCES.cellTableStyle().cellTableHoveredRow());
                        }
                    } else {
                        element.removeClassName(MENU_RESOURCES.cellTableStyle().cellTableHoveredRow());
                    }

                } else if (BrowserEvents.MOUSEOUT.equals(eventType)) {
                    final CommandMenuItem menuItem = (CommandMenuItem) value;
                    menuPresenter.onMouseOut(menuItem, element);
                    if (!menuPresenter.isHover(menuItem)) {
                        element.removeClassName(MENU_RESOURCES.cellTableStyle().cellTableHoveredRow());
                    }

                } else if (BrowserEvents.CLICK.equals(eventType)
                        && ((event.getButton() & NativeEvent.BUTTON_LEFT) != 0)) {
                    final CommandMenuItem menuItem = (CommandMenuItem) value;
                    if (menuItem.isEnabled()) {
                        menuPresenter.onClick(menuItem, element);
                    }
                }

            } else if (value instanceof MenuItem) {
                final MenuItem menuItem = (MenuItem) value;

                if (BrowserEvents.MOUSEOVER.equals(eventType)) {
                    element.addClassName(MENU_RESOURCES.cellTableStyle().cellTableHoveredRow());
                    menuPresenter.onMouseOver(menuItem, element);

                } else if (BrowserEvents.MOUSEOUT.equals(eventType)) {
                    element.removeClassName(MENU_RESOURCES.cellTableStyle().cellTableHoveredRow());

                } else if (BrowserEvents.CLICK.equals(eventType)
                        && ((event.getButton() & NativeEvent.BUTTON_LEFT) != 0)) {
                    menuPresenter.onClick(menuItem, element);
                }
            }
        }
    }

    private Element getElement(final Element parent) {
        if (parent.getFirstChildElement() != null) {
            return parent.getFirstChildElement();
        }

        return parent;
    }

    @Override
    public void render(final Context context, final Item value, final SafeHtmlBuilder sb) {
        if (value != null) {
            if (value instanceof IconMenuItem) {
                new IconMenuItemAppearance(menuPresenter).render(this, context, (IconMenuItem) value, sb);
            } else if (value instanceof MenuItem) {
                new MenuItemAppearance().render(this, context, (MenuItem) value, sb);
            } else if (value instanceof Separator) {
                new SeparatorAppearance().render(this, context, (Separator) value, sb);
            }
        }
    }
}