package org.simantics.document.swt.core; import java.util.Collection; import java.util.HashMap; import java.util.HashSet; import java.util.Map; import org.eclipse.jface.layout.GridDataFactory; import org.eclipse.jface.layout.GridLayoutFactory; import org.eclipse.jface.viewers.ISelectionProvider; import org.eclipse.swt.graphics.Color; import org.eclipse.swt.graphics.Device; import org.eclipse.swt.graphics.Font; import org.eclipse.swt.widgets.Composite; import org.eclipse.swt.widgets.Control; import org.eclipse.ui.IWorkbenchSite; import org.simantics.db.common.utils.Logger; import org.simantics.document.server.JSONObject; import org.simantics.document.server.client.DocumentClient; import org.simantics.document.server.client.WidgetData; import org.simantics.document.server.client.WidgetMapping; import org.simantics.document.server.handler.AbstractEventHandler; import org.simantics.document.server.io.CommandContext; import org.simantics.document.swt.core.base.WidgetContainer; import org.simantics.document.swt.core.widget.FillComposite; import org.simantics.ui.colors.Colors; import org.simantics.ui.fonts.Fonts; import org.simantics.utils.threads.IThreadWorkQueue; import org.simantics.utils.threads.SWTThread; public class SWTDocumentClient extends DocumentClient implements SWTDocument { private Composite container; private IWorkbenchSite site; private ISelectionProvider selectionProvider; private Device device; private IThreadWorkQueue thread; private Map colors = new HashMap(); private Map fonts = new HashMap(); private boolean requireLayout=false; public SWTDocumentClient(WidgetMapping mapping, ISelectionProvider selectionProvider, IWorkbenchSite site, Composite container) { super(mapping, SWTViews.getCommandMapping()); this.container = container; this.site = site; this.selectionProvider = selectionProvider; this.device = container.getDisplay(); this.thread = SWTThread.getThreadAccess(container); JSONObject rootObject = new JSONObject("root"); rootObject.addJSONField("type", "Root"); FillComposite mgr = new FillComposite(); WidgetContainer wc = mgr.createWidget(rootObject); wc.createControl(this, container, rootObject); GridDataFactory.fillDefaults().grab(true, true).minSize(1, 1).applyTo((Control)wc.getControl()); GridLayoutFactory.fillDefaults().applyTo((Composite)wc.getControl()); widgetData.put("root", new WidgetData(this, wc, rootObject)); } @Override public IThreadWorkQueue thread() { return thread; } @Override public Color getColor(org.simantics.datatypes.literal.RGB.Integer descriptor) { Color color = colors.get(descriptor); if(color == null) { color = Colors.swt(device, descriptor); colors.put(descriptor, color); } return color; } @Override public Font getFont(org.simantics.datatypes.literal.Font descriptor) { Font font = fonts.get(descriptor); if(font == null) { font = Fonts.swt(device, descriptor); fonts.put(descriptor, font); } return font; } @Override public ISelectionProvider getSelectionProvider() { return selectionProvider; } @Override public IWorkbenchSite getSite() { return site; } @Override public void post(final AbstractEventHandler handler, CommandContext parameters) { handler.handle(parameters); } @Override protected void updateDocument(Collection objects) { assert thread.currentThreadAccess(); super.updateDocument(objects); if(requireLayout) { container.layout(true, true); requireLayout = false; } } @Override protected void updateTree(HashSet updates) { if(updates.isEmpty()) return; for(WidgetData data : updates) { WidgetContainer container = (WidgetContainer)data.widget; Control ctrl = container.getControl(); if (ctrl == null || ctrl.isDisposed()) continue; if(ctrl instanceof Composite) { Composite composite = (Composite)ctrl; for(Control c : composite.getChildren()) { c.dispose(); } } } super.updateTree(updates); for(WidgetData data : widgetData.values()) { WidgetContainer container = (WidgetContainer)data.widget; if(container != null) container.getOrCreateControl(this, data.object); } } @Override public void layout() { requireLayout = true; } @Override public HashMap getWidgetData() { return widgetData; } public void displayError(String error) { Logger.defaultLogError(error); } }