c208f5c2506d6a0de4a2273aaff47e1c9c79f777
[taxeditor.git] / eu.etaxonomy.taxeditor.store / src / main / java / eu / etaxonomy / taxeditor / ui / section / campanula / EntitySelectionFieldController.java
1 // $Id$
2 /**
3 * Copyright (C) 2013 EDIT
4 * European Distributed Institute of Taxonomy
5 * http://www.e-taxonomy.eu
6 *
7 * The contents of this file are subject to the Mozilla Public License Version 1.1
8 * See LICENSE.TXT at the top of this package for the full license terms.
9 */
10 package eu.etaxonomy.taxeditor.ui.section.campanula;
11
12 import org.eclipse.core.runtime.IStatus;
13 import org.eclipse.jface.wizard.WizardDialog;
14 import org.eclipse.swt.events.SelectionAdapter;
15 import org.eclipse.swt.events.SelectionEvent;
16 import org.eclipse.swt.graphics.Color;
17 import org.eclipse.swt.widgets.Button;
18 import org.eclipse.swt.widgets.Composite;
19 import org.eclipse.swt.widgets.Label;
20 import org.eclipse.swt.widgets.Shell;
21 import org.springframework.security.core.GrantedAuthority;
22
23 import eu.etaxonomy.cdm.api.conversation.ConversationHolder;
24 import eu.etaxonomy.cdm.common.CdmUtils;
25 import eu.etaxonomy.cdm.model.common.Group;
26 import eu.etaxonomy.cdm.model.common.ICdmBase;
27 import eu.etaxonomy.cdm.model.common.IIdentifiableEntity;
28 import eu.etaxonomy.cdm.persistence.hibernate.CdmDataChangeMap;
29 import eu.etaxonomy.taxeditor.model.AbstractUtility;
30 import eu.etaxonomy.taxeditor.model.ImageResources;
31 import eu.etaxonomy.taxeditor.preference.Resources;
32 import eu.etaxonomy.taxeditor.ui.dialog.selection.SelectionDialogFactory;
33 import eu.etaxonomy.taxeditor.ui.element.AbstractCdmFormElement;
34 import eu.etaxonomy.taxeditor.ui.element.CdmFormFactory;
35 import eu.etaxonomy.taxeditor.ui.element.CdmPropertyChangeEvent;
36 import eu.etaxonomy.taxeditor.ui.element.LayoutConstants;
37 import eu.etaxonomy.taxeditor.ui.element.SelectionArbitrator;
38 import eu.etaxonomy.taxeditor.ui.section.campanula.compatibility.ICdmFormElement;
39 import eu.etaxonomy.taxeditor.ui.section.campanula.compatibility.IEntitySelectionElement;
40 import eu.etaxonomy.taxeditor.ui.selection.EditFromSelectionWizard;
41
42 /**
43 * @author pplitzner
44 * @date 13.08.2013
45 *
46 */
47 public class EntitySelectionFieldController<T extends ICdmBase> extends AbstractCdmFormElement implements IEntitySelectionElement<T>{
48
49 /**
50 * Bitmask for configuring functionality of selection element
51 */
52 public static final int NOTHING = 0; // 000
53 public static final int EDITABLE = 1 << 0; // 001
54 public static final int DELETABLE = 1 << 1; // 010
55 public static final int SELECTABLE = 1 << 2; // 100
56 public static final int ALL = EDITABLE | DELETABLE | SELECTABLE; // 111
57
58 protected T entity;
59
60 //TODO also control "label" with this class?
61 // protected Label label;
62 protected Label text;
63 protected Button button_selection;
64
65 private SelectionArbitrator selectionArbitrator;
66
67 protected Button button_edit;
68
69 private final String labelString;
70
71 private Composite selectableComposite;
72
73 private Button button_remove;
74
75 private final boolean isEditable;
76
77 private final boolean isDeletable;
78
79 private final ConversationHolder conversation;
80 private Class<T> clazz;
81
82 /**
83 * <p>
84 * Constructor for AbstractSelectionElement.
85 * </p>
86 *
87 * @param formFactory
88 * a {@link eu.etaxonomy.taxeditor.ui.element.CdmFormFactory}
89 * object.
90 * @param conversation
91 * TODO
92 * @param parentElement
93 * a {@link eu.etaxonomy.taxeditor.ui.element.ICdmFormElement}
94 * object.
95 * @param labelString
96 * a {@link java.lang.String} object.
97 * @param entity
98 * a T object.
99 * @param isEditable
100 * a boolean.
101 * @param isSelectable
102 * a boolean.
103 * @param isDeletable
104 * a boolean.
105 * @param style
106 * a int.
107 * @param <T>
108 * a T object.
109 */
110 public EntitySelectionFieldController(EntitySelectionField entitySelectionField, CdmFormFactory formFactory, ConversationHolder conversation, ICdmFormElement parentElement, String labelString, T entity, int mode, int style) {
111 super(formFactory, parentElement);
112
113 setPropertyChangeListeners(formFactory.getPropertyChangeListeners());
114 formFactory.addPropertyChangeListener(this);
115
116 this.isEditable = (mode & EDITABLE) == EDITABLE;
117 this.isDeletable = (mode & DELETABLE) == DELETABLE;
118 boolean isSelectable = (mode & SELECTABLE) == SELECTABLE;
119
120 this.labelString = labelString;
121
122 this.conversation = conversation;
123
124 if (isSelectable && formFactory.getSelectionProvider() != null) {
125 selectionArbitrator = formFactory.createSelectionArbitrator(this);
126 }
127
128 createControls(entitySelectionField);
129
130 setEntity(entity);
131 }
132
133 public EntitySelectionFieldController(EntitySelectionField entitySelectionField, CdmFormFactory formFactory, ConversationHolder conversation, ICdmFormElement parentElement, Class<T> clazz, String labelString, T entity, int mode, int style) {
134 this(entitySelectionField, formFactory, conversation, parentElement, labelString, entity, mode, style);
135 this.clazz = clazz;
136 }
137
138 private void createControls(EntitySelectionField entitySelectionField) {
139
140 // label = formFactory.createLabel(getLayoutComposite(), labelString, SWT.NULL);
141 //
142 // addControl(label);
143
144 selectableComposite = entitySelectionField;
145
146 int columns = 2;
147 if (isEditable) {
148 columns += 1;
149 }
150 if (isDeletable) {
151 columns += 1;
152 }
153
154 selectableComposite.setLayout(LayoutConstants.LAYOUT(columns, false));
155 selectableComposite.setLayoutData(LayoutConstants.FILL_HORIZONTALLY());
156
157 addControl(selectableComposite);
158
159 text = entitySelectionField.getText();
160 addControl(text);
161
162 text.setLayoutData(LayoutConstants.FILL_HORIZONTALLY());
163 text.setBackground(AbstractUtility.getColor(Resources.COLOR_TEXT_DISABLED_BACKGROUND));
164
165 button_selection = entitySelectionField.getButton_selection();
166 button_selection.setImage(ImageResources.getImage(ImageResources.BROWSE_ICON));
167 button_selection.setToolTipText("Browse existing");
168
169 addControl(button_selection);
170 button_selection.addSelectionListener(this);
171
172 button_edit = entitySelectionField.getButton_edit();
173 if (isEditable) {
174 addControl(button_edit);
175 button_edit.addSelectionListener(new EditListener(this));
176 }
177 else{
178 button_edit.setVisible(false);
179 }
180
181 button_remove = entitySelectionField.getButton_remove();
182 if (isDeletable) {
183 addControl(button_remove);
184 button_remove.addSelectionListener(new DeleteListener(this));
185 }
186 else{
187 button_remove.setVisible(false);
188 }
189 }
190
191 @Override
192 public void widgetSelected(SelectionEvent e) {
193 T selection = SelectionDialogFactory.getSelectionFromDialog(clazz, getShell(), getConversationHolder(), getEntity());
194 setSelectionInternal(selection);
195 }
196
197 /**
198 * Return the selected object
199 *
200 * @return a T object.
201 */
202 public T getSelection() {
203 return entity;
204 }
205
206 /*
207 * (non-Javadoc)
208 *
209 * @see
210 * eu.etaxonomy.taxeditor.forms.IEnableableFormElement#setEnabled(boolean)
211 */
212 /** {@inheritDoc} */
213 @Override
214 public void setEnabled(boolean enabled) {
215 button_selection.setEnabled(enabled);
216 if (isEditable) {
217 button_edit.setEnabled(enabled && entity != null);
218 }
219 }
220
221 /**
222 * <p>
223 * setSelectionInternal
224 * </p>
225 *
226 * @param selection
227 * a T object.
228 */
229 protected void setSelectionInternal(T selection) {
230 if (selection != null && !selection.equals(this.entity)) {
231 setEntity(selection);
232 firePropertyChangeEvent(new CdmPropertyChangeEvent(this, null));
233 }
234 }
235
236 /**
237 * <p>
238 * Setter for the field <code>entity</code>.
239 * </p>
240 *
241 * @param selection
242 * a T object.
243 */
244 public void setEntity(T selection) {
245 this.entity = selection;
246 updateElement();
247 }
248
249 /**
250 * Updates this elements view
251 */
252 protected void updateElement() {
253 String title = CdmUtils.Nz(getTitle());
254 // we have to duplicate ampersands otherwise they are treated as
255 // mnenomic (see Label.setText() documentation)
256 title = title.replace("&", "&&");
257 text.setText(title); // title can be null
258 if (isEditable) {
259 button_edit.setEnabled(entity != null);
260 }
261 }
262
263 @Override
264 public void updateFromWizard() {
265 updateElement();
266 firePropertyChangeEvent(new CdmPropertyChangeEvent(this, null));
267 }
268
269 /**
270 * <p>
271 * getTitle
272 * </p>
273 *
274 * @return a {@link java.lang.String} object.
275 */
276 protected String getTitle() {
277 if (entity != null) {
278 if (entity instanceof IIdentifiableEntity) {
279 return ((IIdentifiableEntity) entity).getTitleCache();
280 } else if (entity instanceof Group) {
281 return ((Group) entity).getName();
282 } else if (entity instanceof GrantedAuthority) {
283 return ((GrantedAuthority) entity).getAuthority();
284 }
285 }
286 return "";
287 }
288
289 /** {@inheritDoc} */
290 @Override
291 public void setSelected(boolean selected) {
292 setBackground(selected ? SELECTED : getPersistentBackground());
293 }
294
295 /*
296 * (non-Javadoc)
297 *
298 * @see eu.etaxonomy.taxeditor.forms.IEntityElement#getEntity()
299 */
300 /**
301 * <p>
302 * Getter for the field <code>entity</code>.
303 * </p>
304 *
305 * @return a T object.
306 */
307 @Override
308 public T getEntity() {
309 return entity;
310 }
311
312 /*
313 * (non-Javadoc)
314 *
315 * @see eu.etaxonomy.taxeditor.forms.section.cdmdetail.ISelectableElement#
316 * getSelectionArbitrator()
317 */
318 /**
319 * <p>
320 * Getter for the field <code>selectionArbitrator</code>.
321 * </p>
322 *
323 * @return a {@link eu.etaxonomy.taxeditor.ui.element.SelectionArbitrator}
324 * object.
325 */
326 @Override
327 public SelectionArbitrator getSelectionArbitrator() {
328 return selectionArbitrator;
329 }
330
331 @Override
332 public Shell getShell() {
333 return getLayoutComposite().getShell();
334 }
335
336 /** {@inheritDoc} */
337 @Override
338 public void setIrrelevant(boolean irrelevant) {
339 String colorId = irrelevant ? Resources.COLOR_COMPOSITE_IRRELEVANT : Resources.COLOR_TEXT_DISABLED_BACKGROUND;
340
341 Color color = AbstractUtility.getColor(colorId);
342 text.setBackground(color);
343 }
344
345 private class DeleteListener extends SelectionAdapter {
346
347 private final EntitySelectionFieldController<T> selectionElement;
348
349 public DeleteListener(EntitySelectionFieldController<T> selectionElement) {
350 this.selectionElement = selectionElement;
351 }
352
353 @Override
354 public void widgetSelected(SelectionEvent e) {
355 setEntity(null);
356 firePropertyChangeEvent(new CdmPropertyChangeEvent(selectionElement, null));
357 }
358 }
359
360 private class EditListener extends SelectionAdapter {
361
362 private final IEntitySelectionElement<T> selectionElement;
363
364 public EditListener(IEntitySelectionElement<T> selectionElement) {
365 this.selectionElement = selectionElement;
366 }
367
368 /** {@inheritDoc} */
369 @Override
370 public void widgetSelected(SelectionEvent e) {
371 WizardDialog dialog = new WizardDialog(selectionElement.getShell(), new EditFromSelectionWizard(selectionElement));
372 if (dialog.open() == IStatus.OK) {
373 selectionElement.updateFromWizard();
374 }
375 }
376 }
377
378 // not used
379 /** {@inheritDoc} */
380 @Override
381 public void widgetDefaultSelected(SelectionEvent e) {
382 }
383
384 /**
385 * <p>
386 * getConversationHolder
387 * </p>
388 *
389 * @return a {@link eu.etaxonomy.cdm.api.conversation.ConversationHolder}
390 * object.
391 */
392 @Override
393 public ConversationHolder getConversationHolder() {
394 return conversation;
395 }
396
397 /** {@inheritDoc} */
398 @Override
399 public void setBackground(Color color) {
400 // label.setBackground(color);
401 }
402
403 /** {@inheritDoc} */
404 @Override
405 public void setLabel(String labelString) {
406 // if (label != null) {
407 // label.setText(labelString);
408 // }
409 }
410
411 /**
412 * <p>
413 * Getter for the field <code>label</code>.
414 * </p>
415 *
416 * @return a {@link java.lang.String} object.
417 */
418 @Override
419 public String getLabel() {
420 // if (label != null) {
421 // return label.getText();
422 // }
423 return null;
424 }
425
426 /** {@inheritDoc} */
427 @Override
428 public void update(CdmDataChangeMap changeEvents) {
429 }
430 }