| /** |
| * Copyright (c) 2011, 2015 - Lunifera GmbH (Gross Enzersdorf, Austria), Loetz GmbH&Co.KG (69115 Heidelberg, Germany) |
| * 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: |
| * Florian Pirchner - Initial implementation |
| */ |
| package org.eclipse.osbp.ecview.core.common.editpart.emf; |
| |
| import java.util.ArrayList; |
| import java.util.List; |
| |
| import org.eclipse.emf.common.notify.Notification; |
| import org.eclipse.emf.ecore.EStructuralFeature; |
| import org.eclipse.osbp.ecview.core.common.context.IViewContext; |
| import org.eclipse.osbp.ecview.core.common.editpart.IEmbeddableEditpart; |
| import org.eclipse.osbp.ecview.core.common.editpart.IEmbeddableParent; |
| import org.eclipse.osbp.ecview.core.common.editpart.IViewEditpart; |
| import org.eclipse.osbp.ecview.core.common.editpart.datatypes.IDatatypeEditpart; |
| import org.eclipse.osbp.ecview.core.common.editpart.datatypes.IDatatypeEditpart.DatatypeBridge; |
| import org.eclipse.osbp.ecview.core.common.editpart.datatypes.IDatatypeEditpart.DatatypeChangeEvent; |
| import org.eclipse.osbp.ecview.core.common.editpart.validation.IValidatorEditpart; |
| import org.eclipse.osbp.ecview.core.common.editpart.visibility.IUiElementAccess; |
| import org.eclipse.osbp.ecview.core.common.memento.IECViewMementoManager; |
| import org.eclipse.osbp.ecview.core.common.model.core.YEmbeddable; |
| import org.eclipse.osbp.ecview.core.common.model.core.YLayout; |
| import org.eclipse.osbp.ecview.core.common.model.core.YMemento; |
| import org.eclipse.osbp.ecview.core.common.model.core.YView; |
| import org.eclipse.osbp.ecview.core.common.model.datatypes.YDatatype; |
| import org.eclipse.osbp.ecview.core.common.presentation.DelegatingPresenterFactory; |
| import org.eclipse.osbp.ecview.core.common.presentation.IWidgetPresentation; |
| import org.eclipse.osbp.ecview.core.common.visibility.IVisibilityHandler; |
| import org.eclipse.osbp.runtime.common.memento.IMementoHandler; |
| import org.slf4j.Logger; |
| import org.slf4j.LoggerFactory; |
| |
| // TODO: Auto-generated Javadoc |
| /** |
| * See {@link ElementEditpart}. |
| * |
| * @param <M> |
| * the generic type |
| */ |
| public abstract class EmbeddableEditpart<M extends YEmbeddable> extends |
| ElementEditpart<M> implements IEmbeddableEditpart, DatatypeBridge, |
| IUiElementAccess { |
| |
| /** The Constant LOGGER. */ |
| private static final Logger LOGGER = LoggerFactory |
| .getLogger(EmbeddableEditpart.class); |
| |
| /** The presentation. */ |
| private IWidgetPresentation<?> presentation; |
| |
| /** The datatype feature. */ |
| private EStructuralFeature datatypeFeature; |
| |
| /** |
| * The default constructor. |
| */ |
| protected EmbeddableEditpart() { |
| } |
| |
| /** |
| * A constructor that becomes passed the datatype feature. |
| * |
| * @param datatypeFeature |
| * the datatype feature |
| */ |
| public EmbeddableEditpart(EStructuralFeature datatypeFeature) { |
| this.datatypeFeature = datatypeFeature; |
| } |
| |
| /** |
| * {@inheritDoc} |
| */ |
| @Override |
| public IEmbeddableParent getParent() { |
| YLayout yParentLayout = getModel().getParent(); |
| if (yParentLayout != null) { |
| return getEditpart(viewContext, yParentLayout); |
| } else { |
| YView yView = getModel().getView(); |
| if (yView != null && yView.getContent() == getModel()) { |
| return (IViewEditpart) getEditpart(viewContext, yView); |
| } |
| } |
| return null; |
| } |
| |
| /* (non-Javadoc) |
| * @see org.eclipse.osbp.ecview.core.common.editpart.IEmbeddableEditpart#getView() |
| */ |
| @Override |
| public IViewEditpart getView() { |
| return viewContext.getViewEditpart(); |
| } |
| |
| /** |
| * Returns the instance of the presentation, but does not load it. |
| * |
| * @param <A> |
| * An instance of {@link IWidgetPresentation} |
| * @return presentation |
| */ |
| @SuppressWarnings("unchecked") |
| protected <A extends IWidgetPresentation<?>> A internalGetPresentation() { |
| return (A) presentation; |
| } |
| |
| /* (non-Javadoc) |
| * @see org.eclipse.osbp.ecview.core.common.editpart.IEmbeddableEditpart#getPresentation() |
| */ |
| @SuppressWarnings("unchecked") |
| @Override |
| public <A extends IWidgetPresentation<?>> A getPresentation() { |
| if (presentation == null) { |
| presentation = createPresenter(); |
| |
| doInitPresentation(presentation); |
| } |
| return (A) presentation; |
| } |
| |
| /** |
| * A hook method to initialize the presentation after creation. |
| * |
| * @param presentation |
| * the presentation |
| */ |
| protected void doInitPresentation(IWidgetPresentation<?> presentation) { |
| |
| } |
| |
| /* (non-Javadoc) |
| * @see org.eclipse.osbp.ecview.core.common.editpart.visibility.IVisibilityProcessable#apply(org.eclipse.osbp.ecview.core.common.visibility.IVisibilityHandler) |
| */ |
| @Override |
| public void apply(IVisibilityHandler handler) { |
| IWidgetPresentation<?> presentation = getPresentation(); |
| if (presentation != null) { |
| presentation.apply(handler); |
| } |
| } |
| |
| /* (non-Javadoc) |
| * @see org.eclipse.osbp.ecview.core.common.editpart.visibility.IVisibilityProcessable#resetVisibilityProperties() |
| */ |
| @Override |
| public void resetVisibilityProperties() { |
| IWidgetPresentation<?> presentation = getPresentation(); |
| if (presentation != null) { |
| presentation.resetVisibilityProperties(); |
| } |
| } |
| |
| /* (non-Javadoc) |
| * @see org.eclipse.osbp.ecview.core.common.editpart.IEmbeddableEditpart#restoreMemento() |
| */ |
| @Override |
| public void restoreMemento() { |
| if (isRendered()) { |
| if (!(getPresentation() instanceof IMementoHandler)) { |
| throw new UnsupportedOperationException( |
| "Memento not supported by element."); |
| } |
| |
| YMemento yMemento = loadMemento(getModel().getMementoId()); |
| if (yMemento != null) { |
| ((IMementoHandler) getPresentation()).applyMemento(yMemento); |
| } else { |
| LOGGER.debug("Memento is null. No apply to presentation. mementoId: " |
| + getModel().getMementoId()); |
| } |
| } |
| } |
| |
| /* (non-Javadoc) |
| * @see org.eclipse.osbp.ecview.core.common.editpart.IEmbeddableEditpart#saveMemento(java.lang.Object) |
| */ |
| @Override |
| public void saveMemento(Object memento) { |
| if (isRendered()) { |
| if (!(getPresentation() instanceof IMementoHandler)) { |
| throw new UnsupportedOperationException( |
| "Memento not supported by element."); |
| } |
| |
| YMemento yMemento = (YMemento) memento; |
| if (yMemento != null) { |
| IECViewMementoManager manager = getView().getContext() |
| .getService(IECViewMementoManager.class.getName()); |
| if (manager != null) { |
| manager.saveMemento(yMemento.getId(), yMemento); |
| } else { |
| LOGGER.warn("IMementoManager is not available."); |
| } |
| } else { |
| LOGGER.warn("Memento is null. No save done. mementoId: " |
| + memento); |
| } |
| } |
| } |
| |
| /** |
| * Load memento. |
| * |
| * @param mementoId |
| * the memento id |
| * @return the y memento |
| */ |
| protected YMemento loadMemento(String mementoId) { |
| IECViewMementoManager manager = getView().getContext().getService( |
| IECViewMementoManager.class.getName()); |
| if (manager == null) { |
| LOGGER.error("IMementoManager is not available."); |
| return null; |
| } |
| return (YMemento) manager.loadMemento(mementoId); |
| } |
| |
| /** |
| * Returns the datatype of the model. Or <code>null</code> if no datatype is |
| * available. |
| * |
| * @return the y datatype |
| */ |
| protected YDatatype internalGetDatatype() { |
| if (datatypeFeature == null) { |
| return null; |
| } |
| return (YDatatype) getModel().eGet(datatypeFeature); |
| } |
| |
| /** |
| * Is called to created the presenter for this edit part. |
| * |
| * @param <A> |
| * the generic type |
| * @return the a |
| */ |
| protected <A extends IWidgetPresentation<?>> A createPresenter() { |
| IViewEditpart viewEditPart = getView(); |
| if (viewEditPart == null) { |
| LOGGER.info("View is null"); |
| return null; |
| } |
| return DelegatingPresenterFactory.getInstance().createPresentation( |
| viewEditPart.getContext(), this); |
| } |
| |
| /* (non-Javadoc) |
| * @see org.eclipse.osbp.ecview.core.common.editpart.emf.ElementEditpart#initialize(org.eclipse.osbp.ecview.core.common.model.core.YElement) |
| */ |
| @Override |
| public void initialize(IViewContext context, M model) { |
| super.initialize(context, model); |
| |
| // directly after initialization the embeddable needs to become |
| // registered at the datatype editpart. No lazy loading can be used |
| // here. |
| registerAtDatatype(); |
| } |
| |
| /* (non-Javadoc) |
| * @see org.eclipse.osbp.ecview.core.common.editpart.emf.ElementEditpart#handleModelSet(int, org.eclipse.emf.common.notify.Notification) |
| */ |
| @Override |
| protected void handleModelSet(int featureId, Notification notification) { |
| checkDisposed(); |
| |
| if (notification.getFeature() == datatypeFeature) { |
| YDatatype oldYDatatype = (YDatatype) notification.getOldValue(); |
| if (oldYDatatype != null) { |
| // unregister the element from the old datatype |
| unregisterFromDatatype(oldYDatatype); |
| } |
| |
| // an register the field to the new datatype if available |
| YDatatype newYDatatype = (YDatatype) notification.getNewValue(); |
| if (newYDatatype != null) { |
| registerAtDatatype(); |
| } |
| } else { |
| super.handleModelSet(featureId, notification); |
| } |
| } |
| |
| /** |
| * Registers the element at the datatype. Changes on the datatype will |
| * update the embeddable. |
| */ |
| protected void registerAtDatatype() { |
| // unregisters the datatype editpart |
| YDatatype yDatatype = internalGetDatatype(); |
| if (yDatatype != null) { |
| IDatatypeEditpart datatypeEditpart = getEditpart(viewContext, yDatatype); |
| datatypeEditpart.addBridge(this); |
| |
| notifyDatatypeChanged(datatypeEditpart.getCurrentState()); |
| } |
| } |
| |
| /** |
| * Unregisters the element from the datatype. So changes on the datatype do |
| * not update the embeddable anymore. |
| * |
| * @param yDatatype |
| * the y datatype |
| */ |
| protected void unregisterFromDatatype(YDatatype yDatatype) { |
| // unregisters the datatype editpart |
| if (yDatatype != null) { |
| IDatatypeEditpart datatypeEditpart = getEditpart(viewContext, yDatatype); |
| datatypeEditpart.removeBridge(this); |
| notifyDatatypeChanged(createDatatypeUnsetEvent(datatypeEditpart)); |
| } |
| } |
| |
| /** |
| * Create an internal event that resets the datatype information. |
| * |
| * @param datatypeEditpart |
| * the datatype editpart |
| * @return the datatype change event |
| */ |
| private DatatypeChangeEvent createDatatypeUnsetEvent( |
| IDatatypeEditpart datatypeEditpart) { |
| |
| List<IValidatorEditpart> toRemove = new ArrayList<>( |
| getDatatypeValidators()); |
| DatatypeChangeEvent event = new DatatypeChangeEvent(true, |
| datatypeEditpart, null, null, toRemove); |
| return event; |
| } |
| |
| /* (non-Javadoc) |
| * @see org.eclipse.osbp.ecview.core.common.editpart.datatypes.IDatatypeEditpart.DatatypeBridge#notifyDatatypeChanged(org.eclipse.osbp.ecview.core.common.editpart.datatypes.IDatatypeEditpart.DatatypeChangeEvent) |
| */ |
| @Override |
| public void notifyDatatypeChanged(DatatypeChangeEvent event) { |
| IWidgetPresentation<?> presentation = getPresentation(); |
| if (presentation != null) { |
| presentation.notifyDatatypeChanged(event); |
| } else { |
| LOGGER.warn("Presentation is null for " + getModel()); |
| } |
| } |
| |
| /** |
| * {@inheritDoc} |
| */ |
| @Override |
| protected void internalDispose() { |
| try { |
| // unregister the element from the datatype |
| YDatatype yDatatype = internalGetDatatype(); |
| if (yDatatype != null) { |
| unregisterFromDatatype(yDatatype); |
| } |
| |
| // dispose the presenter |
| // |
| if (presentation != null) { |
| presentation.dispose(); |
| presentation = null; |
| } |
| |
| } finally { |
| super.internalDispose(); |
| } |
| } |
| |
| /* (non-Javadoc) |
| * @see org.eclipse.osbp.ecview.core.common.editpart.IEmbeddableEditpart#requestRender() |
| */ |
| @Override |
| public void requestRender() { |
| if (getParent() != null) { |
| getParent().renderChild(this); |
| } else { |
| unrender(); |
| } |
| } |
| |
| /* (non-Javadoc) |
| * @see org.eclipse.osbp.ecview.core.common.editpart.IEmbeddableEditpart#render(java.lang.Object) |
| */ |
| @Override |
| public Object render(Object parentWidget) { |
| if (getPresentation() == null) { |
| throw new IllegalStateException("No presentation for " + getModel()); |
| } |
| return getPresentation().createWidget(parentWidget); |
| } |
| |
| /* (non-Javadoc) |
| * @see org.eclipse.osbp.ecview.core.common.editpart.IEmbeddableEditpart#requestUnrender() |
| */ |
| @Override |
| public void requestUnrender() { |
| if (getParent() != null) { |
| getParent().unrenderChild(this); |
| } else { |
| unrender(); |
| } |
| } |
| |
| /* (non-Javadoc) |
| * @see org.eclipse.osbp.ecview.core.common.editpart.IEmbeddableEditpart#unrender() |
| */ |
| @Override |
| public void unrender() { |
| IWidgetPresentation<?> presentation = getPresentation(); |
| if (presentation != null) { |
| presentation.unrender(); |
| } |
| } |
| |
| /* (non-Javadoc) |
| * @see org.eclipse.osbp.ecview.core.common.editpart.IEmbeddableEditpart#isRendered() |
| */ |
| @Override |
| public boolean isRendered() { |
| return internalGetPresentation() != null |
| && internalGetPresentation().isRendered(); |
| } |
| |
| /* (non-Javadoc) |
| * @see org.eclipse.osbp.ecview.core.common.editpart.IEmbeddableEditpart#getWidget() |
| */ |
| @Override |
| public Object getWidget() { |
| IWidgetPresentation<?> presentation = getPresentation(); |
| if (presentation != null) { |
| return presentation.getWidget(); |
| } |
| return null; |
| } |
| |
| /* (non-Javadoc) |
| * @see org.eclipse.osbp.ecview.core.common.editpart.emf.ElementEditpart#requestDispose() |
| */ |
| @Override |
| public void requestDispose() { |
| if (getParent() != null) { |
| getParent().disposeChild(this); |
| } else { |
| // in case where the embeddable is not added to a layout |
| dispose(); |
| } |
| } |
| } |