001: /* uDig - User Friendly Desktop Internet GIS client
002: * http://udig.refractions.net
003: * (C) 2004, Refractions Research Inc.
004: *
005: * This library is free software; you can redistribute it and/or
006: * modify it under the terms of the GNU Lesser General Public
007: * License as published by the Free Software Foundation;
008: * version 2.1 of the License.
009: *
010: * This library is distributed in the hope that it will be useful,
011: * but WITHOUT ANY WARRANTY; without even the implied warranty of
012: * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
013: * Lesser General Public License for more details.
014: */
015: package net.refractions.udig.internal.ui;
016:
017: import java.util.HashMap;
018: import java.util.Map;
019: import java.util.concurrent.CopyOnWriteArraySet;
020:
021: import org.eclipse.core.runtime.preferences.IExportedPreferences;
022: import org.eclipse.core.runtime.preferences.IPreferenceNodeVisitor;
023: import org.eclipse.jface.preference.IPreferenceStore;
024: import org.osgi.service.prefs.BackingStoreException;
025: import org.osgi.service.prefs.Preferences;
026:
027: /**
028: * Uses a scoped preferences to store preferences.
029: *
030: * @author Jesse
031: * @since 1.1.0
032: */
033: public class UDIGExportedPreferences implements IExportedPreferences {
034:
035: private IPreferenceStore store;
036: private CopyOnWriteArraySet<INodeChangeListener> nodeChangeListeners = new CopyOnWriteArraySet<INodeChangeListener>();
037: private CopyOnWriteArraySet<IPreferenceChangeListener> preferenceChangeListeners = new CopyOnWriteArraySet<IPreferenceChangeListener>();
038: private String nodePath;
039: private Map<String, String> map = new HashMap<String, String>();
040: private Map<String, UDIGExportedPreferences> children = new HashMap<String, UDIGExportedPreferences>();
041:
042: public UDIGExportedPreferences(IPreferenceStore store,
043: String nodePath) {
044: if (nodePath.contains(":")) //$NON-NLS-1$
045: throw new IllegalArgumentException(
046: "Node name cannot contain a ':'"); //$NON-NLS-1$
047: if (nodePath.contains("$")) //$NON-NLS-1$
048: throw new IllegalArgumentException(
049: "Node name cannot contain a '$'"); //$NON-NLS-1$
050: this .store = store;
051: this .nodePath = nodePath;
052: try {
053: sync();
054: } catch (Exception e) {
055: UiPlugin.log("", e); //$NON-NLS-1$
056: }
057: }
058:
059: public boolean isExportRoot() {
060: return false;
061: }
062:
063: public void addNodeChangeListener(INodeChangeListener listener) {
064: nodeChangeListeners.add(listener);
065: }
066:
067: public void removeNodeChangeListener(INodeChangeListener listener) {
068: nodeChangeListeners.remove(listener);
069: }
070:
071: public void addPreferenceChangeListener(
072: IPreferenceChangeListener listener) {
073: preferenceChangeListeners.add(listener);
074: }
075:
076: public void removePreferenceChangeListener(
077: IPreferenceChangeListener listener) {
078: preferenceChangeListeners.remove(listener);
079: }
080:
081: public void removeNode() throws BackingStoreException {
082: store.setToDefault(nodePath);
083: }
084:
085: public Preferences node(String path) {
086: String string = nodePath + "/" + path; //$NON-NLS-1$
087: if (children.get(path) != null)
088: return children.get(path);
089:
090: UDIGExportedPreferences preferences = new UDIGExportedPreferences(
091: store, string);
092: children.put(path, preferences);
093: return preferences;
094: }
095:
096: public void accept(IPreferenceNodeVisitor visitor)
097: throws BackingStoreException {
098: visitor.visit(this );
099: }
100:
101: public void put(String key, String value) {
102: map.put(key, value);
103: }
104:
105: public String get(String key, String def) {
106: return map.get(key);
107: }
108:
109: public void remove(String key) {
110: map.remove(key);
111: }
112:
113: public void clear() throws BackingStoreException {
114: map.clear();
115: }
116:
117: public void putInt(String key, int value) {
118: map.put(key, String.valueOf(value));
119: }
120:
121: public int getInt(String key, int def) {
122: String string = map.get(key);
123: if (string == null)
124: return def;
125: return Integer.parseInt(string);
126: }
127:
128: public void putLong(String key, long value) {
129: map.put(key, String.valueOf(value));
130: }
131:
132: public long getLong(String key, long def) {
133: String string = map.get(key);
134: if (string == null)
135: return def;
136: return Long.parseLong(string);
137: }
138:
139: public void putBoolean(String key, boolean value) {
140: map.put(key, String.valueOf(value));
141: }
142:
143: public boolean getBoolean(String key, boolean def) {
144: String string = map.get(key);
145: if (string == null)
146: return def;
147: return Boolean.parseBoolean(string);
148: }
149:
150: public void putFloat(String key, float value) {
151: map.put(key, String.valueOf(value));
152: }
153:
154: public float getFloat(String key, float def) {
155: String string = map.get(key);
156: if (string == null)
157: return def;
158: return Float.parseFloat(string);
159: }
160:
161: public void putDouble(String key, double value) {
162: map.put(key, String.valueOf(value));
163: }
164:
165: public double getDouble(String key, double def) {
166: String string = map.get(key);
167: if (string == null)
168: return def;
169: return Double.parseDouble(string);
170: }
171:
172: public void putByteArray(String key, byte[] value) {
173: map.put(key, String.valueOf(value));
174: }
175:
176: public byte[] getByteArray(String key, byte[] def) {
177: String string = map.get(key);
178: if (string == null)
179: return def;
180: return string.getBytes();
181: }
182:
183: public String[] keys() throws BackingStoreException {
184: return map.keySet().toArray(new String[0]);
185: }
186:
187: public String[] childrenNames() throws BackingStoreException {
188: return children.keySet().toArray(new String[0]);
189: }
190:
191: public Preferences parent() {
192: return null;
193: }
194:
195: public boolean nodeExists(String pathName)
196: throws BackingStoreException {
197: String s = store.getString(nodePath + "/" + pathName); //$NON-NLS-1$
198: return s.length() > 0;
199: }
200:
201: public String name() {
202: int lastIndexOf = nodePath.lastIndexOf('/');
203: if (lastIndexOf == -1)
204: return ""; //$NON-NLS-1$
205: return nodePath.substring(lastIndexOf);
206: }
207:
208: public String absolutePath() {
209: return nodePath;
210: }
211:
212: public void flush() throws BackingStoreException {
213: StringBuilder builder = null;
214: for (Map.Entry<String, String> entry : map.entrySet()) {
215: if (builder == null)
216: builder = new StringBuilder();
217: else
218: builder.append(":"); //$NON-NLS-1$
219: builder.append(entry.getKey());
220: builder.append(":"); //$NON-NLS-1$
221: builder.append(entry.getValue());
222: }
223: if (builder != null)
224: store.putValue(nodePath, builder.toString());
225:
226: StringBuilder encodedChildren = null;
227: for (String entry : children.keySet()) {
228: if (encodedChildren == null)
229: encodedChildren = new StringBuilder();
230: else
231: encodedChildren.append(":"); //$NON-NLS-1$
232: encodedChildren.append(nodePath + "/" + entry); //$NON-NLS-1$
233: }
234: if (encodedChildren != null)
235: store.putValue(
236: nodePath + "$children", encodedChildren.toString()); //$NON-NLS-1$
237:
238: for (UDIGExportedPreferences p : children.values()) {
239: if (p != null)
240: p.flush();
241: }
242: }
243:
244: public void sync() throws BackingStoreException {
245: String[] data = store.getString(nodePath).split(":"); //$NON-NLS-1$
246: if (data.length > 1) {
247: for (int i = 0; i < data.length; i++) {
248: String key = data[i];
249: i++;
250: String value = null;
251: if (data.length > i)
252: value = data[i];
253: map.put(key, value);
254: }
255: }
256: String[] encodedChildren = store.getString(
257: nodePath + "$children").split(":"); //$NON-NLS-1$//$NON-NLS-2$
258: if (encodedChildren.length > 1) {
259: for (String string : encodedChildren) {
260: if (string.length() > 0) {
261: String[] name = string.split("/"); //$NON-NLS-1$
262: children.put(name[name.length - 1], null);
263: }
264: }
265: }
266: }
267:
268: }
|