| /******************************************************************************* |
| * Copyright (c) 2012 Rushan R. Gilmullin and others. |
| * All rights reserved. This program and the accompanying materials |
| * are made available under the terms of the Eclipse Public License 2.0 |
| * which accompanies this distribution, and is available at |
| * https://www.eclipse.org/legal/epl-2.0/ |
| * |
| * SPDX-License-Identifier: EPL-2.0 |
| * |
| * Contributors: |
| * Rushan R. Gilmullin - initial API and implementation |
| *******************************************************************************/ |
| |
| package org.eclipse.osbp.vaaclipse.presentation.renderers; |
| |
| import javax.annotation.PostConstruct; |
| import javax.annotation.PreDestroy; |
| import javax.inject.Inject; |
| |
| import org.eclipse.e4.core.contexts.ContextInjectionFactory; |
| import org.eclipse.e4.core.contexts.IEclipseContext; |
| import org.eclipse.e4.core.di.annotations.CanExecute; |
| import org.eclipse.e4.core.services.contributions.IContributionFactory; |
| import org.eclipse.e4.ui.model.application.ui.MElementContainer; |
| import org.eclipse.e4.ui.model.application.ui.MUIElement; |
| import org.eclipse.e4.ui.model.application.ui.advanced.MPerspective; |
| import org.eclipse.e4.ui.model.application.ui.menu.ItemType; |
| import org.eclipse.e4.ui.model.application.ui.menu.MDirectToolItem; |
| import org.eclipse.e4.ui.model.application.ui.menu.MHandledItem; |
| import org.eclipse.e4.ui.model.application.ui.menu.MHandledToolItem; |
| import org.eclipse.e4.ui.model.application.ui.menu.MItem; |
| import org.eclipse.e4.ui.model.application.ui.menu.MToolBarElement; |
| import org.eclipse.e4.ui.model.application.ui.menu.MToolBarSeparator; |
| import org.eclipse.e4.ui.model.application.ui.menu.MToolItem; |
| import org.eclipse.e4.ui.services.internal.events.EventBroker; |
| import org.eclipse.e4.ui.workbench.UIEvents; |
| import org.eclipse.osbp.vaaclipse.presentation.utils.Commons; |
| import org.eclipse.osbp.vaaclipse.publicapi.resources.ResourceHelper; |
| import org.eclipse.osbp.vaaclipse.widgets.ToolbarButton; |
| import org.eclipse.osbp.vaaclipse.widgets.ToolbarButton.Type; |
| import org.eclipse.osbp.vaaclipse.widgets.ToolbarButtonBase; |
| import org.eclipse.osbp.vaaclipse.widgets.TwoStateToolbarButton; |
| import org.osgi.service.event.Event; |
| import org.osgi.service.event.EventHandler; |
| |
| import com.vaadin.server.Resource; |
| import com.vaadin.ui.Button; |
| import com.vaadin.ui.Button.ClickEvent; |
| import com.vaadin.ui.Button.ClickListener; |
| |
| @SuppressWarnings("restriction") |
| public class ToolItemRenderer extends ItemRenderer { |
| @Inject |
| IContributionFactory contributionFactory; |
| |
| @Inject |
| EventBroker eventBroker; |
| |
| private static final String HCI_STATIC_CONTEXT = "HCI-staticContext"; |
| |
| private EventHandler itemUpdater = new EventHandler() { |
| public void handleEvent(Event event) { |
| // Ensure that this event is for a MMenuItem |
| if (!(event.getProperty(UIEvents.EventTags.ELEMENT) instanceof MToolBarElement)) |
| return; |
| |
| MToolBarElement itemModel = (MToolBarElement) event |
| .getProperty(UIEvents.EventTags.ELEMENT); |
| |
| Button ici = (Button) itemModel.getWidget(); |
| if (ici == null) { |
| return; |
| } |
| |
| String attName = (String) event |
| .getProperty(UIEvents.EventTags.ATTNAME); |
| String newValue = (String) event |
| .getProperty(UIEvents.EventTags.NEW_VALUE); |
| if (UIEvents.UILabel.LABEL.equals(attName)) { |
| ici.setCaption(newValue); |
| } else if (UIEvents.UILabel.ICONURI.equals(attName)) { |
| Resource icon = ResourceHelper.createResource(newValue); |
| ici.setIcon(icon); |
| } else if (UIEvents.UILabel.TOOLTIP.equals(attName)) { |
| ici.setDescription(newValue); |
| } |
| } |
| }; |
| |
| private EventHandler toBeRenderedUpdater = new EventHandler() { |
| public void handleEvent(Event event) { |
| // Ensure that this event is for a MMenuItem |
| if (!(event.getProperty(UIEvents.EventTags.ELEMENT) instanceof MToolBarElement)) |
| return; |
| |
| MToolBarElement itemModel = (MToolBarElement) event |
| .getProperty(UIEvents.EventTags.ELEMENT); |
| String attName = (String) event |
| .getProperty(UIEvents.EventTags.ATTNAME); |
| |
| if (UIEvents.UIElement.VISIBLE.equals(attName)) { |
| Button ici = (Button) itemModel.getWidget(); |
| |
| if (ici == null) { |
| return; |
| } |
| ici.setVisible(itemModel.isVisible()); |
| } |
| } |
| }; |
| |
| private EventHandler selectionUpdater = new EventHandler() { |
| public void handleEvent(Event event) { |
| // Ensure that this event is for a MToolItem |
| if (!(event.getProperty(UIEvents.EventTags.ELEMENT) instanceof MToolBarElement)) |
| return; |
| |
| MToolBarElement itemModel = (MToolBarElement) event |
| .getProperty(UIEvents.EventTags.ELEMENT); |
| if (itemModel.getWidget() instanceof TwoStateToolbarButton) { |
| TwoStateToolbarButton button = (TwoStateToolbarButton) itemModel |
| .getWidget(); |
| Boolean newValue = (Boolean) event |
| .getProperty(UIEvents.EventTags.NEW_VALUE); |
| button.setCheckedState(newValue); |
| } |
| } |
| }; |
| |
| private EventHandler enabledUpdater = new EventHandler() { |
| public void handleEvent(Event event) { |
| // Ensure that this event is for a MMenuItem |
| if (!(event.getProperty(UIEvents.EventTags.ELEMENT) instanceof MToolBarElement)) |
| return; |
| |
| MToolBarElement itemModel = (MToolBarElement) event |
| .getProperty(UIEvents.EventTags.ELEMENT); |
| Button ici = (Button) itemModel.getWidget(); |
| Boolean newValue = (Boolean) event |
| .getProperty(UIEvents.EventTags.NEW_VALUE); |
| ici.setEnabled(newValue); |
| } |
| }; |
| |
| @PostConstruct |
| public void init() { |
| eventBroker.subscribe(UIEvents.UILabel.TOPIC_ALL, itemUpdater); |
| eventBroker.subscribe(UIEvents.Item.TOPIC_SELECTED, selectionUpdater); |
| eventBroker.subscribe(UIEvents.Item.TOPIC_ENABLED, enabledUpdater); |
| eventBroker |
| .subscribe(UIEvents.UIElement.TOPIC_ALL, toBeRenderedUpdater); |
| eventBroker.subscribe(UIEvents.UILabel.TOPIC_LOCALIZED_LABEL, |
| localizeLabel); |
| eventBroker.subscribe(UIEvents.UILabel.TOPIC_LOCALIZED_TOOLTIP, |
| localizeTooltip); |
| eventBroker.subscribe(UIEvents.UILabel.TOPIC_LABEL, localizeLabel); |
| eventBroker.subscribe(UIEvents.UILabel.TOPIC_TOOLTIP, localizeTooltip); |
| } |
| |
| @PreDestroy |
| public void contextDisposed() { |
| eventBroker.unsubscribe(itemUpdater); |
| eventBroker.unsubscribe(selectionUpdater); |
| eventBroker.unsubscribe(enabledUpdater); |
| eventBroker.unsubscribe(toBeRenderedUpdater); |
| eventBroker.unsubscribe(localizeLabel); |
| eventBroker.unsubscribe(localizeTooltip); |
| } |
| |
| @Override |
| public void createWidget(MUIElement element, |
| MElementContainer<MUIElement> parent) { |
| if (element instanceof MHandledToolItem |
| || element instanceof MDirectToolItem) { |
| final MToolItem item = (MToolItem) element; |
| |
| ToolbarButtonBase button; |
| if (item.getType() == ItemType.CHECK) { |
| button = new TwoStateToolbarButton(); |
| ((TwoStateToolbarButton) button).setCheckedState(item |
| .isSelected()); |
| } else if (item.getType() == ItemType.RADIO) { |
| button = new TwoStateToolbarButton(); |
| ((TwoStateToolbarButton) button).setCheckedState(item |
| .isSelected()); |
| ((TwoStateToolbarButton) button) |
| .setSwitchStateByUserClickEnabled(false); |
| } else { // By default - ItemType.PUSH |
| ToolbarButton toolbarButton = new ToolbarButton(); |
| button = toolbarButton; |
| |
| if (item.getTags().contains("link")) { |
| toolbarButton.setType(Type.Link); |
| } |
| } |
| |
| // label and icon |
| button.setLabelAndIcon(Commons.trim(item.getLabel()), |
| Commons.trim(item.getIconURI())); |
| |
| // tooltip |
| if (item.getTooltip() != null) |
| button.setDescription(item.getLocalizedTooltip()); |
| |
| element.setWidget(button); |
| |
| updateItemEnablement(item); |
| button.setEnabled(item.isEnabled()); |
| registerEnablementUpdaters(item); |
| }else if(element instanceof MToolBarSeparator){ |
| ToolbarButton fakeButton = new ToolbarButton(); |
| fakeButton.setType(Type.Link); |
| fakeButton.setLabelAndIcon("", ""); |
| fakeButton.setDescription(""); |
| fakeButton.setEnabled(false); |
| fakeButton.addStyleName("v-spliter"); |
| element.setWidget(fakeButton); |
| } |
| } |
| |
| protected void updateItemEnablement(MItem item) { |
| if (!(item.getWidget() instanceof Button)) |
| return; |
| |
| Button widget = (Button) item.getWidget(); |
| if (widget == null) |
| return; |
| |
| item.setEnabled(canExecute(item)); |
| } |
| |
| public boolean canExecute(MItem item) { |
| if (item instanceof MHandledItem) |
| return canExecute((MHandledItem) item); |
| else if (item instanceof MDirectToolItem) |
| return canExecute((MDirectToolItem) item); |
| else |
| return false; |
| } |
| |
| protected boolean canExecute(MDirectToolItem item) { |
| final IEclipseContext eclipseContext = getContext(item); |
| if (eclipseContext == null) // item is not in hierarchy |
| return false; |
| |
| if (item.getObject() == null) { |
| item.setObject(contributionFactory.create( |
| item.getContributionURI(), getContext(item))); |
| } |
| |
| eclipseContext.set(MItem.class, item); |
| setupContext(eclipseContext, item); |
| |
| if (item.getObject() == null) { |
| return false; |
| } else { |
| return (Boolean) ContextInjectionFactory.invoke(item.getObject(), |
| CanExecute.class, eclipseContext, true); |
| } |
| } |
| |
| @SuppressWarnings("serial") |
| @Override |
| public void hookControllerLogic(MUIElement me) { |
| if (me instanceof MDirectToolItem) { |
| final MDirectToolItem item = (MDirectToolItem) me; |
| |
| final Button button = (Button) item.getWidget(); |
| button.addClickListener(new ClickListener() { |
| |
| @SuppressWarnings("unchecked") |
| @Override |
| public void buttonClick(ClickEvent event) { |
| if (item.getType() == ItemType.CHECK) { |
| item.setSelected(((TwoStateToolbarButton) button) |
| .getCheckedState()); |
| } else if (item.getType() == ItemType.RADIO) { |
| MElementContainer<? extends MToolItem> parent = (MElementContainer<? extends MToolItem>) item |
| .getParent(); |
| for (MToolItem toolItem : parent.getChildren()) { |
| if (toolItem.getType() == ItemType.RADIO) { |
| toolItem.setSelected(toolItem != item); |
| } |
| } |
| } |
| |
| executeItem(item); |
| } |
| }); |
| } else if (me instanceof MHandledToolItem) { |
| final MHandledItem item = (MHandledToolItem) me; |
| |
| final Button button = (Button) item.getWidget(); |
| button.addClickListener(new ClickListener() { |
| |
| @SuppressWarnings("unchecked") |
| @Override |
| public void buttonClick(ClickEvent event) { |
| if (item.getType() == ItemType.CHECK) { |
| item.setSelected(((TwoStateToolbarButton) button) |
| .getCheckedState()); |
| } else if (item.getType() == ItemType.RADIO) { |
| MElementContainer<? extends MToolItem> parent = (MElementContainer<? extends MToolItem>) item |
| .getParent(); |
| for (MToolItem toolItem : parent.getChildren()) { |
| if (toolItem.getType() == ItemType.RADIO) { |
| toolItem.setSelected(toolItem != item); |
| } |
| } |
| } |
| |
| executeItem(item); |
| } |
| }); |
| } |
| } |
| |
| @Override |
| protected void setupContext(IEclipseContext context, MItem item) { |
| super.setupContext(context, item); |
| context.set(MToolItem.class, (MToolItem) item); |
| if (item instanceof MDirectToolItem) |
| context.set(MDirectToolItem.class, (MDirectToolItem) item); |
| else if (item instanceof MHandledToolItem) |
| context.set(MHandledToolItem.class, (MHandledToolItem) item); |
| } |
| |
| private EventHandler localizeLabel = new EventHandler() { |
| @Override |
| public void handleEvent(Event event) { |
| Object element = event.getProperty(UIEvents.EventTags.ELEMENT); |
| |
| if (!(element instanceof MToolBarElement)) |
| return; |
| |
| MToolBarElement item = (MToolBarElement) element; |
| final ToolbarButton button = (ToolbarButton) item.getWidget(); |
| |
| String newValue = (String) event |
| .getProperty(UIEvents.EventTags.NEW_VALUE); |
| |
| String label = Commons.trim(newValue); |
| if (button != null) { |
| button.setCaption(label); |
| } |
| } |
| }; |
| |
| private EventHandler localizeTooltip = new EventHandler() { |
| @Override |
| public void handleEvent(Event event) { |
| Object element = event.getProperty(UIEvents.EventTags.ELEMENT); |
| |
| if (!(element instanceof MToolBarElement)) |
| return; |
| |
| MToolBarElement item = (MToolBarElement) element; |
| final ToolbarButton button = (ToolbarButton) item.getWidget(); |
| |
| String newValue = (String) event |
| .getProperty(UIEvents.EventTags.NEW_VALUE); |
| |
| if (button != null) { |
| button.setDescription(newValue); |
| } |
| } |
| }; |
| } |