Statistics
| Revision:

svn-gvsig-desktop / trunk / org.gvsig.desktop / org.gvsig.desktop.plugin / org.gvsig.app.document.table.app / org.gvsig.app.document.table.app.mainplugin / src / main / java / org / gvsig / app / project / documents / table / TableManager.java @ 46737

History | View | Annotate | Download (21.7 KB)

1
/**
2
 * gvSIG. Desktop Geographic Information System.
3
 *
4
 * Copyright (C) 2007-2013 gvSIG Association.
5
 *
6
 * This program is free software; you can redistribute it and/or
7
 * modify it under the terms of the GNU General Public License
8
 * as published by the Free Software Foundation; either version 3
9
 * of the License, or (at your option) any later version.
10
 *
11
 * This program is distributed in the hope that it will be useful,
12
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14
 * GNU General Public License for more details.
15
 *
16
 * You should have received a copy of the GNU General Public License
17
 * along with this program; if not, write to the Free Software
18
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
19
 * MA  02110-1301, USA.
20
 *
21
 * For any additional information, do not hesitate to contact us
22
 * at info AT gvsig.com, or visit our website www.gvsig.com.
23
 */
24

    
25
package org.gvsig.app.project.documents.table;
26

    
27
import java.awt.Dimension;
28
import java.util.Collections;
29
import java.util.Iterator;
30
import java.util.List;
31
import java.util.logging.Level;
32
import java.util.logging.Logger;
33

    
34
import javax.swing.ImageIcon;
35
import javax.swing.JOptionPane;
36

    
37
import org.gvsig.andami.IconThemeHelper;
38
import org.gvsig.andami.PluginServices;
39
import org.gvsig.andami.messages.NotificationManager;
40
import org.gvsig.andami.ui.mdiManager.IWindow;
41
import org.gvsig.app.ApplicationLocator;
42
import org.gvsig.app.addlayer.AddLayerDialog;
43
import org.gvsig.app.gui.WizardPanel;
44
import org.gvsig.app.project.Project;
45
import org.gvsig.app.project.ProjectManager;
46
import org.gvsig.app.project.documents.AbstractDocument;
47
import org.gvsig.app.project.documents.AbstractDocumentManager;
48
import org.gvsig.app.project.documents.Document;
49
import org.gvsig.app.project.documents.actions.CopyDocumentAction;
50
import org.gvsig.app.project.documents.actions.CutDocumentAction;
51
import org.gvsig.app.project.documents.actions.PasteDocumentAction;
52
import org.gvsig.app.project.documents.gui.IDocumentWindow;
53
import org.gvsig.app.project.documents.gui.WindowLayout;
54
import org.gvsig.app.project.documents.table.TableDocument.TableLink;
55
import org.gvsig.app.project.documents.table.gui.FeatureTableDocumentPanel;
56
import org.gvsig.app.project.documents.table.gui.TableProperties;
57
import org.gvsig.fmap.dal.AbstractStoresRepository;
58
import org.gvsig.fmap.dal.DALLocator;
59
import org.gvsig.fmap.dal.DataManager;
60
import org.gvsig.fmap.dal.DataStore;
61
import org.gvsig.fmap.dal.DataStoreParameters;
62
import org.gvsig.fmap.dal.exception.DataException;
63
import org.gvsig.fmap.dal.exception.InitializeException;
64
import org.gvsig.fmap.dal.exception.ProviderNotRegisteredException;
65
import org.gvsig.fmap.dal.exception.ValidateDataParametersException;
66
import org.gvsig.fmap.dal.feature.FeatureQuery;
67
import org.gvsig.fmap.dal.feature.FeatureQueryOrder;
68
import org.gvsig.fmap.dal.feature.FeatureStore;
69
import org.gvsig.fmap.dal.feature.FeatureType;
70
import org.gvsig.fmap.dal.serverexplorer.filesystem.swing.FilesystemExplorerWizardPanel;
71
import org.gvsig.fmap.mapcontext.layers.vectorial.FLyrVect;
72
import org.gvsig.fmap.mapcontext.layers.vectorial.VectorLayer;
73
import org.gvsig.tools.ToolsLocator;
74
import org.gvsig.tools.dispose.DisposeUtils;
75
import org.gvsig.tools.dynobject.DynObjectManager;
76
import org.gvsig.tools.dynobject.DynStruct;
77
import org.gvsig.tools.evaluator.Evaluator;
78
import org.gvsig.tools.i18n.I18nManager;
79
import org.gvsig.tools.persistence.PersistenceManager;
80
import org.gvsig.tools.swing.api.ToolsSwingLocator;
81
import org.gvsig.tools.swing.api.ToolsSwingUtils;
82
import org.gvsig.tools.swing.api.threadsafedialogs.ThreadSafeDialogsManager;
83
import org.gvsig.tools.util.Invocable;
84
import org.gvsig.tools.util.MappedIterator;
85
import org.gvsig.tools.util.UnmodifiableBasicSet;
86
import org.slf4j.LoggerFactory;
87

    
88
/**
89
 * Factory of Table.
90
 * 
91
 * @author gvSIG Tem
92
 * 
93
 */
94
@SuppressWarnings("UseSpecificCatch")
95
public class TableManager extends AbstractDocumentManager {
96
    
97
    final static private org.slf4j.Logger LOGGER = LoggerFactory.getLogger(TableDocument.class);
98

    
99
    private static class TableDocumentStoresRepository extends AbstractStoresRepository {
100

    
101
        public TableDocumentStoresRepository(String name, String label) {
102
            super(name, label);
103
        }
104

    
105
        @Override
106
        protected DataStoreParameters getMyParameters(String name) {
107
            Project project = ProjectManager.getInstance().getCurrentProject();
108
            TableDocument tableDoc = (TableDocument) project.getDocument(name, TYPENAME);
109
            if( tableDoc==null || tableDoc.getFeatureStore()==null) {
110
                return null;
111
            }
112
            return tableDoc.getFeatureStore().getParameters();
113
        }
114

    
115
        @Override
116
        protected FeatureType getMyFeatureType(String name) {
117
            Project project = ProjectManager.getInstance().getCurrentProject();
118
            TableDocument tableDoc = (TableDocument) project.getDocument(name, TYPENAME);
119
            if( tableDoc==null || tableDoc.getFeatureStore()==null) {
120
                return null;
121
            }
122
            return tableDoc.getFeatureStore().getDefaultFeatureTypeQuietly();
123
        }
124
        
125
        @Override
126
        protected boolean isEmptyMyRepository() {
127
            Project project = ProjectManager.getInstance().getCurrentProject();
128
            return project.getDocuments(TableManager.TYPENAME).isEmpty();
129
        }
130

    
131
        @Override
132
        protected int getMySize() {
133
            Project project = ProjectManager.getInstance().getCurrentProject();
134
            int sz = project.getDocuments(TableManager.TYPENAME).size();
135
            return sz;
136
        }
137

    
138
        @Override
139
        protected UnmodifiableBasicSet<String> getMyKeySet() {
140
            Project project = ProjectManager.getInstance().getCurrentProject();
141
            final List<Document> docs = project.getDocuments(TableManager.TYPENAME);
142
            if( docs==null ) {
143
                return UnmodifiableBasicSet.EMPTY_UNMODIFIABLEBASICSET;
144
            }
145
            UnmodifiableBasicSet<String> x = new UnmodifiableBasicSet<String>() {
146
                @Override
147
                public boolean isEmpty() {
148
                    return docs.isEmpty();
149
                }
150

    
151
                @Override
152
                public int size() {
153
                    return docs.size();
154
                }
155

    
156
                @Override
157
                public Iterator<String> iterator() {
158
                    return new MappedIterator<>(docs.iterator(), (Document t) -> {
159
                        if( t==null ) {
160
                            return null;
161
                        }
162
                        return ((TableDocument)t).getName();
163
                    });
164
                }
165
            };
166
            return x;
167
        }
168

    
169
        
170
        @Override
171
        public Iterator<DataStoreParameters> iterator() {
172
            Project project = ProjectManager.getInstance().getCurrentProject();
173
            List<Document> docs = project.getDocuments(TableManager.TYPENAME);
174
            if( docs==null ) {
175
                return Collections.EMPTY_LIST.iterator();
176
            }
177
            return new MappedIterator<>(docs.iterator(), (Document t) -> {
178
                if( t==null || ((TableDocument)t).getFeatureStore()==null ) {
179
                    return null;
180
                }
181
                return ((TableDocument)t).getFeatureStore().getParameters();
182
            });
183
        }
184

    
185
        @Override
186
        public void add(String name, DataStoreParameters parameters) {
187
            Project project = ProjectManager.getInstance().getCurrentProject();
188
            TableDocument doc = (TableDocument) ProjectManager.getInstance().createDocument(TYPENAME);
189
            doc.setName(name);
190
            //FIXME:
191
            DataManager dataManager = DALLocator.getDataManager();
192
            FeatureStore store;
193
            try {
194
                store = (FeatureStore) dataManager.openStore(
195
                        parameters.getProviderName(),
196
                        parameters
197
                );
198
                doc.setStore(store);
199
                project.addDocument(doc);
200
            } catch (InitializeException | ProviderNotRegisteredException | ValidateDataParametersException ex) {
201
                LOGGER.warn("Can't add table to project", ex);
202
            }
203

    
204
        }
205

    
206
        @Override
207
        public void add(String name, FeatureStore store) {
208
            Project project = ProjectManager.getInstance().getCurrentProject();
209
            TableDocument doc = (TableDocument) ProjectManager.getInstance().createDocument(TYPENAME);
210
            doc.setName(name);
211
            doc.setStore(store);
212
            project.addDocument(doc);
213
        }
214

    
215
        @Override
216
        public DataStore getStore(String name) {
217
            Project project = ProjectManager.getInstance().getCurrentProject();
218
            TableDocument tableDoc = (TableDocument) project.getDocument(name, TYPENAME);
219
            if( tableDoc==null || tableDoc.getFeatureStore()==null) {
220
                return null;
221
            }
222
            FeatureStore store = tableDoc.getFeatureStore();
223
            DisposeUtils.bind(store);
224
            return store;
225
        }
226
        
227
    }
228
    
229
    public static final String PERSISTENCE_TABLE_DOCUMENT_DEFINITION_NAME =
230
        "TableDocument";
231
    public static final String PERSISTENCE_TABLELINK_DEFINITION_NAME =
232
        "TableLink";
233

    
234
    public static String TYPENAME = "project.document.table";
235

    
236
    private DynStruct persistenceDefinition = null;
237

    
238
    @Override
239
    public ImageIcon getIcon() {
240
            return IconThemeHelper.getImageIcon("document-table-icon");
241
    }
242

    
243
    @Override
244
    public ImageIcon getIconSelected() {
245
        return IconThemeHelper.getImageIcon("document-table-icon-sel");
246
    }
247

    
248
    @Override
249
    public String getTitle() {
250
        return PluginServices.getText(this, "Tabla");
251
    }
252

    
253
    @Override
254
    public String getTypeName() {
255
        return TYPENAME;
256
    }
257

    
258
    @Override
259
    public int getPriority() {
260
        return 1;
261
    }
262

    
263
    @Override
264
    public Iterator<? extends Document> createDocumentsByUser() {
265
        return this.createDocumentsByUser(null);
266
    }
267
    
268
    @Override
269
    public Iterator<? extends Document> createDocumentsByUser(Invocable whenDocumentsLoaded) {
270
        AddLayerDialog fopen = null;
271
        try {
272
            fopen =
273
                new AddLayerDialog(PluginServices.getText(this, "Nueva_tabla"));
274
            List<WizardPanel> wizards =
275
                ApplicationLocator.getManager().getWizardPanels();
276

    
277
            Dimension preferredSize = fopen.getPreferredSize();
278
            WizardPanel panel;
279
            Iterator<WizardPanel> iter = wizards.iterator();
280
            while (iter.hasNext()) {
281
                panel = iter.next();
282
                panel.initWizard();
283
                Dimension dim = panel.getPreferredSize();
284
                if( dim.height>preferredSize.height ) {
285
                    preferredSize.height = dim.height;
286
                }
287
                if( dim.width>preferredSize.width ) {
288
                    preferredSize.width = dim.width;
289
                }
290
                
291
                fopen.addWizardTab(panel.getTabName(), panel);
292
            }
293
          
294
            preferredSize.height += ToolsSwingUtils.rows2px(4);
295
            preferredSize.width += ToolsSwingUtils.cols2px(2);
296

    
297
            fopen.setPreferredSize(preferredSize);
298

    
299
            ToolsSwingUtils.ensureRowsCols(fopen, -1, -1, 30, 100);
300
            
301
            PluginServices.getMDIManager().addWindow(fopen);
302
            if (fopen.isAccepted()) {
303
                WizardPanel selectedPanel = (WizardPanel) fopen.getSelectedTab();
304
                if( whenDocumentsLoaded==null ) {
305
                    List<TableDocument> docs = (List) selectedPanel.executeWizard();
306
                    this.checkDocuments(docs);
307
                    return docs.iterator();
308
                }
309
                Thread task = new Thread(() -> {
310
                    List<TableDocument> docs = (List) selectedPanel.executeWizard();
311
                    checkDocuments(docs);
312
                    whenDocumentsLoaded.call(docs.iterator());
313
                }, "DocumentTableLoader");
314
                task.start();
315
                return Collections.EMPTY_LIST.iterator();
316
            }
317
        } catch (Exception e) {
318
            NotificationManager.addError(e);
319
        } finally {
320
            if (fopen != null) {
321
                fopen.dispose();
322
                fopen = null;
323
            }
324
        }
325
        return null;
326
    }
327
    
328
    private void checkDocuments(List<TableDocument> docs) {
329
        if( docs==null ) {
330
            return;
331
        }
332
        for (TableDocument doc : docs) {
333
            try {
334
                FeatureStore store = ((TableDocument)doc).getDataStore();
335
                FeatureType type = store.getDefaultFeatureType();
336
                if( ! type.supportReferences() ) {
337
                    I18nManager i18n = ToolsLocator.getI18nManager();
338
                    ThreadSafeDialogsManager dialogs = ToolsSwingLocator.getThreadSafeDialogsManager();
339
                    dialogs.messageDialog(
340
                            "\""+ doc.getName() + "\"\n"+
341
                            i18n.getTranslation("_The_table_has_no_primary_key_or_OID") +"\n" +
342
                                   i18n.getTranslation("_Many_features_selection_deletion_modification_will_not_be_available_as_they_require_it_for_proper_operation"),
343
                            null, 
344
                            i18n.getTranslation("_Warning"),
345
                            JOptionPane.WARNING_MESSAGE, 
346
                            "TableDoNotSupportReferences"
347
                   );
348
                }
349
            } catch (Exception ex) {
350

    
351
            }
352
        }        
353
    }
354

    
355
    @Override
356
    public AbstractDocument createDocumentByUser() {
357
        return (AbstractDocument) createDocumentsByUser().next();
358
    }
359
    
360
    /**
361
     * Registers in the points of extension the Factory with alias.
362
     * 
363
     */
364
    public static void register() {
365
        I18nManager i18n = ToolsLocator.getI18nManager();
366
        
367
        TableManager factory = new TableManager();
368
        // A?adimos nuestra extension para el tratamiento de la apertura de
369
        // ficheros
370
        // dentro de gvSIG
371
        ToolsLocator.getExtensionPointManager().add("FileTableOpenDialog", "")
372
            .append("FileOpenTable", "", FilesystemExplorerWizardPanel.class);
373

    
374
                IconThemeHelper.registerIcon("document", "document-table-icon", TableManager.class);
375
        IconThemeHelper.registerIcon("document", "document-table-icon-sel", TableManager.class);
376
        IconThemeHelper.registerIcon("document", "document-table-icon-small", TableManager.class);
377

    
378
        PersistenceManager manager = ToolsLocator.getPersistenceManager();
379
        manager.registerFactory(factory);
380

    
381
        if (factory.persistenceDefinition == null) {
382
            DynObjectManager dynman = ToolsLocator.getDynObjectManager();
383
            factory.persistenceDefinition =
384
                dynman.createDynClass(PersistenceManager.PERSISTENCE_NAMESPACE,
385
                    PERSISTENCE_TABLE_DOCUMENT_DEFINITION_NAME,
386
                    "Table document Persistence definition");
387
            factory.persistenceDefinition.extend(manager
388
                .getDefinition(AbstractDocument.PERSISTENCE_DEFINITION_NAME));
389

    
390
            factory.persistenceDefinition.addDynFieldObject("store")
391
                .setClassOfValue(FeatureStore.class).setMandatory(true);
392
            factory.persistenceDefinition.addDynFieldString("featureTypeId")
393
                .setMandatory(false);
394
            factory.persistenceDefinition.addDynFieldArray("attributeNames")
395
                .setClassOfItems(String.class).setMandatory(false);
396
            factory.persistenceDefinition.addDynFieldObject("associatedLayer")
397
                .setClassOfValue(FLyrVect.class).setMandatory(false);
398
            factory.persistenceDefinition.addDynFieldObject("query")
399
                .setClassOfValue(FeatureQuery.class).setMandatory(false);
400
            factory.persistenceDefinition.addDynFieldObject("baseFilter")
401
                .setClassOfValue(Evaluator.class).setMandatory(false);
402
            factory.persistenceDefinition.addDynFieldObject("baseOrder")
403
                .setClassOfValue(FeatureQueryOrder.class).setMandatory(false);
404
            factory.persistenceDefinition.addDynFieldList("linkTable")
405
                .setClassOfItems(TableLink.class).setMandatory(false);          
406
            factory.persistenceDefinition.addDynFieldMap("patterns")
407
                .setClassOfItems(String.class).setMandatory(false);          
408
        }
409
        
410
        
411
        //Register also the TableLink
412
        if (manager.getDefinition(PERSISTENCE_TABLELINK_DEFINITION_NAME) == null){
413
            DynStruct tableLinkDefinition =
414
                manager.addDefinition(TableLink.class,
415
                    PERSISTENCE_TABLELINK_DEFINITION_NAME,
416
                    "TableLink Persistence definition", null, null);                 
417
            
418
            tableLinkDefinition.addDynFieldObject("source")
419
                .setClassOfValue(TableDocument.class).setMandatory(true);
420
            tableLinkDefinition.addDynFieldObject("target")
421
                .setClassOfValue(TableDocument.class).setMandatory(true);
422
            tableLinkDefinition.addDynFieldString("fieldSource").setMandatory(true);
423
            tableLinkDefinition.addDynFieldString("fieldTarget").setMandatory(true);
424
            tableLinkDefinition.addDynFieldBoolean("enabled").setMandatory(true);
425
        }  
426
    
427
        ProjectManager.getInstance().registerDocumentFactory(factory);
428
        
429
        ProjectManager.getInstance().registerDocumentAction(TYPENAME,new CopyDocumentAction());
430
        ProjectManager.getInstance().registerDocumentAction(TYPENAME,new CutDocumentAction());
431
        ProjectManager.getInstance().registerDocumentAction(TYPENAME,new PasteDocumentAction());
432

    
433
        DataManager dataManager = DALLocator.getDataManager();
434
        dataManager.getStoresRepository().addRepository(
435
                new TableDocumentStoresRepository(
436
                    "PROJECT_TABLES",
437
                    i18n.getTranslation("_Project_tables")
438
            )
439
        );
440
    }
441

    
442
    /**
443
     * Create a new table document.
444
     * 
445
     * @return TableDocument.
446
     */
447
    @Override
448
    public AbstractDocument createDocument() {
449
        AbstractDocument doc = new TableDocument(this);
450
        if( this.notifyObservers(NOTIFY_AFTER_CREATEDOCUMENT,doc).isCanceled() ) {
451
            return null;
452
        }
453
            return doc;        
454
    }
455

    
456
    @Override
457
    public Class<? extends IDocumentWindow> getMainWindowClass() {
458
        return FeatureTableDocumentPanel.class;
459
    }
460

    
461
    @Override
462
    public IWindow getMainWindow(Document doc, WindowLayout layout) {
463
       IDocumentWindow win = (IDocumentWindow) super.getMainWindow(doc, layout);
464
        if (win == null) {
465
            try {
466
                win = (IDocumentWindow) this.createDocumentWindow(doc);
467
            } catch(Throwable t){
468
            }
469
            if(win == null){
470
                try {
471
                    ((TableDocument)doc).getFeatureStore().refresh();
472
                } catch (DataException ex) {
473
                    throw new RuntimeException(ex);
474
                }
475
                win = (IDocumentWindow) this.createDocumentWindow(doc);
476
            }
477
            if (layout != null && win != null) {
478
                win.setWindowLayout(layout);
479
            }
480
        }
481
        if( this.notifyObservers(NOTIFY_AFTER_GETMAINWINDOW,win).isCanceled() ) {
482
            return null;
483
        }
484
        return win;
485
    }
486

    
487
    @Override
488
    public IWindow getPropertiesWindow(Document doc) {
489
        IWindow win = super.getPropertiesWindow(doc);
490
        if( win == null ) {
491
            win = new TableProperties((TableDocument) doc);
492
        }
493
        if( this.notifyObservers(NOTIFY_AFTER_GETPROPERTIESWINDOW,win).isCanceled() ) {
494
            return null;
495
        }
496
        return win;        
497
    }
498

    
499
    @Override
500
    protected Class<? extends Document> getDocumentClass() {
501
        return TableDocument.class;
502
    }
503

    
504
    @Override
505
    public DynStruct getDefinition(String className) {
506

    
507
        if (this.persistenceDefinition.getName().equalsIgnoreCase(className)) {
508
            return this.persistenceDefinition;
509
        }
510
        if (this.persistenceDefinition.getFullName()
511
            .equalsIgnoreCase(className)) {
512
            return this.persistenceDefinition;
513
        }
514
        if (this.getDocumentClass().getName().equals(className)) {
515
            return this.persistenceDefinition;
516
        }
517
        return null;
518
    }
519

    
520
    @Override
521
    public boolean manages(Object object) {
522
        return object instanceof TableDocument;
523
    }
524

    
525
    public TableDocument getTableDocument(VectorLayer layer) {
526
        if (layer == null) {
527
            return null;
528
        }
529
        List<Document> tableDocs =
530
            getProject().getDocuments(TableManager.TYPENAME);
531
        for (Document document : tableDocs) {
532
            if (layer == ((TableDocument) document).getAssociatedLayer()) {
533
                return (TableDocument) document;
534
            }
535
        }
536
        return null;
537
    }
538

    
539
    public void removeTableDocument(VectorLayer layer) {
540
        TableDocument doc = getTableDocument(layer);
541
        // Only remove it if it exists
542
        if (doc != null) {
543
            PluginServices.getMDIManager().closeSingletonWindow(doc);
544
            getProject().remove(doc);
545
        }
546
    }
547

    
548
    private Project getProject() {
549
        return ProjectManager.getInstance().getCurrentProject();
550
    }
551
}