Statistics
| Revision:

svn-gvsig-desktop / trunk / org.gvsig.desktop / org.gvsig.desktop.compat.cdc / org.gvsig.fmap.dal / org.gvsig.fmap.dal.impl / src / main / java / org / gvsig / fmap / dal / feature / impl / FeatureTypeManager.java @ 41925

History | View | Annotate | Download (12.5 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
package org.gvsig.fmap.dal.feature.impl;
25

    
26
import java.lang.ref.WeakReference;
27
import java.util.ArrayList;
28
import java.util.Arrays;
29
import java.util.HashMap;
30
import java.util.Iterator;
31
import java.util.List;
32

    
33
import org.gvsig.fmap.dal.exception.DataException;
34
import org.gvsig.fmap.dal.feature.AbstractFeatureStoreTransform;
35
import org.gvsig.fmap.dal.feature.EditableFeature;
36
import org.gvsig.fmap.dal.feature.EditableFeatureAttributeDescriptor;
37
import org.gvsig.fmap.dal.feature.EditableFeatureType;
38
import org.gvsig.fmap.dal.feature.Feature;
39
import org.gvsig.fmap.dal.feature.FeatureAttributeDescriptor;
40
import org.gvsig.fmap.dal.feature.FeatureStore;
41
import org.gvsig.fmap.dal.feature.FeatureStoreTransform;
42
import org.gvsig.fmap.dal.feature.FeatureType;
43
import org.gvsig.fmap.dal.feature.impl.expansionadapter.ExpansionAdapter;
44
import org.gvsig.fmap.dal.feature.spi.FeatureStoreProvider.FeatureTypeChanged;
45
import org.gvsig.tools.persistence.PersistentState;
46
import org.gvsig.tools.persistence.exception.PersistenceException;
47

    
48
public class FeatureTypeManager {
49
        private ExpansionAdapter expansionAdapter;
50
        private ArrayList deleted = new ArrayList();// <FeatureID>
51
        private int deltaSize = 0;
52
        private HashMap added = new HashMap();
53
        private HashMap modifiedFromOriginal = new HashMap();
54
        private FeatureType originalType = null;
55
        private boolean first = true;
56
        private FeatureTypeManagerFeatureStoreTransforms transforms;
57
        private FeatureStore store;
58

    
59
        public FeatureTypeManager(FeatureStore store,
60
                        ExpansionAdapter expansionAdapter) {
61
                this.expansionAdapter = expansionAdapter;
62
                this.store = store;
63
                this.transforms = new FeatureTypeManagerFeatureStoreTransforms();
64
                this.transforms.setFeatureStore(store);
65
        }
66

    
67
        public void dispose() {
68
                this.expansionAdapter.close();
69
                this.expansionAdapter = null;
70
                this.deleted.clear();
71
                this.deleted = null;
72
                this.transforms.clear();
73
        }
74

    
75
        public FeatureType getType(String id) throws DataException {
76
                Integer intNum = ((Integer) added.get(id));
77
                if (intNum == null) {
78
                        intNum = ((Integer) modifiedFromOriginal.get(id));
79
                        if (intNum == null) {
80
                                return null;
81
                        }
82
                }
83
                int num = intNum.intValue();
84
                
85
                if (num == -1) {
86
                    /*
87
                     * This happens for example when we are going back to the
88
                     * original feature type which is not managed by
89
                     * expansionAdapter
90
                     */
91
                    return null;
92
                }
93

    
94
                FeatureType type = (FeatureType) expansionAdapter.getObject(num);
95
                return type;
96
        }
97

    
98
        public int update(FeatureType type, FeatureType oldType) {
99
                // deleted.add(oldType.getId());
100
                if (first) {
101
                        originalType = oldType;
102
                        first = false;
103
                }
104
                int oldNum = -1;
105
                int num = expansionAdapter.addObject(type);
106
                String id = type.getId();
107

    
108
                if (added.containsKey(id)) {
109
                        oldNum = ((Integer) added.get(id)).intValue();
110
                        added.put(id, new Integer(num));
111
                } else {
112
                        if (modifiedFromOriginal.get(id) != null) {
113
                                oldNum = ((Integer) modifiedFromOriginal.get(id)).intValue();
114
                        }
115
                        modifiedFromOriginal.put(id, new Integer(num));
116
                }
117

    
118
                try {
119
                        this.transforms.add(new UpdateFeatureTypeTransform(this.store,
120
                                        oldType, type));
121
                } catch (DataException e) {
122
                        throw new RuntimeException(); // FIXME (pero esto no deberia de
123
                                                                                        // pasar nunca)
124
                }
125
                return oldNum;
126
        }
127

    
128
        private class UpdateFeatureTypeTransform extends AbstractFeatureStoreTransform {
129
                private FeatureType ftSource;
130
                
131
        private EditableFeatureType ftTarget_editable;
132
        private FeatureType ftTarget_non_editable;
133
                
134
                private WeakReference wkRefStore;
135
                private List ftypes = null;
136
                private List attrInSourceToUse;
137

    
138
                UpdateFeatureTypeTransform(FeatureStore featureStore,
139
                                FeatureType ftSource, FeatureType ftTarget) {
140
                        this.ftSource = ftSource;
141
                        
142
                        if (ftTarget instanceof EditableFeatureType) {
143
                            
144
                            ftTarget_editable = (EditableFeatureType) ftTarget;
145
                            ftTarget_non_editable = ftTarget_editable.getNotEditableCopy();
146
                        } else {
147
                            ftTarget_non_editable = ftTarget;
148
                        }
149

    
150
                        this.wkRefStore = new WeakReference(featureStore);
151
                        this.initializeAttributesToUse();
152
                }
153

    
154
                private void initializeAttributesToUse() {
155
                    attrInSourceToUse = new ArrayList();
156
                    
157
                    Iterator iter = null;
158
                    if (ftTarget_editable != null) {
159
                        iter = ftTarget_editable.iterator();
160
                    } else {
161
                        iter = ftTarget_non_editable.iterator();
162
                    }
163

    
164
                        FeatureAttributeDescriptor tAttr, sAttr;
165
                        EditableFeatureAttributeDescriptor ead = null;
166
                        while (iter.hasNext()) {
167
                                tAttr = (FeatureAttributeDescriptor) iter.next();
168
                                sAttr = this.ftSource.getAttributeDescriptor(tAttr.getName());
169
                                if (sAttr == null) {
170
                                    if (tAttr instanceof EditableFeatureAttributeDescriptor) {
171
                                        ead = (EditableFeatureAttributeDescriptor) tAttr;
172
                                        if (ead.getOriginalName() != null) {
173
                                            sAttr = this.ftSource.getAttributeDescriptor(ead.getOriginalName());
174
                                if (sAttr == null) {
175
                                    continue;
176
                                }
177
                                        } else {
178
                                            continue;
179
                                        }
180
                                    } else {
181
                                        continue;
182
                                    }
183
                                }
184
                                if (tAttr.getType() != sAttr.getType()) {
185
                                    /*
186
                                     * Ignore if type is not the same (user removed field
187
                                     * and added another with same name but different type)
188
                                     */
189
                                        continue;
190
                                }
191
                                attrInSourceToUse.add(sAttr.getName());
192
                        }
193
                }
194

    
195
                public void applyTransform(Feature source, EditableFeature target)
196
                                throws DataException {
197
                    
198
                        Iterator iter = target.getType().iterator();
199
                        FeatureAttributeDescriptor tAttr;
200
                        FeatureAttributeDescriptor tAttr_edi;
201
                        FeatureAttributeDescriptor srcAtt;
202
                        
203
                        /*
204
                         * field name in source feature
205
                         */
206
            String s_name;
207
            
208
            /*
209
             * field name in target feature (the same as in source
210
             * except if renamed)
211
             */
212
            String t_name;
213
                        
214
                        EditableFeatureAttributeDescriptor eatd = null;
215
                        while (iter.hasNext()) {
216
                                tAttr = (FeatureAttributeDescriptor) iter.next();
217
                                
218
                                if (ftTarget_editable != null) {
219
                                    /*
220
                                     * If target FT is editable, try to get original name
221
                                     */
222
                                    t_name = tAttr.getName();
223
                                    s_name = t_name;
224
                                    tAttr_edi = ftTarget_editable.getAttributeDescriptor(t_name);
225
                                    if (tAttr_edi instanceof EditableFeatureAttributeDescriptor) {
226
                                        eatd = (EditableFeatureAttributeDescriptor) tAttr_edi;
227
                                        s_name = eatd.getOriginalName();
228
                                    }
229
                                    
230
                                    /*
231
                                     * If not found, use normal name
232
                                     */
233
                                    if (s_name == null) {
234
                                        s_name = tAttr.getName();
235
                                    }
236
                                } else {
237
                                    /*
238
                                     * If target FT is not editable, use normal name
239
                                     */
240
                                    t_name = tAttr.getName();
241
                                    s_name = t_name;
242
                                }
243
                                
244
                                srcAtt = source.getType().getAttributeDescriptor(s_name);
245
                                
246
                                if (srcAtt != null &&
247
                                    /*
248
                                     * This prevents the case when user has removed field and
249
                                     * added new field with same name and different type.
250
                                     * In that case, value will be the default value (else below)
251
                                     */
252
                                    srcAtt.getType() == tAttr.getType()) {
253
                                    
254
                                        target.set(t_name, source.get(s_name));
255
                                        
256
                                } else {
257
                                        target.set(t_name, tAttr.getDefaultValue());
258
                                }
259
                        }
260
                }
261

    
262
                public FeatureType getDefaultFeatureType() throws DataException {
263
                        return this.ftTarget_non_editable;
264
                }
265

    
266
                public FeatureStore getFeatureStore() {
267
                        return (FeatureStore) this.wkRefStore.get();
268
                }
269

    
270
                public List getFeatureTypes() throws DataException {
271
                        if (this.ftypes == null) {
272
                                this.ftypes = Arrays
273
                                                .asList(new FeatureType[] { this.ftTarget_non_editable });
274
                        }
275
                        return this.ftypes;
276
                }
277

    
278
                public FeatureType getSourceFeatureTypeFrom(
279
                                FeatureType targetFeatureType) {
280
                        EditableFeatureType orgType = ftSource.getEditable();
281
                        Iterator iter = orgType.iterator();
282
                        FeatureAttributeDescriptor attr;
283
                        EditableFeatureAttributeDescriptor efad = null;
284

    
285
                        while (iter.hasNext()) {
286
                                attr = (FeatureAttributeDescriptor) iter.next();
287
                                if (!attrInSourceToUse.contains(attr.getName())) {
288
                                    if (attr instanceof EditableFeatureAttributeDescriptor) {
289
                                        efad = (EditableFeatureAttributeDescriptor) attr;
290
                                        if (efad.getOriginalName() != null &&
291
                                            !attrInSourceToUse.contains(efad.getOriginalName())) {
292
                                            iter.remove();
293
                                        }
294
                                    } else {
295
                                        iter.remove();
296
                                    }
297
                                }
298
                        }
299
                        return orgType.getNotEditableCopy();
300
                }
301

    
302
                public void setFeatureStore(FeatureStore featureStore) {
303
                        this.wkRefStore = new WeakReference(featureStore);
304
                }
305

    
306
                public boolean isTransformsOriginalValues() {
307
                        return false;
308
                }
309

    
310
        }
311

    
312
        public void restore(String id) {
313
                deleted.remove(id);
314
                deltaSize++;
315
        }
316

    
317
        public void restore(String id, int num) {
318
                if (added.containsKey(id)) {
319
                        added.put(id, new Integer(num));
320
                } else {
321
                        modifiedFromOriginal.put(id, new Integer(num));
322
                }
323
        }
324

    
325
        public boolean isDeleted(FeatureType type) {
326
                return deleted.contains(type.getId());
327
        }
328

    
329
        public boolean isDeleted(String id) {
330
                return deleted.contains(id);
331
        }
332

    
333
        public void clear() {
334
                added.clear();
335
                modifiedFromOriginal.clear();
336
                expansionAdapter.close();
337
                deleted.clear();// <FeatureID>
338
                deltaSize = 0;
339
        }
340

    
341
        public boolean hasChanges() {
342
                return added.size() > 0 || modifiedFromOriginal.size() > 0
343
                                || deleted.size() > 0;
344
        }
345

    
346
        public Iterator newsIterator() {
347
                return added.values().iterator();
348
        }
349

    
350
        public boolean hasNews() {
351
                return !added.isEmpty();
352
        }
353

    
354
        public long getDeltaSize() {
355
                return deltaSize;
356
        }
357

    
358
        public FeatureType getOriginalFeatureType() {
359
                return originalType;
360
        }
361

    
362
        public DefaultFeatureStoreTransforms getTransforms() {
363
                return this.transforms;
364
        }
365

    
366
        public class FeatureTypeManagerFeatureStoreTransforms extends
367
                        DefaultFeatureStoreTransforms {
368

    
369
                private FeatureTypeManagerFeatureStoreTransforms() {
370

    
371
                }
372

    
373
                protected void checkEditingMode() {
374
                }
375

    
376
                protected void notifyChangeToStore() {
377
                }
378

    
379
                public PersistentState getState() throws PersistenceException {
380
                        // FIXME
381
                        throw new UnsupportedOperationException();
382
                }
383

    
384
                public void loadState(PersistentState state)
385
                                throws PersistenceException {
386
                        // FIXME
387
                        throw new UnsupportedOperationException();
388
                }
389

    
390
                public void loadFromState(PersistentState state) throws PersistenceException {
391
                        // FIXME
392
                        throw new UnsupportedOperationException();
393
                }
394

    
395
                public FeatureStoreTransform add(FeatureStoreTransform transform)
396
                                throws DataException {
397
                        if (!(transform instanceof UpdateFeatureTypeTransform)) {
398
                                // FIXME
399
                                throw new IllegalArgumentException();
400
                        }
401
                        return super.add(transform);
402
                }
403

    
404
        }
405

    
406
        public class FeatureTypesChangedItem implements FeatureTypeChanged {
407

    
408
                private FeatureType source;
409
                private FeatureType target;
410

    
411
                public FeatureTypesChangedItem(FeatureType source, FeatureType target) {
412
                        this.source = source;
413
                        this.target = target;
414
                }
415

    
416
                public FeatureType getSource() {
417
                        return source;
418
                }
419

    
420
                public FeatureType getTarget() {
421
                        return target;
422
                }
423

    
424
        }
425

    
426
        public Iterator getFeatureTypesChanged() throws DataException {
427
                // FIXME this don't work for Store.fType.size() > 1
428
                List list = new ArrayList();
429
                if (modifiedFromOriginal.size() > 0) {
430
                        FeatureType src = this.getOriginalFeatureType();
431
                        list.add(new FeatureTypesChangedItem(src, this.store
432
                                        .getFeatureType(src.getId())));
433
                }
434
                return list.iterator();
435
        }
436

    
437
}