View Javadoc
1   /**
2    * 
3    * Copyright (c) 2014, Openflexo
4    * 
5    * This file is part of Gina-swing, a component of the software infrastructure 
6    * developed at Openflexo.
7    * 
8    * 
9    * Openflexo is dual-licensed under the European Union Public License (EUPL, either 
10   * version 1.1 of the License, or any later version ), which is available at 
11   * https://joinup.ec.europa.eu/software/page/eupl/licence-eupl
12   * and the GNU General Public License (GPL, either version 3 of the License, or any 
13   * later version), which is available at http://www.gnu.org/licenses/gpl.html .
14   * 
15   * You can redistribute it and/or modify under the terms of either of these licenses
16   * 
17   * If you choose to redistribute it and/or modify under the terms of the GNU GPL, you
18   * must include the following additional permission.
19   *
20   *          Additional permission under GNU GPL version 3 section 7
21   *
22   *          If you modify this Program, or any covered work, by linking or 
23   *          combining it with software containing parts covered by the terms 
24   *          of EPL 1.0, the licensors of this Program grant you additional permission
25   *          to convey the resulting work. * 
26   * 
27   * This software is distributed in the hope that it will be useful, but WITHOUT ANY 
28   * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A 
29   * PARTICULAR PURPOSE. 
30   *
31   * See http://www.openflexo.org/license.html for details.
32   * 
33   * 
34   * Please contact Openflexo (openflexo-contacts@openflexo.org)
35   * or visit www.openflexo.org if you need additional information.
36   * 
37   */
38  
39  package org.openflexo.gina.swing.editor;
40  
41  import java.beans.PropertyChangeEvent;
42  import java.beans.PropertyChangeListener;
43  import java.util.ArrayList;
44  import java.util.HashMap;
45  import java.util.List;
46  import java.util.Map;
47  import java.util.logging.Logger;
48  
49  import javax.swing.ImageIcon;
50  
51  import org.openflexo.connie.annotations.NotificationUnsafe;
52  import org.openflexo.gina.FIBFolder;
53  import org.openflexo.gina.FIBLibrary;
54  import org.openflexo.gina.controller.FIBController;
55  import org.openflexo.gina.model.FIBComponent;
56  import org.openflexo.gina.model.FIBModelObject;
57  import org.openflexo.gina.model.FIBValidationReport;
58  import org.openflexo.gina.model.container.FIBPanel;
59  import org.openflexo.gina.model.container.FIBSplitPanel;
60  import org.openflexo.gina.model.container.FIBTabPanel;
61  import org.openflexo.gina.model.graph.FIBGraph;
62  import org.openflexo.gina.model.graph.FIBGraphFunction;
63  import org.openflexo.gina.model.operator.FIBConditional;
64  import org.openflexo.gina.model.operator.FIBIteration;
65  import org.openflexo.gina.model.widget.FIBBrowser;
66  import org.openflexo.gina.model.widget.FIBBrowserAction;
67  import org.openflexo.gina.model.widget.FIBBrowserDragOperation;
68  import org.openflexo.gina.model.widget.FIBBrowserElement;
69  import org.openflexo.gina.model.widget.FIBBrowserElementChildren;
70  import org.openflexo.gina.model.widget.FIBButton;
71  import org.openflexo.gina.model.widget.FIBCheckBox;
72  import org.openflexo.gina.model.widget.FIBCustom;
73  import org.openflexo.gina.model.widget.FIBDropDown;
74  import org.openflexo.gina.model.widget.FIBImage;
75  import org.openflexo.gina.model.widget.FIBLabel;
76  import org.openflexo.gina.model.widget.FIBNumber;
77  import org.openflexo.gina.model.widget.FIBRadioButtonList;
78  import org.openflexo.gina.model.widget.FIBReferencedComponent;
79  import org.openflexo.gina.model.widget.FIBTable;
80  import org.openflexo.gina.model.widget.FIBTableAction;
81  import org.openflexo.gina.model.widget.FIBTableAction.ActionType;
82  import org.openflexo.gina.model.widget.FIBTableColumn;
83  import org.openflexo.gina.model.widget.FIBTextArea;
84  import org.openflexo.gina.model.widget.FIBTextField;
85  import org.openflexo.gina.swing.editor.controller.FIBEditorIconLibrary;
86  import org.openflexo.gina.swing.utils.FIBUtilsIconLibrary;
87  import org.openflexo.gina.swing.view.SwingViewFactory;
88  import org.openflexo.gina.utils.FIBIconLibrary;
89  import org.openflexo.icon.IconFactory;
90  import org.openflexo.pamela.validation.FixProposal;
91  import org.openflexo.pamela.validation.InformationIssue;
92  import org.openflexo.pamela.validation.ValidationError;
93  import org.openflexo.pamela.validation.ValidationModel;
94  import org.openflexo.pamela.validation.ValidationReport;
95  import org.openflexo.pamela.validation.ValidationWarning;
96  import org.openflexo.rm.Resource;
97  
98  /**
99   * A {@link FIBController} used in GINA SwingEditor, and addressing a data object of type T
100  * 
101  * @author sylvain
102  *
103  * @param <T>
104  *            type of data object beeing managed by this controller
105  */
106 public class SwingEditorFIBController<T> extends FIBController implements PropertyChangeListener {
107 
108 	static final Logger LOGGER = Logger.getLogger(SwingEditorFIBController.class.getPackage().getName());
109 
110 	private final Map<Object, ImageIcon> cachedIcons = new HashMap<>();
111 	private final List<ValidationReport> observedReports = new ArrayList<>();
112 	private FIBModelObject selectedObject;
113 
114 	public SwingEditorFIBController(FIBComponent rootComponent) {
115 		super(rootComponent, SwingViewFactory.INSTANCE);
116 		// Default parent localizer is the main localizer
117 		setParentLocalizer(FIBEditor.EDITOR_LOCALIZATION);
118 	}
119 
120 	protected ImageIcon retrieveIconForObject(Object object) {
121 
122 		if (object instanceof FIBModelObject) {
123 			FIBValidationReport report = getValidationReport((FIBModelObject) object);
124 			if (report != null) {
125 				if (!observedReports.contains(report)) {
126 					report.getPropertyChangeSupport().addPropertyChangeListener(this);
127 					// System.out.println("Observing " + report);
128 					observedReports.add(report);
129 				}
130 			}
131 		}
132 
133 		if (object instanceof ValidationError) {
134 			if (((ValidationError<?, ?>) object).isFixable()) {
135 				return FIBUtilsIconLibrary.FIXABLE_ERROR_ICON;
136 			}
137 			else {
138 				return FIBUtilsIconLibrary.UNFIXABLE_ERROR_ICON;
139 			}
140 		}
141 		else if (object instanceof ValidationWarning) {
142 			if (((ValidationWarning<?, ?>) object).isFixable()) {
143 				return FIBUtilsIconLibrary.FIXABLE_WARNING_ICON;
144 			}
145 			else {
146 				return FIBUtilsIconLibrary.UNFIXABLE_WARNING_ICON;
147 			}
148 		}
149 		else if (object instanceof InformationIssue) {
150 			return FIBUtilsIconLibrary.INFO_ISSUE_ICON;
151 		}
152 		else if (object instanceof FixProposal) {
153 			return FIBUtilsIconLibrary.FIX_PROPOSAL_ICON;
154 		}
155 
156 		if (object instanceof FIBFolder) {
157 			return FIBIconLibrary.FOLDER_ICON;
158 		}
159 		else if (object instanceof FIBLibrary) {
160 			return FIBIconLibrary.FOLDER_ICON;
161 		}
162 		else if (object instanceof Resource) {
163 			return FIBEditorIconLibrary.ROOT_COMPONENT_ICON;
164 		}
165 
166 		if (object instanceof FIBIteration) {
167 			return FIBEditorIconLibrary.ITERATION_ICON;
168 		}
169 		else if (object instanceof FIBConditional) {
170 			return FIBEditorIconLibrary.CONDITIONAL_ICON;
171 		}
172 		else if (object instanceof FIBComponent && ((FIBComponent) object).isRootComponent()) {
173 			return FIBEditorIconLibrary.ROOT_COMPONENT_ICON;
174 		}
175 		else if (object instanceof FIBTabPanel) {
176 			return FIBEditorIconLibrary.TABS_ICON;
177 		}
178 		else if (object instanceof FIBPanel) {
179 			return FIBEditorIconLibrary.PANEL_ICON;
180 		}
181 		else if (object instanceof FIBSplitPanel) {
182 			return FIBEditorIconLibrary.SPLIT_PANEL_ICON;
183 		}
184 		else if (object instanceof FIBCheckBox) {
185 			return FIBEditorIconLibrary.CHECKBOX_ICON;
186 		}
187 		else if (object instanceof FIBLabel) {
188 			return FIBEditorIconLibrary.LABEL_ICON;
189 		}
190 		else if (object instanceof FIBTable) {
191 			return FIBEditorIconLibrary.TABLE_ICON;
192 		}
193 		else if (object instanceof FIBBrowser) {
194 			return FIBEditorIconLibrary.BROWSER_ICON;
195 		}
196 		else if (object instanceof FIBTextArea) {
197 			return FIBEditorIconLibrary.TEXTAREA_ICON;
198 		}
199 		else if (object instanceof FIBTextField) {
200 			return FIBEditorIconLibrary.TEXTFIELD_ICON;
201 		}
202 		else if (object instanceof FIBImage) {
203 			return FIBEditorIconLibrary.IMAGE_ICON;
204 		}
205 		else if (object instanceof FIBNumber) {
206 			return FIBEditorIconLibrary.NUMBER_ICON;
207 		}
208 		else if (object instanceof FIBDropDown) {
209 			return FIBEditorIconLibrary.DROPDOWN_ICON;
210 		}
211 		else if (object instanceof FIBRadioButtonList) {
212 			return FIBEditorIconLibrary.RADIOBUTTON_ICON;
213 		}
214 		else if (object instanceof FIBButton) {
215 			return FIBEditorIconLibrary.BUTTON_ICON;
216 		}
217 		else if (object instanceof FIBCustom) {
218 			return FIBEditorIconLibrary.CUSTOM_ICON;
219 		}
220 		else if (object instanceof FIBReferencedComponent) {
221 			return FIBEditorIconLibrary.REFERENCE_COMPONENT_ICON;
222 		}
223 		else if (object instanceof FIBGraph) {
224 			return FIBEditorIconLibrary.GRAPH_ICON;
225 		}
226 		else if (object instanceof FIBGraphFunction) {
227 			return FIBEditorIconLibrary.GRAPH_FUNCTION_ICON;
228 		}
229 		else if (object instanceof FIBTableColumn) {
230 			return FIBEditorIconLibrary.TABLE_COLUMN_ICON;
231 		}
232 		else if (object instanceof FIBTableAction) {
233 			if (((FIBTableAction) object).getActionType() == ActionType.Add) {
234 				return IconFactory.getImageIcon(FIBEditorIconLibrary.TABLE_ACTION_ICON, FIBEditorIconLibrary.DUPLICATE);
235 			}
236 			if (((FIBTableAction) object).getActionType() == ActionType.Delete) {
237 				return IconFactory.getImageIcon(FIBEditorIconLibrary.TABLE_ACTION_ICON, FIBEditorIconLibrary.DELETE);
238 			}
239 			return FIBEditorIconLibrary.TABLE_ACTION_ICON;
240 		}
241 		else if (object instanceof FIBBrowserElement) {
242 			return FIBEditorIconLibrary.BROWSER_ELEMENT_ICON;
243 		}
244 		else if (object instanceof FIBBrowserElementChildren) {
245 			return FIBEditorIconLibrary.BROWSER_ELEMENT_CHILDREN_ICON;
246 		}
247 		else if (object instanceof FIBBrowserAction) {
248 			if (((FIBBrowserAction) object).getActionType() == org.openflexo.gina.model.widget.FIBBrowserAction.ActionType.Add) {
249 				return IconFactory.getImageIcon(FIBEditorIconLibrary.BROWSER_ELEMENT_ACTION_ICON, FIBEditorIconLibrary.DUPLICATE);
250 			}
251 			if (((FIBBrowserAction) object).getActionType() == org.openflexo.gina.model.widget.FIBBrowserAction.ActionType.Delete) {
252 				return IconFactory.getImageIcon(FIBEditorIconLibrary.BROWSER_ELEMENT_ACTION_ICON, FIBEditorIconLibrary.DELETE);
253 			}
254 			return FIBEditorIconLibrary.BROWSER_ELEMENT_ACTION_ICON;
255 		}
256 		else if (object instanceof FIBBrowserDragOperation) {
257 			return FIBEditorIconLibrary.DRAG_OPERATION_ICON;
258 		}
259 
260 		return null;
261 	}
262 
263 	@NotificationUnsafe
264 	public final ImageIcon iconForObject(Object object) {
265 
266 		ImageIcon returned = cachedIcons.get(object);
267 		if (returned == null) {
268 			returned = retrieveIconForObject(object);
269 			if (object instanceof FIBModelObject && hasValidationReport((FIBModelObject) object)) {
270 				if (hasErrors((FIBModelObject) object)) {
271 					returned = IconFactory.getImageIcon(returned, FIBUtilsIconLibrary.ERROR);
272 				}
273 				else if (hasWarnings((FIBModelObject) object)) {
274 					returned = IconFactory.getImageIcon(returned, FIBUtilsIconLibrary.WARNING);
275 				}
276 				cachedIcons.put(object, returned);
277 			}
278 		}
279 		return returned;
280 	}
281 
282 	protected void clearCachedIcons() {
283 		cachedIcons.clear();
284 	}
285 
286 	@Override
287 	public T getDataObject() {
288 		return (T) super.getDataObject();
289 	}
290 
291 	public FIBModelObject getSelectedObject() {
292 		return selectedObject;
293 	}
294 
295 	public void setSelectedObject(FIBModelObject selectedObject) {
296 		if ((selectedObject == null && this.selectedObject != null)
297 				|| (selectedObject != null && !selectedObject.equals(this.selectedObject))) {
298 			FIBModelObject oldValue = this.selectedObject;
299 			this.selectedObject = selectedObject;
300 			getPropertyChangeSupport().firePropertyChange("selectedObject", oldValue, selectedObject);
301 		}
302 	}
303 
304 	public boolean hasValidationReport(FIBModelObject object) {
305 		FIBValidationReport validationReport = getValidationReport(object);
306 		return (validationReport != null);
307 	}
308 
309 	public boolean hasErrors(FIBModelObject object) {
310 		FIBValidationReport validationReport = getValidationReport(object);
311 		if (validationReport != null) {
312 			return validationReport.hasErrors(object);
313 		}
314 		return false;
315 	}
316 
317 	public boolean hasWarnings(FIBModelObject object) {
318 		FIBValidationReport validationReport = getValidationReport(object);
319 		if (validationReport != null) {
320 			return validationReport.hasWarnings(object);
321 		}
322 		return false;
323 	}
324 
325 	public FIBValidationReport getValidationReport(FIBModelObject object) {
326 		return null;
327 	}
328 
329 	public ValidationModel getValidationModel(FIBModelObject object) {
330 		if (object != null) {
331 			return object.getComponent().getModelFactory().getValidationModel();
332 		}
333 		return null;
334 	}
335 
336 	@Override
337 	public void propertyChange(PropertyChangeEvent evt) {
338 		if (evt.getSource() instanceof ValidationReport) {
339 			clearCachedIcons();
340 		}
341 	}
342 
343 }