source: other-projects/FileTransfer-WebSocketPair/testGXTWithGreenstone/src/org/greenstone/gatherer/cdm/DepositorMetadataManager.java@ 33053

Last change on this file since 33053 was 33053, checked in by ak19, 5 years ago

I still had some stuff of Nathan Kelly's (FileTransfer-WebSocketPair) sitting on my USB. Had already commited the Themes folder at the time, 2 years back. Not sure if he wanted this additional folder commited. But I didn't want to delete it and decided it will be better off on SVN. When we use his project, if we find we didn't need this test folder, we can remove it from svn then.

File size: 18.7 KB
Line 
1/**
2 *#########################################################################
3 *
4 * A component of the Gatherer application, part of the Greenstone digital
5 * library suite from the New Zealand Digital Library Project at the
6 * University of Waikato, New Zealand.
7 *
8 * Author: John Thompson, Greenstone Digital Library, University of Waikato
9 *
10 * Copyright (C) 1999 New Zealand Digital Library Project
11 *
12 * This program is free software; you can redistribute it and/or modify
13 * it under the terms of the GNU General Public License as published by
14 * the Free Software Foundation; either version 2 of the License, or
15 * (at your option) any later version.
16 *
17 * This program is distributed in the hope that it will be useful,
18 * but WITHOUT ANY WARRANTY; without even the implied warranty of
19 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
20 * GNU General Public License for more details.
21 *
22 * You should have received a copy of the GNU General Public License
23 * along with this program; if not, write to the Free Software
24 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
25 *########################################################################
26 */
27package org.greenstone.gatherer.cdm;
28
29import java.awt.BorderLayout;
30import java.awt.Color;
31import java.awt.Component;
32import java.awt.Dimension;
33import java.awt.event.ActionEvent;
34import java.awt.event.ActionListener;
35import java.io.File;
36import java.util.ArrayList;
37
38import javax.swing.BorderFactory;
39import javax.swing.BoxLayout;
40import javax.swing.JCheckBox;
41import javax.swing.JComboBox;
42import javax.swing.JComponent;
43import javax.swing.JOptionPane;
44import javax.swing.JPanel;
45import javax.swing.JScrollPane;
46
47import org.greenstone.gatherer.Configuration;
48import org.greenstone.gatherer.Dictionary;
49import org.greenstone.gatherer.Gatherer;
50import org.greenstone.gatherer.collection.CollectionManager;
51import org.greenstone.gatherer.gui.DesignPaneHeader;
52import org.greenstone.gatherer.gui.GComboBox;
53import org.greenstone.gatherer.metadata.MetadataElement;
54import org.greenstone.gatherer.metadata.MetadataSet;
55import org.greenstone.gatherer.metadata.MetadataSetManager;
56import org.greenstone.gatherer.util.Utility;
57
58/**
59 * This manager implements the "Depositor Metadata" section in GLI Format Panel, where
60 * users can customize which metadata elements will be used to describe an item when deposited in the Depositor.
61 *
62 * @author Anna Huang, Greenstone Digital Library, University of Waikato
63 * @version 1.0
64 */
65public class DepositorMetadataManager {
66 /** Display controls of the element */
67 static private Dimension LABEL_SIZE = new Dimension(150, 15);
68 static private Dimension ROW_SIZE = new Dimension(400, 20);
69 static private Dimension MAX_ROW_SIZE = new Dimension(1000, 30);
70
71 /** Available types, corresponds to the HTML input types */
72 static private String[] TYPEOPTIONS = new String[]{"text", "textarea"};
73 /** Default elements to be used in Depositor */
74 static private String DEFAULT_METADATA_ELEMENTS = "dc.Title, dc.Creator, dc.Description";
75 /** Definition attribute of a metadata element */
76 static private String DEFINITION = "definition";
77
78 /** Display controls */
79 private Control controls;
80 /** List of MetadataElementEntry objects, each represents a metadata element */
81 private ArrayList metadata_checklist_model = null;
82 /** Collection configuration file manager */
83 private CollectionMetaManager collmeta_manager = CollectionDesignManager.collectionmeta_manager;
84
85 public DepositorMetadataManager() {
86 }
87
88 /** Destructor. */
89 public void destroy() {
90 if (controls != null) {
91 controls.destroy();
92 controls = null;
93 }
94 if(metadata_checklist_model != null) {
95 metadata_checklist_model.clear();
96 metadata_checklist_model = null;
97 }
98 }
99
100 public Control getControls() {
101 if (controls == null) {
102 controls = new DepositorControl();
103 }
104 return controls;
105 }
106
107 /** Called when the detail mode has changed which in turn may cause several design elements to be available/hidden
108 * @param mode the new mode as an int
109 */
110 public void modeChanged(int mode) {
111 }
112
113 /**
114 * The implementation of this display control is similar to the <code>ArgumentConfiguration</code>,
115 * where each component in the central panel is another JPanel component consists of a checkbox and a drop down list.
116 */
117 private class DepositorControl
118 extends JPanel
119 implements Control {
120
121 private JPanel central_pane = null;
122
123 public DepositorControl() {
124 super();
125 this.setComponentOrientation(Dictionary.getOrientation());
126 JPanel header_panel = new DesignPaneHeader("CDM.GUI.DepositorMetadata", "depositormetadatasettings");
127
128 // load all possible metadata sets, and existing configuration
129 buildModel();
130
131 central_pane = new JPanel();
132 central_pane.setComponentOrientation(Dictionary.getOrientation());
133 central_pane.setBorder(BorderFactory.createEmptyBorder(5,5,5,5));
134 central_pane.setLayout(new BoxLayout(central_pane, BoxLayout.Y_AXIS));
135
136 // build the central pane, ie. create gui component for each metadata element
137 buildPane();
138
139 JPanel collection_checklist_pane = new JPanel();
140 collection_checklist_pane.setComponentOrientation(Dictionary.getOrientation());
141 collection_checklist_pane.setBorder(BorderFactory.createEmptyBorder(5,0,0,0));
142 collection_checklist_pane.setLayout(new BorderLayout());
143 collection_checklist_pane.add(new JScrollPane(central_pane), BorderLayout.CENTER);
144
145 setBorder(BorderFactory.createEmptyBorder(0,5,0,0));
146 setLayout(new BorderLayout());
147 add(header_panel, BorderLayout.NORTH);
148 add(collection_checklist_pane, BorderLayout.CENTER);
149 }
150
151 public void destroy() {
152 }
153
154 public void gainFocus() {
155 }
156
157 public void loseFocus() {
158 StringBuffer converted_javascript = new StringBuffer();
159
160 // get currently selected metadata elements and create the javascript associative array variable
161 if (metadata_checklist_model != null) {
162 int size = metadata_checklist_model.size();
163 for(int i = 0; i < size; i++) {
164 MetadataElementEntry entry = (MetadataElementEntry) metadata_checklist_model.get(i);
165
166 if (entry.isSelected()) {
167 StringBuffer element = new StringBuffer();
168 element.append("{\"name\":\"").append(entry.name).append("\",");
169 element.append("\"label\":\"").append(entry.label).append("\",");
170 element.append("\"tooltip\":\"").append(entry.name).append(": ").append(entry.tooltip).append("\",");
171 element.append("\"type\":\"").append(entry.getType()).append("\"}");
172 if(converted_javascript.length() != 0) {
173 converted_javascript.append(", ");
174 }
175 converted_javascript.append(element);
176 element = null;
177 }
178 }
179
180 // if none of the elements were selected, use the default setting
181 if (converted_javascript.length() == 0) {
182 System.err.println("Error: DepositorMetadataMananger should have at least one selected metadata element.");
183 }
184
185 // save to the configuration file
186 CollectionMeta depositor_metadata_meta = collmeta_manager.getMetadatum("depositormetadata", true);
187 depositor_metadata_meta.setValue(converted_javascript.toString());
188 }
189 }
190
191 private void buildModel()
192 {
193 metadata_checklist_model = new ArrayList();
194 String current_coll_name = CollectionManager.getLoadedCollectionName();
195
196 // get the elements that have already been used in depositor
197 // add the "depositormetadata" meta if not found in the configuration file
198 CollectionMeta depositor_metadata_meta = collmeta_manager.getMetadatum("depositormetadata", true);
199 String selected_metadata_javascript = depositor_metadata_meta.getValue(true);
200
201 // load all MDSets in the collection, ie. .mds files in the collection's metadata directory
202 String file_name = Gatherer.getCollectDirectoryPath() + File.separator + current_coll_name + File.separator + "metadata";
203 ArrayList metadata_sets = MetadataSetManager.listMetadataSets(new File(file_name));
204 if (metadata_sets != null) {
205 // unload the ex mds
206 for (int i = 0, j = metadata_sets.size(); i < j; i++) {
207 if (((MetadataSet) metadata_sets.get(i)).getNamespace().equals("ex")) {
208 metadata_sets.remove(i);
209 break;
210 }
211 }
212 }
213
214 if (metadata_sets == null) {
215 metadata_sets = new ArrayList();
216 }
217 if (metadata_sets.size() == 0) {
218 // load dublin core
219 file_name = org.greenstone.gatherer.gems.MetadataSetManager.getGLIMetadataDirectoryPath();
220 file_name += "dublin.mds";
221 File dublin_mds_file = new File(file_name);
222 if (dublin_mds_file.exists()) {
223 MetadataSetManager.loadMetadataSet(dublin_mds_file);
224 MetadataSet dc = MetadataSetManager.getMetadataSet("dc");
225 metadata_sets.add(dc);
226 }
227 }
228 // if we are still empty :-(
229 if (metadata_sets.size() == 0) {
230 System.err.println("Error: DepositorMetadataMananger can't find any valid metadata set files.");
231 return;
232 }
233
234 // load all the metadata elements
235 for (int i = 0, j = metadata_sets.size(); i < j; i++) {
236 MetadataSet metadata_set = (MetadataSet) metadata_sets.get(i);
237 ArrayList elements = metadata_set.getMetadataSetElements();
238
239 for (int k = 0; elements != null && k < elements.size(); k++) {
240 MetadataElement element = (MetadataElement) elements.get(k);
241 // all names are language independent at the moment.
242 MetadataElementEntry entry = new MetadataElementEntry (element.getFullName(), element.getName(), false);
243 entry.setToolTip(element.getAttribute(DEFINITION, "en"));
244 metadata_checklist_model.add(entry);
245 }
246 }
247
248 if (!selected_metadata_javascript.equals("")) {
249 for (int i = 0, j = metadata_checklist_model.size(); i < j; i++) {
250 MetadataElementEntry entry = (MetadataElementEntry) metadata_checklist_model.get(i);
251
252 String temp = "\"name\":\"" + entry.name + "\"";
253 if (selected_metadata_javascript.indexOf(temp) != -1) {
254 entry.setSelected(true);
255 entry.type = getValueFromJSAssociatedArray(selected_metadata_javascript, entry.name, "type");
256 }
257 temp = null;
258 }
259 } else {
260 // use default elements
261 for (int i = 0, j = metadata_checklist_model.size(); i < j; i++) {
262 MetadataElementEntry entry = (MetadataElementEntry) metadata_checklist_model.get(i);
263 if (DEFAULT_METADATA_ELEMENTS.indexOf(entry.name) != -1) {
264 entry.setSelected(true);
265 entry.type = TYPEOPTIONS[0];
266 }
267 }
268 }
269 }
270
271 private void buildPane() {
272 // use different background color for two adjacent metadata sets
273 String current_namespace = null;
274 String current_bgcolor_name = null;
275 for (int i = 0, j = metadata_checklist_model.size(); i < j; i++) {
276 MetadataElementEntry entry = (MetadataElementEntry) metadata_checklist_model.get(i);
277
278 if (current_namespace == null) {
279 current_namespace = entry.namespace;
280 current_bgcolor_name = "coloring.collection_tree_background";
281 } else {
282 if (!entry.namespace.equals(current_namespace)) {
283 current_namespace = entry.namespace;
284 current_bgcolor_name = (current_bgcolor_name == "coloring.collection_tree_background") ? "coloring.collection_heading_background" : "coloring.collection_tree_background";
285 }
286 }
287
288 if (entry.getGUIControl() == null) {
289 MetadataElementControl element_control = entry.initGUIControl(current_bgcolor_name);
290 central_pane.add(element_control, BorderLayout.NORTH);
291 }
292 }
293
294 }
295
296 /**
297 * Retrieve the value for the specified element in the given javascript associative array expression
298 *
299 * @param text
300 * @param identifier
301 * @param elem_name
302 * @return
303 */
304 private String getValueFromJSAssociatedArray(String text, String identifier, String elem_name) {
305 int p = text.indexOf(elem_name, text.indexOf(identifier));
306 if (p == -1) {
307 return null;
308 }
309 p = text.indexOf("\":\"", p);
310 if (p == -1) {
311 return null;
312 }
313 p += 3;
314
315 return text.substring(p, text.indexOf("\"", p));
316 }
317 }
318
319 private class MetadataElementControl extends JPanel {
320
321 private JCheckBox enabled = null;
322 private JComponent value_control = null;
323
324 public MetadataElementControl (MetadataElementEntry entry, String background_color_name) {
325
326 this.setComponentOrientation(Dictionary.getOrientation());
327 String tip = "<html>" + entry.tooltip + "</html>";
328 tip = Utility.formatHTMLWidth(tip, 80);
329
330 setBackground(Configuration.getColor(background_color_name, false));
331 setBorder(BorderFactory.createEmptyBorder(0,0,0,0));
332 setLayout(new BorderLayout());
333 setPreferredSize(ROW_SIZE);
334 setMaximumSize(MAX_ROW_SIZE);
335
336 // the checkbox component
337 enabled = new JCheckBox(entry.name);
338 enabled.setComponentOrientation(Dictionary.getOrientation());
339 enabled.setSelected(entry.selected);
340 enabled.setOpaque(false);
341 enabled.setPreferredSize(LABEL_SIZE);
342 enabled.setToolTipText(entry.tooltip);
343 add(enabled, BorderLayout.LINE_START);
344
345 // the drop down list component
346 ArrayList option_list = new ArrayList();
347 for (int i = 0; i < TYPEOPTIONS.length; i++) {
348 option_list.add(TYPEOPTIONS[i]);
349 }
350 value_control = new GComboBox(option_list.toArray(), false, false);
351 value_control.setComponentOrientation(Dictionary.getOrientation());
352 selectValue((JComboBox)value_control, entry.type);
353 value_control.setOpaque(true);
354 if (entry.selected) {
355 value_control.setBackground(Color.white);
356 value_control.setEnabled(true);
357 } else {
358 value_control.setBackground(Color.lightGray);
359 value_control.setEnabled(false);
360 value_control.setVisible(false);
361 }
362 add(value_control, BorderLayout.CENTER);
363
364 enabled.addActionListener(new EnabledListener(value_control));
365 }
366
367 private boolean selectValue(JComboBox combobox, String target) {
368 if (target == null) {
369 combobox.setSelectedIndex(0);
370 return false;
371 }
372
373 for (int i = 0; i < combobox.getItemCount(); i++) {
374 if (combobox.getItemAt(i).toString().equals(target)) {
375 combobox.setSelectedIndex(i);
376 return true;
377 }
378 }
379 return false;
380 }
381
382 private class EnabledListener
383 implements ActionListener {
384 private JComponent target = null;
385
386 public EnabledListener(JComponent target) {
387 this.target = target;
388 }
389
390 public void actionPerformed(ActionEvent event) {
391 JCheckBox source = (JCheckBox)event.getSource();
392
393 // check at least one of the elements should be ticked
394 checkTickedElements(source);
395
396 // update the status of the drop-down list component associated with the current checkbox
397 if (this.target == null) {
398 return;
399 }
400
401 if(source.isSelected()) {
402 target.setBackground(Color.white);
403 target.setEnabled(true);
404 target.setVisible(true);
405 }
406 else {
407 target.setBackground(Color.lightGray);
408 target.setEnabled(false);
409 target.setVisible(false);
410 }
411 }
412
413 private void checkTickedElements(JCheckBox source) {
414 if (source.isSelected()) {
415 return;
416 }
417
418 boolean b = false;
419 for (int i = 0, j = metadata_checklist_model.size(); i < j; i++) {
420 if (((MetadataElementEntry) metadata_checklist_model.get(i)).gui_object.enabled.isSelected()) {
421 b = true;
422 break;
423 }
424 }
425
426 // there must be at least one element selected in the list
427 if (b == false) {
428 Object[] options = {Dictionary.get("General.OK")};
429 JOptionPane.showOptionDialog(Gatherer.g_man, Dictionary.get("CDM.DepositorMetadataManager.Warning"), Dictionary.get("General.Warning"), JOptionPane.DEFAULT_OPTION, JOptionPane.WARNING_MESSAGE, null, options, options[0]);
430
431 source.setSelected(true);
432 }
433 }
434 }
435
436 }
437
438 private class MetadataElementEntry implements Comparable {
439 /** namespace, used to distinguish different metadata sets and use different colors when displaying */
440 String namespace = null;
441 /** identifier, with namespace */
442 String name = null;
443 /** language independent label, without namespace, used for display in the depositor web page, eg. Title */
444 String label = null;
445 /** type of the element: text or textarea */
446 String type = null;
447 /** description of the element, used in web page */
448 String tooltip = null;
449 /** whether current element is selected or not */
450 boolean selected ;
451 /** GUI component object associated with this element */
452 MetadataElementControl gui_object = null;
453
454 /**
455 * Constructor
456 * @param name Language independent identifier of the element with namespace, eg. dc.Title
457 * @param label Language independent label of the element, without namespace, eg. Title
458 * @param selected Whether the current element has been selected as depositor metadata element
459 */
460 public MetadataElementEntry(String name, String label, boolean selected) {
461 this.name = name;
462 this.label = label;
463 this.selected = selected;
464
465 if (name.indexOf(".") != -1) {
466 namespace = name.substring(0, name.indexOf("."));
467 }
468 }
469
470 /**
471 * Initiate the <code>MetadataElementControl<code> GUI component object associated with this element, with the specified background color
472 * @param background_color_name System configured color name for the background, eg. "coloring.collection_heading_background", or "coloring.collection_tree_background"
473 * @return the initialized component object
474 */
475 public MetadataElementControl initGUIControl (String background_color_name) {
476 gui_object = new MetadataElementControl(this, background_color_name);
477 return gui_object;
478 }
479
480 /**
481 * Get the associated GUI component
482 * @return
483 */
484 public MetadataElementControl getGUIControl() {
485 return gui_object;
486 }
487
488 /**
489 * Set selected
490 * @param b
491 */
492 public void setSelected(boolean b) {
493 this.selected = b;
494 }
495
496 public boolean isSelected() {
497 return gui_object.enabled.isSelected();
498 }
499
500 /**
501 * Get the selected type for the element
502 * @return type
503 */
504 public String getType() {
505 return ((JComboBox) gui_object.value_control).getSelectedItem().toString();
506 }
507
508 public void setToolTip (String tip) {
509 if (tip == null) {
510 tooltip = "";
511 return;
512 }
513 this.tooltip = tip;
514 }
515
516 public int compareTo(Object obj) {
517 return compareTo((MetadataElementEntry) obj);
518 }
519
520 public int compareTo(MetadataElementEntry obj) {
521 return this.name.compareTo(obj.name);
522 }
523
524 }
525
526}
Note: See TracBrowser for help on using the repository browser.