X-Git-Url: https://gerrit.simantics.org/r/gitweb?a=blobdiff_plain;f=bundles%2Forg.simantics.diagram%2Fsrc%2Forg%2Fsimantics%2Fdiagram%2Fsynchronization%2Fruntime%2FDiagramSelectionUpdater.java;h=28d79aff4f3df3ce831a4864ce9708f34c8bf05f;hb=006602e856bbc3e222789cfe00a923b863e3e91b;hp=e6e0d11dfd9410c3777a489983d839db760b2bba;hpb=969bd23cab98a79ca9101af33334000879fb60c5;p=simantics%2Fplatform.git diff --git a/bundles/org.simantics.diagram/src/org/simantics/diagram/synchronization/runtime/DiagramSelectionUpdater.java b/bundles/org.simantics.diagram/src/org/simantics/diagram/synchronization/runtime/DiagramSelectionUpdater.java index e6e0d11df..28d79aff4 100644 --- a/bundles/org.simantics.diagram/src/org/simantics/diagram/synchronization/runtime/DiagramSelectionUpdater.java +++ b/bundles/org.simantics.diagram/src/org/simantics/diagram/synchronization/runtime/DiagramSelectionUpdater.java @@ -1,168 +1,168 @@ -/******************************************************************************* - * Copyright (c) 2011 Association for Decentralized Information Management in - * Industry THTH ry. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Eclipse Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/epl-v10.html - * - * Contributors: - * VTT Technical Research Centre of Finland - initial API and implementation - *******************************************************************************/ -package org.simantics.diagram.synchronization.runtime; - -import java.util.ArrayList; -import java.util.Collection; -import java.util.Set; -import java.util.concurrent.atomic.AtomicReference; - -import org.simantics.diagram.ui.DiagramModelHints; -import org.simantics.g2d.canvas.ICanvasContext; -import org.simantics.g2d.diagram.DiagramHints; -import org.simantics.g2d.diagram.IDiagram; -import org.simantics.g2d.diagram.handler.DataElementMap; -import org.simantics.g2d.diagram.participant.Selection; -import org.simantics.g2d.element.IElement; -import org.simantics.utils.datastructures.hints.HintListenerAdapter; -import org.simantics.utils.datastructures.hints.IHintContext.Key; -import org.simantics.utils.datastructures.hints.IHintObservable; -import org.simantics.utils.threads.ThreadUtils; - -/** - * @author Tuukka Lehtonen - */ -public class DiagramSelectionUpdater extends HintListenerAdapter { - - private static final boolean DEBUG_SELECTION_UPDATE = false; - - private final ICanvasContext ctx; - private final Selection selection; - private final IDiagram diagram; - - private int selectionId; - private AtomicReference> newSelection = new AtomicReference>(); - - private boolean oneshot = false; - private boolean tracking = false; - - public DiagramSelectionUpdater(ICanvasContext ctx) { - this.ctx = ctx; - this.selection = ctx.getAtMostOneItemOfClass(Selection.class); - if (selection == null) - throw new IllegalArgumentException("no selection participant"); - this.diagram = ctx.getDefaultHintContext().getHint(DiagramHints.KEY_DIAGRAM); - if (diagram == null) - throw new IllegalArgumentException("no diagram"); - } - - public DiagramSelectionUpdater(ICanvasContext ctx, IDiagram diagram) { - this.ctx = ctx; - this.selection = ctx.getAtMostOneItemOfClass(Selection.class); - if (selection == null) - throw new IllegalArgumentException("no selection participant"); - this.diagram = diagram; - if (diagram == null) - throw new IllegalArgumentException("no diagram"); - } - - protected Selection getSelectionParticipant() { - return ctx.getSingleItem(Selection.class); - } - - public DiagramSelectionUpdater setNewSelection(int selectionId, Set newSelection) { - this.selectionId = selectionId; - this.newSelection.set(newSelection); - return this; - } - - public Set getNewSelection() { - return newSelection.get(); - } - - public DiagramSelectionUpdater setOneshot(boolean oneshot) { - this.oneshot = oneshot; - return this; - } - - public DiagramSelectionUpdater track() { - if (!tracking) { - diagram.addKeyHintListener(DiagramModelHints.KEY_DIAGRAM_CONTENTS_UPDATED, this); - tracking = true; - } - return this; - } - - public DiagramSelectionUpdater untrack() { - if (tracking) { - diagram.removeKeyHintListener(DiagramModelHints.KEY_DIAGRAM_CONTENTS_UPDATED, this); - tracking = false; - } - return this; - } - - @Override - public void hintChanged(IHintObservable sender, Key key, Object oldValue, Object newValue) { - if (!ctx.isDisposed() && key == DiagramModelHints.KEY_DIAGRAM_CONTENTS_UPDATED) { - if (DEBUG_SELECTION_UPDATE) - System.out.println(getClass().getSimpleName() + ": DIAGRAM UPDATED @" + System.currentTimeMillis() + ", selection to set: " + newSelection); - Set ns = newSelection.getAndSet(null); - if (ns != null) { - scheduleSetDiagramSelection(2, ns); - } - } - - if (oneshot) { - // Remove self from listening duties. - sender.removeHintListener(this); - } - } - - private void scheduleSetDiagramSelection(final int tries, final Set data) { - ThreadUtils.asyncExec(ctx.getThreadAccess(), new Runnable() { - @Override - public void run() { - setDiagramSelectionToData(tries, data); - } - }); - } - - private void setDiagramSelectionToData(final int tries, final Set data) { - if (DEBUG_SELECTION_UPDATE) - System.out.println("setDiagramSelectionToData(" + tries + ", " + data + ")"); - - DataElementMap dem = diagram.getDiagramClass().getAtMostOneItemOfClass(DataElementMap.class); - if (dem != null) { - final Collection newSelection = new ArrayList(data.size()); - for (Object datum : data) { - IElement element = dem.getElement(diagram, datum); - if (DEBUG_SELECTION_UPDATE) - System.out.println(" DATUM " + datum + " -> " + element); - if (element != null) { - newSelection.add(element); - } else { - if (tries > 0) { - // Try later if there are tries left. - ThreadUtils.asyncExec(ctx.getThreadAccess(), new Runnable() { - @Override - public void run() { - setDiagramSelectionToData(tries - 1, data); - } - }); - return; - } - // Otherwise select whatever is found. - } - } - - if (DEBUG_SELECTION_UPDATE) - System.out.println("[" + tries + "] final new selection: " + newSelection); - - if (!newSelection.isEmpty()) { - //for (IElement e : newSelection) - // e.setHint(Hints.KEY_DIRTY, Hints.VALUE_SG_DIRTY); - selection.setSelection(selectionId, newSelection); - } - } - } - -} +/******************************************************************************* + * Copyright (c) 2011 Association for Decentralized Information Management in + * Industry THTH ry. + * All rights reserved. This program and the accompanying materials + * are made available under the terms of the Eclipse Public License v1.0 + * which accompanies this distribution, and is available at + * http://www.eclipse.org/legal/epl-v10.html + * + * Contributors: + * VTT Technical Research Centre of Finland - initial API and implementation + *******************************************************************************/ +package org.simantics.diagram.synchronization.runtime; + +import java.util.ArrayList; +import java.util.Collection; +import java.util.Set; +import java.util.concurrent.atomic.AtomicReference; + +import org.simantics.diagram.ui.DiagramModelHints; +import org.simantics.g2d.canvas.ICanvasContext; +import org.simantics.g2d.diagram.DiagramHints; +import org.simantics.g2d.diagram.IDiagram; +import org.simantics.g2d.diagram.handler.DataElementMap; +import org.simantics.g2d.diagram.participant.Selection; +import org.simantics.g2d.element.IElement; +import org.simantics.utils.datastructures.hints.HintListenerAdapter; +import org.simantics.utils.datastructures.hints.IHintContext.Key; +import org.simantics.utils.datastructures.hints.IHintObservable; +import org.simantics.utils.threads.ThreadUtils; + +/** + * @author Tuukka Lehtonen + */ +public class DiagramSelectionUpdater extends HintListenerAdapter { + + private static final boolean DEBUG_SELECTION_UPDATE = false; + + private final ICanvasContext ctx; + private final Selection selection; + private final IDiagram diagram; + + private int selectionId; + private AtomicReference> newSelection = new AtomicReference>(); + + private boolean oneshot = false; + private boolean tracking = false; + + public DiagramSelectionUpdater(ICanvasContext ctx) { + this.ctx = ctx; + this.selection = ctx.getAtMostOneItemOfClass(Selection.class); + if (selection == null) + throw new IllegalArgumentException("no selection participant"); + this.diagram = ctx.getDefaultHintContext().getHint(DiagramHints.KEY_DIAGRAM); + if (diagram == null) + throw new IllegalArgumentException("no diagram"); + } + + public DiagramSelectionUpdater(ICanvasContext ctx, IDiagram diagram) { + this.ctx = ctx; + this.selection = ctx.getAtMostOneItemOfClass(Selection.class); + if (selection == null) + throw new IllegalArgumentException("no selection participant"); + this.diagram = diagram; + if (diagram == null) + throw new IllegalArgumentException("no diagram"); + } + + protected Selection getSelectionParticipant() { + return ctx.getSingleItem(Selection.class); + } + + public DiagramSelectionUpdater setNewSelection(int selectionId, Set newSelection) { + this.selectionId = selectionId; + this.newSelection.set(newSelection); + return this; + } + + public Set getNewSelection() { + return newSelection.get(); + } + + public DiagramSelectionUpdater setOneshot(boolean oneshot) { + this.oneshot = oneshot; + return this; + } + + public DiagramSelectionUpdater track() { + if (!tracking) { + diagram.addKeyHintListener(DiagramModelHints.KEY_DIAGRAM_CONTENTS_UPDATED, this); + tracking = true; + } + return this; + } + + public DiagramSelectionUpdater untrack() { + if (tracking) { + diagram.removeKeyHintListener(DiagramModelHints.KEY_DIAGRAM_CONTENTS_UPDATED, this); + tracking = false; + } + return this; + } + + @Override + public void hintChanged(IHintObservable sender, Key key, Object oldValue, Object newValue) { + if (!ctx.isDisposed() && key == DiagramModelHints.KEY_DIAGRAM_CONTENTS_UPDATED) { + if (DEBUG_SELECTION_UPDATE) + System.out.println(getClass().getSimpleName() + ": DIAGRAM UPDATED @" + System.currentTimeMillis() + ", selection to set: " + newSelection); + Set ns = newSelection.getAndSet(null); + if (ns != null) { + scheduleSetDiagramSelection(2, ns); + } + } + + if (oneshot) { + // Remove self from listening duties. + sender.removeHintListener(this); + } + } + + private void scheduleSetDiagramSelection(final int tries, final Set data) { + ThreadUtils.asyncExec(ctx.getThreadAccess(), new Runnable() { + @Override + public void run() { + setDiagramSelectionToData(tries, data); + } + }); + } + + private void setDiagramSelectionToData(final int tries, final Set data) { + if (DEBUG_SELECTION_UPDATE) + System.out.println("setDiagramSelectionToData(" + tries + ", " + data + ")"); + + DataElementMap dem = diagram.getDiagramClass().getAtMostOneItemOfClass(DataElementMap.class); + if (dem != null) { + final Collection newSelection = new ArrayList(data.size()); + for (Object datum : data) { + IElement element = dem.getElement(diagram, datum); + if (DEBUG_SELECTION_UPDATE) + System.out.println(" DATUM " + datum + " -> " + element); + if (element != null) { + newSelection.add(element); + } else { + if (tries > 0) { + // Try later if there are tries left. + ThreadUtils.asyncExec(ctx.getThreadAccess(), new Runnable() { + @Override + public void run() { + setDiagramSelectionToData(tries - 1, data); + } + }); + return; + } + // Otherwise select whatever is found. + } + } + + if (DEBUG_SELECTION_UPDATE) + System.out.println("[" + tries + "] final new selection: " + newSelection); + + if (!newSelection.isEmpty()) { + //for (IElement e : newSelection) + // e.setHint(Hints.KEY_DIRTY, Hints.VALUE_SG_DIRTY); + selection.setSelection(selectionId, newSelection); + } + } + } + +}