Some Eclipse Foundation services are deprecated, or will be soon. Please ensure you've read this important communication.
View | Details | Raw Unified | Return to bug 194734 | Differences between
and this patch

Collapse All | Expand All

(-)src/org/eclipse/core/internal/databinding/beans/JavaBeanObservableMap.java (-193 lines)
Removed Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2006, 2008 IBM Corporation and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
10
 *     Brad Reynolds - bug 171616
11
 *     Matthew hall - bugs 223164, 241585, 226289, 246103
12
 *******************************************************************************/
13
14
package org.eclipse.core.internal.databinding.beans;
15
16
import java.beans.PropertyChangeListener;
17
import java.beans.PropertyDescriptor;
18
import java.lang.reflect.Method;
19
import java.util.HashMap;
20
import java.util.Map;
21
22
import org.eclipse.core.databinding.beans.IBeanObservable;
23
import org.eclipse.core.databinding.observable.Diffs;
24
import org.eclipse.core.databinding.observable.map.ComputedObservableMap;
25
import org.eclipse.core.databinding.observable.set.IObservableSet;
26
import org.eclipse.core.databinding.util.Policy;
27
import org.eclipse.core.internal.databinding.Util;
28
import org.eclipse.core.runtime.IStatus;
29
import org.eclipse.core.runtime.Status;
30
31
/**
32
 * @since 1.0
33
 * 
34
 */
35
public class JavaBeanObservableMap extends ComputedObservableMap implements
36
		IBeanObservable {
37
38
	private PropertyDescriptor propertyDescriptor;
39
	
40
	private PropertyChangeListener elementListener = new PropertyChangeListener() {
41
		public void propertyChange(final java.beans.PropertyChangeEvent event) {
42
			if (!updating) {
43
				getRealm().exec(new Runnable() {
44
					public void run() {
45
						Object source = event.getSource();
46
						Object oldValue = event.getOldValue();
47
						Object newValue = event.getNewValue();
48
						if (oldValue == null && newValue == null) {
49
							oldValue = cachedValues.get(new IdentityWrapper(
50
									source));
51
							newValue = doGet(source);
52
						}
53
						cachedValues.put(new IdentityWrapper(source), newValue);
54
						if (!Util.equals(oldValue, newValue)) {
55
							fireMapChange(Diffs.createMapDiffSingleChange(
56
									source, oldValue, newValue));
57
						}
58
					}
59
				});
60
			}
61
		}
62
	};
63
64
	private ListenerSupport listenerSupport;
65
66
	private boolean updating = false;
67
68
	private boolean attachListeners;
69
70
	// Applicable only while hasListeners() == true
71
	private Map cachedValues;
72
73
	/**
74
	 * @param domain
75
	 * @param propertyDescriptor
76
	 */
77
	public JavaBeanObservableMap(IObservableSet domain,
78
			PropertyDescriptor propertyDescriptor) {
79
		this(domain, propertyDescriptor, true);
80
	}
81
82
	/**
83
	 * @param domain
84
	 * @param propertyDescriptor
85
	 * @param attachListeners
86
	 */
87
	public JavaBeanObservableMap(IObservableSet domain,
88
			PropertyDescriptor propertyDescriptor, boolean attachListeners) {
89
		super(domain, propertyDescriptor.getPropertyType());
90
91
		this.propertyDescriptor = propertyDescriptor;
92
		this.attachListeners = attachListeners;
93
		if (attachListeners) {
94
			this.listenerSupport = new ListenerSupport(elementListener,
95
					propertyDescriptor.getName());
96
		}
97
	}
98
99
	protected void firstListenerAdded() {
100
		if (attachListeners) {
101
			cachedValues = new HashMap();
102
		}
103
		super.firstListenerAdded();
104
	}
105
106
	protected void lastListenerRemoved() {
107
		super.lastListenerRemoved();
108
		if (attachListeners) {
109
			cachedValues = null;
110
		}
111
	}
112
113
	protected void hookListener(Object domainElement) {
114
		if (attachListeners && domainElement != null) {
115
			listenerSupport.hookListener(domainElement);
116
			cachedValues.put(new IdentityWrapper(domainElement),
117
					doGet(domainElement));
118
		}
119
	}
120
121
	protected void unhookListener(Object domainElement) {
122
		if (attachListeners && domainElement != null) {
123
			cachedValues.remove(new IdentityWrapper(domainElement));
124
			listenerSupport.unhookListener(domainElement);
125
		}
126
	}
127
128
	protected Object doGet(Object key) {
129
		if (key == null) {
130
			return null;
131
		}
132
		try {
133
			Method readMethod = propertyDescriptor.getReadMethod();
134
			if (!readMethod.isAccessible()) {
135
				readMethod.setAccessible(true);
136
			}
137
			return readMethod.invoke(key, new Object[0]);
138
		} catch (Exception e) {
139
			Policy.getLog().log(
140
					new Status(IStatus.ERROR, Policy.JFACE_DATABINDING,
141
							IStatus.ERROR, "cannot get value", e)); //$NON-NLS-1$
142
			throw new RuntimeException(e);
143
		}
144
	}
145
146
	protected Object doPut(Object key, Object value) {
147
		try {
148
			Object oldValue = get(key);
149
			if (!Util.equals(oldValue, value)) {
150
				Method writeMethod = propertyDescriptor.getWriteMethod();
151
				if (!writeMethod.isAccessible()) {
152
					writeMethod.setAccessible(true);
153
				}
154
				writeMethod.invoke(key, new Object[] { value });
155
			}
156
157
			if (hasListeners()) {
158
				// oldValue contains the live value which may be different from
159
				// the cached value if the bean does not have listener API or
160
				// does not fire events properly. For consistency we want to
161
				// provide the cached value as the old value, rather than the
162
				// live value so that consumers that hook/unhook listeners can
163
				// do so without maintaining caches of their own.
164
				Object newValue = doGet(key);
165
				oldValue = cachedValues.put(new IdentityWrapper(key), newValue);
166
167
				if (!Util.equals(oldValue, newValue)) {
168
					fireSingleChange(key, oldValue, newValue);
169
				}
170
			}
171
			return oldValue;
172
		} catch (Exception e) {
173
			Policy.getLog().log(
174
					new Status(IStatus.ERROR, Policy.JFACE_DATABINDING,
175
							IStatus.ERROR, "cannot set value", e)); //$NON-NLS-1$
176
			throw new RuntimeException(e);
177
		}
178
	}
179
180
	/* (non-Javadoc)
181
	 * @see org.eclipse.core.databinding.beans.IBeanObservable#getObserved()
182
	 */
183
	public Object getObserved() {
184
		return keySet();
185
	}
186
187
	/* (non-Javadoc)
188
	 * @see org.eclipse.core.databinding.beans.IBeanObservable#getPropertyDescriptor()
189
	 */
190
	public PropertyDescriptor getPropertyDescriptor() {
191
		return propertyDescriptor;
192
	}
193
}
(-)src/org/eclipse/core/internal/databinding/beans/IdentityWrapper.java (-1 / +1 lines)
Lines 29-35 Link Here
29
	public IdentityWrapper(Object o) {
29
	public IdentityWrapper(Object o) {
30
		this.o = o;
30
		this.o = o;
31
	}
31
	}
32
	
32
33
	/**
33
	/**
34
	 * @return the unwrapped object
34
	 * @return the unwrapped object
35
	 */
35
	 */
(-)src/org/eclipse/core/internal/databinding/beans/JavaBeanObservableList.java (-399 lines)
Removed Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2006-2008 IBM Corporation and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
10
 *     Brad Reynolds - bug 171616
11
 *     Matthew Hall - bugs 208858, 221351, 213145, 223164, 244098
12
 *     Mike Evans - bug 217558
13
 *******************************************************************************/
14
15
package org.eclipse.core.internal.databinding.beans;
16
17
import java.beans.PropertyChangeListener;
18
import java.beans.PropertyDescriptor;
19
import java.lang.reflect.Array;
20
import java.lang.reflect.InvocationTargetException;
21
import java.lang.reflect.Method;
22
import java.util.ArrayList;
23
import java.util.Arrays;
24
import java.util.Collection;
25
import java.util.Iterator;
26
import java.util.List;
27
28
import org.eclipse.core.databinding.BindingException;
29
import org.eclipse.core.databinding.beans.IBeanObservable;
30
import org.eclipse.core.databinding.observable.Diffs;
31
import org.eclipse.core.databinding.observable.Realm;
32
import org.eclipse.core.databinding.observable.list.ListDiffEntry;
33
import org.eclipse.core.databinding.observable.list.ObservableList;
34
35
/**
36
 * @since 1.0
37
 * 
38
 */
39
public class JavaBeanObservableList extends ObservableList implements
40
		IBeanObservable {
41
42
	private final Object object;
43
44
	private boolean updating = false;
45
46
	private PropertyDescriptor descriptor;
47
48
	private ListenerSupport listenerSupport;
49
50
	/**
51
	 * @param realm
52
	 * @param object
53
	 * @param descriptor
54
	 * @param elementType
55
	 */
56
	public JavaBeanObservableList(Realm realm, Object object,
57
			PropertyDescriptor descriptor, Class elementType) {
58
		this(realm, object, descriptor, elementType, true);
59
	}
60
61
	/**
62
	 * @param realm
63
	 * @param object
64
	 * @param descriptor
65
	 * @param elementType
66
	 * @param attachListeners
67
	 */
68
	public JavaBeanObservableList(Realm realm, Object object,
69
			PropertyDescriptor descriptor, Class elementType,
70
			boolean attachListeners) {
71
72
		super(realm, new ArrayList(), elementType);
73
		this.object = object;
74
		this.descriptor = descriptor;
75
76
		if (attachListeners) {
77
			PropertyChangeListener listener = new PropertyChangeListener() {
78
				public void propertyChange(java.beans.PropertyChangeEvent event) {
79
					if (!updating) {
80
						getRealm().exec(new Runnable() {
81
							public void run() {
82
								updateWrappedList(new ArrayList(Arrays
83
										.asList(getValues())));
84
							}
85
						});
86
					}
87
				}
88
			};
89
			this.listenerSupport = new ListenerSupport(listener,
90
					descriptor.getName());
91
			listenerSupport.hookListener(this.object);
92
		}
93
94
		// initialize list without firing events
95
		wrappedList.addAll(Arrays.asList(getValues()));
96
	}
97
98
	public void dispose() {
99
		if (listenerSupport != null) {
100
			listenerSupport.dispose();
101
			listenerSupport = null;
102
		}
103
		super.dispose();
104
	}
105
106
	private Object primGetValues() {
107
		Exception ex = null;
108
		try {
109
			Method readMethod = descriptor.getReadMethod();
110
			if (!readMethod.isAccessible()) {
111
				readMethod.setAccessible(true);
112
			}
113
			return readMethod.invoke(object, new Object[0]);
114
		} catch (IllegalArgumentException e) {
115
			ex = e;
116
		} catch (IllegalAccessException e) {
117
			ex = e;
118
		} catch (InvocationTargetException e) {
119
			ex = e;
120
		}
121
		throw new BindingException("Could not read collection values", ex); //$NON-NLS-1$
122
	}
123
124
	private Object[] getValues() {
125
		Object[] values = null;
126
127
		Object result = primGetValues();
128
		if (descriptor.getPropertyType().isArray())
129
			values = (Object[]) result;
130
		else {
131
			// TODO add jUnit for POJO (var. SettableValue) collections
132
			Collection list = (Collection) result;
133
			if (list != null) {
134
				values = list.toArray();
135
			}
136
		}
137
		if (values == null)
138
			values = new Object[0];
139
		return values;
140
	}
141
142
	public Object getObserved() {
143
		return object;
144
	}
145
146
	public PropertyDescriptor getPropertyDescriptor() {
147
		return descriptor;
148
	}
149
150
	private void setValues() {
151
		if (descriptor.getPropertyType().isArray()) {
152
			Class componentType = descriptor.getPropertyType()
153
					.getComponentType();
154
			Object[] newArray = (Object[]) Array.newInstance(componentType,
155
					wrappedList.size());
156
			wrappedList.toArray(newArray);
157
			primSetValues(newArray);
158
		} else {
159
			// assume that it is a java.util.List
160
			primSetValues(new ArrayList(wrappedList));
161
		}
162
	}
163
164
	private void primSetValues(Object newValue) {
165
		Exception ex = null;
166
		try {
167
			Method writeMethod = descriptor.getWriteMethod();
168
			if (!writeMethod.isAccessible()) {
169
				writeMethod.setAccessible(true);
170
			}
171
			writeMethod.invoke(object, new Object[] { newValue });
172
			return;
173
		} catch (IllegalArgumentException e) {
174
			ex = e;
175
		} catch (IllegalAccessException e) {
176
			ex = e;
177
		} catch (InvocationTargetException e) {
178
			ex = e;
179
		}
180
		throw new BindingException("Could not write collection values", ex); //$NON-NLS-1$
181
	}
182
183
	public Object set(int index, Object element) {
184
		getterCalled();
185
		updating = true;
186
		try {
187
			Object oldElement = wrappedList.set(index, element);
188
			setValues();
189
			fireListChange(Diffs.createListDiff(Diffs.createListDiffEntry(
190
					index, false, oldElement), Diffs.createListDiffEntry(index,
191
					true, element)));
192
			return oldElement;
193
		} finally {
194
			updating = false;
195
		}
196
	}
197
198
	public Object move(int oldIndex, int newIndex) {
199
		getterCalled();
200
		updating = true;
201
		try {
202
			int size = wrappedList.size();
203
			if (oldIndex < 0 || oldIndex >= size)
204
				throw new IndexOutOfBoundsException(
205
						"oldIndex: " + oldIndex + ", size:" + size); //$NON-NLS-1$ //$NON-NLS-2$
206
			if (newIndex < 0 || newIndex >= size)
207
				throw new IndexOutOfBoundsException(
208
						"newIndex: " + newIndex + ", size:" + size); //$NON-NLS-1$ //$NON-NLS-2$
209
			if (oldIndex == newIndex)
210
				return wrappedList.get(oldIndex);
211
			Object element = wrappedList.remove(oldIndex);
212
			wrappedList.add(newIndex, element);
213
			setValues();
214
			fireListChange(Diffs.createListDiff(Diffs.createListDiffEntry(
215
					oldIndex, false, element), Diffs.createListDiffEntry(
216
					newIndex, true, element)));
217
			return element;
218
		} finally {
219
			updating = false;
220
		}
221
	}
222
223
	public Object remove(int index) {
224
		getterCalled();
225
		updating = true;
226
		try {
227
			Object oldElement = wrappedList.remove(index);
228
			setValues();
229
			fireListChange(Diffs.createListDiff(Diffs.createListDiffEntry(
230
					index, false, oldElement)));
231
			return oldElement;
232
		} finally {
233
			updating = false;
234
		}
235
	}
236
237
	public boolean add(Object element) {
238
		updating = true;
239
		try {
240
			int index = wrappedList.size();
241
			boolean result = wrappedList.add(element);
242
			setValues();
243
			fireListChange(Diffs.createListDiff(Diffs.createListDiffEntry(
244
					index, true, element)));
245
			return result;
246
		} finally {
247
			updating = false;
248
		}
249
	}
250
251
	public void add(int index, Object element) {
252
		updating = true;
253
		try {
254
			wrappedList.add(index, element);
255
			setValues();
256
			fireListChange(Diffs.createListDiff(Diffs.createListDiffEntry(
257
					index, true, element)));
258
		} finally {
259
			updating = false;
260
		}
261
	}
262
263
	public boolean addAll(Collection c) {
264
		if (c.isEmpty()) {
265
			return false;
266
		}
267
		updating = true;
268
		try {
269
			int index = wrappedList.size();
270
			boolean result = wrappedList.addAll(c);
271
			setValues();
272
			ListDiffEntry[] entries = new ListDiffEntry[c.size()];
273
			int i = 0;
274
			for (Iterator it = c.iterator(); it.hasNext();) {
275
				Object o = it.next();
276
				entries[i++] = Diffs.createListDiffEntry(index++, true, o);
277
			}
278
			fireListChange(Diffs.createListDiff(entries));
279
			return result;
280
		} finally {
281
			updating = false;
282
		}
283
	}
284
285
	public boolean addAll(int index, Collection c) {
286
		if (c.isEmpty()) {
287
			return false;
288
		}
289
		updating = true;
290
		try {
291
			boolean result = wrappedList.addAll(index, c);
292
			setValues();
293
			ListDiffEntry[] entries = new ListDiffEntry[c.size()];
294
			int i = 0;
295
			for (Iterator it = c.iterator(); it.hasNext();) {
296
				Object o = it.next();
297
				entries[i++] = Diffs.createListDiffEntry(index++, true, o);
298
			}
299
			fireListChange(Diffs.createListDiff(entries));
300
			return result;
301
		} finally {
302
			updating = false;
303
		}
304
	}
305
306
	public boolean remove(Object o) {
307
		getterCalled();
308
		int index = wrappedList.indexOf(o);
309
		if (index == -1) {
310
			return false;
311
		}
312
		updating = true;
313
		try {
314
			Object oldElement = wrappedList.remove(index);
315
			setValues();
316
			fireListChange(Diffs.createListDiff(Diffs.createListDiffEntry(
317
					index, false, oldElement)));
318
			return true;
319
		} finally {
320
			updating = false;
321
		}
322
	}
323
324
	public boolean removeAll(Collection c) {
325
		getterCalled();
326
		boolean changed = false;
327
		updating = true;
328
		try {
329
			List diffEntries = new ArrayList();
330
			for (Iterator it = c.iterator(); it.hasNext();) {
331
				Object o = it.next();
332
				int index = wrappedList.indexOf(o);
333
				if (index != -1) {
334
					changed = true;
335
					Object oldElement = wrappedList.remove(index);
336
					diffEntries.add(Diffs.createListDiffEntry(index, false,
337
							oldElement));
338
				}
339
			}
340
			if (changed) {
341
				setValues();
342
				fireListChange(Diffs
343
						.createListDiff((ListDiffEntry[]) diffEntries
344
								.toArray(new ListDiffEntry[diffEntries.size()])));
345
			}
346
			return changed;
347
		} finally {
348
			updating = false;
349
		}
350
	}
351
352
	public boolean retainAll(Collection c) {
353
		getterCalled();
354
		boolean changed = false;
355
		updating = true;
356
		try {
357
			List diffEntries = new ArrayList();
358
			int index = 0;
359
			for (Iterator it = wrappedList.iterator(); it.hasNext();) {
360
				Object o = it.next();
361
				boolean retain = c.contains(o);
362
				if (retain) {
363
					index++;
364
				} else {
365
					changed = true;
366
					it.remove();
367
					diffEntries.add(Diffs.createListDiffEntry(index, false, o));
368
				}
369
			}
370
			if (changed) {
371
				setValues();
372
				fireListChange(Diffs
373
						.createListDiff((ListDiffEntry[]) diffEntries
374
								.toArray(new ListDiffEntry[diffEntries.size()])));
375
			}
376
			return changed;
377
		} finally {
378
			updating = false;
379
		}
380
	}
381
382
	public void clear() {
383
		updating = true;
384
		try {
385
			List diffEntries = new ArrayList();
386
			for (Iterator it = wrappedList.iterator(); it.hasNext();) {
387
				Object o = it.next();
388
				diffEntries.add(Diffs.createListDiffEntry(0, false, o));
389
			}
390
			wrappedList.clear();
391
			setValues();
392
			fireListChange(Diffs.createListDiff((ListDiffEntry[]) diffEntries
393
					.toArray(new ListDiffEntry[diffEntries.size()])));
394
		} finally {
395
			updating = false;
396
		}
397
	}
398
399
}
(-)src/org/eclipse/core/internal/databinding/beans/JavaBeanPropertyObservableMap.java (-263 lines)
Removed Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 221704)
10
 *     Matthew Hall - bug 223164, 226289, 244098, 246103
11
 *******************************************************************************/
12
13
package org.eclipse.core.internal.databinding.beans;
14
15
import java.beans.PropertyChangeEvent;
16
import java.beans.PropertyChangeListener;
17
import java.beans.PropertyDescriptor;
18
import java.lang.reflect.InvocationTargetException;
19
import java.lang.reflect.Method;
20
import java.util.Collections;
21
import java.util.HashMap;
22
import java.util.HashSet;
23
import java.util.Iterator;
24
import java.util.Map;
25
import java.util.Set;
26
27
import org.eclipse.core.databinding.BindingException;
28
import org.eclipse.core.databinding.beans.IBeanObservable;
29
import org.eclipse.core.databinding.observable.Diffs;
30
import org.eclipse.core.databinding.observable.Realm;
31
import org.eclipse.core.databinding.observable.map.ObservableMap;
32
import org.eclipse.core.internal.databinding.Util;
33
import org.eclipse.core.runtime.Assert;
34
35
/**
36
 * @since 1.0
37
 * 
38
 */
39
public class JavaBeanPropertyObservableMap extends ObservableMap implements
40
		IBeanObservable {
41
42
	private final Object object;
43
44
	private Object keyType;
45
	private Object valueType;
46
47
	private boolean updating = false;
48
49
	private PropertyDescriptor descriptor;
50
51
	private ListenerSupport listenerSupport;
52
53
	/**
54
	 * @param realm
55
	 * @param object
56
	 * @param descriptor
57
	 * @param keyType
58
	 * @param valueType
59
	 */
60
	public JavaBeanPropertyObservableMap(Realm realm, Object object,
61
			PropertyDescriptor descriptor, Object keyType, Object valueType) {
62
		this(realm, object, descriptor, keyType, valueType, true);
63
	}
64
65
	/**
66
	 * @param realm
67
	 * @param object
68
	 * @param descriptor
69
	 * @param keyType
70
	 * @param valueType
71
	 * @param attachListeners
72
	 */
73
	public JavaBeanPropertyObservableMap(Realm realm, Object object,
74
			PropertyDescriptor descriptor, Object keyType, Object valueType,
75
			boolean attachListeners) {
76
		super(realm, new HashMap());
77
		this.object = object;
78
		this.descriptor = descriptor;
79
		this.keyType = keyType;
80
		this.valueType = valueType;
81
		if (attachListeners) {
82
			PropertyChangeListener listener = new PropertyChangeListener() {
83
				public void propertyChange(final PropertyChangeEvent event) {
84
					if (!updating) {
85
						getRealm().exec(new Runnable() {
86
							public void run() {
87
								Map oldMap = (Map) event.getOldValue();
88
								Map newMap = (Map) event.getNewValue();
89
								if (oldMap == null && newMap == null) {
90
									oldMap = wrappedMap;
91
									newMap = getMap();
92
								}
93
94
								if (!Util.equals(oldMap, newMap)) {
95
									wrappedMap = new HashMap(newMap);
96
									fireMapChange(Diffs.computeMapDiff(oldMap,
97
											newMap));
98
								}
99
							}
100
						});
101
					}
102
				}
103
			};
104
105
			listenerSupport = new ListenerSupport(listener,
106
					descriptor.getName());
107
			listenerSupport.hookListener(this.object);
108
		}
109
110
		wrappedMap.putAll(getMap());
111
	}
112
113
	public Object getKeyType() {
114
		return keyType;
115
	}
116
117
	public Object getValueType() {
118
		return valueType;
119
	}
120
121
	private Object primGetMap() {
122
		try {
123
			Method readMethod = descriptor.getReadMethod();
124
			if (!readMethod.isAccessible()) {
125
				readMethod.setAccessible(true);
126
			}
127
			return readMethod.invoke(object, new Object[0]);
128
		} catch (IllegalArgumentException e) {
129
		} catch (IllegalAccessException e) {
130
		} catch (InvocationTargetException e) {
131
		}
132
		Assert.isTrue(false, "Could not read collection values"); //$NON-NLS-1$
133
		return null;
134
	}
135
136
	private void primSetMap(Object newValue) {
137
		Exception ex = null;
138
		try {
139
			Method writeMethod = descriptor.getWriteMethod();
140
			if (!writeMethod.isAccessible()) {
141
				writeMethod.setAccessible(true);
142
			}
143
			writeMethod.invoke(object, new Object[] { newValue });
144
			return;
145
		} catch (IllegalArgumentException e) {
146
			ex = e;
147
		} catch (IllegalAccessException e) {
148
			ex = e;
149
		} catch (InvocationTargetException e) {
150
			ex = e;
151
		}
152
		throw new BindingException("Could not write collection values", ex); //$NON-NLS-1$
153
	}
154
155
	private Map getMap() {
156
		Map result = (Map) primGetMap();
157
158
		if (result == null)
159
			result = new HashMap();
160
		return result;
161
	}
162
163
	private void setMap() {
164
		primSetMap(new HashMap(wrappedMap));
165
	}
166
167
	public Object put(Object key, Object value) {
168
		checkRealm();
169
		updating = true;
170
		try {
171
			boolean add = !wrappedMap.containsKey(key);
172
			Object result = wrappedMap.put(key, value);
173
			if (!Util.equals(result, value)) {
174
				setMap();
175
				if (add) {
176
					fireMapChange(Diffs.createMapDiffSingleAdd(key, value));
177
				} else {
178
					fireMapChange(Diffs.createMapDiffSingleChange(key, result,
179
							value));
180
				}
181
			}
182
			return result;
183
		} finally {
184
			updating = false;
185
		}
186
	}
187
188
	public void putAll(Map map) {
189
		checkRealm();
190
		updating = true;
191
		try {
192
			Set addedKeys = new HashSet(map.size());
193
			Map changes = new HashMap(map.size());
194
			for (Iterator it = map.entrySet().iterator(); it.hasNext();) {
195
				Map.Entry entry = (Entry) it.next();
196
				Object key = entry.getKey();
197
				Object newValue = entry.getValue();
198
				boolean add = !wrappedMap.containsKey(key);
199
				Object oldValue = wrappedMap.put(key, newValue);
200
				if (add) {
201
					addedKeys.add(key);
202
				} else if (!Util.equals(oldValue, newValue)) {
203
					changes.put(key, oldValue);
204
				}
205
			}
206
			if (!addedKeys.isEmpty() || !changes.isEmpty()) {
207
				setMap();
208
				fireMapChange(Diffs.createMapDiff(addedKeys,
209
						Collections.EMPTY_SET, changes.keySet(), changes,
210
						wrappedMap));
211
			}
212
		} finally {
213
			updating = false;
214
		}
215
	}
216
217
	public Object remove(Object key) {
218
		checkRealm();
219
		if (!wrappedMap.containsKey(key)) {
220
			return null;
221
		}
222
		updating = true;
223
		try {
224
			Object result = wrappedMap.remove(key);
225
			setMap();
226
			fireMapChange(Diffs.createMapDiffSingleRemove(key, result));
227
			return result;
228
		} finally {
229
			updating = false;
230
		}
231
	}
232
233
	public void clear() {
234
		checkRealm();
235
		if (wrappedMap.isEmpty())
236
			return;
237
		updating = true;
238
		try {
239
			Map oldMap = wrappedMap;
240
			wrappedMap = new HashMap();
241
			setMap();
242
			fireMapChange(Diffs.computeMapDiff(oldMap, Collections.EMPTY_MAP));
243
		} finally {
244
			updating = false;
245
		}
246
	}
247
248
	public Object getObserved() {
249
		return object;
250
	}
251
252
	public PropertyDescriptor getPropertyDescriptor() {
253
		return descriptor;
254
	}
255
256
	public synchronized void dispose() {
257
		if (listenerSupport != null) {
258
			listenerSupport.dispose();
259
			listenerSupport = null;
260
		}
261
		super.dispose();
262
	}
263
}
(-)src/org/eclipse/core/internal/databinding/beans/ListenerSupport.java (-216 lines)
Removed Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2005, 2008 IBM Corporation and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
10
 *     Matthew Hall - bug 118516
11
 *******************************************************************************/
12
package org.eclipse.core.internal.databinding.beans;
13
14
import java.beans.PropertyChangeEvent;
15
import java.beans.PropertyChangeListener;
16
import java.lang.reflect.InvocationTargetException;
17
import java.lang.reflect.Method;
18
import java.util.HashSet;
19
import java.util.Iterator;
20
import java.util.Set;
21
22
import org.eclipse.core.databinding.beans.BeansObservables;
23
import org.eclipse.core.databinding.util.Policy;
24
import org.eclipse.core.runtime.Assert;
25
import org.eclipse.core.runtime.IStatus;
26
import org.eclipse.core.runtime.Status;
27
28
/**
29
 * This is a helper that will hook up and listen for <code>PropertyChangeEvent</code> events
30
 * for a set of target JavaBeans
31
 * 
32
 * @since 1.0
33
 */
34
public class ListenerSupport {
35
36
	private Set elementsListenedTo = new HashSet();
37
	
38
	private PropertyChangeListener listener;
39
40
	private String propertyName;
41
42
	/**
43
	 * Constructs a new instance.
44
	 * 
45
	 * @param listener is the callback that will be called
46
	 * 		when a <code>PropertyChangeEvent</code> is fired on any
47
	 * 		of the target objects.  Will only receive change events 
48
	 * 		when the provided <code>propertyName</code> changes.
49
	 * @param propertyName
50
	 */
51
	public ListenerSupport(final PropertyChangeListener listener,
52
			final String propertyName) {
53
		Assert.isNotNull(listener, "Listener cannot be null"); //$NON-NLS-1$
54
		Assert.isNotNull(propertyName, "Property name cannot be null"); //$NON-NLS-1$
55
56
		this.propertyName = propertyName;
57
		this.listener = new PropertyChangeListener() {
58
			public void propertyChange(PropertyChangeEvent evt) {
59
				if (propertyName.equals(evt.getPropertyName())) {
60
					listener.propertyChange(evt);
61
				}
62
			}
63
		};
64
	}
65
66
	/**
67
	 * Start listen to target (if it supports the JavaBean property change listener pattern)
68
	 * 
69
	 * @param target
70
	 */
71
	public void hookListener(Object target) {
72
		if (processListener(
73
				"addPropertyChangeListener", "Could not attach listener to ", target)) { //$NON-NLS-1$ //$NON-NLS-2$
74
			elementsListenedTo.add(new IdentityWrapper(target));
75
		}
76
	}
77
		
78
	/**
79
	 * Add listeners for new targets (those this instance of<code>ListenerSupport</code> does not 
80
	 * already listen to),
81
	 * Stop to listen to those object that this instance listen to and is one of the object in targets 
82
	 * 
83
	 * @param targets 
84
	 */
85
	public void setHookTargets(Object[] targets) {		
86
		Set elementsToUnhook = new HashSet(elementsListenedTo);
87
		if (targets!=null) {
88
			for (int i = 0; i < targets.length; i++) {
89
				Object newValue = targets[i];
90
				IdentityWrapper identityWrapper = new IdentityWrapper(newValue);
91
				if(!elementsToUnhook.remove(identityWrapper)) 				
92
					hookListener(newValue);
93
			}
94
		}
95
			
96
		for (Iterator it = elementsToUnhook.iterator(); it.hasNext();) {
97
			Object o = it.next();
98
			if (o.getClass()!=IdentityWrapper.class)
99
				o = new IdentityWrapper(o);
100
			elementsListenedTo.remove(o);
101
			unhookListener(o);
102
		}							
103
	}
104
	
105
	/**
106
	 * Stop listen to target
107
	 * 
108
	 * @param target
109
	 */
110
	public void unhookListener(Object target) {
111
		if (target.getClass() == IdentityWrapper.class)
112
			target = ((IdentityWrapper) target).unwrap();
113
114
		if (processListener(
115
				"removePropertyChangeListener", "Cound not remove listener from ", target)) { //$NON-NLS-1$//$NON-NLS-2$
116
			elementsListenedTo.remove(new IdentityWrapper(target));
117
		}
118
	}
119
	
120
	
121
	/**
122
	 * 
123
	 */
124
	public void dispose() {
125
		if (elementsListenedTo!=null) {
126
			Object[] targets = elementsListenedTo.toArray();		
127
			for (int i = 0; i < targets.length; i++) {		
128
				unhookListener(targets[i]);
129
			}			
130
			elementsListenedTo=null;
131
			listener=null;
132
		}
133
	}
134
	
135
	/**
136
	 * @return elements that were registred to
137
	 */
138
	public Object[] getHookedTargets() {
139
		Object[] targets = null;
140
		if (elementsListenedTo!=null && elementsListenedTo.size()>0) {
141
			Object[] identityList = elementsListenedTo.toArray();
142
			targets = new Object[identityList.length];
143
			for (int i = 0; i < identityList.length; i++) 
144
				targets[i]=((IdentityWrapper)identityList[i]).unwrap();							
145
		}
146
		return targets;
147
	}
148
149
	/**
150
	 * Invokes the method for the provided <code>methodName</code> attempting
151
	 * to first use the method with the property name and then the unnamed
152
	 * version.
153
	 * 
154
	 * @param methodName
155
	 *            either addPropertyChangeListener or
156
	 *            removePropertyChangeListener
157
	 * @param message
158
	 *            string that will be prefixed to the target in an error message
159
	 * @param target
160
	 *            object to invoke the method on
161
	 * @return <code>true</code> if the method was invoked successfully
162
	 */
163
	private boolean processListener(String methodName, String message,
164
			Object target) {
165
		Method method = null;
166
		Object[] parameters = null;
167
168
		try {
169
			try {
170
				method = target.getClass().getMethod(
171
						methodName,
172
						new Class[] { String.class,
173
								PropertyChangeListener.class });
174
175
				parameters = new Object[] { propertyName, listener };
176
			} catch (NoSuchMethodException e) {
177
				method = target.getClass().getMethod(methodName,
178
						new Class[] { PropertyChangeListener.class });
179
180
				parameters = new Object[] { listener };
181
			}
182
		} catch (SecurityException e) {
183
			// ignore
184
		} catch (NoSuchMethodException e) {
185
			log(IStatus.WARNING, message + target, e);
186
		}
187
188
		if (method != null) {
189
			if (!method.isAccessible()) {
190
				method.setAccessible(true);
191
			}
192
			try {
193
				method.invoke(target, parameters);
194
				return true;
195
			} catch (IllegalArgumentException e) {
196
				log(IStatus.WARNING, message + target, e);
197
			} catch (IllegalAccessException e) {
198
				log(IStatus.WARNING, message + target, e);
199
			} catch (InvocationTargetException e) {
200
				log(IStatus.WARNING, message + target, e);
201
			}
202
		}
203
		return false;
204
	}
205
206
	/**
207
	 * Logs a message to the Data Binding logger.
208
	 */
209
	private void log(int severity, String message, Throwable throwable) {
210
		if (BeansObservables.DEBUG) {
211
			Policy.getLog().log(
212
					new Status(severity, Policy.JFACE_DATABINDING, IStatus.OK,
213
							message, throwable));
214
		}
215
	}
216
}
(-)src/org/eclipse/core/internal/databinding/beans/JavaBeanObservableSet.java (-301 lines)
Removed Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2006-2008 IBM Corporation and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
10
 *     Brad Reynolds - bug 171616
11
 *     Matthew Hall - bugs 221351, 223164, 244098
12
 *******************************************************************************/
13
14
package org.eclipse.core.internal.databinding.beans;
15
16
import java.beans.PropertyChangeListener;
17
import java.beans.PropertyDescriptor;
18
import java.lang.reflect.Array;
19
import java.lang.reflect.InvocationTargetException;
20
import java.lang.reflect.Method;
21
import java.util.Arrays;
22
import java.util.Collection;
23
import java.util.Collections;
24
import java.util.HashSet;
25
import java.util.Iterator;
26
import java.util.Set;
27
28
import org.eclipse.core.databinding.BindingException;
29
import org.eclipse.core.databinding.beans.IBeanObservable;
30
import org.eclipse.core.databinding.observable.Diffs;
31
import org.eclipse.core.databinding.observable.Realm;
32
import org.eclipse.core.databinding.observable.set.ObservableSet;
33
import org.eclipse.core.runtime.Assert;
34
35
/**
36
 * @since 1.0
37
 * 
38
 */
39
public class JavaBeanObservableSet extends ObservableSet implements IBeanObservable {
40
41
	private final Object object;
42
43
	private boolean updating = false;
44
45
	private PropertyDescriptor descriptor;
46
47
	private ListenerSupport listenerSupport;
48
49
	/**
50
	 * @param realm
51
	 * @param object
52
	 * @param descriptor
53
	 * @param elementType
54
	 */
55
	public JavaBeanObservableSet(Realm realm, Object object,
56
			PropertyDescriptor descriptor, Class elementType) {
57
		this(realm, object, descriptor, elementType, true);
58
	}
59
60
	/**
61
	 * @param realm
62
	 * @param object
63
	 * @param descriptor
64
	 * @param elementType
65
	 * @param attachListeners
66
	 */
67
	public JavaBeanObservableSet(Realm realm, Object object,
68
			PropertyDescriptor descriptor, Class elementType,
69
			boolean attachListeners) {
70
		super(realm, new HashSet(), elementType);
71
		this.object = object;
72
		this.descriptor = descriptor;
73
		if (attachListeners) {
74
			PropertyChangeListener listener = new PropertyChangeListener() {
75
				public void propertyChange(java.beans.PropertyChangeEvent event) {
76
					if (!updating) {
77
						getRealm().exec(new Runnable() {
78
							public void run() {
79
								Set newElements = new HashSet(Arrays
80
										.asList(getValues()));
81
								Set addedElements = new HashSet(newElements);
82
								Set removedElements = new HashSet(wrappedSet);
83
								// remove all new elements from old elements to
84
								// compute
85
								// the removed elements
86
								removedElements.removeAll(newElements);
87
								addedElements.removeAll(wrappedSet);
88
								wrappedSet = newElements;
89
								fireSetChange(Diffs.createSetDiff(
90
										addedElements, removedElements));
91
							}
92
						});
93
					}
94
				}
95
			};
96
			this.listenerSupport = new ListenerSupport(listener, descriptor
97
					.getName());
98
			listenerSupport.hookListener(this.object);
99
		}
100
101
		wrappedSet.addAll(Arrays.asList(getValues()));
102
	}
103
104
	private Object primGetValues() {
105
		try {
106
			Method readMethod = descriptor.getReadMethod();
107
			if (!readMethod.isAccessible()) {
108
				readMethod.setAccessible(true);
109
			}
110
			return readMethod.invoke(object, new Object[0]);
111
		} catch (IllegalArgumentException e) {
112
		} catch (IllegalAccessException e) {
113
		} catch (InvocationTargetException e) {
114
		}
115
		Assert.isTrue(false, "Could not read collection values"); //$NON-NLS-1$
116
		return null;
117
	}
118
119
	private Object[] getValues() {
120
		Object[] values = null;
121
122
		Object result = primGetValues();
123
		if (descriptor.getPropertyType().isArray())
124
			values = (Object[]) result;
125
		else {
126
			// TODO add jUnit for POJO (var. SettableValue) collections
127
			Collection list = (Collection) result;
128
			if (list != null)
129
				values = list.toArray();
130
		}
131
		if (values == null)
132
			values = new Object[0];
133
		return values;
134
	}
135
136
	private void setValues() {
137
		if (descriptor.getPropertyType().isArray()) {
138
			Class componentType = descriptor.getPropertyType()
139
					.getComponentType();
140
			Object[] newArray = (Object[]) Array.newInstance(componentType,
141
					wrappedSet.size());
142
			wrappedSet.toArray(newArray);
143
			primSetValues(newArray);
144
		} else {
145
			// assume that it is a java.util.Set
146
			primSetValues(new HashSet(wrappedSet));
147
		}
148
	}
149
150
	public boolean add(Object o) {
151
		getterCalled();
152
		updating = true;
153
		try {
154
			boolean added = wrappedSet.add(o);
155
			if (added) {
156
				setValues();
157
				fireSetChange(Diffs.createSetDiff(Collections.singleton(o),
158
						Collections.EMPTY_SET));
159
			}
160
			return added;
161
		} finally {
162
			updating = false;
163
		}
164
	}
165
166
	public boolean remove(Object o) {
167
		getterCalled();
168
		updating = true;
169
		try {
170
			boolean removed = wrappedSet.remove(o);
171
			if (removed) {
172
				setValues();
173
				fireSetChange(Diffs.createSetDiff(Collections.EMPTY_SET,
174
						Collections.singleton(o)));
175
			}
176
			return removed;
177
		} finally {
178
			updating = false;
179
		}
180
	}
181
182
	public boolean addAll(Collection c) {
183
		getterCalled();
184
		updating = true;
185
		try {
186
			Set additions = new HashSet();
187
			for (Iterator iterator = c.iterator(); iterator.hasNext();) {
188
				Object element = iterator.next();
189
				if (wrappedSet.add(element))
190
					additions.add(element);
191
			}
192
			boolean changed = !additions.isEmpty();
193
			if (changed) {
194
				setValues();
195
				fireSetChange(Diffs.createSetDiff(additions,
196
						Collections.EMPTY_SET));
197
			}
198
			return changed;
199
		} finally {
200
			updating = false;
201
		}
202
	}
203
204
	public boolean removeAll(Collection c) {
205
		getterCalled();
206
		updating = true;
207
		try {
208
			Set removals = new HashSet();
209
			for (Iterator iterator = c.iterator(); iterator.hasNext();) {
210
				Object element = iterator.next();
211
				if (wrappedSet.remove(element))
212
					removals.add(element);
213
			}
214
			boolean changed = !removals.isEmpty();
215
			if (changed) {
216
				setValues();
217
				fireSetChange(Diffs.createSetDiff(Collections.EMPTY_SET,
218
						removals));
219
			}
220
			return changed;
221
		} finally {
222
			updating = false;
223
		}
224
	}
225
226
	public boolean retainAll(Collection c) {
227
		getterCalled();
228
		updating = true;
229
		try {
230
			Set removals = new HashSet();
231
			for (Iterator iterator = wrappedSet.iterator(); iterator.hasNext();) {
232
				Object element = iterator.next();
233
				if (!c.contains(element)) {
234
					iterator.remove();
235
					removals.add(element);
236
				}
237
			}
238
			boolean changed = !removals.isEmpty();
239
			if (changed) {
240
				setValues();
241
				fireSetChange(Diffs.createSetDiff(Collections.EMPTY_SET,
242
						removals));
243
			}
244
			return changed;
245
		} finally {
246
			updating = false;
247
		}
248
	}
249
250
	public void clear() {
251
		getterCalled();
252
		if (wrappedSet.isEmpty())
253
			return;
254
255
		updating = true;
256
		try {
257
			Set removals = new HashSet(wrappedSet);
258
			wrappedSet.clear();
259
			setValues();
260
			fireSetChange(Diffs.createSetDiff(Collections.EMPTY_SET, removals));
261
		} finally {
262
			updating = false;
263
		}
264
	}
265
266
	private void primSetValues(Object newValue) {
267
		Exception ex = null;
268
		try {
269
			Method writeMethod = descriptor.getWriteMethod();
270
			if (!writeMethod.isAccessible()) {
271
				writeMethod.setAccessible(true);
272
			}
273
			writeMethod.invoke(object, new Object[] { newValue });
274
			return;
275
		} catch (IllegalArgumentException e) {
276
			ex = e;
277
		} catch (IllegalAccessException e) {
278
			ex = e;
279
		} catch (InvocationTargetException e) {
280
			ex = e;
281
		}
282
		throw new BindingException("Could not write collection values", ex); //$NON-NLS-1$
283
	}
284
285
	public Object getObserved() {
286
		return object;
287
	}
288
289
	public PropertyDescriptor getPropertyDescriptor() {
290
		return descriptor;
291
	}
292
293
	public synchronized void dispose() {
294
		if (listenerSupport != null) {
295
			listenerSupport.dispose();
296
			listenerSupport = null;
297
		}
298
299
		super.dispose();
300
	}
301
}
(-)src/org/eclipse/core/internal/databinding/beans/JavaBeanObservableValue.java (-221 lines)
Removed Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2005, 2008 IBM Corporation and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
10
 *     Brad Reynolds - bug 164653
11
 *     Brad Reynolds - bug 164134, 171616
12
 *     Matthew Hall - bug 246103
13
 *******************************************************************************/
14
package org.eclipse.core.internal.databinding.beans;
15
16
import java.beans.PropertyChangeListener;
17
import java.beans.PropertyDescriptor;
18
import java.lang.reflect.InvocationTargetException;
19
import java.lang.reflect.Method;
20
21
import org.eclipse.core.databinding.BindingException;
22
import org.eclipse.core.databinding.beans.BeansObservables;
23
import org.eclipse.core.databinding.beans.IBeanObservable;
24
import org.eclipse.core.databinding.observable.Diffs;
25
import org.eclipse.core.databinding.observable.Realm;
26
import org.eclipse.core.databinding.observable.value.AbstractObservableValue;
27
import org.eclipse.core.databinding.util.Policy;
28
import org.eclipse.core.internal.databinding.Util;
29
import org.eclipse.core.runtime.IStatus;
30
import org.eclipse.core.runtime.Status;
31
32
/**
33
 * @since 1.0
34
 * 
35
 */
36
public class JavaBeanObservableValue extends AbstractObservableValue implements IBeanObservable {
37
	private final Object object;
38
	private boolean updating = false;
39
40
	private final PropertyDescriptor propertyDescriptor;
41
	private ListenerSupport listenerSupport;
42
43
	private boolean attachListeners;
44
45
	// Applicable only while hasListeners() == true
46
	private Object cachedValue;
47
48
	/**
49
	 * @param realm
50
	 * @param object
51
	 * @param descriptor
52
	 */
53
	public JavaBeanObservableValue(Realm realm, Object object,
54
			PropertyDescriptor descriptor) {
55
		this(realm, object, descriptor, true);
56
	}
57
58
	/**
59
	 * @param realm
60
	 * @param object
61
	 * @param descriptor
62
	 * @param attachListeners
63
	 */
64
	public JavaBeanObservableValue(Realm realm, Object object,
65
			PropertyDescriptor descriptor, boolean attachListeners) {
66
		super(realm);
67
		this.object = object;
68
		this.propertyDescriptor = descriptor;
69
		this.attachListeners = attachListeners;
70
	}
71
72
	protected void firstListenerAdded() {
73
		if (!attachListeners) {
74
			return;
75
		}
76
77
		if (listenerSupport == null) {
78
			PropertyChangeListener listener = new PropertyChangeListener() {
79
				public void propertyChange(
80
						final java.beans.PropertyChangeEvent event) {
81
					if (!updating) {
82
						getRealm().exec(new Runnable() {
83
							public void run() {
84
								Object oldValue = event.getOldValue();
85
								Object newValue = event.getNewValue();
86
								if (oldValue == null && newValue == null) {
87
									// this condition is provided for in the
88
									// bean spec, and indicates that an 
89
									// unknown change occured.
90
91
									oldValue = cachedValue;
92
									newValue = doGetValue();
93
								}
94
								cachedValue = newValue;
95
								if (!Util.equals(oldValue, newValue)) {
96
									fireValueChange(Diffs.createValueDiff(
97
											oldValue, newValue));
98
								}
99
							}
100
						});
101
					}
102
				}
103
			};
104
			listenerSupport = new ListenerSupport(listener, propertyDescriptor
105
					.getName());
106
		}
107
		
108
		listenerSupport.hookListener(object);
109
		cachedValue = doGetValue();
110
	}
111
112
	public void doSetValue(Object value) {
113
		updating = true;
114
		try {
115
			Object oldValue = doGetValue();
116
			
117
			if (!Util.equals(oldValue, value)) {
118
				Method writeMethod = propertyDescriptor.getWriteMethod();
119
				if (!writeMethod.isAccessible()) {
120
					writeMethod.setAccessible(true);
121
				}
122
				writeMethod.invoke(object, new Object[] { value });
123
			}
124
			
125
			if (hasListeners()) {
126
				// oldValue contains the live value which may be different from
127
				// the cached value if the bean does not have listener API or
128
				// does not fire events properly. For consistency we want to
129
				// provide the cached value as the old value, rather than the
130
				// live value so that consumers that hook/unhook listeners can
131
				// do so without maintaining caches of their own.
132
				oldValue = cachedValue;
133
				cachedValue = doGetValue();
134
				if (!Util.equals(oldValue, cachedValue)) {
135
					fireValueChange(Diffs
136
							.createValueDiff(oldValue, cachedValue));
137
				}
138
			}
139
		} catch (InvocationTargetException e) {
140
			/*
141
			 * InvocationTargetException wraps any exception thrown by the
142
			 * invoked method.
143
			 */
144
			throw new RuntimeException(e.getCause());
145
		} catch (Exception e) {
146
			if (BeansObservables.DEBUG) {
147
				Policy
148
						.getLog()
149
						.log(
150
								new Status(
151
										IStatus.WARNING,
152
										Policy.JFACE_DATABINDING,
153
										IStatus.OK,
154
										"Could not change value of " + object + "." + propertyDescriptor.getName(), e)); //$NON-NLS-1$ //$NON-NLS-2$
155
			}
156
		} finally {
157
			updating = false;
158
		}
159
	}
160
161
	public Object doGetValue() {
162
		try {
163
			Method readMethod = propertyDescriptor.getReadMethod();
164
			if (readMethod == null) {
165
				throw new BindingException(propertyDescriptor.getName()
166
						+ " property does not have a read method."); //$NON-NLS-1$
167
			}
168
			if (!readMethod.isAccessible()) {
169
				readMethod.setAccessible(true);
170
			}
171
			return readMethod.invoke(object, null);
172
		} catch (InvocationTargetException e) {
173
			/*
174
			 * InvocationTargetException wraps any exception thrown by the
175
			 * invoked method.
176
			 */
177
			throw new RuntimeException(e.getCause());
178
		} catch (Exception e) {
179
			if (BeansObservables.DEBUG) {
180
				Policy
181
						.getLog()
182
						.log(
183
								new Status(
184
										IStatus.WARNING,
185
										Policy.JFACE_DATABINDING,
186
										IStatus.OK,
187
										"Could not read value of " + object + "." + propertyDescriptor.getName(), e)); //$NON-NLS-1$ //$NON-NLS-2$
188
			}
189
			return null;
190
		}
191
	}
192
193
	protected void lastListenerRemoved() {
194
		unhookListener();
195
	}
196
197
	private void unhookListener() {
198
		cachedValue = null;
199
		if (listenerSupport != null) {
200
			listenerSupport.dispose();
201
			listenerSupport = null;
202
		}
203
	}
204
205
	public Object getValueType() {
206
		return propertyDescriptor.getPropertyType();
207
	}
208
209
	public Object getObserved() {
210
		return object;
211
	}
212
213
	public PropertyDescriptor getPropertyDescriptor() {
214
		return propertyDescriptor;
215
	}
216
217
	public synchronized void dispose() {
218
		unhookListener();
219
		super.dispose();
220
	}
221
}
(-)src/org/eclipse/core/databinding/beans/BeansObservables.java (-116 / +64 lines)
Lines 8-24 Link Here
8
 * Contributors:
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
9
 *     IBM Corporation - initial API and implementation
10
 *     Brad Reynolds - bugs 164268, 171616, 147515
10
 *     Brad Reynolds - bugs 164268, 171616, 147515
11
 *     Matthew Hall - bug 221704, 234686, 246625, 226289, 246782
11
 *     Matthew Hall - bug 221704, 234686, 246625, 226289, 246782, 194734
12
 *     Thomas Kratz - bug 213787
12
 *     Thomas Kratz - bug 213787
13
 *******************************************************************************/
13
 *******************************************************************************/
14
package org.eclipse.core.databinding.beans;
14
package org.eclipse.core.databinding.beans;
15
15
16
import java.beans.BeanInfo;
17
import java.beans.IntrospectionException;
18
import java.beans.Introspector;
19
import java.beans.PropertyDescriptor;
16
import java.beans.PropertyDescriptor;
20
17
21
import org.eclipse.core.databinding.BindingException;
22
import org.eclipse.core.databinding.observable.IObservable;
18
import org.eclipse.core.databinding.observable.IObservable;
23
import org.eclipse.core.databinding.observable.Realm;
19
import org.eclipse.core.databinding.observable.Realm;
24
import org.eclipse.core.databinding.observable.list.IObservableList;
20
import org.eclipse.core.databinding.observable.list.IObservableList;
Lines 27-43 Link Here
27
import org.eclipse.core.databinding.observable.masterdetail.MasterDetailObservables;
23
import org.eclipse.core.databinding.observable.masterdetail.MasterDetailObservables;
28
import org.eclipse.core.databinding.observable.set.IObservableSet;
24
import org.eclipse.core.databinding.observable.set.IObservableSet;
29
import org.eclipse.core.databinding.observable.value.IObservableValue;
25
import org.eclipse.core.databinding.observable.value.IObservableValue;
26
import org.eclipse.core.databinding.property.list.IListProperty;
27
import org.eclipse.core.databinding.property.map.IMapProperty;
28
import org.eclipse.core.databinding.property.set.ISetProperty;
29
import org.eclipse.core.databinding.property.value.IValueProperty;
30
import org.eclipse.core.databinding.util.Policy;
30
import org.eclipse.core.databinding.util.Policy;
31
import org.eclipse.core.internal.databinding.Util;
31
import org.eclipse.core.internal.databinding.Util;
32
import org.eclipse.core.internal.databinding.beans.BeanObservableListDecorator;
32
import org.eclipse.core.internal.databinding.beans.BeanObservableListDecorator;
33
import org.eclipse.core.internal.databinding.beans.BeanObservableMapDecorator;
33
import org.eclipse.core.internal.databinding.beans.BeanObservableMapDecorator;
34
import org.eclipse.core.internal.databinding.beans.BeanObservableSetDecorator;
34
import org.eclipse.core.internal.databinding.beans.BeanObservableSetDecorator;
35
import org.eclipse.core.internal.databinding.beans.BeanObservableValueDecorator;
35
import org.eclipse.core.internal.databinding.beans.BeanObservableValueDecorator;
36
import org.eclipse.core.internal.databinding.beans.JavaBeanObservableList;
36
import org.eclipse.core.internal.databinding.beans.BeanPropertyHelper;
37
import org.eclipse.core.internal.databinding.beans.JavaBeanObservableMap;
38
import org.eclipse.core.internal.databinding.beans.JavaBeanObservableSet;
39
import org.eclipse.core.internal.databinding.beans.JavaBeanObservableValue;
40
import org.eclipse.core.internal.databinding.beans.JavaBeanPropertyObservableMap;
41
import org.eclipse.core.runtime.Assert;
37
import org.eclipse.core.runtime.Assert;
42
import org.eclipse.core.runtime.IStatus;
38
import org.eclipse.core.runtime.IStatus;
43
import org.eclipse.core.runtime.Status;
39
import org.eclipse.core.runtime.Status;
Lines 87-95 Link Here
87
	 */
83
	 */
88
	public static IObservableValue observeValue(Realm realm, Object bean,
84
	public static IObservableValue observeValue(Realm realm, Object bean,
89
			String propertyName) {
85
			String propertyName) {
90
		PropertyDescriptor descriptor = getPropertyDescriptor(bean.getClass(),
86
		IValueProperty property = BeanProperties.value(bean.getClass(),
91
				propertyName);
87
				propertyName);
92
		return new JavaBeanObservableValue(realm, bean, descriptor);
88
		PropertyDescriptor propertyDescriptor = ((IBeanProperty) property)
89
				.getPropertyDescriptor();
90
		return new BeanObservableValueDecorator(property.observeValue(realm,
91
				bean), propertyDescriptor);
93
	}
92
	}
94
93
95
	/**
94
	/**
Lines 107-115 Link Here
107
	 */
106
	 */
108
	public static IObservableMap observeMap(IObservableSet domain,
107
	public static IObservableMap observeMap(IObservableSet domain,
109
			Class beanClass, String propertyName) {
108
			Class beanClass, String propertyName) {
110
		PropertyDescriptor descriptor = getPropertyDescriptor(beanClass,
109
		IValueProperty property = BeanProperties.value(beanClass,
111
				propertyName);
110
				propertyName);
112
		return new JavaBeanObservableMap(domain, descriptor);
111
		PropertyDescriptor propertyDescriptor = ((IBeanProperty) property)
112
				.getPropertyDescriptor();
113
		return new BeanObservableMapDecorator(property
114
				.observeDetailValues(domain), propertyDescriptor);
113
	}
115
	}
114
116
115
	/**
117
	/**
Lines 153-162 Link Here
153
	 */
155
	 */
154
	public static IObservableMap observeMap(Realm realm, Object bean,
156
	public static IObservableMap observeMap(Realm realm, Object bean,
155
			String propertyName, Class keyType, Class valueType) {
157
			String propertyName, Class keyType, Class valueType) {
156
		PropertyDescriptor descriptor = getPropertyDescriptor(bean.getClass(),
158
		IMapProperty property = BeanProperties.map(bean.getClass(),
157
				propertyName);
159
				propertyName, keyType, valueType);
158
		return new JavaBeanPropertyObservableMap(realm, bean, descriptor,
160
		PropertyDescriptor propertyDescriptor = ((IBeanProperty) property)
159
				keyType, valueType);
161
				.getPropertyDescriptor();
162
		return new BeanObservableMapDecorator(property.observeMap(realm, bean),
163
				propertyDescriptor);
160
	}
164
	}
161
165
162
	/**
166
	/**
Lines 193-221 Link Here
193
	 *         given bean object
197
	 *         given bean object
194
	 * @since 1.2
198
	 * @since 1.2
195
	 */
199
	 */
196
	public static IObservableMap observeMap(Object bean, String propertyName, Class keyType, Class valueType) {
200
	public static IObservableMap observeMap(Object bean, String propertyName,
197
		return observeMap(Realm.getDefault(), bean, propertyName, keyType, valueType);
201
			Class keyType, Class valueType) {
198
	}
202
		return observeMap(Realm.getDefault(), bean, propertyName, keyType,
199
203
				valueType);
200
	/*package*/ static PropertyDescriptor getPropertyDescriptor(Class beanClass,
201
			String propertyName) {
202
		BeanInfo beanInfo;
203
		try {
204
			beanInfo = Introspector.getBeanInfo(beanClass);
205
		} catch (IntrospectionException e) {
206
			// cannot introspect, give up
207
			return null;
208
		}
209
		PropertyDescriptor[] propertyDescriptors = beanInfo
210
				.getPropertyDescriptors();
211
		for (int i = 0; i < propertyDescriptors.length; i++) {
212
			PropertyDescriptor descriptor = propertyDescriptors[i];
213
			if (descriptor.getName().equals(propertyName)) {
214
				return descriptor;
215
			}
216
		}
217
		throw new BindingException(
218
				"Could not find property with name " + propertyName + " in class " + beanClass); //$NON-NLS-1$ //$NON-NLS-2$
219
	}
204
	}
220
205
221
	/**
206
	/**
Lines 283-291 Link Here
283
	 * collection-typed named property of the given bean object. The returned
268
	 * collection-typed named property of the given bean object. The returned
284
	 * list is mutable. When an item is added or removed the setter is invoked
269
	 * list is mutable. When an item is added or removed the setter is invoked
285
	 * for the list on the parent bean to provide notification to other
270
	 * for the list on the parent bean to provide notification to other
286
	 * listeners via <code>PropertyChangeEvents</code>. This is done to
271
	 * listeners via <code>PropertyChangeEvents</code>. This is done to provide
287
	 * provide the same behavior as is expected from arrays as specified in the
272
	 * the same behavior as is expected from arrays as specified in the bean
288
	 * bean spec in section 7.2.
273
	 * spec in section 7.2.
289
	 * 
274
	 * 
290
	 * @param realm
275
	 * @param realm
291
	 *            the realm
276
	 *            the realm
Lines 294-301 Link Here
294
	 * @param propertyName
279
	 * @param propertyName
295
	 *            the name of the property
280
	 *            the name of the property
296
	 * @param elementType
281
	 * @param elementType
297
	 *            type of the elements in the list. If <code>null</code> and
282
	 *            type of the elements in the list. If <code>null</code> and the
298
	 *            the property is an array the type will be inferred. If
283
	 *            property is an array the type will be inferred. If
299
	 *            <code>null</code> and the property type cannot be inferred
284
	 *            <code>null</code> and the property type cannot be inferred
300
	 *            element type will be <code>null</code>.
285
	 *            element type will be <code>null</code>.
301
	 * @return an observable list tracking the collection-typed named property
286
	 * @return an observable list tracking the collection-typed named property
Lines 303-314 Link Here
303
	 */
288
	 */
304
	public static IObservableList observeList(Realm realm, Object bean,
289
	public static IObservableList observeList(Realm realm, Object bean,
305
			String propertyName, Class elementType) {
290
			String propertyName, Class elementType) {
306
		PropertyDescriptor propertyDescriptor = getPropertyDescriptor(bean
291
		IListProperty property = BeanProperties.list(bean.getClass(),
307
				.getClass(), propertyName);
292
				propertyName, elementType);
308
		elementType = getCollectionElementType(elementType, propertyDescriptor);
293
		PropertyDescriptor propertyDescriptor = ((IBeanProperty) property)
309
294
				.getPropertyDescriptor();
310
		return new JavaBeanObservableList(realm, bean, propertyDescriptor,
295
		return new BeanObservableListDecorator(property
311
				elementType);
296
				.observeList(realm, bean), propertyDescriptor);
312
	}
297
	}
313
298
314
	/**
299
	/**
Lines 495-504 Link Here
495
480
496
		IObservableValue value = MasterDetailObservables.detailValue(master,
481
		IObservableValue value = MasterDetailObservables.detailValue(master,
497
				valueFactory(realm, propertyName), propertyType);
482
				valueFactory(realm, propertyName), propertyType);
498
		BeanObservableValueDecorator decorator = new BeanObservableValueDecorator(
483
		return new BeanObservableValueDecorator(value, BeanPropertyHelper
499
				value, getValueTypePropertyDescriptor(master, propertyName));
484
				.getValueTypePropertyDescriptor(master, propertyName));
500
501
		return decorator;
502
	}
485
	}
503
486
504
	/* package */static void warnIfDifferentRealms(Realm detailRealm,
487
	/* package */static void warnIfDifferentRealms(Realm detailRealm,
Lines 538-547 Link Here
538
	/**
521
	/**
539
	 * Helper method for
522
	 * Helper method for
540
	 * <code>MasterDetailObservables.detailValue(master, valueFactory(realm,
523
	 * <code>MasterDetailObservables.detailValue(master, valueFactory(realm,
541
	 * propertyName), propertyType)</code>.
524
	 * propertyName), propertyType)</code>. This method returns an
542
	 * This method returns an {@link IBeanObservable} with a
525
	 * {@link IBeanObservable} with a {@link PropertyDescriptor} based on the
543
	 * {@link PropertyDescriptor} based on the given master type and property
526
	 * given master type and property name.
544
	 * name.
545
	 * 
527
	 * 
546
	 * @param realm
528
	 * @param realm
547
	 *            the realm
529
	 *            the realm
Lines 564-578 Link Here
564
	 *             instead.
546
	 *             instead.
565
	 */
547
	 */
566
	public static IObservableValue observeDetailValue(Realm realm,
548
	public static IObservableValue observeDetailValue(Realm realm,
567
			IObservableValue master, Class masterType, String propertyName, Class propertyType) {
549
			IObservableValue master, Class masterType, String propertyName,
550
			Class propertyType) {
568
		warnIfDifferentRealms(realm, master.getRealm());
551
		warnIfDifferentRealms(realm, master.getRealm());
569
		Assert.isNotNull(masterType, "masterType cannot be null"); //$NON-NLS-1$
552
		Assert.isNotNull(masterType, "masterType cannot be null"); //$NON-NLS-1$
570
		IObservableValue value = MasterDetailObservables.detailValue(master,
553
		IObservableValue value = MasterDetailObservables.detailValue(master,
571
				valueFactory(realm, propertyName), propertyType);
554
				valueFactory(realm, propertyName), propertyType);
572
		BeanObservableValueDecorator decorator = new BeanObservableValueDecorator(
555
		return new BeanObservableValueDecorator(value, BeanPropertyHelper
573
				value, getPropertyDescriptor(masterType, propertyName));
556
				.getPropertyDescriptor(masterType, propertyName));
574
575
		return decorator;
576
	}
557
	}
577
558
578
	/**
559
	/**
Lines 627-637 Link Here
627
		IObservableList observableList = MasterDetailObservables.detailList(
608
		IObservableList observableList = MasterDetailObservables.detailList(
628
				master, listFactory(realm, propertyName, propertyType),
609
				master, listFactory(realm, propertyName, propertyType),
629
				propertyType);
610
				propertyType);
630
		BeanObservableListDecorator decorator = new BeanObservableListDecorator(
611
		return new BeanObservableListDecorator(observableList,
631
				observableList, getValueTypePropertyDescriptor(master,
612
				BeanPropertyHelper.getValueTypePropertyDescriptor(master,
632
						propertyName));
613
						propertyName));
633
634
		return decorator;
635
	}
614
	}
636
615
637
	/**
616
	/**
Lines 679-689 Link Here
679
		IObservableSet observableSet = MasterDetailObservables.detailSet(
658
		IObservableSet observableSet = MasterDetailObservables.detailSet(
680
				master, setFactory(realm, propertyName, propertyType),
659
				master, setFactory(realm, propertyName, propertyType),
681
				propertyType);
660
				propertyType);
682
		BeanObservableSetDecorator decorator = new BeanObservableSetDecorator(
661
		return new BeanObservableSetDecorator(observableSet, BeanPropertyHelper
683
				observableSet, getValueTypePropertyDescriptor(master,
662
				.getValueTypePropertyDescriptor(master, propertyName));
684
						propertyName));
685
686
		return decorator;
687
	}
663
	}
688
664
689
	/**
665
	/**
Lines 725-734 Link Here
725
		warnIfDifferentRealms(realm, master.getRealm());
701
		warnIfDifferentRealms(realm, master.getRealm());
726
		IObservableMap observableMap = MasterDetailObservables.detailMap(
702
		IObservableMap observableMap = MasterDetailObservables.detailMap(
727
				master, mapPropertyFactory(realm, propertyName));
703
				master, mapPropertyFactory(realm, propertyName));
728
		BeanObservableMapDecorator decorator = new BeanObservableMapDecorator(
704
		return new BeanObservableMapDecorator(observableMap, BeanPropertyHelper
729
				observableMap, getValueTypePropertyDescriptor(master,
705
				.getValueTypePropertyDescriptor(master, propertyName));
730
						propertyName));
731
		return decorator;
732
	}
706
	}
733
707
734
	/**
708
	/**
Lines 771-782 Link Here
771
	 */
745
	 */
772
	public static IObservableSet observeSet(Realm realm, Object bean,
746
	public static IObservableSet observeSet(Realm realm, Object bean,
773
			String propertyName, Class elementType) {
747
			String propertyName, Class elementType) {
774
		PropertyDescriptor propertyDescriptor = getPropertyDescriptor(bean
748
		ISetProperty property = BeanProperties.set(bean.getClass(),
775
				.getClass(), propertyName);
749
				propertyName, elementType);
776
		elementType = getCollectionElementType(elementType, propertyDescriptor);
750
		PropertyDescriptor propertyDescriptor = ((IBeanProperty) property)
777
751
				.getPropertyDescriptor();
778
		return new JavaBeanObservableSet(realm, bean, propertyDescriptor,
752
		return new BeanObservableSetDecorator(property.observeSet(realm, bean),
779
				elementType);
753
				propertyDescriptor);
780
	}
754
	}
781
755
782
	/**
756
	/**
Lines 863-879 Link Here
863
	 * @param propertyName
837
	 * @param propertyName
864
	 *            the name of the property
838
	 *            the name of the property
865
	 * @return a factory for creating {@link IObservableMap} objects
839
	 * @return a factory for creating {@link IObservableMap} objects
866
	 *
840
	 * 
867
	 * @since 1.1
841
	 * @since 1.1
868
	 */
842
	 */
869
	public static IObservableFactory setToMapFactory(final Class beanClass, final String propertyName) {
843
	public static IObservableFactory setToMapFactory(final Class beanClass,
844
			final String propertyName) {
870
		return new IObservableFactory() {
845
		return new IObservableFactory() {
871
			public IObservable createObservable(Object target) {
846
			public IObservable createObservable(Object target) {
872
				return observeMap((IObservableSet) target, beanClass, propertyName);
847
				return observeMap((IObservableSet) target, beanClass,
848
						propertyName);
873
			}
849
			}
874
		};
850
		};
875
	}
851
	}
876
	
852
877
	/**
853
	/**
878
	 * Returns a factory for creating an observable map. The factory, when
854
	 * Returns a factory for creating an observable map. The factory, when
879
	 * provided with a bean object, will create an {@link IObservableMap} in the
855
	 * provided with a bean object, will create an {@link IObservableMap} in the
Lines 911-942 Link Here
911
	public static IObservableFactory mapPropertyFactory(String propertyName) {
887
	public static IObservableFactory mapPropertyFactory(String propertyName) {
912
		return mapPropertyFactory(Realm.getDefault(), propertyName);
888
		return mapPropertyFactory(Realm.getDefault(), propertyName);
913
	}
889
	}
914
915
	/**
916
	 * @param elementType
917
	 *            can be <code>null</code>
918
	 * @param propertyDescriptor
919
	 * @return type of the items in a collection/array property
920
	 */
921
	/*package*/ static Class getCollectionElementType(Class elementType,
922
			PropertyDescriptor propertyDescriptor) {
923
		if (elementType == null) {
924
			Class propertyType = propertyDescriptor.getPropertyType();
925
			elementType = propertyType.isArray() ? propertyType
926
					.getComponentType() : Object.class;
927
		}
928
929
		return elementType;
930
	}
931
932
	/**
933
	 * @param observable
934
	 * @param propertyName
935
	 * @return property descriptor or <code>null</code>
936
	 */
937
	/* package*/ static PropertyDescriptor getValueTypePropertyDescriptor(
938
			IObservableValue observable, String propertyName) {
939
		return (observable.getValueType() != null) ? getPropertyDescriptor(
940
				(Class) observable.getValueType(), propertyName) : null;
941
	}
942
}
890
}
(-)src/org/eclipse/core/databinding/beans/PojoObservables.java (-55 / +51 lines)
Lines 7-13 Link Here
7
 *
7
 *
8
 * Contributors:
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
9
 *     IBM Corporation - initial API and implementation
10
 *     Matthew Hall - bugs 221704, 234686, 246625, 226289, 246782
10
 *     Matthew Hall - bugs 221704, 234686, 246625, 226289, 246782, 194734
11
 *******************************************************************************/
11
 *******************************************************************************/
12
12
13
package org.eclipse.core.databinding.beans;
13
package org.eclipse.core.databinding.beans;
Lines 23-37 Link Here
23
import org.eclipse.core.databinding.observable.masterdetail.MasterDetailObservables;
23
import org.eclipse.core.databinding.observable.masterdetail.MasterDetailObservables;
24
import org.eclipse.core.databinding.observable.set.IObservableSet;
24
import org.eclipse.core.databinding.observable.set.IObservableSet;
25
import org.eclipse.core.databinding.observable.value.IObservableValue;
25
import org.eclipse.core.databinding.observable.value.IObservableValue;
26
import org.eclipse.core.databinding.property.list.IListProperty;
27
import org.eclipse.core.databinding.property.map.IMapProperty;
28
import org.eclipse.core.databinding.property.set.ISetProperty;
29
import org.eclipse.core.databinding.property.value.IValueProperty;
26
import org.eclipse.core.internal.databinding.beans.BeanObservableListDecorator;
30
import org.eclipse.core.internal.databinding.beans.BeanObservableListDecorator;
27
import org.eclipse.core.internal.databinding.beans.BeanObservableMapDecorator;
31
import org.eclipse.core.internal.databinding.beans.BeanObservableMapDecorator;
28
import org.eclipse.core.internal.databinding.beans.BeanObservableSetDecorator;
32
import org.eclipse.core.internal.databinding.beans.BeanObservableSetDecorator;
29
import org.eclipse.core.internal.databinding.beans.BeanObservableValueDecorator;
33
import org.eclipse.core.internal.databinding.beans.BeanObservableValueDecorator;
30
import org.eclipse.core.internal.databinding.beans.JavaBeanObservableList;
34
import org.eclipse.core.internal.databinding.beans.BeanPropertyHelper;
31
import org.eclipse.core.internal.databinding.beans.JavaBeanObservableMap;
32
import org.eclipse.core.internal.databinding.beans.JavaBeanObservableSet;
33
import org.eclipse.core.internal.databinding.beans.JavaBeanObservableValue;
34
import org.eclipse.core.internal.databinding.beans.JavaBeanPropertyObservableMap;
35
35
36
/**
36
/**
37
 * A factory for creating observable objects for POJOs (plain old java objects)
37
 * A factory for creating observable objects for POJOs (plain old java objects)
Lines 73-82 Link Here
73
	 */
73
	 */
74
	public static IObservableValue observeValue(Realm realm, Object pojo,
74
	public static IObservableValue observeValue(Realm realm, Object pojo,
75
			String propertyName) {
75
			String propertyName) {
76
76
		IValueProperty property = PojoProperties.value(pojo.getClass(),
77
		PropertyDescriptor descriptor = BeansObservables.getPropertyDescriptor(
77
				propertyName);
78
				pojo.getClass(), propertyName);
78
		PropertyDescriptor propertyDescriptor = ((IBeanProperty) property)
79
		return new JavaBeanObservableValue(realm, pojo, descriptor, false);
79
				.getPropertyDescriptor();
80
		return new BeanObservableValueDecorator(property.observeValue(realm,
81
				pojo), propertyDescriptor);
80
	}
82
	}
81
83
82
	/**
84
	/**
Lines 94-102 Link Here
94
	 */
96
	 */
95
	public static IObservableMap observeMap(IObservableSet domain,
97
	public static IObservableMap observeMap(IObservableSet domain,
96
			Class pojoClass, String propertyName) {
98
			Class pojoClass, String propertyName) {
97
		PropertyDescriptor descriptor = BeansObservables.getPropertyDescriptor(
99
		IValueProperty property = PojoProperties.value(pojoClass,
98
				pojoClass, propertyName);
100
				propertyName);
99
		return new JavaBeanObservableMap(domain, descriptor, false);
101
		PropertyDescriptor propertyDescriptor = ((IBeanProperty) property)
102
				.getPropertyDescriptor();
103
		return new BeanObservableMapDecorator(property
104
				.observeDetailValues(domain), propertyDescriptor);
100
	}
105
	}
101
106
102
	/**
107
	/**
Lines 161-170 Link Here
161
	 */
166
	 */
162
	public static IObservableMap observeMap(Realm realm, Object pojo,
167
	public static IObservableMap observeMap(Realm realm, Object pojo,
163
			String propertyName, Class keyType, Class valueType) {
168
			String propertyName, Class keyType, Class valueType) {
164
		PropertyDescriptor descriptor = BeansObservables.getPropertyDescriptor(
169
		IMapProperty property = PojoProperties.map(pojo.getClass(),
165
				pojo.getClass(), propertyName);
170
				propertyName, keyType, valueType);
166
		return new JavaBeanPropertyObservableMap(realm, pojo, descriptor,
171
		PropertyDescriptor propertyDescriptor = ((IBeanProperty) property)
167
				keyType, valueType, false);
172
				.getPropertyDescriptor();
173
		return new BeanObservableMapDecorator(property.observeMap(realm, pojo),
174
				propertyDescriptor);
168
	}
175
	}
169
176
170
	/**
177
	/**
Lines 250-258 Link Here
250
	 * collection-typed named property of the given bean object. The returned
257
	 * collection-typed named property of the given bean object. The returned
251
	 * list is mutable. When an item is added or removed the setter is invoked
258
	 * list is mutable. When an item is added or removed the setter is invoked
252
	 * for the list on the parent bean to provide notification to other
259
	 * for the list on the parent bean to provide notification to other
253
	 * listeners via <code>PropertyChangeEvents</code>. This is done to
260
	 * listeners via <code>PropertyChangeEvents</code>. This is done to provide
254
	 * provide the same behavior as is expected from arrays as specified in the
261
	 * the same behavior as is expected from arrays as specified in the bean
255
	 * bean spec in section 7.2.
262
	 * spec in section 7.2.
256
	 * 
263
	 * 
257
	 * @param realm
264
	 * @param realm
258
	 *            the realm
265
	 *            the realm
Lines 261-268 Link Here
261
	 * @param propertyName
268
	 * @param propertyName
262
	 *            the name of the property
269
	 *            the name of the property
263
	 * @param elementType
270
	 * @param elementType
264
	 *            type of the elements in the list. If <code>null</code> and
271
	 *            type of the elements in the list. If <code>null</code> and the
265
	 *            the property is an array the type will be inferred. If
272
	 *            property is an array the type will be inferred. If
266
	 *            <code>null</code> and the property type cannot be inferred
273
	 *            <code>null</code> and the property type cannot be inferred
267
	 *            element type will be <code>null</code>.
274
	 *            element type will be <code>null</code>.
268
	 * @return an observable list tracking the collection-typed named property
275
	 * @return an observable list tracking the collection-typed named property
Lines 270-282 Link Here
270
	 */
277
	 */
271
	public static IObservableList observeList(Realm realm, Object pojo,
278
	public static IObservableList observeList(Realm realm, Object pojo,
272
			String propertyName, Class elementType) {
279
			String propertyName, Class elementType) {
273
		PropertyDescriptor propertyDescriptor = BeansObservables
280
		IListProperty property = PojoProperties.list(pojo.getClass(),
274
				.getPropertyDescriptor(pojo.getClass(), propertyName);
281
				propertyName, elementType);
275
		elementType = BeansObservables.getCollectionElementType(elementType,
282
		PropertyDescriptor propertyDescriptor = ((IBeanProperty) property)
276
				propertyDescriptor);
283
				.getPropertyDescriptor();
277
284
		return new BeanObservableListDecorator(property
278
		return new JavaBeanObservableList(realm, pojo, propertyDescriptor,
285
				.observeList(realm, pojo), propertyDescriptor);
279
				elementType, false);
280
	}
286
	}
281
287
282
	/**
288
	/**
Lines 360-372 Link Here
360
	 */
366
	 */
361
	public static IObservableSet observeSet(Realm realm, Object pojo,
367
	public static IObservableSet observeSet(Realm realm, Object pojo,
362
			String propertyName, Class elementType) {
368
			String propertyName, Class elementType) {
363
		PropertyDescriptor propertyDescriptor = BeansObservables
369
		ISetProperty property = PojoProperties.set(pojo.getClass(),
364
				.getPropertyDescriptor(pojo.getClass(), propertyName);
370
				propertyName, elementType);
365
		elementType = BeansObservables.getCollectionElementType(elementType,
371
		PropertyDescriptor propertyDescriptor = ((IBeanProperty) property)
372
				.getPropertyDescriptor();
373
		return new BeanObservableSetDecorator(property.observeSet(realm, pojo),
366
				propertyDescriptor);
374
				propertyDescriptor);
367
368
		return new JavaBeanObservableSet(realm, pojo, propertyDescriptor,
369
				elementType, false);
370
	}
375
	}
371
376
372
	/**
377
	/**
Lines 594-604 Link Here
594
599
595
		IObservableValue value = MasterDetailObservables.detailValue(master,
600
		IObservableValue value = MasterDetailObservables.detailValue(master,
596
				valueFactory(realm, propertyName), propertyType);
601
				valueFactory(realm, propertyName), propertyType);
597
		BeanObservableValueDecorator decorator = new BeanObservableValueDecorator(
602
		return new BeanObservableValueDecorator(value, BeanPropertyHelper
598
				value, BeansObservables.getValueTypePropertyDescriptor(master,
603
				.getValueTypePropertyDescriptor(master, propertyName));
599
						propertyName));
600
601
		return decorator;
602
	}
604
	}
603
605
604
	/**
606
	/**
Lines 645-655 Link Here
645
		IObservableList observableList = MasterDetailObservables.detailList(
647
		IObservableList observableList = MasterDetailObservables.detailList(
646
				master, listFactory(realm, propertyName, propertyType),
648
				master, listFactory(realm, propertyName, propertyType),
647
				propertyType);
649
				propertyType);
648
		BeanObservableListDecorator decorator = new BeanObservableListDecorator(
650
		return new BeanObservableListDecorator(observableList,
649
				observableList, BeansObservables
651
				BeanPropertyHelper.getValueTypePropertyDescriptor(master,
650
						.getValueTypePropertyDescriptor(master, propertyName));
652
						propertyName));
651
652
		return decorator;
653
	}
653
	}
654
654
655
	/**
655
	/**
Lines 697-707 Link Here
697
		IObservableSet observableSet = MasterDetailObservables.detailSet(
697
		IObservableSet observableSet = MasterDetailObservables.detailSet(
698
				master, setFactory(realm, propertyName, propertyType),
698
				master, setFactory(realm, propertyName, propertyType),
699
				propertyType);
699
				propertyType);
700
		BeanObservableSetDecorator decorator = new BeanObservableSetDecorator(
700
		return new BeanObservableSetDecorator(observableSet, BeanPropertyHelper
701
				observableSet, BeansObservables.getValueTypePropertyDescriptor(
701
				.getValueTypePropertyDescriptor(master, propertyName));
702
						master, propertyName));
703
704
		return decorator;
705
	}
702
	}
706
703
707
	/**
704
	/**
Lines 733-749 Link Here
733
	 * @param propertyName
730
	 * @param propertyName
734
	 * @return an observable map that tracks the map-type named property for the
731
	 * @return an observable map that tracks the map-type named property for the
735
	 *         current value of the master observable value.
732
	 *         current value of the master observable value.
736
	 * @deprecated Use {@link #observeDetailMap(IObservableValue, String)} instead
733
	 * @deprecated Use {@link #observeDetailMap(IObservableValue, String)}
734
	 *             instead
737
	 */
735
	 */
738
	public static IObservableMap observeDetailMap(Realm realm,
736
	public static IObservableMap observeDetailMap(Realm realm,
739
			IObservableValue master, String propertyName) {
737
			IObservableValue master, String propertyName) {
740
		BeansObservables.warnIfDifferentRealms(realm, master.getRealm());
738
		BeansObservables.warnIfDifferentRealms(realm, master.getRealm());
741
		IObservableMap observableMap = MasterDetailObservables.detailMap(
739
		IObservableMap observableMap = MasterDetailObservables.detailMap(
742
				master, mapPropertyFactory(realm, propertyName));
740
				master, mapPropertyFactory(realm, propertyName));
743
		BeanObservableMapDecorator decorator = new BeanObservableMapDecorator(
741
		return new BeanObservableMapDecorator(observableMap, BeanPropertyHelper
744
				observableMap, BeansObservables.getValueTypePropertyDescriptor(
742
				.getValueTypePropertyDescriptor(master, propertyName));
745
						master, propertyName));
746
		return decorator;
747
	}
743
	}
748
744
749
	/**
745
	/**
(-)src/org/eclipse/core/internal/databinding/beans/PojoMapProperty.java (+91 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.internal.databinding.beans;
13
14
import java.beans.PropertyDescriptor;
15
import java.util.Collections;
16
import java.util.HashMap;
17
import java.util.Map;
18
19
import org.eclipse.core.databinding.beans.IBeanProperty;
20
import org.eclipse.core.databinding.observable.map.MapDiff;
21
import org.eclipse.core.databinding.property.INativePropertyListener;
22
import org.eclipse.core.databinding.property.map.IMapPropertyChangeListener;
23
import org.eclipse.core.databinding.property.map.SimpleMapProperty;
24
25
/**
26
 * @since 3.3
27
 * 
28
 */
29
public class PojoMapProperty extends SimpleMapProperty implements IBeanProperty {
30
	private PropertyDescriptor propertyDescriptor;
31
32
	/**
33
	 * @param propertyDescriptor
34
	 * @param keyType
35
	 * @param valueType
36
	 */
37
	public PojoMapProperty(PropertyDescriptor propertyDescriptor,
38
			Class keyType, Class valueType) {
39
		super(keyType, valueType);
40
		this.propertyDescriptor = propertyDescriptor;
41
	}
42
43
	protected Map doGetMap(Object source) {
44
		if (source == null)
45
			return Collections.EMPTY_MAP;
46
		Object propertyValue = BeanPropertyHelper.readProperty(source,
47
				propertyDescriptor);
48
		return asMap(propertyValue);
49
	}
50
51
	private Map asMap(Object propertyValue) {
52
		if (propertyValue == null)
53
			return new HashMap();
54
		return (Map) propertyValue;
55
	}
56
57
	protected void setMap(Object source, Map map, MapDiff diff) {
58
		if (source != null) {
59
			BeanPropertyHelper.writeProperty(source, propertyDescriptor, map);
60
		}
61
	}
62
63
	public PropertyDescriptor getPropertyDescriptor() {
64
		return propertyDescriptor;
65
	}
66
67
	public INativePropertyListener adaptListener(
68
			IMapPropertyChangeListener listener) {
69
		return null;
70
	}
71
72
	public void addListener(Object source, INativePropertyListener listener) {
73
	}
74
75
	public void removeListener(Object source, INativePropertyListener listener) {
76
	}
77
78
	public String toString() {
79
		Class beanClass = propertyDescriptor.getReadMethod()
80
				.getDeclaringClass();
81
		String propertyName = propertyDescriptor.getName();
82
		String s = beanClass.getName() + "." + propertyName + "{:}"; //$NON-NLS-1$ //$NON-NLS-2$
83
84
		Class keyType = (Class) getKeyType();
85
		Class valueType = (Class) getValueType();
86
		if (keyType != null || valueType != null) {
87
			s += " <" + keyType + ", " + valueType + ">"; //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$
88
		}
89
		return s;
90
	}
91
}
(-)src/org/eclipse/core/internal/databinding/beans/BeanMapProperty.java (+131 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.internal.databinding.beans;
13
14
import java.beans.PropertyChangeEvent;
15
import java.beans.PropertyChangeListener;
16
import java.beans.PropertyDescriptor;
17
import java.util.Collections;
18
import java.util.HashMap;
19
import java.util.Map;
20
21
import org.eclipse.core.databinding.beans.IBeanProperty;
22
import org.eclipse.core.databinding.observable.Diffs;
23
import org.eclipse.core.databinding.observable.map.MapDiff;
24
import org.eclipse.core.databinding.property.INativePropertyListener;
25
import org.eclipse.core.databinding.property.map.IMapPropertyChangeListener;
26
import org.eclipse.core.databinding.property.map.MapPropertyChangeEvent;
27
import org.eclipse.core.databinding.property.map.SimpleMapProperty;
28
29
/**
30
 * @since 3.3
31
 * 
32
 */
33
public class BeanMapProperty extends SimpleMapProperty implements IBeanProperty {
34
	private PropertyDescriptor propertyDescriptor;
35
36
	/**
37
	 * @param propertyDescriptor
38
	 * @param keyType
39
	 * @param valueType
40
	 */
41
	public BeanMapProperty(PropertyDescriptor propertyDescriptor,
42
			Class keyType, Class valueType) {
43
		super(keyType, valueType);
44
		this.propertyDescriptor = propertyDescriptor;
45
	}
46
47
	protected Map doGetMap(Object source) {
48
		if (source == null)
49
			return Collections.EMPTY_MAP;
50
		Object propertyValue = BeanPropertyHelper.readProperty(source,
51
				propertyDescriptor);
52
		return asMap(propertyValue);
53
	}
54
55
	private Map asMap(Object propertyValue) {
56
		if (propertyValue == null)
57
			return new HashMap();
58
		return (Map) propertyValue;
59
	}
60
61
	protected void setMap(Object source, Map map, MapDiff diff) {
62
		if (source != null) {
63
			BeanPropertyHelper.writeProperty(source, propertyDescriptor, map);
64
		}
65
	}
66
67
	public PropertyDescriptor getPropertyDescriptor() {
68
		return propertyDescriptor;
69
	}
70
71
	public INativePropertyListener adaptListener(
72
			final IMapPropertyChangeListener listener) {
73
		return new Listener(listener);
74
	}
75
76
	private class Listener implements INativePropertyListener,
77
			PropertyChangeListener {
78
		private final IMapPropertyChangeListener listener;
79
80
		private Listener(IMapPropertyChangeListener listener) {
81
			this.listener = listener;
82
		}
83
84
		public void propertyChange(PropertyChangeEvent evt) {
85
			if (propertyDescriptor.getName().equals(evt.getPropertyName())) {
86
				Object oldValue = evt.getOldValue();
87
				Object newValue = evt.getNewValue();
88
89
				MapDiff diff;
90
				if (oldValue == null && newValue == null) {
91
					diff = null; // unknown change
92
				} else {
93
					diff = Diffs.computeMapDiff(asMap(oldValue),
94
							asMap(newValue));
95
				}
96
97
				listener.handleMapPropertyChange(new MapPropertyChangeEvent(evt
98
						.getSource(), BeanMapProperty.this, diff));
99
			}
100
		}
101
	}
102
103
	public void addListener(Object source, INativePropertyListener listener) {
104
		if (source != null) {
105
			BeanPropertyListenerSupport.hookListener(source, propertyDescriptor
106
					.getName(), (PropertyChangeListener) listener);
107
		}
108
	}
109
110
	public void removeListener(Object source, INativePropertyListener listener) {
111
		if (source != null) {
112
			BeanPropertyListenerSupport.unhookListener(source,
113
					propertyDescriptor.getName(),
114
					(PropertyChangeListener) listener);
115
		}
116
	}
117
118
	public String toString() {
119
		Class beanClass = propertyDescriptor.getReadMethod()
120
				.getDeclaringClass();
121
		String propertyName = propertyDescriptor.getName();
122
		String s = beanClass.getName() + "." + propertyName + "{:}"; //$NON-NLS-1$ //$NON-NLS-2$
123
124
		Class keyType = (Class) getKeyType();
125
		Class valueType = (Class) getValueType();
126
		if (keyType != null || valueType != null) {
127
			s += " <" + keyType + ", " + valueType + ">"; //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$
128
		}
129
		return s;
130
	}
131
}
(-)src/org/eclipse/core/databinding/beans/PojoProperties.java (+157 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.databinding.beans;
13
14
import java.beans.PropertyChangeEvent;
15
16
import org.eclipse.core.databinding.property.list.IListProperty;
17
import org.eclipse.core.databinding.property.map.IMapProperty;
18
import org.eclipse.core.databinding.property.set.ISetProperty;
19
import org.eclipse.core.databinding.property.value.IValueProperty;
20
import org.eclipse.core.internal.databinding.beans.BeanPropertyHelper;
21
import org.eclipse.core.internal.databinding.beans.PojoListProperty;
22
import org.eclipse.core.internal.databinding.beans.PojoMapProperty;
23
import org.eclipse.core.internal.databinding.beans.PojoSetProperty;
24
import org.eclipse.core.internal.databinding.beans.PojoValueProperty;
25
26
/**
27
 * A factory for creating properties for POJOs (plain old java objects) that
28
 * conform to idea of an object with getters and setters but does not provide
29
 * {@link PropertyChangeEvent property change events} on change. This factory is
30
 * identical to {@link BeanProperties} except for this fact.
31
 * 
32
 * @since 1.2
33
 */
34
public class PojoProperties {
35
	/**
36
	 * Returns a value property for the given property name of the given bean
37
	 * class.
38
	 * 
39
	 * @param beanClass
40
	 *            the bean class
41
	 * @param propertyName
42
	 *            the property name
43
	 * @return a value property for the given property name of the given bean
44
	 *         class.
45
	 */
46
	public static IValueProperty value(Class beanClass, String propertyName) {
47
		return value(beanClass, propertyName, null);
48
	}
49
50
	/**
51
	 * Returns a value property for the given property name of the given bean
52
	 * class.
53
	 * 
54
	 * @param beanClass
55
	 *            the bean class
56
	 * @param propertyName
57
	 *            the property name
58
	 * @param valueType
59
	 *            the value type of the returned value property
60
	 * @return a value property for the given property name of the given bean
61
	 *         class.
62
	 */
63
	public static IValueProperty value(Class beanClass, String propertyName,
64
			Class valueType) {
65
		return new PojoValueProperty(BeanPropertyHelper.getPropertyDescriptor(
66
				beanClass, propertyName), valueType);
67
	}
68
69
	/**
70
	 * Returns a set property for the given property name of the given bean
71
	 * class.
72
	 * 
73
	 * @param beanClass
74
	 *            the bean class
75
	 * @param propertyName
76
	 *            the property name
77
	 * @return a set property for the given property name of the given bean
78
	 *         class.
79
	 */
80
	public static ISetProperty set(Class beanClass, String propertyName) {
81
		return set(beanClass, propertyName, null);
82
	}
83
84
	/**
85
	 * Returns a set property for the given property name of the given bean
86
	 * class.
87
	 * 
88
	 * @param beanClass
89
	 *            the bean class
90
	 * @param propertyName
91
	 *            the property name
92
	 * @param elementType
93
	 *            the element type of the returned set property
94
	 * @return a set property for the given property name of the given bean
95
	 *         class.
96
	 */
97
	public static ISetProperty set(Class beanClass, String propertyName,
98
			Class elementType) {
99
		return new PojoSetProperty(BeanPropertyHelper.getPropertyDescriptor(
100
				beanClass, propertyName), elementType);
101
	}
102
103
	/**
104
	 * Returns a list property for the given property name of the given bean
105
	 * class.
106
	 * 
107
	 * @param beanClass
108
	 *            the bean class
109
	 * @param propertyName
110
	 *            the property name
111
	 * @return a list property for the given property name of the given bean
112
	 *         class.
113
	 */
114
	public static IListProperty list(Class beanClass, String propertyName) {
115
		return list(beanClass, propertyName, null);
116
	}
117
118
	/**
119
	 * Returns a list property for the given property name of the given bean
120
	 * class.
121
	 * 
122
	 * @param beanClass
123
	 *            the bean class
124
	 * @param propertyName
125
	 *            the property name
126
	 * @param elementType
127
	 *            the element type of the returned list property
128
	 * @return a list property for the given property name of the given bean
129
	 *         class.
130
	 */
131
	public static IListProperty list(Class beanClass, String propertyName,
132
			Class elementType) {
133
		return new PojoListProperty(BeanPropertyHelper.getPropertyDescriptor(
134
				beanClass, propertyName), elementType);
135
	}
136
137
	/**
138
	 * Returns a map property for the given property name of the given bean
139
	 * class.
140
	 * 
141
	 * @param beanClass
142
	 *            the bean class
143
	 * @param propertyName
144
	 *            the property name
145
	 * @param keyType
146
	 *            the key type of the returned map property
147
	 * @param valueType
148
	 *            the value type of the returned map property
149
	 * @return a map property for the given property name of the given bean
150
	 *         class.
151
	 */
152
	public static IMapProperty map(Class beanClass, String propertyName,
153
			Class keyType, Class valueType) {
154
		return new PojoMapProperty(BeanPropertyHelper.getPropertyDescriptor(
155
				beanClass, propertyName), keyType, valueType);
156
	}
157
}
(-)src/org/eclipse/core/internal/databinding/beans/BeanSetProperty.java (+147 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.internal.databinding.beans;
13
14
import java.beans.PropertyChangeEvent;
15
import java.beans.PropertyChangeListener;
16
import java.beans.PropertyDescriptor;
17
import java.lang.reflect.Array;
18
import java.util.Arrays;
19
import java.util.Collections;
20
import java.util.HashSet;
21
import java.util.Set;
22
23
import org.eclipse.core.databinding.beans.IBeanProperty;
24
import org.eclipse.core.databinding.observable.Diffs;
25
import org.eclipse.core.databinding.observable.set.SetDiff;
26
import org.eclipse.core.databinding.property.INativePropertyListener;
27
import org.eclipse.core.databinding.property.set.ISetPropertyChangeListener;
28
import org.eclipse.core.databinding.property.set.SetPropertyChangeEvent;
29
import org.eclipse.core.databinding.property.set.SimpleSetProperty;
30
31
/**
32
 * @since 3.3
33
 * 
34
 */
35
public class BeanSetProperty extends SimpleSetProperty implements IBeanProperty {
36
	private PropertyDescriptor propertyDescriptor;
37
	private Class elementType;
38
39
	/**
40
	 * @param propertyDescriptor
41
	 * @param elementType
42
	 */
43
	public BeanSetProperty(PropertyDescriptor propertyDescriptor,
44
			Class elementType) {
45
		super(elementType == null ? BeanPropertyHelper
46
				.getCollectionPropertyElementType(propertyDescriptor)
47
				: elementType);
48
		this.propertyDescriptor = propertyDescriptor;
49
	}
50
51
	protected Set doGetSet(Object source) {
52
		if (source == null)
53
			return Collections.EMPTY_SET;
54
		Object propertyValue = BeanPropertyHelper.readProperty(source,
55
				propertyDescriptor);
56
		return asSet(propertyValue);
57
	}
58
59
	private Set asSet(Object propertyValue) {
60
		if (propertyValue == null)
61
			return Collections.EMPTY_SET;
62
		if (propertyDescriptor.getPropertyType().isArray())
63
			return new HashSet(Arrays.asList((Object[]) propertyValue));
64
		return (Set) propertyValue;
65
	}
66
67
	protected void setSet(Object source, Set set, SetDiff diff) {
68
		if (source != null) {
69
			BeanPropertyHelper.writeProperty(source, propertyDescriptor,
70
					convertSetToBeanPropertyType(set));
71
		}
72
	}
73
74
	private Object convertSetToBeanPropertyType(Set set) {
75
		Object propertyValue = set;
76
		if (propertyDescriptor.getPropertyType().isArray()) {
77
			Class componentType = propertyDescriptor.getPropertyType()
78
					.getComponentType();
79
			Object[] array = (Object[]) Array.newInstance(componentType, set
80
					.size());
81
			propertyValue = set.toArray(array);
82
		}
83
		return propertyValue;
84
	}
85
86
	public PropertyDescriptor getPropertyDescriptor() {
87
		return propertyDescriptor;
88
	}
89
90
	public INativePropertyListener adaptListener(
91
			final ISetPropertyChangeListener listener) {
92
		return new Listener(listener);
93
	}
94
95
	private class Listener implements INativePropertyListener,
96
			PropertyChangeListener {
97
		private final ISetPropertyChangeListener listener;
98
99
		private Listener(ISetPropertyChangeListener listener) {
100
			this.listener = listener;
101
		}
102
103
		public void propertyChange(PropertyChangeEvent evt) {
104
			if (propertyDescriptor.getName().equals(evt.getPropertyName())) {
105
				Object oldValue = evt.getOldValue();
106
				Object newValue = evt.getNewValue();
107
108
				SetDiff diff;
109
				if (oldValue == null && newValue == null) {
110
					diff = null; // unknown change
111
				} else {
112
					diff = Diffs.computeSetDiff(asSet(oldValue),
113
							asSet(newValue));
114
				}
115
116
				listener.handleSetPropertyChange(new SetPropertyChangeEvent(evt
117
						.getSource(), BeanSetProperty.this, diff));
118
			}
119
		}
120
	}
121
122
	public void addListener(Object source, INativePropertyListener listener) {
123
		if (source != null) {
124
			BeanPropertyListenerSupport.hookListener(source, propertyDescriptor
125
					.getName(), (PropertyChangeListener) listener);
126
		}
127
	}
128
129
	public void removeListener(Object source, INativePropertyListener listener) {
130
		if (source != null) {
131
			BeanPropertyListenerSupport.unhookListener(source,
132
					propertyDescriptor.getName(),
133
					(PropertyChangeListener) listener);
134
		}
135
	}
136
137
	public String toString() {
138
		Class beanClass = propertyDescriptor.getReadMethod()
139
				.getDeclaringClass();
140
		String propertyName = propertyDescriptor.getName();
141
		String s = beanClass.getName() + "." + propertyName + "{}"; //$NON-NLS-1$ //$NON-NLS-2$
142
143
		if (elementType != null)
144
			s += " <" + elementType.getName() + ">"; //$NON-NLS-1$//$NON-NLS-2$
145
		return s;
146
	}
147
}
(-)src/org/eclipse/core/internal/databinding/beans/PojoListProperty.java (+109 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.internal.databinding.beans;
13
14
import java.beans.PropertyDescriptor;
15
import java.lang.reflect.Array;
16
import java.util.ArrayList;
17
import java.util.Arrays;
18
import java.util.Collections;
19
import java.util.List;
20
21
import org.eclipse.core.databinding.beans.IBeanProperty;
22
import org.eclipse.core.databinding.observable.list.ListDiff;
23
import org.eclipse.core.databinding.property.INativePropertyListener;
24
import org.eclipse.core.databinding.property.list.IListPropertyChangeListener;
25
import org.eclipse.core.databinding.property.list.SimpleListProperty;
26
27
/**
28
 * @since 3.3
29
 * 
30
 */
31
public class PojoListProperty extends SimpleListProperty implements
32
		IBeanProperty {
33
	private PropertyDescriptor propertyDescriptor;
34
35
	/**
36
	 * @param propertyDescriptor
37
	 * @param elementType
38
	 */
39
	public PojoListProperty(PropertyDescriptor propertyDescriptor,
40
			Class elementType) {
41
		super(elementType == null ? BeanPropertyHelper
42
				.getCollectionPropertyElementType(propertyDescriptor)
43
				: elementType);
44
		this.propertyDescriptor = propertyDescriptor;
45
	}
46
47
	protected List doGetList(Object source) {
48
		if (source == null)
49
			return Collections.EMPTY_LIST;
50
		Object propertyValue = BeanPropertyHelper.readProperty(source,
51
				propertyDescriptor);
52
		return asList(propertyValue);
53
	}
54
55
	private List asList(Object propertyValue) {
56
		if (propertyValue == null)
57
			return new ArrayList();
58
		if (propertyDescriptor.getPropertyType().isArray())
59
			return new ArrayList(Arrays.asList((Object[]) propertyValue));
60
		return (List) propertyValue;
61
	}
62
63
	protected void setList(Object source, List list, ListDiff diff) {
64
		if (source != null) {
65
			BeanPropertyHelper.writeProperty(source, propertyDescriptor,
66
					convertListToBeanPropertyType(list));
67
		}
68
	}
69
70
	private Object convertListToBeanPropertyType(List list) {
71
		Object propertyValue = list;
72
		if (propertyDescriptor.getPropertyType().isArray()) {
73
			Class componentType = propertyDescriptor.getPropertyType()
74
					.getComponentType();
75
			Object[] array = (Object[]) Array.newInstance(componentType, list
76
					.size());
77
			list.toArray(array);
78
			propertyValue = array;
79
		}
80
		return propertyValue;
81
	}
82
83
	public PropertyDescriptor getPropertyDescriptor() {
84
		return propertyDescriptor;
85
	}
86
87
	public INativePropertyListener adaptListener(
88
			IListPropertyChangeListener listener) {
89
		return null;
90
	}
91
92
	public void addListener(Object source, INativePropertyListener listener) {
93
	}
94
95
	public void removeListener(Object source, INativePropertyListener listener) {
96
	}
97
98
	public String toString() {
99
		Class beanClass = propertyDescriptor.getReadMethod()
100
				.getDeclaringClass();
101
		String propertyName = propertyDescriptor.getName();
102
		String s = beanClass.getName() + "." + propertyName + "[]"; //$NON-NLS-1$ //$NON-NLS-2$
103
104
		Class elementType = (Class) getElementType();
105
		if (elementType != null)
106
			s += " <" + elementType.getName() + ">"; //$NON-NLS-1$//$NON-NLS-2$
107
		return s;
108
	}
109
}
(-)src/org/eclipse/core/internal/databinding/beans/BeanPropertyHelper.java (+169 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.internal.databinding.beans;
13
14
import java.beans.BeanInfo;
15
import java.beans.IntrospectionException;
16
import java.beans.Introspector;
17
import java.beans.PropertyDescriptor;
18
import java.lang.reflect.InvocationTargetException;
19
import java.lang.reflect.Method;
20
21
import org.eclipse.core.databinding.BindingException;
22
import org.eclipse.core.databinding.beans.BeansObservables;
23
import org.eclipse.core.databinding.observable.value.IObservableValue;
24
import org.eclipse.core.databinding.util.Policy;
25
import org.eclipse.core.runtime.IStatus;
26
import org.eclipse.core.runtime.Status;
27
28
/**
29
 * @since 1.2
30
 * 
31
 */
32
public class BeanPropertyHelper {
33
	/**
34
	 * Sets the contents of the given property on the given source object to the
35
	 * given value.
36
	 * 
37
	 * @param source
38
	 *            the source object which has the property being updated
39
	 * @param propertyDescriptor
40
	 *            the property being changed
41
	 * @param value
42
	 *            the new value of the property
43
	 */
44
	public static void writeProperty(Object source,
45
			PropertyDescriptor propertyDescriptor, Object value) {
46
		try {
47
			Method writeMethod = propertyDescriptor.getWriteMethod();
48
			if (!writeMethod.isAccessible()) {
49
				writeMethod.setAccessible(true);
50
			}
51
			writeMethod.invoke(source, new Object[] { value });
52
		} catch (InvocationTargetException e) {
53
			/*
54
			 * InvocationTargetException wraps any exception thrown by the
55
			 * invoked method.
56
			 */
57
			throw new RuntimeException(e.getCause());
58
		} catch (Exception e) {
59
			if (BeansObservables.DEBUG) {
60
				Policy
61
						.getLog()
62
						.log(
63
								new Status(
64
										IStatus.WARNING,
65
										Policy.JFACE_DATABINDING,
66
										IStatus.OK,
67
										"Could not change value of " + source + "." + propertyDescriptor.getName(), e)); //$NON-NLS-1$ //$NON-NLS-2$
68
			}
69
		}
70
	}
71
72
	/**
73
	 * Returns the contents of the given property for the given bean.
74
	 * 
75
	 * @param source
76
	 *            the source bean
77
	 * @param propertyDescriptor
78
	 *            the property to retrieve
79
	 * @return the contents of the given property for the given bean.
80
	 */
81
	public static Object readProperty(Object source,
82
			PropertyDescriptor propertyDescriptor) {
83
		try {
84
			Method readMethod = propertyDescriptor.getReadMethod();
85
			if (readMethod == null) {
86
				throw new BindingException(propertyDescriptor.getName()
87
						+ " property does not have a read method."); //$NON-NLS-1$
88
			}
89
			if (!readMethod.isAccessible()) {
90
				readMethod.setAccessible(true);
91
			}
92
			return readMethod.invoke(source, null);
93
		} catch (InvocationTargetException e) {
94
			/*
95
			 * InvocationTargetException wraps any exception thrown by the
96
			 * invoked method.
97
			 */
98
			throw new RuntimeException(e.getCause());
99
		} catch (Exception e) {
100
			if (BeansObservables.DEBUG) {
101
				Policy
102
						.getLog()
103
						.log(
104
								new Status(
105
										IStatus.WARNING,
106
										Policy.JFACE_DATABINDING,
107
										IStatus.OK,
108
										"Could not read value of " + source + "." + propertyDescriptor.getName(), e)); //$NON-NLS-1$ //$NON-NLS-2$
109
			}
110
			return null;
111
		}
112
	}
113
114
	/**
115
	 * Returns the element type of the given collection-typed property for the
116
	 * given bean.
117
	 * 
118
	 * @param descriptor
119
	 *            the property being inspected
120
	 * @return the element type of the given collection-typed property if it is
121
	 *         an array property, or Object.class otherwise.
122
	 */
123
	public static Class getCollectionPropertyElementType(
124
			PropertyDescriptor descriptor) {
125
		Class propertyType = descriptor.getPropertyType();
126
		return propertyType.isArray() ? propertyType.getComponentType()
127
				: Object.class;
128
	}
129
130
	/**
131
	 * @param beanClass
132
	 * @param propertyName
133
	 * @return the PropertyDescriptor for the named property on the given bean
134
	 *         class
135
	 */
136
	public static PropertyDescriptor getPropertyDescriptor(Class beanClass,
137
			String propertyName) {
138
		BeanInfo beanInfo;
139
		try {
140
			beanInfo = Introspector.getBeanInfo(beanClass);
141
		} catch (IntrospectionException e) {
142
			// cannot introspect, give up
143
			return null;
144
		}
145
		PropertyDescriptor[] propertyDescriptors = beanInfo
146
				.getPropertyDescriptors();
147
		for (int i = 0; i < propertyDescriptors.length; i++) {
148
			PropertyDescriptor descriptor = propertyDescriptors[i];
149
			if (descriptor.getName().equals(propertyName)) {
150
				return descriptor;
151
			}
152
		}
153
		throw new BindingException(
154
				"Could not find property with name " + propertyName + " in class " + beanClass); //$NON-NLS-1$ //$NON-NLS-2$
155
	}
156
157
	/**
158
	 * @param observable
159
	 * @param propertyName
160
	 * @return property descriptor or <code>null</code>
161
	 */
162
	/* package */public static PropertyDescriptor getValueTypePropertyDescriptor(
163
			IObservableValue observable, String propertyName) {
164
		if (observable.getValueType() != null)
165
			return getPropertyDescriptor((Class) observable.getValueType(),
166
					propertyName);
167
		return null;
168
	}
169
}
(-)src/org/eclipse/core/internal/databinding/beans/PojoSetProperty.java (+107 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.internal.databinding.beans;
13
14
import java.beans.PropertyDescriptor;
15
import java.lang.reflect.Array;
16
import java.util.Arrays;
17
import java.util.Collections;
18
import java.util.HashSet;
19
import java.util.Set;
20
21
import org.eclipse.core.databinding.beans.IBeanProperty;
22
import org.eclipse.core.databinding.observable.set.SetDiff;
23
import org.eclipse.core.databinding.property.INativePropertyListener;
24
import org.eclipse.core.databinding.property.set.ISetPropertyChangeListener;
25
import org.eclipse.core.databinding.property.set.SimpleSetProperty;
26
27
/**
28
 * @since 3.3
29
 * 
30
 */
31
public class PojoSetProperty extends SimpleSetProperty implements IBeanProperty {
32
	private PropertyDescriptor propertyDescriptor;
33
34
	/**
35
	 * @param propertyDescriptor
36
	 * @param elementType
37
	 */
38
	public PojoSetProperty(PropertyDescriptor propertyDescriptor,
39
			Class elementType) {
40
		super(elementType == null ? BeanPropertyHelper
41
				.getCollectionPropertyElementType(propertyDescriptor)
42
				: elementType);
43
		this.propertyDescriptor = propertyDescriptor;
44
	}
45
46
	protected Set doGetSet(Object source) {
47
		if (source == null)
48
			return Collections.EMPTY_SET;
49
		Object propertyValue = BeanPropertyHelper.readProperty(source,
50
				propertyDescriptor);
51
		return asSet(propertyValue);
52
	}
53
54
	private Set asSet(Object propertyValue) {
55
		if (propertyValue == null)
56
			return Collections.EMPTY_SET;
57
		if (propertyDescriptor.getPropertyType().isArray())
58
			return new HashSet(Arrays.asList((Object[]) propertyValue));
59
		return (Set) propertyValue;
60
	}
61
62
	protected void setSet(Object source, Set set, SetDiff diff) {
63
		if (source != null) {
64
			BeanPropertyHelper.writeProperty(source, propertyDescriptor,
65
					convertSetToBeanPropertyType(set));
66
		}
67
	}
68
69
	private Object convertSetToBeanPropertyType(Set set) {
70
		Object propertyValue = set;
71
		if (propertyDescriptor.getPropertyType().isArray()) {
72
			Class componentType = propertyDescriptor.getPropertyType()
73
					.getComponentType();
74
			Object[] array = (Object[]) Array.newInstance(componentType, set
75
					.size());
76
			propertyValue = set.toArray(array);
77
		}
78
		return propertyValue;
79
	}
80
81
	public PropertyDescriptor getPropertyDescriptor() {
82
		return propertyDescriptor;
83
	}
84
85
	public INativePropertyListener adaptListener(
86
			ISetPropertyChangeListener listener) {
87
		return null;
88
	}
89
90
	public void addListener(Object source, INativePropertyListener listener) {
91
	}
92
93
	public void removeListener(Object source, INativePropertyListener listener) {
94
	}
95
96
	public String toString() {
97
		Class beanClass = propertyDescriptor.getReadMethod()
98
				.getDeclaringClass();
99
		String propertyName = propertyDescriptor.getName();
100
		String s = beanClass.getName() + "." + propertyName + "{}"; //$NON-NLS-1$ //$NON-NLS-2$
101
102
		Class elementType = (Class) getElementType();
103
		if (elementType != null)
104
			s += " <" + elementType.getName() + ">"; //$NON-NLS-1$//$NON-NLS-2$
105
		return s;
106
	}
107
}
(-)src/org/eclipse/core/internal/databinding/beans/PojoValueProperty.java (+78 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.internal.databinding.beans;
13
14
import java.beans.PropertyDescriptor;
15
16
import org.eclipse.core.databinding.beans.IBeanProperty;
17
import org.eclipse.core.databinding.property.INativePropertyListener;
18
import org.eclipse.core.databinding.property.value.IValuePropertyChangeListener;
19
import org.eclipse.core.databinding.property.value.SimpleValueProperty;
20
21
/**
22
 * @since 3.3
23
 * 
24
 */
25
public class PojoValueProperty extends SimpleValueProperty implements
26
		IBeanProperty {
27
	private PropertyDescriptor propertyDescriptor;
28
29
	/**
30
	 * @param propertyDescriptor
31
	 * @param valueType
32
	 */
33
	public PojoValueProperty(PropertyDescriptor propertyDescriptor,
34
			Class valueType) {
35
		super(valueType == null ? propertyDescriptor.getPropertyType()
36
				: valueType);
37
		this.propertyDescriptor = propertyDescriptor;
38
	}
39
40
	public Object getValue(Object source) {
41
		if (source == null)
42
			return null;
43
		return BeanPropertyHelper.readProperty(source, propertyDescriptor);
44
	}
45
46
	public void setValue(Object source, Object value) {
47
		if (source != null) {
48
			BeanPropertyHelper.writeProperty(source, propertyDescriptor, value);
49
		}
50
	}
51
52
	public PropertyDescriptor getPropertyDescriptor() {
53
		return propertyDescriptor;
54
	}
55
56
	public INativePropertyListener adaptListener(
57
			IValuePropertyChangeListener listener) {
58
		return null;
59
	}
60
61
	public void addListener(Object source, INativePropertyListener listener) {
62
	}
63
64
	public void removeListener(Object source, INativePropertyListener listener) {
65
	}
66
67
	public String toString() {
68
		Class beanClass = propertyDescriptor.getReadMethod()
69
				.getDeclaringClass();
70
		String propertyName = propertyDescriptor.getName();
71
		String s = beanClass.getName() + "." + propertyName + ""; //$NON-NLS-1$ //$NON-NLS-2$
72
73
		Class valueType = (Class) getValueType();
74
		if (valueType != null)
75
			s += " <" + valueType.getName() + ">"; //$NON-NLS-1$//$NON-NLS-2$
76
		return s;
77
	}
78
}
(-)src/org/eclipse/core/databinding/beans/IBeanProperty.java (+30 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.databinding.beans;
13
14
import java.beans.PropertyDescriptor;
15
16
import org.eclipse.core.databinding.property.IProperty;
17
18
/**
19
 * Provides access to details of bean properties.
20
 * 
21
 * @since 1.2
22
 */
23
public interface IBeanProperty extends IProperty {
24
	/**
25
	 * Returns the property descriptor of the bean property being observed
26
	 * 
27
	 * @return the property descriptor of the bean property being observed
28
	 */
29
	public PropertyDescriptor getPropertyDescriptor();
30
}
(-)src/org/eclipse/core/internal/databinding/beans/BeanValueProperty.java (+119 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.internal.databinding.beans;
13
14
import java.beans.PropertyChangeEvent;
15
import java.beans.PropertyChangeListener;
16
import java.beans.PropertyDescriptor;
17
18
import org.eclipse.core.databinding.beans.IBeanProperty;
19
import org.eclipse.core.databinding.observable.Diffs;
20
import org.eclipse.core.databinding.observable.value.ValueDiff;
21
import org.eclipse.core.databinding.property.INativePropertyListener;
22
import org.eclipse.core.databinding.property.value.IValuePropertyChangeListener;
23
import org.eclipse.core.databinding.property.value.SimpleValueProperty;
24
import org.eclipse.core.databinding.property.value.ValuePropertyChangeEvent;
25
26
/**
27
 * @since 3.3
28
 * 
29
 */
30
public class BeanValueProperty extends SimpleValueProperty implements
31
		IBeanProperty {
32
	private PropertyDescriptor propertyDescriptor;
33
34
	/**
35
	 * @param propertyDescriptor
36
	 * @param valueType
37
	 */
38
	public BeanValueProperty(PropertyDescriptor propertyDescriptor,
39
			Class valueType) {
40
		super(valueType == null ? propertyDescriptor.getPropertyType()
41
				: valueType);
42
		this.propertyDescriptor = propertyDescriptor;
43
	}
44
45
	public Object getValue(Object source) {
46
		if (source == null)
47
			return null;
48
		return BeanPropertyHelper.readProperty(source, propertyDescriptor);
49
	}
50
51
	public void setValue(Object source, Object value) {
52
		if (source != null) {
53
			BeanPropertyHelper.writeProperty(source, propertyDescriptor, value);
54
		}
55
	}
56
57
	public PropertyDescriptor getPropertyDescriptor() {
58
		return propertyDescriptor;
59
	}
60
61
	public INativePropertyListener adaptListener(
62
			final IValuePropertyChangeListener listener) {
63
		return new Listener(listener);
64
	}
65
66
	private class Listener implements INativePropertyListener,
67
			PropertyChangeListener {
68
		private final IValuePropertyChangeListener listener;
69
70
		private Listener(IValuePropertyChangeListener listener) {
71
			this.listener = listener;
72
		}
73
74
		public void propertyChange(PropertyChangeEvent evt) {
75
			if (propertyDescriptor.getName().equals(evt.getPropertyName())) {
76
				Object oldValue = evt.getOldValue();
77
				Object newValue = evt.getNewValue();
78
79
				ValueDiff diff;
80
				if (oldValue == null && newValue == null) {
81
					diff = null; // unknown change
82
				} else {
83
					diff = Diffs.createValueDiff(oldValue, newValue);
84
				}
85
86
				listener
87
						.handleValuePropertyChange(new ValuePropertyChangeEvent(
88
								evt.getSource(), BeanValueProperty.this, diff));
89
			}
90
		}
91
	}
92
93
	public void addListener(Object source, INativePropertyListener listener) {
94
		if (source != null) {
95
			BeanPropertyListenerSupport.hookListener(source, propertyDescriptor
96
					.getName(), (PropertyChangeListener) listener);
97
		}
98
	}
99
100
	public void removeListener(Object source, INativePropertyListener listener) {
101
		if (source != null) {
102
			BeanPropertyListenerSupport.unhookListener(source,
103
					propertyDescriptor.getName(),
104
					(PropertyChangeListener) listener);
105
		}
106
	}
107
108
	public String toString() {
109
		Class beanClass = propertyDescriptor.getReadMethod()
110
				.getDeclaringClass();
111
		String propertyName = propertyDescriptor.getName();
112
		String s = beanClass.getName() + "." + propertyName + ""; //$NON-NLS-1$ //$NON-NLS-2$
113
114
		Class valueType = (Class) getValueType();
115
		if (valueType != null)
116
			s += " <" + valueType.getName() + ">"; //$NON-NLS-1$//$NON-NLS-2$
117
		return s;
118
	}
119
}
(-)src/org/eclipse/core/internal/databinding/beans/BeanPropertyListenerSupport.java (+135 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2005, 2008 IBM Corporation and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
10
 *     Matthew Hall - bug 118516
11
 *******************************************************************************/
12
package org.eclipse.core.internal.databinding.beans;
13
14
import java.beans.PropertyChangeListener;
15
import java.lang.reflect.InvocationTargetException;
16
import java.lang.reflect.Method;
17
18
import org.eclipse.core.databinding.beans.BeansObservables;
19
import org.eclipse.core.databinding.util.Policy;
20
import org.eclipse.core.runtime.Assert;
21
import org.eclipse.core.runtime.IStatus;
22
import org.eclipse.core.runtime.Status;
23
24
/**
25
 * This is a helper that will hook up and listen for
26
 * <code>PropertyChangeEvent</code> events for a set of target JavaBeans
27
 * 
28
 * @since 1.0
29
 */
30
public class BeanPropertyListenerSupport {
31
	/**
32
	 * Start listen to target (if it supports the JavaBean property change
33
	 * listener pattern)
34
	 * 
35
	 * @param bean
36
	 * @param propertyName
37
	 * @param listener
38
	 */
39
	public static void hookListener(Object bean, String propertyName,
40
			PropertyChangeListener listener) {
41
		Assert.isNotNull(bean, "Bean cannot be null"); //$NON-NLS-1$
42
		Assert.isNotNull(listener, "Listener cannot be null"); //$NON-NLS-1$
43
		Assert.isNotNull(propertyName, "Property name cannot be null"); //$NON-NLS-1$
44
		processListener(bean, propertyName, listener,
45
				"addPropertyChangeListener", "Could not attach listener to ");//$NON-NLS-1$ //$NON-NLS-2$
46
	}
47
48
	/**
49
	 * Stop listen to target
50
	 * 
51
	 * @param bean
52
	 * @param propertyName
53
	 * @param listener
54
	 */
55
	public static void unhookListener(Object bean, String propertyName,
56
			PropertyChangeListener listener) {
57
		Assert.isNotNull(bean, "Bean cannot be null"); //$NON-NLS-1$
58
		Assert.isNotNull(listener, "Listener cannot be null"); //$NON-NLS-1$
59
		Assert.isNotNull(propertyName, "Property name cannot be null"); //$NON-NLS-1$
60
61
		processListener(
62
				bean,
63
				propertyName,
64
				listener,
65
				"removePropertyChangeListener", "Cound not remove listener from "); //$NON-NLS-1$ //$NON-NLS-2$
66
	}
67
68
	/**
69
	 * Invokes the method for the provided <code>methodName</code> attempting to
70
	 * first use the method with the property name and then the unnamed version.
71
	 * 
72
	 * @param bean
73
	 *            object to invoke the method on
74
	 * @param methodName
75
	 *            either addPropertyChangeListener or
76
	 *            removePropertyChangeListener
77
	 * @param message
78
	 *            string that will be prefixed to the target in an error message
79
	 * 
80
	 * @return <code>true</code> if the method was invoked successfully
81
	 */
82
	private static boolean processListener(Object bean, String propertyName,
83
			PropertyChangeListener listener, String methodName, String message) {
84
		Method method = null;
85
		Object[] parameters = null;
86
87
		try {
88
			try {
89
				method = bean.getClass().getMethod(
90
						methodName,
91
						new Class[] { String.class,
92
								PropertyChangeListener.class });
93
94
				parameters = new Object[] { propertyName, listener };
95
			} catch (NoSuchMethodException e) {
96
				method = bean.getClass().getMethod(methodName,
97
						new Class[] { PropertyChangeListener.class });
98
99
				parameters = new Object[] { listener };
100
			}
101
		} catch (SecurityException e) {
102
			// ignore
103
		} catch (NoSuchMethodException e) {
104
			log(IStatus.WARNING, message + bean, e);
105
		}
106
107
		if (method != null) {
108
			if (!method.isAccessible()) {
109
				method.setAccessible(true);
110
			}
111
			try {
112
				method.invoke(bean, parameters);
113
				return true;
114
			} catch (IllegalArgumentException e) {
115
				log(IStatus.WARNING, message + bean, e);
116
			} catch (IllegalAccessException e) {
117
				log(IStatus.WARNING, message + bean, e);
118
			} catch (InvocationTargetException e) {
119
				log(IStatus.WARNING, message + bean, e);
120
			}
121
		}
122
		return false;
123
	}
124
125
	/**
126
	 * Logs a message to the Data Binding logger.
127
	 */
128
	private static void log(int severity, String message, Throwable throwable) {
129
		if (BeansObservables.DEBUG) {
130
			Policy.getLog().log(
131
					new Status(severity, Policy.JFACE_DATABINDING, IStatus.OK,
132
							message, throwable));
133
		}
134
	}
135
}
(-)src/org/eclipse/core/internal/databinding/beans/BeanListProperty.java (+149 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.internal.databinding.beans;
13
14
import java.beans.PropertyChangeEvent;
15
import java.beans.PropertyChangeListener;
16
import java.beans.PropertyDescriptor;
17
import java.lang.reflect.Array;
18
import java.util.ArrayList;
19
import java.util.Arrays;
20
import java.util.Collections;
21
import java.util.List;
22
23
import org.eclipse.core.databinding.beans.IBeanProperty;
24
import org.eclipse.core.databinding.observable.Diffs;
25
import org.eclipse.core.databinding.observable.list.ListDiff;
26
import org.eclipse.core.databinding.property.INativePropertyListener;
27
import org.eclipse.core.databinding.property.list.IListPropertyChangeListener;
28
import org.eclipse.core.databinding.property.list.ListPropertyChangeEvent;
29
import org.eclipse.core.databinding.property.list.SimpleListProperty;
30
31
/**
32
 * @since 3.3
33
 * 
34
 */
35
public class BeanListProperty extends SimpleListProperty implements
36
		IBeanProperty {
37
	private final PropertyDescriptor propertyDescriptor;
38
39
	/**
40
	 * @param propertyDescriptor
41
	 * @param elementType
42
	 */
43
	public BeanListProperty(PropertyDescriptor propertyDescriptor,
44
			Class elementType) {
45
		super(elementType == null ? BeanPropertyHelper
46
				.getCollectionPropertyElementType(propertyDescriptor)
47
				: elementType);
48
		this.propertyDescriptor = propertyDescriptor;
49
	}
50
51
	protected List doGetList(Object source) {
52
		if (source == null)
53
			return Collections.EMPTY_LIST;
54
		Object propertyValue = BeanPropertyHelper.readProperty(source,
55
				propertyDescriptor);
56
		return asList(propertyValue);
57
	}
58
59
	private List asList(Object propertyValue) {
60
		if (propertyValue == null)
61
			return new ArrayList();
62
		if (propertyDescriptor.getPropertyType().isArray())
63
			return new ArrayList(Arrays.asList((Object[]) propertyValue));
64
		return (List) propertyValue;
65
	}
66
67
	protected void setList(Object source, List list, ListDiff diff) {
68
		if (source != null) {
69
			BeanPropertyHelper.writeProperty(source, propertyDescriptor,
70
					convertListToBeanPropertyType(list));
71
		}
72
	}
73
74
	private Object convertListToBeanPropertyType(List list) {
75
		Object propertyValue = list;
76
		if (propertyDescriptor.getPropertyType().isArray()) {
77
			Class componentType = propertyDescriptor.getPropertyType()
78
					.getComponentType();
79
			Object[] array = (Object[]) Array.newInstance(componentType, list
80
					.size());
81
			list.toArray(array);
82
			propertyValue = array;
83
		}
84
		return propertyValue;
85
	}
86
87
	public PropertyDescriptor getPropertyDescriptor() {
88
		return propertyDescriptor;
89
	}
90
91
	public INativePropertyListener adaptListener(
92
			final IListPropertyChangeListener listener) {
93
		return new Listener(listener);
94
	}
95
96
	private class Listener implements INativePropertyListener,
97
			PropertyChangeListener {
98
		private final IListPropertyChangeListener listener;
99
100
		private Listener(IListPropertyChangeListener listener) {
101
			this.listener = listener;
102
		}
103
104
		public void propertyChange(PropertyChangeEvent evt) {
105
			if (propertyDescriptor.getName().equals(evt.getPropertyName())) {
106
				Object oldValue = evt.getOldValue();
107
				Object newValue = evt.getNewValue();
108
109
				ListDiff diff;
110
				if (oldValue == null && newValue == null) {
111
					diff = null; // unknown change
112
				} else {
113
					diff = Diffs.computeListDiff(asList(oldValue),
114
							asList(newValue));
115
				}
116
117
				listener.handleListPropertyChange(new ListPropertyChangeEvent(
118
						evt.getSource(), BeanListProperty.this, diff));
119
			}
120
		}
121
	}
122
123
	public void addListener(Object source, INativePropertyListener listener) {
124
		if (source != null) {
125
			BeanPropertyListenerSupport.hookListener(source, propertyDescriptor
126
					.getName(), (PropertyChangeListener) listener);
127
		}
128
	}
129
130
	public void removeListener(Object source, INativePropertyListener listener) {
131
		if (source != null) {
132
			BeanPropertyListenerSupport.unhookListener(source,
133
					propertyDescriptor.getName(),
134
					(PropertyChangeListener) listener);
135
		}
136
	}
137
138
	public String toString() {
139
		Class beanClass = propertyDescriptor.getReadMethod()
140
				.getDeclaringClass();
141
		String propertyName = propertyDescriptor.getName();
142
		String s = beanClass.getName() + "." + propertyName + "[]"; //$NON-NLS-1$ //$NON-NLS-2$
143
144
		Class elementType = (Class) getElementType();
145
		if (elementType != null)
146
			s += " <" + elementType.getName() + ">"; //$NON-NLS-1$//$NON-NLS-2$
147
		return s;
148
	}
149
}
(-)src/org/eclipse/core/databinding/beans/BeanProperties.java (+154 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.databinding.beans;
13
14
import org.eclipse.core.databinding.property.list.IListProperty;
15
import org.eclipse.core.databinding.property.map.IMapProperty;
16
import org.eclipse.core.databinding.property.set.ISetProperty;
17
import org.eclipse.core.databinding.property.value.IValueProperty;
18
import org.eclipse.core.internal.databinding.beans.BeanListProperty;
19
import org.eclipse.core.internal.databinding.beans.BeanMapProperty;
20
import org.eclipse.core.internal.databinding.beans.BeanPropertyHelper;
21
import org.eclipse.core.internal.databinding.beans.BeanSetProperty;
22
import org.eclipse.core.internal.databinding.beans.BeanValueProperty;
23
24
/**
25
 * A factory for creating properties for Java objects that conform to the <a
26
 * href="http://java.sun.com/products/javabeans/docs/spec.html">JavaBean
27
 * specification</a> for bound properties.
28
 * 
29
 * @since 1.2
30
 */
31
public class BeanProperties {
32
	/**
33
	 * Returns a value property for the given property name of the given bean
34
	 * class.
35
	 * 
36
	 * @param beanClass
37
	 *            the bean class
38
	 * @param propertyName
39
	 *            the property name
40
	 * @return a value property for the given property name of the given bean
41
	 *         class.
42
	 */
43
	public static IValueProperty value(Class beanClass, String propertyName) {
44
		return value(beanClass, propertyName, null);
45
	}
46
47
	/**
48
	 * Returns a value property for the given property name of the given bean
49
	 * class.
50
	 * 
51
	 * @param beanClass
52
	 *            the bean class
53
	 * @param propertyName
54
	 *            the property name
55
	 * @param valueType
56
	 *            the value type of the returned value property
57
	 * @return a value property for the given property name of the given bean
58
	 *         class.
59
	 */
60
	public static IValueProperty value(Class beanClass, String propertyName,
61
			Class valueType) {
62
		return new BeanValueProperty(BeanPropertyHelper.getPropertyDescriptor(
63
				beanClass, propertyName), valueType);
64
	}
65
66
	/**
67
	 * Returns a set property for the given property name of the given bean
68
	 * class.
69
	 * 
70
	 * @param beanClass
71
	 *            the bean class
72
	 * @param propertyName
73
	 *            the property name
74
	 * @return a set property for the given property name of the given bean
75
	 *         class.
76
	 */
77
	public static ISetProperty set(Class beanClass, String propertyName) {
78
		return set(beanClass, propertyName, null);
79
	}
80
81
	/**
82
	 * Returns a set property for the given property name of the given bean
83
	 * class.
84
	 * 
85
	 * @param beanClass
86
	 *            the bean class
87
	 * @param propertyName
88
	 *            the property name
89
	 * @param elementType
90
	 *            the element type of the returned set property
91
	 * @return a set property for the given property name of the given bean
92
	 *         class.
93
	 */
94
	public static ISetProperty set(Class beanClass, String propertyName,
95
			Class elementType) {
96
		return new BeanSetProperty(BeanPropertyHelper.getPropertyDescriptor(
97
				beanClass, propertyName), elementType);
98
	}
99
100
	/**
101
	 * Returns a list property for the given property name of the given bean
102
	 * class.
103
	 * 
104
	 * @param beanClass
105
	 *            the bean class
106
	 * @param propertyName
107
	 *            the property name
108
	 * @return a list property for the given property name of the given bean
109
	 *         class.
110
	 */
111
	public static IListProperty list(Class beanClass, String propertyName) {
112
		return list(beanClass, propertyName, null);
113
	}
114
115
	/**
116
	 * Returns a list property for the given property name of the given bean
117
	 * class.
118
	 * 
119
	 * @param beanClass
120
	 *            the bean class
121
	 * @param propertyName
122
	 *            the property name
123
	 * @param elementType
124
	 *            the element type of the returned list property
125
	 * @return a list property for the given property name of the given bean
126
	 *         class.
127
	 */
128
	public static IListProperty list(Class beanClass, String propertyName,
129
			Class elementType) {
130
		return new BeanListProperty(BeanPropertyHelper.getPropertyDescriptor(
131
				beanClass, propertyName), elementType);
132
	}
133
134
	/**
135
	 * Returns a map property for the given property name of the given bean
136
	 * class.
137
	 * 
138
	 * @param beanClass
139
	 *            the bean class
140
	 * @param propertyName
141
	 *            the property name
142
	 * @param keyType
143
	 *            the key type for the returned map property
144
	 * @param valueType
145
	 *            the value type for the returned map property
146
	 * @return a map property for the given property name of the given bean
147
	 *         class.
148
	 */
149
	public static IMapProperty map(Class beanClass, String propertyName,
150
			Class keyType, Class valueType) {
151
		return new BeanMapProperty(BeanPropertyHelper.getPropertyDescriptor(
152
				beanClass, propertyName), keyType, valueType);
153
	}
154
}
(-)src/org/eclipse/jface/examples/databinding/snippets/Snippet025TableViewerWithPropertyDerivedColumns.java (+327 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2006 The Pampered Chef, Inc. and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Coconut Palm Software, Inc. - Initial API and implementation
10
 ******************************************************************************/
11
12
package org.eclipse.jface.examples.databinding.snippets;
13
14
import java.beans.PropertyChangeListener;
15
import java.beans.PropertyChangeSupport;
16
17
import org.eclipse.core.databinding.DataBindingContext;
18
import org.eclipse.core.databinding.beans.BeanProperties;
19
import org.eclipse.core.databinding.observable.Realm;
20
import org.eclipse.core.databinding.observable.list.IObservableList;
21
import org.eclipse.core.databinding.observable.list.WritableList;
22
import org.eclipse.core.databinding.observable.map.IObservableMap;
23
import org.eclipse.core.databinding.observable.set.IObservableSet;
24
import org.eclipse.core.databinding.observable.value.IObservableValue;
25
import org.eclipse.core.databinding.property.value.IValueProperty;
26
import org.eclipse.jface.databinding.swt.SWTObservables;
27
import org.eclipse.jface.databinding.swt.TextProperties;
28
import org.eclipse.jface.databinding.viewers.ObservableListContentProvider;
29
import org.eclipse.jface.databinding.viewers.ObservableMapLabelProvider;
30
import org.eclipse.jface.databinding.viewers.SelectionProviderProperties;
31
import org.eclipse.jface.layout.GridDataFactory;
32
import org.eclipse.jface.layout.GridLayoutFactory;
33
import org.eclipse.jface.viewers.ComboViewer;
34
import org.eclipse.jface.viewers.TableViewer;
35
import org.eclipse.jface.viewers.Viewer;
36
import org.eclipse.jface.viewers.ViewerFilter;
37
import org.eclipse.swt.SWT;
38
import org.eclipse.swt.widgets.Combo;
39
import org.eclipse.swt.widgets.Display;
40
import org.eclipse.swt.widgets.Label;
41
import org.eclipse.swt.widgets.Shell;
42
import org.eclipse.swt.widgets.Table;
43
import org.eclipse.swt.widgets.TableColumn;
44
import org.eclipse.swt.widgets.Text;
45
46
/**
47
 * Demonstrates binding a TableViewer to a collection.
48
 */
49
public class Snippet025TableViewerWithPropertyDerivedColumns {
50
	public static void main(String[] args) {
51
		final Display display = new Display();
52
53
		// Set up data binding. In an RCP application, the threading Realm
54
		// will be set for you automatically by the Workbench. In an SWT
55
		// application, you can do this once, wrapping your binding
56
		// method call.
57
		Realm.runWithDefault(SWTObservables.getRealm(display), new Runnable() {
58
			public void run() {
59
				ViewModel viewModel = new ViewModel();
60
				Shell shell = new View(viewModel).createShell();
61
62
				// The SWT event loop
63
				while (!shell.isDisposed()) {
64
					if (!display.readAndDispatch()) {
65
						display.sleep();
66
					}
67
				}
68
			}
69
		});
70
	}
71
72
	// Minimal JavaBeans support
73
	public static abstract class AbstractModelObject {
74
		private PropertyChangeSupport propertyChangeSupport = new PropertyChangeSupport(
75
				this);
76
77
		public void addPropertyChangeListener(PropertyChangeListener listener) {
78
			propertyChangeSupport.addPropertyChangeListener(listener);
79
		}
80
81
		public void addPropertyChangeListener(String propertyName,
82
				PropertyChangeListener listener) {
83
			propertyChangeSupport.addPropertyChangeListener(propertyName,
84
					listener);
85
		}
86
87
		public void removePropertyChangeListener(PropertyChangeListener listener) {
88
			propertyChangeSupport.removePropertyChangeListener(listener);
89
		}
90
91
		public void removePropertyChangeListener(String propertyName,
92
				PropertyChangeListener listener) {
93
			propertyChangeSupport.removePropertyChangeListener(propertyName,
94
					listener);
95
		}
96
97
		protected void firePropertyChange(String propertyName, Object oldValue,
98
				Object newValue) {
99
			propertyChangeSupport.firePropertyChange(propertyName, oldValue,
100
					newValue);
101
		}
102
	}
103
104
	private static Person UNKNOWN = new Person("unknown", null, null);
105
106
	// The data model class. This is normally a persistent class of some sort.
107
	static class Person extends AbstractModelObject {
108
		// A property...
109
		String name = "Donald Duck";
110
		Person mother;
111
		Person father;
112
113
		public Person(String name, Person mother, Person father) {
114
			this.name = name;
115
			this.mother = mother;
116
			this.father = father;
117
		}
118
119
		public String getName() {
120
			return name;
121
		}
122
123
		public void setName(String name) {
124
			firePropertyChange("name", this.name, this.name = name);
125
		}
126
127
		public Person getMother() {
128
			return mother;
129
		}
130
131
		public void setMother(Person mother) {
132
			firePropertyChange("mother", this.mother, this.mother = mother);
133
		}
134
135
		public Person getFather() {
136
			return father;
137
		}
138
139
		public void setFather(Person father) {
140
			firePropertyChange("father", this.father, this.father = father);
141
		}
142
	}
143
144
	// The View's model--the root of our Model graph for this particular GUI.
145
	//
146
	// Typically each View class has a corresponding ViewModel class.
147
	// The ViewModel is responsible for getting the objects to edit from the
148
	// data access tier. Since this snippet doesn't have any persistent objects
149
	// ro retrieve, this ViewModel just instantiates a model object to edit.
150
	static class ViewModel {
151
		// The model to bind
152
		private IObservableList people = new WritableList();
153
		{
154
			Person fergus = new Person("Fergus McDuck", UNKNOWN, UNKNOWN);
155
			Person downy = new Person("Downy O'Drake", UNKNOWN, UNKNOWN);
156
			Person scrooge = new Person("Scrooge McDuck", downy, fergus);
157
			Person hortense = new Person("Hortense McDuck", downy, fergus);
158
			Person quackmore = new Person("Quackmore Duck", UNKNOWN, UNKNOWN);
159
			Person della = new Person("Della Duck", hortense, quackmore);
160
			Person donald = new Person("Donald Duck", hortense, quackmore);
161
			donald.setFather(quackmore);
162
			donald.setMother(hortense);
163
			della.setFather(quackmore);
164
			della.setMother(hortense);
165
			hortense.setMother(downy);
166
			hortense.setFather(fergus);
167
			scrooge.setMother(downy);
168
			scrooge.setFather(fergus);
169
			people.add(UNKNOWN);
170
			people.add(downy);
171
			people.add(fergus);
172
			people.add(scrooge);
173
			people.add(quackmore);
174
			people.add(hortense);
175
			people.add(della);
176
			people.add(donald);
177
		}
178
179
		public IObservableList getPeople() {
180
			return people;
181
		}
182
	}
183
184
	// The GUI view
185
	static class View {
186
		private ViewModel viewModel;
187
		private Table duckFamily;
188
		private Text nameText;
189
		private Combo motherCombo;
190
		private Combo fatherCombo;
191
192
		public View(ViewModel viewModel) {
193
			this.viewModel = viewModel;
194
		}
195
196
		public Shell createShell() {
197
			// Build a UI
198
			Display display = Display.getDefault();
199
			Shell shell = new Shell(display);
200
			duckFamily = new Table(shell, SWT.BORDER | SWT.FULL_SELECTION);
201
			duckFamily.setHeaderVisible(true);
202
			GridDataFactory.defaultsFor(duckFamily).span(2, 1).applyTo(
203
					duckFamily);
204
			createColumn("Name");
205
			createColumn("Mother");
206
			createColumn("Father");
207
			createColumn("Maternal Grandmother");
208
			createColumn("Maternal Grandfather");
209
			createColumn("Paternal Grandmother");
210
			createColumn("Paternal Grandfather");
211
212
			duckFamily.setLinesVisible(true);
213
214
			new Label(shell, SWT.NONE).setText("Name:");
215
			nameText = new Text(shell, SWT.BORDER);
216
			GridDataFactory.defaultsFor(nameText).grab(true, false).applyTo(
217
					nameText);
218
219
			new Label(shell, SWT.NONE).setText("Mother:");
220
			motherCombo = new Combo(shell, SWT.READ_ONLY);
221
222
			new Label(shell, SWT.NONE).setText("Father:");
223
			fatherCombo = new Combo(shell, SWT.READ_ONLY);
224
225
			DataBindingContext bindingContext = new DataBindingContext();
226
			bindGUI(bindingContext);
227
228
			GridLayoutFactory.swtDefaults().numColumns(2).applyTo(shell);
229
			// Open and return the Shell
230
			shell.setSize(800, 300);
231
			shell.open();
232
			return shell;
233
		}
234
235
		private void createColumn(String string) {
236
			final TableColumn column = new TableColumn(duckFamily, SWT.NONE);
237
			column.setText(string);
238
			column.pack();
239
			if (column.getWidth() < 100)
240
				column.setWidth(100);
241
		}
242
243
		protected void bindGUI(DataBindingContext dbc) {
244
			// Since we're using a JFace Viewer, we do first wrap our Table...
245
			TableViewer peopleViewer = new TableViewer(duckFamily);
246
			peopleViewer.addFilter(new ViewerFilter() {
247
				public boolean select(Viewer viewer, Object parentElement,
248
						Object element) {
249
					return element != UNKNOWN;
250
				}
251
			});
252
253
			// Create a standard content provider
254
			ObservableListContentProvider peopleViewerContentProvider = new ObservableListContentProvider();
255
			peopleViewer.setContentProvider(peopleViewerContentProvider);
256
257
			// And a standard label provider that maps columns
258
			IObservableSet knownElements = peopleViewerContentProvider
259
					.getKnownElements();
260
261
			IValueProperty name = BeanProperties.value(Person.class, "name");
262
			IValueProperty mother = BeanProperties
263
					.value(Person.class, "mother");
264
			IValueProperty father = BeanProperties
265
					.value(Person.class, "father");
266
			IValueProperty viewerSelectionProperty = SelectionProviderProperties
267
					.singleSelection();
268
			IValueProperty textOfTextProperty = TextProperties.text(SWT.Modify);
269
270
			peopleViewer.setLabelProvider(new ObservableMapLabelProvider(
271
					new IObservableMap[] {
272
					// name
273
							name.observeDetailValues(knownElements),
274
							// mother's name
275
							mother.chain(name).observeDetailValues(
276
									knownElements),
277
							// father's name
278
							father.chain(name).observeDetailValues(
279
									knownElements),
280
							// maternal grandmother's name
281
							mother.chain(mother).chain(name)
282
									.observeDetailValues(knownElements),
283
							// maternal grandfather's name
284
							mother.chain(father).chain(name)
285
									.observeDetailValues(knownElements),
286
							// paternal grandmother's name
287
							father.chain(mother).chain(name)
288
									.observeDetailValues(knownElements),
289
							// paternal grandfather's name
290
							father.chain(father).chain(name)
291
									.observeDetailValues(knownElements) }));
292
293
			// Now set the Viewer's input
294
			peopleViewer.setInput(viewModel.getPeople());
295
296
			IObservableValue masterSelection = viewerSelectionProperty
297
					.observeValue(peopleViewer);
298
299
			dbc.bindValue(textOfTextProperty.observeValue(nameText), name
300
					.observeDetailValue(masterSelection), null, null);
301
302
			ComboViewer mothercomboViewer = new ComboViewer(motherCombo);
303
			ObservableListContentProvider motherComboContentProvider = new ObservableListContentProvider();
304
			mothercomboViewer.setContentProvider(motherComboContentProvider);
305
			mothercomboViewer.setLabelProvider(new ObservableMapLabelProvider(
306
					name.observeDetailValues(motherComboContentProvider
307
							.getKnownElements())));
308
			mothercomboViewer.setInput(viewModel.getPeople());
309
310
			dbc.bindValue(viewerSelectionProperty
311
					.observeValue(mothercomboViewer), mother
312
					.observeDetailValue(masterSelection), null, null);
313
314
			ComboViewer fatherComboViewer = new ComboViewer(fatherCombo);
315
			ObservableListContentProvider fatherComboContentProvider = new ObservableListContentProvider();
316
			fatherComboViewer.setContentProvider(fatherComboContentProvider);
317
			fatherComboViewer.setLabelProvider(new ObservableMapLabelProvider(
318
					name.observeDetailValues(fatherComboContentProvider
319
							.getKnownElements())));
320
			fatherComboViewer.setInput(viewModel.getPeople());
321
322
			dbc.bindValue(viewerSelectionProperty
323
					.observeValue(fatherComboViewer), father
324
					.observeDetailValue(masterSelection), null, null);
325
		}
326
	}
327
}
(-)src/org/eclipse/jface/internal/databinding/swt/ListObservableValue.java (-109 lines)
Removed Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2005, 2008 IBM Corporation and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
10
 *     Brad Reynolds - bug 164653
11
 *     Ashley Cambrell - bug 198904
12
 *******************************************************************************/
13
package org.eclipse.jface.internal.databinding.swt;
14
15
import org.eclipse.core.databinding.observable.Diffs;
16
import org.eclipse.jface.internal.databinding.provisional.swt.AbstractSWTObservableValue;
17
import org.eclipse.swt.SWT;
18
import org.eclipse.swt.widgets.Event;
19
import org.eclipse.swt.widgets.List;
20
import org.eclipse.swt.widgets.Listener;
21
22
/**
23
 * @since 3.2
24
 * 
25
 */
26
public class ListObservableValue extends AbstractSWTObservableValue {
27
28
	private final List list;
29
30
	private boolean updating = false;
31
32
	private String currentValue;
33
34
	private Listener listener;
35
36
	/**
37
	 * @param list
38
	 */
39
	public ListObservableValue(List list) {
40
		super(list);
41
		this.list = list;
42
		this.currentValue = (String) doGetValue();
43
44
		if ((list.getStyle() & SWT.MULTI) > 0)
45
			throw new IllegalArgumentException(
46
					"SWT.SINGLE support only for a List selection"); //$NON-NLS-1$
47
48
		listener = new Listener() {
49
50
			public void handleEvent(Event event) {
51
				if (!updating) {
52
					Object oldValue = currentValue;
53
					currentValue = (String) doGetValue();
54
					fireValueChange(Diffs.createValueDiff(oldValue,
55
							currentValue));
56
				}
57
			}
58
59
		};
60
		list.addListener(SWT.Selection, listener);
61
	}
62
63
	public void doSetValue(Object value) {
64
		String oldValue = null;
65
		if (list.getSelection() != null && list.getSelection().length > 0)
66
			oldValue = list.getSelection()[0];
67
		try {
68
			updating = true;
69
			String items[] = list.getItems();
70
			int index = -1;
71
			if (items != null && value != null) {
72
				for (int i = 0; i < items.length; i++) {
73
					if (value.equals(items[i])) {
74
						index = i;
75
						break;
76
					}
77
				}
78
				list.select(index); // -1 will not "unselect"
79
			}
80
			currentValue = (String) value;
81
		} finally {
82
			updating = false;
83
		}
84
		fireValueChange(Diffs.createValueDiff(oldValue, value));
85
	}
86
87
	public Object doGetValue() {
88
		int index = list.getSelectionIndex();
89
		if (index >= 0)
90
			return list.getItem(index);
91
		return null;
92
	}
93
94
	public Object getValueType() {
95
		return String.class;
96
	}
97
98
	/*
99
	 * (non-Javadoc)
100
	 *
101
	 * @see org.eclipse.core.databinding.observable.value.AbstractObservableValue#dispose()
102
	 */
103
	public synchronized void dispose() {
104
		super.dispose();
105
		if (listener != null && !list.isDisposed()) {
106
			list.removeListener(SWT.Selection, listener);
107
		}
108
	}
109
}
(-)src/org/eclipse/jface/internal/databinding/swt/CComboSingleSelectionObservableValue.java (-81 lines)
Removed Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2005, 2008 IBM Corporation and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
10
 *     Brad Reynolds - bug 164653
11
 *     Ashley Cambrell - bug 198904
12
 *******************************************************************************/
13
package org.eclipse.jface.internal.databinding.swt;
14
15
import org.eclipse.core.databinding.observable.Realm;
16
import org.eclipse.swt.custom.CCombo;
17
import org.eclipse.swt.events.SelectionEvent;
18
import org.eclipse.swt.events.SelectionListener;
19
20
/**
21
 * @since 1.0
22
 *
23
 */
24
public class CComboSingleSelectionObservableValue extends
25
		SingleSelectionObservableValue {
26
27
	private SelectionListener selectionListener;
28
29
	/**
30
	 * @param combo
31
	 */
32
	public CComboSingleSelectionObservableValue(CCombo combo) {
33
		super(combo);
34
	}
35
	
36
	/**
37
	 * @param realm
38
	 * @param combo
39
	 */
40
	public CComboSingleSelectionObservableValue(Realm realm, CCombo combo) {
41
		super(realm, combo);
42
	}
43
44
	private CCombo getCCombo() {
45
		return (CCombo) getWidget();
46
	}
47
48
	protected void doAddSelectionListener(final Runnable runnable) {
49
		selectionListener = new SelectionListener() {
50
			public void widgetDefaultSelected(SelectionEvent e) {
51
				runnable.run();
52
			}
53
54
			public void widgetSelected(SelectionEvent e) {
55
				runnable.run();
56
			}
57
		};
58
		getCCombo().addSelectionListener(selectionListener);
59
	}
60
61
	protected int doGetSelectionIndex() {
62
		return getCCombo().getSelectionIndex();
63
	}
64
65
	protected void doSetSelectionIndex(int index) {
66
		getCCombo().setText(getCCombo().getItem(index));
67
	}
68
69
	/*
70
	 * (non-Javadoc)
71
	 *
72
	 * @see org.eclipse.core.databinding.observable.value.AbstractObservableValue#dispose()
73
	 */
74
	public synchronized void dispose() {
75
		super.dispose();
76
		if (selectionListener != null && !getCCombo().isDisposed()) {
77
			getCCombo().removeSelectionListener(selectionListener);
78
		}
79
80
	}
81
}
(-)src/org/eclipse/jface/internal/databinding/swt/ShellObservableValue.java (-74 lines)
Removed Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2007 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 207844)
10
 *     IBM Corporation - initial API and implementation
11
 *     Brad Reynolds - initial API and implementation
12
 *     Matthew Hall - bug 212235
13
 *******************************************************************************/
14
package org.eclipse.jface.internal.databinding.swt;
15
16
import org.eclipse.core.databinding.observable.Diffs;
17
import org.eclipse.core.databinding.observable.Realm;
18
import org.eclipse.core.databinding.observable.value.IObservableValue;
19
import org.eclipse.jface.internal.databinding.provisional.swt.AbstractSWTObservableValue;
20
import org.eclipse.swt.widgets.Shell;
21
22
/**
23
 * An {@link IObservableValue} that tracks the text of a Shell.
24
 * 
25
 * @since 1.2
26
 */
27
public class ShellObservableValue extends AbstractSWTObservableValue {
28
29
	private final Shell shell;
30
31
	/**
32
	 * Constructs a ShellObservableValue which tracks the text of the given
33
	 * Shell.
34
	 * 
35
	 * @param shell
36
	 *            the shell to track
37
	 */
38
	public ShellObservableValue(Shell shell) {
39
		super(shell);
40
		this.shell = shell;
41
	}
42
43
	/**
44
	 * Constructs a ShellObservableValue belonging to the given realm, which
45
	 * tracks the text of the given shell.
46
	 * 
47
	 * @param realm
48
	 *            the realm of the constructed observable
49
	 * @param shell
50
	 *            the shell to track
51
	 */
52
	public ShellObservableValue(Realm realm, Shell shell) {
53
		super(realm, shell);
54
		this.shell = shell;
55
	}
56
57
	protected void doSetValue(final Object value) {
58
		String oldValue = shell.getText();
59
		String newValue = value == null ? "" : value.toString(); //$NON-NLS-1$
60
		shell.setText(newValue);
61
62
		if (!newValue.equals(oldValue)) {
63
			fireValueChange(Diffs.createValueDiff(oldValue, newValue));
64
		}
65
	}
66
67
	protected Object doGetValue() {
68
		return shell.getText();
69
	}
70
71
	public Object getValueType() {
72
		return String.class;
73
	}
74
}
(-)src/org/eclipse/jface/internal/databinding/swt/CComboObservableList.java (-51 lines)
Removed Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2005, 2008 IBM Corporation and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
10
 *******************************************************************************/
11
package org.eclipse.jface.internal.databinding.swt;
12
13
import org.eclipse.jface.databinding.swt.SWTObservables;
14
import org.eclipse.swt.custom.CCombo;
15
16
/**
17
 * @since 3.2
18
 * 
19
 */
20
public class CComboObservableList extends SWTObservableList {
21
22
	private final CCombo ccombo;
23
24
	/**
25
	 * @param ccombo
26
	 */
27
	public CComboObservableList(CCombo ccombo) {
28
		super(SWTObservables.getRealm(ccombo.getDisplay()));
29
		this.ccombo = ccombo;
30
	}
31
32
	protected int getItemCount() {
33
		return ccombo.getItemCount();
34
	}
35
36
	protected void setItems(String[] newItems) {
37
		ccombo.setItems(newItems);
38
	}
39
40
	protected String[] getItems() {
41
		return ccombo.getItems();
42
	}
43
44
	protected String getItem(int index) {
45
		return ccombo.getItem(index);
46
	}
47
48
	protected void setItem(int index, String string) {
49
		ccombo.setItem(index, string);
50
	}
51
}
(-)src/org/eclipse/jface/internal/databinding/swt/ScaleObservableValue.java (-150 lines)
Removed Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2005, 2008 IBM Corporation and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
10
 *     Peter Centgraf - bug 175763
11
 *******************************************************************************/
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.core.databinding.observable.Diffs;
15
import org.eclipse.core.databinding.observable.Realm;
16
import org.eclipse.core.runtime.Assert;
17
import org.eclipse.jface.internal.databinding.provisional.swt.AbstractSWTObservableValue;
18
import org.eclipse.swt.events.SelectionAdapter;
19
import org.eclipse.swt.events.SelectionEvent;
20
import org.eclipse.swt.events.SelectionListener;
21
import org.eclipse.swt.widgets.Scale;
22
23
/**
24
 * @since 1.0
25
 * 
26
 */
27
public class ScaleObservableValue extends AbstractSWTObservableValue {
28
29
	private final Scale scale;
30
31
	private final String attribute;
32
33
	private boolean updating = false;
34
35
	private int currentSelection;
36
	
37
	private SelectionListener listener;
38
39
	/**
40
	 * @param scale
41
	 * @param attribute
42
	 */
43
	public ScaleObservableValue(Scale scale, String attribute) {
44
		super(scale);
45
		this.scale = scale;
46
		this.attribute = attribute;
47
		init();
48
	}
49
	
50
	/**
51
	 * @param realm
52
	 * @param scale
53
	 * @param attribute
54
	 */
55
	public ScaleObservableValue(Realm realm, Scale scale, String attribute) {
56
		super(realm, scale);
57
		this.scale = scale;
58
		this.attribute = attribute;
59
		init();
60
	}
61
	
62
	private void init() {		
63
		if (attribute.equals(SWTProperties.SELECTION)) {
64
			currentSelection = scale.getSelection();
65
			scale.addSelectionListener(listener = new SelectionAdapter() {
66
				public void widgetSelected(SelectionEvent e) {
67
					if (!updating) {
68
						int newSelection = ScaleObservableValue.this.scale
69
						.getSelection();
70
						notifyIfChanged(currentSelection, newSelection);
71
						currentSelection = newSelection;
72
					}
73
				}
74
			});
75
		} else if (!attribute.equals(SWTProperties.MIN)
76
				&& !attribute.equals(SWTProperties.MAX)) {
77
			throw new IllegalArgumentException(
78
					"Attribute name not valid: " + attribute); //$NON-NLS-1$
79
		}
80
	}
81
82
	public void doSetValue(final Object value) {
83
		int oldValue;
84
		int newValue;
85
		try {
86
			updating = true;
87
			newValue = ((Integer) value).intValue();
88
			if (attribute.equals(SWTProperties.SELECTION)) {
89
				oldValue = scale.getSelection();
90
				scale.setSelection(newValue);
91
				currentSelection = newValue;
92
			} else if (attribute.equals(SWTProperties.MIN)) {
93
				oldValue = scale.getMinimum();
94
				scale.setMinimum(newValue);
95
			} else if (attribute.equals(SWTProperties.MAX)) {
96
				oldValue = scale.getMaximum();
97
				scale.setMaximum(newValue);
98
			} else {
99
				Assert.isTrue(false, "invalid attribute name:" + attribute); //$NON-NLS-1$
100
				return;
101
			}
102
			
103
			notifyIfChanged(oldValue, newValue);
104
		} finally {
105
			updating = false;
106
		}
107
	}
108
109
	public Object doGetValue() {
110
		int value = 0;
111
		if (attribute.equals(SWTProperties.SELECTION)) {
112
			value = scale.getSelection();
113
		} else if (attribute.equals(SWTProperties.MIN)) {
114
			value = scale.getMinimum();
115
		} else if (attribute.equals(SWTProperties.MAX)) {
116
			value = scale.getMaximum();
117
		}
118
		return new Integer(value);
119
	}
120
121
	public Object getValueType() {
122
		return Integer.TYPE;
123
	}
124
125
	/**
126
	 * @return attribute being observed
127
	 */
128
	public String getAttribute() {
129
		return attribute;
130
	}
131
	
132
	/* (non-Javadoc)
133
	 * @see org.eclipse.core.databinding.observable.value.AbstractObservableValue#dispose()
134
	 */
135
	public synchronized void dispose() {
136
		super.dispose();
137
		
138
		if (listener != null && !scale.isDisposed()) {
139
			scale.removeSelectionListener(listener);
140
		}
141
		listener = null;
142
	}
143
	
144
	private void notifyIfChanged(int oldValue, int newValue) {
145
		if (oldValue != newValue) {
146
			fireValueChange(Diffs.createValueDiff(new Integer(oldValue),
147
					new Integer(newValue)));
148
		}
149
	}
150
}
(-)src/org/eclipse/jface/internal/databinding/swt/CComboObservableValue.java (-166 lines)
Removed Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2005, 2008 IBM Corporation and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
10
 *     Brad Reynolds - bug 164653
11
 *     Ashley Cambrell - bug 198904
12
 *     Matthew Hall - bug 118516
13
 *     Eric Rizzo - bug 134884
14
 *******************************************************************************/
15
package org.eclipse.jface.internal.databinding.swt;
16
17
import org.eclipse.core.databinding.observable.Diffs;
18
import org.eclipse.core.databinding.observable.Realm;
19
import org.eclipse.core.runtime.Assert;
20
import org.eclipse.jface.internal.databinding.provisional.swt.AbstractSWTObservableValue;
21
import org.eclipse.swt.custom.CCombo;
22
import org.eclipse.swt.events.ModifyEvent;
23
import org.eclipse.swt.events.ModifyListener;
24
25
/**
26
 * @since 3.2
27
 * 
28
 */
29
public class CComboObservableValue extends AbstractSWTObservableValue {
30
31
	/**
32
	 * 
33
	 */
34
35
	private final CCombo ccombo;
36
37
	private final String attribute;
38
39
	private boolean updating = false;
40
41
	private String currentValue;
42
43
	private ModifyListener modifyListener;
44
45
	/**
46
	 * @param ccombo
47
	 * @param attribute
48
	 */
49
	public CComboObservableValue(CCombo ccombo, String attribute) {
50
		super(ccombo);
51
		this.ccombo = ccombo;
52
		this.attribute = attribute;
53
		init();
54
	}
55
56
	/**
57
	 * @param realm
58
	 * @param ccombo
59
	 * @param attribute
60
	 */
61
	public CComboObservableValue(Realm realm, CCombo ccombo, String attribute) {
62
		super(realm, ccombo);
63
		this.ccombo = ccombo;
64
		this.attribute = attribute;
65
		init();
66
	}
67
	
68
	private void init() {		
69
		if (attribute.equals(SWTProperties.SELECTION)
70
				|| attribute.equals(SWTProperties.TEXT)) {
71
			this.currentValue = ccombo.getText();
72
			modifyListener = new ModifyListener() {
73
74
				public void modifyText(ModifyEvent e) {
75
					if (!updating) {
76
						String oldValue = currentValue;
77
						currentValue = CComboObservableValue.this.ccombo
78
								.getText();
79
						
80
						notifyIfChanged(oldValue, currentValue);
81
					}
82
				}
83
			};
84
			ccombo.addModifyListener(modifyListener);
85
		} else
86
			throw new IllegalArgumentException();
87
	}
88
89
	public void doSetValue(final Object value) {
90
		String oldValue = ccombo.getText();
91
		try {
92
			updating = true;
93
			if (attribute.equals(SWTProperties.TEXT)) {
94
				String stringValue = value != null ? value.toString() : ""; //$NON-NLS-1$
95
				ccombo.setText(stringValue);
96
			} else if (attribute.equals(SWTProperties.SELECTION)) {
97
				String items[] = ccombo.getItems();
98
				int index = -1;
99
				if (value == null) {
100
					ccombo.select(-1);
101
				} else if (items != null) {
102
					for (int i = 0; i < items.length; i++) {
103
						if (value.equals(items[i])) {
104
							index = i;
105
							break;
106
						}
107
					}
108
					if (index == -1) {
109
						ccombo.setText((String) value);
110
					} else {
111
						ccombo.select(index); // -1 will not "unselect"
112
					}
113
				}
114
			}
115
		} finally {
116
			updating = false;
117
			currentValue = ccombo.getText();
118
		}
119
		
120
		notifyIfChanged(oldValue, currentValue);
121
	}
122
123
	public Object doGetValue() {
124
		if (attribute.equals(SWTProperties.TEXT))
125
			return ccombo.getText();
126
127
		Assert.isTrue(attribute.equals(SWTProperties.SELECTION),
128
				"unexpected attribute: " + attribute); //$NON-NLS-1$
129
		// The problem with a ccombo, is that it changes the text and
130
		// fires before it update its selection index
131
		return ccombo.getText();
132
	}
133
134
	public Object getValueType() {
135
		Assert.isTrue(attribute.equals(SWTProperties.TEXT)
136
				|| attribute.equals(SWTProperties.SELECTION),
137
				"unexpected attribute: " + attribute); //$NON-NLS-1$
138
		return String.class;
139
	}
140
141
	/**
142
	 * @return attribute being observed
143
	 */
144
	public String getAttribute() {
145
		return attribute;
146
	}
147
148
	/*
149
	 * (non-Javadoc)
150
	 *
151
	 * @see org.eclipse.core.databinding.observable.value.AbstractObservableValue#dispose()
152
	 */
153
	public synchronized void dispose() {
154
		super.dispose();
155
156
		if (modifyListener != null && !ccombo.isDisposed()) {
157
			ccombo.removeModifyListener(modifyListener);
158
		}
159
	}
160
	
161
	private void notifyIfChanged(String oldValue, String newValue) {
162
		if (!oldValue.equals(newValue)) {
163
			fireValueChange(Diffs.createValueDiff(oldValue, ccombo.getText()));			
164
		}
165
	}
166
}
(-)src/org/eclipse/jface/internal/databinding/swt/TableSingleSelectionObservableValue.java (-80 lines)
Removed Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2005, 2008 IBM Corporation and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
10
 *     Brad Reynolds - bug 164653
11
 *     Ashley Cambrell - bug 198904
12
 *******************************************************************************/
13
package org.eclipse.jface.internal.databinding.swt;
14
15
import org.eclipse.core.databinding.observable.Realm;
16
import org.eclipse.swt.events.SelectionEvent;
17
import org.eclipse.swt.events.SelectionListener;
18
import org.eclipse.swt.widgets.Table;
19
20
/**
21
 * @since 1.0
22
 * 
23
 */
24
public class TableSingleSelectionObservableValue extends
25
		SingleSelectionObservableValue {
26
27
	private SelectionListener selectionListener;
28
29
	/**
30
	 * @param table
31
	 */
32
	public TableSingleSelectionObservableValue(Table table) {
33
		super(table);
34
	}
35
	
36
	/**
37
	 * @param realm
38
	 * @param table
39
	 */
40
	public TableSingleSelectionObservableValue(Realm realm, Table table) {
41
		super(realm, table);
42
	}
43
44
	private Table getTable() {
45
		return (Table) getWidget();
46
	}
47
48
	protected void doAddSelectionListener(final Runnable runnable) {
49
		selectionListener = new SelectionListener() {
50
			public void widgetDefaultSelected(SelectionEvent e) {
51
				runnable.run();
52
			}
53
54
			public void widgetSelected(SelectionEvent e) {
55
				runnable.run();
56
			}
57
		};
58
		getTable().addSelectionListener(selectionListener);
59
	}
60
61
	protected int doGetSelectionIndex() {
62
		return getTable().getSelectionIndex();
63
	}
64
65
	protected void doSetSelectionIndex(int index) {
66
		getTable().setSelection(index);
67
	}
68
69
	/*
70
	 * (non-Javadoc)
71
	 *
72
	 * @see org.eclipse.core.databinding.observable.value.AbstractObservableValue#dispose()
73
	 */
74
	public synchronized void dispose() {
75
		super.dispose();
76
		if (selectionListener != null && !getTable().isDisposed()) {
77
			getTable().removeSelectionListener(selectionListener);
78
		}
79
	}
80
}
(-)src/org/eclipse/jface/internal/databinding/swt/SWTObservableList.java (-193 lines)
Removed Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2005, 2008 IBM Corporation and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
10
 *     Matthew Hall - bug 208858
11
 *******************************************************************************/
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import java.util.ArrayList;
15
import java.util.Arrays;
16
import java.util.Collection;
17
import java.util.List;
18
19
import org.eclipse.core.databinding.BindingException;
20
import org.eclipse.core.databinding.observable.Diffs;
21
import org.eclipse.core.databinding.observable.ObservableTracker;
22
import org.eclipse.core.databinding.observable.Realm;
23
import org.eclipse.core.databinding.observable.list.AbstractObservableList;
24
25
/**
26
 * Abstract base class of CComboObservableList, ComboObservableList, and
27
 * ListObservableList.
28
 * 
29
 * @since 3.2
30
 * 
31
 */
32
public abstract class SWTObservableList extends AbstractObservableList {
33
34
	/**
35
	 * 
36
	 */
37
	public SWTObservableList() {
38
		super();
39
	}
40
41
	/**
42
	 * @param realm
43
	 */
44
	public SWTObservableList(Realm realm) {
45
		super(realm);
46
	}
47
48
	public void add(int index, Object element) {
49
		int size = doGetSize();
50
		if (index < 0 || index > size)
51
			index = size;
52
		String[] newItems = new String[size + 1];
53
		System.arraycopy(getItems(), 0, newItems, 0, index);
54
		newItems[index] = (String) element;
55
		System.arraycopy(getItems(), index, newItems, index + 1, size - index);
56
		setItems(newItems);
57
		fireListChange(Diffs.createListDiff(Diffs.createListDiffEntry(index,
58
				true, element)));
59
	}
60
61
	public int doGetSize() {
62
		return getItemCount();
63
	}
64
65
	public Object get(int index) {
66
		getterCalled();
67
		return getItem(index);
68
	}
69
70
	public Object getElementType() {
71
		return String.class;
72
	}
73
74
	/**
75
	 * @param index
76
	 * @return the item at the given index
77
	 */
78
	protected abstract String getItem(int index);
79
80
	/**
81
	 * @return the item count
82
	 */
83
	protected abstract int getItemCount();
84
85
	/**
86
	 * @return the items
87
	 */
88
	protected abstract String[] getItems();
89
90
	private void getterCalled() {
91
		ObservableTracker.getterCalled(this);
92
	}
93
94
	public Object remove(int index) {
95
		getterCalled();
96
		int size = doGetSize();
97
		if (index < 0 || index > size - 1)
98
			throw new BindingException(
99
					"Request to remove an element out of the collection bounds"); //$NON-NLS-1$
100
101
		String[] newItems = new String[size - 1];
102
		String oldElement = getItem(index);
103
		if (newItems.length > 0) {
104
			System.arraycopy(getItems(), 0, newItems, 0, index);
105
			if (size - 1 > index) {
106
				System.arraycopy(getItems(), index + 1, newItems, index, size
107
						- index - 1);
108
			}
109
		}
110
		setItems(newItems);
111
		fireListChange(Diffs.createListDiff(Diffs.createListDiffEntry(index,
112
				false, oldElement)));
113
		return oldElement;
114
	}
115
116
	public Object set(int index, Object element) {
117
		String oldElement = getItem(index);
118
		setItem(index, (String) element);
119
		fireListChange(Diffs.createListDiff(Diffs.createListDiffEntry(index,
120
				false, oldElement), Diffs.createListDiffEntry(index, true,
121
				element)));
122
		return oldElement;
123
	}
124
125
	public Object move(int oldIndex, int newIndex) {
126
		checkRealm();
127
		if (oldIndex == newIndex)
128
			return get(oldIndex);
129
		int size = doGetSize();
130
		if (oldIndex < 0 || oldIndex >= size)
131
			throw new IndexOutOfBoundsException(
132
					"oldIndex: " + oldIndex + ", size:" + size); //$NON-NLS-1$ //$NON-NLS-2$
133
		if (newIndex < 0 || newIndex >= size)
134
			throw new IndexOutOfBoundsException(
135
					"newIndex: " + newIndex + ", size:" + size); //$NON-NLS-1$ //$NON-NLS-2$
136
137
		String[] items = getItems();
138
		String[] newItems = new String[size];
139
		String element = items[oldIndex];
140
		if (newItems.length > 0) {
141
			System.arraycopy(items, 0, newItems, 0, size);
142
			if (oldIndex < newIndex) {
143
				System.arraycopy(items, oldIndex + 1, newItems, oldIndex,
144
						newIndex - oldIndex);
145
			} else {
146
				System.arraycopy(items, newIndex, newItems, newIndex + 1,
147
						oldIndex - newIndex);
148
			}
149
			newItems[newIndex] = element;
150
		}
151
		setItems(newItems);
152
		fireListChange(Diffs.createListDiff(Diffs.createListDiffEntry(oldIndex,
153
				false, element), Diffs.createListDiffEntry(newIndex, true,
154
				element)));
155
		return element;
156
	}
157
158
	public boolean removeAll(Collection c) {
159
		checkRealm();
160
		List oldItems = Arrays.asList(getItems());
161
		List newItems = new ArrayList(oldItems);
162
		boolean removedAll = newItems.removeAll(c);
163
		if (removedAll) {
164
			setItems((String[]) newItems.toArray(new String[newItems.size()]));
165
			fireListChange(Diffs.computeListDiff(oldItems, newItems));
166
		}
167
		return removedAll;
168
	}
169
170
	public boolean retainAll(Collection c) {
171
		checkRealm();
172
		List oldItems = Arrays.asList(getItems());
173
		List newItems = new ArrayList(oldItems);
174
		boolean retainedAll = newItems.retainAll(c);
175
		if (retainedAll) {
176
			setItems((String[]) newItems.toArray(new String[newItems.size()]));
177
			fireListChange(Diffs.computeListDiff(oldItems, newItems));
178
		}
179
		return retainedAll;
180
	}
181
182
	/**
183
	 * @param index
184
	 * @param string
185
	 */
186
	protected abstract void setItem(int index, String string);
187
188
	/**
189
	 * @param newItems
190
	 */
191
	protected abstract void setItems(String[] newItems);
192
193
}
(-)src/org/eclipse/jface/internal/databinding/swt/TextEditableObservableValue.java (-75 lines)
Removed Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2007, 2008 IBM Corporation and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
10
 *******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.core.databinding.observable.Diffs;
15
import org.eclipse.core.databinding.observable.Realm;
16
import org.eclipse.jface.internal.databinding.provisional.swt.AbstractSWTObservableValue;
17
import org.eclipse.swt.widgets.Text;
18
19
/**
20
 * Observable value for the editable property of a Text.
21
 * 
22
 * @since 1.1
23
 */
24
public class TextEditableObservableValue extends AbstractSWTObservableValue {
25
	private Text text;
26
	
27
	/**
28
	 * @param text
29
	 */
30
	public TextEditableObservableValue(Text text) {
31
		super(text);	
32
		this.text = text;
33
	}
34
	
35
	/**
36
	 * @param realm
37
	 * @param text
38
	 */
39
	public TextEditableObservableValue(Realm realm, Text text) {
40
		super(realm, text);
41
		this.text = text;
42
	}
43
44
	/* (non-Javadoc)
45
	 * @see org.eclipse.core.databinding.observable.value.AbstractObservableValue#doGetValue()
46
	 */
47
	protected Object doGetValue() {
48
		return (text.getEditable()) ? Boolean.TRUE : Boolean.FALSE;
49
	}
50
	
51
	/* (non-Javadoc)
52
	 * @see org.eclipse.core.databinding.observable.value.IObservableValue#getValueType()
53
	 */
54
	public Object getValueType() {
55
		return Boolean.TYPE;
56
	}
57
	
58
	/* (non-Javadoc)
59
	 * @see org.eclipse.core.databinding.observable.value.AbstractObservableValue#doSetValue(java.lang.Object)
60
	 */
61
	protected void doSetValue(Object value) {
62
		if (value == null) {
63
			throw new IllegalArgumentException("Parameter value was null."); //$NON-NLS-1$
64
		}
65
		
66
		Boolean oldValue = new Boolean(text.getEditable());
67
		Boolean newValue = (Boolean) value;
68
		
69
		text.setEditable(newValue.booleanValue());
70
		
71
		if (!oldValue.equals(newValue)) {
72
			fireValueChange(Diffs.createValueDiff(oldValue, newValue));
73
		}
74
	}
75
}
(-)src/org/eclipse/jface/internal/databinding/swt/ComboObservableList.java (-51 lines)
Removed Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2005, 2008 IBM Corporation and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
10
 *******************************************************************************/
11
package org.eclipse.jface.internal.databinding.swt;
12
13
import org.eclipse.jface.databinding.swt.SWTObservables;
14
import org.eclipse.swt.widgets.Combo;
15
16
/**
17
 * @since 3.2
18
 * 
19
 */
20
public class ComboObservableList extends SWTObservableList {
21
22
	private final Combo combo;
23
24
	/**
25
	 * @param combo
26
	 */
27
	public ComboObservableList(Combo combo) {
28
		super(SWTObservables.getRealm(combo.getDisplay()));
29
		this.combo = combo;
30
	}
31
32
	protected int getItemCount() {
33
		return combo.getItemCount();
34
	}
35
36
	protected void setItems(String[] newItems) {
37
		combo.setItems(newItems);
38
	}
39
40
	protected String[] getItems() {
41
		return combo.getItems();
42
	}
43
44
	protected String getItem(int index) {
45
		return combo.getItem(index);
46
	}
47
48
	protected void setItem(int index, String string) {
49
		combo.setItem(index, string);
50
	}
51
}
(-)src/org/eclipse/jface/internal/databinding/swt/ItemObservableValue.java (-61 lines)
Removed Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2005, 2008 IBM Corporation and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
10
 *******************************************************************************/
11
package org.eclipse.jface.internal.databinding.swt;
12
13
import org.eclipse.core.databinding.observable.Diffs;
14
import org.eclipse.core.databinding.observable.Realm;
15
import org.eclipse.jface.internal.databinding.provisional.swt.AbstractSWTObservableValue;
16
import org.eclipse.swt.widgets.Item;
17
18
/**
19
 * @since 3.5
20
 * 
21
 */
22
public class ItemObservableValue extends AbstractSWTObservableValue {
23
24
	private final Item item;
25
26
	/**
27
	 * @param item
28
	 */
29
	public ItemObservableValue(Item item) {
30
		super(item);
31
		this.item = item;
32
	}
33
	
34
	/**
35
	 * @param realm
36
	 * @param item
37
	 */
38
	public ItemObservableValue(Realm realm, Item item) {
39
		super(realm, item);
40
		this.item = item;
41
	}
42
43
	public void doSetValue(final Object value) {
44
		String oldValue = item.getText();
45
		String newValue = value == null ? "" : value.toString(); //$NON-NLS-1$
46
		item.setText(newValue);
47
		
48
		if (!newValue.equals(oldValue)) {
49
			fireValueChange(Diffs.createValueDiff(oldValue, newValue));
50
		}
51
	}
52
53
	public Object doGetValue() {
54
		return item.getText();
55
	}
56
57
	public Object getValueType() {
58
		return String.class;
59
	}
60
61
}
(-)src/org/eclipse/jface/internal/databinding/swt/TextObservableValue.java (-198 lines)
Removed Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2005, 2008 IBM Corporation and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
10
 *     Brad Reynolds (bug 135446)
11
 *     Brad Reynolds - bug 164653
12
 *******************************************************************************/
13
package org.eclipse.jface.internal.databinding.swt;
14
15
import org.eclipse.core.databinding.observable.Diffs;
16
import org.eclipse.core.databinding.observable.IObservable;
17
import org.eclipse.core.databinding.observable.Realm;
18
import org.eclipse.jface.databinding.swt.SWTObservables;
19
import org.eclipse.jface.internal.databinding.provisional.swt.AbstractSWTVetoableValue;
20
import org.eclipse.swt.SWT;
21
import org.eclipse.swt.events.VerifyEvent;
22
import org.eclipse.swt.events.VerifyListener;
23
import org.eclipse.swt.widgets.Event;
24
import org.eclipse.swt.widgets.Listener;
25
import org.eclipse.swt.widgets.Text;
26
27
/**
28
 * {@link IObservable} implementation that wraps a {@link Text} widget. The time
29
 * at which listeners should be notified about changes to the text is specified
30
 * on construction.
31
 * 
32
 * <dl>
33
 * <dt>Events:</dt>
34
 * <dd> If the update event type (specified on construction) is
35
 * <code>SWT.Modify</code> a value change event will be fired on every key
36
 * stroke. If the update event type is <code>SWT.FocusOut</code> a value
37
 * change event will be fired on focus out. When in either mode if the user is
38
 * entering text and presses [Escape] the value will be reverted back to the
39
 * last value set using doSetValue(). Regardless of the update event type a
40
 * value changing event will fire on verify to enable vetoing of changes.</dd>
41
 * </dl>
42
 * 
43
 * @since 1.0
44
 */
45
public class TextObservableValue extends AbstractSWTVetoableValue {
46
47
	/**
48
	 * {@link Text} widget that this is being observed.
49
	 */
50
	private final Text text;
51
52
	/**
53
	 * Flag to track when the model is updating the widget. When
54
	 * <code>true</code> the handlers for the SWT events should not process
55
	 * the event as this would cause an infinite loop.
56
	 */
57
	private boolean updating = false;
58
59
	/**
60
	 * SWT event that on firing this observable will fire change events to its
61
	 * listeners.
62
	 */
63
	private final int updateEventType;
64
65
	/**
66
	 * Valid types for the {@link #updateEventType}.
67
	 */
68
	private static final int[] validUpdateEventTypes = new int[] { SWT.Modify,
69
			SWT.FocusOut, SWT.None };
70
71
	/**
72
	 * Previous value of the Text.
73
	 */
74
	private String oldValue;
75
76
	private Listener updateListener = new Listener() {
77
		public void handleEvent(Event event) {
78
			if (!updating) {
79
				String newValue = text.getText();
80
81
				if (!newValue.equals(oldValue)) {
82
					fireValueChange(Diffs.createValueDiff(oldValue, newValue));					
83
					oldValue = newValue;
84
				}
85
			}
86
		}
87
	};
88
89
	private VerifyListener verifyListener;
90
91
	/**
92
	 * Constructs a new instance bound to the given <code>text</code> widget
93
	 * and configured to fire change events to its listeners at the time of the
94
	 * <code>updateEventType</code>.
95
	 * 
96
	 * @param text
97
	 * @param updateEventType
98
	 *            SWT event constant as to what SWT event to update the model in
99
	 *            response to. Appropriate values are: <code>SWT.Modify</code>,
100
	 *            <code>SWT.FocusOut</code>, <code>SWT.None</code>.
101
	 * @throws IllegalArgumentException
102
	 *             if <code>updateEventType</code> is an incorrect type.
103
	 */
104
	public TextObservableValue(final Text text, int updateEventType) {
105
		this(SWTObservables.getRealm(text.getDisplay()), text, updateEventType);
106
	}
107
	
108
	/**
109
	 * Constructs a new instance.
110
	 * 
111
	 * @param realm can not be <code>null</code>
112
	 * @param text
113
	 * @param updateEventType
114
	 */
115
	public TextObservableValue(final Realm realm, Text text, int updateEventType) {
116
		super(realm, text);
117
		
118
		boolean eventValid = false;
119
		for (int i = 0; !eventValid && i < validUpdateEventTypes.length; i++) {
120
			eventValid = (updateEventType == validUpdateEventTypes[i]);
121
		}
122
		if (!eventValid) {
123
			throw new IllegalArgumentException(
124
					"UpdateEventType [" + updateEventType + "] is not supported."); //$NON-NLS-1$//$NON-NLS-2$
125
		}
126
		this.text = text;
127
		this.updateEventType = updateEventType;
128
		if (updateEventType != SWT.None) {
129
			text.addListener(updateEventType, updateListener);
130
		}
131
		
132
		oldValue = text.getText();
133
		
134
		verifyListener = new VerifyListener() {
135
			public void verifyText(VerifyEvent e) {
136
				if (!updating) {
137
					String currentText = TextObservableValue.this.text
138
							.getText();
139
					String newText = currentText.substring(0, e.start) + e.text
140
							+ currentText.substring(e.end);
141
					if (!fireValueChanging(Diffs.createValueDiff(currentText,
142
							newText))) {
143
						e.doit = false;
144
					}
145
				}
146
			}
147
		};
148
		text.addVerifyListener(verifyListener);
149
	}
150
151
	/**
152
	 * Sets the bound {@link Text Text's} text to the passed <code>value</code>.
153
	 * 
154
	 * @param value
155
	 *            new value, String expected
156
	 * @see org.eclipse.core.databinding.observable.value.AbstractVetoableValue#doSetApprovedValue(java.lang.Object)
157
	 * @throws ClassCastException
158
	 *             if the value is anything other than a String
159
	 */
160
	protected void doSetApprovedValue(final Object value) {
161
		try {
162
			updating = true;
163
			text.setText(value == null ? "" : value.toString()); //$NON-NLS-1$
164
			oldValue = text.getText();
165
		} finally {
166
			updating = false;
167
		}
168
	}
169
170
	/**
171
	 * Returns the current value of the {@link Text}.
172
	 * 
173
	 * @see org.eclipse.core.databinding.observable.value.AbstractVetoableValue#doGetValue()
174
	 */
175
	public Object doGetValue() {
176
		return oldValue = text.getText();
177
	}
178
179
	/**
180
	 * Returns the type of the value from {@link #doGetValue()}, i.e.
181
	 * String.class
182
	 * 
183
	 * @see org.eclipse.core.databinding.observable.value.IObservableValue#getValueType()
184
	 */
185
	public Object getValueType() {
186
		return String.class;
187
	}
188
189
	public synchronized void dispose() {
190
		if (!text.isDisposed()) {
191
			if (updateEventType != SWT.None) {
192
				text.removeListener(updateEventType, updateListener);
193
			}
194
			text.removeVerifyListener(verifyListener);
195
		}
196
		super.dispose();
197
	}
198
}
(-)src/org/eclipse/jface/internal/databinding/swt/SpinnerObservableValue.java (-151 lines)
Removed Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2005, 2008 IBM Corporation and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
10
 *     Brad Reynolds - bug 164653
11
 *     Ashley Cambrell - bug 198904
12
 *     Matthew Hall - bug 118516
13
 *******************************************************************************/
14
package org.eclipse.jface.internal.databinding.swt;
15
16
import org.eclipse.core.databinding.observable.Diffs;
17
import org.eclipse.core.databinding.observable.Realm;
18
import org.eclipse.core.runtime.Assert;
19
import org.eclipse.jface.internal.databinding.provisional.swt.AbstractSWTObservableValue;
20
import org.eclipse.swt.events.ModifyEvent;
21
import org.eclipse.swt.events.ModifyListener;
22
import org.eclipse.swt.widgets.Spinner;
23
24
/**
25
 * @since 1.0
26
 * 
27
 */
28
public class SpinnerObservableValue extends AbstractSWTObservableValue {
29
30
	private final Spinner spinner;
31
32
	private final String attribute;
33
34
	private boolean updating = false;
35
36
	private int currentSelection;
37
38
	private ModifyListener modifyListener;
39
40
	/**
41
	 * @param spinner
42
	 * @param attribute
43
	 */
44
	public SpinnerObservableValue(Spinner spinner, String attribute) {
45
		super(spinner);
46
		this.spinner = spinner;
47
		this.attribute = attribute;
48
		init();
49
	}
50
	
51
	/**
52
	 * @param realm
53
	 * @param spinner
54
	 * @param attribute
55
	 */
56
	public SpinnerObservableValue(Realm realm, Spinner spinner, String attribute) {
57
		super(realm, spinner);
58
		this.spinner = spinner;
59
		this.attribute = attribute;
60
		init();
61
	}
62
	
63
	private void init() {		
64
		if (attribute.equals(SWTProperties.SELECTION)) {
65
			currentSelection = spinner.getSelection();
66
			modifyListener = new ModifyListener() {
67
				public void modifyText(ModifyEvent e) {
68
					if (!updating) {
69
						int newSelection = SpinnerObservableValue.this.spinner
70
						.getSelection();
71
						notifyIfChanged(currentSelection, newSelection);
72
						currentSelection = newSelection;
73
					}
74
				}
75
			};
76
			spinner.addModifyListener(modifyListener);
77
		} else if (!attribute.equals(SWTProperties.MIN)
78
				&& !attribute.equals(SWTProperties.MAX)) {
79
			throw new IllegalArgumentException(
80
					"Attribute name not valid: " + attribute); //$NON-NLS-1$
81
		}
82
	}
83
84
	public void doSetValue(final Object value) {
85
		int oldValue;
86
		int newValue;
87
		try {
88
			updating = true;
89
			newValue = ((Integer) value).intValue();
90
			if (attribute.equals(SWTProperties.SELECTION)) {
91
				oldValue = spinner.getSelection();
92
				spinner.setSelection(newValue);
93
				currentSelection = newValue;
94
			} else if (attribute.equals(SWTProperties.MIN)) {
95
				oldValue = spinner.getMinimum();
96
				spinner.setMinimum(newValue);
97
			} else if (attribute.equals(SWTProperties.MAX)) {
98
				oldValue = spinner.getMaximum();
99
				spinner.setMaximum(newValue);
100
			} else {
101
				Assert.isTrue(false, "invalid attribute name:" + attribute); //$NON-NLS-1$
102
				return;
103
			}
104
			notifyIfChanged(oldValue, newValue);
105
		} finally {
106
			updating = false;
107
		}
108
	}
109
110
	public Object doGetValue() {
111
		int value = 0;
112
		if (attribute.equals(SWTProperties.SELECTION)) {
113
			value = spinner.getSelection();
114
		} else if (attribute.equals(SWTProperties.MIN)) {
115
			value = spinner.getMinimum();
116
		} else if (attribute.equals(SWTProperties.MAX)) {
117
			value = spinner.getMaximum();
118
		}
119
		return new Integer(value);
120
	}
121
122
	public Object getValueType() {
123
		return Integer.TYPE;
124
	}
125
126
	/**
127
	 * @return attribute being observed
128
	 */
129
	public String getAttribute() {
130
		return attribute;
131
	}
132
133
	/*
134
	 * (non-Javadoc)
135
	 *
136
	 * @see org.eclipse.core.databinding.observable.value.AbstractObservableValue#dispose()
137
	 */
138
	public synchronized void dispose() {
139
		super.dispose();
140
		if (modifyListener != null && !spinner.isDisposed()) {
141
			spinner.removeModifyListener(modifyListener);
142
		}
143
	}
144
	
145
	private void notifyIfChanged(int oldValue, int newValue) {
146
		if (oldValue != newValue) {
147
			fireValueChange(Diffs.createValueDiff(new Integer(oldValue),
148
					new Integer(newValue)));
149
		}
150
	}
151
}
(-)src/org/eclipse/jface/internal/databinding/swt/ListObservableList.java (-51 lines)
Removed Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2005, 2008 IBM Corporation and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
10
 *******************************************************************************/
11
package org.eclipse.jface.internal.databinding.swt;
12
13
import org.eclipse.jface.databinding.swt.SWTObservables;
14
import org.eclipse.swt.widgets.List;
15
16
/**
17
 * @since 3.2
18
 * 
19
 */
20
public class ListObservableList extends SWTObservableList {
21
22
	private final List list;
23
24
	/**
25
	 * @param list
26
	 */
27
	public ListObservableList(List list) {
28
		super(SWTObservables.getRealm(list.getDisplay()));
29
		this.list = list;
30
	}
31
32
	protected int getItemCount() {
33
		return list.getItemCount();
34
	}
35
36
	protected void setItems(String[] newItems) {
37
		list.setItems(newItems);
38
	}
39
40
	protected String[] getItems() {
41
		return list.getItems();
42
	}
43
44
	protected String getItem(int index) {
45
		return list.getItem(index);
46
	}
47
48
	protected void setItem(int index, String string) {
49
		list.setItem(index, string);
50
	}
51
}
(-)src/org/eclipse/jface/internal/databinding/swt/ItemTooltipObservableValue.java (-104 lines)
Removed Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2005, 2008 IBM Corporation and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
10
 *******************************************************************************/
11
package org.eclipse.jface.internal.databinding.swt;
12
13
import org.eclipse.core.databinding.observable.Diffs;
14
import org.eclipse.core.databinding.observable.Realm;
15
import org.eclipse.jface.internal.databinding.provisional.swt.AbstractSWTObservableValue;
16
import org.eclipse.swt.custom.CTabItem;
17
import org.eclipse.swt.widgets.Item;
18
import org.eclipse.swt.widgets.TabItem;
19
import org.eclipse.swt.widgets.TableColumn;
20
import org.eclipse.swt.widgets.ToolItem;
21
import org.eclipse.swt.widgets.TrayItem;
22
import org.eclipse.swt.widgets.TreeColumn;
23
24
/**
25
 * @since 3.5
26
 * 
27
 */
28
public class ItemTooltipObservableValue extends AbstractSWTObservableValue {
29
30
	private final Item item;
31
32
	/**
33
	 * @param item
34
	 */
35
	public ItemTooltipObservableValue(Item item) {
36
		super(item);
37
		this.item = item;
38
	}
39
	
40
	/**
41
	 * @param realm
42
	 * @param item
43
	 */
44
	public ItemTooltipObservableValue(Realm realm, Item item) {
45
		super(realm, item);
46
		this.item = item;
47
	}
48
49
	public void doSetValue(final Object value) {
50
		String oldValue = (String) doGetValue();
51
52
		String newValue = value == null ? "" : value.toString(); //$NON-NLS-1$
53
		if (item instanceof CTabItem) {
54
			((CTabItem)item).setToolTipText(newValue);
55
		}
56
		else if (item instanceof TabItem) {
57
			((TabItem)item).setToolTipText(newValue);
58
		}
59
		else if (item instanceof TableColumn) {
60
			((TableColumn)item).setToolTipText(newValue);
61
		}
62
		else if (item instanceof ToolItem) {
63
			((ToolItem)item).setToolTipText(newValue);
64
		}
65
		else if (item instanceof TrayItem) {
66
			((TrayItem)item).setToolTipText(newValue);
67
		}
68
		else if (item instanceof TreeColumn) {
69
			((TreeColumn)item).setToolTipText(newValue);
70
		}
71
		
72
		if (!newValue.equals(oldValue)) {
73
			fireValueChange(Diffs.createValueDiff(oldValue, newValue));
74
		}
75
	}
76
77
	public Object doGetValue() {
78
		if (item instanceof CTabItem) {
79
			return ((CTabItem)item).getToolTipText();
80
		}
81
		else if (item instanceof TabItem) {
82
			return ((TabItem)item).getToolTipText();
83
		}
84
		else if (item instanceof TableColumn) {
85
			return ((TableColumn)item).getToolTipText();
86
		}
87
		else if (item instanceof ToolItem) {
88
			return ((ToolItem)item).getToolTipText();
89
		}
90
		else if (item instanceof TrayItem) {
91
			return ((TrayItem)item).getToolTipText();
92
		}
93
		else if (item instanceof TreeColumn) {
94
			return ((TreeColumn)item).getToolTipText();
95
		}
96
		
97
		return null;
98
	}
99
100
	public Object getValueType() {
101
		return String.class;
102
	}
103
104
}
(-)src/org/eclipse/jface/internal/databinding/swt/SWTProperties.java (-97 lines)
Removed Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2005, 2008 IBM Corporation and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
10
 *     Matt Carter - bug 170668
11
 *     Brad Reynolds - bug 170848
12
 *******************************************************************************/
13
package org.eclipse.jface.internal.databinding.swt;
14
15
/**
16
 * Constants used to describe properties of SWT controls.
17
 * 
18
 * @since 1.0
19
 *
20
 */
21
public interface SWTProperties {
22
23
	/**
24
	 * Applies to Control
25
	 */
26
	public static final String ENABLED = "enabled"; //$NON-NLS-1$
27
	/**
28
	 * Applies to Control
29
	 */
30
	public static final String VISIBLE = "visible"; //$NON-NLS-1$
31
	/**
32
	 * Applies to Control
33
	 */
34
	public static final String TOOLTIP_TEXT = "tooltip"; //$NON-NLS-1$	
35
	/**
36
	 * Applies to
37
	 */
38
	public static final String ITEMS = "items"; //$NON-NLS-1$
39
	/**
40
	 * Applies to Spinner
41
	 */
42
	public static final String MAX = "max"; //$NON-NLS-1$
43
	/**
44
	 * Applies to Spinner
45
	 */
46
	public static final String MIN = "min"; //$NON-NLS-1$
47
	/**
48
	 * Applies to Spinner, Button
49
	 */
50
	public static final String SELECTION = "selection"; //$NON-NLS-1$
51
	/**
52
	 * Applies to Spinner, Button
53
	 */
54
	public static final String SELECTION_INDEX = "index"; //$NON-NLS-1$
55
	/**
56
	 * Applies to Text, Label, Combo
57
	 */
58
	public static final String TEXT = "text"; //$NON-NLS-1$
59
	
60
	/**
61
	 * Applies to Label, CLabel.
62
	 */
63
	public static final String IMAGE = "image"; //$NON-NLS-1$
64
	/**
65
	 * Applies to Control
66
	 */
67
	public static final String FOREGROUND = "foreground"; //$NON-NLS-1$
68
	/**
69
	 * Applies to Control
70
	 */
71
	public static final String BACKGROUND = "background"; //$NON-NLS-1$
72
	/**
73
	 * Applies to Control
74
	 */
75
	public static final String FONT = "font"; //$NON-NLS-1$
76
	
77
	/**
78
	 * Applies to Control 
79
	 */
80
	public static final String SIZE = "size";  //$NON-NLS-1$
81
	
82
	/**
83
	 * Applies to Control
84
	 */
85
	public static final String LOCATION = "location"; //$NON-NLS-1$
86
	
87
	/**
88
	 * Applies to Control
89
	 */
90
	public static final String FOCUS = "focus"; //$NON-NLS-1$
91
	
92
	/**
93
	 * Applies to Control
94
	 */
95
	public static final String BOUNDS = "bounds"; //$NON-NLS-1$
96
97
}
(-)src/org/eclipse/jface/internal/databinding/swt/ControlObservableValue.java (-283 lines)
Removed Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2005, 2008 IBM Corporation and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
10
 *     Brad Reynolds - bug 164653
11
 *     Matt Carter - bug 170668
12
 *     Brad Reynolds - bug 170848
13
 *******************************************************************************/
14
package org.eclipse.jface.internal.databinding.swt;
15
16
import java.util.HashMap;
17
import java.util.Map;
18
19
import org.eclipse.core.databinding.observable.Diffs;
20
import org.eclipse.core.databinding.observable.Realm;
21
import org.eclipse.jface.internal.databinding.provisional.swt.AbstractSWTObservableValue;
22
import org.eclipse.jface.util.Util;
23
import org.eclipse.swt.events.ControlEvent;
24
import org.eclipse.swt.events.ControlListener;
25
import org.eclipse.swt.events.FocusEvent;
26
import org.eclipse.swt.events.FocusListener;
27
import org.eclipse.swt.graphics.Color;
28
import org.eclipse.swt.graphics.Font;
29
import org.eclipse.swt.graphics.Point;
30
import org.eclipse.swt.graphics.Rectangle;
31
import org.eclipse.swt.widgets.Control;
32
33
/**
34
 * @since 1.0
35
 * 
36
 */
37
public class ControlObservableValue extends AbstractSWTObservableValue {
38
39
	private final Control control;
40
41
	private final String attribute;
42
43
	private Object valueType;
44
	
45
	private FocusListener focusListener;
46
47
	private ControlListener controlListener;
48
49
	private Boolean currentFocus;
50
51
	private Point currentPoint;
52
53
	private Rectangle currentBounds;
54
55
	private boolean updating;
56
57
	
58
	private static final Map SUPPORTED_ATTRIBUTES = new HashMap();
59
	static {
60
		SUPPORTED_ATTRIBUTES.put(SWTProperties.ENABLED, Boolean.TYPE);
61
		SUPPORTED_ATTRIBUTES.put(SWTProperties.VISIBLE, Boolean.TYPE);
62
		SUPPORTED_ATTRIBUTES.put(SWTProperties.TOOLTIP_TEXT, String.class);
63
		SUPPORTED_ATTRIBUTES.put(SWTProperties.FOREGROUND, Color.class);
64
		SUPPORTED_ATTRIBUTES.put(SWTProperties.BACKGROUND, Color.class);
65
		SUPPORTED_ATTRIBUTES.put(SWTProperties.FONT, Font.class);
66
		SUPPORTED_ATTRIBUTES.put(SWTProperties.LOCATION, Point.class);
67
		SUPPORTED_ATTRIBUTES.put(SWTProperties.SIZE, Point.class);
68
		SUPPORTED_ATTRIBUTES.put(SWTProperties.FOCUS, Boolean.class);
69
		SUPPORTED_ATTRIBUTES.put(SWTProperties.BOUNDS, Rectangle.class);
70
	}
71
	
72
	/**
73
	 * @param control
74
	 * @param attribute
75
	 */
76
	public ControlObservableValue(Control control, String attribute) {
77
		super(control);
78
		this.control = control;
79
		this.attribute = attribute;
80
		if (SUPPORTED_ATTRIBUTES.keySet().contains(attribute)) {
81
			this.valueType = SUPPORTED_ATTRIBUTES.get(attribute); 
82
		} else {
83
			throw new IllegalArgumentException();
84
		}
85
		
86
		init();
87
	}
88
	
89
	/**
90
	 * @param realm 
91
	 * @param control
92
	 * @param attribute
93
	 */
94
	public ControlObservableValue(Realm realm, Control control, String attribute) {
95
		super(realm, control);
96
		this.control = control;
97
		this.attribute = attribute;
98
		if (SUPPORTED_ATTRIBUTES.keySet().contains(attribute)) {
99
			this.valueType = SUPPORTED_ATTRIBUTES.get(attribute); 
100
		} else {
101
			throw new IllegalArgumentException();
102
		}
103
		
104
		init();
105
	}
106
107
	private void init() {
108
		if (SWTProperties.SIZE.equals(attribute)
109
				|| SWTProperties.LOCATION.equals(attribute)
110
				|| SWTProperties.BOUNDS.equals(attribute)) {
111
			this.currentPoint = SWTProperties.SIZE.equals(attribute) ? control
112
					.getSize() : control.getLocation();
113
114
			controlListener = new ControlListener() {
115
116
				public void controlMoved(ControlEvent e) {
117
					if (SWTProperties.LOCATION.equals(attribute)) {
118
						if (!updating) {
119
							Point oldValue = currentPoint;
120
							currentPoint = control.getLocation();
121
122
							notifyIfChanged(oldValue, currentPoint);
123
						}
124
					} else if (SWTProperties.BOUNDS.equals(attribute)) {
125
						if (!updating) {
126
							Rectangle oldValue = currentBounds;
127
							currentBounds = control.getBounds();
128
129
							notifyIfChanged(oldValue, currentBounds);
130
						}
131
					}
132
				}
133
134
				public void controlResized(ControlEvent e) {
135
					if (SWTProperties.LOCATION.equals(attribute)) {
136
						if (!updating) {
137
							Point oldValue = currentPoint;
138
							currentPoint = control.getSize();
139
140
							notifyIfChanged(oldValue, currentPoint);
141
						}
142
					} else if (SWTProperties.BOUNDS.equals(attribute)) {
143
						if (!updating) {
144
							Rectangle oldValue = currentBounds;
145
							currentBounds = control.getBounds();
146
147
							notifyIfChanged(oldValue, currentBounds);
148
						}
149
					}
150
				}
151
			};
152
			control.addControlListener(controlListener);
153
		} else if (SWTProperties.FOCUS.equals(attribute)) {
154
			this.currentFocus = control == control.getDisplay()
155
					.getFocusControl() ? Boolean.TRUE : Boolean.FALSE;
156
			focusListener = new FocusListener() {
157
158
				public void focusGained(FocusEvent e) {
159
					if (!updating) {
160
						Boolean oldValue = currentFocus;
161
						currentFocus = Boolean.TRUE;
162
						notifyIfChanged(oldValue, currentFocus);
163
					}
164
				}
165
166
				public void focusLost(FocusEvent e) {
167
					if (!updating) {
168
						Boolean oldValue = currentFocus;
169
						currentFocus = Boolean.FALSE;
170
						notifyIfChanged(oldValue, currentFocus);
171
					}
172
				}
173
			};
174
			control.addFocusListener(focusListener);
175
		}
176
	}
177
	
178
	public void doSetValue(Object value) {
179
		Object oldValue = doGetValue();
180
		
181
		if (SWTProperties.SIZE.equals(attribute)) {
182
			try {
183
				updating = true;
184
				control.setSize((Point) value);
185
			} finally {
186
				updating = false;
187
				currentPoint = control.getSize();
188
			}
189
		} else if (SWTProperties.LOCATION.equals(attribute)) {
190
			try {
191
				updating = true;
192
				control.setLocation((Point) value);
193
			} finally {
194
				updating = false;
195
				currentPoint = control.getLocation();
196
			}
197
		} else if (SWTProperties.FOCUS.equals(attribute)) {
198
			try {
199
				updating = true;
200
				if (Boolean.TRUE.equals(value)) {
201
					currentFocus = control.setFocus() ? Boolean.TRUE
202
							: Boolean.FALSE;
203
				} else {
204
					// TODO Not possible force the focus to leave the control
205
					// Maybe focus should the move to the Shell containing the
206
					// control
207
					this.currentFocus = control == control.getDisplay()
208
							.getFocusControl() ? Boolean.TRUE : Boolean.FALSE;
209
				}
210
			} finally {
211
				updating = false;
212
			}
213
		} else if (SWTProperties.BOUNDS.equals(attribute)) {
214
			try {
215
				updating = true;
216
				control.setBounds((Rectangle) value);
217
			} finally {
218
				updating = false;
219
				currentBounds = control.getBounds();
220
			}
221
		} else if (attribute.equals(SWTProperties.ENABLED)) {
222
			control.setEnabled(((Boolean) value).booleanValue());
223
		} else if (attribute.equals(SWTProperties.VISIBLE)) {
224
			control.setVisible(((Boolean) value).booleanValue());
225
		} else if (attribute.equals(SWTProperties.TOOLTIP_TEXT)) {
226
			control.setToolTipText((String) value);
227
		} else if (attribute.equals(SWTProperties.FOREGROUND)) {
228
			control.setForeground((Color) value);
229
		} else if (attribute.equals(SWTProperties.BACKGROUND)) {
230
			control.setBackground((Color) value);
231
		} else if (attribute.equals(SWTProperties.FONT)) {
232
			control.setFont((Font) value);
233
		}
234
		
235
		notifyIfChanged(oldValue, value);
236
	}
237
238
	public Object doGetValue() {
239
		if (attribute.equals(SWTProperties.ENABLED)) {
240
			return control.getEnabled() ? Boolean.TRUE : Boolean.FALSE;
241
		}
242
		if (attribute.equals(SWTProperties.VISIBLE)) {
243
			return control.getVisible() ? Boolean.TRUE : Boolean.FALSE;
244
		}
245
		if (attribute.equals(SWTProperties.TOOLTIP_TEXT)) {
246
			return control.getToolTipText();			
247
		}
248
		if (attribute.equals(SWTProperties.FOREGROUND))	 {
249
			return control.getForeground();
250
		}
251
		if (attribute.equals(SWTProperties.BACKGROUND)) {
252
			return control.getBackground();
253
		}
254
		if (attribute.equals(SWTProperties.FONT)) {
255
			return control.getFont();
256
		}
257
		if (SWTProperties.SIZE.equals(attribute)) {
258
			return control.getSize();
259
		}
260
		if (SWTProperties.LOCATION.equals(attribute)) {
261
			return control.getLocation();
262
		}
263
		if (SWTProperties.FOCUS.equals(attribute)) {
264
			return control == control.getDisplay().getFocusControl() ? Boolean.TRUE
265
					: Boolean.FALSE;
266
		}
267
		if (SWTProperties.BOUNDS.equals(attribute)) {
268
			return control.getBounds();
269
		}
270
		
271
		return null;
272
	}
273
274
	public Object getValueType() {
275
		return valueType;
276
	}
277
	
278
	private void notifyIfChanged(Object oldValue, Object newValue) {
279
		if (!Util.equals(oldValue, newValue)) {
280
			fireValueChange(Diffs.createValueDiff(oldValue, newValue));			
281
		}
282
	}
283
}
(-)src/org/eclipse/jface/internal/databinding/swt/CLabelObservableValue.java (-62 lines)
Removed Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2005, 2008 IBM Corporation and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
10
 *     Brad Reynolds - bug 164653
11
 *******************************************************************************/
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.core.databinding.observable.Diffs;
15
import org.eclipse.core.databinding.observable.Realm;
16
import org.eclipse.jface.internal.databinding.provisional.swt.AbstractSWTObservableValue;
17
import org.eclipse.swt.custom.CLabel;
18
19
/**
20
 * @since 1.0
21
 * 
22
 */
23
public class CLabelObservableValue extends AbstractSWTObservableValue {
24
25
	private final CLabel label;
26
27
	/**
28
	 * @param label
29
	 */
30
	public CLabelObservableValue(CLabel label) {
31
		super(label);
32
		this.label = label;
33
	}
34
	
35
	/**
36
	 * @param realm
37
	 * @param label
38
	 */
39
	public CLabelObservableValue(Realm realm, CLabel label) {
40
		super(realm, label);
41
		this.label = label;
42
	}
43
44
	public void doSetValue(final Object value) {
45
		String oldValue = label.getText();
46
		String newValue = value == null ? "" : value.toString();  //$NON-NLS-1$
47
		label.setText(newValue);
48
49
		if (!newValue.equals(oldValue)) {
50
			fireValueChange(Diffs.createValueDiff(oldValue, newValue));
51
		}
52
	}
53
54
	public Object doGetValue() {
55
		return label.getText();
56
	}
57
58
	public Object getValueType() {
59
		return String.class;
60
	}
61
62
}
(-)src/org/eclipse/jface/internal/databinding/swt/SWTObservableValueDecorator.java (-1 / +1 lines)
Lines 6-12 Link Here
6
 * http://www.eclipse.org/legal/epl-v10.html
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
7
 *
8
 * Contributors:
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 245647)
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
10
 ******************************************************************************/
11
11
12
package org.eclipse.jface.internal.databinding.swt;
12
package org.eclipse.jface.internal.databinding.swt;
(-)src/org/eclipse/jface/internal/databinding/swt/SingleSelectionObservableValue.java (-103 lines)
Removed Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2005, 2008 IBM Corporation and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
10
 *     Brad Reynolds - bug 164653
11
 *******************************************************************************/
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.core.databinding.observable.Diffs;
15
import org.eclipse.core.databinding.observable.Realm;
16
import org.eclipse.jface.internal.databinding.provisional.swt.AbstractSWTObservableValue;
17
import org.eclipse.swt.widgets.Control;
18
19
/**
20
 * @since 1.0
21
 * 
22
 */
23
abstract public class SingleSelectionObservableValue extends
24
		AbstractSWTObservableValue {
25
26
	private boolean updating = false;
27
28
	private int currentSelection;
29
30
	/**
31
	 * @param control
32
	 *            the control
33
	 */
34
	public SingleSelectionObservableValue(Control control) {
35
		super(control);
36
		init();
37
	}
38
	
39
	/**
40
	 * @param realm
41
	 * @param control
42
	 */
43
	public SingleSelectionObservableValue(Realm realm, Control control) {
44
		super(realm, control);
45
		init();
46
	}
47
	
48
	private void init() {		
49
		currentSelection = doGetSelectionIndex();
50
		doAddSelectionListener(new Runnable(){
51
			public void run() {
52
				if (!updating) {
53
					int newSelection = doGetSelectionIndex();
54
					notifyIfChanged(currentSelection, newSelection);
55
					currentSelection = newSelection;
56
				}
57
			}
58
		});
59
	}
60
61
	/**
62
	 * @param runnable
63
	 */
64
	protected abstract void doAddSelectionListener(Runnable runnable);
65
66
	public void doSetValue(Object value) {
67
		try {
68
			updating = true;
69
			int intValue = ((Integer) value).intValue();
70
			doSetSelectionIndex(intValue);
71
			notifyIfChanged(currentSelection, intValue);
72
			currentSelection = intValue;
73
		} finally {
74
			updating = false;
75
		}
76
	}
77
78
	/**
79
	 * @param intValue
80
	 *            the selection index
81
	 */
82
	protected abstract void doSetSelectionIndex(int intValue);
83
84
	public Object doGetValue() {
85
		return new Integer(doGetSelectionIndex());
86
	}
87
88
	/**
89
	 * @return the selection index
90
	 */
91
	protected abstract int doGetSelectionIndex();
92
93
	public Object getValueType() {
94
		return Integer.TYPE;
95
	}
96
97
	private void notifyIfChanged(int oldValue, int newValue) {
98
		if (oldValue != newValue) {
99
			fireValueChange(Diffs.createValueDiff(new Integer(
100
					oldValue), new Integer(newValue)));
101
		}
102
	}
103
}
(-)src/org/eclipse/jface/internal/databinding/swt/ButtonObservableValue.java (-110 lines)
Removed Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2005, 2008 IBM Corporation and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
10
 *     Brad Reynolds - bug 164653
11
 *     Ashley Cambrell - bug 198904
12
 *******************************************************************************/
13
package org.eclipse.jface.internal.databinding.swt;
14
15
import org.eclipse.core.databinding.observable.Diffs;
16
import org.eclipse.core.databinding.observable.Realm;
17
import org.eclipse.jface.internal.databinding.provisional.swt.AbstractSWTObservableValue;
18
import org.eclipse.swt.SWT;
19
import org.eclipse.swt.widgets.Button;
20
import org.eclipse.swt.widgets.Event;
21
import org.eclipse.swt.widgets.Listener;
22
23
/**
24
 * @since 1.0
25
 * 
26
 */
27
public class ButtonObservableValue extends AbstractSWTObservableValue {
28
29
	private final Button button;
30
31
	private boolean selectionValue;
32
33
	private Listener updateListener = new Listener() {
34
		public void handleEvent(Event event) {
35
			boolean oldSelectionValue = selectionValue;
36
			selectionValue = button.getSelection();
37
						
38
			notifyIfChanged(oldSelectionValue, selectionValue);
39
		}
40
	};
41
42
	/**
43
	 * @param button
44
	 */
45
	public ButtonObservableValue(Button button) {
46
		super(button);
47
		this.button = button;
48
		init();
49
	}
50
	
51
	/**
52
	 * @param realm
53
	 * @param button
54
	 */
55
	public ButtonObservableValue(Realm realm, Button button) {
56
		super(realm, button);
57
		this.button = button;
58
		init();
59
	}
60
	
61
	private void init() {
62
		button.addListener(SWT.Selection, updateListener);
63
		button.addListener(SWT.DefaultSelection, updateListener);
64
		this.selectionValue = button.getSelection();
65
	}
66
67
	public void doSetValue(final Object value) {
68
		boolean oldSelectionValue = selectionValue;
69
		selectionValue = value == null ? false : ((Boolean) value)
70
				.booleanValue();
71
		
72
		button.setSelection(selectionValue);
73
		notifyIfChanged(oldSelectionValue, selectionValue);
74
	}
75
76
	public Object doGetValue() {
77
		return button.getSelection() ? Boolean.TRUE : Boolean.FALSE;
78
	}
79
80
	public Object getValueType() {
81
		return Boolean.TYPE;
82
	}
83
	
84
	/*
85
	 * (non-Javadoc)
86
	 *
87
	 * @see org.eclipse.core.databinding.observable.value.AbstractObservableValue#dispose()
88
	 */
89
	public synchronized void dispose() {
90
		super.dispose();
91
92
		if (!button.isDisposed()) {
93
			button.removeListener(SWT.Selection, updateListener);
94
			button.removeListener(SWT.DefaultSelection, updateListener);
95
		}
96
	}
97
98
	/**
99
	 * Notifies consumers with a value change event only if a change occurred.
100
	 * 
101
	 * @param oldValue
102
	 * @param newValue
103
	 */
104
	private void notifyIfChanged(boolean oldValue, boolean newValue) {
105
		if (oldValue != newValue) {
106
			fireValueChange(Diffs.createValueDiff(oldValue ? Boolean.TRUE : Boolean.FALSE,
107
					newValue ? Boolean.TRUE : Boolean.FALSE));
108
		}		
109
	}
110
}
(-)src/org/eclipse/jface/internal/databinding/swt/ComboObservableValue.java (-155 lines)
Removed Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2005, 2008 IBM Corporation and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
10
 *     Brad Reynolds - bug 164653
11
 *     Ashley Cambrell - bug 198904
12
 *     Matthew Hall - bug 118516
13
 *******************************************************************************/
14
package org.eclipse.jface.internal.databinding.swt;
15
16
import org.eclipse.core.databinding.observable.Diffs;
17
import org.eclipse.core.databinding.observable.Realm;
18
import org.eclipse.core.runtime.Assert;
19
import org.eclipse.jface.internal.databinding.provisional.swt.AbstractSWTObservableValue;
20
import org.eclipse.swt.events.ModifyEvent;
21
import org.eclipse.swt.events.ModifyListener;
22
import org.eclipse.swt.widgets.Combo;
23
24
/**
25
 * @since 3.2
26
 * 
27
 */
28
public class ComboObservableValue extends AbstractSWTObservableValue {
29
30
	private final Combo combo;
31
	private final String attribute;
32
	private boolean updating = false;
33
	private String currentValue;
34
	private ModifyListener modifyListener;
35
36
	/**
37
	 * @param combo
38
	 * @param attribute
39
	 */
40
	public ComboObservableValue(Combo combo, String attribute) {
41
		super(combo);
42
		this.combo = combo;
43
		this.attribute = attribute;
44
		init();
45
	}
46
		
47
	/**
48
	 * @param realm
49
	 * @param combo
50
	 * @param attribute
51
	 */
52
	public ComboObservableValue(Realm realm, Combo combo, String attribute) {
53
		super(realm, combo);
54
		this.combo = combo;
55
		this.attribute = attribute;
56
		init();
57
	}
58
	
59
	private void init() {		
60
		if (attribute.equals(SWTProperties.SELECTION)
61
				|| attribute.equals(SWTProperties.TEXT)) {
62
			this.currentValue = combo.getText();
63
			modifyListener = new ModifyListener() {
64
65
				public void modifyText(ModifyEvent e) {
66
					if (!updating) {
67
						String oldValue = currentValue;
68
						currentValue = ComboObservableValue.this.combo
69
								.getText();
70
						
71
						notifyIfChanged(oldValue, currentValue);
72
					}
73
				}
74
			};
75
			combo.addModifyListener(modifyListener);
76
		} else
77
			throw new IllegalArgumentException();
78
	}
79
80
	public void doSetValue(final Object value) {
81
		String oldValue = combo.getText();
82
		try {
83
			updating = true;
84
			if (attribute.equals(SWTProperties.TEXT)) {
85
				String stringValue = value != null ? value.toString() : ""; //$NON-NLS-1$
86
				combo.setText(stringValue);
87
			} else if (attribute.equals(SWTProperties.SELECTION)) {
88
				String items[] = combo.getItems();
89
				int index = -1;
90
				if (items != null && value != null) {
91
					for (int i = 0; i < items.length; i++) {
92
						if (value.equals(items[i])) {
93
							index = i;
94
							break;
95
						}
96
					}
97
					if (index == -1) {
98
						combo.setText((String) value);
99
					} else {
100
						combo.select(index); // -1 will not "unselect"
101
					}
102
				}
103
			}
104
		} finally {
105
			updating = false;
106
			currentValue = combo.getText();
107
		}
108
		
109
		notifyIfChanged(oldValue, currentValue);
110
	}
111
112
	public Object doGetValue() {
113
		if (attribute.equals(SWTProperties.TEXT))
114
			return combo.getText();
115
116
		Assert.isTrue(attribute.equals(SWTProperties.SELECTION),
117
				"unexpected attribute: " + attribute); //$NON-NLS-1$
118
		// The problem with a ccombo, is that it changes the text and
119
		// fires before it update its selection index
120
		return combo.getText();
121
	}
122
123
	public Object getValueType() {
124
		Assert.isTrue(attribute.equals(SWTProperties.TEXT)
125
				|| attribute.equals(SWTProperties.SELECTION),
126
				"unexpected attribute: " + attribute); //$NON-NLS-1$
127
		return String.class;
128
	}
129
130
	/**
131
	 * @return attribute being observed
132
	 */
133
	public String getAttribute() {
134
		return attribute;
135
	}
136
137
	/*
138
	 * (non-Javadoc)
139
	 *
140
	 * @see org.eclipse.core.databinding.observable.value.AbstractObservableValue#dispose()
141
	 */
142
	public synchronized void dispose() {
143
		super.dispose();
144
145
		if (modifyListener != null && !combo.isDisposed()) {
146
			combo.removeModifyListener(modifyListener);
147
		}
148
	}
149
	
150
	private void notifyIfChanged(String oldValue, String newValue) {
151
		if (!oldValue.equals(newValue)) {
152
			fireValueChange(Diffs.createValueDiff(oldValue, newValue));
153
		}
154
	}
155
}
(-)src/org/eclipse/jface/internal/databinding/swt/LabelObservableValue.java (-62 lines)
Removed Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2005, 2008 IBM Corporation and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
10
 *     Brad Reynolds - bug 164653
11
 *******************************************************************************/
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.core.databinding.observable.Diffs;
15
import org.eclipse.core.databinding.observable.Realm;
16
import org.eclipse.jface.internal.databinding.provisional.swt.AbstractSWTObservableValue;
17
import org.eclipse.swt.widgets.Label;
18
19
/**
20
 * @since 3.3
21
 * 
22
 */
23
public class LabelObservableValue extends AbstractSWTObservableValue {
24
25
	private final Label label;
26
27
	/**
28
	 * @param label
29
	 */
30
	public LabelObservableValue(Label label) {
31
		super(label);
32
		this.label = label;
33
	}
34
	
35
	/**
36
	 * @param realm
37
	 * @param label
38
	 */
39
	public LabelObservableValue(Realm realm, Label label) {
40
		super(realm, label);
41
		this.label = label;
42
	}
43
44
	public void doSetValue(final Object value) {
45
		String oldValue = label.getText();
46
		String newValue = value == null ? "" : value.toString(); //$NON-NLS-1$
47
		label.setText(newValue);
48
		
49
		if (!newValue.equals(oldValue)) {
50
			fireValueChange(Diffs.createValueDiff(oldValue, newValue));
51
		}
52
	}
53
54
	public Object doGetValue() {
55
		return label.getText();
56
	}
57
58
	public Object getValueType() {
59
		return String.class;
60
	}
61
62
}
(-)src/org/eclipse/jface/internal/databinding/swt/ComboSingleSelectionObservableValue.java (-71 lines)
Removed Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2005, 2008 IBM Corporation and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
10
 *     Brad Reynolds - bug 164653
11
 *     Ashley Cambrell - bugs 198903, 198904
12
 *******************************************************************************/
13
package org.eclipse.jface.internal.databinding.swt;
14
15
import org.eclipse.swt.events.SelectionEvent;
16
import org.eclipse.swt.events.SelectionListener;
17
import org.eclipse.swt.widgets.Combo;
18
19
/**
20
 * @since 1.0
21
 *
22
 */
23
public class ComboSingleSelectionObservableValue extends
24
		SingleSelectionObservableValue {
25
26
	private SelectionListener selectionListener;
27
28
	/**
29
	 * @param combo
30
	 */
31
	public ComboSingleSelectionObservableValue(Combo combo) {
32
		super(combo);
33
	}
34
35
	private Combo getCombo() {
36
		return (Combo) getWidget();
37
	}
38
39
	protected void doAddSelectionListener(final Runnable runnable) {
40
		selectionListener = new SelectionListener() {
41
			public void widgetDefaultSelected(SelectionEvent e) {
42
				runnable.run();
43
			}
44
45
			public void widgetSelected(SelectionEvent e) {
46
				runnable.run();
47
			}
48
		};
49
		getCombo().addSelectionListener(selectionListener);
50
	}
51
52
	protected int doGetSelectionIndex() {
53
		return getCombo().getSelectionIndex();
54
	}
55
56
	protected void doSetSelectionIndex(int index) {
57
		getCombo().select(index);
58
	}
59
60
	/*
61
	 * (non-Javadoc)
62
	 *
63
	 * @see org.eclipse.core.databinding.observable.value.AbstractObservableValue#dispose()
64
	 */
65
	public synchronized void dispose() {
66
		super.dispose();
67
		if (selectionListener != null && !getCombo().isDisposed()) {
68
			getCombo().removeSelectionListener(selectionListener);
69
		}
70
	}
71
}
(-)src/org/eclipse/jface/internal/databinding/swt/ListSingleSelectionObservableValue.java (-71 lines)
Removed Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2005, 2008 IBM Corporation and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
10
 *     Brad Reynolds - bug 164653
11
 *     Ashley Cambrell - bug 198904
12
 *******************************************************************************/
13
package org.eclipse.jface.internal.databinding.swt;
14
15
import org.eclipse.swt.events.SelectionEvent;
16
import org.eclipse.swt.events.SelectionListener;
17
import org.eclipse.swt.widgets.List;
18
19
/**
20
 * @since 1.0
21
 * 
22
 */
23
public class ListSingleSelectionObservableValue extends
24
		SingleSelectionObservableValue {
25
26
	private SelectionListener selectionListener;
27
28
	/**
29
	 * @param combo
30
	 */
31
	public ListSingleSelectionObservableValue(List combo) {
32
		super(combo);
33
	}
34
35
	private List getList() {
36
		return (List) getWidget();
37
	}
38
39
	protected void doAddSelectionListener(final Runnable runnable) {
40
		selectionListener = new SelectionListener() {
41
			public void widgetDefaultSelected(SelectionEvent e) {
42
				runnable.run();
43
			}
44
45
			public void widgetSelected(SelectionEvent e) {
46
				runnable.run();
47
			}
48
		};
49
		getList().addSelectionListener(selectionListener);
50
	}
51
52
	protected int doGetSelectionIndex() {
53
		return getList().getSelectionIndex();
54
	}
55
56
	protected void doSetSelectionIndex(int index) {
57
		getList().setSelection(index);
58
	}
59
60
	/*
61
	 * (non-Javadoc)
62
	 *
63
	 * @see org.eclipse.core.databinding.observable.value.AbstractObservableValue#dispose()
64
	 */
65
	public synchronized void dispose() {
66
		super.dispose();
67
		if (selectionListener != null && !getList().isDisposed()) {
68
			getList().removeSelectionListener(selectionListener);
69
		}
70
	}
71
}
(-)src/org/eclipse/jface/databinding/viewers/ViewersObservables.java (-60 / +104 lines)
Lines 7-32 Link Here
7
 *
7
 *
8
 * Contributors:
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
9
 *     IBM Corporation - initial API and implementation
10
 *     Matthew Hall - bug 206839, 124684, 239302, 245647
10
 *     Matthew Hall - bug 206839, 124684, 239302, 245647, 194734
11
 *******************************************************************************/
11
 *******************************************************************************/
12
12
13
package org.eclipse.jface.databinding.viewers;
13
package org.eclipse.jface.databinding.viewers;
14
14
15
import org.eclipse.core.databinding.observable.Observables;
15
import org.eclipse.core.databinding.observable.Observables;
16
import org.eclipse.core.databinding.observable.Realm;
16
import org.eclipse.core.databinding.observable.list.IObservableList;
17
import org.eclipse.core.databinding.observable.list.IObservableList;
17
import org.eclipse.core.databinding.observable.set.IObservableSet;
18
import org.eclipse.core.databinding.observable.set.IObservableSet;
18
import org.eclipse.core.databinding.observable.value.IObservableValue;
19
import org.eclipse.core.databinding.observable.value.IObservableValue;
20
import org.eclipse.core.databinding.property.list.IListProperty;
21
import org.eclipse.core.databinding.property.set.ISetProperty;
22
import org.eclipse.core.databinding.property.value.IValueProperty;
19
import org.eclipse.jface.databinding.swt.SWTObservables;
23
import org.eclipse.jface.databinding.swt.SWTObservables;
20
import org.eclipse.jface.internal.databinding.swt.SWTDelayedObservableValueDecorator;
24
import org.eclipse.jface.internal.databinding.swt.SWTDelayedObservableValueDecorator;
21
import org.eclipse.jface.internal.databinding.viewers.CheckableCheckedElementsObservableSet;
25
import org.eclipse.jface.internal.databinding.viewers.ViewerObservableListDecorator;
22
import org.eclipse.jface.internal.databinding.viewers.CheckboxViewerCheckedElementsObservableSet;
26
import org.eclipse.jface.internal.databinding.viewers.ViewerObservableSetDecorator;
23
import org.eclipse.jface.internal.databinding.viewers.SelectionProviderMultipleSelectionObservableList;
24
import org.eclipse.jface.internal.databinding.viewers.SelectionProviderSingleSelectionObservableValue;
25
import org.eclipse.jface.internal.databinding.viewers.ViewerFiltersObservableSet;
26
import org.eclipse.jface.internal.databinding.viewers.ViewerInputObservableValue;
27
import org.eclipse.jface.internal.databinding.viewers.ViewerMultipleSelectionObservableList;
28
import org.eclipse.jface.internal.databinding.viewers.ViewerObservableValueDecorator;
27
import org.eclipse.jface.internal.databinding.viewers.ViewerObservableValueDecorator;
29
import org.eclipse.jface.internal.databinding.viewers.ViewerSingleSelectionObservableValue;
30
import org.eclipse.jface.viewers.CheckboxTableViewer;
28
import org.eclipse.jface.viewers.CheckboxTableViewer;
31
import org.eclipse.jface.viewers.CheckboxTreeViewer;
29
import org.eclipse.jface.viewers.CheckboxTreeViewer;
32
import org.eclipse.jface.viewers.ICheckable;
30
import org.eclipse.jface.viewers.ICheckable;
Lines 42-47 Link Here
42
 * @since 1.1
40
 * @since 1.1
43
 */
41
 */
44
public class ViewersObservables {
42
public class ViewersObservables {
43
	private static Realm getDefaultRealm() {
44
		return SWTObservables.getRealm(Display.getDefault());
45
	}
46
47
	private static Realm getRealm(Viewer viewer) {
48
		return SWTObservables.getRealm(viewer.getControl().getDisplay());
49
	}
50
51
	private static void checkNull(Object obj) {
52
		if (obj == null)
53
			throw new IllegalArgumentException();
54
	}
55
56
	private static IObservableValue observeProperty(Object source,
57
			IValueProperty property) {
58
		checkNull(source);
59
		if (source instanceof Viewer) {
60
			return observeViewerProperty((Viewer) source, property);
61
		}
62
		return property.observeValue(getDefaultRealm(), source);
63
	}
64
65
	private static IViewerObservableValue observeViewerProperty(Viewer viewer,
66
			IValueProperty property) {
67
		checkNull(viewer);
68
		return new ViewerObservableValueDecorator(property.observeValue(
69
				getRealm(viewer), viewer), viewer);
70
	}
71
72
	private static IObservableSet observeProperty(Object source,
73
			ISetProperty property) {
74
		checkNull(source);
75
		if (source instanceof Viewer) {
76
			return observeViewerProperty((Viewer) source, property);
77
		}
78
		return property.observeSet(getDefaultRealm(), source);
79
	}
80
81
	private static IViewerObservableSet observeViewerProperty(Viewer viewer,
82
			ISetProperty property) {
83
		checkNull(viewer);
84
		return new ViewerObservableSetDecorator(property.observeSet(
85
				getRealm(viewer), viewer), viewer);
86
	}
87
88
	private static IObservableList observeProperty(Object source,
89
			IListProperty property) {
90
		checkNull(source);
91
		if (source instanceof Viewer) {
92
			return observeViewerProperty((Viewer) source, property);
93
		}
94
		Realm realm = getDefaultRealm();
95
		return property.observeList(realm, source);
96
	}
97
98
	private static IViewerObservableList observeViewerProperty(Viewer viewer,
99
			IListProperty property) {
100
		checkNull(viewer);
101
		Realm realm = getRealm(viewer);
102
		return new ViewerObservableListDecorator(property.observeList(realm,
103
				viewer), viewer);
104
	}
105
45
	/**
106
	/**
46
	 * Returns an observable which delays notification of value change events
107
	 * Returns an observable which delays notification of value change events
47
	 * from <code>observable</code> until <code>delay</code> milliseconds have
108
	 * from <code>observable</code> until <code>delay</code> milliseconds have
Lines 85-110 Link Here
85
	 */
146
	 */
86
	public static IObservableValue observeSingleSelection(
147
	public static IObservableValue observeSingleSelection(
87
			ISelectionProvider selectionProvider) {
148
			ISelectionProvider selectionProvider) {
88
		if (selectionProvider instanceof Viewer) {
149
		return observeProperty(selectionProvider, SelectionProviderProperties
89
			return observeSingleSelection((Viewer) selectionProvider);
150
				.singleSelection());
90
		}
91
		return new SelectionProviderSingleSelectionObservableValue(
92
				SWTObservables.getRealm(Display.getDefault()),
93
				selectionProvider);
94
	}
151
	}
95
152
96
	/**
153
	/**
97
	 * Returns an observable list that tracks the current selection of the
154
	 * Returns an observable list that tracks the current selection of the given
98
	 * given selection provider. Assumes that the selection provider provides
155
	 * selection provider. Assumes that the selection provider provides
99
	 * selections of type {@link IStructuredSelection}. Note that the
156
	 * selections of type {@link IStructuredSelection}. Note that the observable
100
	 * observable list will not honor the full contract of
157
	 * list will not honor the full contract of <code>java.util.List</code> in
101
	 * <code>java.util.List</code> in that it may delete or reorder elements
158
	 * that it may delete or reorder elements based on what the selection
102
	 * based on what the selection provider returns from
159
	 * provider returns from {@link ISelectionProvider#getSelection()} after
103
	 * {@link ISelectionProvider#getSelection()} after having called
160
	 * having called
104
	 * {@link ISelectionProvider#setSelection(org.eclipse.jface.viewers.ISelection)}
161
	 * {@link ISelectionProvider#setSelection(org.eclipse.jface.viewers.ISelection)}
105
	 * based on the requested change to the observable list. The affected
162
	 * based on the requested change to the observable list. The affected
106
	 * methods are <code>add</code>, <code>addAll</code>, and
163
	 * methods are <code>add</code>, <code>addAll</code>, and <code>set</code>.
107
	 * <code>set</code>.
108
	 * 
164
	 * 
109
	 * @param selectionProvider
165
	 * @param selectionProvider
110
	 * @return the observable value tracking the (multi) selection of the given
166
	 * @return the observable value tracking the (multi) selection of the given
Lines 114-125 Link Here
114
	 */
170
	 */
115
	public static IObservableList observeMultiSelection(
171
	public static IObservableList observeMultiSelection(
116
			ISelectionProvider selectionProvider) {
172
			ISelectionProvider selectionProvider) {
117
		if (selectionProvider instanceof Viewer) {
173
		return observeProperty(selectionProvider, SelectionProviderProperties
118
			return observeMultiSelection((Viewer) selectionProvider);
174
				.multipleSelection());
119
		}
120
		return new SelectionProviderMultipleSelectionObservableList(
121
				SWTObservables.getRealm(Display.getDefault()),
122
				selectionProvider, Object.class);
123
	}
175
	}
124
176
125
	/**
177
	/**
Lines 136-158 Link Here
136
	 * @since 1.2
188
	 * @since 1.2
137
	 */
189
	 */
138
	public static IViewerObservableValue observeSingleSelection(Viewer viewer) {
190
	public static IViewerObservableValue observeSingleSelection(Viewer viewer) {
139
		return new ViewerSingleSelectionObservableValue(
191
		return observeViewerProperty(viewer, SelectionProviderProperties
140
				SWTObservables.getRealm(Display.getDefault()),
192
				.singleSelection());
141
				viewer);
142
	}
193
	}
143
	
194
144
	/**
195
	/**
145
	 * Returns an observable list that tracks the current selection of the
196
	 * Returns an observable list that tracks the current selection of the given
146
	 * given viewer. Assumes that the viewer provides
197
	 * viewer. Assumes that the viewer provides selections of type
147
	 * selections of type {@link IStructuredSelection}. Note that the
198
	 * {@link IStructuredSelection}. Note that the observable list will not
148
	 * observable list will not honor the full contract of
199
	 * honor the full contract of <code>java.util.List</code> in that it may
149
	 * <code>java.util.List</code> in that it may delete or reorder elements
200
	 * delete or reorder elements based on what the viewer returns from
150
	 * based on what the viewer returns from
151
	 * {@link ISelectionProvider#getSelection()} after having called
201
	 * {@link ISelectionProvider#getSelection()} after having called
152
	 * {@link ISelectionProvider#setSelection(org.eclipse.jface.viewers.ISelection)}
202
	 * {@link ISelectionProvider#setSelection(org.eclipse.jface.viewers.ISelection)}
153
	 * based on the requested change to the observable list. The affected
203
	 * based on the requested change to the observable list. The affected
154
	 * methods are <code>add</code>, <code>addAll</code>, and
204
	 * methods are <code>add</code>, <code>addAll</code>, and <code>set</code>.
155
	 * <code>set</code>.
156
	 * 
205
	 * 
157
	 * @param viewer
206
	 * @param viewer
158
	 * @return the observable value tracking the (multi) selection of the given
207
	 * @return the observable value tracking the (multi) selection of the given
Lines 160-172 Link Here
160
	 * 
209
	 * 
161
	 * @since 1.2
210
	 * @since 1.2
162
	 */
211
	 */
163
	public static IViewerObservableList observeMultiSelection(
212
	public static IViewerObservableList observeMultiSelection(Viewer viewer) {
164
			Viewer viewer) {
213
		return observeViewerProperty(viewer, SelectionProviderProperties
165
		return new ViewerMultipleSelectionObservableList(
214
				.multipleSelection());
166
				SWTObservables.getRealm(Display.getDefault()),
167
				viewer, Object.class);
168
	}
215
	}
169
	
216
170
	/**
217
	/**
171
	 * Returns an observable value that tracks the input of the given viewer.
218
	 * Returns an observable value that tracks the input of the given viewer.
172
	 * <p>
219
	 * <p>
Lines 179-186 Link Here
179
	 * @since 1.2
226
	 * @since 1.2
180
	 */
227
	 */
181
	public static IObservableValue observeInput(Viewer viewer) {
228
	public static IObservableValue observeInput(Viewer viewer) {
182
		return new ViewerInputObservableValue(SWTObservables.getRealm(viewer
229
		return observeViewerProperty(viewer, ViewerProperties.input());
183
				.getControl().getDisplay()), viewer);
184
	}
230
	}
185
231
186
	/**
232
	/**
Lines 205-212 Link Here
205
			return observeCheckedElements((CheckboxTreeViewer) checkable,
251
			return observeCheckedElements((CheckboxTreeViewer) checkable,
206
					elementType);
252
					elementType);
207
		}
253
		}
208
		return new CheckableCheckedElementsObservableSet(SWTObservables
254
		return observeProperty(checkable, CheckableProperties
209
				.getRealm(Display.getDefault()), checkable, elementType);
255
				.checkedElements(elementType));
210
	}
256
	}
211
257
212
	/**
258
	/**
Lines 224-232 Link Here
224
	 */
270
	 */
225
	public static IViewerObservableSet observeCheckedElements(
271
	public static IViewerObservableSet observeCheckedElements(
226
			CheckboxTableViewer viewer, Object elementType) {
272
			CheckboxTableViewer viewer, Object elementType) {
227
		return new CheckboxViewerCheckedElementsObservableSet(SWTObservables
273
		return observeViewerProperty(viewer, CheckboxTableViewerProperties
228
				.getRealm(viewer.getControl().getDisplay()), viewer,
274
				.checkedElements(elementType));
229
				elementType);
230
	}
275
	}
231
276
232
	/**
277
	/**
Lines 244-252 Link Here
244
	 */
289
	 */
245
	public static IViewerObservableSet observeCheckedElements(
290
	public static IViewerObservableSet observeCheckedElements(
246
			CheckboxTreeViewer viewer, Object elementType) {
291
			CheckboxTreeViewer viewer, Object elementType) {
247
		return new CheckboxViewerCheckedElementsObservableSet(SWTObservables
292
		return observeViewerProperty(viewer, CheckboxTreeViewerProperties
248
				.getRealm(viewer.getControl().getDisplay()), viewer,
293
				.checkedElements(elementType));
249
				elementType);
250
	}
294
	}
251
295
252
	/**
296
	/**
Lines 267-273 Link Here
267
	 * @since 1.3
311
	 * @since 1.3
268
	 */
312
	 */
269
	public static IViewerObservableSet observeFilters(StructuredViewer viewer) {
313
	public static IViewerObservableSet observeFilters(StructuredViewer viewer) {
270
		return new ViewerFiltersObservableSet(SWTObservables.getRealm(viewer
314
		return observeViewerProperty(viewer, StructuredViewerProperties
271
				.getControl().getDisplay()), viewer);
315
				.filters());
272
	}
316
	}
273
}
317
}
(-)src/org/eclipse/jface/internal/databinding/internal/swt/LinkObservableValue.java (-47 lines)
Removed Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Michael Krauter, Catuno GmbH and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Michael Krauter, Catuno GmbH - initial API and implementation (bug 180223)
10
 *******************************************************************************/
11
package org.eclipse.jface.internal.databinding.internal.swt;
12
13
import org.eclipse.core.databinding.observable.Diffs;
14
import org.eclipse.jface.internal.databinding.provisional.swt.AbstractSWTObservableValue;
15
import org.eclipse.swt.widgets.Link;
16
17
/**
18
 * @since 1.2
19
 * 
20
 */
21
public class LinkObservableValue extends AbstractSWTObservableValue {
22
23
	private final Link link;
24
25
	/**
26
	 * @param link
27
	 */
28
	public LinkObservableValue(Link link) {
29
		super(link);
30
		this.link = link;
31
	}
32
33
	public void doSetValue(final Object value) {
34
		String oldValue = link.getText();
35
		link.setText(value == null ? "" : value.toString()); //$NON-NLS-1$
36
		fireValueChange(Diffs.createValueDiff(oldValue, link.getText()));
37
	}
38
39
	public Object doGetValue() {
40
		return link.getText();
41
	}
42
43
	public Object getValueType() {
44
		return String.class;
45
	}
46
47
}
(-)src/org/eclipse/jface/internal/databinding/viewers/SelectionProviderMultipleSelectionObservableList.java (-111 lines)
Removed Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2007 Peter Centgraf and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Peter Centgraf - initial API and implementation, bug 124683
10
 *     Boris Bokowski, IBM Corporation - initial API and implementation
11
 *******************************************************************************/
12
package org.eclipse.jface.internal.databinding.viewers;
13
14
import java.util.ArrayList;
15
import java.util.Collections;
16
import java.util.List;
17
18
import org.eclipse.core.databinding.observable.Diffs;
19
import org.eclipse.core.databinding.observable.Realm;
20
import org.eclipse.core.databinding.observable.list.ListDiff;
21
import org.eclipse.core.databinding.observable.list.WritableList;
22
import org.eclipse.jface.viewers.ISelection;
23
import org.eclipse.jface.viewers.ISelectionChangedListener;
24
import org.eclipse.jface.viewers.ISelectionProvider;
25
import org.eclipse.jface.viewers.IStructuredSelection;
26
import org.eclipse.jface.viewers.SelectionChangedEvent;
27
import org.eclipse.jface.viewers.StructuredSelection;
28
29
/**
30
 * Observes multiple-selection of an {@link ISelectionProvider}.
31
 * 
32
 * @since 1.2
33
 */
34
public class SelectionProviderMultipleSelectionObservableList extends
35
		WritableList {
36
37
	protected ISelectionProvider selectionProvider;
38
	protected boolean handlingSelection;
39
	protected boolean updating;
40
	protected SelectionListener selectionListener = new SelectionListener();
41
42
	class SelectionListener implements ISelectionChangedListener {
43
		public void selectionChanged(SelectionChangedEvent event) {
44
			if (updating) {
45
				return;
46
			}
47
			handlingSelection = true;
48
			try {
49
				updateWrappedList(new ArrayList(getSelectionList(event.getSelection())));
50
			} finally {
51
				handlingSelection = false;
52
			}
53
		}
54
	}
55
56
	/**
57
	 * Create a new observable list based on the current selection of the given
58
	 * selection provider. Assumes that the selection provider provides
59
	 * structured selections.
60
	 * 
61
	 * @param realm
62
	 * @param selectionProvider
63
	 * @param elementType
64
	 */
65
	public SelectionProviderMultipleSelectionObservableList(Realm realm,
66
			ISelectionProvider selectionProvider, Object elementType) {
67
		super(realm, new ArrayList(getSelectionList(selectionProvider)), elementType);
68
		this.selectionProvider = selectionProvider;
69
		selectionProvider.addSelectionChangedListener(selectionListener);
70
	}
71
72
	protected void fireListChange(ListDiff diff) {
73
		if (handlingSelection) {
74
			super.fireListChange(diff);
75
		} else {
76
			// this is a bit of a hack - we are changing the diff to match the order
77
			// of elements returned by the selection provider after we've set the
78
			// selection.
79
			updating = true;
80
			try {
81
				List oldList = getSelectionList(selectionProvider);
82
				selectionProvider
83
						.setSelection(new StructuredSelection(wrappedList));
84
				wrappedList = new ArrayList(getSelectionList(selectionProvider));
85
				super.fireListChange(Diffs.computeListDiff(oldList, wrappedList));
86
			} finally {
87
				updating = false;
88
			}
89
		}
90
	}
91
92
	protected static List getSelectionList(ISelectionProvider selectionProvider) {
93
		if (selectionProvider == null) {
94
			throw new IllegalArgumentException();
95
		}
96
		return getSelectionList(selectionProvider.getSelection());
97
	}
98
99
	protected static List getSelectionList(ISelection sel) {
100
		if (sel instanceof IStructuredSelection) {
101
			return ((IStructuredSelection) sel).toList();
102
		}
103
		return Collections.EMPTY_LIST;
104
	}
105
106
	public synchronized void dispose() {
107
		selectionProvider.removeSelectionChangedListener(selectionListener);
108
		selectionProvider = null;
109
		super.dispose();
110
	}
111
}
(-)src/org/eclipse/jface/internal/databinding/viewers/ViewerMultipleSelectionObservableList.java (-47 lines)
Removed Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2005, 2008 IBM Corporation and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
10
 *     Brad Reynolds - bug 137877
11
 *     Brad Reynolds - bug 164653
12
 *     Brad Reynolds - bug 147515
13
 *     Ashley Cambrell - bug 198906
14
 *******************************************************************************/
15
16
package org.eclipse.jface.internal.databinding.viewers;
17
18
import org.eclipse.core.databinding.observable.Realm;
19
import org.eclipse.jface.databinding.viewers.IViewerObservableList;
20
import org.eclipse.jface.viewers.Viewer;
21
22
/**
23
 * Observes single selection of a <code>Viewer</code>.
24
 * 
25
 * @since 1.2
26
 */
27
public class ViewerMultipleSelectionObservableList extends
28
		SelectionProviderMultipleSelectionObservableList implements
29
		IViewerObservableList {
30
31
	private Viewer viewer;
32
33
	/**
34
	 * @param realm
35
	 * @param viewer
36
	 * @param elementType
37
	 */
38
	public ViewerMultipleSelectionObservableList(Realm realm, Viewer viewer,
39
			Object elementType) {
40
		super(realm, viewer, elementType);
41
		this.viewer = viewer;
42
	}
43
44
	public Viewer getViewer() {
45
		return viewer;
46
	}
47
}
(-)src/org/eclipse/jface/internal/databinding/viewers/CheckboxViewerCheckedElementsObservableSet.java (-90 lines)
Removed Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 124684)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.viewers;
13
14
import java.util.Arrays;
15
import java.util.Set;
16
17
import org.eclipse.core.databinding.observable.Realm;
18
import org.eclipse.jface.databinding.viewers.IViewerObservableSet;
19
import org.eclipse.jface.viewers.CheckboxTableViewer;
20
import org.eclipse.jface.viewers.CheckboxTreeViewer;
21
import org.eclipse.jface.viewers.StructuredViewer;
22
import org.eclipse.jface.viewers.Viewer;
23
24
/**
25
 * An observable set that tracks the checked elements in a CheckboxTableViewer
26
 * or CheckboxTreeViewer
27
 * 
28
 * @since 1.2
29
 */
30
public class CheckboxViewerCheckedElementsObservableSet extends
31
		CheckableCheckedElementsObservableSet implements IViewerObservableSet {
32
	private StructuredViewer viewer;
33
34
	/**
35
	 * Constructs a new instance on the given realm and checkable.
36
	 * 
37
	 * @param realm
38
	 *            the observable's realm
39
	 * @param viewer
40
	 *            the CheckboxTableViewer viewer to track.
41
	 * @param elementType
42
	 *            type of elements in the set
43
	 */
44
	public CheckboxViewerCheckedElementsObservableSet(Realm realm,
45
			CheckboxTableViewer viewer, Object elementType) {
46
		super(realm, viewer, elementType, createElementSet(viewer));
47
		this.viewer = viewer;
48
	}
49
50
	/**
51
	 * Constructs a new instance on the given realm and checkable.
52
	 * 
53
	 * @param realm
54
	 *            the observable's realm
55
	 * @param viewer
56
	 *            the CheckboxTreeViewer viewer to track.
57
	 * @param elementType
58
	 *            type of elements in the set
59
	 */
60
	public CheckboxViewerCheckedElementsObservableSet(Realm realm,
61
			CheckboxTreeViewer viewer, Object elementType) {
62
		super(realm, viewer, elementType, createElementSet(viewer));
63
		this.viewer = viewer;
64
	}
65
66
	Set createDiffSet() {
67
		return ViewerElementSet.withComparer(viewer.getComparer());
68
	}
69
70
	private static Set createElementSet(CheckboxTableViewer viewer) {
71
		Set set = ViewerElementSet.withComparer(viewer.getComparer());
72
		set.addAll(Arrays.asList(viewer.getCheckedElements()));
73
		return set;
74
	}
75
76
	private static Set createElementSet(CheckboxTreeViewer viewer) {
77
		Set set = ViewerElementSet.withComparer(viewer.getComparer());
78
		set.addAll(Arrays.asList(viewer.getCheckedElements()));
79
		return set;
80
	}
81
82
	public Viewer getViewer() {
83
		return viewer;
84
	}
85
86
	public synchronized void dispose() {
87
		viewer = null;
88
		super.dispose();
89
	}
90
}
(-)src/org/eclipse/jface/internal/databinding/viewers/ViewerFiltersObservableSet.java (-174 lines)
Removed Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2005, 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 239302)
10
 *******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.viewers;
13
14
import java.util.Arrays;
15
import java.util.Collection;
16
import java.util.Collections;
17
import java.util.HashSet;
18
import java.util.Iterator;
19
import java.util.Set;
20
21
import org.eclipse.core.databinding.observable.Diffs;
22
import org.eclipse.core.databinding.observable.Realm;
23
import org.eclipse.core.databinding.observable.set.ObservableSet;
24
import org.eclipse.jface.databinding.viewers.IViewerObservableSet;
25
import org.eclipse.jface.viewers.StructuredViewer;
26
import org.eclipse.jface.viewers.Viewer;
27
import org.eclipse.jface.viewers.ViewerFilter;
28
29
/**
30
 * An observable set that tracks the filters of the given viewer. Note that this
31
 * set will not track changes that are made using direct API on StructuredViewer
32
 * (by calling
33
 * {@link StructuredViewer#addFilter(org.eclipse.jface.viewers.ViewerFilter)
34
 * addFilter()},
35
 * {@link StructuredViewer#removeFilter(org.eclipse.jface.viewers.ViewerFilter)
36
 * removeFilter()}, or
37
 * {@link StructuredViewer#setFilters(org.eclipse.jface.viewers.ViewerFilter[])
38
 * setFilters()}) -- it is assumed that filters are only changed through the
39
 * set.
40
 * 
41
 * @since 1.2
42
 */
43
public class ViewerFiltersObservableSet extends ObservableSet implements
44
		IViewerObservableSet {
45
46
	private StructuredViewer viewer;
47
48
	/**
49
	 * @param realm
50
	 * @param viewer
51
	 */
52
	public ViewerFiltersObservableSet(Realm realm, StructuredViewer viewer) {
53
		super(realm, new HashSet(Arrays.asList(viewer.getFilters())),
54
				ViewerFilter.class);
55
		this.viewer = viewer;
56
	}
57
58
	public Viewer getViewer() {
59
		return viewer;
60
	}
61
62
	private void replaceFilters() {
63
		viewer.getControl().setRedraw(false);
64
		try {
65
			viewer.setFilters((ViewerFilter[]) wrappedSet
66
					.toArray(new ViewerFilter[wrappedSet.size()]));
67
		} finally {
68
			viewer.getControl().setRedraw(true);
69
		}
70
	}
71
72
	private void addFilter(ViewerFilter filter) {
73
		viewer.getControl().setRedraw(false);
74
		try {
75
			viewer.addFilter(filter);
76
		} finally {
77
			viewer.getControl().setRedraw(true);
78
		}
79
	}
80
81
	private void removeFilter(ViewerFilter filter) {
82
		viewer.getControl().setRedraw(false);
83
		try {
84
			viewer.removeFilter(filter);
85
		} finally {
86
			viewer.getControl().setRedraw(true);
87
		}
88
	}
89
90
	public boolean add(Object element) {
91
		checkRealm();
92
		boolean added = wrappedSet.add(element);
93
		if (added) {
94
			addFilter((ViewerFilter) element);
95
			fireSetChange(Diffs.createSetDiff(Collections.singleton(element),
96
					Collections.EMPTY_SET));
97
		}
98
		return added;
99
	}
100
101
	public boolean addAll(Collection c) {
102
		getterCalled();
103
		Set additions = new HashSet();
104
		Iterator it = c.iterator();
105
		while (it.hasNext()) {
106
			Object element = it.next();
107
			if (wrappedSet.add(element)) {
108
				additions.add(element);
109
			}
110
		}
111
		if (additions.size() > 0) {
112
			replaceFilters();
113
			fireSetChange(Diffs.createSetDiff(additions, Collections.EMPTY_SET));
114
			return true;
115
		}
116
		return false;
117
	}
118
119
	public void clear() {
120
		getterCalled();
121
		Set removes = new HashSet(wrappedSet);
122
		wrappedSet.clear();
123
		replaceFilters();
124
		fireSetChange(Diffs.createSetDiff(Collections.EMPTY_SET, removes));
125
	}
126
127
	public boolean remove(Object o) {
128
		getterCalled();
129
		boolean removed = wrappedSet.remove(o);
130
		if (removed) {
131
			removeFilter((ViewerFilter) o);
132
			fireSetChange(Diffs.createSetDiff(Collections.EMPTY_SET,
133
					Collections.singleton(o)));
134
		}
135
		return removed;
136
	}
137
138
	public boolean removeAll(Collection c) {
139
		getterCalled();
140
		Set removes = new HashSet();
141
		Iterator it = c.iterator();
142
		while (it.hasNext()) {
143
			Object element = it.next();
144
			if (wrappedSet.remove(element)) {
145
				removes.add(element);
146
			}
147
		}
148
		if (removes.size() > 0) {
149
			replaceFilters();
150
			fireSetChange(Diffs.createSetDiff(Collections.EMPTY_SET, removes));
151
			return true;
152
		}
153
		return false;
154
	}
155
156
	public boolean retainAll(Collection c) {
157
		getterCalled();
158
		Set removes = new HashSet();
159
		Iterator it = wrappedSet.iterator();
160
		while (it.hasNext()) {
161
			Object element = it.next();
162
			if (!c.contains(element)) {
163
				it.remove();
164
				removes.add(element);
165
			}
166
		}
167
		if (removes.size() > 0) {
168
			replaceFilters();
169
			fireSetChange(Diffs.createSetDiff(Collections.EMPTY_SET, removes));
170
			return true;
171
		}
172
		return false;
173
	}
174
}
(-)src/org/eclipse/jface/internal/databinding/viewers/ViewerSingleSelectionObservableValue.java (-45 lines)
Removed Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2005, 2008 IBM Corporation and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
10
 *     Brad Reynolds - bug 137877
11
 *     Brad Reynolds - bug 164653
12
 *     Brad Reynolds - bug 147515
13
 *     Ashley Cambrell - bug 198906
14
 *******************************************************************************/
15
16
package org.eclipse.jface.internal.databinding.viewers;
17
18
import org.eclipse.core.databinding.observable.Realm;
19
import org.eclipse.jface.databinding.viewers.IViewerObservableValue;
20
import org.eclipse.jface.viewers.Viewer;
21
22
/**
23
 * Observes single selection of a <code>Viewer</code>.
24
 * 
25
 * @since 1.2
26
 */
27
public class ViewerSingleSelectionObservableValue extends
28
		SelectionProviderSingleSelectionObservableValue implements
29
		IViewerObservableValue {
30
31
	private Viewer viewer;
32
33
	/**
34
	 * @param realm
35
	 * @param viewer
36
	 */
37
	public ViewerSingleSelectionObservableValue(Realm realm, Viewer viewer) {
38
		super(realm, viewer);
39
		this.viewer = viewer;
40
	}
41
42
	public Viewer getViewer() {
43
		return viewer;
44
	}
45
}
(-)src/org/eclipse/jface/internal/databinding/viewers/ViewerInputObservableValue.java (-73 lines)
Removed Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2007 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 206839)
10
 *******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.viewers;
13
14
import org.eclipse.core.databinding.observable.Diffs;
15
import org.eclipse.core.databinding.observable.Realm;
16
import org.eclipse.core.databinding.observable.value.AbstractObservableValue;
17
import org.eclipse.jface.util.Util;
18
import org.eclipse.jface.viewers.Viewer;
19
20
/**
21
 * Observes the input of a <code>Viewer</code>.
22
 * <p>
23
 * This observer is blind to changes in the viewer's input unless its
24
 * {@link #setValue(Object)} method is called directly.
25
 * 
26
 * @since 1.2
27
 */
28
public class ViewerInputObservableValue extends AbstractObservableValue {
29
30
  private final Viewer viewer;
31
32
  /**
33
   * Constructs a new instance associated with the provided <code>viewer</code>.
34
   * 
35
   * @param realm
36
   * @param viewer
37
   */
38
  public ViewerInputObservableValue( Realm realm, Viewer viewer ) {
39
    super( realm );
40
    if ( viewer == null ) {
41
      throw new IllegalArgumentException( "The 'viewer' parameter is null." ); //$NON-NLS-1$
42
    }
43
44
    this.viewer = viewer;
45
  }
46
47
  /**
48
   * Sets the input to the provided <code>value</code>. Value change events are
49
   * fired after input is set in the viewer.
50
   * 
51
   * @param value object to set as input
52
   */
53
  protected void doSetValue( final Object value ) {
54
    Object oldValue = doGetValue();
55
    viewer.setInput( value );
56
    if ( !Util.equals( oldValue, value ) ) {
57
      fireValueChange( Diffs.createValueDiff( oldValue, value ) );
58
    }
59
  }
60
61
  /**
62
   * Retrieves the current input.
63
   * 
64
   * @return the current input
65
   */
66
  protected Object doGetValue() {
67
    return viewer.getInput();
68
  }
69
70
  public Object getValueType() {
71
    return null;
72
  }
73
}
(-)src/org/eclipse/jface/internal/databinding/viewers/SelectionProviderSingleSelectionObservableValue.java (-147 lines)
Removed Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2005, 2008 IBM Corporation and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
10
 *     Brad Reynolds - bug 137877
11
 *     Brad Reynolds - bug 164653
12
 *     Brad Reynolds - bug 147515
13
 *     Ashley Cambrell - bug 198906
14
 *******************************************************************************/
15
16
package org.eclipse.jface.internal.databinding.viewers;
17
18
import org.eclipse.core.databinding.observable.Diffs;
19
import org.eclipse.core.databinding.observable.Realm;
20
import org.eclipse.core.databinding.observable.value.AbstractObservableValue;
21
import org.eclipse.jface.util.Util;
22
import org.eclipse.jface.viewers.ISelection;
23
import org.eclipse.jface.viewers.ISelectionChangedListener;
24
import org.eclipse.jface.viewers.ISelectionProvider;
25
import org.eclipse.jface.viewers.IStructuredSelection;
26
import org.eclipse.jface.viewers.SelectionChangedEvent;
27
import org.eclipse.jface.viewers.StructuredSelection;
28
29
/**
30
 * Observes single selection of an <code>ISelectionProvider</code>.
31
 *
32
 * @since 1.1
33
 */
34
public class SelectionProviderSingleSelectionObservableValue extends
35
		AbstractObservableValue {
36
37
	private final ISelectionProvider selectionProvider;
38
39
	private boolean updating = false;
40
41
	private Object currentSelection;
42
43
	private ISelectionChangedListener selectionChangedListener;
44
45
	/**
46
	 * Constructs a new instance associated with the provided
47
	 * <code>selectionProvider</code>. In order to initialize itself properly
48
	 * the constructor invokes {@link #doGetValue()}. This could be dangerous
49
	 * for subclasses, see {@link #doGetValue()} for an explanation.
50
	 *
51
	 * @param realm
52
	 *
53
	 * @param selectionProvider
54
	 * @see #doGetValue()
55
	 */
56
	public SelectionProviderSingleSelectionObservableValue(Realm realm,
57
			ISelectionProvider selectionProvider) {
58
		super(realm);
59
		if (selectionProvider == null) {
60
			throw new IllegalArgumentException(
61
					"The 'selectionProvider' parameter is null."); //$NON-NLS-1$
62
		}
63
64
		this.selectionProvider = selectionProvider;
65
		this.currentSelection = doGetValue();
66
67
		selectionChangedListener = new ISelectionChangedListener() {
68
			public void selectionChanged(SelectionChangedEvent event) {
69
				if (!updating) {
70
					Object oldSelection = currentSelection;
71
					currentSelection = doGetValue();
72
					fireValueChange(Diffs.createValueDiff(oldSelection,
73
							currentSelection));
74
				}
75
			}
76
		};
77
		selectionProvider.addSelectionChangedListener(selectionChangedListener);
78
	}
79
80
	/**
81
	 * Sets the selection to the provided <code>value</code>. Value change
82
	 * events are fired after selection is set in the selection provider.
83
	 *
84
	 * @param value
85
	 *            object to set as selected, <code>null</code> if wanting to
86
	 *            remove selection
87
	 */
88
	public void doSetValue(final Object value) {
89
		try {
90
			updating = true;
91
92
			Object oldSelection = currentSelection;
93
			selectionProvider
94
					.setSelection(value == null ? StructuredSelection.EMPTY
95
							: new StructuredSelection(value));
96
			currentSelection = doGetValue();
97
			if (!Util.equals(oldSelection, currentSelection)) {
98
				fireValueChange(Diffs.createValueDiff(oldSelection,
99
						currentSelection));
100
			}
101
		} finally {
102
			updating = false;
103
		}
104
	}
105
106
	/**
107
	 * Retrieves the current selection.
108
	 * <p>
109
	 * If a subclass overrides this method it must not depend upon the subclass
110
	 * to have been fully initialized before this method is invoked.
111
	 * <code>doGetValue()</code> is invoked by the
112
	 * {@link #SelectionProviderSingleSelectionObservableValue(Realm, ISelectionProvider) constructor}
113
	 * which means the subclass's constructor will not have fully executed
114
	 * before this method is invoked.
115
	 * </p>
116
	 *
117
	 * @return selection will be an instance of
118
	 *         <code>IStructuredSelection</code> if a selection exists,
119
	 *         <code>null</code> if no selection
120
	 * @see #SelectionProviderSingleSelectionObservableValue(Realm,
121
	 *      ISelectionProvider)
122
	 */
123
	protected Object doGetValue() {
124
		ISelection selection = selectionProvider.getSelection();
125
		if (selection instanceof IStructuredSelection) {
126
			IStructuredSelection sel = (IStructuredSelection) selection;
127
			return sel.getFirstElement();
128
		}
129
130
		return null;
131
	}
132
133
	public Object getValueType() {
134
		return null;
135
	}
136
137
	/*
138
	 * (non-Javadoc)
139
	 *
140
	 * @see org.eclipse.core.databinding.observable.value.AbstractObservableValue#dispose()
141
	 */
142
	public synchronized void dispose() {
143
		selectionProvider
144
				.removeSelectionChangedListener(selectionChangedListener);
145
		super.dispose();
146
	}
147
}
(-)src/org/eclipse/jface/internal/databinding/viewers/CheckableCheckedElementsObservableSet.java (-219 lines)
Removed Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 124684)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.viewers;
13
14
import java.util.Collection;
15
import java.util.Collections;
16
import java.util.HashSet;
17
import java.util.Iterator;
18
import java.util.Set;
19
20
import org.eclipse.core.databinding.observable.Diffs;
21
import org.eclipse.core.databinding.observable.Realm;
22
import org.eclipse.core.databinding.observable.set.AbstractObservableSet;
23
import org.eclipse.core.runtime.Assert;
24
import org.eclipse.jface.viewers.CheckStateChangedEvent;
25
import org.eclipse.jface.viewers.ICheckStateListener;
26
import org.eclipse.jface.viewers.ICheckable;
27
28
/**
29
 * 
30
 * @since 1.2
31
 */
32
public class CheckableCheckedElementsObservableSet extends
33
		AbstractObservableSet {
34
	private ICheckable checkable;
35
	private Set wrappedSet;
36
	private Object elementType;
37
	private ICheckStateListener listener;
38
39
	/**
40
	 * Constructs a new instance on the given realm and checkable.
41
	 * 
42
	 * @param realm
43
	 *            the observable's realm
44
	 * @param checkable
45
	 *            the ICheckable to track
46
	 * @param elementType
47
	 *            type of elements in the set
48
	 */
49
	public CheckableCheckedElementsObservableSet(Realm realm,
50
			ICheckable checkable, Object elementType) {
51
		this(realm, checkable, elementType, new HashSet());
52
	}
53
54
	/**
55
	 * Constructs a new instance of the given realm, and checkable,
56
	 * 
57
	 * @param realm
58
	 *            the observable's realm
59
	 * @param checkable
60
	 *            the ICheckable to track
61
	 * @param elementType
62
	 *            type of elements in the set
63
	 * @param wrappedSet
64
	 *            the set being wrapped
65
	 */
66
	public CheckableCheckedElementsObservableSet(Realm realm,
67
			ICheckable checkable, Object elementType, final Set wrappedSet) {
68
		super(realm);
69
		Assert.isNotNull(checkable, "Checkable cannot be null"); //$NON-NLS-1$
70
		Assert.isNotNull(wrappedSet, "Wrapped set cannot be null"); //$NON-NLS-1$
71
		this.checkable = checkable;
72
		this.wrappedSet = wrappedSet;
73
		this.elementType = elementType;
74
75
		listener = new ICheckStateListener() {
76
			public void checkStateChanged(CheckStateChangedEvent event) {
77
				Object element = event.getElement();
78
				if (event.getChecked()) {
79
					if (wrappedSet.add(element))
80
						fireSetChange(Diffs.createSetDiff(Collections
81
								.singleton(element), Collections.EMPTY_SET));
82
				} else {
83
					if (wrappedSet.remove(element))
84
						fireSetChange(Diffs.createSetDiff(
85
								Collections.EMPTY_SET, Collections
86
										.singleton(element)));
87
				}
88
			}
89
		};
90
		checkable.addCheckStateListener(listener);
91
	}
92
93
	protected Set getWrappedSet() {
94
		return wrappedSet;
95
	}
96
97
	Set createDiffSet() {
98
		return new HashSet();
99
	}
100
101
	public Object getElementType() {
102
		return elementType;
103
	}
104
105
	public boolean add(Object o) {
106
		getterCalled();
107
		boolean added = wrappedSet.add(o);
108
		if (added) {
109
			checkable.setChecked(o, true);
110
			fireSetChange(Diffs.createSetDiff(Collections.singleton(o),
111
					Collections.EMPTY_SET));
112
		}
113
		return added;
114
	}
115
116
	public boolean remove(Object o) {
117
		getterCalled();
118
		boolean removed = wrappedSet.remove(o);
119
		if (removed) {
120
			checkable.setChecked(o, false);
121
			fireSetChange(Diffs.createSetDiff(Collections.EMPTY_SET,
122
					Collections.singleton(o)));
123
		}
124
		return removed;
125
	}
126
127
	public boolean addAll(Collection c) {
128
		getterCalled();
129
		Set additions = createDiffSet();
130
		for (Iterator iterator = c.iterator(); iterator.hasNext();) {
131
			Object element = iterator.next();
132
			if (wrappedSet.add(element)) {
133
				checkable.setChecked(element, true);
134
				additions.add(element);
135
			}
136
		}
137
		boolean changed = !additions.isEmpty();
138
		if (changed)
139
			fireSetChange(Diffs.createSetDiff(additions, Collections.EMPTY_SET));
140
		return changed;
141
	}
142
143
	public boolean removeAll(Collection c) {
144
		getterCalled();
145
		Set removals = createDiffSet();
146
		for (Iterator iterator = c.iterator(); iterator.hasNext();) {
147
			Object element = iterator.next();
148
			if (wrappedSet.remove(element)) {
149
				checkable.setChecked(element, false);
150
				removals.add(element);
151
			}
152
		}
153
		boolean changed = !removals.isEmpty();
154
		if (changed)
155
			fireSetChange(Diffs.createSetDiff(Collections.EMPTY_SET, removals));
156
		return changed;
157
	}
158
159
	public boolean retainAll(Collection c) {
160
		getterCalled();
161
162
		// To ensure that elements are compared correctly, e.g. ViewerElementSet
163
		Set toRetain = createDiffSet();
164
		toRetain.addAll(c);
165
166
		Set removals = createDiffSet();
167
		for (Iterator iterator = wrappedSet.iterator(); iterator.hasNext();) {
168
			Object element = iterator.next();
169
			if (!toRetain.contains(element)) {
170
				iterator.remove();
171
				checkable.setChecked(element, false);
172
				removals.add(element);
173
			}
174
		}
175
		boolean changed = !removals.isEmpty();
176
		if (changed)
177
			fireSetChange(Diffs.createSetDiff(Collections.EMPTY_SET, removals));
178
		return changed;
179
	}
180
181
	public void clear() {
182
		removeAll(wrappedSet);
183
	}
184
185
	public Iterator iterator() {
186
		getterCalled();
187
		final Iterator wrappedIterator = wrappedSet.iterator();
188
		return new Iterator() {
189
			private Object last = null;
190
191
			public boolean hasNext() {
192
				getterCalled();
193
				return wrappedIterator.hasNext();
194
			}
195
196
			public Object next() {
197
				getterCalled();
198
				return last = wrappedIterator.next();
199
			}
200
201
			public void remove() {
202
				getterCalled();
203
				wrappedIterator.remove();
204
				checkable.setChecked(last, false);
205
				fireSetChange(Diffs.createSetDiff(Collections.EMPTY_SET,
206
						Collections.singleton(last)));
207
			}
208
		};
209
	}
210
211
	public synchronized void dispose() {
212
		if (checkable != null) {
213
			checkable.removeCheckStateListener(listener);
214
			checkable = null;
215
			listener = null;
216
		}
217
		super.dispose();
218
	}
219
}
(-)src/org/eclipse/jface/internal/databinding/provisional/swt/AbstractSWTObservableValue.java (-69 lines)
Removed Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2006 The Pampered Chef, Inc. and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     The Pampered Chef, Inc. - initial API and implementation
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.provisional.swt;
13
14
import org.eclipse.core.databinding.observable.Realm;
15
import org.eclipse.core.databinding.observable.value.AbstractObservableValue;
16
import org.eclipse.jface.databinding.swt.ISWTObservableValue;
17
import org.eclipse.jface.databinding.swt.SWTObservables;
18
import org.eclipse.swt.events.DisposeEvent;
19
import org.eclipse.swt.events.DisposeListener;
20
import org.eclipse.swt.widgets.Widget;
21
22
/**
23
 * NON-API - An abstract superclass for observable values that gurantees that the 
24
 * observable will be disposed when the control to which it is attached is
25
 * disposed.
26
 * 
27
 * @since 1.1
28
 */
29
public abstract class AbstractSWTObservableValue extends AbstractObservableValue implements ISWTObservableValue {
30
31
	private final Widget widget;
32
33
	/**
34
	 * Standard constructor for an SWT ObservableValue.  Makes sure that
35
	 * the observable gets disposed when the SWT widget is disposed.
36
	 * 
37
	 * @param widget
38
	 */
39
	protected AbstractSWTObservableValue(Widget widget) {
40
		this(SWTObservables.getRealm(widget.getDisplay()), widget);
41
	}
42
	
43
	/**
44
	 * Constructor that allows for the setting of the realm. Makes sure that the
45
	 * observable gets disposed when the SWT widget is disposed.
46
	 * 
47
	 * @param realm
48
	 * @param widget
49
	 * @since 1.2
50
	 */
51
	protected AbstractSWTObservableValue(Realm realm, Widget widget) {
52
		super(realm);
53
		this.widget = widget;
54
		widget.addDisposeListener(disposeListener);
55
	}
56
	
57
	private DisposeListener disposeListener = new DisposeListener() {
58
		public void widgetDisposed(DisposeEvent e) {
59
			AbstractSWTObservableValue.this.dispose();
60
		}
61
	};
62
63
	/**
64
	 * @return Returns the widget.
65
	 */
66
	public Widget getWidget() {
67
		return widget;
68
	}
69
}
(-)src/org/eclipse/jface/internal/databinding/provisional/swt/AbstractSWTVetoableValue.java (-71 lines)
Removed Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2006 The Pampered Chef, Inc. and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     The Pampered Chef, Inc. - initial API and implementation
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.provisional.swt;
13
14
import org.eclipse.core.databinding.observable.Realm;
15
import org.eclipse.core.databinding.observable.value.AbstractVetoableValue;
16
import org.eclipse.jface.databinding.swt.ISWTObservableValue;
17
import org.eclipse.jface.databinding.swt.SWTObservables;
18
import org.eclipse.swt.events.DisposeEvent;
19
import org.eclipse.swt.events.DisposeListener;
20
import org.eclipse.swt.widgets.Widget;
21
22
/**
23
 * NON-API - An abstract superclass for vetoable values that gurantees that the 
24
 * observable will be disposed when the control to which it is attached is
25
 * disposed.
26
 * 
27
 * @since 1.1
28
 */
29
public abstract class AbstractSWTVetoableValue extends AbstractVetoableValue implements ISWTObservableValue {
30
31
	private final Widget widget;
32
33
	/**
34
	 * Standard constructor for an SWT VetoableValue.  Makes sure that
35
	 * the observable gets disposed when the SWT widget is disposed.
36
	 * 
37
	 * @param widget
38
	 */
39
	protected AbstractSWTVetoableValue(Widget widget) {
40
		this(SWTObservables.getRealm(widget.getDisplay()), widget);
41
	}
42
	
43
	/**
44
	 * Constructs a new instance for the provided <code>realm</code> and <code>widget</code>.
45
	 * 
46
	 * @param realm
47
	 * @param widget
48
	 * @since 1.2
49
	 */
50
	protected AbstractSWTVetoableValue(Realm realm, Widget widget) {
51
		super(realm);
52
		this.widget = widget;
53
		if (widget == null) {
54
			throw new IllegalArgumentException("The widget parameter is null."); //$NON-NLS-1$
55
		}
56
		widget.addDisposeListener(disposeListener);
57
	}
58
	
59
	private DisposeListener disposeListener = new DisposeListener() {
60
		public void widgetDisposed(DisposeEvent e) {
61
			AbstractSWTVetoableValue.this.dispose();
62
		}
63
	};
64
65
	/**
66
	 * @return Returns the widget.
67
	 */
68
	public Widget getWidget() {
69
		return widget;
70
	}
71
}
(-)src/org/eclipse/jface/databinding/swt/SWTObservables.java (-114 / +181 lines)
Lines 9-17 Link Here
9
 *     IBM Corporation - initial API and implementation
9
 *     IBM Corporation - initial API and implementation
10
 *     Matt Carter - bug 170668
10
 *     Matt Carter - bug 170668
11
 *     Brad Reynolds - bug 170848
11
 *     Brad Reynolds - bug 170848
12
 *     Matthew Hall - bugs 180746, 207844, 245647, 248621, 232917
12
 *     Matthew Hall - bugs 180746, 207844, 245647, 248621, 232917, 194734
13
 *     Michael Krauter - bug 180223
13
 *     Michael Krauter - bug 180223
14
 *     Boris Bokowski - bug 245647
14
 *     Boris Bokowski - bug 245647
15
 *     Tom Schindl - bug 246462
15
 *******************************************************************************/
16
 *******************************************************************************/
16
package org.eclipse.jface.databinding.swt;
17
package org.eclipse.jface.databinding.swt;
17
18
Lines 24-57 Link Here
24
import org.eclipse.core.databinding.observable.value.IObservableValue;
25
import org.eclipse.core.databinding.observable.value.IObservableValue;
25
import org.eclipse.core.databinding.observable.value.IVetoableValue;
26
import org.eclipse.core.databinding.observable.value.IVetoableValue;
26
import org.eclipse.core.databinding.observable.value.ValueChangingEvent;
27
import org.eclipse.core.databinding.observable.value.ValueChangingEvent;
27
import org.eclipse.jface.internal.databinding.internal.swt.LinkObservableValue;
28
import org.eclipse.core.databinding.property.list.IListProperty;
28
import org.eclipse.jface.internal.databinding.swt.ButtonObservableValue;
29
import org.eclipse.core.databinding.property.value.IValueProperty;
29
import org.eclipse.jface.internal.databinding.swt.CComboObservableList;
30
import org.eclipse.jface.internal.databinding.swt.CComboObservableValue;
31
import org.eclipse.jface.internal.databinding.swt.CComboSingleSelectionObservableValue;
32
import org.eclipse.jface.internal.databinding.swt.CLabelObservableValue;
33
import org.eclipse.jface.internal.databinding.swt.ComboObservableList;
34
import org.eclipse.jface.internal.databinding.swt.ComboObservableValue;
35
import org.eclipse.jface.internal.databinding.swt.ComboSingleSelectionObservableValue;
36
import org.eclipse.jface.internal.databinding.swt.ControlObservableValue;
37
import org.eclipse.jface.internal.databinding.swt.ItemObservableValue;
38
import org.eclipse.jface.internal.databinding.swt.ItemTooltipObservableValue;
39
import org.eclipse.jface.internal.databinding.swt.LabelObservableValue;
40
import org.eclipse.jface.internal.databinding.swt.ListObservableList;
41
import org.eclipse.jface.internal.databinding.swt.ListObservableValue;
42
import org.eclipse.jface.internal.databinding.swt.ListSingleSelectionObservableValue;
43
import org.eclipse.jface.internal.databinding.swt.SWTDelayedObservableValueDecorator;
30
import org.eclipse.jface.internal.databinding.swt.SWTDelayedObservableValueDecorator;
44
import org.eclipse.jface.internal.databinding.swt.SWTProperties;
31
import org.eclipse.jface.internal.databinding.swt.SWTObservableListDecorator;
45
import org.eclipse.jface.internal.databinding.swt.ScaleObservableValue;
32
import org.eclipse.jface.internal.databinding.swt.SWTObservableValueDecorator;
46
import org.eclipse.jface.internal.databinding.swt.ShellObservableValue;
33
import org.eclipse.jface.internal.databinding.swt.SWTVetoableValueDecorator;
47
import org.eclipse.jface.internal.databinding.swt.SpinnerObservableValue;
48
import org.eclipse.jface.internal.databinding.swt.TableSingleSelectionObservableValue;
49
import org.eclipse.jface.internal.databinding.swt.TextEditableObservableValue;
50
import org.eclipse.jface.internal.databinding.swt.TextObservableValue;
51
import org.eclipse.swt.SWT;
34
import org.eclipse.swt.SWT;
52
import org.eclipse.swt.custom.CCombo;
35
import org.eclipse.swt.custom.CCombo;
53
import org.eclipse.swt.custom.CLabel;
36
import org.eclipse.swt.custom.CLabel;
54
import org.eclipse.swt.custom.CTabItem;
37
import org.eclipse.swt.custom.CTabItem;
38
import org.eclipse.swt.custom.StyledText;
55
import org.eclipse.swt.widgets.Button;
39
import org.eclipse.swt.widgets.Button;
56
import org.eclipse.swt.widgets.Combo;
40
import org.eclipse.swt.widgets.Combo;
57
import org.eclipse.swt.widgets.Control;
41
import org.eclipse.swt.widgets.Control;
Lines 139-164 Link Here
139
				.observeDelayedValue(delay, observable), observable.getWidget());
123
				.observeDelayedValue(delay, observable), observable.getWidget());
140
	}
124
	}
141
125
126
	private static ISWTObservableValue observeWidgetProperty(Widget widget,
127
			IValueProperty property) {
128
		return new SWTObservableValueDecorator(property.observeValue(
129
				getRealm(widget.getDisplay()), widget), widget);
130
	}
131
142
	/**
132
	/**
133
	 * Returns an observable value tracking the enabled state of the given
134
	 * control
135
	 * 
143
	 * @param control
136
	 * @param control
137
	 *            the control to observe
144
	 * @return an observable value tracking the enabled state of the given
138
	 * @return an observable value tracking the enabled state of the given
145
	 *         control
139
	 *         control
146
	 */
140
	 */
147
	public static ISWTObservableValue observeEnabled(Control control) {
141
	public static ISWTObservableValue observeEnabled(Control control) {
148
		return new ControlObservableValue(control, SWTProperties.ENABLED);
142
		return observeWidgetProperty(control, ControlProperties.enabled());
149
	}
143
	}
150
144
151
	/**
145
	/**
146
	 * Returns an observable value tracking the visible state of the given
147
	 * control
148
	 * 
152
	 * @param control
149
	 * @param control
150
	 *            the control to observe
153
	 * @return an observable value tracking the visible state of the given
151
	 * @return an observable value tracking the visible state of the given
154
	 *         control
152
	 *         control
155
	 */
153
	 */
156
	public static ISWTObservableValue observeVisible(Control control) {
154
	public static ISWTObservableValue observeVisible(Control control) {
157
		return new ControlObservableValue(control, SWTProperties.VISIBLE);
155
		return observeWidgetProperty(control, ControlProperties.visible());
158
	}
156
	}
159
157
160
	/**
158
	/**
161
	 * Returns an observable tracking the tooltip text of the given item. The supported types are:
159
	 * Returns an observable tracking the tooltip text of the given item. The
160
	 * supported types are:
162
	 * <ul>
161
	 * <ul>
163
	 * <li>org.eclipse.swt.widgets.Control</li>
162
	 * <li>org.eclipse.swt.widgets.Control</li>
164
	 * <li>org.eclipse.swt.custom.CTabItem</li>
163
	 * <li>org.eclipse.swt.custom.CTabItem</li>
Lines 168-202 Link Here
168
	 * <li>org.eclipse.swt.widgets.TrayItem</li>
167
	 * <li>org.eclipse.swt.widgets.TrayItem</li>
169
	 * <li>org.eclipse.swt.widgets.TreeColumn</li>
168
	 * <li>org.eclipse.swt.widgets.TreeColumn</li>
170
	 * </ul>
169
	 * </ul>
170
	 * 
171
	 * @param widget
171
	 * @param widget
172
	 * @return an observable value tracking the tooltip text of the given
172
	 * @return an observable value tracking the tooltip text of the given item
173
	 *         item
174
	 * 
173
	 * 
175
	 * @since 1.3
174
	 * @since 1.3
176
	 */
175
	 */
177
	public static ISWTObservableValue observeTooltipText(Widget widget) {
176
	public static ISWTObservableValue observeTooltipText(Widget widget) {
178
		if (widget instanceof Control) {
177
		if (widget instanceof Control) {
179
			return new ControlObservableValue((Control)widget, SWTProperties.TOOLTIP_TEXT);
178
			return observeTooltipText((Control) widget);
180
		} else if (widget instanceof CTabItem
181
				|| widget instanceof TabItem
182
				|| widget instanceof TableColumn
183
				|| widget instanceof ToolItem
184
				|| widget instanceof TrayItem
185
				|| widget instanceof TreeColumn) {
186
			return new ItemTooltipObservableValue((Item) widget);
187
		}
179
		}
188
		
180
189
		throw new IllegalArgumentException(
181
		IValueProperty property;
190
				"Item [" + widget.getClass().getName() + "] is not supported."); //$NON-NLS-1$//$NON-NLS-2$
182
		if (widget instanceof CTabItem) {
183
			property = CTabItemProperties.tooltipText();
184
		} else if (widget instanceof TabItem) {
185
			property = TabItemProperties.tooltipText();
186
		} else if (widget instanceof TableColumn) {
187
			property = TableColumnProperties.tooltipText();
188
		} else if (widget instanceof ToolItem) {
189
			property = ToolItemProperties.tooltipText();
190
		} else if (widget instanceof TrayItem) {
191
			property = TrayItemProperties.tooltipText();
192
		} else if (widget instanceof TreeColumn) {
193
			property = TreeColumnProperties.tooltipText();
194
		} else {
195
			throw new IllegalArgumentException(
196
					"Item [" + widget.getClass().getName() + "] is not supported."); //$NON-NLS-1$//$NON-NLS-2$
197
		}
198
199
		return observeWidgetProperty(widget, property);
191
	}
200
	}
192
201
193
	/**
202
	/**
203
	 * Returns an observable value tracking the tooltip text of the given
204
	 * control
205
	 * 
194
	 * @param control
206
	 * @param control
207
	 *            the control to observe
195
	 * @return an observable value tracking the tooltip text of the given
208
	 * @return an observable value tracking the tooltip text of the given
196
	 *         control
209
	 *         control
197
	 */
210
	 */
198
	public static ISWTObservableValue observeTooltipText(Control control) {
211
	public static ISWTObservableValue observeTooltipText(Control control) {
199
		return observeTooltipText((Widget) control);
212
		return observeWidgetProperty(control, ControlProperties.toolTipText());
200
	}
213
	}
201
214
202
	/**
215
	/**
Lines 217-242 Link Here
217
	 *             if <code>control</code> type is unsupported
230
	 *             if <code>control</code> type is unsupported
218
	 */
231
	 */
219
	public static ISWTObservableValue observeSelection(Control control) {
232
	public static ISWTObservableValue observeSelection(Control control) {
233
		IValueProperty property;
220
		if (control instanceof Spinner) {
234
		if (control instanceof Spinner) {
221
			return new SpinnerObservableValue((Spinner) control,
235
			property = SpinnerProperties.selection();
222
					SWTProperties.SELECTION);
223
		} else if (control instanceof Button) {
236
		} else if (control instanceof Button) {
224
			return new ButtonObservableValue((Button) control);
237
			property = ButtonProperties.selection();
225
		} else if (control instanceof Combo) {
238
		} else if (control instanceof Combo) {
226
			return new ComboObservableValue((Combo) control,
239
			property = ComboProperties.selection();
227
					SWTProperties.SELECTION);
228
		} else if (control instanceof CCombo) {
240
		} else if (control instanceof CCombo) {
229
			return new CComboObservableValue((CCombo) control,
241
			property = CComboProperties.selection();
230
					SWTProperties.SELECTION);
231
		} else if (control instanceof List) {
242
		} else if (control instanceof List) {
232
			return new ListObservableValue((List) control);
243
			property = ListProperties.selection();
233
		} else if (control instanceof Scale) {
244
		} else if (control instanceof Scale) {
234
			return new ScaleObservableValue((Scale) control,
245
			property = ScaleProperties.selection();
235
					SWTProperties.SELECTION);
246
		} else {
247
			throw new IllegalArgumentException(
248
					"Widget [" + control.getClass().getName() + "] is not supported."); //$NON-NLS-1$//$NON-NLS-2$
236
		}
249
		}
237
250
238
		throw new IllegalArgumentException(
251
		return observeWidgetProperty(control, property);
239
				"Widget [" + control.getClass().getName() + "] is not supported."); //$NON-NLS-1$//$NON-NLS-2$
240
	}
252
	}
241
253
242
	/**
254
	/**
Lines 253-267 Link Here
253
	 *             if <code>control</code> type is unsupported
265
	 *             if <code>control</code> type is unsupported
254
	 */
266
	 */
255
	public static ISWTObservableValue observeMin(Control control) {
267
	public static ISWTObservableValue observeMin(Control control) {
268
		IValueProperty property;
256
		if (control instanceof Spinner) {
269
		if (control instanceof Spinner) {
257
			return new SpinnerObservableValue((Spinner) control,
270
			property = SpinnerProperties.minimum();
258
					SWTProperties.MIN);
259
		} else if (control instanceof Scale) {
271
		} else if (control instanceof Scale) {
260
			return new ScaleObservableValue((Scale) control, SWTProperties.MIN);
272
			property = ScaleProperties.minimum();
273
		} else {
274
			throw new IllegalArgumentException(
275
					"Widget [" + control.getClass().getName() + "] is not supported."); //$NON-NLS-1$//$NON-NLS-2$
261
		}
276
		}
262
277
263
		throw new IllegalArgumentException(
278
		return observeWidgetProperty(control, property);
264
				"Widget [" + control.getClass().getName() + "] is not supported."); //$NON-NLS-1$//$NON-NLS-2$
265
	}
279
	}
266
280
267
	/**
281
	/**
Lines 278-292 Link Here
278
	 *             if <code>control</code> type is unsupported
292
	 *             if <code>control</code> type is unsupported
279
	 */
293
	 */
280
	public static ISWTObservableValue observeMax(Control control) {
294
	public static ISWTObservableValue observeMax(Control control) {
295
		IValueProperty property;
281
		if (control instanceof Spinner) {
296
		if (control instanceof Spinner) {
282
			return new SpinnerObservableValue((Spinner) control,
297
			property = SpinnerProperties.maximum();
283
					SWTProperties.MAX);
284
		} else if (control instanceof Scale) {
298
		} else if (control instanceof Scale) {
285
			return new ScaleObservableValue((Scale) control, SWTProperties.MAX);
299
			property = ScaleProperties.maximum();
300
		} else {
301
			throw new IllegalArgumentException(
302
					"Widget [" + control.getClass().getName() + "] is not supported."); //$NON-NLS-1$//$NON-NLS-2$
286
		}
303
		}
287
304
288
		throw new IllegalArgumentException(
305
		return observeWidgetProperty(control, property);
289
				"Widget [" + control.getClass().getName() + "] is not supported."); //$NON-NLS-1$//$NON-NLS-2$
290
	}
306
	}
291
307
292
	/**
308
	/**
Lines 294-314 Link Here
294
	 * <code>control</code>. The supported types are:
310
	 * <code>control</code>. The supported types are:
295
	 * <ul>
311
	 * <ul>
296
	 * <li>org.eclipse.swt.widgets.Text</li>
312
	 * <li>org.eclipse.swt.widgets.Text</li>
313
	 * <li>org.eclipse.swt.custom.StyledText (as of 1.3)</li>
297
	 * </ul>
314
	 * </ul>
298
	 * 
315
	 * 
299
	 * @param control
316
	 * @param control
300
	 * @param event event type to register for change events
317
	 * @param event
318
	 *            event type to register for change events
301
	 * @return observable value
319
	 * @return observable value
302
	 * @throws IllegalArgumentException
320
	 * @throws IllegalArgumentException
303
	 *             if <code>control</code> type is unsupported
321
	 *             if <code>control</code> type is unsupported
304
	 */
322
	 */
305
	public static ISWTObservableValue observeText(Control control, int event) {
323
	public static ISWTObservableValue observeText(Control control, int event) {
324
		IValueProperty property;
306
		if (control instanceof Text) {
325
		if (control instanceof Text) {
307
			return new TextObservableValue((Text) control, event);
326
			property = TextProperties.text(event);
327
		} else if (control instanceof StyledText) {
328
			property = StyledTextProperties.text(event);
329
		} else {
330
			throw new IllegalArgumentException(
331
					"Widget [" + control.getClass().getName() + "] is not supported."); //$NON-NLS-1$//$NON-NLS-2$
308
		}
332
		}
309
333
310
		throw new IllegalArgumentException(
334
		return new SWTVetoableValueDecorator(property.observeValue(
311
				"Widget [" + control.getClass().getName() + "] is not supported."); //$NON-NLS-1$//$NON-NLS-2$
335
				getRealm(control.getDisplay()), control), control);
312
	}
336
	}
313
337
314
	/**
338
	/**
Lines 329-355 Link Here
329
	 * @return observable value
353
	 * @return observable value
330
	 * @throws IllegalArgumentException
354
	 * @throws IllegalArgumentException
331
	 *             if the type of <code>widget</code> is unsupported
355
	 *             if the type of <code>widget</code> is unsupported
332
	 *             
356
	 * 
333
	 * @since 1.3
357
	 * @since 1.3
334
	 */
358
	 */
335
	public static ISWTObservableValue observeText(Widget widget) {
359
	public static ISWTObservableValue observeText(Widget widget) {
336
		if (widget instanceof Label) {
360
		if (widget instanceof Control) {
337
			return new LabelObservableValue((Label) widget);
361
			return observeText((Control) widget);
338
		} else if (widget instanceof Link) {
339
			return new LinkObservableValue((Link) widget);
340
		} else if (widget instanceof CLabel) {
341
			return new CLabelObservableValue((CLabel) widget);
342
		} else if (widget instanceof Combo) {
343
			return new ComboObservableValue((Combo) widget, SWTProperties.TEXT);
344
		} else if (widget instanceof CCombo) {
345
			return new CComboObservableValue((CCombo) widget,
346
					SWTProperties.TEXT);
347
		} else if (widget instanceof Shell) {
348
			return new ShellObservableValue((Shell) widget);
349
		} else if (widget instanceof Text) {
350
			return new TextObservableValue((Text) widget, SWT.None);
351
		} else if (widget instanceof Item) {
362
		} else if (widget instanceof Item) {
352
			return new ItemObservableValue((Item)widget);
363
			return observeWidgetProperty(widget, ItemProperties.text());
353
		}
364
		}
354
365
355
		throw new IllegalArgumentException(
366
		throw new IllegalArgumentException(
Lines 367-372 Link Here
367
	 * <li>org.eclipse.swt.custom.CCombo</li>
378
	 * <li>org.eclipse.swt.custom.CCombo</li>
368
	 * <li>org.eclipse.swt.widgets.Shell</li>
379
	 * <li>org.eclipse.swt.widgets.Shell</li>
369
	 * <li>org.eclipse.swt.widgets.Text (as of 1.3)</li>
380
	 * <li>org.eclipse.swt.widgets.Text (as of 1.3)</li>
381
	 * <li>org.eclipse.swt.custom.StyledText (as of 1.3)</li>
370
	 * </ul>
382
	 * </ul>
371
	 * 
383
	 * 
372
	 * @param control
384
	 * @param control
Lines 375-381 Link Here
375
	 *             if <code>control</code> type is unsupported
387
	 *             if <code>control</code> type is unsupported
376
	 */
388
	 */
377
	public static ISWTObservableValue observeText(Control control) {
389
	public static ISWTObservableValue observeText(Control control) {
378
		return observeText((Widget) control);
390
		if (control instanceof Text || control instanceof StyledText) {
391
			return observeText(control, SWT.None);
392
		}
393
394
		IValueProperty property;
395
		if (control instanceof Label) {
396
			property = LabelProperties.text();
397
		} else if (control instanceof Link) {
398
			property = LinkProperties.text();
399
		} else if (control instanceof CLabel) {
400
			property = CLabelProperties.text();
401
		} else if (control instanceof Combo) {
402
			property = ComboProperties.text();
403
		} else if (control instanceof CCombo) {
404
			property = CComboProperties.text();
405
		} else if (control instanceof Shell) {
406
			property = ShellProperties.text();
407
		} else {
408
			throw new IllegalArgumentException(
409
					"Widget [" + control.getClass().getName() + "] is not supported."); //$NON-NLS-1$//$NON-NLS-2$
410
		}
411
412
		return observeWidgetProperty(control, property);
379
	}
413
	}
380
414
381
	/**
415
	/**
Lines 393-408 Link Here
393
	 *             if <code>control</code> type is unsupported
427
	 *             if <code>control</code> type is unsupported
394
	 */
428
	 */
395
	public static IObservableList observeItems(Control control) {
429
	public static IObservableList observeItems(Control control) {
430
		IListProperty property;
396
		if (control instanceof Combo) {
431
		if (control instanceof Combo) {
397
			return new ComboObservableList((Combo) control);
432
			property = ComboProperties.items();
398
		} else if (control instanceof CCombo) {
433
		} else if (control instanceof CCombo) {
399
			return new CComboObservableList((CCombo) control);
434
			property = CComboProperties.items();
400
		} else if (control instanceof List) {
435
		} else if (control instanceof List) {
401
			return new ListObservableList((List) control);
436
			property = ListProperties.items();
437
		} else {
438
			throw new IllegalArgumentException(
439
					"Widget [" + control.getClass().getName() + "] is not supported."); //$NON-NLS-1$//$NON-NLS-2$
402
		}
440
		}
403
441
404
		throw new IllegalArgumentException(
442
		return new SWTObservableListDecorator(property.observeList(
405
				"Widget [" + control.getClass().getName() + "] is not supported."); //$NON-NLS-1$//$NON-NLS-2$
443
				getRealm(control.getDisplay()), control), control);
406
	}
444
	}
407
445
408
	/**
446
	/**
Lines 422-506 Link Here
422
	 */
460
	 */
423
	public static ISWTObservableValue observeSingleSelectionIndex(
461
	public static ISWTObservableValue observeSingleSelectionIndex(
424
			Control control) {
462
			Control control) {
463
		IValueProperty property;
425
		if (control instanceof Table) {
464
		if (control instanceof Table) {
426
			return new TableSingleSelectionObservableValue((Table) control);
465
			property = TableProperties.singleSelectionIndex();
427
		} else if (control instanceof Combo) {
466
		} else if (control instanceof Combo) {
428
			return new ComboSingleSelectionObservableValue((Combo) control);
467
			property = ComboProperties.singleSelectionIndex();
429
		} else if (control instanceof CCombo) {
468
		} else if (control instanceof CCombo) {
430
			return new CComboSingleSelectionObservableValue((CCombo) control);
469
			property = CComboProperties.singleSelectionIndex();
431
		} else if (control instanceof List) {
470
		} else if (control instanceof List) {
432
			return new ListSingleSelectionObservableValue((List) control);
471
			property = ListProperties.singleSelectionIndex();
472
		} else {
473
			throw new IllegalArgumentException(
474
					"Widget [" + control.getClass().getName() + "] is not supported."); //$NON-NLS-1$//$NON-NLS-2$
433
		}
475
		}
434
476
435
		throw new IllegalArgumentException(
477
		return observeWidgetProperty(control, property);
436
				"Widget [" + control.getClass().getName() + "] is not supported."); //$NON-NLS-1$//$NON-NLS-2$
437
	}
478
	}
438
479
439
	/**
480
	/**
481
	 * Returns an observable value tracking the foreground color of the given
482
	 * control
483
	 * 
440
	 * @param control
484
	 * @param control
485
	 *            the control to observe
441
	 * @return an observable value tracking the foreground color of the given
486
	 * @return an observable value tracking the foreground color of the given
442
	 *         control
487
	 *         control
443
	 */
488
	 */
444
	public static ISWTObservableValue observeForeground(Control control) {
489
	public static ISWTObservableValue observeForeground(Control control) {
445
		return new ControlObservableValue(control, SWTProperties.FOREGROUND);
490
		return observeWidgetProperty(control, ControlProperties.foreground());
446
	}
491
	}
447
492
448
	/**
493
	/**
494
	 * Returns an observable value tracking the background color of the given
495
	 * control
496
	 * 
449
	 * @param control
497
	 * @param control
498
	 *            the control to observe
450
	 * @return an observable value tracking the background color of the given
499
	 * @return an observable value tracking the background color of the given
451
	 *         control
500
	 *         control
452
	 */
501
	 */
453
	public static ISWTObservableValue observeBackground(Control control) {
502
	public static ISWTObservableValue observeBackground(Control control) {
454
		return new ControlObservableValue(control, SWTProperties.BACKGROUND);
503
		return observeWidgetProperty(control, ControlProperties.background());
455
	}
504
	}
456
505
457
	/**
506
	/**
507
	 * Returns an observable value tracking the font of the given control.
508
	 * 
458
	 * @param control
509
	 * @param control
510
	 *            the control to observe
459
	 * @return an observable value tracking the font of the given control
511
	 * @return an observable value tracking the font of the given control
460
	 */
512
	 */
461
	public static ISWTObservableValue observeFont(Control control) {
513
	public static ISWTObservableValue observeFont(Control control) {
462
		return new ControlObservableValue(control, SWTProperties.FONT);
514
		return observeWidgetProperty(control, ControlProperties.font());
463
	}
515
	}
464
	
516
465
	/**
517
	/**
518
	 * Returns an observable value tracking the size of the given control.
519
	 * 
466
	 * @param control
520
	 * @param control
521
	 *            the control to observe
467
	 * @return an observable value tracking the size of the given control
522
	 * @return an observable value tracking the size of the given control
468
	 * @since 1.3
523
	 * @since 1.3
469
	 */
524
	 */
470
	public static ISWTObservableValue observeSize(Control control) {
525
	public static ISWTObservableValue observeSize(Control control) {
471
		return new ControlObservableValue(control,SWTProperties.SIZE);
526
		return observeWidgetProperty(control, ControlProperties.size());
472
	}
527
	}
473
	
528
474
	/**
529
	/**
530
	 * Returns an observable value tracking the location of the given control.
531
	 * 
475
	 * @param control
532
	 * @param control
533
	 *            the control to observe
476
	 * @return an observable value tracking the location of the given control
534
	 * @return an observable value tracking the location of the given control
477
	 * @since 1.3
535
	 * @since 1.3
478
	 */
536
	 */
479
	public static ISWTObservableValue observeLocation(Control control) {
537
	public static ISWTObservableValue observeLocation(Control control) {
480
		return new ControlObservableValue(control,SWTProperties.LOCATION);
538
		return observeWidgetProperty(control, ControlProperties.location());
481
	}
539
	}
482
	
540
483
	/**
541
	/**
542
	 * Returns an observable value tracking the focus of the given control.
543
	 * 
484
	 * @param control
544
	 * @param control
545
	 *            the control to observe
485
	 * @return an observable value tracking the focus of the given control
546
	 * @return an observable value tracking the focus of the given control
486
	 * @since 1.3
547
	 * @since 1.3
487
	 */
548
	 */
488
	public static ISWTObservableValue observeFocus(Control control) {
549
	public static ISWTObservableValue observeFocus(Control control) {
489
		return new ControlObservableValue(control,SWTProperties.FOCUS);
550
		return observeWidgetProperty(control, ControlProperties.focused());
490
	}
551
	}
491
	
552
492
	/**
553
	/**
554
	 * Returns an observable value tracking the bounds of the given control.
555
	 * 
493
	 * @param control
556
	 * @param control
557
	 *            the control to observe
494
	 * @return an observable value tracking the bounds of the given control
558
	 * @return an observable value tracking the bounds of the given control
495
	 * @since 1.3
559
	 * @since 1.3
496
	 */
560
	 */
497
	public static ISWTObservableValue observeBounds(Control control) {
561
	public static ISWTObservableValue observeBounds(Control control) {
498
		return new ControlObservableValue(control,SWTProperties.BOUNDS);
562
		return observeWidgetProperty(control, ControlProperties.bounds());
499
	}
563
	}
500
	
564
501
	/**
565
	/**
502
	 * Returns an observable observing the editable attribute of
566
	 * Returns an observable observing the editable attribute of the provided
503
	 * the provided <code>control</code>. The supported types are:
567
	 * <code>control</code>. The supported types are:
504
	 * <ul>
568
	 * <ul>
505
	 * <li>org.eclipse.swt.widgets.Text</li>
569
	 * <li>org.eclipse.swt.widgets.Text</li>
506
	 * </ul>
570
	 * </ul>
Lines 511-522 Link Here
511
	 *             if <code>control</code> type is unsupported
575
	 *             if <code>control</code> type is unsupported
512
	 */
576
	 */
513
	public static ISWTObservableValue observeEditable(Control control) {
577
	public static ISWTObservableValue observeEditable(Control control) {
578
		IValueProperty property;
514
		if (control instanceof Text) {
579
		if (control instanceof Text) {
515
			return new TextEditableObservableValue((Text) control);
580
			property = TextProperties.editable();
581
		} else {
582
			throw new IllegalArgumentException(
583
					"Widget [" + control.getClass().getName() + "] is not supported."); //$NON-NLS-1$//$NON-NLS-2$
516
		}
584
		}
517
		
585
518
		throw new IllegalArgumentException(
586
		return observeWidgetProperty(control, property);
519
				"Widget [" + control.getClass().getName() + "] is not supported."); //$NON-NLS-1$//$NON-NLS-2$
520
	}
587
	}
521
588
522
	private static class DisplayRealm extends Realm {
589
	private static class DisplayRealm extends Realm {
(-)src/org/eclipse/jface/internal/databinding/swt/SWTObservableListDecorator.java (+57 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.core.databinding.observable.list.DecoratingObservableList;
15
import org.eclipse.core.databinding.observable.list.IObservableList;
16
import org.eclipse.jface.databinding.swt.ISWTObservable;
17
import org.eclipse.swt.SWT;
18
import org.eclipse.swt.widgets.Event;
19
import org.eclipse.swt.widgets.Listener;
20
import org.eclipse.swt.widgets.Widget;
21
22
/**
23
 * @since 3.3
24
 * 
25
 */
26
public class SWTObservableListDecorator extends DecoratingObservableList
27
		implements ISWTObservable {
28
	private Widget widget;
29
30
	/**
31
	 * @param decorated
32
	 * @param widget
33
	 */
34
	public SWTObservableListDecorator(IObservableList decorated, Widget widget) {
35
		super(decorated, true);
36
		this.widget = widget;
37
		widget.addListener(SWT.Dispose, disposeListener);
38
	}
39
40
	private Listener disposeListener = new Listener() {
41
		public void handleEvent(Event event) {
42
			SWTObservableListDecorator.this.dispose();
43
		}
44
	};
45
46
	public void dispose() {
47
		this.widget = null;
48
		super.dispose();
49
	}
50
51
	/**
52
	 * @return Returns the widget.
53
	 */
54
	public Widget getWidget() {
55
		return widget;
56
	}
57
}
(-)src/org/eclipse/jface/databinding/swt/ToolItemProperties.java (+31 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.databinding.swt;
13
14
import org.eclipse.core.databinding.property.value.IValueProperty;
15
import org.eclipse.jface.internal.databinding.swt.ToolItemTooltipTextProperty;
16
17
/**
18
 * A factory for creating properties of SWT ToolItems
19
 * 
20
 * @since 1.3
21
 */
22
public class ToolItemProperties {
23
	/**
24
	 * Returns a value property for the tooltip text of a SWT ToolItems.
25
	 * 
26
	 * @return a value property for the tooltip text of a SWT ToolItems.
27
	 */
28
	public static IValueProperty tooltipText() {
29
		return new ToolItemTooltipTextProperty();
30
	}
31
}
(-)src/org/eclipse/jface/databinding/swt/ButtonProperties.java (+31 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.databinding.swt;
13
14
import org.eclipse.core.databinding.property.value.IValueProperty;
15
import org.eclipse.jface.internal.databinding.swt.ButtonSelectionProperty;
16
17
/**
18
 * A factory for creating properties of SWT Buttons.
19
 * 
20
 * @since 1.3
21
 */
22
public class ButtonProperties {
23
	/**
24
	 * Returns a value property for the selection state of a SWT Button.
25
	 * 
26
	 * @return a value property for the selection state of a SWT Button.
27
	 */
28
	public static IValueProperty selection() {
29
		return new ButtonSelectionProperty();
30
	}
31
}
(-)src/org/eclipse/jface/internal/databinding/viewers/SelectionProviderMultipleSelectionProperty.java (+97 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.viewers;
13
14
import java.util.Collections;
15
import java.util.List;
16
17
import org.eclipse.core.databinding.observable.list.IObservableList;
18
import org.eclipse.core.databinding.observable.list.ListDiff;
19
import org.eclipse.core.databinding.property.INativePropertyListener;
20
import org.eclipse.core.databinding.property.list.IListPropertyChangeListener;
21
import org.eclipse.core.databinding.property.list.ListPropertyChangeEvent;
22
import org.eclipse.core.databinding.property.list.SimpleListProperty;
23
import org.eclipse.jface.databinding.swt.SWTObservables;
24
import org.eclipse.jface.viewers.ISelection;
25
import org.eclipse.jface.viewers.ISelectionChangedListener;
26
import org.eclipse.jface.viewers.ISelectionProvider;
27
import org.eclipse.jface.viewers.IStructuredSelection;
28
import org.eclipse.jface.viewers.SelectionChangedEvent;
29
import org.eclipse.jface.viewers.StructuredSelection;
30
import org.eclipse.jface.viewers.Viewer;
31
32
/**
33
 * @since 3.3
34
 * 
35
 */
36
public class SelectionProviderMultipleSelectionProperty extends
37
		SimpleListProperty {
38
	/**
39
	 */
40
	public SelectionProviderMultipleSelectionProperty() {
41
		super(Object.class);
42
	}
43
44
	public IObservableList observeList(Object source) {
45
		Viewer viewer = (Viewer) source;
46
		return observeList(SWTObservables.getRealm(viewer.getControl()
47
				.getDisplay()), viewer);
48
	}
49
50
	protected List doGetList(Object source) {
51
		ISelection selection = ((ISelectionProvider) source).getSelection();
52
		if (selection instanceof IStructuredSelection) {
53
			return ((IStructuredSelection) selection).toList();
54
		}
55
		return Collections.EMPTY_LIST;
56
	}
57
58
	protected void setList(Object source, List list, ListDiff diff) {
59
		((ISelectionProvider) source)
60
				.setSelection(new StructuredSelection(list));
61
	}
62
63
	public INativePropertyListener adaptListener(
64
			IListPropertyChangeListener listener) {
65
		return new SelectionChangedListener(listener);
66
	}
67
68
	public void addListener(Object source, INativePropertyListener listener) {
69
		((ISelectionProvider) source)
70
				.addSelectionChangedListener((ISelectionChangedListener) listener);
71
	}
72
73
	public void removeListener(Object source, INativePropertyListener listener) {
74
		((ISelectionProvider) source)
75
				.removeSelectionChangedListener((ISelectionChangedListener) listener);
76
77
	}
78
79
	private class SelectionChangedListener implements INativePropertyListener,
80
			ISelectionChangedListener {
81
		private IListPropertyChangeListener listener;
82
83
		private SelectionChangedListener(IListPropertyChangeListener listener) {
84
			this.listener = listener;
85
		}
86
87
		public void selectionChanged(SelectionChangedEvent event) {
88
			listener.handleListPropertyChange(new ListPropertyChangeEvent(event
89
					.getSource(),
90
					SelectionProviderMultipleSelectionProperty.this, null));
91
		}
92
	}
93
94
	public String toString() {
95
		return "ISelectionProvider.selection[]"; //$NON-NLS-1$
96
	}
97
}
(-)src/org/eclipse/jface/databinding/viewers/CheckboxTableViewerProperties.java (+36 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.databinding.viewers;
13
14
import org.eclipse.core.databinding.property.set.ISetProperty;
15
import org.eclipse.jface.internal.databinding.viewers.CheckboxTableViewerCheckedElementsProperty;
16
17
/**
18
 * A factory for creating properties of JFace CheckboxTableViewer
19
 * 
20
 * @since 1.3
21
 */
22
public class CheckboxTableViewerProperties {
23
	/**
24
	 * Returns a set property for the checked elements of a JFace
25
	 * CheckboxTableViewer.
26
	 * 
27
	 * @param elementType
28
	 *            the element type of the returned property
29
	 * 
30
	 * @return a set property for the checked elements of a JFace
31
	 *         CheckboxTableViewer.
32
	 */
33
	public static ISetProperty checkedElements(Object elementType) {
34
		return new CheckboxTableViewerCheckedElementsProperty(elementType);
35
	}
36
}
(-)src/org/eclipse/jface/databinding/viewers/StructuredViewerProperties.java (+31 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.databinding.viewers;
13
14
import org.eclipse.core.databinding.property.set.ISetProperty;
15
import org.eclipse.jface.internal.databinding.viewers.StructuredViewerFiltersProperty;
16
17
/**
18
 * A factory for creating properties of JFace StructuredViewers
19
 * 
20
 * @since 1.3
21
 */
22
public class StructuredViewerProperties {
23
	/**
24
	 * Returns a value property for the input of a JFace StructuredViewer.
25
	 * 
26
	 * @return a value property for the input of a JFace StructuredViewer.
27
	 */
28
	public static ISetProperty filters() {
29
		return new StructuredViewerFiltersProperty();
30
	}
31
}
(-)src/org/eclipse/jface/databinding/swt/CLabelProperties.java (+31 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.databinding.swt;
13
14
import org.eclipse.core.databinding.property.value.IValueProperty;
15
import org.eclipse.jface.internal.databinding.swt.CLabelTextProperty;
16
17
/**
18
 * A factory for creating properties of SWT Labels.
19
 * 
20
 * @since 1.3
21
 */
22
public class CLabelProperties {
23
	/**
24
	 * Returns a value property for the text of a SWT Label.
25
	 * 
26
	 * @return a value property for the text of a SWT Label.
27
	 */
28
	public static IValueProperty text() {
29
		return new CLabelTextProperty();
30
	}
31
}
(-)src/org/eclipse/jface/internal/databinding/swt/ControlEnabledProperty.java (+32 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.swt.widgets.Control;
15
16
/**
17
 * @since 3.3
18
 * 
19
 */
20
public class ControlEnabledProperty extends WidgetBooleanValueProperty {
21
	public boolean doGetBooleanValue(Object source) {
22
		return ((Control) source).getEnabled();
23
	}
24
25
	void doSetBooleanValue(Object source, boolean value) {
26
		((Control) source).setEnabled(value);
27
	}
28
29
	public String toString() {
30
		return "Control.enabled <boolean>"; //$NON-NLS-1$
31
	}
32
}
(-)src/org/eclipse/jface/internal/databinding/swt/ControlFocusedProperty.java (+42 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation
10
 *     Tom Schindl - initial API and implementation
11
 ******************************************************************************/
12
13
package org.eclipse.jface.internal.databinding.swt;
14
15
import org.eclipse.swt.SWT;
16
import org.eclipse.swt.widgets.Control;
17
18
/**
19
 * @since 3.3
20
 * 
21
 */
22
public class ControlFocusedProperty extends WidgetBooleanValueProperty {
23
	/**
24
	 * 
25
	 */
26
	public ControlFocusedProperty() {
27
		super(new int[] { SWT.FocusIn, SWT.FocusOut });
28
	}
29
30
	public boolean doGetBooleanValue(Object source) {
31
		return ((Control) source).isFocusControl();
32
	}
33
34
	public void doSetBooleanValue(Object source, boolean value) {
35
		if (value)
36
			((Control) source).setFocus();
37
	}
38
39
	public String toString() {
40
		return "Control.focus <boolean>"; //$NON-NLS-1$
41
	}
42
}
(-)src/org/eclipse/jface/internal/databinding/swt/CTabItemTooltipTextProperty.java (+32 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.swt.custom.CTabItem;
15
16
/**
17
 * @since 3.3
18
 * 
19
 */
20
public class CTabItemTooltipTextProperty extends WidgetStringValueProperty {
21
	String doGetStringValue(Object source) {
22
		return ((CTabItem) source).getText();
23
	}
24
25
	void doSetStringValue(Object source, String value) {
26
		((CTabItem) source).setText(value == null ? "" : (String) value); //$NON-NLS-1$
27
	}
28
29
	public String toString() {
30
		return "CTabItem.tooltipText <String>"; //$NON-NLS-1$
31
	}
32
}
(-)src/org/eclipse/jface/databinding/swt/StyledTextProperties.java (+36 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.databinding.swt;
13
14
import org.eclipse.core.databinding.property.value.IValueProperty;
15
import org.eclipse.jface.internal.databinding.swt.StyledTextTextProperty;
16
import org.eclipse.swt.SWT;
17
18
/**
19
 * A factory for creating properties of SWT StyledTexts.
20
 * 
21
 * @since 1.3
22
 */
23
public class StyledTextProperties {
24
	/**
25
	 * Returns a value property for the text of a SWT StyledText.
26
	 * 
27
	 * @param event
28
	 *            the SWT event type to register for change events. May be
29
	 *            {@link SWT#None}, {@link SWT#Modify} or {@link SWT#FocusOut}.
30
	 * 
31
	 * @return a value property for the text of a SWT StyledText.
32
	 */
33
	public static IValueProperty text(int event) {
34
		return new StyledTextTextProperty(event);
35
	}
36
}
(-)src/org/eclipse/jface/internal/databinding/swt/ControlLocationProperty.java (+42 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation
10
 *     Tom Schindl - initial API and implementation
11
 ******************************************************************************/
12
13
package org.eclipse.jface.internal.databinding.swt;
14
15
import org.eclipse.swt.SWT;
16
import org.eclipse.swt.graphics.Point;
17
import org.eclipse.swt.widgets.Control;
18
19
/**
20
 * @since 3.3
21
 * 
22
 */
23
public class ControlLocationProperty extends WidgetValueProperty {
24
	/**
25
	 * 
26
	 */
27
	public ControlLocationProperty() {
28
		super(SWT.Move, Point.class);
29
	}
30
31
	public Object getValue(Object source) {
32
		return ((Control) source).getLocation();
33
	}
34
35
	public void setValue(Object source, Object value) {
36
		((Control) source).setLocation((Point) value);
37
	}
38
39
	public String toString() {
40
		return "Control.location <Point>"; //$NON-NLS-1$
41
	}
42
}
(-)src/org/eclipse/jface/internal/databinding/swt/TreeItemTooltipTextProperty.java (+32 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.swt.widgets.TreeItem;
15
16
/**
17
 * @since 3.3
18
 * 
19
 */
20
public class TreeItemTooltipTextProperty extends WidgetStringValueProperty {
21
	String doGetStringValue(Object source) {
22
		return ((TreeItem) source).getText();
23
	}
24
25
	void doSetStringValue(Object source, String value) {
26
		((TreeItem) source).setText(value == null ? "" : value); //$NON-NLS-1$
27
	}
28
29
	public String toString() {
30
		return "TreeItem.tooltipText <String>"; //$NON-NLS-1$
31
	}
32
}
(-)src/org/eclipse/jface/databinding/swt/ScaleProperties.java (+51 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.databinding.swt;
13
14
import org.eclipse.core.databinding.property.value.IValueProperty;
15
import org.eclipse.jface.internal.databinding.swt.ScaleMaximumProperty;
16
import org.eclipse.jface.internal.databinding.swt.ScaleMinimumProperty;
17
import org.eclipse.jface.internal.databinding.swt.ScaleSelectionProperty;
18
19
/**
20
 * A factory for creating properties of SWT Scales.
21
 * 
22
 * @since 1.3
23
 */
24
public class ScaleProperties {
25
	/**
26
	 * Returns a value property for the selected value of a SWT Scale.
27
	 * 
28
	 * @return a value property for the selected value of a SWT Scale.
29
	 */
30
	public static IValueProperty selection() {
31
		return new ScaleSelectionProperty();
32
	}
33
34
	/**
35
	 * Returns a value property for the minimum value of a SWT Scale.
36
	 * 
37
	 * @return a value property for the minimum value of a SWT Scale.
38
	 */
39
	public static IValueProperty minimum() {
40
		return new ScaleMinimumProperty();
41
	}
42
43
	/**
44
	 * Returns a value property for the maximum value of a SWT Scale.
45
	 * 
46
	 * @return a value property for the maximum value of a SWT Scale.
47
	 */
48
	public static IValueProperty maximum() {
49
		return new ScaleMaximumProperty();
50
	}
51
}
(-)src/org/eclipse/jface/internal/databinding/swt/ButtonSelectionProperty.java (+40 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.swt.SWT;
15
import org.eclipse.swt.widgets.Button;
16
17
/**
18
 * @since 3.3
19
 * 
20
 */
21
public class ButtonSelectionProperty extends WidgetBooleanValueProperty {
22
	/**
23
	 * 
24
	 */
25
	public ButtonSelectionProperty() {
26
		super(SWT.Selection);
27
	}
28
29
	boolean doGetBooleanValue(Object source) {
30
		return ((Button) source).getSelection();
31
	}
32
33
	void doSetBooleanValue(Object source, boolean value) {
34
		((Button) source).setSelection(value);
35
	}
36
37
	public String toString() {
38
		return "Button.selection <Boolean>"; //$NON-NLS-1$
39
	}
40
}
(-)src/org/eclipse/jface/internal/databinding/swt/TabItemTooltipTextProperty.java (+32 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.swt.widgets.TabItem;
15
16
/**
17
 * @since 3.3
18
 * 
19
 */
20
public class TabItemTooltipTextProperty extends WidgetStringValueProperty {
21
	String doGetStringValue(Object source) {
22
		return ((TabItem) source).getText();
23
	}
24
25
	void doSetStringValue(Object source, String value) {
26
		((TabItem) source).setText(value == null ? "" : value); //$NON-NLS-1$
27
	}
28
29
	public String toString() {
30
		return "TabItem.tooltipText <String>"; //$NON-NLS-1$
31
	}
32
}
(-)src/org/eclipse/jface/internal/databinding/swt/ControlFontProperty.java (+40 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.swt.graphics.Font;
15
import org.eclipse.swt.widgets.Control;
16
17
/**
18
 * @since 3.3
19
 * 
20
 */
21
public class ControlFontProperty extends WidgetValueProperty {
22
	/**
23
	 * 
24
	 */
25
	public ControlFontProperty() {
26
		super(Font.class);
27
	}
28
29
	public Object getValue(Object source) {
30
		return ((Control) source).getFont();
31
	}
32
33
	public void setValue(Object source, Object value) {
34
		((Control) source).setFont((Font) value);
35
	}
36
37
	public String toString() {
38
		return "Control.font <Font>"; //$NON-NLS-1$
39
	}
40
}
(-)src/org/eclipse/jface/internal/databinding/swt/ScaleMaximumProperty.java (+32 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.swt.widgets.Scale;
15
16
/**
17
 * @since 3.3
18
 * 
19
 */
20
public class ScaleMaximumProperty extends WidgetIntValueProperty {
21
	int doGetIntValue(Object source) {
22
		return ((Scale) source).getMaximum();
23
	}
24
25
	void doSetIntValue(Object source, int value) {
26
		((Scale) source).setMaximum(value);
27
	}
28
29
	public String toString() {
30
		return "Scale.maximum <int>"; //$NON-NLS-1$
31
	}
32
}
(-)src/org/eclipse/jface/internal/databinding/swt/ListSelectionProperty.java (+55 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.swt.SWT;
15
import org.eclipse.swt.widgets.List;
16
17
/**
18
 * @since 3.3
19
 * 
20
 */
21
public class ListSelectionProperty extends WidgetStringValueProperty {
22
	/**
23
	 * 
24
	 */
25
	public ListSelectionProperty() {
26
		super(SWT.Selection);
27
	}
28
29
	String doGetStringValue(Object source) {
30
		List list = (List) source;
31
		int index = list.getSelectionIndex();
32
		if (index >= 0)
33
			return list.getItem(index);
34
		return null;
35
	}
36
37
	void doSetStringValue(Object source, String value) {
38
		List list = (List) source;
39
		String items[] = list.getItems();
40
		int index = -1;
41
		if (items != null && value != null) {
42
			for (int i = 0; i < items.length; i++) {
43
				if (value.equals(items[i])) {
44
					index = i;
45
					break;
46
				}
47
			}
48
			list.select(index);
49
		}
50
	}
51
52
	public String toString() {
53
		return "List.selection <String>"; //$NON-NLS-1$
54
	}
55
}
(-)src/org/eclipse/jface/internal/databinding/swt/ItemTextProperty.java (+32 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.swt.widgets.Item;
15
16
/**
17
 * @since 3.3
18
 * 
19
 */
20
public class ItemTextProperty extends WidgetStringValueProperty {
21
	String doGetStringValue(Object source) {
22
		return ((Item) source).getText();
23
	}
24
25
	void doSetStringValue(Object source, String value) {
26
		((Item) source).setText(value == null ? "" : value); //$NON-NLS-1$
27
	}
28
29
	public String toString() {
30
		return "Item.text <String>"; //$NON-NLS-1$
31
	}
32
}
(-)src/org/eclipse/jface/databinding/viewers/CheckboxTreeViewerProperties.java (+36 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.databinding.viewers;
13
14
import org.eclipse.core.databinding.property.set.ISetProperty;
15
import org.eclipse.jface.internal.databinding.viewers.CheckboxTreeViewerCheckedElementsProperty;
16
17
/**
18
 * A factory for creating properties of JFace CheckboxTreeViewer
19
 * 
20
 * @since 1.3
21
 */
22
public class CheckboxTreeViewerProperties {
23
	/**
24
	 * Returns a set property for the checked elements of a JFace
25
	 * CheckboxTreeViewer.
26
	 * 
27
	 * @param elementType
28
	 *            the element type of the returned property
29
	 * 
30
	 * @return a set property for the checked elements of a JFace
31
	 *         CheckboxTreeViewer.
32
	 */
33
	public static ISetProperty checkedElements(Object elementType) {
34
		return new CheckboxTreeViewerCheckedElementsProperty(elementType);
35
	}
36
}
(-)src/org/eclipse/jface/internal/databinding/swt/LinkTextProperty.java (+32 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.swt.widgets.Link;
15
16
/**
17
 * @since 3.3
18
 * 
19
 */
20
public class LinkTextProperty extends WidgetStringValueProperty {
21
	String doGetStringValue(Object source) {
22
		return ((Link) source).getText();
23
	}
24
25
	void doSetStringValue(Object source, String value) {
26
		((Link) source).setText(value == null ? "" : value); //$NON-NLS-1$
27
	}
28
29
	public String toString() {
30
		return "Link.text <String>"; //$NON-NLS-1$
31
	}
32
}
(-)src/org/eclipse/jface/databinding/swt/ControlProperties.java (+121 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.databinding.swt;
13
14
import org.eclipse.core.databinding.property.value.IValueProperty;
15
import org.eclipse.jface.internal.databinding.swt.ControlBackgroundProperty;
16
import org.eclipse.jface.internal.databinding.swt.ControlBoundsProperty;
17
import org.eclipse.jface.internal.databinding.swt.ControlEnabledProperty;
18
import org.eclipse.jface.internal.databinding.swt.ControlFocusedProperty;
19
import org.eclipse.jface.internal.databinding.swt.ControlFontProperty;
20
import org.eclipse.jface.internal.databinding.swt.ControlForegroundProperty;
21
import org.eclipse.jface.internal.databinding.swt.ControlLocationProperty;
22
import org.eclipse.jface.internal.databinding.swt.ControlSizeProperty;
23
import org.eclipse.jface.internal.databinding.swt.ControlTooltipTextProperty;
24
import org.eclipse.jface.internal.databinding.swt.ControlVisibleProperty;
25
26
/**
27
 * A factory for creating properties of SWT controls.
28
 * 
29
 * @since 1.3
30
 */
31
public class ControlProperties {
32
	/**
33
	 * Returns a value property for the enablement state of a SWT Control.
34
	 * 
35
	 * @return a value property for the enablement state of a SWT Control.
36
	 */
37
	public static IValueProperty enabled() {
38
		return new ControlEnabledProperty();
39
	}
40
41
	/**
42
	 * Returns a value property for the visibility state of a SWT Control.
43
	 * 
44
	 * @return a value property for the visibility state of a SWT Control.
45
	 */
46
	public static IValueProperty visible() {
47
		return new ControlVisibleProperty();
48
	}
49
50
	/**
51
	 * Returns a value property for the tooltip text of a SWT Control.
52
	 * 
53
	 * @return a value property for the tooltip text of a SWT Control.
54
	 */
55
	public static IValueProperty toolTipText() {
56
		return new ControlTooltipTextProperty();
57
	}
58
59
	/**
60
	 * Returns a value property for the foreground color of a SWT Control.
61
	 * 
62
	 * @return a value property for the foreground color of a SWT Control.
63
	 */
64
	public static IValueProperty foreground() {
65
		return new ControlForegroundProperty();
66
	}
67
68
	/**
69
	 * Returns a value property for the background color of a SWT Control.
70
	 * 
71
	 * @return a value property for the background color of a SWT Control.
72
	 */
73
	public static IValueProperty background() {
74
		return new ControlBackgroundProperty();
75
	}
76
77
	/**
78
	 * Returns a value property for the font of a SWT Control.
79
	 * 
80
	 * @return a value property for the font of a SWT Control.
81
	 */
82
	public static IValueProperty font() {
83
		return new ControlFontProperty();
84
	}
85
86
	/**
87
	 * Returns a value property for the size of a SWT Control.
88
	 * 
89
	 * @return a value property for the size of a SWT Control.
90
	 */
91
	public static IValueProperty size() {
92
		return new ControlSizeProperty();
93
	}
94
95
	/**
96
	 * Returns a value property for the location of a SWT Control.
97
	 * 
98
	 * @return a value property for the location of a SWT Control.
99
	 */
100
	public static IValueProperty location() {
101
		return new ControlLocationProperty();
102
	}
103
104
	/**
105
	 * Returns a value property for the bounds of a SWT Control.
106
	 * 
107
	 * @return a value property for the bounds of a SWT Control.
108
	 */
109
	public static IValueProperty bounds() {
110
		return new ControlBoundsProperty();
111
	}
112
113
	/**
114
	 * Returns a value property for the focus state of a SWT Control.
115
	 * 
116
	 * @return a value property for the focus state of a SWT Control.
117
	 */
118
	public static IValueProperty focused() {
119
		return new ControlFocusedProperty();
120
	}
121
}
(-)src/org/eclipse/jface/internal/databinding/swt/TableColumnTooltipTextProperty.java (+32 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.swt.widgets.TableColumn;
15
16
/**
17
 * @since 3.3
18
 * 
19
 */
20
public class TableColumnTooltipTextProperty extends WidgetStringValueProperty {
21
	String doGetStringValue(Object source) {
22
		return ((TableColumn) source).getText();
23
	}
24
25
	void doSetStringValue(Object source, String value) {
26
		((TableColumn) source).setText(value == null ? "" : value); //$NON-NLS-1$
27
	}
28
29
	public String toString() {
30
		return "TableColumn.tooltipText <String>"; //$NON-NLS-1$
31
	}
32
}
(-)src/org/eclipse/jface/internal/databinding/swt/ControlBackgroundProperty.java (+40 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.swt.graphics.Color;
15
import org.eclipse.swt.widgets.Control;
16
17
/**
18
 * @since 3.3
19
 * 
20
 */
21
public class ControlBackgroundProperty extends WidgetValueProperty {
22
	/**
23
	 * 
24
	 */
25
	public ControlBackgroundProperty() {
26
		super(Color.class);
27
	}
28
29
	public Object getValue(Object source) {
30
		return ((Control) source).getBackground();
31
	}
32
33
	public void setValue(Object source, Object value) {
34
		((Control) source).setBackground((Color) value);
35
	}
36
37
	public String toString() {
38
		return "Control.background <Color>"; //$NON-NLS-1$
39
	}
40
}
(-)src/org/eclipse/jface/internal/databinding/swt/ComboSelectionProperty.java (+55 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.swt.SWT;
15
import org.eclipse.swt.widgets.Combo;
16
17
/**
18
 * @since 3.3
19
 * 
20
 */
21
public class ComboSelectionProperty extends WidgetStringValueProperty {
22
	/**
23
	 * 
24
	 */
25
	public ComboSelectionProperty() {
26
		super(SWT.Modify);
27
	}
28
29
	String doGetStringValue(Object source) {
30
		return ((Combo) source).getText();
31
	}
32
33
	void doSetStringValue(Object source, String value) {
34
		Combo combo = (Combo) source;
35
		String items[] = combo.getItems();
36
		int index = -1;
37
		if (items != null && value != null) {
38
			for (int i = 0; i < items.length; i++) {
39
				if (value.equals(items[i])) {
40
					index = i;
41
					break;
42
				}
43
			}
44
			if (index == -1) {
45
				combo.setText(value);
46
			} else {
47
				combo.select(index); // -1 will not "unselect"
48
			}
49
		}
50
	}
51
52
	public String toString() {
53
		return "Combo.selection <String>"; //$NON-NLS-1$
54
	}
55
}
(-)src/org/eclipse/jface/internal/databinding/viewers/CheckboxTreeViewerCheckedElementsProperty.java (+57 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.viewers;
13
14
import java.util.Arrays;
15
import java.util.Set;
16
17
import org.eclipse.core.databinding.observable.set.SetDiff;
18
import org.eclipse.jface.viewers.CheckboxTreeViewer;
19
import org.eclipse.jface.viewers.ICheckable;
20
21
/**
22
 * @since 3.3
23
 * 
24
 */
25
public class CheckboxTreeViewerCheckedElementsProperty extends
26
		CheckableCheckedElementsProperty {
27
	/**
28
	 * @param elementType
29
	 */
30
	public CheckboxTreeViewerCheckedElementsProperty(Object elementType) {
31
		super(elementType);
32
	}
33
34
	protected Set createElementSet(ICheckable checkable) {
35
		return ViewerElementSet.withComparer(((CheckboxTreeViewer) checkable)
36
				.getComparer());
37
	}
38
39
	protected Set doGetSet(ICheckable checkable) {
40
		CheckboxTreeViewer viewer = (CheckboxTreeViewer) checkable;
41
		Set set = createElementSet(viewer);
42
		set.addAll(Arrays.asList(viewer.getCheckedElements()));
43
		return set;
44
	}
45
46
	protected void doSetSet(Object source, Set set, SetDiff diff) {
47
		CheckboxTreeViewer viewer = (CheckboxTreeViewer) source;
48
		viewer.setCheckedElements(set.toArray());
49
	}
50
51
	public String toString() {
52
		String s = "CheckboxTreeViewer.checkedElements{}"; //$NON-NLS-1$
53
		if (getElementType() != null)
54
			s += " <" + getElementType() + ">"; //$NON-NLS-1$//$NON-NLS-2$
55
		return s;
56
	}
57
}
(-)src/org/eclipse/jface/internal/databinding/swt/ControlStringListProperty.java (+64 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import java.util.Arrays;
15
import java.util.List;
16
17
import org.eclipse.core.databinding.observable.list.IObservableList;
18
import org.eclipse.core.databinding.observable.list.ListDiff;
19
import org.eclipse.core.databinding.property.INativePropertyListener;
20
import org.eclipse.core.databinding.property.list.IListPropertyChangeListener;
21
import org.eclipse.core.databinding.property.list.SimpleListProperty;
22
import org.eclipse.jface.databinding.swt.SWTObservables;
23
import org.eclipse.swt.widgets.Control;
24
import org.eclipse.swt.widgets.Widget;
25
26
/**
27
 * @since 3.3
28
 * 
29
 */
30
public abstract class ControlStringListProperty extends SimpleListProperty {
31
	protected ControlStringListProperty() {
32
		super(String.class);
33
	}
34
35
	public IObservableList observeList(Object source) {
36
		Widget widget = (Widget) source;
37
		return observeList(SWTObservables.getRealm(widget.getDisplay()), widget);
38
	}
39
40
	protected void setList(Object source, List list, ListDiff diff) {
41
		String[] strings = (String[]) list.toArray(new String[list.size()]);
42
		doSetStringList((Control) source, strings);
43
	}
44
45
	abstract void doSetStringList(Control control, String[] list);
46
47
	protected List doGetList(Object source) {
48
		String[] list = doGetStringList((Control) source);
49
		return Arrays.asList(list);
50
	}
51
52
	abstract String[] doGetStringList(Control control);
53
54
	public INativePropertyListener adaptListener(
55
			IListPropertyChangeListener listener) {
56
		return null;
57
	}
58
59
	public void addListener(Object source, INativePropertyListener listener) {
60
	}
61
62
	public void removeListener(Object source, INativePropertyListener listener) {
63
	}
64
}
(-)src/org/eclipse/jface/internal/databinding/swt/CLabelTextProperty.java (+32 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.swt.custom.CLabel;
15
16
/**
17
 * @since 3.3
18
 * 
19
 */
20
public class CLabelTextProperty extends WidgetStringValueProperty {
21
	String doGetStringValue(Object source) {
22
		return ((CLabel) source).getText();
23
	}
24
25
	void doSetStringValue(Object source, String value) {
26
		((CLabel) source).setText(value == null ? "" : value); //$NON-NLS-1$
27
	}
28
29
	public String toString() {
30
		return "CLabel.text <String>"; //$NON-NLS-1$
31
	}
32
}
(-)src/org/eclipse/jface/internal/databinding/viewers/ViewerObservableSetDecorator.java (+40 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.viewers;
13
14
import org.eclipse.core.databinding.observable.set.DecoratingObservableSet;
15
import org.eclipse.core.databinding.observable.set.IObservableSet;
16
import org.eclipse.jface.databinding.viewers.IViewerObservableSet;
17
import org.eclipse.jface.viewers.Viewer;
18
19
/**
20
 * @since 3.3
21
 * 
22
 */
23
public class ViewerObservableSetDecorator extends DecoratingObservableSet
24
		implements IViewerObservableSet {
25
	private final Viewer viewer;
26
27
	/**
28
	 * @param decorated
29
	 * @param viewer
30
	 */
31
	public ViewerObservableSetDecorator(IObservableSet decorated, Viewer viewer) {
32
		super(decorated, true);
33
		this.viewer = viewer;
34
	}
35
36
	public Viewer getViewer() {
37
		return viewer;
38
	}
39
40
}
(-)src/org/eclipse/jface/databinding/swt/SpinnerProperties.java (+51 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.databinding.swt;
13
14
import org.eclipse.core.databinding.property.value.IValueProperty;
15
import org.eclipse.jface.internal.databinding.swt.SpinnerMaximumProperty;
16
import org.eclipse.jface.internal.databinding.swt.SpinnerMinimumProperty;
17
import org.eclipse.jface.internal.databinding.swt.SpinnerSelectionProperty;
18
19
/**
20
 * A factory for creating properties of SWT Spinners.
21
 * 
22
 * @since 1.3
23
 */
24
public class SpinnerProperties {
25
	/**
26
	 * Returns a value property for the selected value of a SWT Spinner.
27
	 * 
28
	 * @return a value property for the selected value of a SWT Spinner.
29
	 */
30
	public static IValueProperty selection() {
31
		return new SpinnerSelectionProperty();
32
	}
33
34
	/**
35
	 * Returns a value property for the minimum value of a SWT Spinner.
36
	 * 
37
	 * @return a value property for the minimum value of a SWT Spinner.
38
	 */
39
	public static IValueProperty minimum() {
40
		return new SpinnerMinimumProperty();
41
	}
42
43
	/**
44
	 * Returns a value property for the maximum value of a SWT Spinner.
45
	 * 
46
	 * @return a value property for the maximum value of a SWT Spinner.
47
	 */
48
	public static IValueProperty maximum() {
49
		return new SpinnerMaximumProperty();
50
	}
51
}
(-)src/org/eclipse/jface/internal/databinding/swt/CComboItemsProperty.java (+33 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.swt.custom.CCombo;
15
import org.eclipse.swt.widgets.Control;
16
17
/**
18
 * @since 3.3
19
 * 
20
 */
21
public class CComboItemsProperty extends ControlStringListProperty {
22
	protected void doSetStringList(Control control, String[] list) {
23
		((CCombo) control).setItems(list);
24
	}
25
26
	public String[] doGetStringList(Control control) {
27
		return ((CCombo) control).getItems();
28
	}
29
30
	public String toString() {
31
		return "CCombo.items[] <String>"; //$NON-NLS-1$
32
	}
33
}
(-)src/org/eclipse/jface/internal/databinding/swt/ComboSingleSelectionIndexProperty.java (+40 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.swt.SWT;
15
import org.eclipse.swt.widgets.Combo;
16
17
/**
18
 * @since 3.3
19
 * 
20
 */
21
public class ComboSingleSelectionIndexProperty extends WidgetIntValueProperty {
22
	/**
23
	 * 
24
	 */
25
	public ComboSingleSelectionIndexProperty() {
26
		super(new int[] { SWT.Selection, SWT.DefaultSelection });
27
	}
28
29
	int doGetIntValue(Object source) {
30
		return ((Combo) source).getSelectionIndex();
31
	}
32
33
	void doSetIntValue(Object source, int value) {
34
		((Combo) source).select(value);
35
	}
36
37
	public String toString() {
38
		return "Combo.selectionIndex <int>"; //$NON-NLS-1$
39
	}
40
}
(-)src/org/eclipse/jface/internal/databinding/swt/ToolItemTooltipTextProperty.java (+32 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.swt.widgets.ToolItem;
15
16
/**
17
 * @since 3.3
18
 * 
19
 */
20
public class ToolItemTooltipTextProperty extends WidgetStringValueProperty {
21
	String doGetStringValue(Object source) {
22
		return ((ToolItem) source).getText();
23
	}
24
25
	void doSetStringValue(Object source, String value) {
26
		((ToolItem) source).setText(value == null ? "" : value); //$NON-NLS-1$
27
	}
28
29
	public String toString() {
30
		return "ToolItem.tooltipText <String>"; //$NON-NLS-1$
31
	}
32
}
(-)src/org/eclipse/jface/internal/databinding/swt/SWTVetoableValueDecorator.java (+141 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.core.databinding.observable.Diffs;
15
import org.eclipse.core.databinding.observable.IDecoratingObservable;
16
import org.eclipse.core.databinding.observable.IObservable;
17
import org.eclipse.core.databinding.observable.IStaleListener;
18
import org.eclipse.core.databinding.observable.ObservableTracker;
19
import org.eclipse.core.databinding.observable.StaleEvent;
20
import org.eclipse.core.databinding.observable.value.AbstractVetoableValue;
21
import org.eclipse.core.databinding.observable.value.IObservableValue;
22
import org.eclipse.core.databinding.observable.value.IValueChangeListener;
23
import org.eclipse.core.databinding.observable.value.ValueChangeEvent;
24
import org.eclipse.core.runtime.Assert;
25
import org.eclipse.jface.databinding.swt.ISWTObservableValue;
26
import org.eclipse.swt.SWT;
27
import org.eclipse.swt.widgets.Event;
28
import org.eclipse.swt.widgets.Listener;
29
import org.eclipse.swt.widgets.Widget;
30
31
/**
32
 * @since 3.3
33
 * 
34
 */
35
public class SWTVetoableValueDecorator extends AbstractVetoableValue implements
36
		ISWTObservableValue, IDecoratingObservable {
37
38
	private IObservableValue decorated;
39
	private Widget widget;
40
41
	private IValueChangeListener valueListener = new IValueChangeListener() {
42
		public void handleValueChange(ValueChangeEvent event) {
43
			fireValueChange(event.diff);
44
		}
45
	};
46
47
	private IStaleListener staleListener = new IStaleListener() {
48
		public void handleStale(StaleEvent staleEvent) {
49
			fireStale();
50
		}
51
	};
52
53
	private Listener verifyListener = new Listener() {
54
		public void handleEvent(Event event) {
55
			String currentText = (String) decorated.getValue();
56
			String newText = currentText.substring(0, event.start) + event.text
57
					+ currentText.substring(event.end);
58
			if (!fireValueChanging(Diffs.createValueDiff(currentText, newText))) {
59
				event.doit = false;
60
			}
61
		}
62
	};
63
64
	private Listener disposeListener = new Listener() {
65
		public void handleEvent(Event event) {
66
			SWTVetoableValueDecorator.this.dispose();
67
		}
68
	};
69
70
	/**
71
	 * @param decorated
72
	 * @param widget
73
	 */
74
	public SWTVetoableValueDecorator(IObservableValue decorated, Widget widget) {
75
		super(decorated.getRealm());
76
		this.decorated = decorated;
77
		this.widget = widget;
78
		Assert
79
				.isTrue(decorated.getValueType().equals(String.class),
80
						"SWTVetoableValueDecorator can only decorate observable values of String type"); //$NON-NLS-1$
81
		widget.addListener(SWT.Dispose, disposeListener);
82
	}
83
84
	private void getterCalled() {
85
		ObservableTracker.getterCalled(this);
86
	}
87
88
	protected void firstListenerAdded() {
89
		decorated.addValueChangeListener(valueListener);
90
		decorated.addStaleListener(staleListener);
91
		widget.addListener(SWT.Verify, verifyListener);
92
	}
93
94
	protected void lastListenerRemoved() {
95
		if (decorated != null) {
96
			decorated.removeValueChangeListener(valueListener);
97
			decorated.removeStaleListener(staleListener);
98
		}
99
		if (widget != null && !widget.isDisposed())
100
			widget.removeListener(SWT.Verify, verifyListener);
101
	}
102
103
	protected void doSetApprovedValue(Object value) {
104
		checkRealm();
105
		decorated.setValue(value);
106
	}
107
108
	protected Object doGetValue() {
109
		getterCalled();
110
		return decorated.getValue();
111
	}
112
113
	public Object getValueType() {
114
		return decorated.getValueType();
115
	}
116
117
	public boolean isStale() {
118
		getterCalled();
119
		return decorated.isStale();
120
	}
121
122
	public void dispose() {
123
		if (decorated != null) {
124
			decorated.dispose();
125
			decorated = null;
126
		}
127
		if (widget != null && !widget.isDisposed()) {
128
			widget.removeListener(SWT.Verify, verifyListener);
129
		}
130
		this.widget = null;
131
		super.dispose();
132
	}
133
134
	public Widget getWidget() {
135
		return widget;
136
	}
137
138
	public IObservable getDecorated() {
139
		return decorated;
140
	}
141
}
(-)src/org/eclipse/jface/databinding/swt/TextProperties.java (+46 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.databinding.swt;
13
14
import org.eclipse.core.databinding.property.value.IValueProperty;
15
import org.eclipse.jface.internal.databinding.swt.TextEditableProperty;
16
import org.eclipse.jface.internal.databinding.swt.TextTextProperty;
17
import org.eclipse.swt.SWT;
18
19
/**
20
 * A factory for creating properties of SWT Texts.
21
 * 
22
 * @since 1.3
23
 */
24
public class TextProperties {
25
	/**
26
	 * Returns a value property for the text of a SWT Text.
27
	 * 
28
	 * @param event
29
	 *            the SWT event type to register for change events. May be
30
	 *            {@link SWT#None}, {@link SWT#Modify} or {@link SWT#FocusOut}.
31
	 * 
32
	 * @return a value property for the text of a SWT Text.
33
	 */
34
	public static IValueProperty text(int event) {
35
		return new TextTextProperty(event);
36
	}
37
38
	/**
39
	 * Returns a value property for the editable state of a SWT Text.
40
	 * 
41
	 * @return a value property for the editable state of a SWT Text.
42
	 */
43
	public static IValueProperty editable() {
44
		return new TextEditableProperty();
45
	}
46
}
(-)src/org/eclipse/jface/databinding/swt/ShellProperties.java (+31 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.databinding.swt;
13
14
import org.eclipse.core.databinding.property.value.IValueProperty;
15
import org.eclipse.jface.internal.databinding.swt.ShellTextProperty;
16
17
/**
18
 * A factory for creating properties of SWT Shells.
19
 * 
20
 * @since 1.3
21
 */
22
public class ShellProperties {
23
	/**
24
	 * Returns a value property for the text of a SWT Shell.
25
	 * 
26
	 * @return a value property for the text of a SWT Shell.
27
	 */
28
	public static IValueProperty text() {
29
		return new ShellTextProperty();
30
	}
31
}
(-)src/org/eclipse/jface/databinding/swt/TabItemProperties.java (+31 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.databinding.swt;
13
14
import org.eclipse.core.databinding.property.value.IValueProperty;
15
import org.eclipse.jface.internal.databinding.swt.TabItemTooltipTextProperty;
16
17
/**
18
 * A factory for creating properties of SWT TabItems
19
 * 
20
 * @since 1.3
21
 */
22
public class TabItemProperties {
23
	/**
24
	 * Returns a value property for the tooltip text of a SWT TabItem.
25
	 * 
26
	 * @return a value property for the tooltip text of a SWT TabItem.
27
	 */
28
	public static IValueProperty tooltipText() {
29
		return new TabItemTooltipTextProperty();
30
	}
31
}
(-)src/org/eclipse/jface/databinding/swt/LinkProperties.java (+31 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.databinding.swt;
13
14
import org.eclipse.core.databinding.property.value.IValueProperty;
15
import org.eclipse.jface.internal.databinding.swt.LinkTextProperty;
16
17
/**
18
 * A factory for creating properties of SWT Links.
19
 * 
20
 * @since 1.3
21
 */
22
public class LinkProperties {
23
	/**
24
	 * Returns a value property for the text of a SWT Link.
25
	 * 
26
	 * @return a value property for the text of a SWT Link.
27
	 */
28
	public static IValueProperty text() {
29
		return new LinkTextProperty();
30
	}
31
}
(-)src/org/eclipse/jface/internal/databinding/swt/WidgetBooleanValueProperty.java (+44 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
/**
15
 * @since 3.3
16
 * 
17
 */
18
public abstract class WidgetBooleanValueProperty extends WidgetValueProperty {
19
	WidgetBooleanValueProperty(int[] events) {
20
		super(events, Boolean.TYPE);
21
	}
22
23
	WidgetBooleanValueProperty(int event) {
24
		super(event, Boolean.TYPE);
25
	}
26
27
	WidgetBooleanValueProperty() {
28
		super(Boolean.TYPE);
29
	}
30
31
	public Object getValue(Object source) {
32
		return doGetBooleanValue(source) ? Boolean.TRUE : Boolean.FALSE;
33
	}
34
35
	public void setValue(Object source, Object value) {
36
		if (value == null)
37
			value = Boolean.FALSE;
38
		doSetBooleanValue(source, ((Boolean) value).booleanValue());
39
	}
40
41
	abstract boolean doGetBooleanValue(Object source);
42
43
	abstract void doSetBooleanValue(Object source, boolean value);
44
}
(-)src/org/eclipse/jface/internal/databinding/viewers/CheckableCheckedElementsProperty.java (+123 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.viewers;
13
14
import java.util.Collections;
15
import java.util.HashSet;
16
import java.util.Iterator;
17
import java.util.Set;
18
19
import org.eclipse.core.databinding.observable.Diffs;
20
import org.eclipse.core.databinding.observable.set.IObservableSet;
21
import org.eclipse.core.databinding.observable.set.SetDiff;
22
import org.eclipse.core.databinding.property.INativePropertyListener;
23
import org.eclipse.core.databinding.property.set.ISetPropertyChangeListener;
24
import org.eclipse.core.databinding.property.set.SetPropertyChangeEvent;
25
import org.eclipse.core.databinding.property.set.SimpleSetProperty;
26
import org.eclipse.jface.databinding.swt.SWTObservables;
27
import org.eclipse.jface.viewers.CheckStateChangedEvent;
28
import org.eclipse.jface.viewers.ICheckStateListener;
29
import org.eclipse.jface.viewers.ICheckable;
30
import org.eclipse.jface.viewers.Viewer;
31
32
/**
33
 * @since 3.3
34
 * 
35
 */
36
public class CheckableCheckedElementsProperty extends SimpleSetProperty {
37
	/**
38
	 * @param elementType
39
	 */
40
	public CheckableCheckedElementsProperty(Object elementType) {
41
		super(elementType);
42
	}
43
44
	public IObservableSet observeSet(Object source) {
45
		Viewer viewer = (Viewer) source;
46
		return observeSet(SWTObservables.getRealm(viewer.getControl()
47
				.getDisplay()), viewer);
48
	}
49
50
	protected Set doGetSet(Object source) {
51
		ICheckable checkable = (ICheckable) source;
52
53
		Set set = doGetSet(checkable);
54
		if (set == null) {
55
			set = createElementSet(checkable);
56
		}
57
58
		return set;
59
	}
60
61
	protected Set doGetSet(ICheckable checkable) {
62
		return null; // overridden by viewer-specific subclasses
63
	}
64
65
	protected Set createElementSet(ICheckable checkable) {
66
		return new HashSet();
67
	}
68
69
	protected void setSet(Object source, Set set, SetDiff diff) {
70
		ICheckable checkable = (ICheckable) source;
71
		for (Iterator it = diff.getAdditions().iterator(); it.hasNext();) {
72
			checkable.setChecked(it.next(), true);
73
		}
74
		for (Iterator it = diff.getRemovals().iterator(); it.hasNext();) {
75
			checkable.setChecked(it.next(), false);
76
		}
77
	}
78
79
	public INativePropertyListener adaptListener(
80
			ISetPropertyChangeListener listener) {
81
		return new CheckStateListener(listener);
82
	}
83
84
	public void addListener(Object source, INativePropertyListener listener) {
85
		((ICheckable) source)
86
				.addCheckStateListener((ICheckStateListener) listener);
87
	}
88
89
	public void removeListener(Object source, INativePropertyListener listener) {
90
		((ICheckable) source)
91
				.removeCheckStateListener((ICheckStateListener) listener);
92
	}
93
94
	private class CheckStateListener implements INativePropertyListener,
95
			ICheckStateListener {
96
		private ISetPropertyChangeListener listener;
97
98
		private CheckStateListener(ISetPropertyChangeListener listener) {
99
			this.listener = listener;
100
		}
101
102
		public void checkStateChanged(CheckStateChangedEvent event) {
103
			Object element = event.getElement();
104
			SetDiff diff;
105
			if (event.getChecked()) {
106
				diff = Diffs.createSetDiff(Collections.singleton(element),
107
						Collections.EMPTY_SET);
108
			} else {
109
				diff = Diffs.createSetDiff(Collections.EMPTY_SET, Collections
110
						.singleton(element));
111
			}
112
			listener.handleSetPropertyChange(new SetPropertyChangeEvent(event
113
					.getSource(), CheckableCheckedElementsProperty.this, diff));
114
		}
115
	}
116
117
	public String toString() {
118
		String s = "ICheckable.checkedElements{}"; //$NON-NLS-1$
119
		if (getElementType() != null)
120
			s += " <" + getElementType() + ">"; //$NON-NLS-1$//$NON-NLS-2$
121
		return s;
122
	}
123
}
(-)src/org/eclipse/jface/internal/databinding/swt/WidgetIntValueProperty.java (+42 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
/**
15
 * @since 3.3
16
 * 
17
 */
18
public abstract class WidgetIntValueProperty extends WidgetValueProperty {
19
	WidgetIntValueProperty() {
20
		super(Integer.TYPE);
21
	}
22
23
	WidgetIntValueProperty(int event) {
24
		super(event, Integer.TYPE);
25
	}
26
27
	WidgetIntValueProperty(int[] events) {
28
		super(events, Integer.TYPE);
29
	}
30
31
	public Object getValue(Object source) {
32
		return new Integer(doGetIntValue(source));
33
	}
34
35
	public void setValue(Object source, Object value) {
36
		doSetIntValue(source, ((Integer) value).intValue());
37
	}
38
39
	abstract int doGetIntValue(Object source);
40
41
	abstract void doSetIntValue(Object source, int intValue);
42
}
(-)src/org/eclipse/jface/internal/databinding/swt/ControlSizeProperty.java (+42 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation
10
 *     Tom Schindl - initial API and implementation
11
 ******************************************************************************/
12
13
package org.eclipse.jface.internal.databinding.swt;
14
15
import org.eclipse.swt.SWT;
16
import org.eclipse.swt.graphics.Point;
17
import org.eclipse.swt.widgets.Control;
18
19
/**
20
 * @since 3.3
21
 * 
22
 */
23
public class ControlSizeProperty extends WidgetValueProperty {
24
	/**
25
	 * 
26
	 */
27
	public ControlSizeProperty() {
28
		super(SWT.Resize, Point.class);
29
	}
30
31
	public Object getValue(Object source) {
32
		return ((Control) source).getSize();
33
	}
34
35
	public void setValue(Object source, Object value) {
36
		((Control) source).setSize((Point) value);
37
	}
38
39
	public String toString() {
40
		return "Control.size <Point>"; //$NON-NLS-1$
41
	}
42
}
(-)src/org/eclipse/jface/databinding/swt/CComboProperties.java (+62 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.databinding.swt;
13
14
import org.eclipse.core.databinding.property.list.IListProperty;
15
import org.eclipse.core.databinding.property.value.IValueProperty;
16
import org.eclipse.jface.internal.databinding.swt.CComboItemsProperty;
17
import org.eclipse.jface.internal.databinding.swt.CComboSelectionProperty;
18
import org.eclipse.jface.internal.databinding.swt.CComboSingleSelectionIndexProperty;
19
import org.eclipse.jface.internal.databinding.swt.CComboTextProperty;
20
21
/**
22
 * A factory for creating properties of SWT CCombos
23
 * 
24
 * @since 1.3
25
 */
26
public class CComboProperties {
27
	/**
28
	 * Returns a value property for the selection text of a SWT CCombo.
29
	 * 
30
	 * @return a value property for the selection text of a SWT CCombo.
31
	 */
32
	public static IValueProperty selection() {
33
		return new CComboSelectionProperty();
34
	}
35
36
	/**
37
	 * Returns a value property for the text of a SWT CCombo.
38
	 * 
39
	 * @return a value property for the text of a SWT CCombo.
40
	 */
41
	public static IValueProperty text() {
42
		return new CComboTextProperty();
43
	}
44
45
	/**
46
	 * Returns a list property for the items of a SWT CCombo.
47
	 * 
48
	 * @return a list property for the items of a SWT CCombo.
49
	 */
50
	public static IListProperty items() {
51
		return new CComboItemsProperty();
52
	}
53
54
	/**
55
	 * Returns a value property for the single selection index of a SWT Combo.
56
	 * 
57
	 * @return a value property for the single selection index of a SWT Combo.
58
	 */
59
	public static IValueProperty singleSelectionIndex() {
60
		return new CComboSingleSelectionIndexProperty();
61
	}
62
}
(-)src/org/eclipse/jface/internal/databinding/viewers/CheckboxTableViewerCheckedElementsProperty.java (+57 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.viewers;
13
14
import java.util.Arrays;
15
import java.util.Set;
16
17
import org.eclipse.core.databinding.observable.set.SetDiff;
18
import org.eclipse.jface.viewers.CheckboxTableViewer;
19
import org.eclipse.jface.viewers.ICheckable;
20
21
/**
22
 * @since 3.3
23
 * 
24
 */
25
public class CheckboxTableViewerCheckedElementsProperty extends
26
		CheckableCheckedElementsProperty {
27
	/**
28
	 * @param elementType
29
	 */
30
	public CheckboxTableViewerCheckedElementsProperty(Object elementType) {
31
		super(elementType);
32
	}
33
34
	protected Set createElementSet(ICheckable checkable) {
35
		return ViewerElementSet.withComparer(((CheckboxTableViewer) checkable)
36
				.getComparer());
37
	}
38
39
	protected Set doGetSet(ICheckable checkable) {
40
		CheckboxTableViewer viewer = (CheckboxTableViewer) checkable;
41
		Set set = createElementSet(viewer);
42
		set.addAll(Arrays.asList(viewer.getCheckedElements()));
43
		return set;
44
	}
45
46
	protected void doSetSet(Object source, Set set, SetDiff diff) {
47
		CheckboxTableViewer viewer = (CheckboxTableViewer) source;
48
		viewer.setCheckedElements(set.toArray());
49
	}
50
51
	public String toString() {
52
		String s = "CheckboxTableViewer.checkedElements{}"; //$NON-NLS-1$
53
		if (getElementType() != null)
54
			s += " <" + getElementType() + ">"; //$NON-NLS-1$//$NON-NLS-2$
55
		return s;
56
	}
57
}
(-)src/org/eclipse/jface/internal/databinding/swt/ControlVisibleProperty.java (+32 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.swt.widgets.Control;
15
16
/**
17
 * @since 3.3
18
 * 
19
 */
20
public class ControlVisibleProperty extends WidgetBooleanValueProperty {
21
	boolean doGetBooleanValue(Object source) {
22
		return ((Control) source).getVisible();
23
	}
24
25
	void doSetBooleanValue(Object source, boolean value) {
26
		((Control) source).setVisible(value);
27
	}
28
29
	public String toString() {
30
		return "Control.visible <boolean>"; //$NON-NLS-1$
31
	}
32
}
(-)src/org/eclipse/jface/internal/databinding/swt/ControlTooltipTextProperty.java (+32 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.swt.widgets.Control;
15
16
/**
17
 * @since 3.3
18
 * 
19
 */
20
public class ControlTooltipTextProperty extends WidgetStringValueProperty {
21
	String doGetStringValue(Object source) {
22
		return ((Control) source).getToolTipText();
23
	}
24
25
	void doSetStringValue(Object source, String value) {
26
		((Control) source).setToolTipText(value);
27
	}
28
29
	public String toString() {
30
		return "Control.tooltipText <String>"; //$NON-NLS-1$
31
	}
32
}
(-)src/org/eclipse/jface/databinding/viewers/ViewerProperties.java (+31 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.databinding.viewers;
13
14
import org.eclipse.core.databinding.property.value.IValueProperty;
15
import org.eclipse.jface.internal.databinding.viewers.ViewerInputProperty;
16
17
/**
18
 * A factory for creating properties of JFace Viewers
19
 * 
20
 * @since 1.3
21
 */
22
public class ViewerProperties {
23
	/**
24
	 * Returns a value property for the input of a JFace Viewer.
25
	 * 
26
	 * @return a value property for the input of a JFace Viewer.
27
	 */
28
	public static IValueProperty input() {
29
		return new ViewerInputProperty();
30
	}
31
}
(-)src/org/eclipse/jface/databinding/swt/TreeColumnProperties.java (+31 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.databinding.swt;
13
14
import org.eclipse.core.databinding.property.value.IValueProperty;
15
import org.eclipse.jface.internal.databinding.swt.TreeItemTooltipTextProperty;
16
17
/**
18
 * A factory for creating properties of SWT TabItems
19
 * 
20
 * @since 1.3
21
 */
22
public class TreeColumnProperties {
23
	/**
24
	 * Returns a value property for the tooltip text of a SWT TreeColumn.
25
	 * 
26
	 * @return a value property for the tooltip text of a SWT TreeColumn.
27
	 */
28
	public static IValueProperty tooltipText() {
29
		return new TreeItemTooltipTextProperty();
30
	}
31
}
(-)src/org/eclipse/jface/databinding/swt/CTabItemProperties.java (+31 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.databinding.swt;
13
14
import org.eclipse.core.databinding.property.value.IValueProperty;
15
import org.eclipse.jface.internal.databinding.swt.CTabItemTooltipTextProperty;
16
17
/**
18
 * A factory for creating properties of SWT CTabItems
19
 * 
20
 * @since 1.3
21
 */
22
public class CTabItemProperties {
23
	/**
24
	 * Returns a value property for the tooltip text of a SWT CTabItem.
25
	 * 
26
	 * @return a value property for the tooltip text of a SWT CTabItem.
27
	 */
28
	public static IValueProperty tooltipText() {
29
		return new CTabItemTooltipTextProperty();
30
	}
31
}
(-)src/org/eclipse/jface/internal/databinding/swt/ListSingleSelectionIndexProperty.java (+40 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.swt.SWT;
15
import org.eclipse.swt.widgets.List;
16
17
/**
18
 * @since 3.3
19
 * 
20
 */
21
public class ListSingleSelectionIndexProperty extends WidgetIntValueProperty {
22
	/**
23
	 * 
24
	 */
25
	public ListSingleSelectionIndexProperty() {
26
		super(new int[] { SWT.Selection, SWT.DefaultSelection });
27
	}
28
29
	int doGetIntValue(Object source) {
30
		return ((List) source).getSelectionIndex();
31
	}
32
33
	void doSetIntValue(Object source, int value) {
34
		((List) source).setSelection(value);
35
	}
36
37
	public String toString() {
38
		return "List.selectionIndex <int>"; //$NON-NLS-1$
39
	}
40
}
(-)src/org/eclipse/jface/internal/databinding/swt/CComboSelectionProperty.java (+57 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.swt.SWT;
15
import org.eclipse.swt.custom.CCombo;
16
17
/**
18
 * @since 3.3
19
 * 
20
 */
21
public class CComboSelectionProperty extends WidgetStringValueProperty {
22
	/**
23
	 * 
24
	 */
25
	public CComboSelectionProperty() {
26
		super(SWT.Modify);
27
	}
28
29
	String doGetStringValue(Object source) {
30
		return ((CCombo) source).getText();
31
	}
32
33
	void doSetStringValue(Object source, String value) {
34
		CCombo ccombo = (CCombo) source;
35
		String items[] = ccombo.getItems();
36
		int index = -1;
37
		if (value == null) {
38
			ccombo.select(-1);
39
		} else if (items != null) {
40
			for (int i = 0; i < items.length; i++) {
41
				if (value.equals(items[i])) {
42
					index = i;
43
					break;
44
				}
45
			}
46
			if (index == -1) {
47
				ccombo.setText(value);
48
			} else {
49
				ccombo.select(index); // -1 will not "unselect"
50
			}
51
		}
52
	}
53
54
	public String toString() {
55
		return "CCombo.selection <String>"; //$NON-NLS-1$
56
	}
57
}
(-)src/org/eclipse/jface/databinding/swt/TableProperties.java (+31 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.databinding.swt;
13
14
import org.eclipse.core.databinding.property.value.IValueProperty;
15
import org.eclipse.jface.internal.databinding.swt.TableSingleSelectionIndexProperty;
16
17
/**
18
 * A factory for creating properties of SWT Tables.
19
 * 
20
 * @since 1.3
21
 */
22
public class TableProperties {
23
	/**
24
	 * Returns a value property for the single selection index of a SWT Table.
25
	 * 
26
	 * @return a value property for the single selection index of a SWT Table.
27
	 */
28
	public static IValueProperty singleSelectionIndex() {
29
		return new TableSingleSelectionIndexProperty();
30
	}
31
}
(-)src/org/eclipse/jface/internal/databinding/swt/SpinnerSelectionProperty.java (+40 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.swt.SWT;
15
import org.eclipse.swt.widgets.Spinner;
16
17
/**
18
 * @since 3.3
19
 * 
20
 */
21
public class SpinnerSelectionProperty extends WidgetIntValueProperty {
22
	/**
23
	 * 
24
	 */
25
	public SpinnerSelectionProperty() {
26
		super(SWT.Modify);
27
	}
28
29
	int doGetIntValue(Object source) {
30
		return ((Spinner) source).getSelection();
31
	}
32
33
	void doSetIntValue(Object source, int value) {
34
		((Spinner) source).setSelection(value);
35
	}
36
37
	public String toString() {
38
		return "Spinner.selection <int>"; //$NON-NLS-1$
39
	}
40
}
(-)src/org/eclipse/jface/internal/databinding/swt/ControlBoundsProperty.java (+42 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation
10
 *     Tom Schindl - initial API and implementation
11
 ******************************************************************************/
12
13
package org.eclipse.jface.internal.databinding.swt;
14
15
import org.eclipse.swt.SWT;
16
import org.eclipse.swt.graphics.Rectangle;
17
import org.eclipse.swt.widgets.Control;
18
19
/**
20
 * @since 3.3
21
 * 
22
 */
23
public class ControlBoundsProperty extends WidgetValueProperty {
24
	/**
25
	 * 
26
	 */
27
	public ControlBoundsProperty() {
28
		super(new int[] { SWT.Resize, SWT.Move }, Rectangle.class);
29
	}
30
31
	public Object getValue(Object source) {
32
		return ((Control) source).getBounds();
33
	}
34
35
	public void setValue(Object source, Object value) {
36
		((Control) source).setBounds((Rectangle) value);
37
	}
38
39
	public String toString() {
40
		return "Control.bounds <Rectangle>"; //$NON-NLS-1$
41
	}
42
}
(-)src/org/eclipse/jface/databinding/swt/ComboProperties.java (+62 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.databinding.swt;
13
14
import org.eclipse.core.databinding.property.list.IListProperty;
15
import org.eclipse.core.databinding.property.value.IValueProperty;
16
import org.eclipse.jface.internal.databinding.swt.ComboItemsProperty;
17
import org.eclipse.jface.internal.databinding.swt.ComboSelectionProperty;
18
import org.eclipse.jface.internal.databinding.swt.ComboSingleSelectionIndexProperty;
19
import org.eclipse.jface.internal.databinding.swt.ComboTextProperty;
20
21
/**
22
 * A factory for creating properties of SWT Combos.
23
 * 
24
 * @since 1.3
25
 */
26
public class ComboProperties {
27
	/**
28
	 * Returns a value property for the selection text of a SWT Combo.
29
	 * 
30
	 * @return a value property for the selection text of a SWT Combo.
31
	 */
32
	public static IValueProperty selection() {
33
		return new ComboSelectionProperty();
34
	}
35
36
	/**
37
	 * Returns a value property for the text of a SWT Combo.
38
	 * 
39
	 * @return a value property for the text of a SWT Combo.
40
	 */
41
	public static IValueProperty text() {
42
		return new ComboTextProperty();
43
	}
44
45
	/**
46
	 * Returns a list property for the items of a SWT Combo.
47
	 * 
48
	 * @return a list property for the items of a SWT Combo.
49
	 */
50
	public static IListProperty items() {
51
		return new ComboItemsProperty();
52
	}
53
54
	/**
55
	 * Returns a value property for the single selection index of a SWT Combo.
56
	 * 
57
	 * @return a value property for the single selection index of a SWT Combo.
58
	 */
59
	public static IValueProperty singleSelectionIndex() {
60
		return new ComboSingleSelectionIndexProperty();
61
	}
62
}
(-)src/org/eclipse/jface/databinding/viewers/CheckableProperties.java (+34 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.databinding.viewers;
13
14
import org.eclipse.core.databinding.property.set.ISetProperty;
15
import org.eclipse.jface.internal.databinding.viewers.CheckableCheckedElementsProperty;
16
17
/**
18
 * A factory for creating properties of JFace ICheckables
19
 * 
20
 * @since 1.3
21
 */
22
public class CheckableProperties {
23
	/**
24
	 * Returns a set property for the checked elements of a JFace ICheckable.
25
	 * 
26
	 * @param elementType
27
	 *            the element type of the returned property
28
	 * 
29
	 * @return a set property for the checked elements of a JFace ICheckable.
30
	 */
31
	public static ISetProperty checkedElements(Object elementType) {
32
		return new CheckableCheckedElementsProperty(elementType);
33
	}
34
}
(-)src/org/eclipse/jface/internal/databinding/swt/ComboTextProperty.java (+40 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.swt.SWT;
15
import org.eclipse.swt.widgets.Combo;
16
17
/**
18
 * @since 3.3
19
 * 
20
 */
21
public class ComboTextProperty extends WidgetStringValueProperty {
22
	/**
23
	 * 
24
	 */
25
	public ComboTextProperty() {
26
		super(SWT.Modify);
27
	}
28
29
	String doGetStringValue(Object source) {
30
		return ((Combo) source).getText();
31
	}
32
33
	void doSetStringValue(Object source, String value) {
34
		((Combo) source).setText(value != null ? value : ""); //$NON-NLS-1$
35
	}
36
37
	public String toString() {
38
		return "Combo.text <String>"; //$NON-NLS-1$
39
	}
40
}
(-)src/org/eclipse/jface/internal/databinding/swt/StyledTextTextProperty.java (+52 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.swt.SWT;
15
import org.eclipse.swt.custom.StyledText;
16
17
/**
18
 * @since 3.3
19
 * 
20
 */
21
public class StyledTextTextProperty extends WidgetStringValueProperty {
22
	/**
23
	 * @param event
24
	 */
25
	public StyledTextTextProperty(int event) {
26
		super(checkEvent(event));
27
	}
28
29
	private static int checkEvent(int event) {
30
		switch (event) {
31
		case SWT.None:
32
		case SWT.Modify:
33
		case SWT.FocusOut:
34
			return event;
35
		default:
36
			throw new IllegalArgumentException("UpdateEventType [" //$NON-NLS-1$
37
					+ event + "] is not supported."); //$NON-NLS-1$
38
		}
39
	}
40
41
	String doGetStringValue(Object source) {
42
		return ((StyledText) source).getText();
43
	}
44
45
	void doSetStringValue(Object source, String value) {
46
		((StyledText) source).setText(value == null ? "" : value); //$NON-NLS-1$
47
	}
48
49
	public String toString() {
50
		return "StyledText.text <String>"; //$NON-NLS-1$
51
	}
52
}
(-)src/org/eclipse/jface/internal/databinding/swt/LabelTextProperty.java (+32 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.swt.widgets.Label;
15
16
/**
17
 * @since 3.3
18
 * 
19
 */
20
public class LabelTextProperty extends WidgetStringValueProperty {
21
	String doGetStringValue(Object source) {
22
		return ((Label) source).getText();
23
	}
24
25
	void doSetStringValue(Object source, String value) {
26
		((Label) source).setText(value == null ? "" : value); //$NON-NLS-1$
27
	}
28
29
	public String toString() {
30
		return "Label.text <String>"; //$NON-NLS-1$
31
	}
32
}
(-)src/org/eclipse/jface/databinding/swt/LabelProperties.java (+31 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.databinding.swt;
13
14
import org.eclipse.core.databinding.property.value.IValueProperty;
15
import org.eclipse.jface.internal.databinding.swt.LabelTextProperty;
16
17
/**
18
 * A factory for creating properties of SWT Labels.
19
 * 
20
 * @since 1.3
21
 */
22
public class LabelProperties {
23
	/**
24
	 * Returns a value property for the text of a SWT Label.
25
	 * 
26
	 * @return a value property for the text of a SWT Label.
27
	 */
28
	public static IValueProperty text() {
29
		return new LabelTextProperty();
30
	}
31
}
(-)src/org/eclipse/jface/internal/databinding/swt/TextTextProperty.java (+52 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.swt.SWT;
15
import org.eclipse.swt.widgets.Text;
16
17
/**
18
 * @since 3.3
19
 * 
20
 */
21
public class TextTextProperty extends WidgetStringValueProperty {
22
	/**
23
	 * @param event
24
	 */
25
	public TextTextProperty(int event) {
26
		super(checkEvent(event));
27
	}
28
29
	private static int checkEvent(int event) {
30
		switch (event) {
31
		case SWT.None:
32
		case SWT.Modify:
33
		case SWT.FocusOut:
34
			return event;
35
		default:
36
			throw new IllegalArgumentException("UpdateEventType [" //$NON-NLS-1$
37
					+ event + "] is not supported."); //$NON-NLS-1$
38
		}
39
	}
40
41
	String doGetStringValue(Object source) {
42
		return ((Text) source).getText();
43
	}
44
45
	void doSetStringValue(Object source, String value) {
46
		((Text) source).setText(value == null ? "" : value); //$NON-NLS-1$
47
	}
48
49
	public String toString() {
50
		return "Text.text <String>"; //$NON-NLS-1$
51
	}
52
}
(-)src/org/eclipse/jface/internal/databinding/swt/SpinnerMaximumProperty.java (+32 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.swt.widgets.Spinner;
15
16
/**
17
 * @since 3.3
18
 * 
19
 */
20
public class SpinnerMaximumProperty extends WidgetIntValueProperty {
21
	int doGetIntValue(Object source) {
22
		return ((Spinner) source).getMaximum();
23
	}
24
25
	void doSetIntValue(Object source, int value) {
26
		((Spinner) source).setMaximum(value);
27
	}
28
29
	public String toString() {
30
		return "Spinner.maximum <int>"; //$NON-NLS-1$
31
	}
32
}
(-)src/org/eclipse/jface/internal/databinding/viewers/ViewerObservableListDecorator.java (+41 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.viewers;
13
14
import org.eclipse.core.databinding.observable.list.DecoratingObservableList;
15
import org.eclipse.core.databinding.observable.list.IObservableList;
16
import org.eclipse.jface.databinding.viewers.IViewerObservableList;
17
import org.eclipse.jface.viewers.Viewer;
18
19
/**
20
 * @since 3.3
21
 * 
22
 */
23
public class ViewerObservableListDecorator extends DecoratingObservableList
24
		implements IViewerObservableList {
25
	private final Viewer viewer;
26
27
	/**
28
	 * @param decorated
29
	 * @param viewer
30
	 */
31
	public ViewerObservableListDecorator(IObservableList decorated,
32
			Viewer viewer) {
33
		super(decorated, true);
34
		this.viewer = viewer;
35
	}
36
37
	public Viewer getViewer() {
38
		return viewer;
39
	}
40
41
}
(-)src/org/eclipse/jface/databinding/swt/ListProperties.java (+52 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.databinding.swt;
13
14
import org.eclipse.core.databinding.property.list.IListProperty;
15
import org.eclipse.core.databinding.property.value.IValueProperty;
16
import org.eclipse.jface.internal.databinding.swt.ListItemsProperty;
17
import org.eclipse.jface.internal.databinding.swt.ListSelectionProperty;
18
import org.eclipse.jface.internal.databinding.swt.ListSingleSelectionIndexProperty;
19
20
/**
21
 * A factory for creating properties of SWT List controls.
22
 * 
23
 * @since 1.3
24
 */
25
public class ListProperties {
26
	/**
27
	 * Returns a value property for observing the selection text of a SWT List.
28
	 * 
29
	 * @return a value property for observing the selection text of a SWT List.
30
	 */
31
	public static IValueProperty selection() {
32
		return new ListSelectionProperty();
33
	}
34
35
	/**
36
	 * Returns a list property for observing the items in a SWT List.
37
	 * 
38
	 * @return a list property for observing the items in a SWT List.
39
	 */
40
	public static IListProperty items() {
41
		return new ListItemsProperty();
42
	}
43
44
	/**
45
	 * Returns a value property for the single selection index of a SWT List.
46
	 * 
47
	 * @return a value property for the single selection index of a SWT List.
48
	 */
49
	public static IValueProperty singleSelectionIndex() {
50
		return new ListSingleSelectionIndexProperty();
51
	}
52
}
(-)src/org/eclipse/jface/internal/databinding/viewers/ViewerInputProperty.java (+61 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.viewers;
13
14
import org.eclipse.core.databinding.observable.value.IObservableValue;
15
import org.eclipse.core.databinding.property.INativePropertyListener;
16
import org.eclipse.core.databinding.property.value.IValuePropertyChangeListener;
17
import org.eclipse.core.databinding.property.value.SimpleValueProperty;
18
import org.eclipse.jface.databinding.swt.SWTObservables;
19
import org.eclipse.jface.viewers.Viewer;
20
21
/**
22
 * @since 3.3
23
 * 
24
 */
25
public class ViewerInputProperty extends SimpleValueProperty {
26
	/**
27
	 * 
28
	 */
29
	public ViewerInputProperty() {
30
		super(null);
31
	}
32
33
	public IObservableValue observeValue(Object source) {
34
		Viewer viewer = (Viewer) source;
35
		return observeValue(SWTObservables.getRealm(viewer.getControl()
36
				.getDisplay()), viewer);
37
	}
38
39
	public Object getValue(Object source) {
40
		return ((Viewer) source).getInput();
41
	}
42
43
	public void setValue(Object source, Object value) {
44
		((Viewer) source).setInput(value);
45
	}
46
47
	public INativePropertyListener adaptListener(
48
			IValuePropertyChangeListener listener) {
49
		return null;
50
	}
51
52
	public void addListener(Object source, INativePropertyListener listener) {
53
	}
54
55
	public void removeListener(Object source, INativePropertyListener listener) {
56
	}
57
58
	public String toString() {
59
		return "Viewer.input"; //$NON-NLS-1$
60
	}
61
}
(-)src/org/eclipse/jface/internal/databinding/viewers/SelectionProviderSingleSelectionProperty.java (+95 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.viewers;
13
14
import org.eclipse.core.databinding.observable.value.IObservableValue;
15
import org.eclipse.core.databinding.property.INativePropertyListener;
16
import org.eclipse.core.databinding.property.value.IValuePropertyChangeListener;
17
import org.eclipse.core.databinding.property.value.SimpleValueProperty;
18
import org.eclipse.core.databinding.property.value.ValuePropertyChangeEvent;
19
import org.eclipse.jface.databinding.swt.SWTObservables;
20
import org.eclipse.jface.viewers.ISelection;
21
import org.eclipse.jface.viewers.ISelectionChangedListener;
22
import org.eclipse.jface.viewers.ISelectionProvider;
23
import org.eclipse.jface.viewers.IStructuredSelection;
24
import org.eclipse.jface.viewers.SelectionChangedEvent;
25
import org.eclipse.jface.viewers.StructuredSelection;
26
import org.eclipse.jface.viewers.Viewer;
27
28
/**
29
 * @since 3.3
30
 * 
31
 */
32
public class SelectionProviderSingleSelectionProperty extends
33
		SimpleValueProperty {
34
	/**
35
	 * 
36
	 */
37
	public SelectionProviderSingleSelectionProperty() {
38
		super(null);
39
	}
40
41
	public IObservableValue observeValue(Object source) {
42
		Viewer viewer = (Viewer) source;
43
		return observeValue(SWTObservables.getRealm(viewer.getControl()
44
				.getDisplay()), viewer);
45
	}
46
47
	public Object getValue(Object source) {
48
		ISelection selection = ((ISelectionProvider) source).getSelection();
49
		if (selection instanceof IStructuredSelection) {
50
			return ((IStructuredSelection) selection).getFirstElement();
51
		}
52
		return null;
53
	}
54
55
	public void setValue(Object source, Object value) {
56
		((ISelectionProvider) source)
57
				.setSelection(value == null ? StructuredSelection.EMPTY
58
						: new StructuredSelection(value));
59
	}
60
61
	public INativePropertyListener adaptListener(
62
			IValuePropertyChangeListener listener) {
63
		return new SelectionChangedListener(listener);
64
	}
65
66
	public void addListener(Object source, INativePropertyListener listener) {
67
		((ISelectionProvider) source)
68
				.addSelectionChangedListener((ISelectionChangedListener) listener);
69
	}
70
71
	public void removeListener(Object source, INativePropertyListener listener) {
72
		((ISelectionProvider) source)
73
				.removeSelectionChangedListener((ISelectionChangedListener) listener);
74
75
	}
76
77
	private class SelectionChangedListener implements INativePropertyListener,
78
			ISelectionChangedListener {
79
		private IValuePropertyChangeListener listener;
80
81
		private SelectionChangedListener(IValuePropertyChangeListener listener) {
82
			this.listener = listener;
83
		}
84
85
		public void selectionChanged(SelectionChangedEvent event) {
86
			listener.handleValuePropertyChange(new ValuePropertyChangeEvent(
87
					event.getSource(),
88
					SelectionProviderSingleSelectionProperty.this, null));
89
		}
90
	}
91
92
	public String toString() {
93
		return "ISelectionProvider.selection"; //$NON-NLS-1$
94
	}
95
}
(-)src/org/eclipse/jface/databinding/swt/TableColumnProperties.java (+31 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.databinding.swt;
13
14
import org.eclipse.core.databinding.property.value.IValueProperty;
15
import org.eclipse.jface.internal.databinding.swt.TableColumnTooltipTextProperty;
16
17
/**
18
 * A factory for creating properties of SWT TableColumns
19
 * 
20
 * @since 1.3
21
 */
22
public class TableColumnProperties {
23
	/**
24
	 * Returns a value property for the tooltip text of a SWT TableColumns.
25
	 * 
26
	 * @return a value property for the tooltip text of a SWT TableColumns.
27
	 */
28
	public static IValueProperty tooltipText() {
29
		return new TableColumnTooltipTextProperty();
30
	}
31
}
(-)src/org/eclipse/jface/internal/databinding/swt/ComboItemsProperty.java (+33 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.swt.widgets.Combo;
15
import org.eclipse.swt.widgets.Control;
16
17
/**
18
 * @since 3.3
19
 * 
20
 */
21
public class ComboItemsProperty extends ControlStringListProperty {
22
	protected void doSetStringList(Control control, String[] list) {
23
		((Combo) control).setItems(list);
24
	}
25
26
	public String[] doGetStringList(Control control) {
27
		return ((Combo) control).getItems();
28
	}
29
30
	public String toString() {
31
		return "Combo.items[] <String>"; //$NON-NLS-1$
32
	}
33
}
(-)src/org/eclipse/jface/internal/databinding/viewers/StructuredViewerFiltersProperty.java (+76 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.viewers;
13
14
import java.util.Arrays;
15
import java.util.HashSet;
16
import java.util.Set;
17
18
import org.eclipse.core.databinding.observable.set.IObservableSet;
19
import org.eclipse.core.databinding.observable.set.SetDiff;
20
import org.eclipse.core.databinding.property.INativePropertyListener;
21
import org.eclipse.core.databinding.property.set.ISetPropertyChangeListener;
22
import org.eclipse.core.databinding.property.set.SimpleSetProperty;
23
import org.eclipse.jface.databinding.swt.SWTObservables;
24
import org.eclipse.jface.viewers.StructuredViewer;
25
import org.eclipse.jface.viewers.Viewer;
26
import org.eclipse.jface.viewers.ViewerFilter;
27
28
/**
29
 * @since 3.3
30
 * 
31
 */
32
public class StructuredViewerFiltersProperty extends SimpleSetProperty {
33
	/**
34
	 * 
35
	 */
36
	public StructuredViewerFiltersProperty() {
37
		super(ViewerFilter.class);
38
	}
39
40
	public IObservableSet observeSet(Object source) {
41
		Viewer viewer = (Viewer) source;
42
		return observeSet(SWTObservables.getRealm(viewer.getControl()
43
				.getDisplay()), viewer);
44
	}
45
46
	protected Set doGetSet(Object source) {
47
		return new HashSet(Arrays.asList(((StructuredViewer) source)
48
				.getFilters()));
49
	}
50
51
	public void setSet(Object source, Set set, SetDiff diff) {
52
		StructuredViewer viewer = (StructuredViewer) source;
53
		viewer.getControl().setRedraw(false);
54
		try {
55
			viewer.setFilters((ViewerFilter[]) set.toArray(new ViewerFilter[set
56
					.size()]));
57
		} finally {
58
			viewer.getControl().setRedraw(true);
59
		}
60
	}
61
62
	public INativePropertyListener adaptListener(
63
			ISetPropertyChangeListener listener) {
64
		return null;
65
	}
66
67
	public void addListener(Object source, INativePropertyListener listener) {
68
	}
69
70
	public void removeListener(Object source, INativePropertyListener listener) {
71
	}
72
73
	public String toString() {
74
		return "StructuredViewer.filters{} <ViewerFilter>"; //$NON-NLS-1$
75
	}
76
}
(-)src/org/eclipse/jface/internal/databinding/swt/CComboSingleSelectionIndexProperty.java (+40 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.swt.SWT;
15
import org.eclipse.swt.custom.CCombo;
16
17
/**
18
 * @since 3.3
19
 * 
20
 */
21
public class CComboSingleSelectionIndexProperty extends WidgetIntValueProperty {
22
	/**
23
	 * 
24
	 */
25
	public CComboSingleSelectionIndexProperty() {
26
		super(new int[] { SWT.Selection, SWT.DefaultSelection });
27
	}
28
29
	int doGetIntValue(Object source) {
30
		return ((CCombo) source).getSelectionIndex();
31
	}
32
33
	void doSetIntValue(Object source, int value) {
34
		((CCombo) source).select(value);
35
	}
36
37
	public String toString() {
38
		return "CCombo.selectionIndex <int>"; //$NON-NLS-1$
39
	}
40
}
(-)src/org/eclipse/jface/internal/databinding/swt/ListItemsProperty.java (+33 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.swt.widgets.Control;
15
import org.eclipse.swt.widgets.List;
16
17
/**
18
 * @since 3.3
19
 * 
20
 */
21
public class ListItemsProperty extends ControlStringListProperty {
22
	protected void doSetStringList(Control control, String[] list) {
23
		((List) control).setItems(list);
24
	}
25
26
	public String[] doGetStringList(Control control) {
27
		return ((List) control).getItems();
28
	}
29
30
	public String toString() {
31
		return "List.items[] <String>"; //$NON-NLS-1$
32
	}
33
}
(-)src/org/eclipse/jface/internal/databinding/swt/ControlForegroundProperty.java (+40 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.swt.graphics.Color;
15
import org.eclipse.swt.widgets.Control;
16
17
/**
18
 * @since 3.3
19
 * 
20
 */
21
public class ControlForegroundProperty extends WidgetValueProperty {
22
	/**
23
	 * 
24
	 */
25
	public ControlForegroundProperty() {
26
		super(Color.class);
27
	}
28
29
	public Object getValue(Object source) {
30
		return ((Control) source).getForeground();
31
	}
32
33
	public void setValue(Object source, Object value) {
34
		((Control) source).setForeground((Color) value);
35
	}
36
37
	public String toString() {
38
		return "Control.foreground <Color>"; //$NON-NLS-1$
39
	}
40
}
(-)src/org/eclipse/jface/internal/databinding/swt/ScaleMinimumProperty.java (+32 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.swt.widgets.Scale;
15
16
/**
17
 * @since 3.3
18
 * 
19
 */
20
public class ScaleMinimumProperty extends WidgetIntValueProperty {
21
	int doGetIntValue(Object source) {
22
		return ((Scale) source).getMinimum();
23
	}
24
25
	void doSetIntValue(Object source, int value) {
26
		((Scale) source).setMinimum(value);
27
	}
28
29
	public String toString() {
30
		return "Scale.minimum <int>"; //$NON-NLS-1$
31
	}
32
}
(-)src/org/eclipse/jface/internal/databinding/swt/WidgetStringValueProperty.java (+38 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
/**
15
 * @since 3.3
16
 * 
17
 */
18
public abstract class WidgetStringValueProperty extends WidgetValueProperty {
19
	WidgetStringValueProperty(int event) {
20
		super(event, String.class);
21
	}
22
23
	WidgetStringValueProperty() {
24
		super(String.class);
25
	}
26
27
	public Object getValue(Object source) {
28
		return doGetStringValue(source);
29
	}
30
31
	public void setValue(Object source, Object value) {
32
		doSetStringValue(source, (String) value);
33
	}
34
35
	abstract String doGetStringValue(Object source);
36
37
	abstract void doSetStringValue(Object source, String value);
38
}
(-)src/org/eclipse/jface/internal/databinding/swt/SpinnerMinimumProperty.java (+32 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.swt.widgets.Spinner;
15
16
/**
17
 * @since 3.3
18
 * 
19
 */
20
public class SpinnerMinimumProperty extends WidgetIntValueProperty {
21
	int doGetIntValue(Object source) {
22
		return ((Spinner) source).getMinimum();
23
	}
24
25
	void doSetIntValue(Object source, int value) {
26
		((Spinner) source).setMinimum(value);
27
	}
28
29
	public String toString() {
30
		return "Spinner.minimum <int>"; //$NON-NLS-1$
31
	}
32
}
(-)src/org/eclipse/jface/databinding/swt/ItemProperties.java (+31 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.databinding.swt;
13
14
import org.eclipse.core.databinding.property.value.IValueProperty;
15
import org.eclipse.jface.internal.databinding.swt.ItemTextProperty;
16
17
/**
18
 * A factory for creating properties of SWT controls.
19
 * 
20
 * @since 1.3
21
 */
22
public class ItemProperties {
23
	/**
24
	 * Returns a value property for the text of a SWT Item.
25
	 * 
26
	 * @return a value property for the text of a SWT Item
27
	 */
28
	public static IValueProperty text() {
29
		return new ItemTextProperty();
30
	}
31
}
(-)src/org/eclipse/jface/internal/databinding/swt/ScaleSelectionProperty.java (+40 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.swt.SWT;
15
import org.eclipse.swt.widgets.Scale;
16
17
/**
18
 * @since 3.3
19
 * 
20
 */
21
public class ScaleSelectionProperty extends WidgetIntValueProperty {
22
	/**
23
	 * 
24
	 */
25
	public ScaleSelectionProperty() {
26
		super(SWT.Selection);
27
	}
28
29
	int doGetIntValue(Object source) {
30
		return ((Scale) source).getSelection();
31
	}
32
33
	void doSetIntValue(Object source, int value) {
34
		((Scale) source).setSelection(value);
35
	}
36
37
	public String toString() {
38
		return "Scale.selection <int>"; //$NON-NLS-1$
39
	}
40
}
(-)src/org/eclipse/jface/internal/databinding/swt/WidgetValueProperty.java (+88 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.core.databinding.observable.value.IObservableValue;
15
import org.eclipse.core.databinding.property.INativePropertyListener;
16
import org.eclipse.core.databinding.property.value.IValuePropertyChangeListener;
17
import org.eclipse.core.databinding.property.value.SimpleValueProperty;
18
import org.eclipse.core.databinding.property.value.ValuePropertyChangeEvent;
19
import org.eclipse.jface.databinding.swt.SWTObservables;
20
import org.eclipse.swt.SWT;
21
import org.eclipse.swt.widgets.Event;
22
import org.eclipse.swt.widgets.Listener;
23
import org.eclipse.swt.widgets.Widget;
24
25
abstract class WidgetValueProperty extends SimpleValueProperty {
26
	private int[] events;
27
28
	WidgetValueProperty(Object valueType) {
29
		this(null, valueType);
30
	}
31
32
	WidgetValueProperty(int event, Object valueType) {
33
		this(new int[] { event }, valueType);
34
	}
35
36
	WidgetValueProperty(int[] events, Object valueType) {
37
		super(valueType);
38
		this.events = events;
39
	}
40
41
	public IObservableValue observeValue(Object source) {
42
		Widget widget = (Widget) source;
43
		return observeValue(SWTObservables.getRealm(widget.getDisplay()),
44
				widget);
45
	}
46
47
	public INativePropertyListener adaptListener(
48
			IValuePropertyChangeListener listener) {
49
		return new WidgetListener(listener);
50
	}
51
52
	public void addListener(Object source, INativePropertyListener listener) {
53
		if (events != null) {
54
			for (int i = 0; i < events.length; i++) {
55
				int event = events[i];
56
				if (event != SWT.None) {
57
					((Widget) source).addListener(event, (Listener) listener);
58
				}
59
			}
60
		}
61
	}
62
63
	public void removeListener(Object source, INativePropertyListener listener) {
64
		if (events != null) {
65
			Widget widget = (Widget) source;
66
			if (!widget.isDisposed()) {
67
				for (int i = 0; i < events.length; i++) {
68
					int event = events[i];
69
					if (event != SWT.None)
70
						widget.removeListener(event, (Listener) listener);
71
				}
72
			}
73
		}
74
	}
75
76
	private class WidgetListener implements INativePropertyListener, Listener {
77
		private final IValuePropertyChangeListener listener;
78
79
		protected WidgetListener(IValuePropertyChangeListener listener) {
80
			this.listener = listener;
81
		}
82
83
		public void handleEvent(Event event) {
84
			listener.handleValuePropertyChange(new ValuePropertyChangeEvent(
85
					event.widget, WidgetValueProperty.this, null));
86
		}
87
	}
88
}
(-)src/org/eclipse/jface/databinding/swt/TrayItemProperties.java (+31 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.databinding.swt;
13
14
import org.eclipse.core.databinding.property.value.IValueProperty;
15
import org.eclipse.jface.internal.databinding.swt.TrayItemTooltipTextProperty;
16
17
/**
18
 * A factory for creating properties of SWT TrayItems
19
 * 
20
 * @since 1.3
21
 */
22
public class TrayItemProperties {
23
	/**
24
	 * Returns a value property for the tooltip text of a SWT TrayItems.
25
	 * 
26
	 * @return a value property for the tooltip text of a SWT TrayItems.
27
	 */
28
	public static IValueProperty tooltipText() {
29
		return new TrayItemTooltipTextProperty();
30
	}
31
}
(-)src/org/eclipse/jface/internal/databinding/swt/TextEditableProperty.java (+32 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.swt.widgets.Text;
15
16
/**
17
 * @since 3.3
18
 * 
19
 */
20
public class TextEditableProperty extends WidgetBooleanValueProperty {
21
	boolean doGetBooleanValue(Object source) {
22
		return ((Text) source).getEditable();
23
	}
24
25
	void doSetBooleanValue(Object source, boolean value) {
26
		((Text) source).setEditable(value);
27
	}
28
29
	public String toString() {
30
		return "Text.editable <boolean>"; //$NON-NLS-1$
31
	}
32
}
(-)src/org/eclipse/jface/databinding/viewers/SelectionProviderProperties.java (+46 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.databinding.viewers;
13
14
import org.eclipse.core.databinding.property.list.IListProperty;
15
import org.eclipse.core.databinding.property.value.IValueProperty;
16
import org.eclipse.jface.internal.databinding.viewers.SelectionProviderMultipleSelectionProperty;
17
import org.eclipse.jface.internal.databinding.viewers.SelectionProviderSingleSelectionProperty;
18
19
/**
20
 * A factory for creating properties of JFace ISelectionProviders
21
 * 
22
 * @since 1.3
23
 */
24
public class SelectionProviderProperties {
25
	/**
26
	 * Returns a value property for the single selection of a JFace
27
	 * ISelectionProvider.
28
	 * 
29
	 * @return a value property for the single selection of a JFace
30
	 *         ISelectionProvider.
31
	 */
32
	public static IValueProperty singleSelection() {
33
		return new SelectionProviderSingleSelectionProperty();
34
	}
35
36
	/**
37
	 * Returns a list property for the multiple selection of a JFace
38
	 * ISelectionProvider.
39
	 * 
40
	 * @return a list property for the multiple selection of a JFace
41
	 *         ISelectionProvider.
42
	 */
43
	public static IListProperty multipleSelection() {
44
		return new SelectionProviderMultipleSelectionProperty();
45
	}
46
}
(-)src/org/eclipse/jface/internal/databinding/swt/TrayItemTooltipTextProperty.java (+32 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.swt.widgets.TrayItem;
15
16
/**
17
 * @since 3.3
18
 * 
19
 */
20
public class TrayItemTooltipTextProperty extends WidgetStringValueProperty {
21
	String doGetStringValue(Object source) {
22
		return ((TrayItem) source).getText();
23
	}
24
25
	void doSetStringValue(Object source, String value) {
26
		((TrayItem) source).setText(value == null ? "" : value); //$NON-NLS-1$
27
	}
28
29
	public String toString() {
30
		return "TrayItem.tooltipText <String>"; //$NON-NLS-1$
31
	}
32
}
(-)src/org/eclipse/jface/internal/databinding/swt/ShellTextProperty.java (+32 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.swt.widgets.Shell;
15
16
/**
17
 * @since 3.3
18
 * 
19
 */
20
public class ShellTextProperty extends WidgetStringValueProperty {
21
	String doGetStringValue(Object source) {
22
		return ((Shell) source).getText();
23
	}
24
25
	void doSetStringValue(Object source, String value) {
26
		((Shell) source).setText(value == null ? "" : value); //$NON-NLS-1$
27
	}
28
29
	public String toString() {
30
		return "Shell.text <String>"; //$NON-NLS-1$
31
	}
32
}
(-)src/org/eclipse/jface/internal/databinding/swt/TableSingleSelectionIndexProperty.java (+40 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.swt.SWT;
15
import org.eclipse.swt.widgets.Table;
16
17
/**
18
 * @since 3.3
19
 * 
20
 */
21
public class TableSingleSelectionIndexProperty extends WidgetIntValueProperty {
22
	/**
23
	 * 
24
	 */
25
	public TableSingleSelectionIndexProperty() {
26
		super(new int[] { SWT.Selection, SWT.DefaultSelection });
27
	}
28
29
	int doGetIntValue(Object source) {
30
		return ((Table) source).getSelectionIndex();
31
	}
32
33
	void doSetIntValue(Object source, int value) {
34
		((Table) source).setSelection(value);
35
	}
36
37
	public String toString() {
38
		return "Table.selectionIndex <int>"; //$NON-NLS-1$
39
	}
40
}
(-)src/org/eclipse/jface/internal/databinding/swt/CComboTextProperty.java (+40 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.jface.internal.databinding.swt;
13
14
import org.eclipse.swt.SWT;
15
import org.eclipse.swt.custom.CCombo;
16
17
/**
18
 * @since 3.3
19
 * 
20
 */
21
public class CComboTextProperty extends WidgetStringValueProperty {
22
	/**
23
	 * 
24
	 */
25
	public CComboTextProperty() {
26
		super(SWT.Modify);
27
	}
28
29
	String doGetStringValue(Object source) {
30
		return ((CCombo) source).getText();
31
	}
32
33
	void doSetStringValue(Object source, String value) {
34
		((CCombo) source).setText(value != null ? value : ""); //$NON-NLS-1$
35
	}
36
37
	public String toString() {
38
		return "CCombo.text <String>"; //$NON-NLS-1$
39
	}
40
}
(-)src/org/eclipse/core/databinding/observable/set/AbstractObservableSet.java (-28 / +4 lines)
Lines 7-13 Link Here
7
 *
7
 *
8
 * Contributors:
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
9
 *     IBM Corporation - initial API and implementation
10
 *     Matthew Hall - bug 208332
10
 *     Matthew Hall - bug 208332, 194734
11
 *******************************************************************************/
11
 *******************************************************************************/
12
12
13
package org.eclipse.core.databinding.observable.set;
13
package org.eclipse.core.databinding.observable.set;
Lines 17-23 Link Here
17
import java.util.Set;
17
import java.util.Set;
18
18
19
import org.eclipse.core.databinding.observable.AbstractObservable;
19
import org.eclipse.core.databinding.observable.AbstractObservable;
20
import org.eclipse.core.databinding.observable.ChangeSupport;
21
import org.eclipse.core.databinding.observable.ObservableTracker;
20
import org.eclipse.core.databinding.observable.ObservableTracker;
22
import org.eclipse.core.databinding.observable.Realm;
21
import org.eclipse.core.databinding.observable.Realm;
23
22
Lines 36-43 Link Here
36
public abstract class AbstractObservableSet extends AbstractObservable implements
35
public abstract class AbstractObservableSet extends AbstractObservable implements
37
		IObservableSet {
36
		IObservableSet {
38
37
39
	private ChangeSupport changeSupport;
40
41
	private boolean stale = false;
38
	private boolean stale = false;
42
39
43
	protected AbstractObservableSet() {
40
	protected AbstractObservableSet() {
Lines 54-75 Link Here
54
	
51
	
55
	protected AbstractObservableSet(Realm realm) {
52
	protected AbstractObservableSet(Realm realm) {
56
		super(realm);
53
		super(realm);
57
		changeSupport = new ChangeSupport(realm){
58
			protected void firstListenerAdded() {
59
				AbstractObservableSet.this.firstListenerAdded();
60
			}
61
			protected void lastListenerRemoved() {
62
				AbstractObservableSet.this.lastListenerRemoved();
63
			}
64
		};
65
	}
54
	}
66
	
55
	
67
	public synchronized void addSetChangeListener(ISetChangeListener listener) {
56
	public synchronized void addSetChangeListener(ISetChangeListener listener) {
68
		changeSupport.addListener(SetChangeEvent.TYPE, listener);
57
		addListener(SetChangeEvent.TYPE, listener);
69
	}
58
	}
70
59
71
	public synchronized void removeSetChangeListener(ISetChangeListener listener) {
60
	public synchronized void removeSetChangeListener(ISetChangeListener listener) {
72
		changeSupport.removeListener(SetChangeEvent.TYPE, listener);
61
		removeListener(SetChangeEvent.TYPE, listener);
73
	}
62
	}
74
63
75
	protected abstract Set getWrappedSet();
64
	protected abstract Set getWrappedSet();
Lines 78-84 Link Here
78
		// fire general change event first
67
		// fire general change event first
79
		super.fireChange();
68
		super.fireChange();
80
69
81
		changeSupport.fireEvent(new SetChangeEvent(this, diff));
70
		fireEvent(new SetChangeEvent(this, diff));
82
	}
71
	}
83
	
72
	
84
	public boolean contains(Object o) {
73
	public boolean contains(Object o) {
Lines 202-218 Link Here
202
	protected void fireChange() {
191
	protected void fireChange() {
203
		throw new RuntimeException("fireChange should not be called, use fireSetChange() instead"); //$NON-NLS-1$
192
		throw new RuntimeException("fireChange should not be called, use fireSetChange() instead"); //$NON-NLS-1$
204
	}
193
	}
205
	
206
	/* (non-Javadoc)
207
	 * @see org.eclipse.jface.provisional.databinding.observable.AbstractObservable#dispose()
208
	 */
209
	public synchronized void dispose() {
210
		super.dispose();
211
		
212
		if (changeSupport != null) {
213
			changeSupport.dispose();
214
			changeSupport = null;
215
		}
216
	}
217
	
218
}
194
}
(-)src/org/eclipse/core/databinding/observable/map/ComputedObservableMap.java (-1 / +15 lines)
Lines 7-13 Link Here
7
 *
7
 *
8
 * Contributors:
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
9
 *     IBM Corporation - initial API and implementation
10
 *     Matthew Hall - bugs 241585, 247394, 226289
10
 *     Matthew Hall - bugs 241585, 247394, 226289, 194734
11
 *******************************************************************************/
11
 *******************************************************************************/
12
12
13
package org.eclipse.core.databinding.observable.map;
13
package org.eclipse.core.databinding.observable.map;
Lines 21-26 Link Here
21
import java.util.Set;
21
import java.util.Set;
22
22
23
import org.eclipse.core.databinding.observable.Diffs;
23
import org.eclipse.core.databinding.observable.Diffs;
24
import org.eclipse.core.databinding.observable.IStaleListener;
25
import org.eclipse.core.databinding.observable.StaleEvent;
24
import org.eclipse.core.databinding.observable.set.IObservableSet;
26
import org.eclipse.core.databinding.observable.set.IObservableSet;
25
import org.eclipse.core.databinding.observable.set.ISetChangeListener;
27
import org.eclipse.core.databinding.observable.set.ISetChangeListener;
26
import org.eclipse.core.databinding.observable.set.SetChangeEvent;
28
import org.eclipse.core.databinding.observable.set.SetChangeEvent;
Lines 60-65 Link Here
60
		}
62
		}
61
	};
63
	};
62
64
65
	private IStaleListener staleListener = new IStaleListener() {
66
		public void handleStale(StaleEvent staleEvent) {
67
			fireStale();
68
		}
69
	};
70
63
	private Set entrySet = new EntrySet();
71
	private Set entrySet = new EntrySet();
64
72
65
	private class EntrySet extends AbstractSet {
73
	private class EntrySet extends AbstractSet {
Lines 137-142 Link Here
137
	private void hookListeners() {
145
	private void hookListeners() {
138
		if (keySet != null) {
146
		if (keySet != null) {
139
			keySet.addSetChangeListener(setChangeListener);
147
			keySet.addSetChangeListener(setChangeListener);
148
			keySet.addStaleListener(staleListener);
140
			for (Iterator it = this.keySet.iterator(); it.hasNext();) {
149
			for (Iterator it = this.keySet.iterator(); it.hasNext();) {
141
				Object key = it.next();
150
				Object key = it.next();
142
				hookListener(key);
151
				hookListener(key);
Lines 147-152 Link Here
147
	private void unhookListeners() {
156
	private void unhookListeners() {
148
		if (keySet != null) {
157
		if (keySet != null) {
149
			keySet.removeSetChangeListener(setChangeListener);
158
			keySet.removeSetChangeListener(setChangeListener);
159
			keySet.removeStaleListener(staleListener);
150
			Object[] keys = keySet.toArray();
160
			Object[] keys = keySet.toArray();
151
			for (int i = 0; i < keys.length; i++) {
161
			for (int i = 0; i < keys.length; i++) {
152
				unhookListener(keys[i]);
162
				unhookListener(keys[i]);
Lines 210-215 Link Here
210
	 */
220
	 */
211
	protected abstract Object doPut(Object key, Object value);
221
	protected abstract Object doPut(Object key, Object value);
212
222
223
	public boolean isStale() {
224
		return super.isStale() || keySet.isStale();
225
	}
226
213
	public synchronized void dispose() {
227
	public synchronized void dispose() {
214
		unhookListeners();
228
		unhookListeners();
215
		entrySet = null;
229
		entrySet = null;
(-)META-INF/MANIFEST.MF (+6 lines)
Lines 14-19 Link Here
14
 org.eclipse.core.databinding.observable.masterdetail,
14
 org.eclipse.core.databinding.observable.masterdetail,
15
 org.eclipse.core.databinding.observable.set;x-internal:=false,
15
 org.eclipse.core.databinding.observable.set;x-internal:=false,
16
 org.eclipse.core.databinding.observable.value;x-internal:=false,
16
 org.eclipse.core.databinding.observable.value;x-internal:=false,
17
 org.eclipse.core.databinding.property,
18
 org.eclipse.core.databinding.property.list,
19
 org.eclipse.core.databinding.property.map,
20
 org.eclipse.core.databinding.property.set,
21
 org.eclipse.core.databinding.property.value,
17
 org.eclipse.core.databinding.util,
22
 org.eclipse.core.databinding.util,
18
 org.eclipse.core.databinding.validation;x-internal:=false,
23
 org.eclipse.core.databinding.validation;x-internal:=false,
19
 org.eclipse.core.internal.databinding;x-friends:="org.eclipse.core.databinding.beans",
24
 org.eclipse.core.internal.databinding;x-friends:="org.eclipse.core.databinding.beans",
Lines 21-26 Link Here
21
 org.eclipse.core.internal.databinding.observable;x-internal:=true,
26
 org.eclipse.core.internal.databinding.observable;x-internal:=true,
22
 org.eclipse.core.internal.databinding.observable.masterdetail;x-friends:="org.eclipse.jface.tests.databinding",
27
 org.eclipse.core.internal.databinding.observable.masterdetail;x-friends:="org.eclipse.jface.tests.databinding",
23
 org.eclipse.core.internal.databinding.observable.tree;x-friends:="org.eclipse.jface.databinding,org.eclipse.jface.tests.databinding",
28
 org.eclipse.core.internal.databinding.observable.tree;x-friends:="org.eclipse.jface.databinding,org.eclipse.jface.tests.databinding",
29
 org.eclipse.core.internal.databinding.property;x-friends:="org.eclipse.jface.databinding,org.eclipse.jface.tests.databinding",
24
 org.eclipse.core.internal.databinding.validation;x-friends:="org.eclipse.jface.tests.databinding"
30
 org.eclipse.core.internal.databinding.validation;x-friends:="org.eclipse.jface.tests.databinding"
25
Require-Bundle: org.eclipse.equinox.common;bundle-version="[3.2.0,4.0.0)"
31
Require-Bundle: org.eclipse.equinox.common;bundle-version="[3.2.0,4.0.0)"
26
Import-Package-Comment: see http://wiki.eclipse.org/
32
Import-Package-Comment: see http://wiki.eclipse.org/
(-)src/org/eclipse/core/databinding/property/value/IValueProperty.java (+159 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.databinding.property.value;
13
14
import org.eclipse.core.databinding.observable.Realm;
15
import org.eclipse.core.databinding.observable.list.IObservableList;
16
import org.eclipse.core.databinding.observable.map.IObservableMap;
17
import org.eclipse.core.databinding.observable.set.IObservableSet;
18
import org.eclipse.core.databinding.observable.value.IObservableValue;
19
import org.eclipse.core.databinding.property.IProperty;
20
import org.eclipse.core.databinding.property.list.IListProperty;
21
import org.eclipse.core.databinding.property.map.IMapProperty;
22
import org.eclipse.core.databinding.property.set.ISetProperty;
23
24
/**
25
 * Interface for value-typed properties
26
 * 
27
 * @since 1.2
28
 * @noimplement This interface is not intended to be implemented by clients.
29
 *              Clients should instead subclass one of the classes that
30
 *              implement this interface. Note that direct implementers of this
31
 *              interface outside of the framework will be broken in future
32
 *              releases when methods are added to this interface.
33
 * @see ValueProperty
34
 * @see SimpleValueProperty
35
 */
36
public interface IValueProperty extends IProperty {
37
	/**
38
	 * Returns an observable value observing this value property on the given
39
	 * property source.
40
	 * 
41
	 * @param source
42
	 *            the property source
43
	 * @return an observable value observing this value property on the given
44
	 *         property source
45
	 */
46
	public IObservableValue observeValue(Object source);
47
48
	/**
49
	 * Returns an observable value observing this value property on the given
50
	 * property source
51
	 * 
52
	 * @param realm
53
	 *            the observable's realm
54
	 * @param source
55
	 *            the property source
56
	 * @return an observable value observing this value property on the given
57
	 *         property source
58
	 */
59
	public IObservableValue observeValue(Realm realm, Object source);
60
61
	/**
62
	 * Returns an observable value on the master observable's realm which tracks
63
	 * this property on the current value of <code>master</code>.
64
	 * 
65
	 * @param master
66
	 *            the master observable
67
	 * @return an observable value which tracks this property of the current
68
	 *         value of <code>master</code>.
69
	 */
70
	public IObservableValue observeDetailValue(IObservableValue master);
71
72
	/**
73
	 * Returns an observable list on the master observable's realm which tracks
74
	 * this property on each element of <code>master</code>.
75
	 * 
76
	 * @param master
77
	 *            the master observable
78
	 * @return an observable list which tracks this property on each element of
79
	 *         the master observable.
80
	 */
81
	public IObservableList observeDetailValues(IObservableList master);
82
83
	/**
84
	 * Returns an observable map on the master observable's realm where the
85
	 * map's key set is the specified master set, and where each key maps to the
86
	 * current property value for each element.
87
	 * 
88
	 * @param master
89
	 *            the master observable
90
	 * @return an observable map that tracks the current value of this property
91
	 *         for the elements in the given set.
92
	 */
93
	public IObservableMap observeDetailValues(IObservableSet master);
94
95
	/**
96
	 * Returns an observable map on the master observable's realm where the
97
	 * map's key set is the same as the master observable map, and where each
98
	 * value is the property value of the corresponding value in the master
99
	 * observable map.
100
	 * 
101
	 * @param master
102
	 *            the master observable
103
	 * @return an observable map on the master observable's realm which tracks
104
	 *         the current value of this property for the elements in the given
105
	 *         map's values collection
106
	 */
107
	public IObservableMap observeDetailValues(IObservableMap master);
108
109
	/**
110
	 * Returns the nested combination of this property and the specified detail
111
	 * value property. Value modifications made through the returned property
112
	 * are delegated to the detail property, using the value of this property as
113
	 * the source.
114
	 * 
115
	 * @param detailValue
116
	 *            the detail property
117
	 * @return the nested combination of the master and detail properties
118
	 */
119
	public IValueProperty chain(IValueProperty detailValue);
120
121
	/**
122
	 * Returns the nested combination of this property and the specified detail
123
	 * list property. List modifications made through the returned property are
124
	 * delegated to the detail property, using the value of the master property
125
	 * as the source.
126
	 * 
127
	 * @param detailList
128
	 *            the detail property
129
	 * @return the nested combination of the master value and detail list
130
	 *         properties
131
	 */
132
	public IListProperty chain(IListProperty detailList);
133
134
	/**
135
	 * Returns the nested combination of this property and the specified detail
136
	 * set property. Set modifications made through the returned property are
137
	 * delegated to the detail property, using the value of the master property
138
	 * as the source.
139
	 * 
140
	 * @param detailSet
141
	 *            the detail property
142
	 * @return the nested combination of the master value and detail set
143
	 *         properties
144
	 */
145
	public ISetProperty chain(ISetProperty detailSet);
146
147
	/**
148
	 * Returns the nested combination of this property and the specified detail
149
	 * map property. Map modifications made through the returned property are
150
	 * delegated to the detail property, using the value of the master property
151
	 * as the source.
152
	 * 
153
	 * @param detailMap
154
	 *            the detail property
155
	 * @return the nested combination of the master value and detial map
156
	 *         properties
157
	 */
158
	public IMapProperty chain(IMapProperty detailMap);
159
}
(-)src/org/eclipse/core/databinding/property/set/ISetPropertyChangeListener.java (+29 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.databinding.property.set;
13
14
import org.eclipse.core.databinding.property.IPropertyChangeListener;
15
16
/**
17
 * Listener for changes to set properties on a property source
18
 * 
19
 * @since 1.2
20
 */
21
public interface ISetPropertyChangeListener extends IPropertyChangeListener {
22
	/**
23
	 * Handle a change to a set property on a specific property source.
24
	 * 
25
	 * @param event
26
	 *            an event describing the set change that occured.
27
	 */
28
	public void handleSetPropertyChange(SetPropertyChangeEvent event);
29
}
(-)src/org/eclipse/core/databinding/property/value/ObservableMapSimpleValuePropertyObservableMap.java (+355 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.databinding.property.value;
13
14
import java.util.AbstractSet;
15
import java.util.Collections;
16
import java.util.HashMap;
17
import java.util.HashSet;
18
import java.util.Iterator;
19
import java.util.Map;
20
import java.util.Set;
21
22
import org.eclipse.core.databinding.observable.Diffs;
23
import org.eclipse.core.databinding.observable.IObserving;
24
import org.eclipse.core.databinding.observable.IStaleListener;
25
import org.eclipse.core.databinding.observable.ObservableTracker;
26
import org.eclipse.core.databinding.observable.StaleEvent;
27
import org.eclipse.core.databinding.observable.map.AbstractObservableMap;
28
import org.eclipse.core.databinding.observable.map.IMapChangeListener;
29
import org.eclipse.core.databinding.observable.map.IObservableMap;
30
import org.eclipse.core.databinding.observable.map.MapChangeEvent;
31
import org.eclipse.core.databinding.observable.map.MapDiff;
32
import org.eclipse.core.databinding.observable.set.IObservableSet;
33
import org.eclipse.core.databinding.observable.set.ISetChangeListener;
34
import org.eclipse.core.databinding.observable.set.SetChangeEvent;
35
import org.eclipse.core.databinding.observable.set.WritableSet;
36
import org.eclipse.core.databinding.property.INativePropertyListener;
37
import org.eclipse.core.internal.databinding.IdentityWrapper;
38
import org.eclipse.core.internal.databinding.Util;
39
40
/**
41
 * @since 1.2
42
 * 
43
 */
44
class ObservableMapSimpleValuePropertyObservableMap extends
45
		AbstractObservableMap implements IObserving {
46
	private IObservableMap masterMap;
47
	private SimpleValueProperty detailProperty;
48
49
	private IObservableSet knownMasterValues;
50
	private Map cachedValues;
51
52
	private boolean updating = false;
53
54
	private IMapChangeListener masterListener = new IMapChangeListener() {
55
		public void handleMapChange(final MapChangeEvent event) {
56
			if (!isDisposed()) {
57
				updateKnownValues();
58
				if (!updating)
59
					fireMapChange(convertDiff(event.diff));
60
			}
61
		}
62
63
		private void updateKnownValues() {
64
			Set identityKnownValues = new HashSet();
65
			for (Iterator it = masterMap.values().iterator(); it.hasNext();) {
66
				identityKnownValues.add(new IdentityWrapper(it.next()));
67
			}
68
69
			knownMasterValues.retainAll(identityKnownValues);
70
			knownMasterValues.addAll(identityKnownValues);
71
		}
72
73
		private MapDiff convertDiff(MapDiff diff) {
74
			Map oldValues = new HashMap();
75
			Map newValues = new HashMap();
76
77
			Set addedKeys = diff.getAddedKeys();
78
			for (Iterator it = addedKeys.iterator(); it.hasNext();) {
79
				Object key = it.next();
80
				Object newSource = diff.getNewValue(key);
81
				Object newValue = detailProperty.getValue(newSource);
82
				newValues.put(key, newValue);
83
			}
84
85
			Set removedKeys = diff.getRemovedKeys();
86
			for (Iterator it = removedKeys.iterator(); it.hasNext();) {
87
				Object key = it.next();
88
				Object oldSource = diff.getOldValue(key);
89
				Object oldValue = detailProperty.getValue(oldSource);
90
				oldValues.put(key, oldValue);
91
			}
92
93
			Set changedKeys = new HashSet(diff.getChangedKeys());
94
			for (Iterator it = changedKeys.iterator(); it.hasNext();) {
95
				Object key = it.next();
96
97
				Object oldSource = diff.getOldValue(key);
98
				Object newSource = diff.getNewValue(key);
99
100
				Object oldValue = detailProperty.getValue(oldSource);
101
				Object newValue = detailProperty.getValue(newSource);
102
103
				if (Util.equals(oldValue, newValue)) {
104
					it.remove();
105
				} else {
106
					oldValues.put(key, oldValue);
107
					newValues.put(key, newValue);
108
				}
109
			}
110
111
			return Diffs.createMapDiff(addedKeys, removedKeys, changedKeys,
112
					oldValues, newValues);
113
		}
114
	};
115
116
	private IStaleListener staleListener = new IStaleListener() {
117
		public void handleStale(StaleEvent staleEvent) {
118
			fireStale();
119
		}
120
	};
121
122
	private INativePropertyListener detailListener;
123
124
	/**
125
	 * @param map
126
	 * @param valueProperty
127
	 */
128
	public ObservableMapSimpleValuePropertyObservableMap(IObservableMap map,
129
			SimpleValueProperty valueProperty) {
130
		super(map.getRealm());
131
		this.masterMap = map;
132
		this.detailProperty = valueProperty;
133
134
		IValuePropertyChangeListener listener = new IValuePropertyChangeListener() {
135
			public void handleValuePropertyChange(ValuePropertyChangeEvent event) {
136
				Object masterValue = event.getSource();
137
				final Set keys = keysFor(masterValue);
138
139
				final Object oldDetailValue = event.diff.getOldValue();
140
				final Object newDetailValue = event.diff.getNewValue();
141
142
				if (!Util.equals(oldDetailValue, newDetailValue)) {
143
					fireMapChange(new MapDiff() {
144
						public Set getAddedKeys() {
145
							return Collections.EMPTY_SET;
146
						}
147
148
						public Set getChangedKeys() {
149
							return keys;
150
						}
151
152
						public Set getRemovedKeys() {
153
							return Collections.EMPTY_SET;
154
						}
155
156
						public Object getNewValue(Object key) {
157
							return newDetailValue;
158
						}
159
160
						public Object getOldValue(Object key) {
161
							return oldDetailValue;
162
						}
163
					});
164
				}
165
			}
166
167
			private Set keysFor(Object value) {
168
				Set keys = new HashSet();
169
170
				for (Iterator it = masterMap.entrySet().iterator(); it
171
						.hasNext();) {
172
					Map.Entry entry = (Entry) it.next();
173
					if (entry.getValue() == value) {
174
						keys.add(entry.getKey());
175
					}
176
				}
177
178
				return keys;
179
			}
180
		};
181
		this.detailListener = detailProperty.adaptListener(listener);
182
	}
183
184
	protected void firstListenerAdded() {
185
		knownMasterValues = new WritableSet(getRealm());
186
		cachedValues = new HashMap();
187
		knownMasterValues.addSetChangeListener(new ISetChangeListener() {
188
			public void handleSetChange(SetChangeEvent event) {
189
				for (Iterator it = event.diff.getRemovals().iterator(); it
190
						.hasNext();) {
191
					IdentityWrapper wrapper = (IdentityWrapper) it.next();
192
					Object key = wrapper.unwrap();
193
					detailProperty.removeListener(key, detailListener);
194
					cachedValues.remove(wrapper);
195
				}
196
				for (Iterator it = event.diff.getAdditions().iterator(); it
197
						.hasNext();) {
198
					IdentityWrapper wrapper = (IdentityWrapper) it.next();
199
					Object key = wrapper.unwrap();
200
					cachedValues.put(wrapper, detailProperty.getValue(key));
201
					detailProperty.addListener(key, detailListener);
202
				}
203
			}
204
		});
205
		for (Iterator it = masterMap.values().iterator(); it.hasNext();) {
206
			knownMasterValues.add(new IdentityWrapper(it.next()));
207
		}
208
209
		masterMap.addMapChangeListener(masterListener);
210
		masterMap.addStaleListener(staleListener);
211
	}
212
213
	protected void lastListenerRemoved() {
214
		masterMap.removeMapChangeListener(masterListener);
215
		masterMap.removeStaleListener(staleListener);
216
		if (knownMasterValues != null) {
217
			knownMasterValues.clear(); // removes attached listeners
218
			knownMasterValues.dispose();
219
			knownMasterValues = null;
220
		}
221
		cachedValues = null;
222
	}
223
224
	private Set entrySet;
225
226
	public Set entrySet() {
227
		getterCalled();
228
		if (entrySet == null)
229
			entrySet = new EntrySet();
230
		return entrySet;
231
	}
232
233
	class EntrySet extends AbstractSet {
234
		public Iterator iterator() {
235
			return new Iterator() {
236
				Iterator it = masterMap.entrySet().iterator();
237
238
				public boolean hasNext() {
239
					getterCalled();
240
					return it.hasNext();
241
				}
242
243
				public Object next() {
244
					getterCalled();
245
					Map.Entry next = (Map.Entry) it.next();
246
					return new MapEntry(next.getKey());
247
				}
248
249
				public void remove() {
250
					it.remove();
251
				}
252
			};
253
		}
254
255
		public int size() {
256
			return masterMap.size();
257
		}
258
	}
259
260
	class MapEntry implements Map.Entry {
261
		private Object key;
262
263
		MapEntry(Object key) {
264
			this.key = key;
265
		}
266
267
		public Object getKey() {
268
			getterCalled();
269
			return key;
270
		}
271
272
		public Object getValue() {
273
			getterCalled();
274
			if (!masterMap.containsKey(key))
275
				return null;
276
			return detailProperty.getValue(masterMap.get(key));
277
		}
278
279
		public Object setValue(Object value) {
280
			if (!masterMap.containsKey(key))
281
				return null;
282
			Object source = masterMap.get(key);
283
284
			Object oldValue = detailProperty.getValue(source);
285
286
			updating = true;
287
			try {
288
				detailProperty.setValue(source, value);
289
			} finally {
290
				updating = false;
291
			}
292
293
			Object newValue = detailProperty.getValue(source);
294
295
			if (!Util.equals(oldValue, newValue)) {
296
				fireMapChange(Diffs.createMapDiffSingleChange(key, oldValue,
297
						newValue));
298
			}
299
300
			return oldValue;
301
		}
302
303
		public boolean equals(Object o) {
304
			getterCalled();
305
			if (o == this)
306
				return true;
307
			if (o == null)
308
				return false;
309
			if (!(o instanceof Map.Entry))
310
				return false;
311
			Map.Entry that = (Map.Entry) o;
312
			return Util.equals(this.getKey(), that.getKey())
313
					&& Util.equals(this.getValue(), that.getValue());
314
		}
315
316
		public int hashCode() {
317
			getterCalled();
318
			Object value = getValue();
319
			return (key == null ? 0 : key.hashCode())
320
					^ (value == null ? 0 : value.hashCode());
321
		}
322
	}
323
324
	public boolean isStale() {
325
		getterCalled();
326
		return masterMap.isStale();
327
	}
328
329
	private void getterCalled() {
330
		ObservableTracker.getterCalled(this);
331
	}
332
333
	public Object getObserved() {
334
		return masterMap;
335
	}
336
337
	public synchronized void dispose() {
338
		if (masterMap != null) {
339
			masterMap.removeMapChangeListener(masterListener);
340
			masterMap = null;
341
		}
342
		if (knownMasterValues != null) {
343
			knownMasterValues.clear(); // detaches listeners
344
			knownMasterValues.dispose();
345
			knownMasterValues = null;
346
		}
347
348
		masterListener = null;
349
		detailListener = null;
350
		detailProperty = null;
351
		cachedValues = null;
352
353
		super.dispose();
354
	}
355
}
(-)src/org/eclipse/core/databinding/property/set/SimpleSetProperty.java (+446 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation
10
 ******************************************************************************/
11
12
package org.eclipse.core.databinding.property.set;
13
14
import java.util.Collection;
15
import java.util.Collections;
16
import java.util.HashSet;
17
import java.util.Iterator;
18
import java.util.Set;
19
20
import org.eclipse.core.databinding.observable.Diffs;
21
import org.eclipse.core.databinding.observable.IObservable;
22
import org.eclipse.core.databinding.observable.Realm;
23
import org.eclipse.core.databinding.observable.masterdetail.IObservableFactory;
24
import org.eclipse.core.databinding.observable.masterdetail.MasterDetailObservables;
25
import org.eclipse.core.databinding.observable.set.IObservableSet;
26
import org.eclipse.core.databinding.observable.set.SetDiff;
27
import org.eclipse.core.databinding.observable.value.IObservableValue;
28
import org.eclipse.core.databinding.property.INativePropertyListener;
29
30
/**
31
 * Simplified abstract implementation of ISetProperty. This class takes care of
32
 * most of the functional requirements for an ISetProperty implementation,
33
 * leaving only the property-specific details to subclasses.
34
 * <p>
35
 * Subclasses must implement these methods:
36
 * <ul>
37
 * <li> {@link #getSet(Object)}
38
 * <li> {@link #setSet(Object, Set, SetDiff)}
39
 * <li> {@link #adaptListener(ISetPropertyChangeListener)}
40
 * <li> {@link #addListener(Object, INativePropertyListener)}
41
 * <li> {@link #removeListener(Object, INativePropertyListener)}
42
 * <li> {@link #toString()}
43
 * </ul>
44
 * 
45
 * @since 1.2
46
 */
47
public abstract class SimpleSetProperty extends SetProperty {
48
	private final Object elementType;
49
50
	protected SimpleSetProperty(Object elementType) {
51
		this.elementType = elementType;
52
	}
53
54
	/**
55
	 * Returns the type of the elements in the collection or <code>null</code>
56
	 * if untyped
57
	 * 
58
	 * @return the type of the elements in the collection or <code>null</code>
59
	 *         if untyped
60
	 * @noreference This method is not intended to be referenced by clients.
61
	 */
62
	protected final Object getElementType() {
63
		return elementType;
64
	}
65
66
	/**
67
	 * Returns whether the source's collection property contains the given
68
	 * element.
69
	 * 
70
	 * @param source
71
	 *            the property source
72
	 * @param o
73
	 *            the element
74
	 * @return whether the source's collection property contains the given
75
	 *         element.
76
	 * @noreference This method is not intended to be referenced by clients.
77
	 */
78
	protected boolean contains(Object source, Object o) {
79
		return getSet(source).contains(o);
80
	}
81
82
	/**
83
	 * Returns whether the source's collection property contains all elements in
84
	 * the given collection
85
	 * 
86
	 * @param source
87
	 *            the property source
88
	 * @param c
89
	 *            the collection of elements to test for
90
	 * @return whether the source's collection property contains all elements in
91
	 *         the given collection
92
	 * @noreference This method is not intended to be referenced by clients.
93
	 */
94
	protected boolean containsAll(Object source, Collection c) {
95
		return getSet(source).containsAll(c);
96
	}
97
98
	/**
99
	 * Returns a Set with the current contents of the source's set property
100
	 * 
101
	 * @param source
102
	 *            the property source
103
	 * @return a Set with the current contents of the source's set property
104
	 * @noreference This method is not intended to be referenced by clients.
105
	 */
106
	protected final Set getSet(Object source) {
107
		return Collections.unmodifiableSet(doGetSet(source));
108
	}
109
110
	/**
111
	 * Returns an unmodifiable Set with the current contents of the source's set
112
	 * property
113
	 * 
114
	 * @param source
115
	 *            the property source
116
	 * @return an unmodifiable Set with the current contents of the source's set
117
	 *         property
118
	 * @noreference This method is not intended to be referenced by clients.
119
	 */
120
	protected abstract Set doGetSet(Object source);
121
122
	/**
123
	 * Returns whether the source's collection property is equal to the
124
	 * argument.
125
	 * 
126
	 * @param source
127
	 *            the property source
128
	 * @param o
129
	 *            the object to test for equality to the source's collection
130
	 *            property
131
	 * @return whether the source's collection property is equal to the argument
132
	 * @noreference This method is not intended to be referenced by clients.
133
	 */
134
	protected boolean equals(Object source, Object o) {
135
		return getSet(source).equals(o);
136
	}
137
138
	/**
139
	 * Returns the hash code of the source's collection property.
140
	 * 
141
	 * @param source
142
	 *            the property source
143
	 * @return the hash code of the source's collection property
144
	 * @noreference This method is not intended to be referenced by clients.
145
	 */
146
	protected int hashCode(Object source) {
147
		return getSet(source).hashCode();
148
	}
149
150
	/**
151
	 * Returns whether the source's collection property is empty
152
	 * 
153
	 * @param source
154
	 *            the property source
155
	 * @return whether the source's collection property is empty
156
	 * @noreference This method is not intended to be referenced by clients.
157
	 */
158
	protected boolean isEmpty(Object source) {
159
		return getSet(source).isEmpty();
160
	}
161
162
	/**
163
	 * Returns the size of the source's collection property
164
	 * 
165
	 * @param source
166
	 *            the property source
167
	 * @return the size of the source's collection property
168
	 * @noreference This method is not intended to be referenced by clients.
169
	 */
170
	protected int size(Object source) {
171
		return getSet(source).size();
172
	}
173
174
	/**
175
	 * Returns an array of all elements in the source's collection property
176
	 * 
177
	 * @param source
178
	 *            the property source
179
	 * @param array
180
	 *            the array into which the elements will be copied. If the array
181
	 *            is not large enough to hold all elements, the elements will be
182
	 *            returned in a new array of the same runtime type.
183
	 * @return an array of all elements in the source's collection property
184
	 * @noreference This method is not intended to be referenced by clients.
185
	 */
186
	protected Object[] toArray(Object source, Object[] array) {
187
		return getSet(source).toArray(array);
188
	}
189
190
	/**
191
	 * Returns an array of all elements in the source's collection property
192
	 * 
193
	 * @param source
194
	 *            the property source
195
	 * @return an array of all elements in the source's collection property
196
	 * @noreference This method is not intended to be referenced by clients.
197
	 */
198
	protected Object[] toArray(Object source) {
199
		return getSet(source).toArray();
200
	}
201
202
	/**
203
	 * Updates the property on the source with the specified change.
204
	 * 
205
	 * @param source
206
	 *            the property source
207
	 * @param set
208
	 *            the new set
209
	 * @param diff
210
	 *            a diff describing the change
211
	 * @noreference This method is not intended to be referenced by clients.
212
	 */
213
	protected abstract void setSet(Object source, Set set, SetDiff diff);
214
215
	/**
216
	 * Adds the element to the source's collection property
217
	 * 
218
	 * @param source
219
	 *            the property source
220
	 * @param o
221
	 *            the element to add
222
	 * @return whether the element was added to the source's collection property
223
	 * @noreference This method is not intended to be referenced by clients.
224
	 */
225
	protected boolean add(Object source, Object o) {
226
		Set set = getSet(source);
227
		if (!set.contains(o)) {
228
			set = new HashSet(set);
229
			boolean added = set.add(o);
230
			if (added) {
231
				setSet(source, set, Diffs.createSetDiff(Collections
232
						.singleton(o), Collections.EMPTY_SET));
233
			}
234
			return added;
235
		}
236
		return false;
237
	}
238
239
	/**
240
	 * Adds all elements in the specified collection to the source's collection
241
	 * property.
242
	 * 
243
	 * @param source
244
	 *            the property source
245
	 * @param c
246
	 *            the collection of elements to add.
247
	 * @return whether the source's collection property was changed
248
	 * @noreference This method is not intended to be referenced by clients.
249
	 */
250
	protected boolean addAll(Object source, Collection c) {
251
		if (c.isEmpty())
252
			return false;
253
254
		Set set = getSet(source);
255
		Set additions = new HashSet();
256
		for (Iterator it = c.iterator(); it.hasNext();) {
257
			Object o = it.next();
258
			if (!set.contains(o)) {
259
				additions.add(o);
260
			}
261
		}
262
		boolean changed = !additions.isEmpty();
263
		if (changed) {
264
			set = new HashSet(set);
265
			set.addAll(additions);
266
267
			setSet(source, set, Diffs.createSetDiff(additions,
268
					Collections.EMPTY_SET));
269
		}
270
		return changed;
271
	}
272
273
	/**
274
	 * Removes all elements from the source's collection property.
275
	 * 
276
	 * @param source
277
	 *            the property source
278
	 * @noreference This method is not intended to be referenced by clients.
279
	 */
280
	protected void clear(Object source) {
281
		if (!isEmpty(source)) {
282
			setSet(source, new HashSet(), Diffs.createSetDiff(
283
					Collections.EMPTY_SET, getSet(source)));
284
		}
285
	}
286
287
	/**
288
	 * Removes the element from the source's collection property
289
	 * 
290
	 * @param source
291
	 *            the property source
292
	 * @param o
293
	 *            the element to remove
294
	 * @return whether the element was removed from the source's collection
295
	 *         property
296
	 * @noreference This method is not intended to be referenced by clients.
297
	 */
298
	protected boolean remove(Object source, Object o) {
299
		Set set = getSet(source);
300
		if (set.contains(o)) {
301
			set = new HashSet(set);
302
			boolean removed = set.remove(o);
303
			if (removed) {
304
				setSet(source, set, Diffs.createSetDiff(Collections.EMPTY_SET,
305
						Collections.singleton(o)));
306
			}
307
			return removed;
308
		}
309
		return false;
310
	}
311
312
	/**
313
	 * Removes all elements from the source's collection property which are
314
	 * contained in the specified collection.
315
	 * 
316
	 * @param source
317
	 *            the property source
318
	 * @param c
319
	 *            the collection of elements to be removed
320
	 * @return whether the source's collection property was changed
321
	 * @noreference This method is not intended to be referenced by clients.
322
	 */
323
	protected boolean removeAll(Object source, Collection c) {
324
		if (c.isEmpty())
325
			return false;
326
327
		Set set = new HashSet(getSet(source));
328
		Set removals = new HashSet();
329
		for (Iterator it = set.iterator(); it.hasNext();) {
330
			Object o = it.next();
331
			if (c.contains(o)) {
332
				removals.add(o);
333
				it.remove();
334
			}
335
		}
336
		boolean changed = !removals.isEmpty();
337
		if (changed) {
338
			setSet(source, set, Diffs.createSetDiff(Collections.EMPTY_SET,
339
					removals));
340
		}
341
		return changed;
342
	}
343
344
	/**
345
	 * Removes all elements from the source's collection property which are not
346
	 * contained in the specified collection.
347
	 * 
348
	 * @param source
349
	 *            the property source
350
	 * @param c
351
	 *            the collection of elements to retain
352
	 * @return whether the source's collection property was changed
353
	 * @noreference This method is not intended to be referenced by clients.
354
	 */
355
	protected boolean retainAll(Object source, Collection c) {
356
		if (isEmpty(source))
357
			return false;
358
		if (c.isEmpty()) {
359
			clear(source);
360
			return true;
361
		}
362
363
		Set set = new HashSet(getSet(source));
364
		Set removals = new HashSet();
365
		for (Iterator it = set.iterator(); it.hasNext();) {
366
			Object o = it.next();
367
			if (!c.contains(o)) {
368
				removals.add(o);
369
				it.remove();
370
			}
371
		}
372
		boolean changed = !removals.isEmpty();
373
		if (changed) {
374
			setSet(source, set, Diffs.createSetDiff(Collections.EMPTY_SET,
375
					removals));
376
		}
377
		return changed;
378
	}
379
380
	/**
381
	 * Returns a listener which implements the correct listener interface for
382
	 * the expected source object, and which parlays property change events from
383
	 * the source object to the given listener. If there is no listener API for
384
	 * this property, this method returns null.
385
	 * 
386
	 * @param listener
387
	 *            the property listener to receive events
388
	 * @return a native listener which parlays property change events to the
389
	 *         specified listener.
390
	 * @throws ClassCastException
391
	 *             if the provided listener does not implement the correct
392
	 *             listener interface (IValueProperty, IListProperty,
393
	 *             ISetProperty or IMapProperty) depending on the property.
394
	 * @noreference This method is not intended to be referenced by clients.
395
	 * @noreference This method is not intended to be referenced by clients.
396
	 */
397
	protected abstract INativePropertyListener adaptListener(
398
			ISetPropertyChangeListener listener);
399
400
	/**
401
	 * Adds the specified listener as a listener for this property on the
402
	 * specified property source. If the source object has no listener API for
403
	 * this property (i.e. {@link #adaptListener(ISetPropertyChangeListener)}
404
	 * returns null), this method does nothing.
405
	 * 
406
	 * @param source
407
	 *            the property source
408
	 * @param listener
409
	 *            a listener obtained from calling
410
	 *            {@link #adaptListener(ISetPropertyChangeListener)}.
411
	 * @noreference This method is not intended to be referenced by clients.
412
	 */
413
	protected abstract void addListener(Object source,
414
			INativePropertyListener listener);
415
416
	/**
417
	 * Removes the specified listener as a listener for this property on the
418
	 * specified property source. If the source object has no listener API for
419
	 * this property (i.e. {@link #adaptListener(ISetPropertyChangeListener)}
420
	 * returns null), this method does nothing.
421
	 * 
422
	 * @param source
423
	 *            the property source
424
	 * @param listener
425
	 *            a listener obtained from calling
426
	 *            {@link #adaptListener(ISetPropertyChangeListener)} .
427
	 * @noreference This method is not intended to be referenced by clients.
428
	 */
429
	protected abstract void removeListener(Object source,
430
			INativePropertyListener listener);
431
432
	public IObservableSet observeSet(Realm realm, Object source) {
433
		return new SimpleSetPropertyObservableSet(realm, source, this);
434
	}
435
436
	public IObservableSet observeDetailSet(IObservableValue master) {
437
		final Realm realm = master.getRealm();
438
		IObservableFactory factory = new IObservableFactory() {
439
			public IObservable createObservable(Object target) {
440
				return SimpleSetProperty.this.observeSet(realm, target);
441
			}
442
		};
443
		return MasterDetailObservables.detailSet(master, factory,
444
				getElementType());
445
	}
446
}
(-)src/org/eclipse/core/databinding/property/list/IListProperty.java (+82 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.databinding.property.list;
13
14
import org.eclipse.core.databinding.observable.Realm;
15
import org.eclipse.core.databinding.observable.list.IObservableList;
16
import org.eclipse.core.databinding.observable.value.IObservableValue;
17
import org.eclipse.core.databinding.property.IProperty;
18
import org.eclipse.core.databinding.property.value.IValueProperty;
19
20
/**
21
 * Interface for list-typed properties.
22
 * 
23
 * @since 1.2
24
 * @noimplement This interface is not intended to be implemented by clients.
25
 *              Clients should instead subclass one of the classes that
26
 *              implement this interface. Note that direct implementers of this
27
 *              interface outside of the framework will be broken in future
28
 *              releases when methods are added to this interface.
29
 * @see ListProperty
30
 * @see SimpleListProperty
31
 */
32
public interface IListProperty extends IProperty {
33
	/**
34
	 * Returns an observable list observing this list property on the given
35
	 * property source
36
	 * 
37
	 * @param source
38
	 *            the property source
39
	 * @return an observable list observing this list property on the given
40
	 *         property source
41
	 */
42
	public IObservableList observeList(Object source);
43
44
	/**
45
	 * Returns an observable list observing this list property on the given
46
	 * property source
47
	 * 
48
	 * @param realm
49
	 *            the observable's realm
50
	 * @param source
51
	 *            the property source
52
	 * @return an observable list observing this list property on the given
53
	 *         property source
54
	 */
55
	public IObservableList observeList(Realm realm, Object source);
56
57
	/**
58
	 * Returns an observable list on the master observable's realm which tracks
59
	 * this property of the current value of <code>master</code>.
60
	 * 
61
	 * @param master
62
	 *            the master observable
63
	 * @return an observable list on the given realm which tracks this property
64
	 *         of the current value of <code>master</code>.
65
	 */
66
	public IObservableList observeDetailList(IObservableValue master);
67
68
	/**
69
	 * Returns the nested combination of this property and the specified detail
70
	 * value property. Note that because this property is a projection of value
71
	 * properties over a list, the only modification supported is through the
72
	 * {@link IObservableList#set(int, Object)} method. Modifications made
73
	 * through the returned property are delegated to the detail property, using
74
	 * the corresponding list element from the master property as the source.
75
	 * 
76
	 * @param detailValue
77
	 *            the detail property
78
	 * @return the nested combination of the master list and detail value
79
	 *         properties
80
	 */
81
	public IListProperty chain(IValueProperty detailValue);
82
}
(-)src/org/eclipse/core/internal/databinding/property/ValuePropertyDetailValue.java (+70 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.internal.databinding.property;
13
14
import org.eclipse.core.databinding.observable.Realm;
15
import org.eclipse.core.databinding.observable.list.IObservableList;
16
import org.eclipse.core.databinding.observable.map.IObservableMap;
17
import org.eclipse.core.databinding.observable.set.IObservableSet;
18
import org.eclipse.core.databinding.observable.value.IObservableValue;
19
import org.eclipse.core.databinding.property.value.IValueProperty;
20
import org.eclipse.core.databinding.property.value.ValueProperty;
21
22
/**
23
 * @since 1.2
24
 * 
25
 */
26
public class ValuePropertyDetailValue extends ValueProperty implements
27
		IValueProperty {
28
	private IValueProperty masterProperty;
29
	private IValueProperty detailProperty;
30
31
	/**
32
	 * @param masterProperty
33
	 * @param detailProperty
34
	 */
35
	public ValuePropertyDetailValue(IValueProperty masterProperty,
36
			IValueProperty detailProperty) {
37
		this.masterProperty = masterProperty;
38
		this.detailProperty = detailProperty;
39
	}
40
41
	public IObservableValue observeValue(Realm realm, Object source) {
42
		IObservableValue master = masterProperty.observeValue(realm, source);
43
		return detailProperty.observeDetailValue(master);
44
	}
45
46
	public IObservableValue observeDetailValue(IObservableValue master) {
47
		IObservableValue masterValue = masterProperty
48
				.observeDetailValue(master);
49
		return detailProperty.observeDetailValue(masterValue);
50
	}
51
52
	public IObservableList observeDetailValues(IObservableList master) {
53
		master = masterProperty.observeDetailValues(master);
54
		return detailProperty.observeDetailValues(master);
55
	}
56
57
	public IObservableMap observeDetailValues(IObservableSet master) {
58
		IObservableMap masterMap = masterProperty.observeDetailValues(master);
59
		return detailProperty.observeDetailValues(masterMap);
60
	}
61
62
	public IObservableMap observeDetailValues(IObservableMap master) {
63
		master = masterProperty.observeDetailValues(master);
64
		return detailProperty.observeDetailValues(master);
65
	}
66
67
	public String toString() {
68
		return masterProperty + " => " + detailProperty; //$NON-NLS-1$
69
	}
70
}
(-)src/org/eclipse/core/internal/databinding/property/ValuePropertyDetailSet.java (+53 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.internal.databinding.property;
13
14
import org.eclipse.core.databinding.observable.Realm;
15
import org.eclipse.core.databinding.observable.set.IObservableSet;
16
import org.eclipse.core.databinding.observable.value.IObservableValue;
17
import org.eclipse.core.databinding.property.set.ISetProperty;
18
import org.eclipse.core.databinding.property.set.SetProperty;
19
import org.eclipse.core.databinding.property.value.IValueProperty;
20
21
/**
22
 * @since 3.3
23
 * 
24
 */
25
public class ValuePropertyDetailSet extends SetProperty {
26
	private IValueProperty masterProperty;
27
	private ISetProperty detailProperty;
28
29
	/**
30
	 * @param masterProperty
31
	 * @param detailProperty
32
	 */
33
	public ValuePropertyDetailSet(IValueProperty masterProperty,
34
			ISetProperty detailProperty) {
35
		this.masterProperty = masterProperty;
36
		this.detailProperty = detailProperty;
37
	}
38
39
	public IObservableSet observeSet(Realm realm, Object source) {
40
		IObservableValue master = masterProperty.observeValue(realm, source);
41
		return detailProperty.observeDetailSet(master);
42
	}
43
44
	public IObservableSet observeDetailSet(IObservableValue master) {
45
		IObservableValue masterValue = masterProperty
46
				.observeDetailValue(master);
47
		return detailProperty.observeDetailSet(masterValue);
48
	}
49
50
	public String toString() {
51
		return masterProperty + " => " + detailProperty; //$NON-NLS-1$
52
	}
53
}
(-)src/org/eclipse/core/databinding/property/set/SimpleSetPropertyObservableSet.java (+343 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.databinding.property.set;
13
14
import java.util.Collection;
15
import java.util.Collections;
16
import java.util.ConcurrentModificationException;
17
import java.util.HashSet;
18
import java.util.Iterator;
19
import java.util.Set;
20
21
import org.eclipse.core.databinding.observable.Diffs;
22
import org.eclipse.core.databinding.observable.Realm;
23
import org.eclipse.core.databinding.observable.set.AbstractObservableSet;
24
import org.eclipse.core.databinding.observable.set.SetDiff;
25
import org.eclipse.core.databinding.property.IProperty;
26
import org.eclipse.core.databinding.property.INativePropertyListener;
27
import org.eclipse.core.databinding.property.IPropertyObservable;
28
29
/**
30
 * @since 1.2
31
 * 
32
 */
33
class SimpleSetPropertyObservableSet extends AbstractObservableSet implements
34
		IPropertyObservable {
35
	private Object source;
36
	private SimpleSetProperty property;
37
38
	private volatile boolean updating = false;
39
40
	private volatile int modCount = 0;
41
42
	private INativePropertyListener listener;
43
44
	private Set cachedSet;
45
46
	/**
47
	 * @param realm
48
	 * @param source
49
	 * @param property
50
	 */
51
	public SimpleSetPropertyObservableSet(Realm realm, Object source,
52
			SimpleSetProperty property) {
53
		super(realm);
54
		this.source = source;
55
		this.property = property;
56
	}
57
58
	protected void firstListenerAdded() {
59
		if (!isDisposed()) {
60
			cachedSet = property.getSet(source);
61
62
			if (listener == null) {
63
				listener = property
64
						.adaptListener(new ISetPropertyChangeListener() {
65
							public void handleSetPropertyChange(
66
									final SetPropertyChangeEvent event) {
67
								modCount++;
68
								if (!isDisposed() && !updating) {
69
									getRealm().exec(new Runnable() {
70
										public void run() {
71
											Set oldSet = cachedSet;
72
											Set newSet = cachedSet = property
73
													.getSet(source);
74
											SetDiff diff = event.diff;
75
											if (diff == null) {
76
												diff = Diffs.computeSetDiff(
77
														oldSet, newSet);
78
											}
79
											fireSetChange(diff);
80
										}
81
									});
82
								}
83
							}
84
						});
85
			}
86
			property.addListener(source, listener);
87
		}
88
	}
89
90
	protected void lastListenerRemoved() {
91
		if (listener != null) {
92
			property.removeListener(source, listener);
93
		}
94
95
		cachedSet = null;
96
	}
97
98
	protected Set getWrappedSet() {
99
		return property.getSet(source);
100
	}
101
102
	public Object getElementType() {
103
		return property.getElementType();
104
	}
105
106
	// Queries
107
108
	protected int doGetSize() {
109
		return property.size(source);
110
	}
111
112
	// Single change operations
113
114
	public boolean add(Object o) {
115
		checkRealm();
116
117
		boolean changed;
118
119
		boolean wasUpdating = updating;
120
		updating = true;
121
		try {
122
			changed = property.add(source, o);
123
			modCount++;
124
		} finally {
125
			updating = wasUpdating;
126
		}
127
128
		cachedSet = property.getSet(source);
129
130
		if (changed)
131
			fireSetChange(Diffs.createSetDiff(Collections.singleton(o),
132
					Collections.EMPTY_SET));
133
134
		return changed;
135
	}
136
137
	public Iterator iterator() {
138
		getterCalled();
139
		return new Iterator() {
140
			int expectedModCount = modCount;
141
			Iterator delegate = new HashSet(property.getSet(source)).iterator();
142
			Object last = null;
143
144
			public boolean hasNext() {
145
				getterCalled();
146
				checkForComodification();
147
				return delegate.hasNext();
148
			}
149
150
			public Object next() {
151
				getterCalled();
152
				checkForComodification();
153
				last = delegate.next();
154
				return last;
155
			}
156
157
			public void remove() {
158
				checkRealm();
159
				checkForComodification();
160
161
				delegate.remove(); // stay in sync
162
163
				boolean wasUpdating = updating;
164
				updating = true;
165
				try {
166
					property.remove(source, last);
167
					modCount++;
168
				} finally {
169
					updating = wasUpdating;
170
				}
171
172
				cachedSet = property.getSet(source);
173
174
				fireSetChange(Diffs.createSetDiff(Collections.EMPTY_SET,
175
						Collections.singleton(last)));
176
177
				last = null;
178
				expectedModCount = modCount;
179
			}
180
181
			private void checkForComodification() {
182
				if (expectedModCount != modCount)
183
					throw new ConcurrentModificationException();
184
			}
185
		};
186
	}
187
188
	public boolean remove(Object o) {
189
		getterCalled();
190
191
		boolean changed;
192
193
		boolean wasUpdating = updating;
194
		updating = true;
195
		try {
196
			changed = property.remove(source, o);
197
			modCount++;
198
		} finally {
199
			updating = wasUpdating;
200
		}
201
202
		cachedSet = property.getSet(source);
203
		fireSetChange(Diffs.createSetDiff(Collections.EMPTY_SET, Collections
204
				.singleton(o)));
205
206
		return changed;
207
	}
208
209
	// Bulk change operations
210
211
	public boolean addAll(Collection c) {
212
		getterCalled();
213
214
		if (c.isEmpty())
215
			return false;
216
217
		Set additions = new HashSet(c);
218
		additions.removeAll(property.getSet(source));
219
		if (additions.isEmpty())
220
			return false;
221
222
		boolean wasUpdating = updating;
223
		updating = true;
224
		try {
225
			property.addAll(source, c);
226
			modCount++;
227
		} finally {
228
			updating = wasUpdating;
229
		}
230
231
		cachedSet = property.getSet(source);
232
		fireSetChange(Diffs.createSetDiff(additions, Collections.EMPTY_SET));
233
234
		return true;
235
	}
236
237
	public boolean removeAll(Collection c) {
238
		getterCalled();
239
240
		if (property.isEmpty(source) || c.isEmpty())
241
			return false;
242
243
		Set removals = new HashSet(c);
244
		removals.retainAll(property.getSet(source));
245
		if (removals.isEmpty())
246
			return false;
247
248
		boolean wasUpdating = updating;
249
		updating = true;
250
		try {
251
			property.removeAll(source, c);
252
			modCount++;
253
		} finally {
254
			updating = wasUpdating;
255
		}
256
257
		cachedSet = property.getSet(source);
258
		fireSetChange(Diffs.createSetDiff(Collections.EMPTY_SET, removals));
259
260
		return true;
261
	}
262
263
	public boolean retainAll(Collection c) {
264
		getterCalled();
265
266
		if (property.isEmpty(source))
267
			return false;
268
269
		if (c.isEmpty()) {
270
			clear();
271
			return true;
272
		}
273
274
		Set removals = new HashSet(property.getSet(source));
275
		removals.removeAll(c);
276
		if (removals.isEmpty())
277
			return false;
278
279
		boolean wasUpdating = updating;
280
		updating = true;
281
		try {
282
			property.retainAll(source, c);
283
			modCount++;
284
		} finally {
285
			updating = wasUpdating;
286
		}
287
288
		cachedSet = property.getSet(source);
289
		fireSetChange(Diffs.createSetDiff(Collections.EMPTY_SET, removals));
290
291
		return true;
292
	}
293
294
	public void clear() {
295
		getterCalled();
296
297
		if (property.isEmpty(source))
298
			return;
299
300
		Set removals = new HashSet(property.getSet(source));
301
302
		boolean wasUpdating = updating;
303
		updating = true;
304
		try {
305
			property.clear(source);
306
			modCount++;
307
		} finally {
308
			updating = wasUpdating;
309
		}
310
311
		cachedSet = property.getSet(source);
312
		fireSetChange(Diffs.createSetDiff(Collections.EMPTY_SET, removals));
313
	}
314
315
	public boolean equals(Object o) {
316
		getterCalled();
317
		return property.equals(source, o);
318
	}
319
320
	public int hashCode() {
321
		getterCalled();
322
		return property.hashCode(source);
323
	}
324
325
	public Object getObserved() {
326
		return source;
327
	}
328
329
	public IProperty getProperty() {
330
		return property;
331
	}
332
333
	public synchronized void dispose() {
334
		if (!isDisposed()) {
335
			if (listener != null)
336
				property.removeListener(source, listener);
337
			property = null;
338
			source = null;
339
			listener = null;
340
		}
341
		super.dispose();
342
	}
343
}
(-)src/org/eclipse/core/databinding/property/value/ValueProperty.java (+47 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 IBM Corporation and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
10
 ******************************************************************************/
11
12
package org.eclipse.core.databinding.property.value;
13
14
import org.eclipse.core.databinding.observable.Realm;
15
import org.eclipse.core.databinding.observable.value.IObservableValue;
16
import org.eclipse.core.databinding.property.Properties;
17
import org.eclipse.core.databinding.property.Property;
18
import org.eclipse.core.databinding.property.list.IListProperty;
19
import org.eclipse.core.databinding.property.map.IMapProperty;
20
import org.eclipse.core.databinding.property.set.ISetProperty;
21
22
/**
23
 * Abstract implementation of IValueProperty
24
 * 
25
 * @since 1.2
26
 */
27
public abstract class ValueProperty extends Property implements IValueProperty {
28
	public IObservableValue observeValue(Object source) {
29
		return observeValue(Realm.getDefault(), source);
30
	}
31
32
	public final IValueProperty chain(IValueProperty detailValue) {
33
		return Properties.detailValue(this, detailValue);
34
	}
35
36
	public final IListProperty chain(IListProperty detailList) {
37
		return Properties.detailList(this, detailList);
38
	}
39
40
	public final ISetProperty chain(ISetProperty detailSet) {
41
		return Properties.detailSet(this, detailSet);
42
	}
43
44
	public final IMapProperty chain(IMapProperty detailMap) {
45
		return Properties.detailMap(this, detailMap);
46
	}
47
}
(-)src/org/eclipse/core/databinding/property/Properties.java (+201 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.databinding.property;
13
14
import org.eclipse.core.databinding.observable.list.IObservableList;
15
import org.eclipse.core.databinding.observable.map.IObservableMap;
16
import org.eclipse.core.databinding.property.list.IListProperty;
17
import org.eclipse.core.databinding.property.map.IMapProperty;
18
import org.eclipse.core.databinding.property.set.ISetProperty;
19
import org.eclipse.core.databinding.property.value.IValueProperty;
20
import org.eclipse.core.internal.databinding.property.ListPropertyDetailValuesList;
21
import org.eclipse.core.internal.databinding.property.MapPropertyDetailValuesMap;
22
import org.eclipse.core.internal.databinding.property.SetPropertyDetailValuesMap;
23
import org.eclipse.core.internal.databinding.property.ValuePropertyDetailList;
24
import org.eclipse.core.internal.databinding.property.ValuePropertyDetailMap;
25
import org.eclipse.core.internal.databinding.property.ValuePropertyDetailSet;
26
import org.eclipse.core.internal.databinding.property.ValuePropertyDetailValue;
27
28
/**
29
 * A factory for chaining properties together to create nested properties.
30
 * <p>
31
 * Example: Suppose class <code>A</code> has a property <code>b</code> of type
32
 * <code>B</code>, and that class <code>B</code> has a property <code>c</code>
33
 * of type <code>C</code>:
34
 * 
35
 * <pre>
36
 * A a = new A();
37
 * B b = a.getB();
38
 * IValueProperty ab = BeanProperties.valueProperty(A.class, &quot;b&quot;);
39
 * assertTrue(ab.getValue(a) == b);
40
 * 
41
 * IValueProperty bc = BeanProperties.valueProperty(B.class, &quot;c&quot;);
42
 * C c = b.getC();
43
 * assertTrue(bc.getValue(b) == c);
44
 * </pre>
45
 * 
46
 * Using Properties, the <code>ab</code> and <code>bc</code> properties may be
47
 * combined to form a nested <code>abc</code> property:
48
 * 
49
 * <pre>
50
 * IValueProperty abc = Properties.detailValue(ab, bc)
51
 * assertTrue(abc.getValue(a) == c);
52
 * </pre>
53
 * 
54
 * @since 1.2
55
 */
56
public class Properties {
57
	// Properties of IValueProperty properties
58
59
	/**
60
	 * Returns the nested combination of the master value and detail value
61
	 * properties. Value modifications made through the returned property are
62
	 * delegated to the detail property, using the value of the master property
63
	 * as the source.
64
	 * 
65
	 * @param masterValue
66
	 *            the master property
67
	 * @param detailValue
68
	 *            the detail property
69
	 * @return the nested combination of the master and detail properties
70
	 */
71
	public static IValueProperty detailValue(IValueProperty masterValue,
72
			IValueProperty detailValue) {
73
		return new ValuePropertyDetailValue(masterValue, detailValue);
74
	}
75
76
	/**
77
	 * Returns the nested combination of the master value and detail list
78
	 * properties. List modifications made through the returned property are
79
	 * delegated to the detail property, using the value of the master property
80
	 * as the source.
81
	 * 
82
	 * @param masterValue
83
	 *            the master property
84
	 * @param detailList
85
	 *            the detail property
86
	 * @return the nested combination of the master value and detail list
87
	 *         properties
88
	 */
89
	public static IListProperty detailList(IValueProperty masterValue,
90
			IListProperty detailList) {
91
		return new ValuePropertyDetailList(masterValue, detailList);
92
	}
93
94
	/**
95
	 * Returns the nested combination of the master value and detail set
96
	 * properties. Set modifications made through the returned property are
97
	 * delegated to the detail property, using the value of the master property
98
	 * as the source.
99
	 * 
100
	 * @param masterValue
101
	 *            the master property
102
	 * @param detailSet
103
	 *            the detail property
104
	 * @return the nested combination of the master value and detail set
105
	 *         properties
106
	 */
107
	public static ISetProperty detailSet(IValueProperty masterValue,
108
			ISetProperty detailSet) {
109
		return new ValuePropertyDetailSet(masterValue, detailSet);
110
	}
111
112
	/**
113
	 * Returns the nested combination of the master value and detail map
114
	 * properties. Map modifications made through the returned property are
115
	 * delegated to the detail property, using the value of the master property
116
	 * as the source.
117
	 * 
118
	 * @param masterValue
119
	 *            the master property
120
	 * @param detailMap
121
	 *            the detail property
122
	 * @return the nested combination of the master value and detial map
123
	 *         properties
124
	 */
125
	public static IMapProperty detailMap(IValueProperty masterValue,
126
			IMapProperty detailMap) {
127
		return new ValuePropertyDetailMap(masterValue, detailMap);
128
	}
129
130
	// Properties of IListProperty master properties
131
132
	/**
133
	 * Returns the nested combination of the master list and detail value
134
	 * properties. Note that because this property is a projection of value
135
	 * properties over a list, the only modification supported is through the
136
	 * {@link IObservableList#set(int, Object)} method. Modifications made
137
	 * through the returned property are delegated to the detail property, using
138
	 * the corresponding list element from the master property as the source.
139
	 * 
140
	 * @param masterList
141
	 *            the master property
142
	 * @param detailValue
143
	 *            the detail property
144
	 * @return the nested combination of the master list and detail value
145
	 *         properties
146
	 */
147
	public static IListProperty detailValues(IListProperty masterList,
148
			IValueProperty detailValue) {
149
		return new ListPropertyDetailValuesList(masterList, detailValue);
150
	}
151
152
	// Properties of ISetProperty master properties
153
154
	/**
155
	 * Returns the nested combination of the master set and detail value
156
	 * properties. Note that because this property is a projection of value
157
	 * properties over a set, the only modifications supported are through the
158
	 * {@link IObservableMap#put(Object, Object)} and
159
	 * {@link IObservableMap#putAll(java.util.Map)} methods. In the latter case,
160
	 * this property does not put entries for keys not already in the master key
161
	 * set. Modifications made through the returned property are delegated to
162
	 * the detail property, using the corresponding set element from the master
163
	 * property as the source.
164
	 * 
165
	 * @param masterKeySet
166
	 *            the master property
167
	 * @param detailValues
168
	 *            the detail property
169
	 * @return the nested combination of the master set and detail value
170
	 *         properties
171
	 */
172
	public static IMapProperty detailValues(ISetProperty masterKeySet,
173
			IValueProperty detailValues) {
174
		return new SetPropertyDetailValuesMap(masterKeySet, detailValues);
175
	}
176
177
	// Properties of IMapProperty master properties
178
179
	/**
180
	 * Returns the nested combination of the master map and detail value
181
	 * properties. Note that because this property is a projection of value
182
	 * properties over a values collection, the only modifications supported are
183
	 * through the {@link IObservableMap#put(Object, Object)} and
184
	 * {@link IObservableMap#putAll(java.util.Map)} methods. In the latter case,
185
	 * this property does not entries for keys not already contained in the
186
	 * master map's key set. Modifications made through the returned property
187
	 * are delegated to the detail property, using the corresponding entry value
188
	 * from the master property as the source.
189
	 * 
190
	 * @param masterMap
191
	 *            the master property
192
	 * @param detailValues
193
	 *            the detail property
194
	 * @return the nested combination of the master map and detail value
195
	 *         properties.
196
	 */
197
	public static IMapProperty detailValues(IMapProperty masterMap,
198
			IValueProperty detailValues) {
199
		return new MapPropertyDetailValuesMap(masterMap, detailValues);
200
	}
201
}
(-)src/org/eclipse/core/databinding/property/map/IMapProperty.java (+86 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.databinding.property.map;
13
14
import org.eclipse.core.databinding.observable.Realm;
15
import org.eclipse.core.databinding.observable.map.IObservableMap;
16
import org.eclipse.core.databinding.observable.value.IObservableValue;
17
import org.eclipse.core.databinding.property.IProperty;
18
import org.eclipse.core.databinding.property.value.IValueProperty;
19
20
/**
21
 * Interface for map-typed properties
22
 * 
23
 * @since 1.2
24
 * @noimplement This interface is not intended to be implemented by clients.
25
 *              Clients should instead subclass one of the classes that
26
 *              implement this interface. Note that direct implementers of this
27
 *              interface outside of the framework will be broken in future
28
 *              releases when methods are added to this interface.
29
 * @see MapProperty
30
 * @see SimpleMapProperty
31
 */
32
public interface IMapProperty extends IProperty {
33
	/**
34
	 * Returns an observable map observing this map property on the given
35
	 * property source
36
	 * 
37
	 * @param source
38
	 *            the property source
39
	 * @return an observable map observing this map-typed property on the given
40
	 *         property source
41
	 */
42
	public IObservableMap observeMap(Object source);
43
44
	/**
45
	 * Returns an observable map observing this map property on the given
46
	 * property source
47
	 * 
48
	 * @param realm
49
	 *            the observable's realm
50
	 * @param source
51
	 *            the property source
52
	 * @return an observable map observing this map-typed property on the given
53
	 *         property source
54
	 */
55
	public IObservableMap observeMap(Realm realm, Object source);
56
57
	/**
58
	 * Returns an observable map on the master observable's realm which tracks
59
	 * this property of the values in the entry set of <code>master</code>.
60
	 * 
61
	 * @param master
62
	 *            the master observable
63
	 * @return an observable map on the master observable's realm which tracks
64
	 *         this property of the values in the entry set of
65
	 *         <code>master</code>.
66
	 */
67
	public IObservableMap observeDetailMap(IObservableValue master);
68
69
	/**
70
	 * Returns the nested combination of this property and the specified detail
71
	 * value property. Note that because this property is a projection of value
72
	 * properties over a values collection, the only modifications supported are
73
	 * through the {@link IObservableMap#put(Object, Object)} and
74
	 * {@link IObservableMap#putAll(java.util.Map)} methods. In the latter case,
75
	 * this property does not entries for keys not already contained in the
76
	 * master map's key set. Modifications made through the returned property
77
	 * are delegated to the detail property, using the corresponding entry value
78
	 * from the master property as the source.
79
	 * 
80
	 * @param detailValues
81
	 *            the detail property
82
	 * @return the nested combination of the master map and detail value
83
	 *         properties.
84
	 */
85
	public IMapProperty chain(IValueProperty detailValues);
86
}
(-)src/org/eclipse/core/internal/databinding/property/ValuePropertyDetailMap.java (+53 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.internal.databinding.property;
13
14
import org.eclipse.core.databinding.observable.Realm;
15
import org.eclipse.core.databinding.observable.map.IObservableMap;
16
import org.eclipse.core.databinding.observable.value.IObservableValue;
17
import org.eclipse.core.databinding.property.map.IMapProperty;
18
import org.eclipse.core.databinding.property.map.MapProperty;
19
import org.eclipse.core.databinding.property.value.IValueProperty;
20
21
/**
22
 * @since 3.3
23
 * 
24
 */
25
public class ValuePropertyDetailMap extends MapProperty {
26
	private final IValueProperty masterProperty;
27
	private final IMapProperty detailProperty;
28
29
	/**
30
	 * @param masterProperty
31
	 * @param detailProperty
32
	 */
33
	public ValuePropertyDetailMap(IValueProperty masterProperty,
34
			IMapProperty detailProperty) {
35
		this.masterProperty = masterProperty;
36
		this.detailProperty = detailProperty;
37
	}
38
39
	public IObservableMap observeMap(Realm realm, Object source) {
40
		IObservableValue master = masterProperty.observeValue(realm, source);
41
		return detailProperty.observeDetailMap(master);
42
	}
43
44
	public IObservableMap observeDetailMap(IObservableValue master) {
45
		IObservableValue masterValue = masterProperty
46
				.observeDetailValue(master);
47
		return detailProperty.observeDetailMap(masterValue);
48
	}
49
50
	public String toString() {
51
		return masterProperty + " => " + detailProperty; //$NON-NLS-1$
52
	}
53
}
(-)src/org/eclipse/core/databinding/property/value/ValuePropertyChangeEvent.java (+59 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.databinding.property.value;
13
14
import org.eclipse.core.databinding.observable.value.ValueDiff;
15
import org.eclipse.core.databinding.property.IPropertyChangeListener;
16
import org.eclipse.core.databinding.property.PropertyChangeEvent;
17
18
/**
19
 * Value change event describing a change of a value property on a particular
20
 * property source.
21
 * 
22
 * @since 1.2
23
 */
24
public class ValuePropertyChangeEvent extends PropertyChangeEvent {
25
	private static final long serialVersionUID = 1L;
26
27
	/**
28
	 * The value property that changed
29
	 */
30
	public final IValueProperty property;
31
32
	/**
33
	 * ValueDiff with the old and new values of the property, or null if the
34
	 * change is unknown.
35
	 */
36
	public final ValueDiff diff;
37
38
	/**
39
	 * Constructs a ValuePropertyChangeEvent with the given attributes
40
	 * 
41
	 * @param source
42
	 *            the property source
43
	 * @param property
44
	 *            the property that changed on the source
45
	 * @param diff
46
	 *            a ValueDiff describing the changes to the value property
47
	 */
48
	public ValuePropertyChangeEvent(Object source, IValueProperty property,
49
			ValueDiff diff) {
50
		super(source);
51
		this.property = property;
52
		this.diff = diff;
53
	}
54
55
	protected void dispatch(IPropertyChangeListener listener) {
56
		((IValuePropertyChangeListener) listener)
57
				.handleValuePropertyChange(this);
58
	}
59
}
(-)src/org/eclipse/core/databinding/property/IProperty.java (+29 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.databinding.property;
13
14
/**
15
 * Marker interface for all property types in the properties framework.
16
 * 
17
 * @since 1.2
18
 * @noimplement This interface is not intended to be implemented by clients.
19
 */
20
public interface IProperty {
21
	/**
22
	 * Returns a string description of this property, suitable for debugging
23
	 * purposes
24
	 * 
25
	 * @return a string description of this property, suitable for debugging
26
	 *         purposes
27
	 */
28
	String toString();
29
}
(-)src/org/eclipse/core/databinding/property/list/SimpleListProperty.java (+597 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.databinding.property.list;
13
14
import java.util.ArrayList;
15
import java.util.Collection;
16
import java.util.Collections;
17
import java.util.Iterator;
18
import java.util.List;
19
import java.util.ListIterator;
20
21
import org.eclipse.core.databinding.observable.Diffs;
22
import org.eclipse.core.databinding.observable.IObservable;
23
import org.eclipse.core.databinding.observable.Realm;
24
import org.eclipse.core.databinding.observable.list.IObservableList;
25
import org.eclipse.core.databinding.observable.list.ListDiff;
26
import org.eclipse.core.databinding.observable.list.ListDiffEntry;
27
import org.eclipse.core.databinding.observable.masterdetail.IObservableFactory;
28
import org.eclipse.core.databinding.observable.masterdetail.MasterDetailObservables;
29
import org.eclipse.core.databinding.observable.value.IObservableValue;
30
import org.eclipse.core.databinding.property.INativePropertyListener;
31
32
/**
33
 * Simplified abstract implementation of IListProperty. This class takes care of
34
 * most of the functional requirements for an IListProperty implementation,
35
 * leaving only the property-specific details to subclasses.
36
 * <p>
37
 * Subclasses must implement these methods:
38
 * <ul>
39
 * <li> {@link #getList(Object)}
40
 * <li> {@link #setList(Object, List, ListDiff)}
41
 * <li> {@link #adaptListener(IListPropertyChangeListener)}
42
 * <li> {@link #addListener(Object, INativePropertyListener)}
43
 * <li> {@link #removeListener(Object, INativePropertyListener)}
44
 * <li> {@link #toString()}
45
 * </ul>
46
 * 
47
 * @since 1.2
48
 */
49
public abstract class SimpleListProperty extends ListProperty {
50
	private final Object elementType;
51
52
	protected SimpleListProperty(Object elementType) {
53
		this.elementType = elementType;
54
	}
55
56
	/**
57
	 * Returns the type of the elements in the collection or <code>null</code>
58
	 * if untyped
59
	 * 
60
	 * @return the type of the elements in the collection or <code>null</code>
61
	 *         if untyped
62
	 * @noreference This method is not intended to be referenced by clients.
63
	 */
64
	protected final Object getElementType() {
65
		return elementType;
66
	}
67
68
	/**
69
	 * Returns whether the source's collection property contains all elements in
70
	 * the given collection
71
	 * 
72
	 * @param source
73
	 *            the property source
74
	 * @param c
75
	 *            the collection of elements to test for
76
	 * @return whether the source's collection property contains all elements in
77
	 *         the given collection
78
	 * @noreference This method is not intended to be referenced by clients.
79
	 */
80
	protected boolean containsAll(Object source, Collection c) {
81
		return getList(source).containsAll(c);
82
	}
83
84
	/**
85
	 * Returns whether the source's collection property contains the given
86
	 * element.
87
	 * 
88
	 * @param source
89
	 *            the property source
90
	 * @param o
91
	 *            the element
92
	 * @return whether the source's collection property contains the given
93
	 *         element.
94
	 * @noreference This method is not intended to be referenced by clients.
95
	 */
96
	protected boolean contains(Object source, Object o) {
97
		return getList(source).contains(o);
98
	}
99
100
	/**
101
	 * Returns whether the source's collection property is equal to the
102
	 * argument.
103
	 * 
104
	 * @param source
105
	 *            the property source
106
	 * @param o
107
	 *            the object to test for equality to the source's collection
108
	 *            property
109
	 * @return whether the source's collection property is equal to the argument
110
	 * @noreference This method is not intended to be referenced by clients.
111
	 */
112
	protected boolean equals(Object source, Object o) {
113
		return getList(source).equals(o);
114
	}
115
116
	/**
117
	 * Returns the hash code of the source's collection property.
118
	 * 
119
	 * @param source
120
	 *            the property source
121
	 * @return the hash code of the source's collection property
122
	 * @noreference This method is not intended to be referenced by clients.
123
	 */
124
	protected int hashCode(Object source) {
125
		return getList(source).hashCode();
126
	}
127
128
	/**
129
	 * Returns whether the source's collection property is empty
130
	 * 
131
	 * @param source
132
	 *            the property source
133
	 * @return whether the source's collection property is empty
134
	 * @noreference This method is not intended to be referenced by clients.
135
	 */
136
	protected boolean isEmpty(Object source) {
137
		return getList(source).isEmpty();
138
	}
139
140
	/**
141
	 * Returns the size of the source's collection property
142
	 * 
143
	 * @param source
144
	 *            the property source
145
	 * @return the size of the source's collection property
146
	 * @noreference This method is not intended to be referenced by clients.
147
	 */
148
	protected int size(Object source) {
149
		return getList(source).size();
150
	}
151
152
	/**
153
	 * Returns an array of all elements in the source's collection property
154
	 * 
155
	 * @param source
156
	 *            the property source
157
	 * @param array
158
	 *            the array into which the elements will be copied. If the array
159
	 *            is not large enough to hold all elements, the elements will be
160
	 *            returned in a new array of the same runtime type.
161
	 * @return an array of all elements in the source's collection property
162
	 * @noreference This method is not intended to be referenced by clients.
163
	 */
164
	protected Object[] toArray(Object source, Object[] array) {
165
		return getList(source).toArray(array);
166
	}
167
168
	/**
169
	 * Returns an array of all elements in the source's collection property
170
	 * 
171
	 * @param source
172
	 *            the property source
173
	 * @return an array of all elements in the source's collection property
174
	 * @noreference This method is not intended to be referenced by clients.
175
	 */
176
	protected Object[] toArray(Object source) {
177
		return getList(source).toArray();
178
	}
179
180
	/**
181
	 * Returns a listener which implements the correct listener interface for
182
	 * the expected source object, and which parlays property change events from
183
	 * the source object to the given listener. If there is no listener API for
184
	 * this property, this method returns null.
185
	 * 
186
	 * @param listener
187
	 *            the property listener to receive events
188
	 * @return a native listener which parlays property change events to the
189
	 *         specified listener.
190
	 * @throws ClassCastException
191
	 *             if the provided listener does not implement the correct
192
	 *             listener interface (IValueProperty, IListProperty,
193
	 *             ISetProperty or IMapProperty) depending on the property.
194
	 * @noreference This method is not intended to be referenced by clients.
195
	 * @noreference This method is not intended to be referenced by clients.
196
	 */
197
	protected abstract INativePropertyListener adaptListener(
198
			IListPropertyChangeListener listener);
199
200
	/**
201
	 * Inserts the element into the source's list property at the specified
202
	 * position
203
	 * 
204
	 * @param source
205
	 *            the property source
206
	 * @param index
207
	 *            the insertion index
208
	 * @param element
209
	 *            the element to insert
210
	 * @noreference This method is not intended to be referenced by clients.
211
	 */
212
	protected void add(Object source, int index, Object element) {
213
		List list = new ArrayList(getList(source));
214
		list.add(index, element);
215
		setList(source, list, Diffs.createListDiff(Diffs.createListDiffEntry(
216
				index, true, element)));
217
	}
218
219
	/**
220
	 * Adds the element to the source's collection property
221
	 * 
222
	 * @param source
223
	 *            the property source
224
	 * @param o
225
	 *            the element to add
226
	 * @return whether the element was added to the source's collection property
227
	 * @noreference This method is not intended to be referenced by clients.
228
	 */
229
	protected boolean add(Object source, Object o) {
230
		add(source, size(source), o);
231
		return true;
232
	}
233
234
	/**
235
	 * Adds all elements in the specified collection to the source's collection
236
	 * property.
237
	 * 
238
	 * @param source
239
	 *            the property source
240
	 * @param c
241
	 *            the collection of elements to add.
242
	 * @return whether the source's collection property was changed
243
	 * @noreference This method is not intended to be referenced by clients.
244
	 */
245
	protected boolean addAll(Object source, Collection c) {
246
		if (c.isEmpty())
247
			return false;
248
		addAll(source, size(source), c);
249
		return true;
250
	}
251
252
	/**
253
	 * Inserts all elements in the specified collection into the source's list
254
	 * property at the specified index.
255
	 * 
256
	 * @param source
257
	 *            the property source
258
	 * @param index
259
	 *            the insertion index
260
	 * @param c
261
	 *            the collection of elements to add
262
	 * @return whether the source's list property was changed
263
	 * @noreference This method is not intended to be referenced by clients.
264
	 */
265
	protected boolean addAll(Object source, int index, Collection c) {
266
		if (c.isEmpty()) {
267
			return false;
268
		}
269
270
		List list = new ArrayList(getList(source));
271
		List entries = new ArrayList();
272
		int i = index;
273
		for (Iterator it = c.iterator(); it.hasNext(); i++) {
274
			Object o = it.next();
275
			list.add(i, o);
276
			entries.add(Diffs.createListDiffEntry(i, true, o));
277
		}
278
		boolean changed = !entries.isEmpty();
279
		if (changed) {
280
			ListDiffEntry[] ea = (ListDiffEntry[]) entries
281
					.toArray(new ListDiffEntry[entries.size()]);
282
			setList(source, list, Diffs.createListDiff(ea));
283
		}
284
		return changed;
285
	}
286
287
	/**
288
	 * Adds the specified listener as a listener for this property on the
289
	 * specified property source. If the source object has no listener API for
290
	 * this property (i.e. {@link #adaptListener(IListPropertyChangeListener)}
291
	 * returns null), this method does nothing.
292
	 * 
293
	 * @param source
294
	 *            the property source
295
	 * @param listener
296
	 *            a listener obtained from calling
297
	 *            {@link #adaptListener(IListPropertyChangeListener)}.
298
	 * @noreference This method is not intended to be referenced by clients.
299
	 */
300
	protected abstract void addListener(Object source,
301
			INativePropertyListener listener);
302
303
	/**
304
	 * Removes all elements from the source's collection property.
305
	 * 
306
	 * @param source
307
	 *            the property source
308
	 * @noreference This method is not intended to be referenced by clients.
309
	 */
310
	protected void clear(Object source) {
311
		if (!isEmpty(source)) {
312
			List list = getList(source);
313
			ListDiffEntry[] entries = new ListDiffEntry[list.size()];
314
			int i = 0;
315
			for (Iterator it = getList(source).iterator(); it.hasNext(); i++) {
316
				entries[i] = Diffs.createListDiffEntry(0, false, it.next());
317
			}
318
			setList(source, new ArrayList(), Diffs.createListDiff(entries));
319
		}
320
	}
321
322
	/**
323
	 * Returns the element at the specified position in the source's list
324
	 * property
325
	 * 
326
	 * @param source
327
	 *            the property source
328
	 * @param index
329
	 *            the element position
330
	 * @return the element at the given position in the source's list property
331
	 * @noreference This method is not intended to be referenced by clients.
332
	 */
333
	protected Object get(Object source, int index) {
334
		return getList(source).get(index);
335
	}
336
337
	/**
338
	 * Returns an unmodifiable List with the current contents of the source's
339
	 * list property
340
	 * 
341
	 * @param source
342
	 *            the property source
343
	 * @return an unmodifiable List with the current contents of the source's
344
	 *         list property
345
	 * @noreference This method is not intended to be referenced by clients.
346
	 */
347
	protected final List getList(Object source) {
348
		return Collections.unmodifiableList(doGetList(source));
349
	}
350
351
	/**
352
	 * Returns a List with the current contents of the source's list property
353
	 * 
354
	 * @param source
355
	 *            the property source
356
	 * @return a List with the current contents of the source's list property
357
	 * @noreference This method is not intended to be referenced by clients.
358
	 */
359
	protected abstract List doGetList(Object source);
360
361
	/**
362
	 * Returns the index of the first location of the given element in the
363
	 * source's list property, or -1 if the list does not contain the element.
364
	 * 
365
	 * @param source
366
	 *            the property source
367
	 * @param o
368
	 *            the element
369
	 * @return the index of the first location of the given element in the
370
	 *         source's list property, or -1 if the list does not contain the
371
	 *         element
372
	 * @noreference This method is not intended to be referenced by clients.
373
	 */
374
	protected int indexOf(Object source, Object o) {
375
		return getList(source).indexOf(o);
376
	}
377
378
	/**
379
	 * Returns the index of the last location of the given element in the
380
	 * source's list property, or -1 if the list does not contain the given
381
	 * element.
382
	 * 
383
	 * @param source
384
	 * @param o
385
	 * @return the index of the last location of the given element in the
386
	 *         source's list property, or -1 if the list does not contain the
387
	 *         element
388
	 * @noreference This method is not intended to be referenced by clients.
389
	 */
390
	protected int lastIndexOf(Object source, Object o) {
391
		return getList(source).lastIndexOf(o);
392
	}
393
394
	/**
395
	 * Moves the element at the specified old position in the source's list
396
	 * property to the specified new position
397
	 * 
398
	 * @param source
399
	 *            the property source
400
	 * @param oldIndex
401
	 *            the old element position
402
	 * @param newIndex
403
	 *            the new element position
404
	 * @return the element that was moved
405
	 * @noreference This method is not intended to be referenced by clients.
406
	 */
407
	protected Object move(Object source, int oldIndex, int newIndex) {
408
		if (oldIndex == newIndex)
409
			return get(source, oldIndex);
410
		List list = new ArrayList(getList(source));
411
		Object result = list.remove(oldIndex);
412
		list.add(newIndex, result);
413
		setList(source, list, Diffs.createListDiff(Diffs.createListDiffEntry(
414
				oldIndex, false, result), Diffs.createListDiffEntry(newIndex,
415
				true, result)));
416
		return result;
417
	}
418
419
	public IObservableList observeList(Realm realm, Object source) {
420
		return new SimpleListPropertyObservableList(realm, source, this);
421
	}
422
423
	public IObservableList observeDetailList(IObservableValue master) {
424
		final Realm realm = master.getRealm();
425
		return MasterDetailObservables.detailList(master,
426
				new IObservableFactory() {
427
					public IObservable createObservable(Object target) {
428
						return observeList(realm, target);
429
					}
430
				}, getElementType());
431
	}
432
433
	/**
434
	 * Removes the element from the source's list property which is located at
435
	 * the specified position
436
	 * 
437
	 * @param source
438
	 *            the property source
439
	 * @param index
440
	 *            the index of the element to remove
441
	 * @return the element that was removed from the source's list property
442
	 * @noreference This method is not intended to be referenced by clients.
443
	 */
444
	protected Object remove(Object source, int index) {
445
		List list = new ArrayList(getList(source));
446
		Object result = list.remove(index);
447
		setList(source, list, Diffs.createListDiff(Diffs.createListDiffEntry(
448
				index, false, result)));
449
		return result;
450
	}
451
452
	/**
453
	 * Removes the element from the source's collection property
454
	 * 
455
	 * @param source
456
	 *            the property source
457
	 * @param o
458
	 *            the element to remove
459
	 * @return whether the element was removed from the source's collection
460
	 *         property
461
	 * @noreference This method is not intended to be referenced by clients.
462
	 */
463
	protected boolean remove(Object source, Object o) {
464
		int i = indexOf(source, o);
465
		if (i == -1)
466
			return false;
467
		remove(source, i);
468
		return true;
469
	}
470
471
	/**
472
	 * Removes all elements from the source's collection property which are
473
	 * contained in the specified collection.
474
	 * 
475
	 * @param source
476
	 *            the property source
477
	 * @param c
478
	 *            the collection of elements to be removed
479
	 * @return whether the source's collection property was changed
480
	 * @noreference This method is not intended to be referenced by clients.
481
	 */
482
	protected boolean removeAll(Object source, Collection c) {
483
		if (isEmpty(source)) {
484
			return false;
485
		}
486
		if (c.isEmpty()) {
487
			return false;
488
		}
489
		List list = new ArrayList(getList(source));
490
		List entries = new ArrayList();
491
		for (ListIterator it = list.listIterator(); it.hasNext();) {
492
			Object o = it.next();
493
			if (c.contains(o)) {
494
				entries.add(Diffs.createListDiffEntry(it.previousIndex(),
495
						false, o));
496
				it.remove();
497
			}
498
		}
499
		boolean changed = !entries.isEmpty();
500
		if (changed) {
501
			ListDiffEntry[] ea = (ListDiffEntry[]) entries
502
					.toArray(new ListDiffEntry[entries.size()]);
503
			setList(source, list, Diffs.createListDiff(ea));
504
		}
505
		return changed;
506
	}
507
508
	/**
509
	 * Removes the specified listener as a listener for this property on the
510
	 * specified property source. If the source object has no listener API for
511
	 * this property (i.e. {@link #adaptListener(IListPropertyChangeListener)}
512
	 * returns null), this method does nothing.
513
	 * 
514
	 * @param source
515
	 *            the property source
516
	 * @param listener
517
	 *            a listener obtained from calling
518
	 *            {@link #adaptListener(IListPropertyChangeListener)}.
519
	 * @noreference This method is not intended to be referenced by clients.
520
	 */
521
	protected abstract void removeListener(Object source,
522
			INativePropertyListener listener);
523
524
	/**
525
	 * Removes all elements from the source's collection property which are not
526
	 * contained in the specified collection.
527
	 * 
528
	 * @param source
529
	 *            the property source
530
	 * @param c
531
	 *            the collection of elements to retain
532
	 * @return whether the source's collection property was changed
533
	 * @noreference This method is not intended to be referenced by clients.
534
	 */
535
	protected boolean retainAll(Object source, Collection c) {
536
		if (isEmpty(source)) {
537
			return false;
538
		}
539
		if (c.isEmpty()) {
540
			clear(source);
541
			return true;
542
		}
543
		List list = new ArrayList(getList(source));
544
		List entries = new ArrayList();
545
		for (ListIterator it = list.listIterator(); it.hasNext();) {
546
			Object o = it.next();
547
			if (!c.contains(o)) {
548
				entries.add(Diffs.createListDiffEntry(it.previousIndex(),
549
						false, o));
550
				it.remove();
551
			}
552
		}
553
		boolean changed = !entries.isEmpty();
554
		if (changed) {
555
			ListDiffEntry[] ea = (ListDiffEntry[]) entries
556
					.toArray(new ListDiffEntry[entries.size()]);
557
			setList(source, list, Diffs.createListDiff(ea));
558
		}
559
		return changed;
560
	}
561
562
	/**
563
	 * Replaces the element at the specified position in the source's list
564
	 * property with the given element.
565
	 * 
566
	 * @param source
567
	 *            the property source
568
	 * @param index
569
	 *            the element position
570
	 * @param element
571
	 *            the replacement element
572
	 * @return the element previously at the specified position in the source's
573
	 *         list property
574
	 * @noreference This method is not intended to be referenced by clients.
575
	 */
576
	protected Object set(Object source, int index, Object element) {
577
		List list = new ArrayList(getList(source));
578
		Object result = list.set(index, element);
579
		setList(source, list, Diffs.createListDiff(Diffs.createListDiffEntry(
580
				index, false, result), Diffs.createListDiffEntry(index, true,
581
				element)));
582
		return result;
583
	}
584
585
	/**
586
	 * Updates the property on the source with the specified change.
587
	 * 
588
	 * @param source
589
	 *            the property source
590
	 * @param list
591
	 *            the new list
592
	 * @param diff
593
	 *            a diff describing the change
594
	 * @noreference This method is not intended to be referenced by clients.
595
	 */
596
	protected abstract void setList(Object source, List list, ListDiff diff);
597
}
(-)src/org/eclipse/core/databinding/property/IPropertyObservable.java (+28 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.databinding.property;
13
14
import org.eclipse.core.databinding.observable.IObserving;
15
16
/**
17
 * Provides access to the details of property observables
18
 * 
19
 * @since 1.2
20
 */
21
public interface IPropertyObservable extends IObserving {
22
	/**
23
	 * Returns the property being observed
24
	 * 
25
	 * @return the property being observed
26
	 */
27
	IProperty getProperty();
28
}
(-)src/org/eclipse/core/databinding/property/set/SetPropertyChangeEvent.java (+58 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.databinding.property.set;
13
14
import org.eclipse.core.databinding.observable.set.SetDiff;
15
import org.eclipse.core.databinding.property.IPropertyChangeListener;
16
import org.eclipse.core.databinding.property.PropertyChangeEvent;
17
18
/**
19
 * Set change event describing an incremental change of a set property on a
20
 * particular property source.
21
 * 
22
 * @since 1.2
23
 */
24
public class SetPropertyChangeEvent extends PropertyChangeEvent {
25
	private static final long serialVersionUID = 1L;
26
27
	/**
28
	 * The set property that changed
29
	 */
30
	public final ISetProperty property;
31
32
	/**
33
	 * SetDiff enumerating the added and removed elements in the set, or null if
34
	 * the change is unknown.
35
	 */
36
	public final SetDiff diff;
37
38
	/**
39
	 * Constructs a SetPropertyChangeEvent with the given attributes
40
	 * 
41
	 * @param source
42
	 *            the property source
43
	 * @param property
44
	 *            the property that changed on the source
45
	 * @param diff
46
	 *            a SetDiff describing the changes to the set property
47
	 */
48
	public SetPropertyChangeEvent(Object source, ISetProperty property,
49
			SetDiff diff) {
50
		super(source);
51
		this.property = property;
52
		this.diff = diff;
53
	}
54
55
	protected void dispatch(IPropertyChangeListener listener) {
56
		((ISetPropertyChangeListener) listener).handleSetPropertyChange(this);
57
	}
58
}
(-)src/org/eclipse/core/internal/databinding/property/MapPropertyDetailValuesMap.java (+52 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.internal.databinding.property;
13
14
import org.eclipse.core.databinding.observable.Realm;
15
import org.eclipse.core.databinding.observable.map.IObservableMap;
16
import org.eclipse.core.databinding.observable.value.IObservableValue;
17
import org.eclipse.core.databinding.property.map.IMapProperty;
18
import org.eclipse.core.databinding.property.map.MapProperty;
19
import org.eclipse.core.databinding.property.value.IValueProperty;
20
21
/**
22
 * @since 3.3
23
 * 
24
 */
25
public class MapPropertyDetailValuesMap extends MapProperty {
26
	private final IMapProperty masterProperty;
27
	private final IValueProperty detailProperty;
28
29
	/**
30
	 * @param masterProperty
31
	 * @param detailProperty
32
	 */
33
	public MapPropertyDetailValuesMap(IMapProperty masterProperty,
34
			IValueProperty detailProperty) {
35
		this.masterProperty = masterProperty;
36
		this.detailProperty = detailProperty;
37
	}
38
39
	public IObservableMap observeMap(Realm realm, Object source) {
40
		IObservableMap master = masterProperty.observeMap(realm, source);
41
		return detailProperty.observeDetailValues(master);
42
	}
43
44
	public IObservableMap observeDetailMap(IObservableValue master) {
45
		IObservableMap masterMap = masterProperty.observeDetailMap(master);
46
		return detailProperty.observeDetailValues(masterMap);
47
	}
48
49
	public String toString() {
50
		return masterProperty + " => " + detailProperty; //$NON-NLS-1$
51
	}
52
}
(-)src/org/eclipse/core/databinding/property/list/SimpleListPropertyObservableList.java (+639 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.databinding.property.list;
13
14
import java.util.ArrayList;
15
import java.util.Collection;
16
import java.util.Collections;
17
import java.util.ConcurrentModificationException;
18
import java.util.Iterator;
19
import java.util.List;
20
import java.util.ListIterator;
21
22
import org.eclipse.core.databinding.observable.Diffs;
23
import org.eclipse.core.databinding.observable.ObservableTracker;
24
import org.eclipse.core.databinding.observable.Realm;
25
import org.eclipse.core.databinding.observable.list.AbstractObservableList;
26
import org.eclipse.core.databinding.observable.list.ListDiff;
27
import org.eclipse.core.databinding.observable.list.ListDiffEntry;
28
import org.eclipse.core.databinding.property.IProperty;
29
import org.eclipse.core.databinding.property.INativePropertyListener;
30
import org.eclipse.core.databinding.property.IPropertyObservable;
31
32
/**
33
 * @since 1.2
34
 * 
35
 */
36
class SimpleListPropertyObservableList extends AbstractObservableList implements
37
		IPropertyObservable {
38
	private Object source;
39
	private SimpleListProperty property;
40
41
	private volatile boolean updating = false;
42
43
	private volatile int modCount = 0;
44
45
	private INativePropertyListener listener;
46
47
	private List cachedList;
48
49
	/**
50
	 * @param realm
51
	 * @param source
52
	 * @param property
53
	 */
54
	public SimpleListPropertyObservableList(Realm realm, Object source,
55
			SimpleListProperty property) {
56
		super(realm);
57
		this.source = source;
58
		this.property = property;
59
	}
60
61
	protected void firstListenerAdded() {
62
		if (!isDisposed()) {
63
			cachedList = property.getList(source);
64
65
			if (listener == null) {
66
				listener = property
67
						.adaptListener(new IListPropertyChangeListener() {
68
							public void handleListPropertyChange(
69
									final ListPropertyChangeEvent event) {
70
								modCount++;
71
								if (!isDisposed() && !updating) {
72
									getRealm().exec(new Runnable() {
73
										public void run() {
74
											List oldList = cachedList;
75
											List newList = cachedList = property
76
													.getList(source);
77
											ListDiff diff = event.diff;
78
											if (diff == null) {
79
												diff = Diffs.computeListDiff(
80
														oldList, newList);
81
											}
82
											fireListChange(diff);
83
										}
84
									});
85
								}
86
							}
87
						});
88
			}
89
			property.addListener(source, listener);
90
		}
91
	}
92
93
	protected void lastListenerRemoved() {
94
		if (listener != null) {
95
			property.removeListener(source, listener);
96
		}
97
98
		cachedList = null;
99
	}
100
101
	private void getterCalled() {
102
		ObservableTracker.getterCalled(this);
103
	}
104
105
	public Object getElementType() {
106
		return property.getElementType();
107
	}
108
109
	// Queries
110
111
	protected int doGetSize() {
112
		return property.size(source);
113
	}
114
115
	public boolean contains(Object o) {
116
		getterCalled();
117
		return property.contains(source, o);
118
	}
119
120
	public boolean containsAll(Collection c) {
121
		getterCalled();
122
		return property.containsAll(source, c);
123
	}
124
125
	public Object get(int index) {
126
		getterCalled();
127
		return property.get(source, index);
128
	}
129
130
	public int indexOf(Object o) {
131
		getterCalled();
132
		return property.indexOf(source, o);
133
	}
134
135
	public boolean isEmpty() {
136
		getterCalled();
137
		return property.isEmpty(source);
138
	}
139
140
	public int lastIndexOf(Object o) {
141
		getterCalled();
142
		return property.lastIndexOf(source, o);
143
	}
144
145
	public Object[] toArray() {
146
		getterCalled();
147
		return property.toArray(source);
148
	}
149
150
	public Object[] toArray(Object[] a) {
151
		getterCalled();
152
		return property.toArray(source, a);
153
	}
154
155
	// Single change operations
156
157
	public boolean add(Object o) {
158
		checkRealm();
159
		add(property.size(source), o);
160
		return true;
161
	}
162
163
	public void add(int index, Object o) {
164
		checkRealm();
165
		boolean wasUpdating = updating;
166
		updating = true;
167
		try {
168
			property.add(source, index, o);
169
			modCount++;
170
		} finally {
171
			updating = wasUpdating;
172
		}
173
174
		cachedList = property.getList(source);
175
		fireListChange(Diffs.createListDiff(Diffs.createListDiffEntry(index,
176
				true, o)));
177
	}
178
179
	public Iterator iterator() {
180
		getterCalled();
181
		return new Iterator() {
182
			int expectedModCount = modCount;
183
			ListIterator delegate = new ArrayList(property.getList(source))
184
					.listIterator();
185
186
			Object lastElement = null;
187
			int lastIndex = -1;
188
189
			public boolean hasNext() {
190
				getterCalled();
191
				checkForComodification();
192
				return delegate.hasNext();
193
			}
194
195
			public Object next() {
196
				getterCalled();
197
				checkForComodification();
198
				Object next = lastElement = delegate.next();
199
				lastIndex = delegate.previousIndex();
200
				return next;
201
			}
202
203
			public void remove() {
204
				checkRealm();
205
				checkForComodification();
206
				if (lastIndex == -1)
207
					throw new IllegalStateException();
208
209
				delegate.remove(); // stay in sync
210
211
				boolean wasUpdating = updating;
212
				updating = true;
213
				try {
214
					property.remove(source, lastIndex);
215
					modCount++;
216
				} finally {
217
					updating = wasUpdating;
218
				}
219
220
				cachedList = property.getList(source);
221
				fireListChange(Diffs.createListDiff(Diffs.createListDiffEntry(
222
						lastIndex, false, lastElement)));
223
224
				lastElement = null;
225
				lastIndex = -1;
226
227
				expectedModCount = modCount;
228
			}
229
230
			private void checkForComodification() {
231
				if (expectedModCount != modCount)
232
					throw new ConcurrentModificationException();
233
			}
234
		};
235
	}
236
237
	public Object move(int oldIndex, int newIndex) {
238
		checkRealm();
239
240
		int size = property.size(source);
241
		if (oldIndex < 0 || oldIndex >= size || newIndex < 0
242
				|| newIndex >= size)
243
			throw new IndexOutOfBoundsException();
244
		if (oldIndex == newIndex)
245
			return property.get(source, oldIndex);
246
247
		Object element;
248
249
		boolean wasUpdating = updating;
250
		updating = true;
251
		try {
252
			element = property.move(source, oldIndex, newIndex);
253
			modCount++;
254
		} finally {
255
			updating = wasUpdating;
256
		}
257
258
		cachedList = property.getList(source);
259
		fireListChange(Diffs.createListDiff(Diffs.createListDiffEntry(oldIndex,
260
				false, element), Diffs.createListDiffEntry(newIndex, true,
261
				element)));
262
263
		return element;
264
	}
265
266
	public boolean remove(Object o) {
267
		checkRealm();
268
269
		int index = property.indexOf(source, o);
270
		if (index == -1)
271
			return false;
272
273
		remove(index);
274
275
		return true;
276
	}
277
278
	public ListIterator listIterator() {
279
		return listIterator(0);
280
	}
281
282
	public ListIterator listIterator(final int index) {
283
		getterCalled();
284
		return new ListIterator() {
285
			int expectedModCount = modCount;
286
			ListIterator delegate = new ArrayList(property.getList(source))
287
					.listIterator(index);
288
289
			Object lastElement = null;
290
			int lastIndex = -1;
291
292
			public boolean hasNext() {
293
				getterCalled();
294
				checkForComodification();
295
				return delegate.hasNext();
296
			}
297
298
			public int nextIndex() {
299
				getterCalled();
300
				checkForComodification();
301
				return delegate.nextIndex();
302
			}
303
304
			public Object next() {
305
				getterCalled();
306
				checkForComodification();
307
				lastElement = delegate.next();
308
				lastIndex = delegate.previousIndex();
309
				return lastElement;
310
			}
311
312
			public boolean hasPrevious() {
313
				getterCalled();
314
				checkForComodification();
315
				return delegate.hasPrevious();
316
			}
317
318
			public int previousIndex() {
319
				getterCalled();
320
				checkForComodification();
321
				return delegate.previousIndex();
322
			}
323
324
			public Object previous() {
325
				getterCalled();
326
				checkForComodification();
327
				lastElement = delegate.previous();
328
				lastIndex = delegate.nextIndex();
329
				return lastElement;
330
			}
331
332
			public void add(Object o) {
333
				checkRealm();
334
				checkForComodification();
335
				int index = delegate.nextIndex();
336
337
				delegate.add(o); // keep in sync
338
339
				boolean wasUpdating = updating;
340
				updating = true;
341
				try {
342
					property.add(source, index, o);
343
					modCount++;
344
				} finally {
345
					updating = wasUpdating;
346
				}
347
348
				cachedList = property.getList(source);
349
				fireListChange(Diffs.createListDiff(Diffs.createListDiffEntry(
350
						index, true, o)));
351
352
				lastElement = null;
353
				lastIndex = -1;
354
				expectedModCount = modCount;
355
			}
356
357
			public void set(Object o) {
358
				checkRealm();
359
				checkForComodification();
360
361
				delegate.set(o);
362
363
				boolean wasUpdating = updating;
364
				updating = true;
365
				try {
366
					property.set(source, lastIndex, o);
367
					modCount++;
368
				} finally {
369
					updating = wasUpdating;
370
				}
371
372
				cachedList = property.getList(source);
373
				fireListChange(Diffs.createListDiff(Diffs.createListDiffEntry(
374
						lastIndex, false, lastElement), Diffs
375
						.createListDiffEntry(lastIndex, true, o)));
376
377
				lastElement = o;
378
379
				expectedModCount = modCount;
380
			}
381
382
			public void remove() {
383
				checkRealm();
384
				checkForComodification();
385
				if (lastIndex == -1)
386
					throw new IllegalStateException();
387
388
				delegate.remove(); // keep in sync
389
390
				boolean wasUpdating = updating;
391
				updating = true;
392
				try {
393
					property.remove(source, lastIndex);
394
					modCount++;
395
				} finally {
396
					updating = wasUpdating;
397
				}
398
399
				cachedList = property.getList(source);
400
				fireListChange(Diffs.createListDiff(Diffs.createListDiffEntry(
401
						lastIndex, false, lastElement)));
402
403
				lastElement = null;
404
				lastIndex = -1;
405
				expectedModCount = modCount;
406
			}
407
408
			private void checkForComodification() {
409
				if (expectedModCount != modCount)
410
					throw new ConcurrentModificationException();
411
			}
412
		};
413
	}
414
415
	public Object remove(int index) {
416
		checkRealm();
417
418
		Object element;
419
420
		boolean wasUpdating = updating;
421
		updating = true;
422
		try {
423
			element = property.remove(source, index);
424
			modCount++;
425
		} finally {
426
			updating = wasUpdating;
427
		}
428
429
		cachedList = property.getList(source);
430
		fireListChange(Diffs.createListDiff(Diffs.createListDiffEntry(index,
431
				false, element)));
432
433
		return element;
434
	}
435
436
	public Object set(int index, Object o) {
437
		checkRealm();
438
439
		Object oldElement;
440
441
		boolean wasUpdating = updating;
442
		updating = true;
443
		try {
444
			oldElement = property.set(source, index, o);
445
			modCount++;
446
		} finally {
447
			updating = wasUpdating;
448
		}
449
450
		cachedList = property.getList(source);
451
		fireListChange(Diffs.createListDiff(Diffs.createListDiffEntry(index,
452
				false, oldElement), Diffs.createListDiffEntry(index, true, o)));
453
454
		return oldElement;
455
	}
456
457
	public List subList(int fromIndex, int toIndex) {
458
		getterCalled();
459
		return Collections.unmodifiableList(property.getList(source).subList(
460
				fromIndex, toIndex));
461
	}
462
463
	// Bulk change operations
464
465
	public boolean addAll(Collection c) {
466
		checkRealm();
467
468
		return addAll(property.size(source), c);
469
	}
470
471
	public boolean addAll(int index, Collection c) {
472
		checkRealm();
473
474
		if (c.isEmpty())
475
			return false;
476
477
		ListDiffEntry[] entries = new ListDiffEntry[c.size()];
478
		int offsetIndex = 0;
479
		for (Iterator it = c.iterator(); it.hasNext();) {
480
			Object element = it.next();
481
			entries[offsetIndex] = Diffs.createListDiffEntry(index
482
					+ offsetIndex, true, element);
483
			offsetIndex++;
484
		}
485
486
		boolean changed;
487
488
		boolean wasUpdating = updating;
489
		updating = true;
490
		try {
491
			changed = property.addAll(source, index, c);
492
			modCount++;
493
		} finally {
494
			updating = wasUpdating;
495
		}
496
497
		cachedList = property.getList(source);
498
		if (changed)
499
			fireListChange(Diffs.createListDiff(entries));
500
501
		return changed;
502
	}
503
504
	public boolean removeAll(Collection c) {
505
		checkRealm();
506
507
		if (property.isEmpty(source) || c.isEmpty())
508
			return false;
509
510
		boolean changed;
511
512
		List entries = new ArrayList();
513
514
		boolean wasUpdating = updating;
515
		updating = true;
516
		try {
517
			List list = new ArrayList(property.getList(source));
518
			for (ListIterator it = list.listIterator(); it.hasNext();) {
519
				Object element = it.next();
520
				int index = it.previousIndex();
521
				if (c.contains(element)) {
522
					it.remove();
523
					entries.add(Diffs
524
							.createListDiffEntry(index, false, element));
525
				}
526
			}
527
			changed = property.removeAll(source, c);
528
			modCount++;
529
		} finally {
530
			updating = wasUpdating;
531
		}
532
533
		cachedList = property.getList(source);
534
535
		if (changed)
536
			fireListChange(Diffs.createListDiff((ListDiffEntry[]) entries
537
					.toArray(new ListDiffEntry[entries.size()])));
538
539
		return changed;
540
	}
541
542
	public boolean retainAll(Collection c) {
543
		checkRealm();
544
545
		if (property.isEmpty(source))
546
			return false;
547
548
		if (c.isEmpty()) {
549
			clear();
550
			return true;
551
		}
552
553
		boolean changed;
554
555
		List entries = new ArrayList();
556
557
		boolean wasUpdating = updating;
558
		updating = true;
559
		try {
560
			List list = new ArrayList(property.getList(source));
561
			for (ListIterator it = list.listIterator(); it.hasNext();) {
562
				Object element = it.next();
563
				int index = it.previousIndex();
564
				if (!c.contains(element)) {
565
					it.remove();
566
					entries.add(Diffs
567
							.createListDiffEntry(index, false, element));
568
				}
569
			}
570
			changed = property.retainAll(source, c);
571
			modCount++;
572
		} finally {
573
			updating = wasUpdating;
574
		}
575
576
		cachedList = property.getList(source);
577
578
		if (changed)
579
			fireListChange(Diffs.createListDiff((ListDiffEntry[]) entries
580
					.toArray(new ListDiffEntry[entries.size()])));
581
582
		return changed;
583
	}
584
585
	public void clear() {
586
		checkRealm();
587
588
		if (property.isEmpty(source))
589
			return;
590
591
		List entries = new ArrayList();
592
		for (Iterator it = property.getList(source).iterator(); it.hasNext();) {
593
			// always report 0 as the remove index
594
			entries.add(Diffs.createListDiffEntry(0, false, it.next()));
595
		}
596
597
		boolean wasUpdating = updating;
598
		updating = true;
599
		try {
600
			property.clear(source);
601
			modCount++;
602
		} finally {
603
			updating = wasUpdating;
604
		}
605
606
		cachedList = property.getList(source);
607
		fireListChange(Diffs.createListDiff((ListDiffEntry[]) entries
608
				.toArray(new ListDiffEntry[entries.size()])));
609
	}
610
611
	public boolean equals(Object o) {
612
		getterCalled();
613
		return property.equals(source, o);
614
	}
615
616
	public int hashCode() {
617
		getterCalled();
618
		return property.hashCode(source);
619
	}
620
621
	public Object getObserved() {
622
		return source;
623
	}
624
625
	public IProperty getProperty() {
626
		return property;
627
	}
628
629
	public synchronized void dispose() {
630
		if (!isDisposed()) {
631
			if (listener != null)
632
				property.removeListener(source, listener);
633
			property = null;
634
			source = null;
635
			listener = null;
636
		}
637
		super.dispose();
638
	}
639
}
(-)src/org/eclipse/core/databinding/property/value/IValuePropertyChangeListener.java (+29 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.databinding.property.value;
13
14
import org.eclipse.core.databinding.property.IPropertyChangeListener;
15
16
/**
17
 * Listener for changes to value properties on a property source
18
 * 
19
 * @since 1.2
20
 */
21
public interface IValuePropertyChangeListener extends IPropertyChangeListener {
22
	/**
23
	 * Handle a change to a value property on a specific property source.
24
	 * 
25
	 * @param event
26
	 *            an event describing the value change that occured.
27
	 */
28
	public void handleValuePropertyChange(ValuePropertyChangeEvent event);
29
}
(-)src/org/eclipse/core/internal/databinding/property/ListPropertyDetailValuesList.java (+52 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.internal.databinding.property;
13
14
import org.eclipse.core.databinding.observable.Realm;
15
import org.eclipse.core.databinding.observable.list.IObservableList;
16
import org.eclipse.core.databinding.observable.value.IObservableValue;
17
import org.eclipse.core.databinding.property.list.IListProperty;
18
import org.eclipse.core.databinding.property.list.ListProperty;
19
import org.eclipse.core.databinding.property.value.IValueProperty;
20
21
/**
22
 * @since 3.3
23
 * 
24
 */
25
public class ListPropertyDetailValuesList extends ListProperty {
26
	private final IListProperty masterProperty;
27
	private final IValueProperty detailProperty;
28
29
	/**
30
	 * @param masterProperty
31
	 * @param detailProperty
32
	 */
33
	public ListPropertyDetailValuesList(IListProperty masterProperty,
34
			IValueProperty detailProperty) {
35
		this.masterProperty = masterProperty;
36
		this.detailProperty = detailProperty;
37
	}
38
39
	public IObservableList observeList(Realm realm, Object source) {
40
		IObservableList master = masterProperty.observeList(realm, source);
41
		return detailProperty.observeDetailValues(master);
42
	}
43
44
	public IObservableList observeDetailList(IObservableValue master) {
45
		IObservableList masterList = masterProperty.observeDetailList(master);
46
		return detailProperty.observeDetailValues(masterList);
47
	}
48
49
	public String toString() {
50
		return masterProperty + " => " + detailProperty; //$NON-NLS-1$
51
	}
52
}
(-)src/org/eclipse/core/databinding/property/value/ObservableSetSimpleValuePropertyObservableMap.java (+142 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.databinding.property.value;
13
14
import java.util.HashMap;
15
import java.util.Iterator;
16
import java.util.Map;
17
18
import org.eclipse.core.databinding.observable.Diffs;
19
import org.eclipse.core.databinding.observable.IObserving;
20
import org.eclipse.core.databinding.observable.map.ComputedObservableMap;
21
import org.eclipse.core.databinding.observable.set.IObservableSet;
22
import org.eclipse.core.databinding.observable.value.ValueDiff;
23
import org.eclipse.core.databinding.property.INativePropertyListener;
24
25
/**
26
 * @since 1.2
27
 */
28
class ObservableSetSimpleValuePropertyObservableMap extends
29
		ComputedObservableMap implements IObserving {
30
	private SimpleValueProperty detailProperty;
31
32
	private INativePropertyListener listener;
33
34
	private Map cachedValues;
35
36
	private boolean updating;
37
38
	/**
39
	 * @param keySet
40
	 * @param valueProperty
41
	 */
42
	public ObservableSetSimpleValuePropertyObservableMap(IObservableSet keySet,
43
			SimpleValueProperty valueProperty) {
44
		super(keySet);
45
		this.detailProperty = valueProperty;
46
	}
47
48
	protected void firstListenerAdded() {
49
		if (listener == null) {
50
			cachedValues = new HashMap(this);
51
52
			listener = detailProperty
53
					.adaptListener(new IValuePropertyChangeListener() {
54
						public void handleValuePropertyChange(
55
								final ValuePropertyChangeEvent event) {
56
							if (!isDisposed() && !updating) {
57
								getRealm().exec(new Runnable() {
58
									public void run() {
59
										Object key = event.getSource();
60
										Object oldValue;
61
										Object newValue;
62
63
										ValueDiff diff = event.diff;
64
										if (diff == null) {
65
											oldValue = cachedValues.get(key);
66
											newValue = detailProperty
67
													.getValue(key);
68
										} else {
69
											oldValue = event.diff.getOldValue();
70
											newValue = event.diff.getNewValue();
71
										}
72
73
										cachedValues.put(key, newValue);
74
										fireMapChange(Diffs
75
												.createMapDiffSingleChange(key,
76
														oldValue, newValue));
77
									}
78
								});
79
							}
80
						}
81
					});
82
		}
83
		super.firstListenerAdded();
84
	}
85
86
	protected void lastListenerRemoved() {
87
		super.lastListenerRemoved();
88
	}
89
90
	protected void hookListener(Object addedKey) {
91
		if (listener != null) {
92
			detailProperty.addListener(addedKey, listener);
93
		}
94
	}
95
96
	protected void unhookListener(Object removedKey) {
97
		if (listener != null) {
98
			detailProperty.removeListener(removedKey, listener);
99
		}
100
	}
101
102
	protected Object doGet(Object key) {
103
		return detailProperty.getValue(key);
104
	}
105
106
	protected Object doPut(Object key, Object value) {
107
		Object oldValue = detailProperty.getValue(key);
108
109
		updating = true;
110
		try {
111
			detailProperty.setValue(key, value);
112
		} finally {
113
			updating = false;
114
		}
115
		Object newValue = detailProperty.getValue(key);
116
		cachedValues.put(key, newValue);
117
118
		if (oldValue != newValue) {
119
			fireMapChange(Diffs.createMapDiffSingleChange(key, oldValue,
120
					newValue));
121
		}
122
		return oldValue;
123
	}
124
125
	public Object getObserved() {
126
		return keySet();
127
	}
128
129
	public synchronized void dispose() {
130
		if (!isDisposed()) {
131
			if (listener != null) {
132
				for (Iterator it = values().iterator(); it.hasNext();) {
133
					unhookListener(it.next());
134
				}
135
				listener = null;
136
			}
137
			detailProperty = null;
138
		}
139
140
		super.dispose();
141
	}
142
}
(-)src/org/eclipse/core/internal/databinding/property/SetPropertyDetailValuesMap.java (+53 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.internal.databinding.property;
13
14
import org.eclipse.core.databinding.observable.Realm;
15
import org.eclipse.core.databinding.observable.map.IObservableMap;
16
import org.eclipse.core.databinding.observable.set.IObservableSet;
17
import org.eclipse.core.databinding.observable.value.IObservableValue;
18
import org.eclipse.core.databinding.property.map.MapProperty;
19
import org.eclipse.core.databinding.property.set.ISetProperty;
20
import org.eclipse.core.databinding.property.value.IValueProperty;
21
22
/**
23
 * @since 3.3
24
 * 
25
 */
26
public class SetPropertyDetailValuesMap extends MapProperty {
27
	private final ISetProperty masterProperty;
28
	private final IValueProperty detailProperty;
29
30
	/**
31
	 * @param masterProperty
32
	 * @param detailProperty
33
	 */
34
	public SetPropertyDetailValuesMap(ISetProperty masterProperty,
35
			IValueProperty detailProperty) {
36
		this.masterProperty = masterProperty;
37
		this.detailProperty = detailProperty;
38
	}
39
40
	public IObservableMap observeMap(Realm realm, Object source) {
41
		IObservableSet master = masterProperty.observeSet(realm, source);
42
		return detailProperty.observeDetailValues(master);
43
	}
44
45
	public IObservableMap observeDetailMap(IObservableValue master) {
46
		IObservableSet masterSet = masterProperty.observeDetailSet(master);
47
		return detailProperty.observeDetailValues(masterSet);
48
	}
49
50
	public String toString() {
51
		return masterProperty + " => " + detailProperty; //$NON-NLS-1$
52
	}
53
}
(-)src/org/eclipse/core/databinding/property/value/SimpleValuePropertyObservableValue.java (+146 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.databinding.property.value;
13
14
import org.eclipse.core.databinding.observable.Diffs;
15
import org.eclipse.core.databinding.observable.Realm;
16
import org.eclipse.core.databinding.observable.value.AbstractObservableValue;
17
import org.eclipse.core.databinding.observable.value.ValueDiff;
18
import org.eclipse.core.databinding.property.IProperty;
19
import org.eclipse.core.databinding.property.INativePropertyListener;
20
import org.eclipse.core.databinding.property.IPropertyObservable;
21
import org.eclipse.core.internal.databinding.Util;
22
23
/**
24
 * @since 1.2
25
 * 
26
 */
27
class SimpleValuePropertyObservableValue extends AbstractObservableValue
28
		implements IPropertyObservable {
29
	private Object source;
30
	private SimpleValueProperty property;
31
32
	private boolean updating = false;
33
	private Object cachedValue;
34
35
	private INativePropertyListener listener;
36
37
	/**
38
	 * @param realm
39
	 * @param source
40
	 * @param property
41
	 */
42
	public SimpleValuePropertyObservableValue(Realm realm, Object source,
43
			SimpleValueProperty property) {
44
		super(realm);
45
		this.source = source;
46
		this.property = property;
47
	}
48
49
	protected void firstListenerAdded() {
50
		if (!isDisposed()) {
51
			cachedValue = property.getValue(source);
52
			if (listener == null) {
53
				listener = property
54
						.adaptListener(new IValuePropertyChangeListener() {
55
							public void handleValuePropertyChange(
56
									final ValuePropertyChangeEvent event) {
57
								if (!isDisposed() && !updating) {
58
									getRealm().exec(new Runnable() {
59
										public void run() {
60
											ValueDiff diff = event.diff;
61
											if (diff == null) {
62
												Object oldValue = cachedValue;
63
												Object newValue = cachedValue = property
64
														.getValue(source);
65
												if (Util.equals(oldValue,
66
														newValue))
67
													return;
68
69
												diff = Diffs.createValueDiff(
70
														oldValue, newValue);
71
											}
72
73
											fireValueChange(diff);
74
										}
75
									});
76
								}
77
							}
78
						});
79
			}
80
			property.addListener(source, listener);
81
		}
82
	}
83
84
	protected void lastListenerRemoved() {
85
		if (listener != null) {
86
			property.removeListener(source, listener);
87
		}
88
		cachedValue = null;
89
	}
90
91
	protected Object doGetValue() {
92
		if (hasListeners()) {
93
			Object oldValue = cachedValue;
94
			Object newValue = cachedValue = property.getValue(source);
95
96
			if (hasListeners() && !Util.equals(oldValue, newValue)) {
97
				fireValueChange(Diffs.createValueDiff(oldValue, newValue));
98
			}
99
			return newValue;
100
		}
101
		return property.getValue(source);
102
	}
103
104
	protected void doSetValue(Object value) {
105
		if (hasListeners()) {
106
			Object oldValue = cachedValue;
107
108
			updating = true;
109
			try {
110
				property.setValue(source, value);
111
			} finally {
112
				updating = false;
113
			}
114
115
			Object newValue = cachedValue = property.getValue(source);
116
			if (hasListeners() && !Util.equals(oldValue, newValue)) {
117
				fireValueChange(Diffs.createValueDiff(oldValue, newValue));
118
			}
119
		} else {
120
			property.setValue(source, value);
121
		}
122
	}
123
124
	public Object getValueType() {
125
		return property.getValueType();
126
	}
127
128
	public Object getObserved() {
129
		return source;
130
	}
131
132
	public IProperty getProperty() {
133
		return property;
134
	}
135
136
	public synchronized void dispose() {
137
		if (!isDisposed()) {
138
			if (listener != null)
139
				property.removeListener(source, listener);
140
			source = null;
141
			property = null;
142
			listener = null;
143
		}
144
		super.dispose();
145
	}
146
}
(-)src/org/eclipse/core/databinding/property/list/ListProperty.java (+33 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.databinding.property.list;
13
14
import org.eclipse.core.databinding.observable.Realm;
15
import org.eclipse.core.databinding.observable.list.IObservableList;
16
import org.eclipse.core.databinding.property.Properties;
17
import org.eclipse.core.databinding.property.Property;
18
import org.eclipse.core.databinding.property.value.IValueProperty;
19
20
/**
21
 * Abstract implementation of IListProperty.
22
 * 
23
 * @since 1.2
24
 */
25
public abstract class ListProperty extends Property implements IListProperty {
26
	public IObservableList observeList(Object source) {
27
		return observeList(Realm.getDefault(), source);
28
	}
29
30
	public final IListProperty chain(IValueProperty detailValue) {
31
		return Properties.detailValues(this, detailValue);
32
	}
33
}
(-)src/org/eclipse/core/databinding/property/PropertyChangeEvent.java (+44 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.databinding.property;
13
14
import java.util.EventObject;
15
16
/**
17
 * Base class for change events in the properties API
18
 * 
19
 * @since 1.2
20
 */
21
public abstract class PropertyChangeEvent extends EventObject {
22
	private static final long serialVersionUID = 1L;
23
24
	protected PropertyChangeEvent(Object source) {
25
		super(source);
26
	}
27
28
	protected abstract void dispatch(IPropertyChangeListener listener);
29
30
	public boolean equals(Object obj) {
31
		if (obj == this)
32
			return true;
33
		if (obj == null)
34
			return false;
35
		if (getClass() != obj.getClass())
36
			return false;
37
38
		return getSource().equals(((PropertyChangeEvent) obj).getSource());
39
	}
40
41
	public int hashCode() {
42
		return getSource().hashCode();
43
	}
44
}
(-)src/org/eclipse/core/databinding/property/map/IMapPropertyChangeListener.java (+29 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.databinding.property.map;
13
14
import org.eclipse.core.databinding.property.IPropertyChangeListener;
15
16
/**
17
 * Listener for changes to map properties on a property source
18
 * 
19
 * @since 1.2
20
 */
21
public interface IMapPropertyChangeListener extends IPropertyChangeListener {
22
	/**
23
	 * Handle a change to a map property on a specific property source.
24
	 * 
25
	 * @param event
26
	 *            an event describing the map change that occured.
27
	 */
28
	public void handleMapPropertyChange(MapPropertyChangeEvent event);
29
}
(-)src/org/eclipse/core/databinding/property/map/MapProperty.java (+33 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.databinding.property.map;
13
14
import org.eclipse.core.databinding.observable.Realm;
15
import org.eclipse.core.databinding.observable.map.IObservableMap;
16
import org.eclipse.core.databinding.property.Properties;
17
import org.eclipse.core.databinding.property.Property;
18
import org.eclipse.core.databinding.property.value.IValueProperty;
19
20
/**
21
 * Abstract implementation of IMapProperty
22
 * 
23
 * @since 1.2
24
 */
25
public abstract class MapProperty extends Property implements IMapProperty {
26
	public IObservableMap observeMap(Object source) {
27
		return observeMap(Realm.getDefault(), source);
28
	}
29
30
	public final IMapProperty chain(IValueProperty detailValues) {
31
		return Properties.detailValues(this, detailValues);
32
	}
33
}
(-)src/org/eclipse/core/databinding/property/set/SetProperty.java (+34 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.databinding.property.set;
13
14
import org.eclipse.core.databinding.observable.Realm;
15
import org.eclipse.core.databinding.observable.set.IObservableSet;
16
import org.eclipse.core.databinding.property.Properties;
17
import org.eclipse.core.databinding.property.Property;
18
import org.eclipse.core.databinding.property.map.IMapProperty;
19
import org.eclipse.core.databinding.property.value.IValueProperty;
20
21
/**
22
 * Abstract implementation of ISetProperty
23
 * 
24
 * @since 1.2
25
 */
26
public abstract class SetProperty extends Property implements ISetProperty {
27
	public IObservableSet observeSet(Object source) {
28
		return observeSet(Realm.getDefault(), source);
29
	}
30
31
	public final IMapProperty chain(IValueProperty detailValues) {
32
		return Properties.detailValues(this, detailValues);
33
	}
34
}
(-)src/org/eclipse/core/databinding/property/value/SimpleValueProperty.java (+156 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.databinding.property.value;
13
14
import org.eclipse.core.databinding.observable.IObservable;
15
import org.eclipse.core.databinding.observable.Realm;
16
import org.eclipse.core.databinding.observable.list.IObservableList;
17
import org.eclipse.core.databinding.observable.map.IObservableMap;
18
import org.eclipse.core.databinding.observable.masterdetail.IObservableFactory;
19
import org.eclipse.core.databinding.observable.masterdetail.MasterDetailObservables;
20
import org.eclipse.core.databinding.observable.set.IObservableSet;
21
import org.eclipse.core.databinding.observable.value.IObservableValue;
22
import org.eclipse.core.databinding.property.INativePropertyListener;
23
24
/**
25
 * Simplified abstract implementation of IValueProperty. This class takes care
26
 * of most of the functional requirements for an IValueProperty implementation,
27
 * leaving only the property-specific details to subclasses.
28
 * <p>
29
 * Subclasses must implement these methods:
30
 * <ul>
31
 * <li> {@link #getValue(Object)}
32
 * <li> {@link #setValue(Object, Object)}
33
 * <li> {@link #adaptListener(IValuePropertyChangeListener)}
34
 * <li> {@link #addListener(Object, INativePropertyListener)}
35
 * <li> {@link #removeListener(Object, INativePropertyListener)}
36
 * <li> {@link #toString()}
37
 * </ul>
38
 * 
39
 * @since 1.2
40
 */
41
public abstract class SimpleValueProperty extends ValueProperty {
42
	private final Object valueType;
43
44
	protected SimpleValueProperty(Object valueType) {
45
		this.valueType = valueType;
46
	}
47
48
	/**
49
	 * Returns the value type of the property, or <code>null</code> if untyped.
50
	 * 
51
	 * @return the value type of the property, or <code>null</code> if untyped.
52
	 * @noreference This method is not intended to be referenced by clients.
53
	 */
54
	protected final Object getValueType() {
55
		return valueType;
56
	}
57
58
	/**
59
	 * Returns the source's value property
60
	 * 
61
	 * @param source
62
	 *            the property source
63
	 * @return the current value of the source's value property
64
	 * @noreference This method is not intended to be referenced by clients.
65
	 */
66
	protected abstract Object getValue(Object source);
67
68
	/**
69
	 * Sets the source's value property to the specified value
70
	 * 
71
	 * @param source
72
	 *            the property source
73
	 * @param value
74
	 *            the new value
75
	 * @noreference This method is not intended to be referenced by clients.
76
	 */
77
	protected abstract void setValue(Object source, Object value);
78
79
	/**
80
	 * Returns a listener which implements the correct listener interface for
81
	 * the expected source object, and which parlays property change events from
82
	 * the source object to the given listener. If there is no listener API for
83
	 * this property, this method returns null.
84
	 * 
85
	 * @param listener
86
	 *            the property listener to receive events
87
	 * @return a native listener which parlays property change events to the
88
	 *         specified listener.
89
	 * @throws ClassCastException
90
	 *             if the provided listener does not implement the correct
91
	 *             listener interface (IValueProperty, IListProperty,
92
	 *             ISetProperty or IMapProperty) depending on the property.
93
	 * @noreference This method is not intended to be referenced by clients.
94
	 */
95
	protected abstract INativePropertyListener adaptListener(
96
			IValuePropertyChangeListener listener);
97
98
	/**
99
	 * Adds the specified listener as a listener for this property on the
100
	 * specified property source. If the source object has no listener API for
101
	 * this property (i.e. {@link #adaptListener(IValuePropertyChangeListener)}
102
	 * returns null), this method does nothing.
103
	 * 
104
	 * @param source
105
	 *            the property source
106
	 * @param listener
107
	 *            a listener obtained from calling
108
	 *            {@link #adaptListener(IValuePropertyChangeListener)}.
109
	 * @noreference This method is not intended to be referenced by clients.
110
	 */
111
	protected abstract void addListener(Object source,
112
			INativePropertyListener listener);
113
114
	/**
115
	 * Removes the specified listener as a listener for this property on the
116
	 * specified property source. If the source object has no listener API for
117
	 * this property (i.e. {@link #adaptListener(IValuePropertyChangeListener)}
118
	 * returns null), this method does nothing.
119
	 * 
120
	 * @param source
121
	 *            the property source
122
	 * @param listener
123
	 *            a listener obtained from calling
124
	 *            {@link #adaptListener(IValuePropertyChangeListener)}.
125
	 * @noreference This method is not intended to be referenced by clients.
126
	 */
127
	protected abstract void removeListener(Object source,
128
			INativePropertyListener listener);
129
130
	public IObservableValue observeValue(Realm realm, Object source) {
131
		return new SimpleValuePropertyObservableValue(realm, source, this);
132
	}
133
134
	public IObservableValue observeDetailValue(IObservableValue master) {
135
		final Realm realm = master.getRealm();
136
		IObservableFactory factory = new IObservableFactory() {
137
			public IObservable createObservable(Object target) {
138
				return new SimpleValuePropertyObservableValue(realm, target,
139
						SimpleValueProperty.this);
140
			}
141
		};
142
		return MasterDetailObservables.detailValue(master, factory, valueType);
143
	}
144
145
	public IObservableList observeDetailValues(IObservableList master) {
146
		return new ObservableListSimpleValuePropertyObservableList(master, this);
147
	}
148
149
	public IObservableMap observeDetailValues(IObservableSet master) {
150
		return new ObservableSetSimpleValuePropertyObservableMap(master, this);
151
	}
152
153
	public IObservableMap observeDetailValues(IObservableMap master) {
154
		return new ObservableMapSimpleValuePropertyObservableMap(master, this);
155
	}
156
}
(-)src/org/eclipse/core/internal/databinding/property/ValuePropertyDetailList.java (+53 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.internal.databinding.property;
13
14
import org.eclipse.core.databinding.observable.Realm;
15
import org.eclipse.core.databinding.observable.list.IObservableList;
16
import org.eclipse.core.databinding.observable.value.IObservableValue;
17
import org.eclipse.core.databinding.property.list.IListProperty;
18
import org.eclipse.core.databinding.property.list.ListProperty;
19
import org.eclipse.core.databinding.property.value.IValueProperty;
20
21
/**
22
 * @since 3.3
23
 * 
24
 */
25
public class ValuePropertyDetailList extends ListProperty {
26
	private final IValueProperty masterProperty;
27
	private final IListProperty detailProperty;
28
29
	/**
30
	 * @param masterProperty
31
	 * @param detailProperty
32
	 */
33
	public ValuePropertyDetailList(IValueProperty masterProperty,
34
			IListProperty detailProperty) {
35
		this.masterProperty = masterProperty;
36
		this.detailProperty = detailProperty;
37
	}
38
39
	public IObservableList observeList(Realm realm, Object source) {
40
		IObservableValue master = masterProperty.observeValue(realm, source);
41
		return detailProperty.observeDetailList(master);
42
	}
43
44
	public IObservableList observeDetailList(IObservableValue master) {
45
		IObservableValue masterValue = masterProperty
46
				.observeDetailValue(master);
47
		return detailProperty.observeDetailList(masterValue);
48
	}
49
50
	public String toString() {
51
		return masterProperty + " => " + detailProperty; //$NON-NLS-1$
52
	}
53
}
(-)src/org/eclipse/core/databinding/property/list/IListPropertyChangeListener.java (+29 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.databinding.property.list;
13
14
import org.eclipse.core.databinding.property.IPropertyChangeListener;
15
16
/**
17
 * Listener for changes to list properties on a property source
18
 * 
19
 * @since 1.2
20
 */
21
public interface IListPropertyChangeListener extends IPropertyChangeListener {
22
	/**
23
	 * Handle a change to a list property on a specific property source.
24
	 * 
25
	 * @param event
26
	 *            an event describing the list change that occured.
27
	 */
28
	public void handleListPropertyChange(ListPropertyChangeEvent event);
29
}
(-)src/org/eclipse/core/databinding/property/map/SimpleMapProperty.java (+378 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation
10
 ******************************************************************************/
11
12
package org.eclipse.core.databinding.property.map;
13
14
import java.util.Collections;
15
import java.util.HashMap;
16
import java.util.HashSet;
17
import java.util.Iterator;
18
import java.util.Map;
19
import java.util.Set;
20
21
import org.eclipse.core.databinding.observable.Diffs;
22
import org.eclipse.core.databinding.observable.IObservable;
23
import org.eclipse.core.databinding.observable.Realm;
24
import org.eclipse.core.databinding.observable.map.IObservableMap;
25
import org.eclipse.core.databinding.observable.map.MapDiff;
26
import org.eclipse.core.databinding.observable.masterdetail.IObservableFactory;
27
import org.eclipse.core.databinding.observable.masterdetail.MasterDetailObservables;
28
import org.eclipse.core.databinding.observable.value.IObservableValue;
29
import org.eclipse.core.databinding.property.INativePropertyListener;
30
import org.eclipse.core.internal.databinding.Util;
31
32
/**
33
 * Simplified abstract implementation of IMapProperty. This class takes care of
34
 * most of the functional requirements for an IMapProperty implementation,
35
 * leaving only the property-specific details to subclasses.
36
 * <p>
37
 * Subclasses must implement these methods:
38
 * <ul>
39
 * <li>{@link #getKeyType()}
40
 * <li>{@link #getValueType()}
41
 * </ul>
42
 * 
43
 * @since 1.2
44
 */
45
public abstract class SimpleMapProperty extends MapProperty implements
46
		IMapProperty {
47
	private final Object keyType;
48
	private final Object valueType;
49
50
	protected SimpleMapProperty(Object keyType, Object valueType) {
51
		this.keyType = keyType;
52
		this.valueType = valueType;
53
	}
54
55
	/**
56
	 * Returns the element type of the map's key set or <code>null</code> if the
57
	 * key set is untyped.
58
	 * 
59
	 * @return the element type of the map's key set or <code>null</code> if the
60
	 *         key set is untyped.
61
	 * @noreference This method is not intended to be referenced by clients.
62
	 */
63
	protected final Object getKeyType() {
64
		return keyType;
65
	}
66
67
	/**
68
	 * Returns the element type of the map's values collection or
69
	 * <code>null</code> if the collection is untyped.
70
	 * 
71
	 * @return the element type of the map's values collection or
72
	 *         <code>null</code> if the collection is untyped.
73
	 * @noreference This method is not intended to be referenced by clients.
74
	 */
75
	protected final Object getValueType() {
76
		return valueType;
77
	}
78
79
	/**
80
	 * Returns an unmodifiable Map with the current contents of the source's map
81
	 * property.
82
	 * 
83
	 * @param source
84
	 *            the property source
85
	 * @return a Map with the current contents of the source's map property
86
	 * @noreference This method is not intended to be referenced by clients.
87
	 */
88
	protected final Map getMap(Object source) {
89
		return Collections.unmodifiableMap(doGetMap(source));
90
	}
91
92
	/**
93
	 * Returns a Map with the current contents of the source's map property
94
	 * 
95
	 * @param source
96
	 *            the property source
97
	 * @return a Map with the current contents of the source's map property
98
	 * @noreference This method is not intended to be referenced by clients.
99
	 */
100
	protected abstract Map doGetMap(Object source);
101
102
	/**
103
	 * Returns a listener which implements the correct listener interface for
104
	 * the expected source object, and which parlays property change events from
105
	 * the source object to the given listener. If there is no listener API for
106
	 * this property, this method returns null.
107
	 * 
108
	 * @param listener
109
	 *            the property listener to receive events
110
	 * @return a native listener which parlays property change events to the
111
	 *         specified listener.
112
	 * @throws ClassCastException
113
	 *             if the provided listener does not implement the correct
114
	 *             listener interface (IValueProperty, IListProperty,
115
	 *             ISetProperty or IMapProperty) depending on the property.
116
	 * @noreference This method is not intended to be referenced by clients.
117
	 */
118
	protected abstract INativePropertyListener adaptListener(
119
			IMapPropertyChangeListener listener);
120
121
	/**
122
	 * Adds the specified listener as a listener for this property on the
123
	 * specified property source. If the source object has no listener API for
124
	 * this property (i.e. {@link #adaptListener(IMapPropertyChangeListener)}
125
	 * returns null), this method does nothing.
126
	 * 
127
	 * @param source
128
	 *            the property source
129
	 * @param listener
130
	 *            a listener obtained from calling
131
	 *            {@link #adaptListener(IMapPropertyChangeListener)} .
132
	 * @noreference This method is not intended to be referenced by clients.
133
	 */
134
	protected abstract void addListener(Object source,
135
			INativePropertyListener listener);
136
137
	/**
138
	 * Removes the specified listener as a listener for this property on the
139
	 * specified property source. If the source object has no listener API for
140
	 * this property (i.e. {@link #adaptListener(IMapPropertyChangeListener)}
141
	 * returns null), this method does nothing.
142
	 * 
143
	 * @param source
144
	 *            the property source
145
	 * @param listener
146
	 *            a listener obtained from calling
147
	 *            {@link #adaptListener(IMapPropertyChangeListener)} .
148
	 * @noreference This method is not intended to be referenced by clients.
149
	 */
150
	protected abstract void removeListener(Object source,
151
			INativePropertyListener listener);
152
153
	/**
154
	 * Returns whether the specified key is contained in the key set of the
155
	 * source's map property
156
	 * 
157
	 * @param source
158
	 *            the property source
159
	 * @param key
160
	 *            the key
161
	 * @return whether the specified key is contained in the key set of the
162
	 *         source's map property
163
	 * @noreference This method is not intended to be referenced by clients.
164
	 */
165
	protected boolean containsKey(Object source, Object key) {
166
		return getMap(source).containsKey(key);
167
	}
168
169
	/**
170
	 * Returns whether the specified value is contains in the values collection
171
	 * of the source's map property
172
	 * 
173
	 * @param source
174
	 *            the property source
175
	 * @param value
176
	 *            the value
177
	 * @return whether the specified value is contains in the values collection
178
	 *         of the source's map property
179
	 * @noreference This method is not intended to be referenced by clients.
180
	 */
181
	protected boolean containsValue(Object source, Object value) {
182
		return getMap(source).containsValue(value);
183
	}
184
185
	/**
186
	 * Returns whether the source's map property is equal to the argument
187
	 * 
188
	 * @param source
189
	 *            the property source
190
	 * @param o
191
	 *            the object to test for equality
192
	 * @return whether the source's map property is equal to the argument
193
	 * @noreference This method is not intended to be referenced by clients.
194
	 */
195
	protected boolean equals(Object source, Object o) {
196
		return getMap(source).equals(o);
197
	}
198
199
	/**
200
	 * Returns the value associated with the specified key in the source's map
201
	 * property
202
	 * 
203
	 * @param source
204
	 *            the property source
205
	 * @param key
206
	 *            the key
207
	 * @return the value associated with the specified key in the source's map
208
	 *         property
209
	 * @noreference This method is not intended to be referenced by clients.
210
	 */
211
	protected Object get(Object source, Object key) {
212
		return getMap(source).get(key);
213
	}
214
215
	/**
216
	 * Returns the hash code of the source's map property
217
	 * 
218
	 * @param source
219
	 *            the property source
220
	 * @return the hash code of the source's map property
221
	 * @noreference This method is not intended to be referenced by clients.
222
	 */
223
	protected int hashCode(Object source) {
224
		return getMap(source).hashCode();
225
	}
226
227
	/**
228
	 * Returns whether the source's map property is empty
229
	 * 
230
	 * @param source
231
	 *            the property source
232
	 * @return whether the source's map property is empty
233
	 * @noreference This method is not intended to be referenced by clients.
234
	 */
235
	protected boolean isEmpty(Object source) {
236
		return getMap(source).isEmpty();
237
	}
238
239
	/**
240
	 * Returns the size of the source's map property
241
	 * 
242
	 * @param source
243
	 *            the property source
244
	 * @return the size of the source's map property
245
	 * @noreference This method is not intended to be referenced by clients.
246
	 */
247
	protected int size(Object source) {
248
		return getMap(source).size();
249
	}
250
251
	/**
252
	 * Updates the property on the source with the specified change.
253
	 * 
254
	 * @param source
255
	 *            the property source
256
	 * @param map
257
	 *            the new map
258
	 * @param diff
259
	 *            a diff describing the change
260
	 * @noreference This method is not intended to be referenced by clients.
261
	 */
262
	protected abstract void setMap(Object source, Map map, MapDiff diff);
263
264
	/**
265
	 * Removes all mapping from the source's map property
266
	 * 
267
	 * @param source
268
	 *            the property source
269
	 * @noreference This method is not intended to be referenced by clients.
270
	 */
271
	protected void clear(Object source) {
272
		if (!isEmpty(source)) {
273
			setMap(source, new HashMap(), Diffs
274
					.createMapDiffRemoveAll(new HashMap(getMap(source))));
275
		}
276
	}
277
278
	/**
279
	 * Associates the specified value with the specified key in the source's map
280
	 * property
281
	 * 
282
	 * @param source
283
	 *            the property source
284
	 * @param key
285
	 *            the key
286
	 * @param value
287
	 *            the value
288
	 * @return the value that was previously associated with the given key in
289
	 *         the source's map property
290
	 * @noreference This method is not intended to be referenced by clients.
291
	 */
292
	protected Object put(Object source, Object key, Object value) {
293
		Map map = new HashMap(getMap(source));
294
		boolean addition = !map.containsKey(key);
295
		Object result = map.put(key, value);
296
		MapDiff diff;
297
		if (addition) {
298
			diff = Diffs.createMapDiffSingleAdd(key, value);
299
		} else {
300
			diff = Diffs.createMapDiffSingleChange(key, result, value);
301
		}
302
		setMap(source, map, diff);
303
		return result;
304
	}
305
306
	/**
307
	 * Adds all mappings in the specified map to the source's map property.
308
	 * 
309
	 * @param source
310
	 *            the property source
311
	 * @param t
312
	 *            the map
313
	 * @noreference This method is not intended to be referenced by clients.
314
	 */
315
	protected void putAll(Object source, Map t) {
316
		if (t.isEmpty())
317
			return;
318
319
		Map map = new HashMap(getMap(source));
320
		Set addedKeys = new HashSet();
321
		Set changedKeys = new HashSet();
322
		Map oldValues = new HashMap();
323
		Map newValues = new HashMap();
324
		for (Iterator it = t.entrySet().iterator(); it.hasNext();) {
325
			Map.Entry entry = (Map.Entry) it.next();
326
			Object key = entry.getKey();
327
			Object newValue = entry.getValue();
328
			boolean addition = !map.containsKey(key);
329
			Object oldValue = map.put(key, newValue);
330
			if (addition) {
331
				addedKeys.add(key);
332
			} else if (!Util.equals(oldValue, newValue)) {
333
				changedKeys.add(key);
334
				oldValues.put(key, oldValue);
335
			}
336
			newValues.put(key, newValue);
337
		}
338
		setMap(source, map, Diffs.createMapDiff(addedKeys,
339
				Collections.EMPTY_SET, changedKeys, oldValues, newValues));
340
	}
341
342
	/**
343
	 * Removes the mapping for the specified key from the source's map property
344
	 * 
345
	 * @param source
346
	 *            the property source
347
	 * @param key
348
	 *            the key
349
	 * @return the value that was previously associated with the specified key
350
	 *         in the source's map property, or null if no such mapping exists
351
	 * @noreference This method is not intended to be referenced by clients.
352
	 */
353
	protected Object remove(Object source, Object key) {
354
		Map map = getMap(source);
355
		if (map.containsKey(key)) {
356
			map = new HashMap(map);
357
			Object result = map.remove(key);
358
			setMap(source, map, Diffs.createMapDiffSingleRemove(key, result));
359
			return result;
360
		}
361
		return null;
362
	}
363
364
	public IObservableMap observeMap(Realm realm, Object source) {
365
		return new SimpleMapPropertyObservableMap(realm, source, this);
366
	}
367
368
	public IObservableMap observeDetailMap(IObservableValue master) {
369
		final Realm realm = master.getRealm();
370
		IObservableFactory factory = new IObservableFactory() {
371
			public IObservable createObservable(Object target) {
372
				return new SimpleMapPropertyObservableMap(realm, target,
373
						SimpleMapProperty.this);
374
			}
375
		};
376
		return MasterDetailObservables.detailMap(master, factory);
377
	}
378
}
(-)src/org/eclipse/core/databinding/property/IPropertyChangeListener.java (+22 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.databinding.property;
13
14
/**
15
 * Marker interface for all listener types in the properties framework.
16
 * 
17
 * @noimplement This interface is not intended to be implemented by clients.
18
 * 
19
 * @since 1.2
20
 */
21
public interface IPropertyChangeListener {
22
}
(-)src/org/eclipse/core/databinding/property/value/ObservableListSimpleValuePropertyObservableList.java (+441 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.databinding.property.value;
13
14
import java.lang.reflect.Array;
15
import java.util.ArrayList;
16
import java.util.Collection;
17
import java.util.HashMap;
18
import java.util.HashSet;
19
import java.util.Iterator;
20
import java.util.List;
21
import java.util.ListIterator;
22
import java.util.Map;
23
import java.util.Set;
24
25
import org.eclipse.core.databinding.observable.Diffs;
26
import org.eclipse.core.databinding.observable.IObserving;
27
import org.eclipse.core.databinding.observable.IStaleListener;
28
import org.eclipse.core.databinding.observable.ObservableTracker;
29
import org.eclipse.core.databinding.observable.StaleEvent;
30
import org.eclipse.core.databinding.observable.list.AbstractObservableList;
31
import org.eclipse.core.databinding.observable.list.IListChangeListener;
32
import org.eclipse.core.databinding.observable.list.IObservableList;
33
import org.eclipse.core.databinding.observable.list.ListChangeEvent;
34
import org.eclipse.core.databinding.observable.list.ListDiff;
35
import org.eclipse.core.databinding.observable.list.ListDiffEntry;
36
import org.eclipse.core.databinding.observable.set.IObservableSet;
37
import org.eclipse.core.databinding.observable.set.ISetChangeListener;
38
import org.eclipse.core.databinding.observable.set.SetChangeEvent;
39
import org.eclipse.core.databinding.observable.set.WritableSet;
40
import org.eclipse.core.databinding.property.INativePropertyListener;
41
import org.eclipse.core.internal.databinding.IdentityWrapper;
42
import org.eclipse.core.internal.databinding.Util;
43
44
/**
45
 * @since 1.2
46
 */
47
class ObservableListSimpleValuePropertyObservableList extends
48
		AbstractObservableList implements IObserving {
49
	private IObservableList masterList;
50
	private SimpleValueProperty detailProperty;
51
52
	private IObservableSet knownMasterElements;
53
	private Map cachedValues;
54
55
	private boolean updating;
56
57
	private IListChangeListener masterListener = new IListChangeListener() {
58
		public void handleListChange(ListChangeEvent event) {
59
			if (!isDisposed()) {
60
				updateKnownElements();
61
				fireListChange(convertDiff(event.diff));
62
			}
63
		}
64
65
		private void updateKnownElements() {
66
			Set identityKnownElements = new HashSet();
67
			for (Iterator it = masterList.iterator(); it.hasNext();) {
68
				identityKnownElements.add(new IdentityWrapper(it.next()));
69
			}
70
71
			knownMasterElements.retainAll(identityKnownElements);
72
			knownMasterElements.addAll(identityKnownElements);
73
		}
74
75
		private ListDiff convertDiff(ListDiff diff) {
76
			// Convert diff to detail value
77
			ListDiffEntry[] masterEntries = diff.getDifferences();
78
			ListDiffEntry[] detailEntries = new ListDiffEntry[masterEntries.length];
79
			for (int i = 0; i < masterEntries.length; i++) {
80
				ListDiffEntry masterDifference = masterEntries[i];
81
				int index = masterDifference.getPosition();
82
				boolean addition = masterDifference.isAddition();
83
				Object masterElement = masterDifference.getElement();
84
				Object elementDetailValue = detailProperty
85
						.getValue(masterElement);
86
				detailEntries[i] = Diffs.createListDiffEntry(index, addition,
87
						elementDetailValue);
88
			}
89
			return Diffs.createListDiff(detailEntries);
90
		}
91
	};
92
93
	private IStaleListener staleListener = new IStaleListener() {
94
		public void handleStale(StaleEvent staleEvent) {
95
			fireStale();
96
		}
97
	};
98
99
	private INativePropertyListener detailListener;
100
101
	/**
102
	 * @param masterList
103
	 * @param valueProperty
104
	 */
105
	public ObservableListSimpleValuePropertyObservableList(
106
			IObservableList masterList, SimpleValueProperty valueProperty) {
107
		super(masterList.getRealm());
108
		this.masterList = masterList;
109
		this.detailProperty = valueProperty;
110
111
		IValuePropertyChangeListener listener = new IValuePropertyChangeListener() {
112
			public void handleValuePropertyChange(
113
					final ValuePropertyChangeEvent event) {
114
				if (!isDisposed() && !updating) {
115
					Object masterElement = event.getSource();
116
					int[] indices = indicesOf(masterElement);
117
					Object oldValue = event.diff.getOldValue();
118
					Object newValue = event.diff.getNewValue();
119
					ListDiffEntry[] entries = new ListDiffEntry[indices.length * 2];
120
					for (int i = 0; i < indices.length; i++) {
121
						int index = indices[i];
122
						entries[i * 2] = Diffs.createListDiffEntry(index,
123
								false, oldValue);
124
						entries[i * 2 + 1] = Diffs.createListDiffEntry(index,
125
								true, newValue);
126
					}
127
128
					ListDiff diff = Diffs.createListDiff(entries);
129
					cachedValues.put(new IdentityWrapper(masterElement),
130
							newValue);
131
					fireListChange(diff);
132
				}
133
			}
134
135
			private int[] indicesOf(Object element) {
136
				List indices = new ArrayList();
137
138
				for (ListIterator it = ObservableListSimpleValuePropertyObservableList.this.masterList
139
						.listIterator(); it.hasNext();) {
140
					if (element == it.next())
141
						indices.add(new Integer(it.previousIndex()));
142
				}
143
144
				int[] result = new int[indices.size()];
145
				for (int i = 0; i < result.length; i++) {
146
					result[i] = ((Integer) indices.get(i)).intValue();
147
				}
148
				return result;
149
			}
150
		};
151
		this.detailListener = detailProperty.adaptListener(listener);
152
	}
153
154
	protected void firstListenerAdded() {
155
		knownMasterElements = new WritableSet(getRealm());
156
		cachedValues = new HashMap();
157
		knownMasterElements.addSetChangeListener(new ISetChangeListener() {
158
			public void handleSetChange(SetChangeEvent event) {
159
				for (Iterator it = event.diff.getRemovals().iterator(); it
160
						.hasNext();) {
161
					IdentityWrapper wrapper = (IdentityWrapper) it.next();
162
					Object key = wrapper.unwrap();
163
					detailProperty.removeListener(key, detailListener);
164
					cachedValues.remove(wrapper);
165
				}
166
				for (Iterator it = event.diff.getAdditions().iterator(); it
167
						.hasNext();) {
168
					IdentityWrapper wrapper = (IdentityWrapper) it.next();
169
					Object key = wrapper.unwrap();
170
					cachedValues.put(wrapper, detailProperty.getValue(key));
171
					detailProperty.addListener(key, detailListener);
172
				}
173
			}
174
		});
175
		for (Iterator it = masterList.iterator(); it.hasNext();) {
176
			knownMasterElements.add(new IdentityWrapper(it.next()));
177
		}
178
179
		masterList.addListChangeListener(masterListener);
180
		masterList.addStaleListener(staleListener);
181
	}
182
183
	protected void lastListenerRemoved() {
184
		masterList.removeListChangeListener(masterListener);
185
		masterList.removeStaleListener(staleListener);
186
		if (knownMasterElements != null) {
187
			knownMasterElements.clear(); // clears cachedValues
188
			knownMasterElements.dispose();
189
			knownMasterElements = null;
190
		}
191
		cachedValues = null;
192
	}
193
194
	protected int doGetSize() {
195
		getterCalled();
196
		return masterList.size();
197
	}
198
199
	private void getterCalled() {
200
		ObservableTracker.getterCalled(this);
201
	}
202
203
	public Object getElementType() {
204
		return detailProperty.getValueType();
205
	}
206
207
	public Object get(int index) {
208
		getterCalled();
209
		Object masterElement = masterList.get(index);
210
		return detailProperty.getValue(masterElement);
211
	}
212
213
	public boolean add(Object o) {
214
		throw new UnsupportedOperationException();
215
	}
216
217
	public boolean addAll(Collection c) {
218
		throw new UnsupportedOperationException();
219
	}
220
221
	public boolean addAll(int index, Collection c) {
222
		throw new UnsupportedOperationException();
223
	}
224
225
	public boolean contains(Object o) {
226
		getterCalled();
227
228
		for (Iterator it = masterList.iterator(); it.hasNext();) {
229
			if (Util.equals(detailProperty.getValue(it.next()), o))
230
				return true;
231
		}
232
		return false;
233
	}
234
235
	public boolean isEmpty() {
236
		getterCalled();
237
		return masterList.isEmpty();
238
	}
239
240
	public boolean isStale() {
241
		getterCalled();
242
		return masterList.isStale();
243
	}
244
245
	public Iterator iterator() {
246
		getterCalled();
247
		return new Iterator() {
248
			Iterator it = masterList.iterator();
249
250
			public boolean hasNext() {
251
				getterCalled();
252
				return it.hasNext();
253
			}
254
255
			public Object next() {
256
				getterCalled();
257
				Object masterElement = it.next();
258
				return detailProperty.getValue(masterElement);
259
			}
260
261
			public void remove() {
262
				throw new UnsupportedOperationException();
263
			}
264
		};
265
	}
266
267
	public Object move(int oldIndex, int newIndex) {
268
		throw new UnsupportedOperationException();
269
	}
270
271
	public boolean remove(Object o) {
272
		throw new UnsupportedOperationException();
273
	}
274
275
	public boolean removeAll(Collection c) {
276
		throw new UnsupportedOperationException();
277
	}
278
279
	public boolean retainAll(Collection c) {
280
		throw new UnsupportedOperationException();
281
	}
282
283
	public Object[] toArray() {
284
		getterCalled();
285
		Object[] masterElements = masterList.toArray();
286
		Object[] result = new Object[masterElements.length];
287
		for (int i = 0; i < result.length; i++) {
288
			result[i] = detailProperty.getValue(masterElements[i]);
289
		}
290
		return result;
291
	}
292
293
	public Object[] toArray(Object[] a) {
294
		getterCalled();
295
		Object[] masterElements = masterList.toArray();
296
		if (a.length < masterElements.length)
297
			a = (Object[]) Array.newInstance(a.getClass().getComponentType(),
298
					masterElements.length);
299
		for (int i = 0; i < masterElements.length; i++) {
300
			a[i] = detailProperty.getValue(masterElements[i]);
301
		}
302
		return a;
303
	}
304
305
	public void add(int index, Object o) {
306
		throw new UnsupportedOperationException();
307
	}
308
309
	public void clear() {
310
		throw new UnsupportedOperationException();
311
	}
312
313
	public ListIterator listIterator() {
314
		return listIterator(0);
315
	}
316
317
	public ListIterator listIterator(final int index) {
318
		getterCalled();
319
		return new ListIterator() {
320
			ListIterator it = masterList.listIterator(index);
321
			int lastIndex = -1;
322
			Object lastMasterElement;
323
			Object lastElement;
324
			boolean haveIterated = false;
325
326
			public void add(Object arg0) {
327
				throw new UnsupportedOperationException();
328
			}
329
330
			public boolean hasNext() {
331
				getterCalled();
332
				return it.hasNext();
333
			}
334
335
			public boolean hasPrevious() {
336
				getterCalled();
337
				return it.hasPrevious();
338
			}
339
340
			public Object next() {
341
				getterCalled();
342
				lastMasterElement = it.next();
343
				lastElement = detailProperty.getValue(lastMasterElement);
344
				lastIndex = it.previousIndex();
345
				haveIterated = true;
346
				return lastElement;
347
			}
348
349
			public int nextIndex() {
350
				getterCalled();
351
				return it.nextIndex();
352
			}
353
354
			public Object previous() {
355
				getterCalled();
356
				lastMasterElement = it.previous();
357
				lastElement = detailProperty.getValue(lastMasterElement);
358
				lastIndex = it.nextIndex();
359
				haveIterated = true;
360
				return lastElement;
361
			}
362
363
			public int previousIndex() {
364
				getterCalled();
365
				return it.previousIndex();
366
			}
367
368
			public void remove() {
369
				throw new UnsupportedOperationException();
370
			}
371
372
			public void set(Object o) {
373
				checkRealm();
374
				if (!haveIterated)
375
					throw new IllegalStateException();
376
377
				boolean wasUpdating = updating;
378
				updating = true;
379
				try {
380
					detailProperty.setValue(lastElement, o);
381
				} finally {
382
					updating = wasUpdating;
383
				}
384
385
				cachedValues.put(new IdentityWrapper(lastMasterElement), o);
386
				fireListChange(Diffs.createListDiff(Diffs.createListDiffEntry(
387
						lastIndex, false, lastElement), Diffs
388
						.createListDiffEntry(lastIndex, true, o)));
389
390
				lastElement = o;
391
			}
392
		};
393
	}
394
395
	public Object remove(int index) {
396
		throw new UnsupportedOperationException();
397
	}
398
399
	public Object set(int index, Object o) {
400
		checkRealm();
401
		Object masterElement = masterList.get(index);
402
		Object oldValue = detailProperty.getValue(masterElement);
403
404
		boolean wasUpdating = updating;
405
		updating = true;
406
		try {
407
			detailProperty.setValue(masterElement, o);
408
		} finally {
409
			updating = wasUpdating;
410
		}
411
412
		cachedValues.put(new IdentityWrapper(masterElement), o);
413
		fireListChange(Diffs.createListDiff(Diffs.createListDiffEntry(index,
414
				false, oldValue), Diffs.createListDiffEntry(index, true, o)));
415
416
		return oldValue;
417
	}
418
419
	public Object getObserved() {
420
		return masterList;
421
	}
422
423
	public synchronized void dispose() {
424
		if (masterList != null) {
425
			masterList.removeListChangeListener(masterListener);
426
			masterList = null;
427
		}
428
		if (knownMasterElements != null) {
429
			knownMasterElements.clear(); // detaches listeners
430
			knownMasterElements.dispose();
431
			knownMasterElements = null;
432
		}
433
434
		masterListener = null;
435
		detailListener = null;
436
		detailProperty = null;
437
		cachedValues = null;
438
439
		super.dispose();
440
	}
441
}
(-)src/org/eclipse/core/databinding/property/INativePropertyListener.java (+23 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.databinding.property;
13
14
/**
15
 * Marker interface for "native" property listeners. A native listener
16
 * implements the listener interface supported by the source object, and parlays
17
 * events received from the source object to the property change listener
18
 * provided when the native listener was constructed.
19
 * 
20
 * @since 1.2
21
 */
22
public interface INativePropertyListener {
23
}
(-)src/org/eclipse/core/databinding/property/set/ISetProperty.java (+87 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.databinding.property.set;
13
14
import org.eclipse.core.databinding.observable.Realm;
15
import org.eclipse.core.databinding.observable.map.IObservableMap;
16
import org.eclipse.core.databinding.observable.set.IObservableSet;
17
import org.eclipse.core.databinding.observable.value.IObservableValue;
18
import org.eclipse.core.databinding.property.IProperty;
19
import org.eclipse.core.databinding.property.map.IMapProperty;
20
import org.eclipse.core.databinding.property.value.IValueProperty;
21
22
/**
23
 * Interface for set-typed properties
24
 * 
25
 * @since 1.2
26
 * @noimplement This interface is not intended to be implemented by clients.
27
 *              Clients should instead subclass one of the classes that
28
 *              implement this interface. Note that direct implementers of this
29
 *              interface outside of the framework will be broken in future
30
 *              releases when methods are added to this interface.
31
 * @see SetProperty
32
 * @see SimpleSetProperty
33
 */
34
public interface ISetProperty extends IProperty {
35
	/**
36
	 * Returns an observable set observing this set property on the given
37
	 * property source
38
	 * 
39
	 * @param source
40
	 *            the property source
41
	 * @return an observable set observing this set property on the given
42
	 *         property source
43
	 */
44
	public IObservableSet observeSet(Object source);
45
46
	/**
47
	 * Returns an observable set observing this set property on the given
48
	 * property source
49
	 * 
50
	 * @param realm
51
	 *            the observable's realm
52
	 * @param source
53
	 *            the property source
54
	 * @return an observable set observing this set property on the given
55
	 *         property source
56
	 */
57
	public IObservableSet observeSet(Realm realm, Object source);
58
59
	/**
60
	 * Returns an observable set on the master observable's realm which tracks
61
	 * this property of the current value of <code>master</code>.
62
	 * 
63
	 * @param master
64
	 *            the master observable
65
	 * @return an observable set on the given realm which tracks this property
66
	 *         of the current value of <code>master</code>.
67
	 */
68
	public IObservableSet observeDetailSet(IObservableValue master);
69
70
	/**
71
	 * Returns the nested combination of this property and the specified detail
72
	 * value property. Note that because this property is a projection of value
73
	 * properties over a set, the only modifications supported are through the
74
	 * {@link IObservableMap#put(Object, Object)} and
75
	 * {@link IObservableMap#putAll(java.util.Map)} methods. In the latter case,
76
	 * this property does not put entries for keys not already in the master key
77
	 * set. Modifications made through the returned property are delegated to
78
	 * the detail property, using the corresponding set element from the master
79
	 * property as the source.
80
	 * 
81
	 * @param detailValues
82
	 *            the detail property
83
	 * @return the nested combination of the master set and detail value
84
	 *         properties
85
	 */
86
	public IMapProperty chain(IValueProperty detailValues);
87
}
(-)src/org/eclipse/core/databinding/property/map/SimpleMapPropertyObservableMap.java (+257 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.databinding.property.map;
13
14
import java.util.Collection;
15
import java.util.Collections;
16
import java.util.HashSet;
17
import java.util.Iterator;
18
import java.util.Map;
19
import java.util.Set;
20
21
import org.eclipse.core.databinding.observable.Diffs;
22
import org.eclipse.core.databinding.observable.ObservableTracker;
23
import org.eclipse.core.databinding.observable.Realm;
24
import org.eclipse.core.databinding.observable.map.AbstractObservableMap;
25
import org.eclipse.core.databinding.observable.map.MapDiff;
26
import org.eclipse.core.databinding.property.IProperty;
27
import org.eclipse.core.databinding.property.INativePropertyListener;
28
import org.eclipse.core.databinding.property.IPropertyObservable;
29
30
/**
31
 * @since 1.2
32
 */
33
class SimpleMapPropertyObservableMap extends AbstractObservableMap implements
34
		IPropertyObservable {
35
	private Object source;
36
	private SimpleMapProperty property;
37
38
	private volatile boolean updating = false;
39
40
	private volatile int modCount = 0;
41
42
	private INativePropertyListener listener;
43
44
	private Map cachedMap;
45
46
	/**
47
	 * @param realm
48
	 * @param source
49
	 * @param property
50
	 */
51
	public SimpleMapPropertyObservableMap(Realm realm, Object source,
52
			SimpleMapProperty property) {
53
		super(realm);
54
		this.source = source;
55
		this.property = property;
56
	}
57
58
	private void getterCalled() {
59
		ObservableTracker.getterCalled(this);
60
	}
61
62
	protected void firstListenerAdded() {
63
		if (!isDisposed()) {
64
			cachedMap = property.getMap(source);
65
66
			if (listener == null) {
67
				listener = property
68
						.adaptListener(new IMapPropertyChangeListener() {
69
							public void handleMapPropertyChange(
70
									final MapPropertyChangeEvent event) {
71
								modCount++;
72
								if (!isDisposed() && !updating) {
73
									getRealm().exec(new Runnable() {
74
										public void run() {
75
											Map oldMap = cachedMap;
76
											Map newMap = cachedMap = property
77
													.getMap(source);
78
											MapDiff diff = event.diff;
79
											if (diff == null) {
80
												diff = Diffs.computeMapDiff(
81
														oldMap, newMap);
82
											}
83
											fireMapChange(diff);
84
										}
85
									});
86
								}
87
							}
88
						});
89
			}
90
			property.addListener(source, listener);
91
		}
92
	}
93
94
	protected void lastListenerRemoved() {
95
		if (listener != null) {
96
			property.removeListener(source, listener);
97
		}
98
99
		cachedMap = null;
100
	}
101
102
	public boolean containsKey(Object key) {
103
		getterCalled();
104
		return property.containsKey(source, key);
105
	}
106
107
	public boolean containsValue(Object value) {
108
		getterCalled();
109
		return property.containsValue(source, value);
110
	}
111
112
	public Set entrySet() {
113
		getterCalled();
114
		// unmodifiable for now
115
		return Collections.unmodifiableSet(property.getMap(source).entrySet());
116
	}
117
118
	public Object get(Object key) {
119
		getterCalled();
120
		return property.get(source, key);
121
	}
122
123
	public boolean isEmpty() {
124
		getterCalled();
125
		return property.isEmpty(source);
126
	}
127
128
	public Set keySet() {
129
		getterCalled();
130
		return Collections.unmodifiableSet(property.getMap(source).keySet());
131
	}
132
133
	public Object put(Object key, Object value) {
134
		checkRealm();
135
136
		boolean add;
137
		Object oldValue;
138
139
		boolean wasUpdating = updating;
140
		updating = true;
141
		try {
142
			add = !property.containsKey(source, key);
143
			oldValue = property.put(source, key, value);
144
			modCount++;
145
		} finally {
146
			updating = wasUpdating;
147
		}
148
149
		cachedMap = property.getMap(source);
150
		MapDiff diff;
151
		if (add)
152
			diff = Diffs.createMapDiffSingleAdd(key, value);
153
		else
154
			diff = Diffs.createMapDiffSingleChange(key, oldValue, value);
155
		fireMapChange(diff);
156
157
		return property.put(source, key, value);
158
	}
159
160
	public void putAll(Map m) {
161
		checkRealm();
162
163
		Map oldValues = cachedMap;
164
		Set changedKeys = new HashSet();
165
		Set addedKeys = new HashSet();
166
		for (Iterator it = m.entrySet().iterator(); it.hasNext();) {
167
			Map.Entry entry = (Entry) it.next();
168
			Object key = entry.getKey();
169
			if (property.containsKey(source, key)) {
170
				changedKeys.add(key);
171
			} else {
172
				addedKeys.add(key);
173
			}
174
		}
175
176
		boolean wasUpdating = updating;
177
		updating = true;
178
		try {
179
			property.putAll(source, m);
180
			modCount++;
181
		} finally {
182
			updating = wasUpdating;
183
		}
184
185
		Map newValues = cachedMap = property.getMap(source);
186
		fireMapChange(Diffs.createMapDiff(addedKeys, Collections.EMPTY_SET,
187
				changedKeys, oldValues, newValues));
188
	}
189
190
	public Object remove(Object key) {
191
		checkRealm();
192
193
		if (!property.containsKey(source, key))
194
			return null;
195
196
		Object oldValue;
197
198
		boolean wasUpdating = updating;
199
		updating = true;
200
		try {
201
			oldValue = property.remove(source, key);
202
			modCount++;
203
		} finally {
204
			updating = wasUpdating;
205
		}
206
207
		cachedMap = property.getMap(source);
208
		fireMapChange(Diffs.createMapDiffSingleRemove(key, oldValue));
209
210
		return oldValue;
211
	}
212
213
	public int size() {
214
		getterCalled();
215
		return property.size(source);
216
	}
217
218
	public Collection values() {
219
		getterCalled();
220
		return Collections.unmodifiableCollection(property.getMap(source)
221
				.values());
222
	}
223
224
	public void clear() {
225
		getterCalled();
226
		property.clear(source);
227
	}
228
229
	public boolean equals(Object o) {
230
		getterCalled();
231
		return property.equals(source, o);
232
	}
233
234
	public int hashCode() {
235
		getterCalled();
236
		return property.hashCode(source);
237
	}
238
239
	public Object getObserved() {
240
		return source;
241
	}
242
243
	public IProperty getProperty() {
244
		return property;
245
	}
246
247
	public synchronized void dispose() {
248
		if (!isDisposed()) {
249
			if (listener != null)
250
				property.removeListener(source, listener);
251
			property = null;
252
			source = null;
253
			listener = null;
254
		}
255
		super.dispose();
256
	}
257
}
(-)src/org/eclipse/core/databinding/property/list/ListPropertyChangeEvent.java (+58 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.databinding.property.list;
13
14
import org.eclipse.core.databinding.observable.list.ListDiff;
15
import org.eclipse.core.databinding.property.IPropertyChangeListener;
16
import org.eclipse.core.databinding.property.PropertyChangeEvent;
17
18
/**
19
 * List change event describing an incremental change of a list property on a
20
 * particular property source.
21
 * 
22
 * @since 1.2
23
 */
24
public class ListPropertyChangeEvent extends PropertyChangeEvent {
25
	private static final long serialVersionUID = 1L;
26
27
	/**
28
	 * The list property that changed
29
	 */
30
	public final IListProperty property;
31
32
	/**
33
	 * ListDiff enumerating the added and removed elements in the list, or null
34
	 * if the change is unknown.
35
	 */
36
	public final ListDiff diff;
37
38
	/**
39
	 * Constructs a ListPropertyChangeEvent with the given attributes
40
	 * 
41
	 * @param source
42
	 *            the property source
43
	 * @param property
44
	 *            the property that changed on the source
45
	 * @param diff
46
	 *            a ListDiff describing the changes to the list property
47
	 */
48
	public ListPropertyChangeEvent(Object source, IListProperty property,
49
			ListDiff diff) {
50
		super(source);
51
		this.property = property;
52
		this.diff = diff;
53
	}
54
55
	protected void dispatch(IPropertyChangeListener listener) {
56
		((IListPropertyChangeListener) listener).handleListPropertyChange(this);
57
	}
58
}
(-)src/org/eclipse/core/databinding/property/map/MapPropertyChangeEvent.java (+58 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.databinding.property.map;
13
14
import org.eclipse.core.databinding.observable.map.MapDiff;
15
import org.eclipse.core.databinding.property.IPropertyChangeListener;
16
import org.eclipse.core.databinding.property.PropertyChangeEvent;
17
18
/**
19
 * Map change event describing an incremental change of a map property on a
20
 * particular property source.
21
 * 
22
 * @since 1.2
23
 */
24
public class MapPropertyChangeEvent extends PropertyChangeEvent {
25
	private static final long serialVersionUID = 1L;
26
27
	/**
28
	 * The map property that changed
29
	 */
30
	public final IMapProperty property;
31
32
	/**
33
	 * MapDiff enumerating the added, changed, and removed entries in the map,
34
	 * or null if the change is unknown.
35
	 */
36
	public final MapDiff diff;
37
38
	/**
39
	 * Constructs a MapPropertyChangeEvent with the given attributes
40
	 * 
41
	 * @param source
42
	 *            the property source
43
	 * @param property
44
	 *            the property that changed on the source
45
	 * @param diff
46
	 *            a MapDiff describing the changes to the map property
47
	 */
48
	public MapPropertyChangeEvent(Object source, IMapProperty property,
49
			MapDiff diff) {
50
		super(source);
51
		this.property = property;
52
		this.diff = diff;
53
	}
54
55
	protected void dispatch(IPropertyChangeListener listener) {
56
		((IMapPropertyChangeListener) listener).handleMapPropertyChange(this);
57
	}
58
}
(-)src/org/eclipse/core/databinding/property/Property.java (+26 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 194734)
10
 ******************************************************************************/
11
12
package org.eclipse.core.databinding.property;
13
14
/**
15
 * Abstract IProperty implementation
16
 */
17
public abstract class Property implements IProperty {
18
	/**
19
	 * Returns a string description of this property, suitable for debugging
20
	 * purposes
21
	 * 
22
	 * @return a string description of this property, suitable for debugging
23
	 *         purposes
24
	 */
25
	public abstract String toString();
26
}
(-)src/org/eclipse/jface/tests/databinding/swt/SWTObservablesTest.java (-62 / +124 lines)
Lines 7-45 Link Here
7
 *
7
 *
8
 * Contributors:
8
 * Contributors:
9
 *     Brad Reynolds - initial API and implementation
9
 *     Brad Reynolds - initial API and implementation
10
 *     Chris Aniszczyk <zx@code9.com> - bug 131435
10
 *     Matthew Hall - bug 248621
11
 *     Matthew Hall - bug 248621
11
 ******************************************************************************/
12
 ******************************************************************************/
12
13
13
package org.eclipse.jface.tests.databinding.swt;
14
package org.eclipse.jface.tests.databinding.swt;
14
15
16
import org.eclipse.core.databinding.observable.IDecoratingObservable;
15
import org.eclipse.core.databinding.observable.list.IObservableList;
17
import org.eclipse.core.databinding.observable.list.IObservableList;
18
import org.eclipse.core.databinding.property.IPropertyObservable;
19
import org.eclipse.jface.databinding.conformance.util.ChangeEventTracker;
16
import org.eclipse.jface.databinding.conformance.util.RealmTester;
20
import org.eclipse.jface.databinding.conformance.util.RealmTester;
21
import org.eclipse.jface.databinding.swt.ISWTObservable;
17
import org.eclipse.jface.databinding.swt.ISWTObservableValue;
22
import org.eclipse.jface.databinding.swt.ISWTObservableValue;
18
import org.eclipse.jface.databinding.swt.SWTObservables;
23
import org.eclipse.jface.databinding.swt.SWTObservables;
19
import org.eclipse.jface.internal.databinding.swt.ButtonObservableValue;
24
import org.eclipse.jface.internal.databinding.swt.CComboSelectionProperty;
20
import org.eclipse.jface.internal.databinding.swt.CComboObservableList;
25
import org.eclipse.jface.internal.databinding.swt.CComboTextProperty;
21
import org.eclipse.jface.internal.databinding.swt.CComboObservableValue;
26
import org.eclipse.jface.internal.databinding.swt.CLabelTextProperty;
22
import org.eclipse.jface.internal.databinding.swt.CLabelObservableValue;
27
import org.eclipse.jface.internal.databinding.swt.CTabItemTooltipTextProperty;
23
import org.eclipse.jface.internal.databinding.swt.ComboObservableList;
28
import org.eclipse.jface.internal.databinding.swt.ComboSelectionProperty;
24
import org.eclipse.jface.internal.databinding.swt.ComboObservableValue;
29
import org.eclipse.jface.internal.databinding.swt.ComboTextProperty;
25
import org.eclipse.jface.internal.databinding.swt.ControlObservableValue;
30
import org.eclipse.jface.internal.databinding.swt.ControlTooltipTextProperty;
26
import org.eclipse.jface.internal.databinding.swt.ItemObservableValue;
31
import org.eclipse.jface.internal.databinding.swt.ItemTextProperty;
27
import org.eclipse.jface.internal.databinding.swt.ItemTooltipObservableValue;
32
import org.eclipse.jface.internal.databinding.swt.LabelTextProperty;
28
import org.eclipse.jface.internal.databinding.swt.LabelObservableValue;
33
import org.eclipse.jface.internal.databinding.swt.ScaleMaximumProperty;
29
import org.eclipse.jface.internal.databinding.swt.ListObservableList;
34
import org.eclipse.jface.internal.databinding.swt.ScaleMinimumProperty;
30
import org.eclipse.jface.internal.databinding.swt.ListObservableValue;
35
import org.eclipse.jface.internal.databinding.swt.ScaleSelectionProperty;
31
import org.eclipse.jface.internal.databinding.swt.SWTProperties;
36
import org.eclipse.jface.internal.databinding.swt.SpinnerMaximumProperty;
32
import org.eclipse.jface.internal.databinding.swt.ScaleObservableValue;
37
import org.eclipse.jface.internal.databinding.swt.SpinnerMinimumProperty;
33
import org.eclipse.jface.internal.databinding.swt.SpinnerObservableValue;
38
import org.eclipse.jface.internal.databinding.swt.SpinnerSelectionProperty;
34
import org.eclipse.jface.internal.databinding.swt.TableSingleSelectionObservableValue;
39
import org.eclipse.jface.internal.databinding.swt.StyledTextTextProperty;
35
import org.eclipse.jface.internal.databinding.swt.TextEditableObservableValue;
40
import org.eclipse.jface.internal.databinding.swt.TableSingleSelectionIndexProperty;
36
import org.eclipse.jface.internal.databinding.swt.TextObservableValue;
41
import org.eclipse.jface.internal.databinding.swt.TextEditableProperty;
42
import org.eclipse.jface.internal.databinding.swt.TextTextProperty;
37
import org.eclipse.jface.tests.databinding.AbstractSWTTestCase;
43
import org.eclipse.jface.tests.databinding.AbstractSWTTestCase;
38
import org.eclipse.swt.SWT;
44
import org.eclipse.swt.SWT;
39
import org.eclipse.swt.custom.CCombo;
45
import org.eclipse.swt.custom.CCombo;
40
import org.eclipse.swt.custom.CLabel;
46
import org.eclipse.swt.custom.CLabel;
41
import org.eclipse.swt.custom.CTabFolder;
47
import org.eclipse.swt.custom.CTabFolder;
42
import org.eclipse.swt.custom.CTabItem;
48
import org.eclipse.swt.custom.CTabItem;
49
import org.eclipse.swt.custom.StyledText;
43
import org.eclipse.swt.graphics.Color;
50
import org.eclipse.swt.graphics.Color;
44
import org.eclipse.swt.graphics.Font;
51
import org.eclipse.swt.graphics.Font;
45
import org.eclipse.swt.widgets.Button;
52
import org.eclipse.swt.widgets.Button;
Lines 96-149 Link Here
96
		Spinner spinner = new Spinner(shell, SWT.NONE);
103
		Spinner spinner = new Spinner(shell, SWT.NONE);
97
		ISWTObservableValue value = SWTObservables.observeSelection(spinner);
104
		ISWTObservableValue value = SWTObservables.observeSelection(spinner);
98
		assertNotNull(value);
105
		assertNotNull(value);
99
		assertTrue(value instanceof SpinnerObservableValue);
106
		assertTrue(value.getWidget() == spinner);
100
107
101
		SpinnerObservableValue spinnerObservable = (SpinnerObservableValue) value;
108
		IPropertyObservable propertyObservable = getPropertyObservable(value);
102
		assertEquals(SWTProperties.SELECTION, spinnerObservable.getAttribute());
109
		assertTrue(propertyObservable.getProperty() instanceof SpinnerSelectionProperty);
103
	}
110
	}
104
111
105
	public void testObserveSelectionOfButton() throws Exception {
112
	public void testObserveSelectionOfButton() throws Exception {
106
		Button button = new Button(shell, SWT.PUSH);
113
		Button button = new Button(shell, SWT.PUSH);
107
		ISWTObservableValue value = SWTObservables.observeSelection(button);
114
		ISWTObservableValue value = SWTObservables.observeSelection(button);
108
		assertNotNull(value);
115
		assertNotNull(value);
109
		assertTrue(value instanceof ButtonObservableValue);
116
		assertTrue(value.getWidget() == button);
110
	}
117
	}
111
118
112
	public void testObserveSelectionOfCombo() throws Exception {
119
	public void testObserveSelectionOfCombo() throws Exception {
113
		Combo combo = new Combo(shell, SWT.NONE);
120
		Combo combo = new Combo(shell, SWT.NONE);
114
		ISWTObservableValue value = SWTObservables.observeSelection(combo);
121
		ISWTObservableValue value = SWTObservables.observeSelection(combo);
115
		assertNotNull(value);
122
		assertNotNull(value);
116
		assertTrue(value instanceof ComboObservableValue);
123
		assertTrue(value.getWidget() == combo);
117
124
118
		ComboObservableValue comboObservable = (ComboObservableValue) value;
125
		IPropertyObservable propertyObservable = getPropertyObservable(value);
119
		assertEquals(SWTProperties.SELECTION, comboObservable.getAttribute());
126
		assertTrue(propertyObservable.getProperty() instanceof ComboSelectionProperty);
120
	}
127
	}
121
128
122
	public void testObserveSelectionOfCCombo() throws Exception {
129
	public void testObserveSelectionOfCCombo() throws Exception {
123
		CCombo combo = new CCombo(shell, SWT.NONE);
130
		CCombo combo = new CCombo(shell, SWT.NONE);
124
		ISWTObservableValue value = SWTObservables.observeSelection(combo);
131
		ISWTObservableValue value = SWTObservables.observeSelection(combo);
125
		assertNotNull(value);
132
		assertNotNull(value);
126
		assertTrue(value instanceof CComboObservableValue);
133
		assertTrue(value.getWidget() == combo);
127
134
128
		CComboObservableValue ccomboObservable = (CComboObservableValue) value;
135
		IPropertyObservable property = getPropertyObservable(value);
129
		assertEquals(SWTProperties.SELECTION, ccomboObservable.getAttribute());
136
		assertTrue(property.getProperty() instanceof CComboSelectionProperty);
130
	}
137
	}
131
138
132
	public void testObserveSelectionOfList() throws Exception {
139
	public void testObserveSelectionOfList() throws Exception {
133
		List list = new List(shell, SWT.NONE);
140
		List list = new List(shell, SWT.NONE);
134
		ISWTObservableValue value = SWTObservables.observeSelection(list);
141
		ISWTObservableValue value = SWTObservables.observeSelection(list);
135
		assertNotNull(value);
142
		assertNotNull(value);
136
		assertTrue(value instanceof ListObservableValue);
143
		assertTrue(value.getWidget() == list);
137
	}
144
	}
138
	
145
	
139
	public void testObserveSelectionOfScale() throws Exception {
146
	public void testObserveSelectionOfScale() throws Exception {
140
		Scale scale = new Scale(shell, SWT.NONE);
147
		Scale scale = new Scale(shell, SWT.NONE);
141
		ISWTObservableValue value = SWTObservables.observeSelection(scale);
148
		ISWTObservableValue value = SWTObservables.observeSelection(scale);
142
		assertNotNull(value);
149
		assertNotNull(value);
143
		assertTrue(value instanceof ScaleObservableValue);
150
		assertTrue(value.getWidget() == scale);
144
		
151
		
145
		ScaleObservableValue scaleObservable = (ScaleObservableValue) value;
152
		IPropertyObservable property = getPropertyObservable(value);
146
		assertEquals(SWTProperties.SELECTION, scaleObservable.getAttribute());
153
		assertTrue(property.getProperty() instanceof ScaleSelectionProperty);
147
	}
154
	}
148
155
149
	public void testObserveSelectionOfUnsupportedControl() throws Exception {
156
	public void testObserveSelectionOfUnsupportedControl() throws Exception {
Lines 162-168 Link Here
162
		ISWTObservableValue value = SWTObservables.observeText(text,
169
		ISWTObservableValue value = SWTObservables.observeText(text,
163
				SWT.FocusOut);
170
				SWT.FocusOut);
164
		assertNotNull(value);
171
		assertNotNull(value);
165
		assertTrue(value instanceof TextObservableValue);
172
		assertTrue(value.getWidget() == text);
173
		IPropertyObservable propertyObservable = getPropertyObservable(value);
174
		assertTrue(propertyObservable.getProperty() instanceof TextTextProperty);
175
176
		assertFalse(text.isListening(SWT.FocusOut));
177
		ChangeEventTracker.observe(value);
178
		assertTrue(text.isListening(SWT.FocusOut));
179
	}
180
181
	public void testObserveTextOfStyledText() throws Exception {
182
		StyledText text = new StyledText(shell, SWT.NONE);
183
		assertFalse(text.isListening(SWT.FocusOut));
184
185
		ISWTObservableValue value = SWTObservables.observeText(text,
186
				SWT.FocusOut);
187
		assertNotNull(value);
188
		assertTrue(value.getWidget() == text);
189
		IPropertyObservable propertyObservable = getPropertyObservable(value);
190
		assertTrue(propertyObservable.getProperty() instanceof StyledTextTextProperty);
191
192
		assertFalse(text.isListening(SWT.FocusOut));
193
		ChangeEventTracker.observe(value);
166
		assertTrue(text.isListening(SWT.FocusOut));
194
		assertTrue(text.isListening(SWT.FocusOut));
167
	}
195
	}
168
196
Lines 179-219 Link Here
179
		Label label = new Label(shell, SWT.NONE);
207
		Label label = new Label(shell, SWT.NONE);
180
		ISWTObservableValue value = SWTObservables.observeText(label);
208
		ISWTObservableValue value = SWTObservables.observeText(label);
181
		assertNotNull(label);
209
		assertNotNull(label);
182
		assertTrue(value instanceof LabelObservableValue);
210
		assertTrue(value.getWidget() == label);
211
		IPropertyObservable propertyObservable = getPropertyObservable(value);
212
		assertTrue(propertyObservable.getProperty() instanceof LabelTextProperty);
183
	}
213
	}
184
214
185
	public void testObserveTextOfCLabel() throws Exception {
215
	public void testObserveTextOfCLabel() throws Exception {
186
		CLabel label = new CLabel(shell, SWT.NONE);
216
		CLabel label = new CLabel(shell, SWT.NONE);
187
		ISWTObservableValue value = SWTObservables.observeText(label);
217
		ISWTObservableValue value = SWTObservables.observeText(label);
188
		assertNotNull(label);
218
		assertNotNull(label);
189
		assertTrue(value instanceof CLabelObservableValue);
219
		assertTrue(value.getWidget() == label);
220
		IPropertyObservable propertyObservable = getPropertyObservable(value);
221
		assertTrue(propertyObservable.getProperty() instanceof CLabelTextProperty);
190
	}
222
	}
191
223
192
	public void testObserveTextOfCombo() throws Exception {
224
	public void testObserveTextOfCombo() throws Exception {
193
		Combo combo = new Combo(shell, SWT.NONE);
225
		Combo combo = new Combo(shell, SWT.NONE);
194
		ISWTObservableValue value = SWTObservables.observeText(combo);
226
		ISWTObservableValue value = SWTObservables.observeText(combo);
195
		assertNotNull(value);
227
		assertNotNull(value);
196
		assertTrue(value instanceof ComboObservableValue);
228
		assertTrue(value.getWidget() == combo);
197
229
198
		ComboObservableValue comboObservable = (ComboObservableValue) value;
230
		assertTrue(getPropertyObservable(value).getProperty() instanceof ComboTextProperty);
199
		assertEquals(SWTProperties.TEXT, comboObservable.getAttribute());
231
	}
232
233
	/**
234
	 * @param observable
235
	 * @return
236
	 */
237
	private IPropertyObservable getPropertyObservable(
238
			ISWTObservableValue observable) {
239
		IDecoratingObservable decoratingObservable = (IDecoratingObservable) observable;
240
		IPropertyObservable propertyObservable = (IPropertyObservable) decoratingObservable
241
				.getDecorated();
242
		return propertyObservable;
200
	}
243
	}
201
244
202
	public void testObserveTextOfCCombo() throws Exception {
245
	public void testObserveTextOfCCombo() throws Exception {
203
		CCombo combo = new CCombo(shell, SWT.NONE);
246
		CCombo combo = new CCombo(shell, SWT.NONE);
204
		ISWTObservableValue value = SWTObservables.observeText(combo);
247
		ISWTObservableValue value = SWTObservables.observeText(combo);
205
		assertNotNull(value);
248
		assertNotNull(value);
206
		assertTrue(value instanceof CComboObservableValue);
249
		assertTrue(value.getWidget() == combo);
207
250
208
		CComboObservableValue ccomboObservable = (CComboObservableValue) value;
251
		IDecoratingObservable decorating = (IDecoratingObservable) value;
209
		assertEquals(SWTProperties.TEXT, ccomboObservable.getAttribute());
252
		IPropertyObservable property = (IPropertyObservable) decorating
253
				.getDecorated();
254
		assertTrue(property.getProperty() instanceof CComboTextProperty);
210
	}
255
	}
211
256
212
	public void testObserveTextOfText() throws Exception {
257
	public void testObserveTextOfText() throws Exception {
213
		Text text = new Text(shell, SWT.NONE);
258
		Text text = new Text(shell, SWT.NONE);
214
		ISWTObservableValue value = SWTObservables.observeText(text);
259
		ISWTObservableValue value = SWTObservables.observeText(text);
215
		assertNotNull(value);
260
		assertNotNull(value);
216
		assertTrue(value instanceof TextObservableValue);
261
262
		assertTrue(value.getWidget() == text);
263
		IPropertyObservable propertyObservable = getPropertyObservable(value);
264
		assertTrue(propertyObservable.getProperty() instanceof TextTextProperty);
265
		
217
		assertFalse(text.isListening(SWT.Modify));
266
		assertFalse(text.isListening(SWT.Modify));
218
		assertFalse(text.isListening(SWT.FocusOut));
267
		assertFalse(text.isListening(SWT.FocusOut));
219
	}
268
	}
Lines 223-229 Link Here
223
		Item item = new CTabItem(ctf, SWT.NONE);
272
		Item item = new CTabItem(ctf, SWT.NONE);
224
		ISWTObservableValue value = SWTObservables.observeText(item);
273
		ISWTObservableValue value = SWTObservables.observeText(item);
225
		assertNotNull(value);
274
		assertNotNull(value);
226
		assertTrue(value instanceof ItemObservableValue);
275
		assertTrue(value.getWidget() == item);
276
		IPropertyObservable propertyObservable = getPropertyObservable(value);
277
		assertTrue(propertyObservable.getProperty() instanceof ItemTextProperty);
227
	}
278
	}
228
279
229
	public void testObserveTextOfUnsupportedControl() throws Exception {
280
	public void testObserveTextOfUnsupportedControl() throws Exception {
Lines 240-246 Link Here
240
		Item item = new CTabItem(ctf, SWT.NONE);
291
		Item item = new CTabItem(ctf, SWT.NONE);
241
		ISWTObservableValue value = SWTObservables.observeTooltipText(item);
292
		ISWTObservableValue value = SWTObservables.observeTooltipText(item);
242
		assertNotNull(value);
293
		assertNotNull(value);
243
		assertTrue(value instanceof ItemTooltipObservableValue);
294
		assertTrue(value.getWidget() == item);
295
		IPropertyObservable propertyObservable = getPropertyObservable(value);
296
		assertTrue(propertyObservable.getProperty() instanceof CTabItemTooltipTextProperty);
244
	}
297
	}
245
298
246
	public void testObserveTooltipOfUnsupportedControl() throws Exception {
299
	public void testObserveTooltipOfUnsupportedControl() throws Exception {
Lines 256-283 Link Here
256
		Label label = new Label(shell, SWT.NONE);
309
		Label label = new Label(shell, SWT.NONE);
257
		ISWTObservableValue value = SWTObservables.observeTooltipText(label);
310
		ISWTObservableValue value = SWTObservables.observeTooltipText(label);
258
		assertNotNull(value);
311
		assertNotNull(value);
259
		assertTrue(value instanceof ControlObservableValue);
312
		assertTrue(value.getWidget() == label);
313
		IPropertyObservable propertyObservable = getPropertyObservable(value);
314
		assertTrue(propertyObservable.getProperty() instanceof ControlTooltipTextProperty);
260
	}
315
	}
261
316
262
	public void testObserveItemsOfCombo() throws Exception {
317
	public void testObserveItemsOfCombo() throws Exception {
263
		Combo combo = new Combo(shell, SWT.NONE);
318
		Combo combo = new Combo(shell, SWT.NONE);
264
		IObservableList list = SWTObservables.observeItems(combo);
319
		IObservableList list = SWTObservables.observeItems(combo);
265
		assertNotNull(list);
320
		assertNotNull(list);
266
		assertTrue(list instanceof ComboObservableList);
321
		assertTrue(list instanceof ISWTObservable);
322
		assertTrue(((ISWTObservable) list).getWidget() == combo);
267
	}
323
	}
268
324
269
	public void testObserveItemsOfCCombo() throws Exception {
325
	public void testObserveItemsOfCCombo() throws Exception {
270
		CCombo ccombo = new CCombo(shell, SWT.NONE);
326
		CCombo ccombo = new CCombo(shell, SWT.NONE);
271
		IObservableList list = SWTObservables.observeItems(ccombo);
327
		IObservableList list = SWTObservables.observeItems(ccombo);
272
		assertNotNull(list);
328
		assertNotNull(list);
273
		assertTrue(list instanceof CComboObservableList);
329
		ISWTObservable swtObservable = (ISWTObservable) list;
330
		assertTrue(swtObservable.getWidget() == ccombo);
274
	}
331
	}
275
332
276
	public void testObserveItemsOfList() throws Exception {
333
	public void testObserveItemsOfList() throws Exception {
277
		List list = new List(shell, SWT.NONE);
334
		List list = new List(shell, SWT.NONE);
278
		IObservableList observableList = SWTObservables.observeItems(list);
335
		IObservableList observableList = SWTObservables.observeItems(list);
279
		assertNotNull(observableList);
336
		assertNotNull(observableList);
280
		assertTrue(observableList instanceof ListObservableList);
337
		ISWTObservable swtObservable = (ISWTObservable) observableList;
338
		assertTrue(swtObservable.getWidget() == list);
281
	}
339
	}
282
340
283
	public void testObserveItemsOfUnsupportedControl() throws Exception {
341
	public void testObserveItemsOfUnsupportedControl() throws Exception {
Lines 294-300 Link Here
294
		ISWTObservableValue value = SWTObservables
352
		ISWTObservableValue value = SWTObservables
295
				.observeSingleSelectionIndex(table);
353
				.observeSingleSelectionIndex(table);
296
		assertNotNull(value);
354
		assertNotNull(value);
297
		assertTrue(value instanceof TableSingleSelectionObservableValue);
355
		assertTrue(value.getWidget() == table);
356
		IPropertyObservable propertyObservable = getPropertyObservable(value);
357
		assertTrue(propertyObservable.getProperty() instanceof TableSingleSelectionIndexProperty);
298
	}
358
	}
299
359
300
	public void testObserveSingleSelectionIndexOfUnsupportedControl()
360
	public void testObserveSingleSelectionIndexOfUnsupportedControl()
Lines 312-331 Link Here
312
		Spinner spinner = new Spinner(shell, SWT.NONE);
372
		Spinner spinner = new Spinner(shell, SWT.NONE);
313
		ISWTObservableValue value = SWTObservables.observeMin(spinner);
373
		ISWTObservableValue value = SWTObservables.observeMin(spinner);
314
		assertNotNull(value);
374
		assertNotNull(value);
315
		assertTrue(value instanceof SpinnerObservableValue);
375
		assertTrue(value.getWidget() == spinner);
316
		
376
		
317
		SpinnerObservableValue spinnerObservable = (SpinnerObservableValue) value;
377
		IPropertyObservable propertyObservable = getPropertyObservable(value);
318
		assertEquals(SWTProperties.MIN, spinnerObservable.getAttribute());
378
		assertTrue(propertyObservable.getProperty() instanceof SpinnerMinimumProperty);
319
	}
379
	}
320
	
380
	
321
	public void testObserveMinOfScale() throws Exception {
381
	public void testObserveMinOfScale() throws Exception {
322
		Scale scale = new Scale(shell, SWT.NONE);
382
		Scale scale = new Scale(shell, SWT.NONE);
323
		ISWTObservableValue value = SWTObservables.observeMin(scale);
383
		ISWTObservableValue value = SWTObservables.observeMin(scale);
324
		assertNotNull(value);
384
		assertNotNull(value);
325
		assertTrue(value instanceof ScaleObservableValue);
385
		assertTrue(value.getWidget() == scale);
326
		
386
		
327
		ScaleObservableValue scaleObservable = (ScaleObservableValue) value;
387
		IPropertyObservable propertyObservable = getPropertyObservable(value);
328
		assertEquals(SWTProperties.MIN, scaleObservable.getAttribute());
388
		assertTrue(propertyObservable.getProperty() instanceof ScaleMinimumProperty);
329
	}
389
	}
330
390
331
	public void testObserveMinOfUnsupportedControl() throws Exception {
391
	public void testObserveMinOfUnsupportedControl() throws Exception {
Lines 341-360 Link Here
341
		Spinner spinner = new Spinner(shell, SWT.NONE);
401
		Spinner spinner = new Spinner(shell, SWT.NONE);
342
		ISWTObservableValue value = SWTObservables.observeMax(spinner);
402
		ISWTObservableValue value = SWTObservables.observeMax(spinner);
343
		assertNotNull(value);
403
		assertNotNull(value);
344
		assertTrue(value instanceof SpinnerObservableValue);
404
		assertTrue(value.getWidget() == spinner);
345
		
405
		
346
		SpinnerObservableValue spinnerObservable = (SpinnerObservableValue) value;
406
		IPropertyObservable propertyObservable = getPropertyObservable(value);
347
		assertEquals(SWTProperties.MAX, spinnerObservable.getAttribute());
407
		assertTrue(propertyObservable.getProperty() instanceof SpinnerMaximumProperty);
348
	}
408
	}
349
	
409
	
350
	public void testObserveMaxOfScale() throws Exception {
410
	public void testObserveMaxOfScale() throws Exception {
351
		Scale scale = new Scale(shell, SWT.NONE);
411
		Scale scale = new Scale(shell, SWT.NONE);
352
		ISWTObservableValue value = SWTObservables.observeMax(scale);
412
		ISWTObservableValue value = SWTObservables.observeMax(scale);
353
		assertNotNull(value);
413
		assertNotNull(value);
354
		assertTrue(value instanceof ScaleObservableValue);
414
		assertTrue(value.getWidget() == scale);
355
		
415
		
356
		ScaleObservableValue scaleObservable = (ScaleObservableValue) value;
416
		IPropertyObservable propertyObservable = getPropertyObservable(value);
357
		assertEquals(SWTProperties.MAX, scaleObservable.getAttribute());
417
		assertTrue(propertyObservable.getProperty() instanceof ScaleMaximumProperty);
358
	}
418
	}
359
	
419
	
360
	public void testObserveMaxOfUnsupportedControl() throws Exception {
420
	public void testObserveMaxOfUnsupportedControl() throws Exception {
Lines 370-376 Link Here
370
		Text text = new Text(shell, SWT.NONE);
430
		Text text = new Text(shell, SWT.NONE);
371
		ISWTObservableValue value = SWTObservables.observeEditable(text);
431
		ISWTObservableValue value = SWTObservables.observeEditable(text);
372
		assertNotNull(value);
432
		assertNotNull(value);
373
		assertTrue(value instanceof TextEditableObservableValue);
433
		assertTrue(value.getWidget() == text);
434
		IPropertyObservable propertyObservable = getPropertyObservable(value);
435
		assertTrue(propertyObservable.getProperty() instanceof TextEditableProperty);
374
	}
436
	}
375
	
437
	
376
	public void testObserveEditableOfUnsupportedControl() throws Exception {
438
	public void testObserveEditableOfUnsupportedControl() throws Exception {
(-)src/org/eclipse/jface/tests/internal/databinding/swt/ScaleObservableValueMaxTest.java (-6 / +7 lines)
Lines 7-13 Link Here
7
 *
7
 *
8
 * Contributors:
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
9
 *     IBM Corporation - initial API and implementation
10
 *     Matthew Hall - bug 213145
10
 *     Matthew Hall - bug 213145, 194734
11
 *******************************************************************************/
11
 *******************************************************************************/
12
12
13
package org.eclipse.jface.tests.internal.databinding.swt;
13
package org.eclipse.jface.tests.internal.databinding.swt;
Lines 22-29 Link Here
22
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
22
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
23
import org.eclipse.jface.databinding.conformance.swt.SWTMutableObservableValueContractTest;
23
import org.eclipse.jface.databinding.conformance.swt.SWTMutableObservableValueContractTest;
24
import org.eclipse.jface.databinding.swt.SWTObservables;
24
import org.eclipse.jface.databinding.swt.SWTObservables;
25
import org.eclipse.jface.internal.databinding.swt.SWTProperties;
25
import org.eclipse.jface.databinding.swt.ScaleProperties;
26
import org.eclipse.jface.internal.databinding.swt.ScaleObservableValue;
27
import org.eclipse.swt.SWT;
26
import org.eclipse.swt.SWT;
28
import org.eclipse.swt.widgets.Display;
27
import org.eclipse.swt.widgets.Display;
29
import org.eclipse.swt.widgets.Scale;
28
import org.eclipse.swt.widgets.Scale;
Lines 73-81 Link Here
73
	}
72
	}
74
73
75
	public static Test suite() {
74
	public static Test suite() {
76
		TestSuite suite = new TestSuite(ScaleObservableValueMaxTest.class.toString());
75
		TestSuite suite = new TestSuite(ScaleObservableValueMaxTest.class
76
				.toString());
77
		suite.addTestSuite(ScaleObservableValueMaxTest.class);
77
		suite.addTestSuite(ScaleObservableValueMaxTest.class);
78
		suite.addTest(SWTMutableObservableValueContractTest.suite(new Delegate()));
78
		suite.addTest(SWTMutableObservableValueContractTest
79
				.suite(new Delegate()));
79
		return suite;
80
		return suite;
80
	}
81
	}
81
82
Lines 96-102 Link Here
96
		}
97
		}
97
98
98
		public IObservableValue createObservableValue(Realm realm) {
99
		public IObservableValue createObservableValue(Realm realm) {
99
			return new ScaleObservableValue(realm, scale, SWTProperties.MAX);
100
			return ScaleProperties.maximum().observeValue(realm, scale);
100
		}
101
		}
101
102
102
		public void change(IObservable observable) {
103
		public void change(IObservable observable) {
(-)src/org/eclipse/jface/tests/internal/databinding/swt/TableSingleSelectionObservableValueTest.java (-17 / +23 lines)
Lines 7-13 Link Here
7
 *
7
 *
8
 * Contributors:
8
 * Contributors:
9
 *     Brad Reynolds - initial API and implementation
9
 *     Brad Reynolds - initial API and implementation
10
 *     Matthew Hall - bugs 118516, 213145
10
 *     Matthew Hall - bugs 118516, 213145, 194734
11
 ******************************************************************************/
11
 ******************************************************************************/
12
12
13
package org.eclipse.jface.tests.internal.databinding.swt;
13
package org.eclipse.jface.tests.internal.databinding.swt;
Lines 23-29 Link Here
23
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
23
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
24
import org.eclipse.jface.databinding.conformance.swt.SWTMutableObservableValueContractTest;
24
import org.eclipse.jface.databinding.conformance.swt.SWTMutableObservableValueContractTest;
25
import org.eclipse.jface.databinding.swt.SWTObservables;
25
import org.eclipse.jface.databinding.swt.SWTObservables;
26
import org.eclipse.jface.internal.databinding.swt.TableSingleSelectionObservableValue;
26
import org.eclipse.jface.databinding.swt.TableProperties;
27
import org.eclipse.swt.SWT;
27
import org.eclipse.swt.SWT;
28
import org.eclipse.swt.widgets.Display;
28
import org.eclipse.swt.widgets.Display;
29
import org.eclipse.swt.widgets.Shell;
29
import org.eclipse.swt.widgets.Shell;
Lines 33-66 Link Here
33
/**
33
/**
34
 * @since 3.2
34
 * @since 3.2
35
 */
35
 */
36
public class TableSingleSelectionObservableValueTest extends ObservableDelegateTest {
36
public class TableSingleSelectionObservableValueTest extends
37
		ObservableDelegateTest {
37
	private Delegate delegate;
38
	private Delegate delegate;
38
	private IObservableValue observable;
39
	private IObservableValue observable;
39
	private Table table;
40
	private Table table;
40
	
41
41
	public TableSingleSelectionObservableValueTest() {
42
	public TableSingleSelectionObservableValueTest() {
42
		this(null);
43
		this(null);
43
	}
44
	}
44
	
45
45
	public TableSingleSelectionObservableValueTest(String testName) {
46
	public TableSingleSelectionObservableValueTest(String testName) {
46
		super(testName, new Delegate());
47
		super(testName, new Delegate());
47
	}
48
	}
48
	
49
49
	protected void setUp() throws Exception {
50
	protected void setUp() throws Exception {
50
		super.setUp();
51
		super.setUp();
51
		
52
52
		observable = (IObservableValue) getObservable();
53
		observable = (IObservableValue) getObservable();
53
		delegate = (Delegate) getObservableContractDelegate();
54
		delegate = (Delegate) getObservableContractDelegate();
54
		table = delegate.table;
55
		table = delegate.table;
55
	}
56
	}
56
	
57
57
	protected IObservable doCreateObservable() {
58
	protected IObservable doCreateObservable() {
58
		Delegate delegate = (Delegate) getObservableContractDelegate();
59
		Delegate delegate = (Delegate) getObservableContractDelegate();
59
		return delegate.createObservableValue(SWTObservables.getRealm(Display.getDefault()));
60
		return delegate.createObservableValue(SWTObservables.getRealm(Display
61
				.getDefault()));
60
	}
62
	}
61
	
63
62
	public void testSetValue() throws Exception {
64
	public void testSetValue() throws Exception {
63
		//preconditions
65
		// preconditions
64
		assertEquals(-1, table.getSelectionIndex());
66
		assertEquals(-1, table.getSelectionIndex());
65
		assertEquals(-1, ((Integer) observable.getValue()).intValue());
67
		assertEquals(-1, ((Integer) observable.getValue()).intValue());
66
68
Lines 70-88 Link Here
70
				.getSelectionIndex());
72
				.getSelectionIndex());
71
		assertEquals("observable value", value, observable.getValue());
73
		assertEquals("observable value", value, observable.getValue());
72
	}
74
	}
73
	
75
74
	public void testGetValue() throws Exception {
76
	public void testGetValue() throws Exception {
75
		int value = 1;
77
		int value = 1;
76
		table.setSelection(value);
78
		table.setSelection(value);
77
		
79
78
		assertEquals("table selection index", value, table.getSelectionIndex());
80
		assertEquals("table selection index", value, table.getSelectionIndex());
79
		assertEquals("observable value", new Integer(value), observable.getValue());
81
		assertEquals("observable value", new Integer(value), observable
82
				.getValue());
80
	}
83
	}
81
84
82
	public static Test suite() {
85
	public static Test suite() {
83
		TestSuite suite = new TestSuite(TableSingleSelectionObservableValueTest.class.toString());
86
		TestSuite suite = new TestSuite(
87
				TableSingleSelectionObservableValueTest.class.toString());
84
		suite.addTestSuite(TableSingleSelectionObservableValueTest.class);
88
		suite.addTestSuite(TableSingleSelectionObservableValueTest.class);
85
		suite.addTest(SWTMutableObservableValueContractTest.suite(new Delegate()));
89
		suite.addTest(SWTMutableObservableValueContractTest
90
				.suite(new Delegate()));
86
		return suite;
91
		return suite;
87
	}
92
	}
88
93
Lines 104-110 Link Here
104
		}
109
		}
105
110
106
		public IObservableValue createObservableValue(Realm realm) {
111
		public IObservableValue createObservableValue(Realm realm) {
107
			return new TableSingleSelectionObservableValue(realm, table);
112
			return TableProperties.singleSelectionIndex().observeValue(realm,
113
					table);
108
		}
114
		}
109
115
110
		public Object getValueType(IObservableValue observable) {
116
		public Object getValueType(IObservableValue observable) {
(-)src/org/eclipse/jface/tests/internal/databinding/swt/CLabelObservableValueTest.java (-24 / +27 lines)
Lines 7-13 Link Here
7
 *
7
 *
8
 * Contributors:
8
 * Contributors:
9
 *     Brad Reynolds - initial API and implementation
9
 *     Brad Reynolds - initial API and implementation
10
 *     Matthew Hall - bug 213145
10
 *     Matthew Hall - bug 213145, 194734
11
 ******************************************************************************/
11
 ******************************************************************************/
12
12
13
package org.eclipse.jface.tests.internal.databinding.swt;
13
package org.eclipse.jface.tests.internal.databinding.swt;
Lines 21-28 Link Here
21
import org.eclipse.core.databinding.observable.value.IObservableValue;
21
import org.eclipse.core.databinding.observable.value.IObservableValue;
22
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
22
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
23
import org.eclipse.jface.databinding.conformance.swt.SWTMutableObservableValueContractTest;
23
import org.eclipse.jface.databinding.conformance.swt.SWTMutableObservableValueContractTest;
24
import org.eclipse.jface.databinding.swt.CLabelProperties;
24
import org.eclipse.jface.databinding.swt.SWTObservables;
25
import org.eclipse.jface.databinding.swt.SWTObservables;
25
import org.eclipse.jface.internal.databinding.swt.CLabelObservableValue;
26
import org.eclipse.swt.SWT;
26
import org.eclipse.swt.SWT;
27
import org.eclipse.swt.custom.CLabel;
27
import org.eclipse.swt.custom.CLabel;
28
import org.eclipse.swt.widgets.Display;
28
import org.eclipse.swt.widgets.Display;
Lines 36-73 Link Here
36
	private Delegate delegate;
36
	private Delegate delegate;
37
	private IObservableValue observable;
37
	private IObservableValue observable;
38
	private CLabel label;
38
	private CLabel label;
39
	
39
40
	protected void setUp() throws Exception {
40
	protected void setUp() throws Exception {
41
		super.setUp();
41
		super.setUp();
42
		
42
43
		delegate = new Delegate();
43
		delegate = new Delegate();
44
		delegate.setUp();
44
		delegate.setUp();
45
		label = delegate.label;
45
		label = delegate.label;
46
		observable = delegate.createObservableValue(SWTObservables.getRealm(Display.getDefault()));
46
		observable = delegate.createObservableValue(SWTObservables
47
				.getRealm(Display.getDefault()));
47
	}
48
	}
48
	
49
49
	protected void tearDown() throws Exception {
50
	protected void tearDown() throws Exception {
50
		super.tearDown();
51
		super.tearDown();
51
		
52
52
		delegate.tearDown();
53
		delegate.tearDown();
53
		observable.dispose();
54
		observable.dispose();
54
	}
55
	}
55
	
56
56
    public void testSetValue() throws Exception {
57
	public void testSetValue() throws Exception {
57
    	//preconditions
58
		// preconditions
58
        assertEquals(null, label.getText());
59
		assertEquals(null, label.getText());
59
        assertEquals(null, observable.getValue());
60
		assertEquals(null, observable.getValue());
60
        
61
61
        String value = "value";
62
		String value = "value";
62
        observable.setValue(value);
63
		observable.setValue(value);
63
        assertEquals("label text", value, label.getText());
64
		assertEquals("label text", value, label.getText());
64
        assertEquals("observable value", value, observable.getValue());
65
		assertEquals("observable value", value, observable.getValue());
65
    }
66
	}
66
	
67
67
	public static Test suite() {
68
	public static Test suite() {
68
		TestSuite suite = new TestSuite(CLabelObservableValueTest.class.getName());
69
		TestSuite suite = new TestSuite(CLabelObservableValueTest.class
70
				.getName());
69
		suite.addTestSuite(CLabelObservableValueTest.class);
71
		suite.addTestSuite(CLabelObservableValueTest.class);
70
		suite.addTest(SWTMutableObservableValueContractTest.suite(new Delegate()));
72
		suite.addTest(SWTMutableObservableValueContractTest
73
				.suite(new Delegate()));
71
		return suite;
74
		return suite;
72
	}
75
	}
73
76
Lines 87-104 Link Here
87
		}
90
		}
88
91
89
		public IObservableValue createObservableValue(Realm realm) {
92
		public IObservableValue createObservableValue(Realm realm) {
90
			return new CLabelObservableValue(realm, label);
93
			return CLabelProperties.text().observeValue(realm, label);
91
		}
94
		}
92
95
93
		public void change(IObservable observable) {
96
		public void change(IObservable observable) {
94
			IObservableValue value = (IObservableValue) observable;
97
			IObservableValue value = (IObservableValue) observable;
95
			value.setValue(value.getValue() + "a");
98
			value.setValue(value.getValue() + "a");
96
		}
99
		}
97
		
100
98
		public Object getValueType(IObservableValue observable) {
101
		public Object getValueType(IObservableValue observable) {
99
			return String.class;
102
			return String.class;
100
		}
103
		}
101
		
104
102
		public Object createValue(IObservableValue observable) {
105
		public Object createValue(IObservableValue observable) {
103
			return observable.getValue() + "a";
106
			return observable.getValue() + "a";
104
		}
107
		}
(-)src/org/eclipse/jface/tests/internal/databinding/swt/SpinnerObservableValueTest.java (-4 / +4 lines)
Lines 8-20 Link Here
8
 * Contributors:
8
 * Contributors:
9
 *     Brad Reynolds - initial API and implementation
9
 *     Brad Reynolds - initial API and implementation
10
 *     Ashley Cambrell - bug 198904
10
 *     Ashley Cambrell - bug 198904
11
 *     Matthew Hall - bug 194734
11
 ******************************************************************************/
12
 ******************************************************************************/
12
13
13
package org.eclipse.jface.tests.internal.databinding.swt;
14
package org.eclipse.jface.tests.internal.databinding.swt;
14
15
15
import org.eclipse.jface.databinding.conformance.util.ValueChangeEventTracker;
16
import org.eclipse.jface.databinding.conformance.util.ValueChangeEventTracker;
16
import org.eclipse.jface.internal.databinding.swt.SWTProperties;
17
import org.eclipse.jface.databinding.swt.ISWTObservableValue;
17
import org.eclipse.jface.internal.databinding.swt.SpinnerObservableValue;
18
import org.eclipse.jface.databinding.swt.SWTObservables;
18
import org.eclipse.jface.tests.databinding.AbstractSWTTestCase;
19
import org.eclipse.jface.tests.databinding.AbstractSWTTestCase;
19
import org.eclipse.swt.SWT;
20
import org.eclipse.swt.SWT;
20
import org.eclipse.swt.widgets.Spinner;
21
import org.eclipse.swt.widgets.Spinner;
Lines 26-33 Link Here
26
public class SpinnerObservableValueTest extends AbstractSWTTestCase {
27
public class SpinnerObservableValueTest extends AbstractSWTTestCase {
27
	public void testDispose() throws Exception {
28
	public void testDispose() throws Exception {
28
		Spinner spinner = new Spinner(getShell(), SWT.NONE);
29
		Spinner spinner = new Spinner(getShell(), SWT.NONE);
29
		SpinnerObservableValue observableValue = new SpinnerObservableValue(
30
		ISWTObservableValue observableValue = SWTObservables.observeSelection(spinner);
30
				spinner, SWTProperties.SELECTION);
31
		ValueChangeEventTracker testCounterValueChangeListener = new ValueChangeEventTracker();
31
		ValueChangeEventTracker testCounterValueChangeListener = new ValueChangeEventTracker();
32
		observableValue.addValueChangeListener(testCounterValueChangeListener);
32
		observableValue.addValueChangeListener(testCounterValueChangeListener);
33
33
(-)src/org/eclipse/jface/tests/internal/databinding/swt/ScaleObservableValueSelectionTest.java (-7 / +7 lines)
Lines 7-13 Link Here
7
 *
7
 *
8
 * Contributors:
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
9
 *     IBM Corporation - initial API and implementation
10
 *     Matthew Hall - bug 213145
10
 *     Matthew Hall - bug 213145, 194734
11
 *******************************************************************************/
11
 *******************************************************************************/
12
12
13
package org.eclipse.jface.tests.internal.databinding.swt;
13
package org.eclipse.jface.tests.internal.databinding.swt;
Lines 22-29 Link Here
22
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
22
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
23
import org.eclipse.jface.databinding.conformance.swt.SWTMutableObservableValueContractTest;
23
import org.eclipse.jface.databinding.conformance.swt.SWTMutableObservableValueContractTest;
24
import org.eclipse.jface.databinding.swt.SWTObservables;
24
import org.eclipse.jface.databinding.swt.SWTObservables;
25
import org.eclipse.jface.internal.databinding.swt.SWTProperties;
25
import org.eclipse.jface.databinding.swt.ScaleProperties;
26
import org.eclipse.jface.internal.databinding.swt.ScaleObservableValue;
27
import org.eclipse.swt.SWT;
26
import org.eclipse.swt.SWT;
28
import org.eclipse.swt.widgets.Display;
27
import org.eclipse.swt.widgets.Display;
29
import org.eclipse.swt.widgets.Scale;
28
import org.eclipse.swt.widgets.Scale;
Lines 42-52 Link Here
42
	public ScaleObservableValueSelectionTest() {
41
	public ScaleObservableValueSelectionTest() {
43
		this(null);
42
		this(null);
44
	}
43
	}
45
	
44
46
	public ScaleObservableValueSelectionTest(String testName) {
45
	public ScaleObservableValueSelectionTest(String testName) {
47
		super(testName, new Delegate());
46
		super(testName, new Delegate());
48
	}
47
	}
49
	
48
50
	protected void setUp() throws Exception {
49
	protected void setUp() throws Exception {
51
		super.setUp();
50
		super.setUp();
52
51
Lines 56-62 Link Here
56
	}
55
	}
57
56
58
	protected IObservable doCreateObservable() {
57
	protected IObservable doCreateObservable() {
59
		return getObservableContractDelegate().createObservable(SWTObservables.getRealm(Display.getDefault()));
58
		return getObservableContractDelegate().createObservable(
59
				SWTObservables.getRealm(Display.getDefault()));
60
	}
60
	}
61
61
62
	public void testGetValue() throws Exception {
62
	public void testGetValue() throws Exception {
Lines 97-103 Link Here
97
		}
97
		}
98
98
99
		public IObservableValue createObservableValue(Realm realm) {
99
		public IObservableValue createObservableValue(Realm realm) {
100
			return new ScaleObservableValue(realm, scale, SWTProperties.SELECTION);
100
			return ScaleProperties.selection().observeValue(realm, scale);
101
		}
101
		}
102
102
103
		public void change(IObservable observable) {
103
		public void change(IObservable observable) {
(-)src/org/eclipse/jface/tests/internal/databinding/swt/SWTObservableListTest.java (-115 lines)
Removed Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2007 Matthew Hall and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 208858)
10
 *     Matthew Hall - bug 213145
11
 ******************************************************************************/
12
13
package org.eclipse.jface.tests.internal.databinding.swt;
14
15
import junit.framework.Test;
16
import junit.framework.TestSuite;
17
18
import org.eclipse.core.databinding.observable.IObservable;
19
import org.eclipse.core.databinding.observable.IObservableCollection;
20
import org.eclipse.core.databinding.observable.Realm;
21
import org.eclipse.jface.databinding.conformance.MutableObservableListContractTest;
22
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableCollectionContractDelegate;
23
import org.eclipse.jface.internal.databinding.swt.SWTObservableList;
24
import org.eclipse.jface.tests.databinding.AbstractDefaultRealmTestCase;
25
26
/**
27
 * @since 3.3
28
 */
29
public class SWTObservableListTest extends AbstractDefaultRealmTestCase {
30
	SWTObservableListStub list;
31
32
	protected void setUp() throws Exception {
33
		super.setUp();
34
		list = new SWTObservableListStub(Realm.getDefault(), 0);
35
	}
36
37
	public void testMove_ForwardAndBackward() {
38
		String element0 = "element0";
39
		String element1 = "element1";
40
41
		list.add(element0);
42
		list.add(element1);
43
44
		// move forward
45
		assertEquals(element0, list.move(0, 1));
46
		assertEquals(element1, list.move(0, 1));
47
48
		// move backward
49
		assertEquals(element1, list.move(1, 0));
50
		assertEquals(element0, list.move(1, 0));
51
	}
52
53
	public static Test suite() {
54
		TestSuite suite = new TestSuite(SWTObservableListTest.class.toString());
55
		suite.addTestSuite(SWTObservableListTest.class);
56
		suite.addTest(MutableObservableListContractTest.suite(new Delegate()));
57
		return suite;
58
	}
59
60
	static class Delegate extends AbstractObservableCollectionContractDelegate {
61
		public IObservableCollection createObservableCollection(Realm realm,
62
				int elementCount) {
63
			return new SWTObservableListStub(realm, elementCount);
64
		}
65
66
		private int counter;
67
68
		public Object createElement(IObservableCollection collection) {
69
			return "Item" + counter++;
70
		}
71
72
		public Object getElementType(IObservableCollection collection) {
73
			return String.class;
74
		}
75
76
		public void change(IObservable observable) {
77
			((SWTObservableListStub) observable).fireChange();
78
		}
79
	}
80
81
	static class SWTObservableListStub extends SWTObservableList {
82
		String[] items;
83
84
		public SWTObservableListStub(Realm realm, int elementCount) {
85
			super(realm);
86
			items = new String[elementCount];
87
			for (int i = 0; i < items.length; i++)
88
				items[i] = Integer.toString(i);
89
		}
90
91
		protected String getItem(int index) {
92
			return items[index];
93
		}
94
95
		protected int getItemCount() {
96
			return items.length;
97
		}
98
99
		protected String[] getItems() {
100
			return items;
101
		}
102
103
		protected void setItem(int index, String string) {
104
			items[index] = string;
105
		}
106
107
		protected void setItems(String[] newItems) {
108
			items = newItems;
109
		}
110
111
		protected void fireChange() {
112
			super.fireChange();
113
		}
114
	}
115
}
(-)src/org/eclipse/jface/tests/internal/databinding/swt/TableObservableValueTest.java (-3 / +5 lines)
Lines 8-18 Link Here
8
 * Contributors:
8
 * Contributors:
9
 *     Brad Reynolds - initial API and implementation
9
 *     Brad Reynolds - initial API and implementation
10
 *     Ashley Cambrell - bug 198904
10
 *     Ashley Cambrell - bug 198904
11
 *     Matthew Hall - bug 194734
11
 ******************************************************************************/
12
 ******************************************************************************/
12
13
13
package org.eclipse.jface.tests.internal.databinding.swt;
14
package org.eclipse.jface.tests.internal.databinding.swt;
14
15
15
import org.eclipse.jface.internal.databinding.swt.TableSingleSelectionObservableValue;
16
import org.eclipse.core.databinding.observable.value.IObservableValue;
17
import org.eclipse.jface.databinding.swt.SWTObservables;
16
import org.eclipse.jface.tests.databinding.AbstractSWTTestCase;
18
import org.eclipse.jface.tests.databinding.AbstractSWTTestCase;
17
import org.eclipse.swt.SWT;
19
import org.eclipse.swt.SWT;
18
import org.eclipse.swt.widgets.Table;
20
import org.eclipse.swt.widgets.Table;
Lines 24-31 Link Here
24
public class TableObservableValueTest extends AbstractSWTTestCase {
26
public class TableObservableValueTest extends AbstractSWTTestCase {
25
	public void testDispose() throws Exception {
27
	public void testDispose() throws Exception {
26
		Table table = new Table(getShell(), SWT.NONE);
28
		Table table = new Table(getShell(), SWT.NONE);
27
		TableSingleSelectionObservableValue observableValue = new TableSingleSelectionObservableValue(
29
		IObservableValue observableValue = SWTObservables
28
				table);
30
				.observeSingleSelectionIndex(table);
29
31
30
		TableItem item1 = new TableItem(table, SWT.NONE);
32
		TableItem item1 = new TableItem(table, SWT.NONE);
31
		item1.setText("Item1");
33
		item1.setText("Item1");
(-)src/org/eclipse/jface/tests/internal/databinding/swt/TextObservableValueFocusOutTest.java (-8 / +10 lines)
Lines 7-13 Link Here
7
 *
7
 *
8
 * Contributors:
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
9
 *     IBM Corporation - initial API and implementation
10
 *     Matthew Hall - bug 213145
10
 *     Matthew Hall - bug 213145, 194734
11
 *******************************************************************************/
11
 *******************************************************************************/
12
12
13
package org.eclipse.jface.tests.internal.databinding.swt;
13
package org.eclipse.jface.tests.internal.databinding.swt;
Lines 21-27 Link Here
21
import org.eclipse.core.databinding.observable.value.IObservableValue;
21
import org.eclipse.core.databinding.observable.value.IObservableValue;
22
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
22
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
23
import org.eclipse.jface.databinding.conformance.swt.SWTMutableObservableValueContractTest;
23
import org.eclipse.jface.databinding.conformance.swt.SWTMutableObservableValueContractTest;
24
import org.eclipse.jface.internal.databinding.swt.TextObservableValue;
24
import org.eclipse.jface.databinding.swt.TextProperties;
25
import org.eclipse.swt.SWT;
25
import org.eclipse.swt.SWT;
26
import org.eclipse.swt.widgets.Shell;
26
import org.eclipse.swt.widgets.Shell;
27
import org.eclipse.swt.widgets.Text;
27
import org.eclipse.swt.widgets.Text;
Lines 31-38 Link Here
31
 */
31
 */
32
public class TextObservableValueFocusOutTest extends TestCase {
32
public class TextObservableValueFocusOutTest extends TestCase {
33
	public static Test suite() {
33
	public static Test suite() {
34
		TestSuite suite = new TestSuite(TextObservableValueFocusOutTest.class.toString());
34
		TestSuite suite = new TestSuite(TextObservableValueFocusOutTest.class
35
		suite.addTest(SWTMutableObservableValueContractTest.suite(new Delegate()));
35
				.toString());
36
		suite.addTest(SWTMutableObservableValueContractTest
37
				.suite(new Delegate()));
36
		return suite;
38
		return suite;
37
	}
39
	}
38
40
Lines 41-47 Link Here
41
		private Shell shell;
43
		private Shell shell;
42
44
43
		private Text text;
45
		private Text text;
44
		
46
45
		public void setUp() {
47
		public void setUp() {
46
			shell = new Shell();
48
			shell = new Shell();
47
			text = new Text(shell, SWT.NONE);
49
			text = new Text(shell, SWT.NONE);
Lines 52-58 Link Here
52
		}
54
		}
53
55
54
		public IObservableValue createObservableValue(Realm realm) {
56
		public IObservableValue createObservableValue(Realm realm) {
55
			return new TextObservableValue(realm, text, SWT.FocusOut);
57
			return TextProperties.text(SWT.FocusOut).observeValue(realm, text);
56
		}
58
		}
57
59
58
		public Object getValueType(IObservableValue observable) {
60
		public Object getValueType(IObservableValue observable) {
Lines 61-70 Link Here
61
63
62
		public void change(IObservable observable) {
64
		public void change(IObservable observable) {
63
			text.setFocus();
65
			text.setFocus();
64
			
66
65
			IObservableValue observableValue = (IObservableValue) observable;
67
			IObservableValue observableValue = (IObservableValue) observable;
66
			text.setText((String) createValue(observableValue));
68
			text.setText((String) createValue(observableValue));
67
			
69
68
			text.notifyListeners(SWT.FocusOut, null);
70
			text.notifyListeners(SWT.FocusOut, null);
69
		}
71
		}
70
72
(-)src/org/eclipse/jface/tests/internal/databinding/swt/TextEditableObservableValueTest.java (-28 / +34 lines)
Lines 7-13 Link Here
7
 *
7
 *
8
 * Contributors:
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
9
 *     IBM Corporation - initial API and implementation
10
 *     Matthew Hall - bug 213145
10
 *     Matthew Hall - bug 213145, 194734
11
 *******************************************************************************/
11
 *******************************************************************************/
12
12
13
package org.eclipse.jface.tests.internal.databinding.swt;
13
package org.eclipse.jface.tests.internal.databinding.swt;
Lines 21-27 Link Here
21
import org.eclipse.jface.databinding.conformance.ObservableDelegateTest;
21
import org.eclipse.jface.databinding.conformance.ObservableDelegateTest;
22
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
22
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
23
import org.eclipse.jface.databinding.conformance.swt.SWTMutableObservableValueContractTest;
23
import org.eclipse.jface.databinding.conformance.swt.SWTMutableObservableValueContractTest;
24
import org.eclipse.jface.internal.databinding.swt.TextEditableObservableValue;
24
import org.eclipse.jface.databinding.swt.TextProperties;
25
import org.eclipse.swt.SWT;
25
import org.eclipse.swt.SWT;
26
import org.eclipse.swt.widgets.Shell;
26
import org.eclipse.swt.widgets.Shell;
27
import org.eclipse.swt.widgets.Text;
27
import org.eclipse.swt.widgets.Text;
Lines 29-37 Link Here
29
/**
29
/**
30
 * @since 1.1
30
 * @since 1.1
31
 */
31
 */
32
public class TextEditableObservableValueTest extends
32
public class TextEditableObservableValueTest extends ObservableDelegateTest {
33
		ObservableDelegateTest {
33
34
	
35
	private Delegate delegate;
34
	private Delegate delegate;
36
	private Text text;
35
	private Text text;
37
	private IObservableValue observable;
36
	private IObservableValue observable;
Lines 39-116 Link Here
39
	public TextEditableObservableValueTest() {
38
	public TextEditableObservableValueTest() {
40
		this(null);
39
		this(null);
41
	}
40
	}
42
	
41
43
	public TextEditableObservableValueTest(String testName) {
42
	public TextEditableObservableValueTest(String testName) {
44
		super(testName, new Delegate());
43
		super(testName, new Delegate());
45
	}
44
	}
46
45
47
	/* (non-Javadoc)
46
	/*
48
	 * @see org.eclipse.jface.conformance.databinding.ObservableDelegateTest#setUp()
47
	 * (non-Javadoc)
48
	 * 
49
	 * @see
50
	 * org.eclipse.jface.conformance.databinding.ObservableDelegateTest#setUp()
49
	 */
51
	 */
50
	protected void setUp() throws Exception {
52
	protected void setUp() throws Exception {
51
		super.setUp();
53
		super.setUp();
52
		
54
53
		delegate = (Delegate) getObservableContractDelegate();
55
		delegate = (Delegate) getObservableContractDelegate();
54
		observable = (IObservableValue) getObservable();
56
		observable = (IObservableValue) getObservable();
55
		text = delegate.text;
57
		text = delegate.text;
56
	}
58
	}
57
	
59
58
	protected IObservable doCreateObservable() {
60
	protected IObservable doCreateObservable() {
59
		return super.doCreateObservable();
61
		return super.doCreateObservable();
60
	}
62
	}
61
	
63
62
	public void testGetValue() throws Exception {
64
	public void testGetValue() throws Exception {
63
		text.setEditable(false);
65
		text.setEditable(false);
64
		assertEquals(Boolean.valueOf(text.getEditable()), observable.getValue());
66
		assertEquals(Boolean.valueOf(text.getEditable()), observable.getValue());
65
		
67
66
		text.setEditable(true);
68
		text.setEditable(true);
67
		assertEquals(Boolean.valueOf(text.getEditable()), observable.getValue());
69
		assertEquals(Boolean.valueOf(text.getEditable()), observable.getValue());
68
	}
70
	}
69
	
71
70
	public void testSetValue() throws Exception {
72
	public void testSetValue() throws Exception {
71
		text.setEditable(false);
73
		text.setEditable(false);
72
		observable.setValue(Boolean.TRUE);
74
		observable.setValue(Boolean.TRUE);
73
		assertEquals(Boolean.TRUE, Boolean.valueOf(text.getEditable()));
75
		assertEquals(Boolean.TRUE, Boolean.valueOf(text.getEditable()));
74
		
76
75
		observable.setValue(Boolean.FALSE);
77
		observable.setValue(Boolean.FALSE);
76
		assertEquals(Boolean.FALSE, Boolean.valueOf(text.getEditable()));
78
		assertEquals(Boolean.FALSE, Boolean.valueOf(text.getEditable()));
77
	}
79
	}
78
	
80
79
	public static Test suite() {
81
	public static Test suite() {
80
		TestSuite suite = new TestSuite(TextEditableObservableValueTest.class.toString());
82
		TestSuite suite = new TestSuite(TextEditableObservableValueTest.class
83
				.toString());
81
		suite.addTestSuite(TextEditableObservableValueTest.class);
84
		suite.addTestSuite(TextEditableObservableValueTest.class);
82
		suite.addTest(SWTMutableObservableValueContractTest.suite(new Delegate()));
85
		suite.addTest(SWTMutableObservableValueContractTest
86
				.suite(new Delegate()));
83
		return suite;
87
		return suite;
84
	}
88
	}
85
	
89
86
	/*package*/ static class Delegate extends AbstractObservableValueContractDelegate {
90
	/* package */static class Delegate extends
91
			AbstractObservableValueContractDelegate {
87
		private Shell shell;
92
		private Shell shell;
88
		Text text;
93
		Text text;
89
		
94
90
		public void setUp() {			
95
		public void setUp() {
91
			shell = new Shell();
96
			shell = new Shell();
92
			text = new Text(shell, SWT.NONE);
97
			text = new Text(shell, SWT.NONE);
93
		}
98
		}
94
99
95
		public void tearDown() {			
100
		public void tearDown() {
96
			shell.dispose();
101
			shell.dispose();
97
		}
102
		}
98
		
103
99
		public IObservableValue createObservableValue(Realm realm) {
104
		public IObservableValue createObservableValue(Realm realm) {
100
			return new TextEditableObservableValue(realm, text);
105
			return TextProperties.editable().observeValue(realm, text);
101
		}
106
		}
102
		
107
103
		public Object getValueType(IObservableValue observable) {
108
		public Object getValueType(IObservableValue observable) {
104
			return Boolean.TYPE;
109
			return Boolean.TYPE;
105
		}
110
		}
106
		
111
107
		public void change(IObservable observable) {
112
		public void change(IObservable observable) {
108
			IObservableValue observableValue = (IObservableValue) observable;
113
			IObservableValue observableValue = (IObservableValue) observable;
109
			observableValue.setValue(createValue(observableValue));
114
			observableValue.setValue(createValue(observableValue));
110
		}
115
		}
111
		
116
112
		public Object createValue(IObservableValue observable) {
117
		public Object createValue(IObservableValue observable) {
113
			return (Boolean.TRUE.equals(observable.getValue()) ? Boolean.FALSE: Boolean.TRUE);
118
			return (Boolean.TRUE.equals(observable.getValue()) ? Boolean.FALSE
119
					: Boolean.TRUE);
114
		}
120
		}
115
	}
121
	}
116
}
122
}
(-)src/org/eclipse/jface/tests/internal/databinding/swt/ControlObservableValueTest.java (-40 / +23 lines)
Lines 8-19 Link Here
8
 * Contributors:
8
 * Contributors:
9
 *     Brad Reynolds - initial API and implementation
9
 *     Brad Reynolds - initial API and implementation
10
 *     Brad Reynolds - bug 170848
10
 *     Brad Reynolds - bug 170848
11
 *     Matthew Hall - bug 194734
11
 ******************************************************************************/
12
 ******************************************************************************/
12
13
13
package org.eclipse.jface.tests.internal.databinding.swt;
14
package org.eclipse.jface.tests.internal.databinding.swt;
14
15
15
import org.eclipse.jface.internal.databinding.swt.ControlObservableValue;
16
import org.eclipse.jface.databinding.swt.ISWTObservableValue;
16
import org.eclipse.jface.internal.databinding.swt.SWTProperties;
17
import org.eclipse.jface.databinding.swt.SWTObservables;
17
import org.eclipse.jface.resource.JFaceResources;
18
import org.eclipse.jface.resource.JFaceResources;
18
import org.eclipse.jface.tests.databinding.AbstractDefaultRealmTestCase;
19
import org.eclipse.jface.tests.databinding.AbstractDefaultRealmTestCase;
19
import org.eclipse.swt.SWT;
20
import org.eclipse.swt.SWT;
Lines 47-95 Link Here
47
	}
48
	}
48
49
49
	public void testSetValueEnabled() throws Exception {
50
	public void testSetValueEnabled() throws Exception {
50
		ControlObservableValue observableValue = new ControlObservableValue(
51
		ISWTObservableValue observableValue = SWTObservables
51
				shell, SWTProperties.ENABLED);
52
				.observeEnabled(shell);
52
		Boolean value = Boolean.FALSE;
53
		Boolean value = Boolean.FALSE;
53
		observableValue.setValue(value);
54
		observableValue.setValue(value);
54
		assertFalse(shell.isEnabled());
55
		assertFalse(shell.isEnabled());
55
	}
56
	}
56
57
57
	public void testGetValueEnabled() throws Exception {
58
	public void testGetValueEnabled() throws Exception {
58
		ControlObservableValue value = new ControlObservableValue(shell,
59
		ISWTObservableValue value = SWTObservables.observeEnabled(shell);
59
				SWTProperties.ENABLED);
60
		shell.setEnabled(false);
60
		shell.setEnabled(false);
61
		assertEquals(Boolean.FALSE, value.getValue());
61
		assertEquals(Boolean.FALSE, value.getValue());
62
	}
62
	}
63
63
64
	public void testGetValueTypeEnabled() throws Exception {
64
	public void testGetValueTypeEnabled() throws Exception {
65
		ControlObservableValue value = new ControlObservableValue(shell,
65
		ISWTObservableValue value = SWTObservables.observeEnabled(shell);
66
				SWTProperties.ENABLED);
67
		assertEquals(boolean.class, value.getValueType());
66
		assertEquals(boolean.class, value.getValueType());
68
	}
67
	}
69
68
70
	public void testSetValueVisible() throws Exception {
69
	public void testSetValueVisible() throws Exception {
71
		ControlObservableValue value = new ControlObservableValue(shell,
70
		ISWTObservableValue value = SWTObservables.observeVisible(shell);
72
				SWTProperties.VISIBLE);
73
		value.setValue(Boolean.FALSE);
71
		value.setValue(Boolean.FALSE);
74
		assertFalse(shell.isVisible());
72
		assertFalse(shell.isVisible());
75
	}
73
	}
76
74
77
	public void testGetValueVisible() throws Exception {
75
	public void testGetValueVisible() throws Exception {
78
		ControlObservableValue value = new ControlObservableValue(shell,
76
		ISWTObservableValue value = SWTObservables.observeVisible(shell);
79
				SWTProperties.VISIBLE);
80
		shell.setVisible(false);
77
		shell.setVisible(false);
81
		assertEquals(Boolean.FALSE, value.getValue());
78
		assertEquals(Boolean.FALSE, value.getValue());
82
	}
79
	}
83
80
84
	public void testGetValueTypeVisible() throws Exception {
81
	public void testGetValueTypeVisible() throws Exception {
85
		ControlObservableValue value = new ControlObservableValue(shell,
82
		ISWTObservableValue value = SWTObservables.observeVisible(shell);
86
				SWTProperties.VISIBLE);
87
		assertEquals(Boolean.TYPE, value.getValueType());
83
		assertEquals(Boolean.TYPE, value.getValueType());
88
	}
84
	}
89
85
90
	public void testSetValueForeground() throws Exception {
86
	public void testSetValueForeground() throws Exception {
91
		ControlObservableValue value = new ControlObservableValue(shell,
87
		ISWTObservableValue value = SWTObservables.observeForeground(shell);
92
				SWTProperties.FOREGROUND);
93
88
94
		Color color = shell.getDisplay().getSystemColor(SWT.COLOR_BLACK);
89
		Color color = shell.getDisplay().getSystemColor(SWT.COLOR_BLACK);
95
90
Lines 98-105 Link Here
98
	}
93
	}
99
94
100
	public void testGetValueForeground() throws Exception {
95
	public void testGetValueForeground() throws Exception {
101
		ControlObservableValue value = new ControlObservableValue(shell,
96
		ISWTObservableValue value = SWTObservables.observeForeground(shell);
102
				SWTProperties.FOREGROUND);
103
97
104
		Color color = shell.getDisplay().getSystemColor(SWT.COLOR_BLACK);
98
		Color color = shell.getDisplay().getSystemColor(SWT.COLOR_BLACK);
105
		shell.setForeground(color);
99
		shell.setForeground(color);
Lines 107-120 Link Here
107
	}
101
	}
108
102
109
	public void testGetValueTypeForgroundColor() throws Exception {
103
	public void testGetValueTypeForgroundColor() throws Exception {
110
		ControlObservableValue value = new ControlObservableValue(shell,
104
		ISWTObservableValue value = SWTObservables.observeForeground(shell);
111
				SWTProperties.FOREGROUND);
112
		assertEquals(Color.class, value.getValueType());
105
		assertEquals(Color.class, value.getValueType());
113
	}
106
	}
114
107
115
	public void testGetValueBackground() throws Exception {
108
	public void testGetValueBackground() throws Exception {
116
		ControlObservableValue value = new ControlObservableValue(shell,
109
		ISWTObservableValue value = SWTObservables.observeBackground(shell);
117
				SWTProperties.BACKGROUND);
118
110
119
		Color color = shell.getDisplay().getSystemColor(SWT.COLOR_BLACK);
111
		Color color = shell.getDisplay().getSystemColor(SWT.COLOR_BLACK);
120
		shell.setBackground(color);
112
		shell.setBackground(color);
Lines 122-129 Link Here
122
	}
114
	}
123
115
124
	public void testSetValueBackground() throws Exception {
116
	public void testSetValueBackground() throws Exception {
125
		ControlObservableValue value = new ControlObservableValue(shell,
117
		ISWTObservableValue value = SWTObservables.observeBackground(shell);
126
				SWTProperties.BACKGROUND);
127
118
128
		Color color = shell.getDisplay().getSystemColor(SWT.COLOR_BLACK);
119
		Color color = shell.getDisplay().getSystemColor(SWT.COLOR_BLACK);
129
120
Lines 132-151 Link Here
132
	}
123
	}
133
124
134
	public void testGetValueTypeBackgroundColor() throws Exception {
125
	public void testGetValueTypeBackgroundColor() throws Exception {
135
		ControlObservableValue value = new ControlObservableValue(shell,
126
		ISWTObservableValue value = SWTObservables.observeBackground(shell);
136
				SWTProperties.BACKGROUND);
137
		assertEquals(Color.class, value.getValueType());
127
		assertEquals(Color.class, value.getValueType());
138
	}
128
	}
139
129
140
	public void testGetValueTypeTooltip() throws Exception {
130
	public void testGetValueTypeTooltip() throws Exception {
141
		ControlObservableValue value = new ControlObservableValue(shell,
131
		ISWTObservableValue value = SWTObservables.observeTooltipText(shell);
142
				SWTProperties.TOOLTIP_TEXT);
143
		assertEquals(String.class, value.getValueType());
132
		assertEquals(String.class, value.getValueType());
144
	}
133
	}
145
134
146
	public void testSetValueFont() throws Exception {
135
	public void testSetValueFont() throws Exception {
147
		ControlObservableValue value = new ControlObservableValue(shell,
136
		ISWTObservableValue value = SWTObservables.observeFont(shell);
148
				SWTProperties.FONT);
149
137
150
		Font font = JFaceResources.getDialogFont();
138
		Font font = JFaceResources.getDialogFont();
151
139
Lines 154-161 Link Here
154
	}
142
	}
155
143
156
	public void testGetValueFont() throws Exception {
144
	public void testGetValueFont() throws Exception {
157
		ControlObservableValue value = new ControlObservableValue(shell,
145
		ISWTObservableValue value = SWTObservables.observeFont(shell);
158
				SWTProperties.FONT);
159
146
160
		Font font = JFaceResources.getDialogFont();
147
		Font font = JFaceResources.getDialogFont();
161
		shell.setFont(font);
148
		shell.setFont(font);
Lines 163-192 Link Here
163
	}
150
	}
164
151
165
	public void testGetValueTypeFont() throws Exception {
152
	public void testGetValueTypeFont() throws Exception {
166
		ControlObservableValue value = new ControlObservableValue(shell,
153
		ISWTObservableValue value = SWTObservables.observeFont(shell);
167
				SWTProperties.FONT);
168
		assertEquals(Font.class, value.getValueType());
154
		assertEquals(Font.class, value.getValueType());
169
	}
155
	}
170
156
171
	public void testSetValueTooltipText() throws Exception {
157
	public void testSetValueTooltipText() throws Exception {
172
		ControlObservableValue value = new ControlObservableValue(shell,
158
		ISWTObservableValue value = SWTObservables.observeTooltipText(shell);
173
				SWTProperties.TOOLTIP_TEXT);
174
		String text = "text";
159
		String text = "text";
175
		value.setValue(text);
160
		value.setValue(text);
176
		assertEquals(text, shell.getToolTipText());
161
		assertEquals(text, shell.getToolTipText());
177
	}
162
	}
178
163
179
	public void testGetValueTooltipText() throws Exception {
164
	public void testGetValueTooltipText() throws Exception {
180
		ControlObservableValue value = new ControlObservableValue(shell,
165
		ISWTObservableValue value = SWTObservables.observeTooltipText(shell);
181
				SWTProperties.TOOLTIP_TEXT);
182
		String text = "text";
166
		String text = "text";
183
		shell.setToolTipText(text);
167
		shell.setToolTipText(text);
184
		assertEquals(text, value.getValue());
168
		assertEquals(text, value.getValue());
185
	}
169
	}
186
170
187
	public void testGetValueTypeTooltipText() throws Exception {
171
	public void testGetValueTypeTooltipText() throws Exception {
188
		ControlObservableValue value = new ControlObservableValue(shell,
172
		ISWTObservableValue value = SWTObservables.observeTooltipText(shell);
189
				SWTProperties.TOOLTIP_TEXT);
190
		assertEquals(String.class, value.getValueType());
173
		assertEquals(String.class, value.getValueType());
191
	}
174
	}
192
}
175
}
(-)src/org/eclipse/jface/tests/internal/databinding/swt/LabelObservableValueTest.java (-28 / +31 lines)
Lines 7-13 Link Here
7
 *
7
 *
8
 * Contributors:
8
 * Contributors:
9
 *     Brad Reynolds - initial API and implementation
9
 *     Brad Reynolds - initial API and implementation
10
 *     Matthew Hall - bug 213145
10
 *     Matthew Hall - bug 213145, 194734
11
 ******************************************************************************/
11
 ******************************************************************************/
12
12
13
package org.eclipse.jface.tests.internal.databinding.swt;
13
package org.eclipse.jface.tests.internal.databinding.swt;
Lines 21-28 Link Here
21
import org.eclipse.jface.databinding.conformance.ObservableDelegateTest;
21
import org.eclipse.jface.databinding.conformance.ObservableDelegateTest;
22
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
22
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
23
import org.eclipse.jface.databinding.conformance.swt.SWTMutableObservableValueContractTest;
23
import org.eclipse.jface.databinding.conformance.swt.SWTMutableObservableValueContractTest;
24
import org.eclipse.jface.databinding.swt.LabelProperties;
24
import org.eclipse.jface.databinding.swt.SWTObservables;
25
import org.eclipse.jface.databinding.swt.SWTObservables;
25
import org.eclipse.jface.internal.databinding.swt.LabelObservableValue;
26
import org.eclipse.swt.SWT;
26
import org.eclipse.swt.SWT;
27
import org.eclipse.swt.widgets.Display;
27
import org.eclipse.swt.widgets.Display;
28
import org.eclipse.swt.widgets.Label;
28
import org.eclipse.swt.widgets.Label;
Lines 35-77 Link Here
35
	private Delegate delegate;
35
	private Delegate delegate;
36
	private IObservableValue observable;
36
	private IObservableValue observable;
37
	private Label label;
37
	private Label label;
38
	
38
39
	public LabelObservableValueTest() {
39
	public LabelObservableValueTest() {
40
		this(null);
40
		this(null);
41
	}
41
	}
42
	
42
43
	public LabelObservableValueTest(String testName) {
43
	public LabelObservableValueTest(String testName) {
44
		super(testName, new Delegate());
44
		super(testName, new Delegate());
45
	}
45
	}
46
	
46
47
	protected void setUp() throws Exception {
47
	protected void setUp() throws Exception {
48
		super.setUp();
48
		super.setUp();
49
		
49
50
		delegate = (Delegate) getObservableContractDelegate();
50
		delegate = (Delegate) getObservableContractDelegate();
51
		observable = (IObservableValue) getObservable();
51
		observable = (IObservableValue) getObservable();
52
		label = delegate.label;
52
		label = delegate.label;
53
	}
53
	}
54
	
54
55
	protected IObservable doCreateObservable() {
55
	protected IObservable doCreateObservable() {
56
		return getObservableContractDelegate().createObservable(SWTObservables.getRealm(Display.getDefault()));
56
		return getObservableContractDelegate().createObservable(
57
				SWTObservables.getRealm(Display.getDefault()));
57
	}
58
	}
58
	
59
59
    public void testSetValue() throws Exception {
60
	public void testSetValue() throws Exception {
60
    	//preconditions
61
		// preconditions
61
        assertEquals("", label.getText());
62
		assertEquals("", label.getText());
62
        assertEquals("", observable.getValue());
63
		assertEquals("", observable.getValue());
63
        
64
64
        String value = "value";
65
		String value = "value";
65
        observable.setValue(value);
66
		observable.setValue(value);
66
        assertEquals("label text", value, label.getText());
67
		assertEquals("label text", value, label.getText());
67
        assertEquals("observable value", value, observable.getValue());
68
		assertEquals("observable value", value, observable.getValue());
68
    }
69
	}
69
    
70
70
    public static Test suite() {
71
	public static Test suite() {
71
    	TestSuite suite = new TestSuite(LabelObservableValueTest.class.toString());
72
		TestSuite suite = new TestSuite(LabelObservableValueTest.class
72
    	suite.addTestSuite(LabelObservableValueTest.class);
73
				.toString());
73
    	suite.addTest(SWTMutableObservableValueContractTest.suite(new Delegate()));
74
		suite.addTestSuite(LabelObservableValueTest.class);
74
    	return suite;
75
		suite.addTest(SWTMutableObservableValueContractTest
76
				.suite(new Delegate()));
77
		return suite;
75
	}
78
	}
76
79
77
	/* package */static class Delegate extends
80
	/* package */static class Delegate extends
Lines 90-107 Link Here
90
		}
93
		}
91
94
92
		public IObservableValue createObservableValue(Realm realm) {
95
		public IObservableValue createObservableValue(Realm realm) {
93
			return new LabelObservableValue(realm, label);
96
			return LabelProperties.text().observeValue(realm, label);
94
		}
97
		}
95
98
96
		public void change(IObservable observable) {
99
		public void change(IObservable observable) {
97
			IObservableValue value = (IObservableValue) observable;
100
			IObservableValue value = (IObservableValue) observable;
98
			value.setValue(value.getValue() + "a");
101
			value.setValue(value.getValue() + "a");
99
		}
102
		}
100
		
103
101
		public Object getValueType(IObservableValue observable) {
104
		public Object getValueType(IObservableValue observable) {
102
			return String.class;
105
			return String.class;
103
		}
106
		}
104
		
107
105
		public Object createValue(IObservableValue observable) {
108
		public Object createValue(IObservableValue observable) {
106
			return observable.getValue() + "a";
109
			return observable.getValue() + "a";
107
		}
110
		}
(-)src/org/eclipse/jface/tests/internal/databinding/swt/TextObservableValueTest.java (-16 / +28 lines)
Lines 10-21 Link Here
10
 *     Brad Reynolds - bug 116920
10
 *     Brad Reynolds - bug 116920
11
 *     Brad Reynolds - bug 164653
11
 *     Brad Reynolds - bug 164653
12
 *     Ashley Cambrell - bug 198904
12
 *     Ashley Cambrell - bug 198904
13
 *     Matthew Hall - bug 194734
13
 *******************************************************************************/
14
 *******************************************************************************/
14
15
15
package org.eclipse.jface.tests.internal.databinding.swt;
16
package org.eclipse.jface.tests.internal.databinding.swt;
16
17
18
import org.eclipse.core.databinding.observable.Realm;
19
import org.eclipse.core.databinding.observable.value.IObservableValue;
17
import org.eclipse.jface.databinding.conformance.util.ValueChangeEventTracker;
20
import org.eclipse.jface.databinding.conformance.util.ValueChangeEventTracker;
18
import org.eclipse.jface.internal.databinding.swt.TextObservableValue;
21
import org.eclipse.jface.databinding.swt.TextProperties;
19
import org.eclipse.jface.tests.databinding.AbstractDefaultRealmTestCase;
22
import org.eclipse.jface.tests.databinding.AbstractDefaultRealmTestCase;
20
import org.eclipse.swt.SWT;
23
import org.eclipse.swt.SWT;
21
import org.eclipse.swt.widgets.Shell;
24
import org.eclipse.swt.widgets.Shell;
Lines 35-41 Link Here
35
38
36
		Shell shell = new Shell();
39
		Shell shell = new Shell();
37
		text = new Text(shell, SWT.NONE);
40
		text = new Text(shell, SWT.NONE);
38
		
41
39
		listener = new ValueChangeEventTracker();
42
		listener = new ValueChangeEventTracker();
40
	}
43
	}
41
44
Lines 45-92 Link Here
45
	 */
48
	 */
46
	public void testConstructorUpdateEventTypes() {
49
	public void testConstructorUpdateEventTypes() {
47
		try {
50
		try {
48
			new TextObservableValue(text, SWT.NONE);
51
			TextProperties.text(SWT.None);
49
			new TextObservableValue(text, SWT.FocusOut);
52
			TextProperties.text(SWT.FocusOut);
50
			new TextObservableValue(text, SWT.Modify);
53
			TextProperties.text(SWT.Modify);
51
			assertTrue(true);
54
			assertTrue(true);
52
		} catch (IllegalArgumentException e) {
55
		} catch (IllegalArgumentException e) {
53
			fail();
56
			fail();
54
		}
57
		}
55
58
56
		try {
59
		try {
57
			new TextObservableValue(text, SWT.Verify);
60
			TextProperties.text(SWT.Verify);
58
			fail();
61
			fail();
59
		} catch (IllegalArgumentException e) {
62
		} catch (IllegalArgumentException e) {
60
			assertTrue(true);
63
			assertTrue(true);
61
		}
64
		}
62
	}
65
	}
63
	
66
64
	/**
67
	/**
65
	 * https://bugs.eclipse.org/bugs/show_bug.cgi?id=171132
68
	 * https://bugs.eclipse.org/bugs/show_bug.cgi?id=171132
66
	 * 
69
	 * 
67
	 * @throws Exception
70
	 * @throws Exception
68
	 */
71
	 */
69
	public void testGetValueBeforeFocusOutChangeEventsFire() throws Exception {
72
	public void testGetValueBeforeFocusOutChangeEventsFire() throws Exception {
70
		TextObservableValue observableValue = new TextObservableValue(text, SWT.FocusOut);
73
		IObservableValue observableValue = TextProperties.text(SWT.FocusOut)
74
				.observeValue(Realm.getDefault(), text);
71
		observableValue.addValueChangeListener(listener);
75
		observableValue.addValueChangeListener(listener);
72
		
76
73
		String a = "a";
77
		String a = "a";
74
		String b = "b";
78
		String b = "b";
75
		
79
76
		text.setText(a);
80
		text.setText(a);
77
		assertEquals(a, observableValue.getValue()); //fetch the value updating the buffered value
81
78
		
82
		assertEquals(0, listener.count);
83
84
		// fetching the value updates the buffered value
85
		assertEquals(a, observableValue.getValue());
86
		assertEquals(1, listener.count);
87
79
		text.setText(b);
88
		text.setText(b);
80
		text.notifyListeners(SWT.FocusOut, null);
89
81
		
82
		assertEquals(1, listener.count);
90
		assertEquals(1, listener.count);
91
92
		text.notifyListeners(SWT.FocusOut, null);
93
94
		assertEquals(2, listener.count);
83
		assertEquals(a, listener.event.diff.getOldValue());
95
		assertEquals(a, listener.event.diff.getOldValue());
84
		assertEquals(b, listener.event.diff.getNewValue());
96
		assertEquals(b, listener.event.diff.getNewValue());
85
	}
97
	}
86
98
87
	public void testDispose() throws Exception {
99
	public void testDispose() throws Exception {
88
		TextObservableValue observableValue = new TextObservableValue(text,
100
		IObservableValue observableValue = TextProperties.text(SWT.Modify)
89
				SWT.Modify);
101
				.observeValue(Realm.getDefault(), text);
90
		ValueChangeEventTracker testCounterValueChangeListener = new ValueChangeEventTracker();
102
		ValueChangeEventTracker testCounterValueChangeListener = new ValueChangeEventTracker();
91
		observableValue.addValueChangeListener(testCounterValueChangeListener);
103
		observableValue.addValueChangeListener(testCounterValueChangeListener);
92
104
(-)src/org/eclipse/jface/tests/internal/databinding/swt/CComboSingleSelectionObservableValueTest.java (-16 / +18 lines)
Lines 8-14 Link Here
8
 * Contributors:
8
 * Contributors:
9
 *     Brad Reynolds - initial API and implementation
9
 *     Brad Reynolds - initial API and implementation
10
 *     Ashley Cambrell - bug 198903
10
 *     Ashley Cambrell - bug 198903
11
 *     Matthew Hall - bug 213145
11
 *     Matthew Hall - bug 213145, 194734
12
 ******************************************************************************/
12
 ******************************************************************************/
13
13
14
package org.eclipse.jface.tests.internal.databinding.swt;
14
package org.eclipse.jface.tests.internal.databinding.swt;
Lines 21-28 Link Here
21
import org.eclipse.core.databinding.observable.value.IObservableValue;
21
import org.eclipse.core.databinding.observable.value.IObservableValue;
22
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
22
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
23
import org.eclipse.jface.databinding.conformance.swt.SWTMutableObservableValueContractTest;
23
import org.eclipse.jface.databinding.conformance.swt.SWTMutableObservableValueContractTest;
24
import org.eclipse.jface.databinding.swt.ISWTObservable;
24
import org.eclipse.jface.databinding.swt.CComboProperties;
25
import org.eclipse.jface.internal.databinding.swt.CComboSingleSelectionObservableValue;
25
import org.eclipse.jface.databinding.swt.SWTObservables;
26
import org.eclipse.jface.tests.databinding.AbstractSWTTestCase;
26
import org.eclipse.jface.tests.databinding.AbstractSWTTestCase;
27
import org.eclipse.swt.SWT;
27
import org.eclipse.swt.SWT;
28
import org.eclipse.swt.custom.CCombo;
28
import org.eclipse.swt.custom.CCombo;
Lines 31-41 Link Here
31
/**
31
/**
32
 * @since 3.2
32
 * @since 3.2
33
 */
33
 */
34
public class CComboSingleSelectionObservableValueTest extends AbstractSWTTestCase {
34
public class CComboSingleSelectionObservableValueTest extends
35
		AbstractSWTTestCase {
35
	public void testSetValue() throws Exception {
36
	public void testSetValue() throws Exception {
36
		CCombo combo = new CCombo(getShell(), SWT.NONE);
37
		CCombo combo = new CCombo(getShell(), SWT.NONE);
37
		CComboSingleSelectionObservableValue observableValue = new CComboSingleSelectionObservableValue(
38
		IObservableValue observableValue = SWTObservables
38
				combo);
39
				.observeSingleSelectionIndex(combo);
39
		combo.add("Item1");
40
		combo.add("Item1");
40
		combo.add("Item2");
41
		combo.add("Item2");
41
42
Lines 52-60 Link Here
52
	}
53
	}
53
54
54
	public static Test suite() {
55
	public static Test suite() {
55
		TestSuite suite = new TestSuite(CComboSingleSelectionObservableValueTest.class.getName());
56
		TestSuite suite = new TestSuite(
57
				CComboSingleSelectionObservableValueTest.class.getName());
56
		suite.addTestSuite(CComboSingleSelectionObservableValueTest.class);
58
		suite.addTestSuite(CComboSingleSelectionObservableValueTest.class);
57
		suite.addTest(SWTMutableObservableValueContractTest.suite(new Delegate()));
59
		suite.addTest(SWTMutableObservableValueContractTest
60
				.suite(new Delegate()));
58
		return suite;
61
		return suite;
59
	}
62
	}
60
63
Lines 75-87 Link Here
75
		}
78
		}
76
79
77
		public IObservableValue createObservableValue(Realm realm) {
80
		public IObservableValue createObservableValue(Realm realm) {
78
			return new CComboSingleSelectionObservableValue(realm, combo);
81
			return CComboProperties.singleSelectionIndex().observeValue(realm,
82
					combo);
79
		}
83
		}
80
84
81
		public void change(IObservable observable) {
85
		public void change(IObservable observable) {
82
			int index = _createValue((IObservableValue) observable);
86
			IObservableValue value = (IObservableValue) observable;
83
			combo.select(index);
87
			value.setValue(createValue(value));
84
			combo.notifyListeners(SWT.Selection, null);
85
		}
88
		}
86
89
87
		public Object getValueType(IObservableValue observable) {
90
		public Object getValueType(IObservableValue observable) {
Lines 91-102 Link Here
91
		public Object createValue(IObservableValue observable) {
94
		public Object createValue(IObservableValue observable) {
92
			return new Integer(_createValue(observable));
95
			return new Integer(_createValue(observable));
93
		}
96
		}
94
		
97
95
		private int _createValue(IObservableValue observable) {
98
		private int _createValue(IObservableValue observable) {
96
			CCombo combo = ((CCombo) ((ISWTObservable) observable).getWidget());
97
			int value = Math.max(0, combo.getSelectionIndex());
99
			int value = Math.max(0, combo.getSelectionIndex());
98
			
100
99
			//returns either 0 or 1 depending upon current value
101
			// returns either 0 or 1 depending upon current value
100
			return Math.abs(value - 1);
102
			return Math.abs(value - 1);
101
		}
103
		}
102
	}
104
	}
(-)src/org/eclipse/jface/tests/internal/databinding/swt/SWTDelayedObservableValueDecoratorTest.java (-45 / +8 lines)
Lines 7-13 Link Here
7
 *
7
 *
8
 * Contributors:
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 212223)
9
 *     Matthew Hall - initial API and implementation (bug 212223)
10
 *     Matthew Hall - bug 213145, 245647
10
 *     Matthew Hall - bug 213145, 245647, 194734
11
 ******************************************************************************/
11
 ******************************************************************************/
12
12
13
package org.eclipse.jface.tests.internal.databinding.swt;
13
package org.eclipse.jface.tests.internal.databinding.swt;
Lines 15-36 Link Here
15
import junit.framework.Test;
15
import junit.framework.Test;
16
import junit.framework.TestSuite;
16
import junit.framework.TestSuite;
17
17
18
import org.eclipse.core.databinding.observable.Diffs;
19
import org.eclipse.core.databinding.observable.IObservable;
18
import org.eclipse.core.databinding.observable.IObservable;
20
import org.eclipse.core.databinding.observable.Realm;
19
import org.eclipse.core.databinding.observable.Realm;
21
import org.eclipse.core.databinding.observable.value.IObservableValue;
20
import org.eclipse.core.databinding.observable.value.IObservableValue;
21
import org.eclipse.core.databinding.observable.value.WritableValue;
22
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
22
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
23
import org.eclipse.jface.databinding.conformance.swt.SWTMutableObservableValueContractTest;
23
import org.eclipse.jface.databinding.conformance.swt.SWTMutableObservableValueContractTest;
24
import org.eclipse.jface.databinding.conformance.util.ValueChangeEventTracker;
24
import org.eclipse.jface.databinding.conformance.util.ValueChangeEventTracker;
25
import org.eclipse.jface.databinding.swt.ISWTObservableValue;
25
import org.eclipse.jface.databinding.swt.ISWTObservableValue;
26
import org.eclipse.jface.databinding.swt.SWTObservables;
26
import org.eclipse.jface.databinding.swt.SWTObservables;
27
import org.eclipse.jface.internal.databinding.provisional.swt.AbstractSWTObservableValue;
27
import org.eclipse.jface.internal.databinding.swt.SWTObservableValueDecorator;
28
import org.eclipse.jface.tests.databinding.AbstractDefaultRealmTestCase;
28
import org.eclipse.jface.tests.databinding.AbstractDefaultRealmTestCase;
29
import org.eclipse.swt.SWT;
29
import org.eclipse.swt.SWT;
30
import org.eclipse.swt.widgets.Display;
30
import org.eclipse.swt.widgets.Display;
31
import org.eclipse.swt.widgets.Event;
31
import org.eclipse.swt.widgets.Event;
32
import org.eclipse.swt.widgets.Shell;
32
import org.eclipse.swt.widgets.Shell;
33
import org.eclipse.swt.widgets.Widget;
34
33
35
/**
34
/**
36
 * Tests for DelayedObservableValue
35
 * Tests for DelayedObservableValue
Lines 43-57 Link Here
43
	private Shell shell;
42
	private Shell shell;
44
	private Object oldValue;
43
	private Object oldValue;
45
	private Object newValue;
44
	private Object newValue;
46
	private SWTObservableValueStub target;
45
	private ISWTObservableValue target;
47
	private ISWTObservableValue delayed;
46
	private ISWTObservableValue delayed;
48
47
49
	protected void setUp() throws Exception {
48
	protected void setUp() throws Exception {
50
		super.setUp();
49
		super.setUp();
51
		display = Display.getCurrent();
50
		display = Display.getCurrent();
52
		shell = new Shell(display);
51
		shell = new Shell(display);
53
		target = new SWTObservableValueStub(SWTObservables.getRealm(display),
52
		target = new SWTObservableValueDecorator(new WritableValue(
54
				shell);
53
				SWTObservables.getRealm(display)), shell);
55
		oldValue = new Object();
54
		oldValue = new Object();
56
		newValue = new Object();
55
		newValue = new Object();
57
		target.setValue(oldValue);
56
		target.setValue(oldValue);
Lines 93-135 Link Here
93
		assertEquals(newValue, tracker.event.diff.getNewValue());
92
		assertEquals(newValue, tracker.event.diff.getNewValue());
94
	}
93
	}
95
94
96
	static class SWTObservableValueStub extends AbstractSWTObservableValue {
97
		private Object value;
98
		private boolean stale;
99
100
		Object overrideValue;
101
102
		public SWTObservableValueStub(Realm realm, Widget widget) {
103
			super(realm, widget);
104
		}
105
106
		protected Object doGetValue() {
107
			return value;
108
		}
109
110
		protected void doSetValue(Object value) {
111
			Object oldValue = this.value;
112
			if (overrideValue != null)
113
				value = overrideValue;
114
			this.value = value;
115
			stale = false;
116
			fireValueChange(Diffs.createValueDiff(oldValue, value));
117
		}
118
119
		public Object getValueType() {
120
			return Object.class;
121
		}
122
123
		protected void fireStale() {
124
			stale = true;
125
			super.fireStale();
126
		}
127
128
		public boolean isStale() {
129
			return stale;
130
		}
131
	}
132
133
	public static Test suite() {
95
	public static Test suite() {
134
		TestSuite suite = new TestSuite(
96
		TestSuite suite = new TestSuite(
135
				SWTDelayedObservableValueDecoratorTest.class.getName());
97
				SWTDelayedObservableValueDecoratorTest.class.getName());
Lines 155-161 Link Here
155
117
156
		public IObservableValue createObservableValue(Realm realm) {
118
		public IObservableValue createObservableValue(Realm realm) {
157
			return SWTObservables.observeDelayedValue(0,
119
			return SWTObservables.observeDelayedValue(0,
158
					new SWTObservableValueStub(realm, shell));
120
					new SWTObservableValueDecorator(new WritableValue(realm,
121
							null, Object.class), shell));
159
		}
122
		}
160
123
161
		public Object getValueType(IObservableValue observable) {
124
		public Object getValueType(IObservableValue observable) {
(-)src/org/eclipse/jface/tests/internal/databinding/swt/SpinnerObservableValueMinTest.java (-10 / +12 lines)
Lines 7-13 Link Here
7
 *
7
 *
8
 * Contributors:
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
9
 *     IBM Corporation - initial API and implementation
10
 *     Matthew Hall - bug 213145
10
 *     Matthew Hall - bug 213145, 194734
11
 *******************************************************************************/
11
 *******************************************************************************/
12
12
13
package org.eclipse.jface.tests.internal.databinding.swt;
13
package org.eclipse.jface.tests.internal.databinding.swt;
Lines 22-29 Link Here
22
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
22
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
23
import org.eclipse.jface.databinding.conformance.swt.SWTMutableObservableValueContractTest;
23
import org.eclipse.jface.databinding.conformance.swt.SWTMutableObservableValueContractTest;
24
import org.eclipse.jface.databinding.swt.SWTObservables;
24
import org.eclipse.jface.databinding.swt.SWTObservables;
25
import org.eclipse.jface.internal.databinding.swt.SWTProperties;
25
import org.eclipse.jface.databinding.swt.SpinnerProperties;
26
import org.eclipse.jface.internal.databinding.swt.SpinnerObservableValue;
27
import org.eclipse.swt.SWT;
26
import org.eclipse.swt.SWT;
28
import org.eclipse.swt.widgets.Display;
27
import org.eclipse.swt.widgets.Display;
29
import org.eclipse.swt.widgets.Shell;
28
import org.eclipse.swt.widgets.Shell;
Lines 46-62 Link Here
46
	public SpinnerObservableValueMinTest(String testName) {
45
	public SpinnerObservableValueMinTest(String testName) {
47
		super(testName, new Delegate());
46
		super(testName, new Delegate());
48
	}
47
	}
49
	
48
50
	protected void setUp() throws Exception {
49
	protected void setUp() throws Exception {
51
		super.setUp();
50
		super.setUp();
52
		
51
53
		delegate = (Delegate) getObservableContractDelegate();
52
		delegate = (Delegate) getObservableContractDelegate();
54
		observable = (IObservableValue) getObservable();
53
		observable = (IObservableValue) getObservable();
55
		spinner = delegate.spinner;
54
		spinner = delegate.spinner;
56
	}
55
	}
57
	
56
58
	protected IObservable doCreateObservable() {
57
	protected IObservable doCreateObservable() {
59
		return getObservableContractDelegate().createObservable(SWTObservables.getRealm(Display.getDefault()));
58
		return getObservableContractDelegate().createObservable(
59
				SWTObservables.getRealm(Display.getDefault()));
60
	}
60
	}
61
61
62
	public void testGetValue() throws Exception {
62
	public void testGetValue() throws Exception {
Lines 72-80 Link Here
72
	}
72
	}
73
73
74
	public static Test suite() {
74
	public static Test suite() {
75
		TestSuite suite = new TestSuite(SpinnerObservableValueMinTest.class.toString());
75
		TestSuite suite = new TestSuite(SpinnerObservableValueMinTest.class
76
				.toString());
76
		suite.addTestSuite(SpinnerObservableValueMinTest.class);
77
		suite.addTestSuite(SpinnerObservableValueMinTest.class);
77
		suite.addTest(SWTMutableObservableValueContractTest.suite(new Delegate()));
78
		suite.addTest(SWTMutableObservableValueContractTest
79
				.suite(new Delegate()));
78
		return suite;
80
		return suite;
79
	}
81
	}
80
82
Lines 95-101 Link Here
95
		}
97
		}
96
98
97
		public IObservableValue createObservableValue(Realm realm) {
99
		public IObservableValue createObservableValue(Realm realm) {
98
			return new SpinnerObservableValue(realm, spinner, SWTProperties.MIN);
100
			return SpinnerProperties.minimum().observeValue(realm, spinner);
99
		}
101
		}
100
102
101
		public void change(IObservable observable) {
103
		public void change(IObservable observable) {
(-)src/org/eclipse/jface/tests/internal/databinding/swt/SpinnerObservableValueMaxTest.java (-10 / +12 lines)
Lines 7-13 Link Here
7
 *
7
 *
8
 * Contributors:
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
9
 *     IBM Corporation - initial API and implementation
10
 *     Matthew Hall - bug 213145
10
 *     Matthew Hall - bug 213145, 194734
11
 *******************************************************************************/
11
 *******************************************************************************/
12
12
13
package org.eclipse.jface.tests.internal.databinding.swt;
13
package org.eclipse.jface.tests.internal.databinding.swt;
Lines 22-29 Link Here
22
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
22
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
23
import org.eclipse.jface.databinding.conformance.swt.SWTMutableObservableValueContractTest;
23
import org.eclipse.jface.databinding.conformance.swt.SWTMutableObservableValueContractTest;
24
import org.eclipse.jface.databinding.swt.SWTObservables;
24
import org.eclipse.jface.databinding.swt.SWTObservables;
25
import org.eclipse.jface.internal.databinding.swt.SWTProperties;
25
import org.eclipse.jface.databinding.swt.SpinnerProperties;
26
import org.eclipse.jface.internal.databinding.swt.SpinnerObservableValue;
27
import org.eclipse.swt.SWT;
26
import org.eclipse.swt.SWT;
28
import org.eclipse.swt.widgets.Display;
27
import org.eclipse.swt.widgets.Display;
29
import org.eclipse.swt.widgets.Shell;
28
import org.eclipse.swt.widgets.Shell;
Lines 46-52 Link Here
46
	public SpinnerObservableValueMaxTest(String testName) {
45
	public SpinnerObservableValueMaxTest(String testName) {
47
		super(testName, new Delegate());
46
		super(testName, new Delegate());
48
	}
47
	}
49
	
48
50
	protected void setUp() throws Exception {
49
	protected void setUp() throws Exception {
51
		super.setUp();
50
		super.setUp();
52
51
Lines 54-62 Link Here
54
		observable = (IObservableValue) getObservable();
53
		observable = (IObservableValue) getObservable();
55
		spinner = delegate.spinner;
54
		spinner = delegate.spinner;
56
	}
55
	}
57
	
56
58
	protected IObservable doCreateObservable() {
57
	protected IObservable doCreateObservable() {
59
		return getObservableContractDelegate().createObservable(SWTObservables.getRealm(Display.getDefault()));
58
		return getObservableContractDelegate().createObservable(
59
				SWTObservables.getRealm(Display.getDefault()));
60
	}
60
	}
61
61
62
	public void testGetValue() throws Exception {
62
	public void testGetValue() throws Exception {
Lines 70-80 Link Here
70
		observable.setValue(new Integer(max));
70
		observable.setValue(new Integer(max));
71
		assertEquals(max, spinner.getMaximum());
71
		assertEquals(max, spinner.getMaximum());
72
	}
72
	}
73
	
73
74
	public static Test suite() {
74
	public static Test suite() {
75
		TestSuite suite = new TestSuite(SpinnerObservableValueMaxTest.class.toString());
75
		TestSuite suite = new TestSuite(SpinnerObservableValueMaxTest.class
76
				.toString());
76
		suite.addTestSuite(SpinnerObservableValueMaxTest.class);
77
		suite.addTestSuite(SpinnerObservableValueMaxTest.class);
77
		suite.addTest(SWTMutableObservableValueContractTest.suite(new Delegate()));
78
		suite.addTest(SWTMutableObservableValueContractTest
79
				.suite(new Delegate()));
78
		return suite;
80
		return suite;
79
	}
81
	}
80
82
Lines 95-101 Link Here
95
		}
97
		}
96
98
97
		public IObservableValue createObservableValue(Realm realm) {
99
		public IObservableValue createObservableValue(Realm realm) {
98
			return new SpinnerObservableValue(realm, spinner, SWTProperties.MAX);
100
			return SpinnerProperties.maximum().observeValue(realm, spinner);
99
		}
101
		}
100
102
101
		public void change(IObservable observable) {
103
		public void change(IObservable observable) {
(-)src/org/eclipse/jface/tests/internal/databinding/swt/ButtonObservableValueTest.java (-24 / +26 lines)
Lines 8-14 Link Here
8
 * Contributors:
8
 * Contributors:
9
 *     Brad Reynolds - initial API and implementation
9
 *     Brad Reynolds - initial API and implementation
10
 *     Ashley Cambrell - bug 198904
10
 *     Ashley Cambrell - bug 198904
11
 *     Matthew Hall - bug 213145
11
 *     Matthew Hall - bug 213145, 194734
12
 ******************************************************************************/
12
 ******************************************************************************/
13
13
14
package org.eclipse.jface.tests.internal.databinding.swt;
14
package org.eclipse.jface.tests.internal.databinding.swt;
Lines 22-28 Link Here
22
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
22
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
23
import org.eclipse.jface.databinding.conformance.swt.SWTMutableObservableValueContractTest;
23
import org.eclipse.jface.databinding.conformance.swt.SWTMutableObservableValueContractTest;
24
import org.eclipse.jface.databinding.conformance.util.ValueChangeEventTracker;
24
import org.eclipse.jface.databinding.conformance.util.ValueChangeEventTracker;
25
import org.eclipse.jface.internal.databinding.swt.ButtonObservableValue;
25
import org.eclipse.jface.databinding.swt.ButtonProperties;
26
import org.eclipse.jface.databinding.swt.ISWTObservableValue;
27
import org.eclipse.jface.databinding.swt.SWTObservables;
26
import org.eclipse.jface.tests.databinding.AbstractSWTTestCase;
28
import org.eclipse.jface.tests.databinding.AbstractSWTTestCase;
27
import org.eclipse.swt.SWT;
29
import org.eclipse.swt.SWT;
28
import org.eclipse.swt.widgets.Button;
30
import org.eclipse.swt.widgets.Button;
Lines 33-54 Link Here
33
 */
35
 */
34
public class ButtonObservableValueTest extends AbstractSWTTestCase {
36
public class ButtonObservableValueTest extends AbstractSWTTestCase {
35
	private Button button;
37
	private Button button;
36
	private ButtonObservableValue observableValue;
38
	private ISWTObservableValue observableValue;
37
	private ValueChangeEventTracker listener;
39
	private ValueChangeEventTracker listener;
38
	
40
39
	/* (non-Javadoc)
40
	 * @see junit.framework.TestCase#setUp()
41
	 */
42
	protected void setUp() throws Exception {
41
	protected void setUp() throws Exception {
43
		super.setUp();
42
		super.setUp();
44
		
43
45
		Shell shell = getShell();
44
		Shell shell = getShell();
46
		button = new Button(shell, SWT.CHECK);
45
		button = new Button(shell, SWT.CHECK);
47
		observableValue = new ButtonObservableValue(
46
		observableValue = SWTObservables.observeSelection(button);
48
				button);
49
		listener = new ValueChangeEventTracker();
47
		listener = new ValueChangeEventTracker();
50
	}
48
	}
51
	
49
52
	public void testSelection_ChangeNotifiesObservable() throws Exception {
50
	public void testSelection_ChangeNotifiesObservable() throws Exception {
53
		observableValue.addValueChangeListener(listener);
51
		observableValue.addValueChangeListener(listener);
54
		button.setSelection(true);
52
		button.setSelection(true);
Lines 60-78 Link Here
60
		assertEquals("Selection event should notify observable.", 1,
58
		assertEquals("Selection event should notify observable.", 1,
61
				listener.count);
59
				listener.count);
62
	}
60
	}
63
	
61
64
	public void testSelection_NoChange() throws Exception {
62
	public void testSelection_NoChange() throws Exception {
65
		button.setSelection(true);
63
		button.setSelection(true);
66
		button.notifyListeners(SWT.Selection, null);
64
		button.notifyListeners(SWT.Selection, null);
67
		observableValue.addValueChangeListener(listener);
65
		observableValue.addValueChangeListener(listener);
68
		
66
69
		//precondition
67
		// precondition
70
		assertEquals(0, listener.count);
68
		assertEquals(0, listener.count);
71
		
69
72
		button.notifyListeners(SWT.Selection, null);
70
		button.notifyListeners(SWT.Selection, null);
73
		assertEquals("Value did not change.  Listeners should not have been notified.", 0, listener.count);
71
		assertEquals(
72
				"Value did not change.  Listeners should not have been notified.",
73
				0, listener.count);
74
	}
74
	}
75
	
75
76
	public void testSetValue_NullConvertedToFalse() {
76
	public void testSetValue_NullConvertedToFalse() {
77
		button.setSelection(true);
77
		button.setSelection(true);
78
		assertEquals(Boolean.TRUE, observableValue.getValue());
78
		assertEquals(Boolean.TRUE, observableValue.getValue());
Lines 104-112 Link Here
104
	}
104
	}
105
105
106
	public static Test suite() {
106
	public static Test suite() {
107
		TestSuite suite = new TestSuite(ButtonObservableValueTest.class.getName());
107
		TestSuite suite = new TestSuite(ButtonObservableValueTest.class
108
				.getName());
108
		suite.addTestSuite(ButtonObservableValueTest.class);
109
		suite.addTestSuite(ButtonObservableValueTest.class);
109
		suite.addTest(SWTMutableObservableValueContractTest.suite(new Delegate()));
110
		suite.addTest(SWTMutableObservableValueContractTest
111
				.suite(new Delegate()));
110
		return suite;
112
		return suite;
111
	}
113
	}
112
114
Lines 130-136 Link Here
130
		}
132
		}
131
133
132
		public IObservableValue createObservableValue(Realm realm) {
134
		public IObservableValue createObservableValue(Realm realm) {
133
			return new ButtonObservableValue(realm, button);
135
			return ButtonProperties.selection().observeValue(realm, button);
134
		}
136
		}
135
137
136
		public Object getValueType(IObservableValue observable) {
138
		public Object getValueType(IObservableValue observable) {
Lines 138-151 Link Here
138
		}
140
		}
139
141
140
		public void change(IObservable observable) {
142
		public void change(IObservable observable) {
141
			button.setSelection(changeValue(button));
143
			((IObservableValue) observable).setValue(Boolean
142
			button.notifyListeners(SWT.Selection, null);
144
					.valueOf(changeValue(button)));
143
		}
145
		}
144
		
146
145
		public Object createValue(IObservableValue observable) {
147
		public Object createValue(IObservableValue observable) {
146
			return Boolean.valueOf(changeValue(button));
148
			return Boolean.valueOf(changeValue(button));
147
		}
149
		}
148
		
150
149
		private boolean changeValue(Button button) {
151
		private boolean changeValue(Button button) {
150
			return !button.getSelection();
152
			return !button.getSelection();
151
		}
153
		}
(-)src/org/eclipse/jface/tests/internal/databinding/swt/ScaleObservableValueMinTest.java (-10 / +12 lines)
Lines 7-13 Link Here
7
 *
7
 *
8
 * Contributors:
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
9
 *     IBM Corporation - initial API and implementation
10
 *     Matthew Hall - bug 213145
10
 *     Matthew Hall - bug 213145, 194734
11
 *******************************************************************************/
11
 *******************************************************************************/
12
12
13
package org.eclipse.jface.tests.internal.databinding.swt;
13
package org.eclipse.jface.tests.internal.databinding.swt;
Lines 22-29 Link Here
22
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
22
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
23
import org.eclipse.jface.databinding.conformance.swt.SWTMutableObservableValueContractTest;
23
import org.eclipse.jface.databinding.conformance.swt.SWTMutableObservableValueContractTest;
24
import org.eclipse.jface.databinding.swt.SWTObservables;
24
import org.eclipse.jface.databinding.swt.SWTObservables;
25
import org.eclipse.jface.internal.databinding.swt.SWTProperties;
25
import org.eclipse.jface.databinding.swt.ScaleProperties;
26
import org.eclipse.jface.internal.databinding.swt.ScaleObservableValue;
27
import org.eclipse.swt.SWT;
26
import org.eclipse.swt.SWT;
28
import org.eclipse.swt.widgets.Display;
27
import org.eclipse.swt.widgets.Display;
29
import org.eclipse.swt.widgets.Scale;
28
import org.eclipse.swt.widgets.Scale;
Lines 42-52 Link Here
42
	public ScaleObservableValueMinTest() {
41
	public ScaleObservableValueMinTest() {
43
		this(null);
42
		this(null);
44
	}
43
	}
45
	
44
46
	public ScaleObservableValueMinTest(String testName) {
45
	public ScaleObservableValueMinTest(String testName) {
47
		super(testName, new Delegate());
46
		super(testName, new Delegate());
48
	}
47
	}
49
	
48
50
	protected void setUp() throws Exception {
49
	protected void setUp() throws Exception {
51
		super.setUp();
50
		super.setUp();
52
51
Lines 56-64 Link Here
56
	}
55
	}
57
56
58
	protected IObservable doCreateObservable() {
57
	protected IObservable doCreateObservable() {
59
		return getObservableContractDelegate().createObservable(SWTObservables.getRealm(Display.getDefault()));
58
		return getObservableContractDelegate().createObservable(
59
				SWTObservables.getRealm(Display.getDefault()));
60
	}
60
	}
61
	
61
62
	public void testGetValue() throws Exception {
62
	public void testGetValue() throws Exception {
63
		int min = 100;
63
		int min = 100;
64
		scale.setMinimum(min);
64
		scale.setMinimum(min);
Lines 72-80 Link Here
72
	}
72
	}
73
73
74
	public static Test suite() {
74
	public static Test suite() {
75
		TestSuite suite = new TestSuite(ScaleObservableValueMinTest.class.toString());
75
		TestSuite suite = new TestSuite(ScaleObservableValueMinTest.class
76
				.toString());
76
		suite.addTestSuite(ScaleObservableValueMinTest.class);
77
		suite.addTestSuite(ScaleObservableValueMinTest.class);
77
		suite.addTest(SWTMutableObservableValueContractTest.suite(new Delegate()));
78
		suite.addTest(SWTMutableObservableValueContractTest
79
				.suite(new Delegate()));
78
		return suite;
80
		return suite;
79
	}
81
	}
80
82
Lines 95-101 Link Here
95
		}
97
		}
96
98
97
		public IObservableValue createObservableValue(Realm realm) {
99
		public IObservableValue createObservableValue(Realm realm) {
98
			return new ScaleObservableValue(realm, scale, SWTProperties.MIN);
100
			return ScaleProperties.minimum().observeValue(realm, scale);
99
		}
101
		}
100
102
101
		public void change(IObservable observable) {
103
		public void change(IObservable observable) {
(-)src/org/eclipse/jface/tests/internal/databinding/swt/ListSingleSelectionObservableValueTest.java (-5 / +7 lines)
Lines 7-17 Link Here
7
 *
7
 *
8
 * Contributors:
8
 * Contributors:
9
 *     Ashley Cambrell - initial API and implementation
9
 *     Ashley Cambrell - initial API and implementation
10
 *     Matthew Hall - bug 194734
10
 ******************************************************************************/
11
 ******************************************************************************/
11
12
12
package org.eclipse.jface.tests.internal.databinding.swt;
13
package org.eclipse.jface.tests.internal.databinding.swt;
13
14
14
import org.eclipse.jface.internal.databinding.swt.ListSingleSelectionObservableValue;
15
import org.eclipse.core.databinding.observable.value.IObservableValue;
16
import org.eclipse.jface.databinding.swt.SWTObservables;
15
import org.eclipse.jface.tests.databinding.AbstractSWTTestCase;
17
import org.eclipse.jface.tests.databinding.AbstractSWTTestCase;
16
import org.eclipse.swt.SWT;
18
import org.eclipse.swt.SWT;
17
import org.eclipse.swt.widgets.List;
19
import org.eclipse.swt.widgets.List;
Lines 23-30 Link Here
23
public class ListSingleSelectionObservableValueTest extends AbstractSWTTestCase {
25
public class ListSingleSelectionObservableValueTest extends AbstractSWTTestCase {
24
	public void testSetValue() throws Exception {
26
	public void testSetValue() throws Exception {
25
		List list = new List(getShell(), SWT.NONE);
27
		List list = new List(getShell(), SWT.NONE);
26
		ListSingleSelectionObservableValue observableValue = new ListSingleSelectionObservableValue(
28
		IObservableValue observableValue = SWTObservables
27
				list);
29
				.observeSingleSelectionIndex(list);
28
		list.add("Item1");
30
		list.add("Item1");
29
31
30
		assertEquals(-1, list.getSelectionIndex());
32
		assertEquals(-1, list.getSelectionIndex());
Lines 39-46 Link Here
39
41
40
	public void testDispose() throws Exception {
42
	public void testDispose() throws Exception {
41
		List list = new List(getShell(), SWT.NONE);
43
		List list = new List(getShell(), SWT.NONE);
42
		ListSingleSelectionObservableValue observableValue = new ListSingleSelectionObservableValue(
44
		IObservableValue observableValue = SWTObservables
43
				list);
45
				.observeSingleSelectionIndex(list);
44
		list.add("Item1");
46
		list.add("Item1");
45
		list.add("Item2");
47
		list.add("Item2");
46
48
(-)src/org/eclipse/jface/tests/internal/databinding/swt/ShellObservableValueTest.java (-7 / +10 lines)
Lines 7-13 Link Here
7
 *
7
 *
8
 * Contributors:
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 212235)
9
 *     Matthew Hall - initial API and implementation (bug 212235)
10
 *     Matthew Hall - bug 213145
10
 *     Matthew Hall - bug 213145, 194734
11
 ******************************************************************************/
11
 ******************************************************************************/
12
12
13
package org.eclipse.jface.tests.internal.databinding.swt;
13
package org.eclipse.jface.tests.internal.databinding.swt;
Lines 21-27 Link Here
21
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
21
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
22
import org.eclipse.jface.databinding.conformance.swt.SWTMutableObservableValueContractTest;
22
import org.eclipse.jface.databinding.conformance.swt.SWTMutableObservableValueContractTest;
23
import org.eclipse.jface.databinding.conformance.util.ValueChangeEventTracker;
23
import org.eclipse.jface.databinding.conformance.util.ValueChangeEventTracker;
24
import org.eclipse.jface.internal.databinding.swt.ShellObservableValue;
24
import org.eclipse.jface.databinding.swt.SWTObservables;
25
import org.eclipse.jface.databinding.swt.ShellProperties;
25
import org.eclipse.jface.tests.databinding.AbstractDefaultRealmTestCase;
26
import org.eclipse.jface.tests.databinding.AbstractDefaultRealmTestCase;
26
import org.eclipse.swt.widgets.Shell;
27
import org.eclipse.swt.widgets.Shell;
27
28
Lines 34-46 Link Here
34
	String oldValue;
35
	String oldValue;
35
	String newValue;
36
	String newValue;
36
	Shell shell;
37
	Shell shell;
37
	ShellObservableValue observable;
38
	IObservableValue observable;
38
	ValueChangeEventTracker tracker;
39
	ValueChangeEventTracker tracker;
39
40
40
	protected void setUp() throws Exception {
41
	protected void setUp() throws Exception {
41
		super.setUp();
42
		super.setUp();
42
		shell = new Shell();
43
		shell = new Shell();
43
		observable = new ShellObservableValue(shell);
44
		observable = SWTObservables.observeText(shell);
44
		oldValue = "old";
45
		oldValue = "old";
45
		newValue = "new";
46
		newValue = "new";
46
		shell.setText(oldValue);
47
		shell.setText(oldValue);
Lines 88-96 Link Here
88
	}
89
	}
89
90
90
	public static Test suite() {
91
	public static Test suite() {
91
		TestSuite suite = new TestSuite(ShellObservableValueTest.class.toString());
92
		TestSuite suite = new TestSuite(ShellObservableValueTest.class
93
				.toString());
92
		suite.addTestSuite(ShellObservableValueTest.class);
94
		suite.addTestSuite(ShellObservableValueTest.class);
93
		suite.addTest(SWTMutableObservableValueContractTest.suite(new Delegate()));
95
		suite.addTest(SWTMutableObservableValueContractTest
96
				.suite(new Delegate()));
94
		return suite;
97
		return suite;
95
	}
98
	}
96
99
Lines 109-115 Link Here
109
		}
112
		}
110
113
111
		public IObservableValue createObservableValue(Realm realm) {
114
		public IObservableValue createObservableValue(Realm realm) {
112
			return new ShellObservableValue(realm, shell);
115
			return ShellProperties.text().observeValue(realm, shell);
113
		}
116
		}
114
117
115
		public Object getValueType(IObservableValue observable) {
118
		public Object getValueType(IObservableValue observable) {
(-)src/org/eclipse/jface/tests/internal/databinding/swt/ComboSingleSelectionObservableValueTest.java (-3 / +5 lines)
Lines 7-16 Link Here
7
 *
7
 *
8
 * Contributors:
8
 * Contributors:
9
 *     Ashley Cambrell - initial API and implementation (bug 198903)
9
 *     Ashley Cambrell - initial API and implementation (bug 198903)
10
 *     Matthew Hall - bug 194734
10
 ******************************************************************************/
11
 ******************************************************************************/
11
package org.eclipse.jface.tests.internal.databinding.swt;
12
package org.eclipse.jface.tests.internal.databinding.swt;
12
13
13
import org.eclipse.jface.internal.databinding.swt.ComboSingleSelectionObservableValue;
14
import org.eclipse.core.databinding.observable.value.IObservableValue;
15
import org.eclipse.jface.databinding.swt.SWTObservables;
14
import org.eclipse.jface.tests.databinding.AbstractSWTTestCase;
16
import org.eclipse.jface.tests.databinding.AbstractSWTTestCase;
15
import org.eclipse.swt.SWT;
17
import org.eclipse.swt.SWT;
16
import org.eclipse.swt.widgets.Combo;
18
import org.eclipse.swt.widgets.Combo;
Lines 23-30 Link Here
23
		AbstractSWTTestCase {
25
		AbstractSWTTestCase {
24
	public void testSetValue() throws Exception {
26
	public void testSetValue() throws Exception {
25
		Combo combo = new Combo(getShell(), SWT.NONE);
27
		Combo combo = new Combo(getShell(), SWT.NONE);
26
		ComboSingleSelectionObservableValue observableValue = new ComboSingleSelectionObservableValue(
28
		IObservableValue observableValue = SWTObservables
27
				combo);
29
				.observeSingleSelectionIndex(combo);
28
		combo.add("Item1");
30
		combo.add("Item1");
29
		combo.add("Item2");
31
		combo.add("Item2");
30
32
(-)src/org/eclipse/jface/tests/internal/databinding/swt/CComboObservableValueTextTest.java (-9 / +11 lines)
Lines 7-13 Link Here
7
 *
7
 *
8
 * Contributors:
8
 * Contributors:
9
 *     Brad Reynolds - initial API and implementation
9
 *     Brad Reynolds - initial API and implementation
10
 *     Matthew Hall - bug 213145
10
 *     Matthew Hall - bug 213145, 194734
11
 ******************************************************************************/
11
 ******************************************************************************/
12
12
13
package org.eclipse.jface.tests.internal.databinding.swt;
13
package org.eclipse.jface.tests.internal.databinding.swt;
Lines 22-31 Link Here
22
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
22
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
23
import org.eclipse.jface.databinding.conformance.swt.SWTMutableObservableValueContractTest;
23
import org.eclipse.jface.databinding.conformance.swt.SWTMutableObservableValueContractTest;
24
import org.eclipse.jface.databinding.conformance.util.ValueChangeEventTracker;
24
import org.eclipse.jface.databinding.conformance.util.ValueChangeEventTracker;
25
import org.eclipse.jface.databinding.swt.ISWTObservable;
25
import org.eclipse.jface.databinding.swt.CComboProperties;
26
import org.eclipse.jface.databinding.swt.SWTObservables;
26
import org.eclipse.jface.databinding.swt.SWTObservables;
27
import org.eclipse.jface.internal.databinding.swt.CComboObservableValue;
27
import org.eclipse.jface.internal.databinding.swt.SWTObservableValueDecorator;
28
import org.eclipse.jface.internal.databinding.swt.SWTProperties;
29
import org.eclipse.swt.SWT;
28
import org.eclipse.swt.SWT;
30
import org.eclipse.swt.custom.CCombo;
29
import org.eclipse.swt.custom.CCombo;
31
import org.eclipse.swt.widgets.Display;
30
import org.eclipse.swt.widgets.Display;
Lines 66-74 Link Here
66
	}
65
	}
67
66
68
	public static Test suite() {
67
	public static Test suite() {
69
		TestSuite suite = new TestSuite(CComboObservableValueTextTest.class.getName());
68
		TestSuite suite = new TestSuite(CComboObservableValueTextTest.class
69
				.getName());
70
		suite.addTestSuite(CComboObservableValueTextTest.class);
70
		suite.addTestSuite(CComboObservableValueTextTest.class);
71
		suite.addTest(SWTMutableObservableValueContractTest.suite(new Delegate()));
71
		suite.addTest(SWTMutableObservableValueContractTest
72
				.suite(new Delegate()));
72
		return suite;
73
		return suite;
73
	}
74
	}
74
75
Lines 88-99 Link Here
88
		}
89
		}
89
90
90
		public IObservableValue createObservableValue(Realm realm) {
91
		public IObservableValue createObservableValue(Realm realm) {
91
			return new CComboObservableValue(realm, combo, SWTProperties.TEXT);
92
			return new SWTObservableValueDecorator(CComboProperties.text()
93
					.observeValue(realm, combo), combo);
92
		}
94
		}
93
95
94
		public void change(IObservable observable) {
96
		public void change(IObservable observable) {
95
			CCombo combo = (CCombo) ((ISWTObservable) observable).getWidget();
97
			IObservableValue ov = (IObservableValue) observable;
96
			combo.setText(combo.getText() + "a");
98
			ov.setValue(createValue(ov));
97
		}
99
		}
98
100
99
		public Object getValueType(IObservableValue observable) {
101
		public Object getValueType(IObservableValue observable) {
(-)src/org/eclipse/jface/tests/internal/databinding/swt/ComboObservableValueTextTest.java (-9 / +11 lines)
Lines 7-13 Link Here
7
 *
7
 *
8
 * Contributors:
8
 * Contributors:
9
 *     Brad Reynolds - initial API and implementation
9
 *     Brad Reynolds - initial API and implementation
10
 *     Matthew Hall - bug 213145
10
 *     Matthew Hall - bug 213145, 194734
11
 ******************************************************************************/
11
 ******************************************************************************/
12
12
13
package org.eclipse.jface.tests.internal.databinding.swt;
13
package org.eclipse.jface.tests.internal.databinding.swt;
Lines 22-31 Link Here
22
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
22
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
23
import org.eclipse.jface.databinding.conformance.swt.SWTMutableObservableValueContractTest;
23
import org.eclipse.jface.databinding.conformance.swt.SWTMutableObservableValueContractTest;
24
import org.eclipse.jface.databinding.conformance.util.ValueChangeEventTracker;
24
import org.eclipse.jface.databinding.conformance.util.ValueChangeEventTracker;
25
import org.eclipse.jface.databinding.swt.ISWTObservable;
25
import org.eclipse.jface.databinding.swt.ComboProperties;
26
import org.eclipse.jface.databinding.swt.SWTObservables;
26
import org.eclipse.jface.databinding.swt.SWTObservables;
27
import org.eclipse.jface.internal.databinding.swt.ComboObservableValue;
27
import org.eclipse.jface.internal.databinding.swt.SWTObservableValueDecorator;
28
import org.eclipse.jface.internal.databinding.swt.SWTProperties;
29
import org.eclipse.swt.SWT;
28
import org.eclipse.swt.SWT;
30
import org.eclipse.swt.widgets.Combo;
29
import org.eclipse.swt.widgets.Combo;
31
import org.eclipse.swt.widgets.Display;
30
import org.eclipse.swt.widgets.Display;
Lines 67-75 Link Here
67
	}
66
	}
68
67
69
	public static Test suite() {
68
	public static Test suite() {
70
		TestSuite suite = new TestSuite(ComboObservableValueTextTest.class.toString());
69
		TestSuite suite = new TestSuite(ComboObservableValueTextTest.class
70
				.toString());
71
		suite.addTestSuite(ComboObservableValueTextTest.class);
71
		suite.addTestSuite(ComboObservableValueTextTest.class);
72
		suite.addTest(SWTMutableObservableValueContractTest.suite(new Delegate()));
72
		suite.addTest(SWTMutableObservableValueContractTest
73
				.suite(new Delegate()));
73
		return suite;
74
		return suite;
74
	}
75
	}
75
76
Lines 89-100 Link Here
89
		}
90
		}
90
91
91
		public IObservableValue createObservableValue(Realm realm) {
92
		public IObservableValue createObservableValue(Realm realm) {
92
			return new ComboObservableValue(realm, combo, SWTProperties.TEXT);
93
			return new SWTObservableValueDecorator(ComboProperties.text()
94
					.observeValue(realm, combo), combo);
93
		}
95
		}
94
96
95
		public void change(IObservable observable) {
97
		public void change(IObservable observable) {
96
			Combo combo = (Combo) ((ISWTObservable) observable).getWidget();
98
			((IObservableValue) observable)
97
			combo.setText(combo.getText() + "a");
99
					.setValue(createValue((IObservableValue) observable));
98
		}
100
		}
99
101
100
		public Object getValueType(IObservableValue observable) {
102
		public Object getValueType(IObservableValue observable) {
(-)src/org/eclipse/jface/tests/internal/databinding/swt/SpinnerObservableValueSelectionTest.java (-11 / +12 lines)
Lines 7-13 Link Here
7
 *
7
 *
8
 * Contributors:
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
9
 *     IBM Corporation - initial API and implementation
10
 *     Matthew Hall - bug 213145
10
 *     Matthew Hall - bug 213145, 194734
11
 *******************************************************************************/
11
 *******************************************************************************/
12
12
13
package org.eclipse.jface.tests.internal.databinding.swt;
13
package org.eclipse.jface.tests.internal.databinding.swt;
Lines 22-29 Link Here
22
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
22
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
23
import org.eclipse.jface.databinding.conformance.swt.SWTMutableObservableValueContractTest;
23
import org.eclipse.jface.databinding.conformance.swt.SWTMutableObservableValueContractTest;
24
import org.eclipse.jface.databinding.swt.SWTObservables;
24
import org.eclipse.jface.databinding.swt.SWTObservables;
25
import org.eclipse.jface.internal.databinding.swt.SWTProperties;
25
import org.eclipse.jface.databinding.swt.SpinnerProperties;
26
import org.eclipse.jface.internal.databinding.swt.SpinnerObservableValue;
27
import org.eclipse.swt.SWT;
26
import org.eclipse.swt.SWT;
28
import org.eclipse.swt.widgets.Display;
27
import org.eclipse.swt.widgets.Display;
29
import org.eclipse.swt.widgets.Shell;
28
import org.eclipse.swt.widgets.Shell;
Lines 38-44 Link Here
38
	private Spinner spinner;
37
	private Spinner spinner;
39
38
40
	private IObservableValue observable;
39
	private IObservableValue observable;
41
	
40
42
	public SpinnerObservableValueSelectionTest() {
41
	public SpinnerObservableValueSelectionTest() {
43
		this(null);
42
		this(null);
44
	}
43
	}
Lines 56-62 Link Here
56
	}
55
	}
57
56
58
	protected IObservable doCreateObservable() {
57
	protected IObservable doCreateObservable() {
59
		return getObservableContractDelegate().createObservable(SWTObservables.getRealm(Display.getDefault()));
58
		return getObservableContractDelegate().createObservable(
59
				SWTObservables.getRealm(Display.getDefault()));
60
	}
60
	}
61
61
62
	public void testGetValue() throws Exception {
62
	public void testGetValue() throws Exception {
Lines 72-80 Link Here
72
	}
72
	}
73
73
74
	public static Test suite() {
74
	public static Test suite() {
75
		TestSuite suite = new TestSuite(SpinnerObservableValueSelectionTest.class.toString());
75
		TestSuite suite = new TestSuite(
76
				SpinnerObservableValueSelectionTest.class.toString());
76
		suite.addTestSuite(SpinnerObservableValueSelectionTest.class);
77
		suite.addTestSuite(SpinnerObservableValueSelectionTest.class);
77
		suite.addTest(SWTMutableObservableValueContractTest.suite(new Delegate()));
78
		suite.addTest(SWTMutableObservableValueContractTest
79
				.suite(new Delegate()));
78
		return suite;
80
		return suite;
79
	}
81
	}
80
82
Lines 95-107 Link Here
95
		}
97
		}
96
98
97
		public IObservableValue createObservableValue(Realm realm) {
99
		public IObservableValue createObservableValue(Realm realm) {
98
			return new SpinnerObservableValue(realm, spinner, SWTProperties.SELECTION);
100
			return SpinnerProperties.selection().observeValue(realm, spinner);
99
		}
101
		}
100
102
101
		public void change(IObservable observable) {
103
		public void change(IObservable observable) {
102
			spinner
104
			spinner.setSelection(createIntegerValue(
103
					.setSelection(createIntegerValue(
105
					(IObservableValue) observable).intValue());
104
							(IObservableValue) observable).intValue());
105
			spinner.notifyListeners(SWT.Selection, null);
106
			spinner.notifyListeners(SWT.Selection, null);
106
		}
107
		}
107
108
(-)src/org/eclipse/jface/tests/internal/databinding/swt/ComboObservableValueTest.java (-16 / +22 lines)
Lines 8-20 Link Here
8
 * Contributors:
8
 * Contributors:
9
 *     Brad Reynolds - initial API and implementation
9
 *     Brad Reynolds - initial API and implementation
10
 *     Ashley Cambrell - bug 198904
10
 *     Ashley Cambrell - bug 198904
11
 *     Matthew Hall - bug 194734
11
 ******************************************************************************/
12
 ******************************************************************************/
12
13
13
package org.eclipse.jface.tests.internal.databinding.swt;
14
package org.eclipse.jface.tests.internal.databinding.swt;
14
15
16
import org.eclipse.core.databinding.observable.Realm;
17
import org.eclipse.core.databinding.observable.value.IObservableValue;
18
import org.eclipse.core.databinding.property.value.IValueProperty;
15
import org.eclipse.jface.databinding.conformance.util.ValueChangeEventTracker;
19
import org.eclipse.jface.databinding.conformance.util.ValueChangeEventTracker;
16
import org.eclipse.jface.internal.databinding.swt.ComboObservableValue;
20
import org.eclipse.jface.databinding.swt.ComboProperties;
17
import org.eclipse.jface.internal.databinding.swt.SWTProperties;
21
import org.eclipse.jface.databinding.swt.SWTObservables;
22
import org.eclipse.jface.internal.databinding.swt.ComboSelectionProperty;
23
import org.eclipse.jface.internal.databinding.swt.ComboTextProperty;
18
import org.eclipse.jface.tests.databinding.AbstractSWTTestCase;
24
import org.eclipse.jface.tests.databinding.AbstractSWTTestCase;
19
import org.eclipse.swt.SWT;
25
import org.eclipse.swt.SWT;
20
import org.eclipse.swt.widgets.Combo;
26
import org.eclipse.swt.widgets.Combo;
Lines 26-33 Link Here
26
public class ComboObservableValueTest extends AbstractSWTTestCase {
32
public class ComboObservableValueTest extends AbstractSWTTestCase {
27
	public void testDispose() throws Exception {
33
	public void testDispose() throws Exception {
28
		Combo combo = new Combo(getShell(), SWT.NONE);
34
		Combo combo = new Combo(getShell(), SWT.NONE);
29
		ComboObservableValue observableValue = new ComboObservableValue(combo,
35
		IObservableValue observableValue = SWTObservables.observeText(combo);
30
				SWTProperties.TEXT);
31
		ValueChangeEventTracker testCounterValueChangeListener = new ValueChangeEventTracker();
36
		ValueChangeEventTracker testCounterValueChangeListener = new ValueChangeEventTracker();
32
		observableValue.addValueChangeListener(testCounterValueChangeListener);
37
		observableValue.addValueChangeListener(testCounterValueChangeListener);
33
38
Lines 51-75 Link Here
51
	}
56
	}
52
57
53
	public void testSetValueWithNull() {
58
	public void testSetValueWithNull() {
54
		testSetValueWithNull(SWTProperties.TEXT);
59
		testSetValueWithNull(ComboProperties.text());
55
		testSetValueWithNull(SWTProperties.SELECTION);
60
		testSetValueWithNull(ComboProperties.selection());
56
	}
61
	}
57
62
58
	protected void testSetValueWithNull(String observableMode) {
63
	protected void testSetValueWithNull(IValueProperty property) {
59
		Combo combo = new Combo(getShell(), SWT.NONE);
64
		Combo combo = new Combo(getShell(), SWT.NONE);
60
		combo.setItems(new String[] {"one", "two", "three"});
65
		combo.setItems(new String[] { "one", "two", "three" });
61
		ComboObservableValue observable = new ComboObservableValue(
66
		IObservableValue observable = property.observeValue(Realm.getDefault(),
62
				combo, observableMode);
67
				combo);
63
68
64
		observable.doSetValue("two");
69
		observable.setValue("two");
65
		assertEquals("two", combo.getText());
70
		assertEquals("two", combo.getText());
66
		if (observableMode.equals(SWTProperties.SELECTION)) {
71
		if (property instanceof ComboSelectionProperty) {
67
			assertEquals("expect selection at index 1 in mode " + observableMode, 1, combo.getSelectionIndex());
72
			assertEquals("expect selection at index 1 in selection mode", 1,
73
					combo.getSelectionIndex());
68
		}
74
		}
69
75
70
		if (observableMode.equals(SWTProperties.TEXT)) {
76
		if (property instanceof ComboTextProperty) {
71
			observable.doSetValue(null);
77
			observable.setValue(null);
72
			assertEquals("expect empty text in mode " + observableMode, "", combo.getText());
78
			assertEquals("expect empty text in text mode", "", combo.getText());
73
		}
79
		}
74
	}
80
	}
75
}
81
}
(-)src/org/eclipse/jface/tests/internal/databinding/swt/CComboObservableValueSelectionTest.java (-11 / +12 lines)
Lines 22-31 Link Here
22
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
22
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
23
import org.eclipse.jface.databinding.conformance.swt.SWTMutableObservableValueContractTest;
23
import org.eclipse.jface.databinding.conformance.swt.SWTMutableObservableValueContractTest;
24
import org.eclipse.jface.databinding.conformance.util.ValueChangeEventTracker;
24
import org.eclipse.jface.databinding.conformance.util.ValueChangeEventTracker;
25
import org.eclipse.jface.databinding.swt.CComboProperties;
25
import org.eclipse.jface.databinding.swt.ISWTObservable;
26
import org.eclipse.jface.databinding.swt.ISWTObservable;
26
import org.eclipse.jface.databinding.swt.SWTObservables;
27
import org.eclipse.jface.databinding.swt.SWTObservables;
27
import org.eclipse.jface.internal.databinding.swt.CComboObservableValue;
28
import org.eclipse.jface.internal.databinding.swt.SWTObservableValueDecorator;
28
import org.eclipse.jface.internal.databinding.swt.SWTProperties;
29
import org.eclipse.swt.SWT;
29
import org.eclipse.swt.SWT;
30
import org.eclipse.swt.custom.CCombo;
30
import org.eclipse.swt.custom.CCombo;
31
import org.eclipse.swt.widgets.Display;
31
import org.eclipse.swt.widgets.Display;
Lines 57-72 Link Here
57
		IObservableValue observable = (IObservableValue) delegate
57
		IObservableValue observable = (IObservableValue) delegate
58
				.createObservable(SWTObservables.getRealm(Display.getDefault()));
58
				.createObservable(SWTObservables.getRealm(Display.getDefault()));
59
59
60
		ValueChangeEventTracker listener = ValueChangeEventTracker.observe(observable);
60
		ValueChangeEventTracker listener = ValueChangeEventTracker
61
				.observe(observable);
61
		combo.select(0);
62
		combo.select(0);
62
63
63
		assertEquals("Observable was not notified.", 1, listener.count);
64
		assertEquals("Observable was not notified.", 1, listener.count);
64
	}
65
	}
65
66
66
	public static Test suite() {
67
	public static Test suite() {
67
		TestSuite suite = new TestSuite(CComboObservableValueSelectionTest.class.getName());
68
		TestSuite suite = new TestSuite(
69
				CComboObservableValueSelectionTest.class.getName());
68
		suite.addTestSuite(CComboObservableValueSelectionTest.class);
70
		suite.addTestSuite(CComboObservableValueSelectionTest.class);
69
		suite.addTest(SWTMutableObservableValueContractTest.suite(new Delegate()));
71
		suite.addTest(SWTMutableObservableValueContractTest
72
				.suite(new Delegate()));
70
		return suite;
73
		return suite;
71
	}
74
	}
72
75
Lines 88-102 Link Here
88
		}
91
		}
89
92
90
		public IObservableValue createObservableValue(Realm realm) {
93
		public IObservableValue createObservableValue(Realm realm) {
91
			return new CComboObservableValue(realm, combo,
94
			return new SWTObservableValueDecorator(CComboProperties.selection()
92
					SWTProperties.SELECTION);
95
					.observeValue(realm, combo), combo);
93
		}
96
		}
94
97
95
		public void change(IObservable observable) {
98
		public void change(IObservable observable) {
96
			int index = combo
99
			IObservableValue ov = (IObservableValue) observable;
97
					.indexOf((String) createValue((IObservableValue) observable));
100
			ov.setValue(createValue(ov));
98
99
			combo.select(index);
100
		}
101
		}
101
102
102
		public Object getValueType(IObservableValue observable) {
103
		public Object getValueType(IObservableValue observable) {
(-)src/org/eclipse/jface/tests/internal/databinding/swt/CComboObservableValueTest.java (-12 / +16 lines)
Lines 9-21 Link Here
9
 *     Brad Reynolds - initial API and implementation
9
 *     Brad Reynolds - initial API and implementation
10
 *     Ashley Cambrell - bug 198904
10
 *     Ashley Cambrell - bug 198904
11
 *     Eric Rizzo - bug 134884
11
 *     Eric Rizzo - bug 134884
12
 *     Matthew Hall - bug 194734
12
 ******************************************************************************/
13
 ******************************************************************************/
13
14
14
package org.eclipse.jface.tests.internal.databinding.swt;
15
package org.eclipse.jface.tests.internal.databinding.swt;
15
16
17
import org.eclipse.core.databinding.observable.Realm;
18
import org.eclipse.core.databinding.observable.value.IObservableValue;
19
import org.eclipse.core.databinding.property.value.IValueProperty;
16
import org.eclipse.jface.databinding.conformance.util.ValueChangeEventTracker;
20
import org.eclipse.jface.databinding.conformance.util.ValueChangeEventTracker;
17
import org.eclipse.jface.internal.databinding.swt.CComboObservableValue;
21
import org.eclipse.jface.databinding.swt.CComboProperties;
18
import org.eclipse.jface.internal.databinding.swt.SWTProperties;
22
import org.eclipse.jface.databinding.swt.ISWTObservableValue;
23
import org.eclipse.jface.databinding.swt.SWTObservables;
19
import org.eclipse.jface.tests.databinding.AbstractSWTTestCase;
24
import org.eclipse.jface.tests.databinding.AbstractSWTTestCase;
20
import org.eclipse.swt.SWT;
25
import org.eclipse.swt.SWT;
21
import org.eclipse.swt.custom.CCombo;
26
import org.eclipse.swt.custom.CCombo;
Lines 26-33 Link Here
26
public class CComboObservableValueTest extends AbstractSWTTestCase {
31
public class CComboObservableValueTest extends AbstractSWTTestCase {
27
	public void testDispose() throws Exception {
32
	public void testDispose() throws Exception {
28
		CCombo combo = new CCombo(getShell(), SWT.NONE);
33
		CCombo combo = new CCombo(getShell(), SWT.NONE);
29
		CComboObservableValue observableValue = new CComboObservableValue(
34
		ISWTObservableValue observableValue = SWTObservables.observeText(combo);
30
				combo, SWTProperties.TEXT);
31
35
32
		ValueChangeEventTracker testCounterValueChangeListener = new ValueChangeEventTracker();
36
		ValueChangeEventTracker testCounterValueChangeListener = new ValueChangeEventTracker();
33
		observableValue.addValueChangeListener(testCounterValueChangeListener);
37
		observableValue.addValueChangeListener(testCounterValueChangeListener);
Lines 52-72 Link Here
52
	}
56
	}
53
57
54
	public void testSetValueWithNull() {
58
	public void testSetValueWithNull() {
55
		testSetValueWithNull(SWTProperties.TEXT);
59
		testSetValueWithNull(CComboProperties.text());
56
		testSetValueWithNull(SWTProperties.SELECTION);
60
		testSetValueWithNull(CComboProperties.selection());
57
	}
61
	}
58
62
59
	protected void testSetValueWithNull(String observableMode) {
63
	protected void testSetValueWithNull(IValueProperty property) {
60
		CCombo combo = new CCombo(getShell(), SWT.NONE);
64
		CCombo combo = new CCombo(getShell(), SWT.NONE);
61
		combo.setItems(new String[] {"one", "two", "three"});
65
		combo.setItems(new String[] { "one", "two", "three" });
62
		CComboObservableValue observable = new CComboObservableValue(
66
		IObservableValue observable = property.observeValue(Realm.getDefault(),
63
				combo, observableMode);
67
				combo);
64
68
65
		observable.doSetValue("two");
69
		observable.setValue("two");
66
		assertEquals("two", combo.getText());
70
		assertEquals("two", combo.getText());
67
		assertEquals(1, combo.getSelectionIndex());
71
		assertEquals(1, combo.getSelectionIndex());
68
72
69
		observable.doSetValue(null);
73
		observable.setValue(null);
70
		assertEquals("", combo.getText());
74
		assertEquals("", combo.getText());
71
		assertEquals(-1, combo.getSelectionIndex());
75
		assertEquals(-1, combo.getSelectionIndex());
72
	}
76
	}
(-)src/org/eclipse/jface/tests/internal/databinding/swt/TextObservableValueModifyTest.java (-7 / +9 lines)
Lines 7-13 Link Here
7
 *
7
 *
8
 * Contributors:
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
9
 *     IBM Corporation - initial API and implementation
10
 *     Matthew Hall - bug 213145
10
 *     Matthew Hall - bug 213145, 194734
11
 *******************************************************************************/
11
 *******************************************************************************/
12
12
13
package org.eclipse.jface.tests.internal.databinding.swt;
13
package org.eclipse.jface.tests.internal.databinding.swt;
Lines 21-27 Link Here
21
import org.eclipse.core.databinding.observable.value.IObservableValue;
21
import org.eclipse.core.databinding.observable.value.IObservableValue;
22
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
22
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
23
import org.eclipse.jface.databinding.conformance.swt.SWTMutableObservableValueContractTest;
23
import org.eclipse.jface.databinding.conformance.swt.SWTMutableObservableValueContractTest;
24
import org.eclipse.jface.internal.databinding.swt.TextObservableValue;
24
import org.eclipse.jface.databinding.swt.TextProperties;
25
import org.eclipse.swt.SWT;
25
import org.eclipse.swt.SWT;
26
import org.eclipse.swt.widgets.Shell;
26
import org.eclipse.swt.widgets.Shell;
27
import org.eclipse.swt.widgets.Text;
27
import org.eclipse.swt.widgets.Text;
Lines 31-38 Link Here
31
 */
31
 */
32
public class TextObservableValueModifyTest extends TestCase {
32
public class TextObservableValueModifyTest extends TestCase {
33
	public static Test suite() {
33
	public static Test suite() {
34
		TestSuite suite = new TestSuite(TextObservableValueModifyTest.class.toString());
34
		TestSuite suite = new TestSuite(TextObservableValueModifyTest.class
35
		suite.addTest(SWTMutableObservableValueContractTest.suite(new Delegate()));
35
				.toString());
36
		suite.addTest(SWTMutableObservableValueContractTest
37
				.suite(new Delegate()));
36
		return suite;
38
		return suite;
37
	}
39
	}
38
40
Lines 41-47 Link Here
41
		private Shell shell;
43
		private Shell shell;
42
44
43
		private Text text;
45
		private Text text;
44
		
46
45
		public void setUp() {
47
		public void setUp() {
46
			shell = new Shell();
48
			shell = new Shell();
47
			text = new Text(shell, SWT.NONE);
49
			text = new Text(shell, SWT.NONE);
Lines 52-58 Link Here
52
		}
54
		}
53
55
54
		public IObservableValue createObservableValue(Realm realm) {
56
		public IObservableValue createObservableValue(Realm realm) {
55
			return new TextObservableValue(realm, text, SWT.Modify);
57
			return TextProperties.text(SWT.Modify).observeValue(realm, text);
56
		}
58
		}
57
59
58
		public Object getValueType(IObservableValue observable) {
60
		public Object getValueType(IObservableValue observable) {
Lines 61-67 Link Here
61
63
62
		public void change(IObservable observable) {
64
		public void change(IObservable observable) {
63
			text.setFocus();
65
			text.setFocus();
64
			
66
65
			IObservableValue observableValue = (IObservableValue) observable;
67
			IObservableValue observableValue = (IObservableValue) observable;
66
			text.setText((String) createValue(observableValue));
68
			text.setText((String) createValue(observableValue));
67
		}
69
		}
(-)src/org/eclipse/jface/tests/internal/databinding/swt/ComboObservableValueSelectionTest.java (-10 / +11 lines)
Lines 7-13 Link Here
7
 *
7
 *
8
 * Contributors:
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
9
 *     IBM Corporation - initial API and implementation
10
 *     Matthew Hall - bug 213145
10
 *     Matthew Hall - bug 213145, 194734
11
 *******************************************************************************/
11
 *******************************************************************************/
12
12
13
package org.eclipse.jface.tests.internal.databinding.swt;
13
package org.eclipse.jface.tests.internal.databinding.swt;
Lines 22-31 Link Here
22
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
22
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
23
import org.eclipse.jface.databinding.conformance.swt.SWTMutableObservableValueContractTest;
23
import org.eclipse.jface.databinding.conformance.swt.SWTMutableObservableValueContractTest;
24
import org.eclipse.jface.databinding.conformance.util.ValueChangeEventTracker;
24
import org.eclipse.jface.databinding.conformance.util.ValueChangeEventTracker;
25
import org.eclipse.jface.databinding.swt.ComboProperties;
25
import org.eclipse.jface.databinding.swt.ISWTObservable;
26
import org.eclipse.jface.databinding.swt.ISWTObservable;
26
import org.eclipse.jface.databinding.swt.SWTObservables;
27
import org.eclipse.jface.databinding.swt.SWTObservables;
27
import org.eclipse.jface.internal.databinding.swt.ComboObservableValue;
28
import org.eclipse.jface.internal.databinding.swt.SWTObservableValueDecorator;
28
import org.eclipse.jface.internal.databinding.swt.SWTProperties;
29
import org.eclipse.swt.SWT;
29
import org.eclipse.swt.SWT;
30
import org.eclipse.swt.widgets.Combo;
30
import org.eclipse.swt.widgets.Combo;
31
import org.eclipse.swt.widgets.Display;
31
import org.eclipse.swt.widgets.Display;
Lines 33-39 Link Here
33
33
34
/**
34
/**
35
 * @since 3.2
35
 * @since 3.2
36
 *
36
 * 
37
 */
37
 */
38
public class ComboObservableValueSelectionTest extends TestCase {
38
public class ComboObservableValueSelectionTest extends TestCase {
39
	private Delegate delegate;
39
	private Delegate delegate;
Lines 67-75 Link Here
67
	}
67
	}
68
68
69
	public static Test suite() {
69
	public static Test suite() {
70
		TestSuite suite = new TestSuite(ComboObservableValueSelectionTest.class.toString());
70
		TestSuite suite = new TestSuite(ComboObservableValueSelectionTest.class
71
				.toString());
71
		suite.addTestSuite(ComboObservableValueSelectionTest.class);
72
		suite.addTestSuite(ComboObservableValueSelectionTest.class);
72
		suite.addTest(SWTMutableObservableValueContractTest.suite(new Delegate()));
73
		suite.addTest(SWTMutableObservableValueContractTest
74
				.suite(new Delegate()));
73
		return suite;
75
		return suite;
74
	}
76
	}
75
77
Lines 91-106 Link Here
91
		}
93
		}
92
94
93
		public IObservableValue createObservableValue(Realm realm) {
95
		public IObservableValue createObservableValue(Realm realm) {
94
			return new ComboObservableValue(realm, combo,
96
			return new SWTObservableValueDecorator(ComboProperties.selection()
95
					SWTProperties.SELECTION);
97
					.observeValue(realm, combo), combo);
96
		}
98
		}
97
99
98
		public void change(IObservable observable) {
100
		public void change(IObservable observable) {
99
			int index = combo
101
			int index = combo
100
					.indexOf((String) createValue((IObservableValue) observable));
102
					.indexOf((String) createValue((IObservableValue) observable));
101
103
102
			combo.select(index);
104
			((IObservableValue) observable).setValue(combo.getItem(index));
103
			combo.notifyListeners(SWT.Selection, null);
104
		}
105
		}
105
106
106
		public Object getValueType(IObservableValue observable) {
107
		public Object getValueType(IObservableValue observable) {
(-)src/org/eclipse/core/tests/internal/databinding/beans/JavaBeanObservableArrayBasedListTest.java (-64 / +76 lines)
Lines 7-18 Link Here
7
 *
7
 *
8
 * Contributors:
8
 * Contributors:
9
 *     Brad Reynolds - initial API and implementation
9
 *     Brad Reynolds - initial API and implementation
10
 *     Matthew Hall - bugs 221351, 213145, 244098, 246103
10
 *     Matthew Hall - bugs 221351, 213145, 244098, 246103, 194734
11
 ******************************************************************************/
11
 ******************************************************************************/
12
12
13
package org.eclipse.core.tests.internal.databinding.beans;
13
package org.eclipse.core.tests.internal.databinding.beans;
14
14
15
import java.beans.IntrospectionException;
16
import java.beans.PropertyChangeEvent;
15
import java.beans.PropertyChangeEvent;
17
import java.beans.PropertyChangeListener;
16
import java.beans.PropertyChangeListener;
18
import java.beans.PropertyDescriptor;
17
import java.beans.PropertyDescriptor;
Lines 25-38 Link Here
25
import junit.framework.Test;
24
import junit.framework.Test;
26
import junit.framework.TestSuite;
25
import junit.framework.TestSuite;
27
26
27
import org.eclipse.core.databinding.beans.BeanProperties;
28
import org.eclipse.core.databinding.beans.BeansObservables;
28
import org.eclipse.core.databinding.beans.BeansObservables;
29
import org.eclipse.core.databinding.beans.IBeanObservable;
30
import org.eclipse.core.databinding.beans.IBeanProperty;
29
import org.eclipse.core.databinding.observable.IObservable;
31
import org.eclipse.core.databinding.observable.IObservable;
30
import org.eclipse.core.databinding.observable.IObservableCollection;
32
import org.eclipse.core.databinding.observable.IObservableCollection;
31
import org.eclipse.core.databinding.observable.Realm;
33
import org.eclipse.core.databinding.observable.Realm;
32
import org.eclipse.core.databinding.observable.list.IObservableList;
34
import org.eclipse.core.databinding.observable.list.IObservableList;
33
import org.eclipse.core.databinding.observable.list.ListChangeEvent;
35
import org.eclipse.core.databinding.observable.list.ListChangeEvent;
34
import org.eclipse.core.databinding.observable.list.ListDiffEntry;
36
import org.eclipse.core.databinding.observable.list.ListDiff;
35
import org.eclipse.core.internal.databinding.beans.JavaBeanObservableList;
36
import org.eclipse.jface.databinding.conformance.MutableObservableListContractTest;
37
import org.eclipse.jface.databinding.conformance.MutableObservableListContractTest;
37
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableCollectionContractDelegate;
38
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableCollectionContractDelegate;
38
import org.eclipse.jface.databinding.conformance.util.CurrentRealm;
39
import org.eclipse.jface.databinding.conformance.util.CurrentRealm;
Lines 46-52 Link Here
46
 */
47
 */
47
public class JavaBeanObservableArrayBasedListTest extends
48
public class JavaBeanObservableArrayBasedListTest extends
48
		AbstractDefaultRealmTestCase {
49
		AbstractDefaultRealmTestCase {
49
	private JavaBeanObservableList list;
50
	private IObservableList list;
51
	private IBeanObservable beanObservable;
50
52
51
	private PropertyDescriptor propertyDescriptor;
53
	private PropertyDescriptor propertyDescriptor;
52
54
Lines 63-91 Link Here
63
		super.setUp();
65
		super.setUp();
64
66
65
		propertyName = "array";
67
		propertyName = "array";
66
		propertyDescriptor = new PropertyDescriptor(propertyName, Bean.class);
68
		propertyDescriptor = ((IBeanProperty) BeanProperties.list(
69
				Bean.class, propertyName)).getPropertyDescriptor();
67
		bean = new Bean(new Object[0]);
70
		bean = new Bean(new Object[0]);
68
71
69
		list = new JavaBeanObservableList(SWTObservables.getRealm(Display
72
		list = BeansObservables.observeList(SWTObservables.getRealm(Display
70
				.getDefault()), bean, propertyDescriptor, Bean.class);
73
				.getDefault()), bean, propertyName);
74
		beanObservable = (IBeanObservable) list;
71
	}
75
	}
72
76
73
	public void testGetObserved() throws Exception {
77
	public void testGetObserved() throws Exception {
74
		assertSame(bean, list.getObserved());
78
		assertSame(bean, beanObservable.getObserved());
75
	}
79
	}
76
80
77
	public void testGetPropertyDescriptor() throws Exception {
81
	public void testGetPropertyDescriptor() throws Exception {
78
		assertSame(propertyDescriptor, list.getPropertyDescriptor());
82
		assertEquals(propertyDescriptor, beanObservable.getPropertyDescriptor());
79
	}
83
	}
80
84
81
	public void testRegistersListenerOnCreation()
85
	public void testRegistersListenerAfterFirstListenerIsAdded()
82
			throws Exception {
86
			throws Exception {
87
		assertFalse(bean.changeSupport.hasListeners(propertyName));
88
		list.addListChangeListener(new ListChangeEventTracker());
83
		assertTrue(bean.changeSupport.hasListeners(propertyName));
89
		assertTrue(bean.changeSupport.hasListeners(propertyName));
84
	}
90
	}
85
91
86
	public void testRemovesListenerOnDisposal()
92
	public void testRemovesListenerAfterLastListenerIsRemoved()
87
			throws Exception {
93
			throws Exception {
88
		list.dispose();
94
		ListChangeEventTracker listener = new ListChangeEventTracker();
95
		list.addListChangeListener(listener);
96
97
		assertTrue(bean.changeSupport.hasListeners(propertyName));
98
		list.removeListChangeListener(listener);
89
		assertFalse(bean.changeSupport.hasListeners(propertyName));
99
		assertFalse(bean.changeSupport.hasListeners(propertyName));
90
	}
100
	}
91
101
Lines 120-127 Link Here
120
		assertEquals(1, listener.count);
130
		assertEquals(1, listener.count);
121
		ListChangeEvent event = listener.event;
131
		ListChangeEvent event = listener.event;
122
132
123
		assertEquals(list, event.getObservableList());
133
		assertSame(list, event.getObservableList());
124
		assertEntry(event.diff.getDifferences()[0], true, 0, element);
134
		assertDiff(event.diff, Collections.EMPTY_LIST, Collections
135
				.singletonList("1"));
125
	}
136
	}
126
137
127
	public void testAdd_FiresPropertyChangeEvent() throws Exception {
138
	public void testAdd_FiresPropertyChangeEvent() throws Exception {
Lines 150-156 Link Here
150
		list.add(0, element);
161
		list.add(0, element);
151
162
152
		ListChangeEvent event = listener.event;
163
		ListChangeEvent event = listener.event;
153
		assertEntry(event.diff.getDifferences()[0], true, 0, element);
164
		assertDiff(event.diff, Collections.EMPTY_LIST, Collections
165
				.singletonList("1"));
154
	}
166
	}
155
167
156
	public void testAddAtIndexPropertyChangeEvent() throws Exception {
168
	public void testAddAtIndexPropertyChangeEvent() throws Exception {
Lines 182-189 Link Here
182
194
183
		assertEquals(1, listener.count);
195
		assertEquals(1, listener.count);
184
		ListChangeEvent event = listener.event;
196
		ListChangeEvent event = listener.event;
185
		assertEquals(list, event.getObservableList());
197
		assertSame(list, event.getObservableList());
186
		assertEntry(event.diff.getDifferences()[0], false, 0, element);
198
199
		assertDiff(event.diff, Collections.singletonList("1"),
200
				Collections.EMPTY_LIST);
187
	}
201
	}
188
202
189
	public void testRemovePropertyChangeEvent() throws Exception {
203
	public void testRemovePropertyChangeEvent() throws Exception {
Lines 218-225 Link Here
218
232
219
		assertEquals(1, listener.count);
233
		assertEquals(1, listener.count);
220
		ListChangeEvent event = listener.event;
234
		ListChangeEvent event = listener.event;
221
		assertEquals(list, event.getObservableList());
235
		assertSame(list, event.getObservableList());
222
		assertEntry(event.diff.getDifferences()[0], false, 0, element);
236
237
		assertDiff(event.diff, Collections.singletonList(element),
238
				Collections.EMPTY_LIST);
223
	}
239
	}
224
240
225
	public void testRemoveAtIndexPropertyChangeEvent() throws Exception {
241
	public void testRemoveAtIndexPropertyChangeEvent() throws Exception {
Lines 252-261 Link Here
252
268
253
		assertEquals(1, listener.count);
269
		assertEquals(1, listener.count);
254
		ListChangeEvent event = listener.event;
270
		ListChangeEvent event = listener.event;
255
		assertEquals(list, event.getObservableList());
271
		assertSame(list, event.getObservableList());
256
272
257
		assertEntry(event.diff.getDifferences()[0], true, 0, elements.get(0));
273
		assertDiff(event.diff, Collections.EMPTY_LIST, Arrays
258
		assertEntry(event.diff.getDifferences()[1], true, 1, elements.get(1));
274
				.asList(new String[] { "1", "2" }));
259
	}
275
	}
260
276
261
	public void testAddAllPropertyChangeEvent() throws Exception {
277
	public void testAddAllPropertyChangeEvent() throws Exception {
Lines 292-300 Link Here
292
308
293
		assertEquals(1, listener.count);
309
		assertEquals(1, listener.count);
294
		ListChangeEvent event = listener.event;
310
		ListChangeEvent event = listener.event;
295
		assertEquals(list, event.getObservableList());
311
		assertSame(list, event.getObservableList());
296
		assertEntry(event.diff.getDifferences()[0], true, 2, elements.get(0));
312
297
		assertEntry(event.diff.getDifferences()[1], true, 3, elements.get(1));
313
		assertDiff(event.diff, Arrays.asList(new Object[] { "1", "2" }), Arrays
314
				.asList(new Object[] { "1", "2", "1", "2" }));
298
	}
315
	}
299
316
300
	public void testAddAllAtIndexPropertyChangeEvent() throws Exception {
317
	public void testAddAllAtIndexPropertyChangeEvent() throws Exception {
Lines 306-321 Link Here
306
	}
323
	}
307
324
308
	public void testRemoveAll() throws Exception {
325
	public void testRemoveAll() throws Exception {
309
		List elements = Arrays.asList(new String[] { "1", "2" });
326
		list.addAll(Arrays.asList(new String[] { "1", "2", "3", "4" }));
310
		list.addAll(elements);
311
		list.addAll(elements);
312
313
		assertEquals(4, bean.getArray().length);
327
		assertEquals(4, bean.getArray().length);
314
		list.removeAll(elements);
328
329
		list.removeAll(Arrays.asList(new String[] { "2", "4" }));
315
330
316
		assertEquals(2, bean.getArray().length);
331
		assertEquals(2, bean.getArray().length);
317
		assertEquals(elements.get(0), bean.getArray()[0]);
332
		assertEquals("1", bean.getArray()[0]);
318
		assertEquals(elements.get(1), bean.getArray()[1]);
333
		assertEquals("3", bean.getArray()[1]);
319
	}
334
	}
320
335
321
	public void testRemoveAllListChangeEvent() throws Exception {
336
	public void testRemoveAllListChangeEvent() throws Exception {
Lines 330-338 Link Here
330
		list.removeAll(elements);
345
		list.removeAll(elements);
331
346
332
		ListChangeEvent event = listener.event;
347
		ListChangeEvent event = listener.event;
333
		assertEquals(list, event.getObservableList());
348
		assertSame(list, event.getObservableList());
334
		assertEntry(event.diff.getDifferences()[0], false, 0, elements.get(0));
349
335
		assertEntry(event.diff.getDifferences()[1], false, 0, elements.get(1));
350
		assertDiff(event.diff, Arrays
351
				.asList(new Object[] { "1", "2", "1", "2" }),
352
				Collections.EMPTY_LIST);
336
	}
353
	}
337
354
338
	public void testRemoveAllPropertyChangeEvent() throws Exception {
355
	public void testRemoveAllPropertyChangeEvent() throws Exception {
Lines 369-377 Link Here
369
386
370
		assertEquals(1, listener.count);
387
		assertEquals(1, listener.count);
371
		ListChangeEvent event = listener.event;
388
		ListChangeEvent event = listener.event;
372
		assertEquals(list, event.getObservableList());
389
		assertSame(list, event.getObservableList());
373
		assertEntry(event.diff.getDifferences()[0], false, 2, elements.get(2));
390
374
		assertEntry(event.diff.getDifferences()[1], false, 2, elements.get(3));
391
		assertDiff(event.diff, Arrays
392
				.asList(new Object[] { "0", "1", "2", "3" }), Arrays
393
				.asList(new Object[] { "0", "1" }));
375
	}
394
	}
376
395
377
	public void testRetainAllPropertyChangeEvent() throws Exception {
396
	public void testRetainAllPropertyChangeEvent() throws Exception {
Lines 425-433 Link Here
425
444
426
		assertEquals(1, listener.count);
445
		assertEquals(1, listener.count);
427
		ListChangeEvent event = listener.event;
446
		ListChangeEvent event = listener.event;
428
		assertEquals(list, event.getObservableList());
447
		assertSame(list, event.getObservableList());
429
		assertEntry(event.diff.getDifferences()[0], false, 0, oldElement);
448
430
		assertEntry(event.diff.getDifferences()[1], true, 0, newElement);
449
		assertDiff(event.diff, Collections.singletonList(oldElement),
450
				Collections.singletonList(newElement));
431
	}
451
	}
432
452
433
	public void testSetPropertyChangeEvent() throws Exception {
453
	public void testSetPropertyChangeEvent() throws Exception {
Lines 473-483 Link Here
473
		assertEquals(Collections.singletonList("new"), list);
493
		assertEquals(Collections.singletonList("new"), list);
474
	}
494
	}
475
495
476
	private static void assertEntry(ListDiffEntry entry, boolean addition,
496
	private static void assertDiff(ListDiff diff, List oldList, List newList) {
477
			int position, Object element) {
497
		oldList = new ArrayList(oldList); // defensive copy in case arg is
478
		assertEquals("addition", addition, entry.isAddition());
498
		// unmodifiable
479
		assertEquals("position", position, entry.getPosition());
499
		diff.applyTo(oldList);
480
		assertEquals("element", element, entry.getElement());
500
		assertEquals("applying diff to list did not produce expected result",
501
				newList, oldList);
481
	}
502
	}
482
503
483
	private static void assertPropertyChangeEvent(Bean bean, Runnable runnable) {
504
	private static void assertPropertyChangeEvent(Bean bean, Runnable runnable) {
Lines 492-499 Link Here
492
		PropertyChangeEvent event = listener.evt;
513
		PropertyChangeEvent event = listener.evt;
493
		assertEquals("event did not fire", 1, listener.count);
514
		assertEquals("event did not fire", 1, listener.count);
494
		assertEquals("array", event.getPropertyName());
515
		assertEquals("array", event.getPropertyName());
495
		assertTrue("old value", Arrays.equals(old, (Object[]) event.getOldValue()));
516
		assertTrue("old value", Arrays.equals(old, (Object[]) event
496
		assertTrue("new value", Arrays.equals(bean.getArray(), (Object[]) event.getNewValue()));
517
				.getOldValue()));
518
		assertTrue("new value", Arrays.equals(bean.getArray(), (Object[]) event
519
				.getNewValue()));
497
		assertFalse("lists are equal", Arrays.equals(bean.getArray(), old));
520
		assertFalse("lists are equal", Arrays.equals(bean.getArray(), old));
498
	}
521
	}
499
522
Lines 503-513 Link Here
503
526
504
		PropertyChangeEvent evt;
527
		PropertyChangeEvent evt;
505
528
506
		/*
507
		 * (non-Javadoc)
508
		 * 
509
		 * @see java.beans.PropertyChangeListener#propertyChange(java.beans.PropertyChangeEvent)
510
		 */
511
		public void propertyChange(PropertyChangeEvent evt) {
529
		public void propertyChange(PropertyChangeEvent evt) {
512
			count++;
530
			count++;
513
			this.evt = evt;
531
			this.evt = evt;
Lines 515-521 Link Here
515
	}
533
	}
516
534
517
	public static Test suite() {
535
	public static Test suite() {
518
		TestSuite suite = new TestSuite(JavaBeanObservableArrayBasedListTest.class.getName());
536
		TestSuite suite = new TestSuite(
537
				JavaBeanObservableArrayBasedListTest.class.getName());
519
		suite.addTestSuite(JavaBeanObservableArrayBasedListTest.class);
538
		suite.addTestSuite(JavaBeanObservableArrayBasedListTest.class);
520
		suite.addTest(MutableObservableListContractTest.suite(new Delegate()));
539
		suite.addTest(MutableObservableListContractTest.suite(new Delegate()));
521
		return suite;
540
		return suite;
Lines 525-541 Link Here
525
		public IObservableCollection createObservableCollection(Realm realm,
544
		public IObservableCollection createObservableCollection(Realm realm,
526
				int elementCount) {
545
				int elementCount) {
527
			String propertyName = "array";
546
			String propertyName = "array";
528
			PropertyDescriptor propertyDescriptor;
529
			try {
530
				propertyDescriptor = new PropertyDescriptor(propertyName,
531
						Bean.class);
532
			} catch (IntrospectionException e) {
533
				throw new RuntimeException(e);
534
			}
535
			Object bean = new Bean(new Object[0]);
547
			Object bean = new Bean(new Object[0]);
536
548
537
			IObservableList list = new JavaBeanObservableList(realm, bean,
549
			IObservableList list = BeansObservables.observeList(realm, bean,
538
					propertyDescriptor, String.class);
550
					propertyName, String.class);
539
			for (int i = 0; i < elementCount; i++)
551
			for (int i = 0; i < elementCount; i++)
540
				list.add(createElement(list));
552
				list.add(createElement(list));
541
			return list;
553
			return list;
(-)src/org/eclipse/core/tests/internal/databinding/beans/BeanObservableListDecoratorTest.java (-14 / +8 lines)
Lines 7-13 Link Here
7
 *
7
 *
8
 * Contributors:
8
 * Contributors:
9
 *     Brad Reynolds - initial API and implementation
9
 *     Brad Reynolds - initial API and implementation
10
 *     Matthew Hall - bugs 208858, 213145, 246625
10
 *     Matthew Hall - bugs 208858, 213145, 246625, 194734
11
 ******************************************************************************/
11
 ******************************************************************************/
12
12
13
package org.eclipse.core.tests.internal.databinding.beans;
13
package org.eclipse.core.tests.internal.databinding.beans;
Lines 18-30 Link Here
18
import junit.framework.TestCase;
18
import junit.framework.TestCase;
19
import junit.framework.TestSuite;
19
import junit.framework.TestSuite;
20
20
21
import org.eclipse.core.databinding.beans.BeansObservables;
21
import org.eclipse.core.databinding.observable.IObservable;
22
import org.eclipse.core.databinding.observable.IObservable;
22
import org.eclipse.core.databinding.observable.IObservableCollection;
23
import org.eclipse.core.databinding.observable.IObservableCollection;
23
import org.eclipse.core.databinding.observable.Realm;
24
import org.eclipse.core.databinding.observable.Realm;
24
import org.eclipse.core.databinding.observable.list.IObservableList;
25
import org.eclipse.core.databinding.observable.list.IObservableList;
25
import org.eclipse.core.databinding.observable.list.WritableList;
26
import org.eclipse.core.databinding.observable.list.WritableList;
26
import org.eclipse.core.internal.databinding.beans.BeanObservableListDecorator;
27
import org.eclipse.core.internal.databinding.beans.BeanObservableListDecorator;
27
import org.eclipse.core.internal.databinding.beans.JavaBeanObservableList;
28
import org.eclipse.jface.databinding.conformance.MutableObservableListContractTest;
28
import org.eclipse.jface.databinding.conformance.MutableObservableListContractTest;
29
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableCollectionContractDelegate;
29
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableCollectionContractDelegate;
30
import org.eclipse.jface.databinding.swt.SWTObservables;
30
import org.eclipse.jface.databinding.swt.SWTObservables;
Lines 36-71 Link Here
36
public class BeanObservableListDecoratorTest extends TestCase {
36
public class BeanObservableListDecoratorTest extends TestCase {
37
	private Bean bean;
37
	private Bean bean;
38
	private PropertyDescriptor propertyDescriptor;
38
	private PropertyDescriptor propertyDescriptor;
39
	private JavaBeanObservableList observableList;
39
	private IObservableList observableList;
40
	private BeanObservableListDecorator decorator;
40
	private BeanObservableListDecorator decorator;
41
41
42
	/*
43
	 * (non-Javadoc)
44
	 * 
45
	 * @see junit.framework.TestCase#setUp()
46
	 */
47
	protected void setUp() throws Exception {
42
	protected void setUp() throws Exception {
48
		super.setUp();
43
		super.setUp();
49
		
44
		
50
		bean = new Bean();
45
		bean = new Bean();
51
		propertyDescriptor = new PropertyDescriptor(
46
		propertyDescriptor = new PropertyDescriptor(
52
				"list", Bean.class,"getList","setList");
47
				"list", Bean.class,"getList","setList");
53
		observableList = new JavaBeanObservableList(
48
		observableList = BeansObservables.observeList(
54
				SWTObservables.getRealm(Display.getDefault()), bean,
49
				SWTObservables.getRealm(Display.getDefault()), bean, "list");
55
				propertyDescriptor, Bean.class);
56
		decorator = new BeanObservableListDecorator(observableList, propertyDescriptor);
50
		decorator = new BeanObservableListDecorator(observableList, propertyDescriptor);
57
	}
51
	}
58
52
59
	public void testGetDelegate() throws Exception {
53
	public void testGetDelegate() throws Exception {
60
		assertEquals(observableList, decorator.getDecorated());
54
		assertSame(observableList, decorator.getDecorated());
61
	}
55
	}
62
56
63
	public void testGetObserved() throws Exception {
57
	public void testGetObserved() throws Exception {
64
		assertEquals(bean, decorator.getObserved());
58
		assertSame(bean, decorator.getObserved());
65
	}
59
	}
66
60
67
	public void testGetPropertyDescriptor() throws Exception {
61
	public void testGetPropertyDescriptor() throws Exception {
68
		assertEquals(propertyDescriptor, decorator.getPropertyDescriptor());
62
		assertSame(propertyDescriptor, decorator.getPropertyDescriptor());
69
	}
63
	}
70
64
71
	public static Test suite() {
65
	public static Test suite() {
(-)src/org/eclipse/core/tests/internal/databinding/beans/JavaBeanObservableListTest.java (-97 / +112 lines)
Lines 7-18 Link Here
7
 *
7
 *
8
 * Contributors:
8
 * Contributors:
9
 *     Brad Reynolds - initial API and implementation
9
 *     Brad Reynolds - initial API and implementation
10
 *     Matthew Hall - bugs 221351, 213145, 244098, 246103
10
 *     Matthew Hall - bugs 221351, 213145, 244098, 246103, 194734
11
 ******************************************************************************/
11
 ******************************************************************************/
12
12
13
package org.eclipse.core.tests.internal.databinding.beans;
13
package org.eclipse.core.tests.internal.databinding.beans;
14
14
15
import java.beans.IntrospectionException;
16
import java.beans.PropertyChangeEvent;
15
import java.beans.PropertyChangeEvent;
17
import java.beans.PropertyChangeListener;
16
import java.beans.PropertyChangeListener;
18
import java.beans.PropertyDescriptor;
17
import java.beans.PropertyDescriptor;
Lines 25-38 Link Here
25
import junit.framework.Test;
24
import junit.framework.Test;
26
import junit.framework.TestSuite;
25
import junit.framework.TestSuite;
27
26
27
import org.eclipse.core.databinding.beans.BeanProperties;
28
import org.eclipse.core.databinding.beans.BeansObservables;
28
import org.eclipse.core.databinding.beans.BeansObservables;
29
import org.eclipse.core.databinding.beans.IBeanObservable;
30
import org.eclipse.core.databinding.beans.IBeanProperty;
31
import org.eclipse.core.databinding.beans.PojoObservables;
29
import org.eclipse.core.databinding.observable.IObservable;
32
import org.eclipse.core.databinding.observable.IObservable;
30
import org.eclipse.core.databinding.observable.IObservableCollection;
33
import org.eclipse.core.databinding.observable.IObservableCollection;
31
import org.eclipse.core.databinding.observable.Realm;
34
import org.eclipse.core.databinding.observable.Realm;
32
import org.eclipse.core.databinding.observable.list.IObservableList;
35
import org.eclipse.core.databinding.observable.list.IObservableList;
33
import org.eclipse.core.databinding.observable.list.ListChangeEvent;
36
import org.eclipse.core.databinding.observable.list.ListChangeEvent;
34
import org.eclipse.core.databinding.observable.list.ListDiffEntry;
37
import org.eclipse.core.databinding.observable.list.ListDiff;
35
import org.eclipse.core.internal.databinding.beans.JavaBeanObservableList;
36
import org.eclipse.jface.databinding.conformance.MutableObservableListContractTest;
38
import org.eclipse.jface.databinding.conformance.MutableObservableListContractTest;
37
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableCollectionContractDelegate;
39
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableCollectionContractDelegate;
38
import org.eclipse.jface.databinding.conformance.util.ChangeEventTracker;
40
import org.eclipse.jface.databinding.conformance.util.ChangeEventTracker;
Lines 46-52 Link Here
46
 * @since 1.1
48
 * @since 1.1
47
 */
49
 */
48
public class JavaBeanObservableListTest extends AbstractDefaultRealmTestCase {
50
public class JavaBeanObservableListTest extends AbstractDefaultRealmTestCase {
49
	private JavaBeanObservableList list;
51
	private IObservableList list;
52
	private IBeanObservable beanObservable;
50
53
51
	private PropertyDescriptor propertyDescriptor;
54
	private PropertyDescriptor propertyDescriptor;
52
55
Lines 63-89 Link Here
63
		super.setUp();
66
		super.setUp();
64
67
65
		propertyName = "list";
68
		propertyName = "list";
66
		propertyDescriptor = new PropertyDescriptor(propertyName, Bean.class);
69
		propertyDescriptor = ((IBeanProperty) BeanProperties.list(
70
				Bean.class, propertyName)).getPropertyDescriptor();
67
		bean = new Bean(new ArrayList());
71
		bean = new Bean(new ArrayList());
68
72
69
		list = new JavaBeanObservableList(SWTObservables.getRealm(Display
73
		list = BeansObservables.observeList(SWTObservables.getRealm(Display
70
				.getDefault()), bean, propertyDescriptor, String.class);
74
				.getDefault()), bean, propertyName);
75
		beanObservable = (IBeanObservable) list;
71
	}
76
	}
72
77
73
	public void testGetObserved() throws Exception {
78
	public void testGetObserved() throws Exception {
74
		assertEquals(bean, list.getObserved());
79
		assertEquals(bean, beanObservable.getObserved());
75
	}
80
	}
76
81
77
	public void testGetPropertyDescriptor() throws Exception {
82
	public void testGetPropertyDescriptor() throws Exception {
78
		assertEquals(propertyDescriptor, list.getPropertyDescriptor());
83
		assertEquals(propertyDescriptor, beanObservable.getPropertyDescriptor());
79
	}
84
	}
80
85
81
	public void testRegistersListenerOnCreation() throws Exception {
86
	public void testRegistersListenerAfterFirstListenerIsAdded()
87
			throws Exception {
88
		assertFalse(bean.changeSupport.hasListeners(propertyName));
89
		list.addListChangeListener(new ListChangeEventTracker());
82
		assertTrue(bean.changeSupport.hasListeners(propertyName));
90
		assertTrue(bean.changeSupport.hasListeners(propertyName));
83
	}
91
	}
84
92
85
	public void testRemovesListenerOnDisposal() throws Exception {
93
	public void testRemovesListenerAfterLastListenerIsRemoved()
86
		list.dispose();
94
			throws Exception {
95
		ListChangeEventTracker listener = new ListChangeEventTracker();
96
		list.addListChangeListener(listener);
97
98
		assertTrue(bean.changeSupport.hasListeners(propertyName));
99
		list.removeListChangeListener(listener);
87
		assertFalse(bean.changeSupport.hasListeners(propertyName));
100
		assertFalse(bean.changeSupport.hasListeners(propertyName));
88
	}
101
	}
89
102
Lines 118-132 Link Here
118
		assertEquals(1, listener.count);
131
		assertEquals(1, listener.count);
119
		ListChangeEvent event = listener.event;
132
		ListChangeEvent event = listener.event;
120
133
121
		assertEquals(list, event.getObservableList());
134
		assertSame(list, event.getObservableList());
122
		assertEntry(event.diff.getDifferences()[0], true, 0, element);
135
		assertDiff(event.diff, Collections.EMPTY_LIST, Collections
136
				.singletonList("1"));
123
	}
137
	}
124
138
125
	public void testAddFiresPropertyChangeEvent() throws Exception {
139
	public void testAddFiresPropertyChangeEvent() throws Exception {
126
		assertPropertyChangeEvent(bean, new Runnable() {
140
		assertPropertyChangeEvent(bean, new Runnable() {
127
			public void run() {
141
			public void run() {
128
				list.add("0");
142
				list.add("0");
129
			}			
143
			}
130
		});
144
		});
131
	}
145
	}
132
146
Lines 148-161 Link Here
148
		list.add(0, element);
162
		list.add(0, element);
149
163
150
		ListChangeEvent event = listener.event;
164
		ListChangeEvent event = listener.event;
151
		assertEntry(event.diff.getDifferences()[0], true, 0, element);
165
		assertDiff(event.diff, Collections.EMPTY_LIST, Collections
166
				.singletonList("1"));
152
	}
167
	}
153
	
168
154
	public void testAddAtIndexPropertyChangeEvent() throws Exception {
169
	public void testAddAtIndexPropertyChangeEvent() throws Exception {
155
		assertPropertyChangeEvent(bean, new Runnable() {
170
		assertPropertyChangeEvent(bean, new Runnable() {
156
			public void run() {
171
			public void run() {
157
				list.add(0, "0");
172
				list.add(0, "0");
158
			}			
173
			}
159
		});
174
		});
160
	}
175
	}
161
176
Lines 164-170 Link Here
164
		list.add(element);
179
		list.add(element);
165
180
166
		assertEquals(1, bean.getList().size());
181
		assertEquals(1, bean.getList().size());
167
		assertPropertyChangeEvent(bean, new Runnable(){
182
		assertPropertyChangeEvent(bean, new Runnable() {
168
			public void run() {
183
			public void run() {
169
				list.clear();
184
				list.clear();
170
			}
185
			}
Lines 175-186 Link Here
175
	public void testRemove() throws Exception {
190
	public void testRemove() throws Exception {
176
		String element = "1";
191
		String element = "1";
177
		list.add(element);
192
		list.add(element);
178
		
193
179
		assertEquals(1, bean.getList().size());
194
		assertEquals(1, bean.getList().size());
180
		list.remove(element);
195
		list.remove(element);
181
		assertEquals(0, bean.getList().size());
196
		assertEquals(0, bean.getList().size());
182
	}
197
	}
183
	
198
184
	public void testRemoveListChangeEvent() throws Exception {
199
	public void testRemoveListChangeEvent() throws Exception {
185
		String element = "1";
200
		String element = "1";
186
		list.add(element);
201
		list.add(element);
Lines 193-209 Link Here
193
208
194
		assertEquals(1, listener.count);
209
		assertEquals(1, listener.count);
195
		ListChangeEvent event = listener.event;
210
		ListChangeEvent event = listener.event;
196
		assertEquals(list, event.getObservableList());
211
		assertSame(list, event.getObservableList());
197
		assertEntry(event.diff.getDifferences()[0], false, 0, element);
212
213
		assertDiff(event.diff, Collections.singletonList("1"),
214
				Collections.EMPTY_LIST);
198
	}
215
	}
199
	
216
200
	public void testRemovePropertyChangeEvent() throws Exception {
217
	public void testRemovePropertyChangeEvent() throws Exception {
201
		list.add("0");
218
		list.add("0");
202
		
219
203
		assertPropertyChangeEvent(bean, new Runnable() {
220
		assertPropertyChangeEvent(bean, new Runnable() {
204
			public void run() {
221
			public void run() {
205
				list.remove("0");
222
				list.remove("0");
206
			}			
223
			}
207
		});
224
		});
208
	}
225
	}
209
226
Lines 229-244 Link Here
229
246
230
		assertEquals(1, listener.count);
247
		assertEquals(1, listener.count);
231
		ListChangeEvent event = listener.event;
248
		ListChangeEvent event = listener.event;
232
		assertEquals(list, event.getObservableList());
249
		assertSame(list, event.getObservableList());
233
		assertEntry(event.diff.getDifferences()[0], false, 0, element);
250
251
		assertDiff(event.diff, Collections.singletonList(element),
252
				Collections.EMPTY_LIST);
234
	}
253
	}
235
	
254
236
	public void testRemoveAtIndexPropertyChangeEvent() throws Exception {
255
	public void testRemoveAtIndexPropertyChangeEvent() throws Exception {
237
		list.add("0");
256
		list.add("0");
238
		assertPropertyChangeEvent(bean, new Runnable() {
257
		assertPropertyChangeEvent(bean, new Runnable() {
239
			public void run() {
258
			public void run() {
240
				list.remove(0);
259
				list.remove(0);
241
			}			
260
			}
242
		});
261
		});
243
	}
262
	}
244
263
Lines 263-279 Link Here
263
282
264
		assertEquals(1, listener.count);
283
		assertEquals(1, listener.count);
265
		ListChangeEvent event = listener.event;
284
		ListChangeEvent event = listener.event;
266
		assertEquals(list, event.getObservableList());
285
		assertSame(list, event.getObservableList());
267
286
268
		assertEntry(event.diff.getDifferences()[0], true, 0, elements.get(0));
287
		assertDiff(event.diff, Collections.EMPTY_LIST, Arrays
269
		assertEntry(event.diff.getDifferences()[1], true, 1, elements.get(1));
288
				.asList(new String[] { "1", "2" }));
270
	}
289
	}
271
	
290
272
	public void testAddAllPropertyChangeEvent() throws Exception {
291
	public void testAddAllPropertyChangeEvent() throws Exception {
273
		assertPropertyChangeEvent(bean, new Runnable() {
292
		assertPropertyChangeEvent(bean, new Runnable() {
274
			public void run() {
293
			public void run() {
275
				list.addAll(Arrays.asList(new String[] {"0", "1"}));
294
				list.addAll(Arrays.asList(new String[] { "0", "1" }));
276
			}			
295
			}
277
		});
296
		});
278
	}
297
	}
279
298
Lines 303-332 Link Here
303
322
304
		assertEquals(1, listener.count);
323
		assertEquals(1, listener.count);
305
		ListChangeEvent event = listener.event;
324
		ListChangeEvent event = listener.event;
306
		assertEquals(list, event.getObservableList());
325
		assertSame(list, event.getObservableList());
307
		assertEntry(event.diff.getDifferences()[0], true, 2, elements.get(0));
326
308
		assertEntry(event.diff.getDifferences()[1], true, 3, elements.get(1));
327
		assertDiff(event.diff, Arrays.asList(new Object[] { "1", "2" }), Arrays
328
				.asList(new Object[] { "1", "2", "1", "2" }));
309
	}
329
	}
310
	
330
311
	public void testAddAllAtIndexPropertyChangeEvent() throws Exception {
331
	public void testAddAllAtIndexPropertyChangeEvent() throws Exception {
312
		assertPropertyChangeEvent(bean, new Runnable() {
332
		assertPropertyChangeEvent(bean, new Runnable() {
313
			public void run() {
333
			public void run() {
314
				list.addAll(0, Arrays.asList(new String[] {"1", "2"}));
334
				list.addAll(0, Arrays.asList(new String[] { "1", "2" }));
315
			}			
335
			}
316
		});
336
		});
317
	}
337
	}
318
338
319
	public void testRemoveAll() throws Exception {
339
	public void testRemoveAll() throws Exception {
320
		List elements = Arrays.asList(new String[] { "1", "2" });
340
		list.addAll(Arrays.asList(new String[] { "1", "2", "3", "4" }));
321
		list.addAll(elements);
322
		list.addAll(elements);
323
324
		assertEquals(4, bean.getList().size());
341
		assertEquals(4, bean.getList().size());
325
		list.removeAll(elements);
342
343
		list.removeAll(Arrays.asList(new String[] { "2", "4" }));
326
344
327
		assertEquals(2, bean.getList().size());
345
		assertEquals(2, bean.getList().size());
328
		assertEquals(elements.get(0), bean.getList().get(0));
346
		assertEquals("1", bean.getList().get(0));
329
		assertEquals(elements.get(1), bean.getList().get(1));
347
		assertEquals("3", bean.getList().get(1));
330
	}
348
	}
331
349
332
	public void testRemoveAllListChangeEvent() throws Exception {
350
	public void testRemoveAllListChangeEvent() throws Exception {
Lines 342-357 Link Here
342
360
343
		ListChangeEvent event = listener.event;
361
		ListChangeEvent event = listener.event;
344
		assertEquals(list, event.getObservableList());
362
		assertEquals(list, event.getObservableList());
345
		assertEntry(event.diff.getDifferences()[0], false, 0, elements.get(0));
363
		assertSame(list, event.getObservableList());
346
		assertEntry(event.diff.getDifferences()[1], false, 0, elements.get(1));
364
365
		assertDiff(event.diff, Arrays
366
				.asList(new Object[] { "1", "2", "1", "2" }),
367
				Collections.EMPTY_LIST);
347
	}
368
	}
348
	
369
349
	public void testRemoveAllPropertyChangeEvent() throws Exception {
370
	public void testRemoveAllPropertyChangeEvent() throws Exception {
350
		list.add("0");
371
		list.add("0");
351
		assertPropertyChangeEvent(bean, new Runnable() {
372
		assertPropertyChangeEvent(bean, new Runnable() {
352
			public void run() {
373
			public void run() {
353
				list.removeAll(Arrays.asList(new String[] {"0"}));
374
				list.removeAll(Arrays.asList(new String[] { "0" }));
354
			}			
375
			}
355
		});
376
		});
356
	}
377
	}
357
378
Lines 380-397 Link Here
380
401
381
		assertEquals(1, listener.count);
402
		assertEquals(1, listener.count);
382
		ListChangeEvent event = listener.event;
403
		ListChangeEvent event = listener.event;
383
		assertEquals(list, event.getObservableList());
404
		assertSame(list, event.getObservableList());
384
		assertEntry(event.diff.getDifferences()[0], false, 2, elements.get(2));
405
385
		assertEntry(event.diff.getDifferences()[1], false, 2, elements.get(3));
406
		assertDiff(event.diff, Arrays
407
				.asList(new Object[] { "0", "1", "2", "3" }), Arrays
408
				.asList(new Object[] { "0", "1" }));
386
	}
409
	}
387
	
410
388
	public void testRetainAllPropertyChangeEvent() throws Exception {
411
	public void testRetainAllPropertyChangeEvent() throws Exception {
389
		list.addAll(Arrays.asList(new String[] {"0", "1"}));
412
		list.addAll(Arrays.asList(new String[] { "0", "1" }));
390
		
413
391
		assertPropertyChangeEvent(bean, new Runnable() {
414
		assertPropertyChangeEvent(bean, new Runnable() {
392
			public void run() {
415
			public void run() {
393
				list.retainAll(Arrays.asList(new String[] {"0"}));
416
				list.retainAll(Arrays.asList(new String[] { "0" }));
394
			}			
417
			}
395
		});
418
		});
396
	}
419
	}
397
420
Lines 435-443 Link Here
435
458
436
		assertEquals(1, listener.count);
459
		assertEquals(1, listener.count);
437
		ListChangeEvent event = listener.event;
460
		ListChangeEvent event = listener.event;
438
		assertEquals(list, event.getObservableList());
461
		assertSame(list, event.getObservableList());
439
		assertEntry(event.diff.getDifferences()[0], false, 0, oldElement);
462
440
		assertEntry(event.diff.getDifferences()[1], true, 0, newElement);
463
		assertDiff(event.diff, Collections.singletonList(oldElement),
464
				Collections.singletonList(newElement));
441
	}
465
	}
442
466
443
	public void testSetPropertyChangeEvent() throws Exception {
467
	public void testSetPropertyChangeEvent() throws Exception {
Lines 445-451 Link Here
445
		assertPropertyChangeEvent(bean, new Runnable() {
469
		assertPropertyChangeEvent(bean, new Runnable() {
446
			public void run() {
470
			public void run() {
447
				list.set(0, "1");
471
				list.set(0, "1");
448
			}			
472
			}
449
		});
473
		});
450
	}
474
	}
451
475
Lines 462-478 Link Here
462
486
463
	public void testConstructor_RegistersListener() throws Exception {
487
	public void testConstructor_RegistersListener() throws Exception {
464
		Bean bean = new Bean();
488
		Bean bean = new Bean();
465
		new JavaBeanObservableList(Realm.getDefault(), bean,
489
		IObservableList observable = BeansObservables.observeList(Realm
466
				new PropertyDescriptor("list", Bean.class), Bean.class);
490
				.getDefault(), bean, "list");
467
491
492
		assertFalse(bean.hasListeners("list"));
493
		ChangeEventTracker.observe(observable);
468
		assertTrue(bean.hasListeners("list"));
494
		assertTrue(bean.hasListeners("list"));
469
	}
495
	}
470
496
471
	public void testConstructor_SkipsRegisterListener() throws Exception {
497
	public void testConstructor_SkipsRegisterListener() throws Exception {
472
		Bean bean = new Bean();
498
		Bean bean = new Bean();
473
		JavaBeanObservableList observable = new JavaBeanObservableList(Realm
499
		IObservableList observable = PojoObservables.observeList(Realm
474
				.getDefault(), bean,
500
				.getDefault(), bean, "list");
475
				new PropertyDescriptor("list", Bean.class), Bean.class, false);
476
501
477
		assertFalse(bean.hasListeners("list"));
502
		assertFalse(bean.hasListeners("list"));
478
		ChangeEventTracker.observe(observable);
503
		ChangeEventTracker.observe(observable);
Lines 496-524 Link Here
496
		bean.setList(Collections.singletonList("new"));
521
		bean.setList(Collections.singletonList("new"));
497
522
498
		assertEquals(1, tracker.count);
523
		assertEquals(1, tracker.count);
499
		
524
500
		List list = new ArrayList();
525
		List list = new ArrayList();
501
		list.add("old");
526
		list.add("old");
502
		tracker.event.diff.applyTo(list);
527
		tracker.event.diff.applyTo(list);
503
		assertEquals(Collections.singletonList("new"), list);
528
		assertEquals(Collections.singletonList("new"), list);
504
	}
529
	}
505
530
506
	private static void assertEntry(ListDiffEntry entry, boolean addition,
531
	private static void assertDiff(ListDiff diff, List oldList, List newList) {
507
			int position, Object element) {
532
		oldList = new ArrayList(oldList); // defensive copy in case arg is
508
		assertEquals("addition", addition, entry.isAddition());
533
		// unmodifiable
509
		assertEquals("position", position, entry.getPosition());
534
		diff.applyTo(oldList);
510
		assertEquals("element", element, entry.getElement());
535
		assertEquals("applying diff to list did not produce expected result",
536
				newList, oldList);
511
	}
537
	}
512
538
513
	private static void assertPropertyChangeEvent(Bean bean, Runnable runnable) {
539
	private static void assertPropertyChangeEvent(Bean bean, Runnable runnable) {
514
		PropertyChangeTracker listener = new PropertyChangeTracker();
540
		PropertyChangeTracker listener = new PropertyChangeTracker();
515
		bean.addPropertyChangeListener(listener);
541
		bean.addPropertyChangeListener(listener);
516
		
542
517
		List old = bean.getList();
543
		List old = bean.getList();
518
		assertEquals(0, listener.count);
544
		assertEquals(0, listener.count);
519
		
545
520
		runnable.run();
546
		runnable.run();
521
		
547
522
		PropertyChangeEvent event = listener.evt;
548
		PropertyChangeEvent event = listener.evt;
523
		assertEquals("event did not fire", 1, listener.count);
549
		assertEquals("event did not fire", 1, listener.count);
524
		assertEquals("list", event.getPropertyName());
550
		assertEquals("list", event.getPropertyName());
Lines 526-543 Link Here
526
		assertEquals("new value", bean.getList(), event.getNewValue());
552
		assertEquals("new value", bean.getList(), event.getNewValue());
527
		assertFalse("lists are equal", bean.getList().equals(old));
553
		assertFalse("lists are equal", bean.getList().equals(old));
528
	}
554
	}
529
	
555
530
	private static class PropertyChangeTracker implements
556
	private static class PropertyChangeTracker implements
531
			PropertyChangeListener {
557
			PropertyChangeListener {
532
		int count;
558
		int count;
533
559
534
		PropertyChangeEvent evt;
560
		PropertyChangeEvent evt;
535
561
536
		/*
537
		 * (non-Javadoc)
538
		 * 
539
		 * @see java.beans.PropertyChangeListener#propertyChange(java.beans.PropertyChangeEvent)
540
		 */
541
		public void propertyChange(PropertyChangeEvent evt) {
562
		public void propertyChange(PropertyChangeEvent evt) {
542
			count++;
563
			count++;
543
			this.evt = evt;
564
			this.evt = evt;
Lines 545-551 Link Here
545
	}
566
	}
546
567
547
	public static Test suite() {
568
	public static Test suite() {
548
		TestSuite suite = new TestSuite(JavaBeanObservableListTest.class.getName());
569
		TestSuite suite = new TestSuite(JavaBeanObservableListTest.class
570
				.getName());
549
		suite.addTestSuite(JavaBeanObservableListTest.class);
571
		suite.addTestSuite(JavaBeanObservableListTest.class);
550
		suite.addTest(MutableObservableListContractTest.suite(new Delegate()));
572
		suite.addTest(MutableObservableListContractTest.suite(new Delegate()));
551
		return suite;
573
		return suite;
Lines 555-571 Link Here
555
		public IObservableCollection createObservableCollection(Realm realm,
577
		public IObservableCollection createObservableCollection(Realm realm,
556
				int elementCount) {
578
				int elementCount) {
557
			String propertyName = "list";
579
			String propertyName = "list";
558
			PropertyDescriptor propertyDescriptor;
559
			try {
560
				propertyDescriptor = new PropertyDescriptor(propertyName,
561
						Bean.class);
562
			} catch (IntrospectionException e) {
563
				throw new RuntimeException(e);
564
			}
565
			Object bean = new Bean(new ArrayList());
580
			Object bean = new Bean(new ArrayList());
566
581
567
			IObservableList list = new JavaBeanObservableList(realm, bean,
582
			IObservableList list = BeansObservables.observeList(realm, bean,
568
					propertyDescriptor, String.class);
583
					propertyName, String.class);
569
			for (int i = 0; i < elementCount; i++)
584
			for (int i = 0; i < elementCount; i++)
570
				list.add(createElement(list));
585
				list.add(createElement(list));
571
			return list;
586
			return list;
(-)src/org/eclipse/core/tests/internal/databinding/beans/BeanObservableValueDecoratorTest.java (-18 / +11 lines)
Lines 7-21 Link Here
7
 *
7
 *
8
 * Contributors:
8
 * Contributors:
9
 *     Brad Reynolds - initial API and implementation
9
 *     Brad Reynolds - initial API and implementation
10
 *     Matthew Hall - bug 246625
10
 *     Matthew Hall - bug 246625, 194734
11
 ******************************************************************************/
11
 ******************************************************************************/
12
12
13
package org.eclipse.core.tests.internal.databinding.beans;
13
package org.eclipse.core.tests.internal.databinding.beans;
14
14
15
import java.beans.PropertyDescriptor;
15
import java.beans.PropertyDescriptor;
16
16
17
import org.eclipse.core.databinding.beans.BeansObservables;
18
import org.eclipse.core.databinding.observable.value.IObservableValue;
17
import org.eclipse.core.internal.databinding.beans.BeanObservableValueDecorator;
19
import org.eclipse.core.internal.databinding.beans.BeanObservableValueDecorator;
18
import org.eclipse.core.internal.databinding.beans.JavaBeanObservableValue;
19
import org.eclipse.jface.databinding.swt.SWTObservables;
20
import org.eclipse.jface.databinding.swt.SWTObservables;
20
import org.eclipse.jface.tests.databinding.AbstractDefaultRealmTestCase;
21
import org.eclipse.jface.tests.databinding.AbstractDefaultRealmTestCase;
21
import org.eclipse.swt.widgets.Display;
22
import org.eclipse.swt.widgets.Display;
Lines 25-62 Link Here
25
 */
26
 */
26
public class BeanObservableValueDecoratorTest extends AbstractDefaultRealmTestCase {
27
public class BeanObservableValueDecoratorTest extends AbstractDefaultRealmTestCase {
27
	private Bean bean;
28
	private Bean bean;
28
	private JavaBeanObservableValue observableValue;
29
	private IObservableValue observableValue;
29
	private BeanObservableValueDecorator decorator;
30
	private BeanObservableValueDecorator decorator;
30
	private PropertyDescriptor propertyDescriptor;
31
	private PropertyDescriptor propertyDescriptor;
31
	
32
	
32
	/*
33
	 * (non-Javadoc)
34
	 * 
35
	 * @see junit.framework.TestCase#setUp()
36
	 */
37
	protected void setUp() throws Exception {
33
	protected void setUp() throws Exception {
38
		super.setUp();
34
		super.setUp();
39
		
35
		
40
		bean = new Bean();
36
		bean = new Bean();
41
		propertyDescriptor = new PropertyDescriptor("value",
37
		propertyDescriptor = new PropertyDescriptor("value", Bean.class);
42
				Bean.class);
38
		observableValue = BeansObservables.observeValue(SWTObservables
43
		observableValue = new JavaBeanObservableValue(
39
				.getRealm(Display.getDefault()), bean, "value");
44
				SWTObservables.getRealm(Display.getDefault()), bean,
40
		decorator = new BeanObservableValueDecorator(observableValue,
45
				propertyDescriptor);
41
				propertyDescriptor);
46
		decorator = new BeanObservableValueDecorator(
47
				observableValue, observableValue
48
						.getPropertyDescriptor());
49
	}
42
	}
50
43
51
	public void testGetDelegate() throws Exception {
44
	public void testGetDelegate() throws Exception {
52
		assertEquals(observableValue, decorator.getDecorated());
45
		assertSame(observableValue, decorator.getDecorated());
53
	}
46
	}
54
	
47
	
55
	public void testGetObserved() throws Exception {
48
	public void testGetObserved() throws Exception {
56
		assertEquals(bean, decorator.getObserved());
49
		assertSame(bean, decorator.getObserved());
57
	}
50
	}
58
51
59
	public void testGetPropertyDescriptor() throws Exception {
52
	public void testGetPropertyDescriptor() throws Exception {
60
		assertEquals(propertyDescriptor, decorator.getPropertyDescriptor());
53
		assertSame(propertyDescriptor, decorator.getPropertyDescriptor());
61
	}
54
	}
62
}
55
}
(-)src/org/eclipse/core/tests/internal/databinding/beans/JavaBeanObservableMapTest.java (-9 / +20 lines)
Lines 7-13 Link Here
7
 *
7
 *
8
 * Contributors:
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
9
 *     IBM Corporation - initial API and implementation
10
 *     Matthew Hall - bugs 213145, 241585, 246103
10
 *     Matthew Hall - bugs 213145, 241585, 246103, 194734
11
 *******************************************************************************/
11
 *******************************************************************************/
12
12
13
package org.eclipse.core.tests.internal.databinding.beans;
13
package org.eclipse.core.tests.internal.databinding.beans;
Lines 20-33 Link Here
20
import junit.framework.TestCase;
20
import junit.framework.TestCase;
21
import junit.framework.TestSuite;
21
import junit.framework.TestSuite;
22
22
23
import org.eclipse.core.databinding.beans.BeanProperties;
23
import org.eclipse.core.databinding.beans.BeansObservables;
24
import org.eclipse.core.databinding.beans.BeansObservables;
25
import org.eclipse.core.databinding.beans.IBeanObservable;
26
import org.eclipse.core.databinding.beans.IBeanProperty;
27
import org.eclipse.core.databinding.beans.PojoObservables;
24
import org.eclipse.core.databinding.observable.Realm;
28
import org.eclipse.core.databinding.observable.Realm;
25
import org.eclipse.core.databinding.observable.map.IMapChangeListener;
29
import org.eclipse.core.databinding.observable.map.IMapChangeListener;
26
import org.eclipse.core.databinding.observable.map.IObservableMap;
30
import org.eclipse.core.databinding.observable.map.IObservableMap;
27
import org.eclipse.core.databinding.observable.map.MapChangeEvent;
31
import org.eclipse.core.databinding.observable.map.MapChangeEvent;
28
import org.eclipse.core.databinding.observable.map.MapDiff;
32
import org.eclipse.core.databinding.observable.map.MapDiff;
29
import org.eclipse.core.databinding.observable.set.WritableSet;
33
import org.eclipse.core.databinding.observable.set.WritableSet;
30
import org.eclipse.core.internal.databinding.beans.JavaBeanObservableMap;
31
import org.eclipse.core.tests.databinding.observable.ThreadRealm;
34
import org.eclipse.core.tests.databinding.observable.ThreadRealm;
32
import org.eclipse.jface.databinding.conformance.util.ChangeEventTracker;
35
import org.eclipse.jface.databinding.conformance.util.ChangeEventTracker;
33
import org.eclipse.jface.databinding.conformance.util.CurrentRealm;
36
import org.eclipse.jface.databinding.conformance.util.CurrentRealm;
Lines 46-52 Link Here
46
49
47
	private PropertyDescriptor propertyDescriptor;
50
	private PropertyDescriptor propertyDescriptor;
48
51
49
	private JavaBeanObservableMap map;
52
	private IObservableMap map;
53
	private IBeanObservable beanObservable;
50
54
51
	protected void setUp() throws Exception {
55
	protected void setUp() throws Exception {
52
		ThreadRealm realm = new ThreadRealm();
56
		ThreadRealm realm = new ThreadRealm();
Lines 58-65 Link Here
58
		set.add(model1);
62
		set.add(model1);
59
		set.add(model2);
63
		set.add(model2);
60
64
61
		propertyDescriptor = new PropertyDescriptor("value", Bean.class);
65
		String propertyName = "value";
62
		map = new JavaBeanObservableMap(set, propertyDescriptor);
66
		propertyDescriptor = ((IBeanProperty) BeanProperties.value(
67
				Bean.class, propertyName)).getPropertyDescriptor();
68
		map = BeansObservables.observeMap(set, Bean.class, propertyName);
69
		beanObservable = (IBeanObservable) map;
63
	}
70
	}
64
71
65
	public void testGetValue() throws Exception {
72
	public void testGetValue() throws Exception {
Lines 139-149 Link Here
139
	}
146
	}
140
	
147
	
141
	public void testGetObserved() throws Exception {
148
	public void testGetObserved() throws Exception {
142
		assertEquals(set, map.getObserved());
149
		assertEquals(set, beanObservable.getObserved());
143
	}
150
	}
144
	
151
	
145
	public void testGetPropertyDescriptor() throws Exception {
152
	public void testGetPropertyDescriptor() throws Exception {
146
		assertEquals(propertyDescriptor, map.getPropertyDescriptor());
153
		assertEquals(propertyDescriptor, beanObservable.getPropertyDescriptor());
147
	}
154
	}
148
	
155
	
149
	public void testConstructor_SkipRegisterListeners() throws Exception {
156
	public void testConstructor_SkipRegisterListeners() throws Exception {
Lines 152-158 Link Here
152
		Bean bean = new Bean();
159
		Bean bean = new Bean();
153
		set.add(bean);
160
		set.add(bean);
154
		
161
		
155
		JavaBeanObservableMap observable = new JavaBeanObservableMap(set, new PropertyDescriptor("value", Bean.class), false);
162
		IObservableMap observable = PojoObservables.observeMap(set, Bean.class,
163
				"value");
164
		assertFalse(bean.hasListeners("value"));
156
		ChangeEventTracker.observe(observable);
165
		ChangeEventTracker.observe(observable);
157
166
158
		assertFalse(bean.hasListeners("value"));
167
		assertFalse(bean.hasListeners("value"));
Lines 164-170 Link Here
164
		Bean bean = new Bean();
173
		Bean bean = new Bean();
165
		set.add(bean);
174
		set.add(bean);
166
		
175
		
167
		JavaBeanObservableMap observable = new JavaBeanObservableMap(set, new PropertyDescriptor("value", Bean.class));
176
		IObservableMap observable = BeansObservables.observeMap(set,
177
				Bean.class, "value");
178
		assertFalse(bean.hasListeners("value"));
168
		ChangeEventTracker.observe(observable);
179
		ChangeEventTracker.observe(observable);
169
180
170
		assertTrue(bean.hasListeners("value"));
181
		assertTrue(bean.hasListeners("value"));
(-)src/org/eclipse/core/tests/internal/databinding/beans/JavaBeanObservableValueTest.java (-26 / +22 lines)
Lines 9-33 Link Here
9
 *     Brad Reynolds - initial API and implementation
9
 *     Brad Reynolds - initial API and implementation
10
 *     Brad Reynolds - bug 171616
10
 *     Brad Reynolds - bug 171616
11
 *     Katarzyna Marszalek - test case for bug 198519
11
 *     Katarzyna Marszalek - test case for bug 198519
12
 *     Matthew Hall - bug 213145, 246103
12
 *     Matthew Hall - bug 213145, 246103, 194734
13
 ******************************************************************************/
13
 ******************************************************************************/
14
14
15
package org.eclipse.core.tests.internal.databinding.beans;
15
package org.eclipse.core.tests.internal.databinding.beans;
16
16
17
import java.beans.IntrospectionException;
18
import java.beans.PropertyDescriptor;
17
import java.beans.PropertyDescriptor;
19
18
20
import junit.framework.Test;
19
import junit.framework.Test;
21
import junit.framework.TestSuite;
20
import junit.framework.TestSuite;
22
21
22
import org.eclipse.core.databinding.beans.BeanProperties;
23
import org.eclipse.core.databinding.beans.BeansObservables;
23
import org.eclipse.core.databinding.beans.BeansObservables;
24
import org.eclipse.core.databinding.beans.IBeanObservable;
25
import org.eclipse.core.databinding.beans.IBeanProperty;
26
import org.eclipse.core.databinding.beans.PojoObservables;
24
import org.eclipse.core.databinding.observable.ChangeEvent;
27
import org.eclipse.core.databinding.observable.ChangeEvent;
25
import org.eclipse.core.databinding.observable.IChangeListener;
28
import org.eclipse.core.databinding.observable.IChangeListener;
26
import org.eclipse.core.databinding.observable.IObservable;
29
import org.eclipse.core.databinding.observable.IObservable;
27
import org.eclipse.core.databinding.observable.Realm;
30
import org.eclipse.core.databinding.observable.Realm;
28
import org.eclipse.core.databinding.observable.value.ComputedValue;
31
import org.eclipse.core.databinding.observable.value.ComputedValue;
29
import org.eclipse.core.databinding.observable.value.IObservableValue;
32
import org.eclipse.core.databinding.observable.value.IObservableValue;
30
import org.eclipse.core.internal.databinding.beans.JavaBeanObservableValue;
31
import org.eclipse.jface.databinding.conformance.MutableObservableValueContractTest;
33
import org.eclipse.jface.databinding.conformance.MutableObservableValueContractTest;
32
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
34
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
33
import org.eclipse.jface.databinding.conformance.util.ChangeEventTracker;
35
import org.eclipse.jface.databinding.conformance.util.ChangeEventTracker;
Lines 40-74 Link Here
40
 */
42
 */
41
public class JavaBeanObservableValueTest extends AbstractDefaultRealmTestCase {
43
public class JavaBeanObservableValueTest extends AbstractDefaultRealmTestCase {
42
	private Bean bean;
44
	private Bean bean;
43
	private JavaBeanObservableValue observableValue;
45
	private IObservableValue observableValue;
46
	private IBeanObservable beanObservable;
44
	private PropertyDescriptor propertyDescriptor;
47
	private PropertyDescriptor propertyDescriptor;
45
	private String propertyName;
48
	private String propertyName;
46
49
47
	/* (non-Javadoc)
48
	 * @see junit.framework.TestCase#setUp()
49
	 */
50
	protected void setUp() throws Exception {
50
	protected void setUp() throws Exception {
51
		super.setUp();
51
		super.setUp();
52
		
52
		
53
		bean = new Bean();
53
		bean = new Bean();
54
		propertyName = "value";
54
		propertyName = "value";
55
		propertyDescriptor = new PropertyDescriptor(propertyName, Bean.class);
55
		propertyDescriptor = ((IBeanProperty) BeanProperties.value(
56
		observableValue = new JavaBeanObservableValue(Realm.getDefault(), bean, propertyDescriptor);
56
				Bean.class, propertyName)).getPropertyDescriptor();
57
		observableValue = BeansObservables.observeValue(bean, propertyName);
58
		beanObservable = (IBeanObservable) observableValue;
57
	}
59
	}
58
60
59
	public void testGetObserved() throws Exception {
61
	public void testGetObserved() throws Exception {
60
		assertEquals(bean, observableValue.getObserved());
62
		assertEquals(bean, beanObservable.getObserved());
61
	}
63
	}
62
64
63
	public void testGetPropertyDescriptor() throws Exception {
65
	public void testGetPropertyDescriptor() throws Exception {
64
    	assertEquals(propertyDescriptor, observableValue.getPropertyDescriptor());
66
    	assertEquals(propertyDescriptor, beanObservable.getPropertyDescriptor());
65
	}
67
	}
66
68
67
	public void testSetValueThrowsExceptionThrownByBean() throws Exception {
69
	public void testSetValueThrowsExceptionThrownByBean() throws Exception {
68
		ThrowsSetException temp = new ThrowsSetException();
70
		ThrowsSetException temp = new ThrowsSetException();
69
		JavaBeanObservableValue observable = new JavaBeanObservableValue(Realm
71
		IObservableValue observable = BeansObservables.observeValue(temp,
70
				.getDefault(), temp,
72
				"value");
71
				new PropertyDescriptor("value", ThrowsSetException.class));
72
73
73
		try {
74
		try {
74
			observable.setValue("");
75
			observable.setValue("");
Lines 80-88 Link Here
80
	
81
	
81
	public void testGetValueThrowsExceptionThrownByBean() throws Exception {
82
	public void testGetValueThrowsExceptionThrownByBean() throws Exception {
82
		ThrowsGetException temp = new ThrowsGetException();
83
		ThrowsGetException temp = new ThrowsGetException();
83
		JavaBeanObservableValue observable = new JavaBeanObservableValue(Realm
84
		IObservableValue observable = BeansObservables.observeValue(temp,
84
				.getDefault(), temp,
85
				"value");
85
				new PropertyDescriptor("value", ThrowsGetException.class));
86
86
87
		try {
87
		try {
88
			observable.getValue();
88
			observable.getValue();
Lines 109-122 Link Here
109
	}
109
	}
110
110
111
	public void testConstructor_RegistersListeners() throws Exception {
111
	public void testConstructor_RegistersListeners() throws Exception {
112
		JavaBeanObservableValue observable = new JavaBeanObservableValue(Realm.getDefault(), bean, propertyDescriptor);
112
		IObservableValue observable = BeansObservables.observeValue(bean,
113
				propertyName);
113
		ChangeEventTracker.observe(observable);
114
		ChangeEventTracker.observe(observable);
114
		
115
		
115
		assertTrue(bean.hasListeners(propertyName));
116
		assertTrue(bean.hasListeners(propertyName));
116
	}
117
	}
117
	
118
	
118
	public void testConstructor_SkipRegisterListeners() throws Exception {
119
	public void testConstructor_SkipRegisterListeners() throws Exception {
119
		JavaBeanObservableValue observable = new JavaBeanObservableValue(Realm.getDefault(), bean, propertyDescriptor, false);
120
		IObservableValue observable = PojoObservables.observeValue(bean,
121
				propertyName);
120
		ChangeEventTracker.observe(observable);
122
		ChangeEventTracker.observe(observable);
121
		
123
		
122
		assertFalse(bean.hasListeners(propertyName));
124
		assertFalse(bean.hasListeners(propertyName));
Lines 156-168 Link Here
156
		}
158
		}
157
		
159
		
158
		public IObservableValue createObservableValue(Realm realm) {
160
		public IObservableValue createObservableValue(Realm realm) {
159
			try {
161
			return BeansObservables.observeValue(realm, bean, "value");
160
				PropertyDescriptor propertyDescriptor = new PropertyDescriptor("value", Bean.class);
161
				return new JavaBeanObservableValue(realm, bean,
162
						propertyDescriptor);					
163
			} catch (IntrospectionException e) {
164
				throw new RuntimeException(e);
165
			}
166
		}
162
		}
167
		
163
		
168
		public void change(IObservable observable) {
164
		public void change(IObservable observable) {
(-)src/org/eclipse/core/tests/internal/databinding/beans/JavaBeanObservableSetTest.java (-31 / +31 lines)
Lines 7-18 Link Here
7
 *
7
 *
8
 * Contributors:
8
 * Contributors:
9
 *     Brad Reynolds - initial API and implementation
9
 *     Brad Reynolds - initial API and implementation
10
 *     Matthew Hall - bugs 221351, 213145, 244098, 246103
10
 *     Matthew Hall - bugs 221351, 213145, 244098, 246103, 194734
11
 ******************************************************************************/
11
 ******************************************************************************/
12
12
13
package org.eclipse.core.tests.internal.databinding.beans;
13
package org.eclipse.core.tests.internal.databinding.beans;
14
14
15
import java.beans.IntrospectionException;
16
import java.beans.PropertyDescriptor;
15
import java.beans.PropertyDescriptor;
17
import java.util.Arrays;
16
import java.util.Arrays;
18
import java.util.Collections;
17
import java.util.Collections;
Lines 22-35 Link Here
22
import junit.framework.TestCase;
21
import junit.framework.TestCase;
23
import junit.framework.TestSuite;
22
import junit.framework.TestSuite;
24
23
24
import org.eclipse.core.databinding.beans.BeanProperties;
25
import org.eclipse.core.databinding.beans.BeansObservables;
25
import org.eclipse.core.databinding.beans.BeansObservables;
26
import org.eclipse.core.databinding.beans.IBeanObservable;
27
import org.eclipse.core.databinding.beans.IBeanProperty;
28
import org.eclipse.core.databinding.beans.PojoObservables;
26
import org.eclipse.core.databinding.observable.IObservable;
29
import org.eclipse.core.databinding.observable.IObservable;
27
import org.eclipse.core.databinding.observable.IObservableCollection;
30
import org.eclipse.core.databinding.observable.IObservableCollection;
28
import org.eclipse.core.databinding.observable.Realm;
31
import org.eclipse.core.databinding.observable.Realm;
29
import org.eclipse.core.databinding.observable.set.IObservableSet;
32
import org.eclipse.core.databinding.observable.set.IObservableSet;
30
import org.eclipse.core.databinding.observable.set.ISetChangeListener;
33
import org.eclipse.core.databinding.observable.set.ISetChangeListener;
31
import org.eclipse.core.databinding.observable.set.SetChangeEvent;
34
import org.eclipse.core.databinding.observable.set.SetChangeEvent;
32
import org.eclipse.core.internal.databinding.beans.JavaBeanObservableSet;
33
import org.eclipse.jface.databinding.conformance.MutableObservableSetContractTest;
35
import org.eclipse.jface.databinding.conformance.MutableObservableSetContractTest;
34
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableCollectionContractDelegate;
36
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableCollectionContractDelegate;
35
import org.eclipse.jface.databinding.conformance.util.ChangeEventTracker;
37
import org.eclipse.jface.databinding.conformance.util.ChangeEventTracker;
Lines 42-87 Link Here
42
 * @since 3.3
44
 * @since 3.3
43
 */
45
 */
44
public class JavaBeanObservableSetTest extends TestCase {
46
public class JavaBeanObservableSetTest extends TestCase {
45
	private JavaBeanObservableSet observableSet;
47
	private IObservableSet observableSet;
48
	private IBeanObservable beanObservable;
46
	private Bean bean;
49
	private Bean bean;
47
	private PropertyDescriptor propertyDescriptor;
50
	private PropertyDescriptor propertyDescriptor;
48
	private String propertyName;
51
	private String propertyName;
49
	private SetChangeListener listener;
52
	private SetChangeListener listener;
50
53
51
	/*
52
	 * (non-Javadoc)
53
	 * 
54
	 * @see junit.framework.TestCase#setUp()
55
	 */
56
	protected void setUp() throws Exception {
54
	protected void setUp() throws Exception {
57
		bean = new Bean();
55
		bean = new Bean();
58
		propertyName = "set";
56
		propertyName = "set";
59
		propertyDescriptor = new PropertyDescriptor(propertyName, Bean.class);
57
		propertyDescriptor = ((IBeanProperty) BeanProperties.set(
58
				Bean.class, propertyName)).getPropertyDescriptor();
60
59
61
		observableSet = new JavaBeanObservableSet(SWTObservables
60
		observableSet = BeansObservables
62
				.getRealm(Display.getDefault()), bean, propertyDescriptor,
61
				.observeSet(SWTObservables.getRealm(Display.getDefault()),
63
				Bean.class);
62
						bean, propertyName, Bean.class);
63
		beanObservable = (IBeanObservable) observableSet;
64
		listener = new SetChangeListener();
64
		listener = new SetChangeListener();
65
	}
65
	}
66
66
67
	public void testGetObserved() throws Exception {
67
	public void testGetObserved() throws Exception {
68
		assertEquals(bean, observableSet.getObserved());
68
		assertEquals(bean, beanObservable.getObserved());
69
	}
69
	}
70
70
71
	public void testGetPropertyDescriptor() throws Exception {
71
	public void testGetPropertyDescriptor() throws Exception {
72
		assertEquals(propertyDescriptor, observableSet.getPropertyDescriptor());
72
		assertEquals(propertyDescriptor, beanObservable.getPropertyDescriptor());
73
	}
73
	}
74
	
74
	
75
	public void testGetElementType() throws Exception {
75
	public void testGetElementType() throws Exception {
76
		assertEquals(Bean.class, observableSet.getElementType());
76
		assertEquals(Bean.class, observableSet.getElementType());
77
	}
77
	}
78
	
78
	
79
	public void testRegistersListenerOnCreation() throws Exception {
79
	public void testRegistersListenerAfterFirstListenerIsAdded() throws Exception {
80
		assertFalse(bean.changeSupport.hasListeners(propertyName));
81
		observableSet.addSetChangeListener(new SetChangeListener());
80
		assertTrue(bean.changeSupport.hasListeners(propertyName));
82
		assertTrue(bean.changeSupport.hasListeners(propertyName));
81
	}
83
	}
82
		
84
		
83
	public void testRemovesListenerOnDisposal() throws Exception {
85
    public void testRemovesListenerAfterLastListenerIsRemoved() throws Exception {
84
		observableSet.dispose();
86
		observableSet.addSetChangeListener(listener);
87
		
88
		assertTrue(bean.changeSupport.hasListeners(propertyName));
89
		observableSet.removeSetChangeListener(listener);
85
		assertFalse(bean.changeSupport.hasListeners(propertyName));
90
		assertFalse(bean.changeSupport.hasListeners(propertyName));
86
	}
91
	}
87
	
92
	
Lines 94-109 Link Here
94
99
95
	public void testConstructor_RegisterListeners() throws Exception {
100
	public void testConstructor_RegisterListeners() throws Exception {
96
		bean = new Bean();
101
		bean = new Bean();
97
		new JavaBeanObservableSet(new CurrentRealm(true), bean,
102
		observableSet = BeansObservables.observeSet(new CurrentRealm(true), bean,
98
				propertyDescriptor, Bean.class);
103
				propertyName);
104
		assertFalse(bean.hasListeners(propertyName));
105
		ChangeEventTracker.observe(observableSet);
99
		assertTrue(bean.hasListeners(propertyName));
106
		assertTrue(bean.hasListeners(propertyName));
100
	}
107
	}
101
108
102
	public void testConstructor_SkipsRegisterListeners() throws Exception {
109
	public void testConstructor_SkipsRegisterListeners() throws Exception {
103
		bean = new Bean();
110
		bean = new Bean();
104
111
105
		observableSet = new JavaBeanObservableSet(new CurrentRealm(true), bean,
112
		observableSet = PojoObservables.observeSet(new CurrentRealm(true),
106
				propertyDescriptor, Bean.class, false);
113
				bean, propertyName);
107
		assertFalse(bean.hasListeners(propertyName));
114
		assertFalse(bean.hasListeners(propertyName));
108
		ChangeEventTracker.observe(observableSet);
115
		ChangeEventTracker.observe(observableSet);
109
		assertFalse(bean.hasListeners(propertyName));
116
		assertFalse(bean.hasListeners(propertyName));
Lines 151-166 Link Here
151
				int elementCount) {
158
				int elementCount) {
152
			Bean bean = new Bean();
159
			Bean bean = new Bean();
153
			String propertyName = "set";
160
			String propertyName = "set";
154
			PropertyDescriptor propertyDescriptor;
155
			try {
156
				propertyDescriptor = new PropertyDescriptor(propertyName,
157
						Bean.class);
158
			} catch (IntrospectionException e) {
159
				throw new RuntimeException(e);
160
			}
161
161
162
			IObservableSet set = new JavaBeanObservableSet(realm,
162
			IObservableSet set = BeansObservables.observeSet(realm, bean,
163
					bean, propertyDescriptor, String.class);
163
					propertyName, String.class);
164
			for (int i = 0; i < elementCount; i++)
164
			for (int i = 0; i < elementCount; i++)
165
				set.add(createElement(set));
165
				set.add(createElement(set));
166
			return set;
166
			return set;
(-)src/org/eclipse/core/tests/internal/databinding/beans/BeanObservableSetDecoratorTest.java (-19 / +13 lines)
Lines 7-13 Link Here
7
 *
7
 *
8
 * Contributors:
8
 * Contributors:
9
 *     Brad Reynolds - initial API and implementation
9
 *     Brad Reynolds - initial API and implementation
10
 *     Matthew Hall - bug 246625
10
 *     Matthew Hall - bug 246625, 194734
11
 ******************************************************************************/
11
 ******************************************************************************/
12
12
13
package org.eclipse.core.tests.internal.databinding.beans;
13
package org.eclipse.core.tests.internal.databinding.beans;
Lines 16-23 Link Here
16
16
17
import junit.framework.TestCase;
17
import junit.framework.TestCase;
18
18
19
import org.eclipse.core.databinding.beans.BeansObservables;
20
import org.eclipse.core.databinding.observable.set.IObservableSet;
19
import org.eclipse.core.internal.databinding.beans.BeanObservableSetDecorator;
21
import org.eclipse.core.internal.databinding.beans.BeanObservableSetDecorator;
20
import org.eclipse.core.internal.databinding.beans.JavaBeanObservableSet;
21
import org.eclipse.jface.databinding.swt.SWTObservables;
22
import org.eclipse.jface.databinding.swt.SWTObservables;
22
import org.eclipse.swt.widgets.Display;
23
import org.eclipse.swt.widgets.Display;
23
24
Lines 26-62 Link Here
26
 */
27
 */
27
public class BeanObservableSetDecoratorTest extends TestCase {
28
public class BeanObservableSetDecoratorTest extends TestCase {
28
	private PropertyDescriptor propertyDescriptor;
29
	private PropertyDescriptor propertyDescriptor;
29
	private JavaBeanObservableSet observableSet;
30
	private IObservableSet observableSet;
30
	private BeanObservableSetDecorator decorator;
31
	private BeanObservableSetDecorator decorator;
31
	private Bean bean;
32
	private Bean bean;
32
33
33
	/*
34
	 * (non-Javadoc)
35
	 * 
36
	 * @see junit.framework.TestCase#setUp()
37
	 */
38
	protected void setUp() throws Exception {
34
	protected void setUp() throws Exception {
39
		super.setUp();
35
		super.setUp();
40
36
41
		bean = new Bean();
37
		bean = new Bean();
42
		propertyDescriptor = new PropertyDescriptor("set",
38
		propertyDescriptor = new PropertyDescriptor("set", Bean.class);
43
				Bean.class);
39
		observableSet = BeansObservables.observeSet(SWTObservables
44
		observableSet = new JavaBeanObservableSet(
40
				.getRealm(Display.getDefault()), bean, "set");
45
				SWTObservables.getRealm(Display.getDefault()), bean,
41
		decorator = new BeanObservableSetDecorator(observableSet,
46
				propertyDescriptor, String.class);
42
				propertyDescriptor);
47
		decorator = new BeanObservableSetDecorator(
48
				observableSet, propertyDescriptor);
49
	}
43
	}
50
44
51
	public void testGetDelegate() throws Exception {
45
	public void testGetDecorated() throws Exception {
52
		assertEquals(observableSet, decorator.getDecorated());
46
		assertSame(observableSet, decorator.getDecorated());
53
	}
47
	}
54
48
55
	public void testGetObserved() throws Exception {
49
	public void testGetObserved() throws Exception {
56
		assertEquals(bean, decorator.getObserved());
50
		assertSame(bean, decorator.getObserved());
57
	}
51
	}
58
52
59
	public void testGetPropertyDescriptor() throws Exception {
53
	public void testGetPropertyDescriptor() throws Exception {
60
		assertEquals(propertyDescriptor, decorator.getPropertyDescriptor());
54
		assertSame(propertyDescriptor, decorator.getPropertyDescriptor());
61
	}
55
	}
62
}
56
}
(-)src/org/eclipse/core/tests/internal/databinding/beans/JavaBeanObservableArrayBasedSetTest.java (-28 / +29 lines)
Lines 8-19 Link Here
8
 * Contributors:
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 221351)
9
 *     Matthew Hall - initial API and implementation (bug 221351)
10
 *     Brad Reynolds - through JavaBeanObservableArrayBasedListTest.java
10
 *     Brad Reynolds - through JavaBeanObservableArrayBasedListTest.java
11
 *     Matthew Hall - bug 213145, 244098, 246103
11
 *     Matthew Hall - bug 213145, 244098, 246103, 194734
12
 ******************************************************************************/
12
 ******************************************************************************/
13
13
14
package org.eclipse.core.tests.internal.databinding.beans;
14
package org.eclipse.core.tests.internal.databinding.beans;
15
15
16
import java.beans.IntrospectionException;
17
import java.beans.PropertyChangeEvent;
16
import java.beans.PropertyChangeEvent;
18
import java.beans.PropertyChangeListener;
17
import java.beans.PropertyChangeListener;
19
import java.beans.PropertyDescriptor;
18
import java.beans.PropertyDescriptor;
Lines 25-37 Link Here
25
import junit.framework.Test;
24
import junit.framework.Test;
26
import junit.framework.TestSuite;
25
import junit.framework.TestSuite;
27
26
27
import org.eclipse.core.databinding.beans.BeanProperties;
28
import org.eclipse.core.databinding.beans.BeansObservables;
28
import org.eclipse.core.databinding.beans.BeansObservables;
29
import org.eclipse.core.databinding.beans.IBeanObservable;
30
import org.eclipse.core.databinding.beans.IBeanProperty;
29
import org.eclipse.core.databinding.observable.IObservable;
31
import org.eclipse.core.databinding.observable.IObservable;
30
import org.eclipse.core.databinding.observable.IObservableCollection;
32
import org.eclipse.core.databinding.observable.IObservableCollection;
31
import org.eclipse.core.databinding.observable.Realm;
33
import org.eclipse.core.databinding.observable.Realm;
32
import org.eclipse.core.databinding.observable.set.IObservableSet;
34
import org.eclipse.core.databinding.observable.set.IObservableSet;
33
import org.eclipse.core.databinding.observable.set.SetChangeEvent;
35
import org.eclipse.core.databinding.observable.set.SetChangeEvent;
34
import org.eclipse.core.internal.databinding.beans.JavaBeanObservableSet;
35
import org.eclipse.jface.databinding.conformance.MutableObservableSetContractTest;
36
import org.eclipse.jface.databinding.conformance.MutableObservableSetContractTest;
36
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableCollectionContractDelegate;
37
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableCollectionContractDelegate;
37
import org.eclipse.jface.databinding.conformance.util.CurrentRealm;
38
import org.eclipse.jface.databinding.conformance.util.CurrentRealm;
Lines 45-51 Link Here
45
 */
46
 */
46
public class JavaBeanObservableArrayBasedSetTest extends
47
public class JavaBeanObservableArrayBasedSetTest extends
47
		AbstractDefaultRealmTestCase {
48
		AbstractDefaultRealmTestCase {
48
	private JavaBeanObservableSet set;
49
	private IObservableSet set;
50
	private IBeanObservable beanObservable;
49
51
50
	private PropertyDescriptor propertyDescriptor;
52
	private PropertyDescriptor propertyDescriptor;
51
53
Lines 57-83 Link Here
57
		super.setUp();
59
		super.setUp();
58
60
59
		propertyName = "array";
61
		propertyName = "array";
60
		propertyDescriptor = new PropertyDescriptor(propertyName, Bean.class);
62
		propertyDescriptor = ((IBeanProperty) BeanProperties.set(
63
				Bean.class, propertyName)).getPropertyDescriptor();
61
		bean = new Bean(new HashSet());
64
		bean = new Bean(new HashSet());
62
65
63
		set = new JavaBeanObservableSet(SWTObservables.getRealm(Display
66
		set = BeansObservables.observeSet(SWTObservables.getRealm(Display
64
				.getDefault()), bean, propertyDescriptor, String.class);
67
				.getDefault()), bean, propertyName);
68
		beanObservable = (IBeanObservable) set;
65
	}
69
	}
66
70
67
	public void testGetObserved() throws Exception {
71
	public void testGetObserved() throws Exception {
68
		assertEquals(bean, set.getObserved());
72
		assertEquals(bean, beanObservable.getObserved());
69
	}
73
	}
70
74
71
	public void testGetPropertyDescriptor() throws Exception {
75
	public void testGetPropertyDescriptor() throws Exception {
72
		assertEquals(propertyDescriptor, set.getPropertyDescriptor());
76
		assertEquals(propertyDescriptor, beanObservable.getPropertyDescriptor());
73
	}
77
	}
74
78
75
	public void testRegistersListenerOnCreation() throws Exception {
79
	public void testRegistersListenerAfterFirstListenerIsAdded()
80
			throws Exception {
81
		assertFalse(bean.changeSupport.hasListeners(propertyName));
82
		SetChangeEventTracker.observe(set);
76
		assertTrue(bean.changeSupport.hasListeners(propertyName));
83
		assertTrue(bean.changeSupport.hasListeners(propertyName));
77
	}
84
	}
78
85
79
	public void testRemovesListenerOnDisposal() throws Exception {
86
	public void testRemovesListenerAfterLastListenerIsRemoved()
80
		set.dispose();
87
			throws Exception {
88
		SetChangeEventTracker listener = SetChangeEventTracker.observe(set);
89
90
		assertTrue(bean.changeSupport.hasListeners(propertyName));
91
		set.removeSetChangeListener(listener);
81
		assertFalse(bean.changeSupport.hasListeners(propertyName));
92
		assertFalse(bean.changeSupport.hasListeners(propertyName));
82
	}
93
	}
83
94
Lines 309-315 Link Here
309
		assertEquals("array", event.getPropertyName());
320
		assertEquals("array", event.getPropertyName());
310
		assertTrue("old value", Arrays.equals(old, (Object[]) event
321
		assertTrue("old value", Arrays.equals(old, (Object[]) event
311
				.getOldValue()));
322
				.getOldValue()));
312
		assertTrue("new value", Arrays.equals(bean.getArray(), (Object[]) event.getNewValue()));
323
		assertTrue("new value", Arrays.equals(bean.getArray(), (Object[]) event
324
				.getNewValue()));
313
		assertFalse("sets are equal", Arrays.equals(bean.getArray(), old));
325
		assertFalse("sets are equal", Arrays.equals(bean.getArray(), old));
314
	}
326
	}
315
327
Lines 319-329 Link Here
319
331
320
		PropertyChangeEvent evt;
332
		PropertyChangeEvent evt;
321
333
322
		/*
323
		 * (non-Javadoc)
324
		 * 
325
		 * @see java.beans.PropertyChangeListener#propertyChange(java.beans.PropertyChangeEvent)
326
		 */
327
		public void propertyChange(PropertyChangeEvent evt) {
334
		public void propertyChange(PropertyChangeEvent evt) {
328
			count++;
335
			count++;
329
			this.evt = evt;
336
			this.evt = evt;
Lines 331-337 Link Here
331
	}
338
	}
332
339
333
	public static Test suite() {
340
	public static Test suite() {
334
		TestSuite suite = new TestSuite(JavaBeanObservableArrayBasedSetTest.class.getName());
341
		TestSuite suite = new TestSuite(
342
				JavaBeanObservableArrayBasedSetTest.class.getName());
335
		suite.addTestSuite(JavaBeanObservableArrayBasedSetTest.class);
343
		suite.addTestSuite(JavaBeanObservableArrayBasedSetTest.class);
336
		suite.addTest(MutableObservableSetContractTest.suite(new Delegate()));
344
		suite.addTest(MutableObservableSetContractTest.suite(new Delegate()));
337
		return suite;
345
		return suite;
Lines 341-357 Link Here
341
		public IObservableCollection createObservableCollection(Realm realm,
349
		public IObservableCollection createObservableCollection(Realm realm,
342
				int elementCount) {
350
				int elementCount) {
343
			String propertyName = "array";
351
			String propertyName = "array";
344
			PropertyDescriptor propertyDescriptor;
345
			try {
346
				propertyDescriptor = new PropertyDescriptor(propertyName,
347
						Bean.class);
348
			} catch (IntrospectionException e) {
349
				throw new RuntimeException(e);
350
			}
351
			Object bean = new Bean(new Object[0]);
352
			Object bean = new Bean(new Object[0]);
352
353
353
			IObservableSet set = new JavaBeanObservableSet(realm, bean,
354
			IObservableSet set = BeansObservables.observeSet(realm, bean,
354
					propertyDescriptor, String.class);
355
					propertyName, String.class);
355
			for (int i = 0; i < elementCount; i++)
356
			for (int i = 0; i < elementCount; i++)
356
				set.add(createElement(set));
357
				set.add(createElement(set));
357
			return set;
358
			return set;
(-)src/org/eclipse/core/tests/internal/databinding/beans/ListenerSupportTest.java (-231 lines)
Removed Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2007, 2008 IBM Corporation and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
10
 *******************************************************************************/
11
12
package org.eclipse.core.tests.internal.databinding.beans;
13
14
import java.beans.PropertyChangeEvent;
15
import java.beans.PropertyChangeListener;
16
import java.beans.PropertyChangeSupport;
17
import java.util.Arrays;
18
19
import org.eclipse.core.databinding.util.ILogger;
20
import org.eclipse.core.databinding.util.Policy;
21
import org.eclipse.core.internal.databinding.beans.ListenerSupport;
22
import org.eclipse.core.runtime.IStatus;
23
import org.eclipse.jface.tests.databinding.AbstractDefaultRealmTestCase;
24
25
/**
26
 * @since 1.1
27
 */
28
public class ListenerSupportTest extends AbstractDefaultRealmTestCase {
29
	private PropertyChangeListenerStub listener;
30
	private String propertyName;
31
32
	protected void setUp() throws Exception {
33
		super.setUp();
34
35
		listener = new PropertyChangeListenerStub();
36
		propertyName = "value";
37
	}
38
39
	public void testAddPropertyChangeListenerWithPropertyName()
40
			throws Exception {
41
		SpecificListenerBean bean = new SpecificListenerBean();
42
43
		ListenerSupport support = new ListenerSupport(listener, propertyName);
44
		assertFalse(bean.changeSupport.hasListeners(propertyName));
45
		assertNull(support.getHookedTargets());
46
		
47
		support.hookListener(bean);
48
		assertTrue("has listeners", bean.changeSupport.hasListeners(propertyName));
49
		assertTrue("hooked target", Arrays.asList(support.getHookedTargets()).contains(bean));
50
	}
51
52
	public void testAddPropertyChangeListenerWithoutPropertyName()
53
			throws Exception {
54
		GenericListenerBean bean = new GenericListenerBean();
55
56
		ListenerSupport support = new ListenerSupport(listener, propertyName);
57
		assertFalse(bean.changeSupport.hasListeners(propertyName));
58
		assertNull(support.getHookedTargets());
59
		
60
		support.hookListener(bean);
61
		assertTrue("has listeners", bean.changeSupport.hasListeners(propertyName));
62
		assertTrue("hooked target", Arrays.asList(support.getHookedTargets()).contains(bean));
63
	}
64
65
	public void testChangeListenerIsOnlyNotifiedWhenWatchedPropertyChanges()
66
			throws Exception {
67
		GenericListenerBean bean = new GenericListenerBean();
68
		ListenerSupport support = new ListenerSupport(listener, propertyName);
69
		support.hookListener(bean);
70
71
		assertEquals(0, listener.count);
72
		bean.setValue("1");
73
		assertEquals(1, listener.count);
74
		assertEquals("value", listener.event.getPropertyName());
75
76
		bean.setOther("2");
77
		assertEquals(1, listener.count);
78
	}
79
80
	public void testLogStatusWhenAddPropertyChangeListenerMethodIsNotFound()
81
			throws Exception {
82
		class BeanStub {
83
		}
84
85
		class Log implements ILogger {
86
			int count;
87
			IStatus status;
88
89
			public void log(IStatus status) {
90
				count++;
91
				this.status = status;
92
			}
93
		}
94
95
		Log log = new Log();
96
		Policy.setLog(log);
97
98
		ListenerSupport support = new ListenerSupport(listener, "value");
99
		BeanStub bean = new BeanStub();
100
101
		assertEquals(0, log.count);
102
		support.hookListener(bean);
103
		assertEquals(1, log.count);
104
		assertEquals(IStatus.WARNING, log.status.getSeverity());
105
	}
106
107
	public void testRemovePropertyChangeListenerWithPropertyName()
108
			throws Exception {
109
		SpecificListenerBean bean = new SpecificListenerBean();
110
		ListenerSupport support = new ListenerSupport(listener, propertyName);
111
		support.hookListener(bean);
112
113
		assertTrue(bean.changeSupport.hasListeners(propertyName));
114
		assertTrue(Arrays.asList(support.getHookedTargets()).contains(bean));
115
		
116
		support.unhookListener(bean);
117
		assertFalse("has listeners", bean.changeSupport.hasListeners(propertyName));
118
		assertNull("unhooked target", support.getHookedTargets());
119
	}
120
121
	public void testRemovePropertyChangeListenerWithoutPropertyName()
122
			throws Exception {
123
		GenericListenerBean bean = new GenericListenerBean();
124
		ListenerSupport support = new ListenerSupport(listener, propertyName);
125
		support.hookListener(bean);
126
127
		assertTrue(bean.changeSupport.hasListeners(propertyName));
128
		assertTrue(Arrays.asList(support.getHookedTargets()).contains(bean));
129
		
130
		support.unhookListener(bean);
131
		assertFalse("has listeners", bean.changeSupport.hasListeners(propertyName));
132
		assertNull("unhooked target", support.getHookedTargets());
133
	}
134
135
	public void testLogStatusWhenRemovePropertyChangeListenerMethodIsNotFound()
136
			throws Exception {
137
		class InvalidBean {
138
		}
139
140
		class Log implements ILogger {
141
			int count;
142
			IStatus status;
143
144
			public void log(IStatus status) {
145
				count++;
146
				this.status = status;
147
			}
148
		}
149
150
		Log log = new Log();
151
		Policy.setLog(log);
152
153
		ListenerSupport support = new ListenerSupport(listener, "value");
154
		InvalidBean bean = new InvalidBean();
155
156
		support.hookListener(bean);
157
		log.count = 0;
158
		log.status = null;
159
		assertEquals(0, log.count);
160
		support.unhookListener(bean);
161
		assertEquals(1, log.count);
162
		assertEquals(IStatus.WARNING, log.status.getSeverity());
163
	}
164
165
	static class GenericListenerBean {
166
		private String other;
167
		PropertyChangeSupport changeSupport = new PropertyChangeSupport(this);
168
		private String value;
169
170
		public String getValue() {
171
			return value;
172
		}
173
174
		public void setValue(String value) {
175
			changeSupport.firePropertyChange("value", this.value,
176
					this.value = value);
177
		}
178
179
		public String getOther() {
180
			return other;
181
		}
182
183
		public void setOther(String other) {
184
			changeSupport.firePropertyChange("other", this.other,
185
					this.other = other);
186
		}
187
188
		public void addPropertyChangeListener(PropertyChangeListener listener) {
189
			changeSupport.addPropertyChangeListener(listener);
190
		}
191
192
		public void removePropertyChangeListener(PropertyChangeListener listener) {
193
			changeSupport.removePropertyChangeListener(listener);
194
		}
195
	}
196
197
	static class SpecificListenerBean {
198
		PropertyChangeSupport changeSupport = new PropertyChangeSupport(this);
199
		String propertyName;
200
		String value;
201
202
		public void addPropertyChangeListener(String name,
203
				PropertyChangeListener listener) {
204
			this.propertyName = name;
205
			changeSupport.addPropertyChangeListener(name, listener);
206
		}
207
208
		public void removePropertyChangeListener(String name,
209
				PropertyChangeListener listener) {
210
			changeSupport.removePropertyChangeListener(name, listener);
211
		}
212
213
		public String getValue() {
214
			return value;
215
		}
216
217
		public void setValue(String value) {
218
			this.value = value;
219
		}
220
	}
221
222
	static class PropertyChangeListenerStub implements PropertyChangeListener {
223
		PropertyChangeEvent event;
224
		int count;
225
226
		public void propertyChange(PropertyChangeEvent evt) {
227
			count++;
228
			this.event = evt;
229
		}
230
	}
231
}
(-)src/org/eclipse/jface/tests/databinding/BindingTestSuite.java (-28 / +33 lines)
Lines 77-82 Link Here
77
import org.eclipse.core.tests.internal.databinding.beans.BeanObservableListDecoratorTest;
77
import org.eclipse.core.tests.internal.databinding.beans.BeanObservableListDecoratorTest;
78
import org.eclipse.core.tests.internal.databinding.beans.BeanObservableSetDecoratorTest;
78
import org.eclipse.core.tests.internal.databinding.beans.BeanObservableSetDecoratorTest;
79
import org.eclipse.core.tests.internal.databinding.beans.BeanObservableValueDecoratorTest;
79
import org.eclipse.core.tests.internal.databinding.beans.BeanObservableValueDecoratorTest;
80
import org.eclipse.core.tests.internal.databinding.beans.BeanPropertyListenerSupportTest;
81
import org.eclipse.core.tests.internal.databinding.beans.BeanValuePropertyTest;
80
import org.eclipse.core.tests.internal.databinding.beans.JavaBeanObservableArrayBasedListTest;
82
import org.eclipse.core.tests.internal.databinding.beans.JavaBeanObservableArrayBasedListTest;
81
import org.eclipse.core.tests.internal.databinding.beans.JavaBeanObservableArrayBasedSetTest;
83
import org.eclipse.core.tests.internal.databinding.beans.JavaBeanObservableArrayBasedSetTest;
82
import org.eclipse.core.tests.internal.databinding.beans.JavaBeanObservableListTest;
84
import org.eclipse.core.tests.internal.databinding.beans.JavaBeanObservableListTest;
Lines 84-90 Link Here
84
import org.eclipse.core.tests.internal.databinding.beans.JavaBeanObservableSetTest;
86
import org.eclipse.core.tests.internal.databinding.beans.JavaBeanObservableSetTest;
85
import org.eclipse.core.tests.internal.databinding.beans.JavaBeanObservableValueTest;
87
import org.eclipse.core.tests.internal.databinding.beans.JavaBeanObservableValueTest;
86
import org.eclipse.core.tests.internal.databinding.beans.JavaBeanPropertyObservableMapTest;
88
import org.eclipse.core.tests.internal.databinding.beans.JavaBeanPropertyObservableMapTest;
87
import org.eclipse.core.tests.internal.databinding.beans.ListenerSupportTest;
88
import org.eclipse.core.tests.internal.databinding.conversion.DateConversionSupportTest;
89
import org.eclipse.core.tests.internal.databinding.conversion.DateConversionSupportTest;
89
import org.eclipse.core.tests.internal.databinding.conversion.IdentityConverterTest;
90
import org.eclipse.core.tests.internal.databinding.conversion.IdentityConverterTest;
90
import org.eclipse.core.tests.internal.databinding.conversion.IntegerToStringConverterTest;
91
import org.eclipse.core.tests.internal.databinding.conversion.IntegerToStringConverterTest;
Lines 163-169 Link Here
163
import org.eclipse.jface.tests.internal.databinding.swt.LabelObservableValueTest;
164
import org.eclipse.jface.tests.internal.databinding.swt.LabelObservableValueTest;
164
import org.eclipse.jface.tests.internal.databinding.swt.ListSingleSelectionObservableValueTest;
165
import org.eclipse.jface.tests.internal.databinding.swt.ListSingleSelectionObservableValueTest;
165
import org.eclipse.jface.tests.internal.databinding.swt.SWTDelayedObservableValueDecoratorTest;
166
import org.eclipse.jface.tests.internal.databinding.swt.SWTDelayedObservableValueDecoratorTest;
166
import org.eclipse.jface.tests.internal.databinding.swt.SWTObservableListTest;
167
import org.eclipse.jface.tests.internal.databinding.swt.ScaleObservableValueMaxTest;
167
import org.eclipse.jface.tests.internal.databinding.swt.ScaleObservableValueMaxTest;
168
import org.eclipse.jface.tests.internal.databinding.swt.ScaleObservableValueMinTest;
168
import org.eclipse.jface.tests.internal.databinding.swt.ScaleObservableValueMinTest;
169
import org.eclipse.jface.tests.internal.databinding.swt.ScaleObservableValueSelectionTest;
169
import org.eclipse.jface.tests.internal.databinding.swt.ScaleObservableValueSelectionTest;
Lines 172-177 Link Here
172
import org.eclipse.jface.tests.internal.databinding.swt.SpinnerObservableValueMinTest;
172
import org.eclipse.jface.tests.internal.databinding.swt.SpinnerObservableValueMinTest;
173
import org.eclipse.jface.tests.internal.databinding.swt.SpinnerObservableValueSelectionTest;
173
import org.eclipse.jface.tests.internal.databinding.swt.SpinnerObservableValueSelectionTest;
174
import org.eclipse.jface.tests.internal.databinding.swt.SpinnerObservableValueTest;
174
import org.eclipse.jface.tests.internal.databinding.swt.SpinnerObservableValueTest;
175
import org.eclipse.jface.tests.internal.databinding.swt.StyledTextObservableValueFocusOutTest;
176
import org.eclipse.jface.tests.internal.databinding.swt.StyledTextObservableValueModifyTest;
177
import org.eclipse.jface.tests.internal.databinding.swt.StyledTextObservableValueTest;
175
import org.eclipse.jface.tests.internal.databinding.swt.TableObservableValueTest;
178
import org.eclipse.jface.tests.internal.databinding.swt.TableObservableValueTest;
176
import org.eclipse.jface.tests.internal.databinding.swt.TableSingleSelectionObservableValueTest;
179
import org.eclipse.jface.tests.internal.databinding.swt.TableSingleSelectionObservableValueTest;
177
import org.eclipse.jface.tests.internal.databinding.swt.TextEditableObservableValueTest;
180
import org.eclipse.jface.tests.internal.databinding.swt.TextEditableObservableValueTest;
Lines 198-204 Link Here
198
	}
201
	}
199
202
200
	public BindingTestSuite() {
203
	public BindingTestSuite() {
201
		
204
202
		// org.eclipse.core.tests.databinding
205
		// org.eclipse.core.tests.databinding
203
		addTestSuite(AggregateValidationStatusTest.class);
206
		addTestSuite(AggregateValidationStatusTest.class);
204
		addTestSuite(BindingTest.class);
207
		addTestSuite(BindingTest.class);
Lines 253-271 Link Here
253
		addTest(ObservableSetTest.suite());
256
		addTest(ObservableSetTest.suite());
254
		addTest(UnionSetTest.suite());
257
		addTest(UnionSetTest.suite());
255
		addTest(WritableSetTest.suite());
258
		addTest(WritableSetTest.suite());
256
		
259
257
		//org.eclipse.core.tests.databinding.observable.value
260
		// org.eclipse.core.tests.databinding.observable.value
258
		addTestSuite(AbstractObservableValueTest.class);
261
		addTestSuite(AbstractObservableValueTest.class);
259
		addTestSuite(AbstractVetoableValueTest.class);
262
		addTestSuite(AbstractVetoableValueTest.class);
260
		addTestSuite(ComputedValueTest.class);
263
		addTestSuite(ComputedValueTest.class);
261
		addTest(DecoratingObservableValueTest.suite());
264
		addTest(DecoratingObservableValueTest.suite());
262
		addTest(SelectObservableValueTest.suite());
265
		addTest(SelectObservableValueTest.suite());
263
		addTest(WritableValueTest.suite());
266
		addTest(WritableValueTest.suite());
264
		
267
265
		//org.eclipse.core.tests.databinding.validation
268
		// org.eclipse.core.tests.databinding.validation
266
		addTestSuite(MultiValidatorTest.class);
269
		addTestSuite(MultiValidatorTest.class);
267
		addTestSuite(ValidationStatusTest.class);
270
		addTestSuite(ValidationStatusTest.class);
268
		
271
269
		// org.eclipse.core.tests.internal.databinding
272
		// org.eclipse.core.tests.internal.databinding
270
		addTestSuite(BindingMessagesTest.class);
273
		addTestSuite(BindingMessagesTest.class);
271
		addTestSuite(BindingStatusTest.class);
274
		addTestSuite(BindingStatusTest.class);
Lines 298-308 Link Here
298
		addTestSuite(StringToNumberParserTest.class);
301
		addTestSuite(StringToNumberParserTest.class);
299
		addTestSuite(StringToShortConverterTest.class);
302
		addTestSuite(StringToShortConverterTest.class);
300
303
301
		//org.eclipse.core.tests.internal.databinding.internal.beans
304
		// org.eclipse.core.tests.internal.databinding.internal.beans
302
		addTest(BeanObservableListDecoratorTest.suite());
305
		addTest(BeanObservableListDecoratorTest.suite());
303
		addTestSuite(BeanObservableSetDecoratorTest.class);
306
		addTestSuite(BeanObservableSetDecoratorTest.class);
304
		addTestSuite(BeanObservableValueDecoratorTest.class);
307
		addTestSuite(BeanObservableValueDecoratorTest.class);
305
		addTestSuite(BeanObservableListDecoratorTest.class);
308
		addTestSuite(BeanObservableListDecoratorTest.class);
309
		addTestSuite(BeanValuePropertyTest.class);
306
		addTest(JavaBeanObservableArrayBasedListTest.suite());
310
		addTest(JavaBeanObservableArrayBasedListTest.suite());
307
		addTest(JavaBeanObservableArrayBasedSetTest.suite());
311
		addTest(JavaBeanObservableArrayBasedSetTest.suite());
308
		addTest(JavaBeanObservableListTest.suite());
312
		addTest(JavaBeanObservableListTest.suite());
Lines 310-318 Link Here
310
		addTest(JavaBeanObservableSetTest.suite());
314
		addTest(JavaBeanObservableSetTest.suite());
311
		addTest(JavaBeanObservableValueTest.suite());
315
		addTest(JavaBeanObservableValueTest.suite());
312
		addTestSuite(JavaBeanPropertyObservableMapTest.class);
316
		addTestSuite(JavaBeanPropertyObservableMapTest.class);
313
		addTestSuite(ListenerSupportTest.class);
317
		addTestSuite(BeanPropertyListenerSupportTest.class);
314
		
318
315
		//org.eclipse.core.tests.internal.databinding.observable
319
		// org.eclipse.core.tests.internal.databinding.observable
316
		addTest(ConstantObservableValueTest.suite());
320
		addTest(ConstantObservableValueTest.suite());
317
		addTest(DelayedObservableValueTest.suite());
321
		addTest(DelayedObservableValueTest.suite());
318
		addTest(EmptyObservableListTest.suite());
322
		addTest(EmptyObservableListTest.suite());
Lines 325-332 Link Here
325
		addTest(ValidatedObservableValueTest.suite());
329
		addTest(ValidatedObservableValueTest.suite());
326
		addTest(ValidatedObservableListTest.suite());
330
		addTest(ValidatedObservableListTest.suite());
327
		addTest(ValidatedObservableSetTest.suite());
331
		addTest(ValidatedObservableSetTest.suite());
328
//		addTest(ValidatedObservableMapTest.suite());
332
		// addTest(ValidatedObservableMapTest.suite());
329
		
333
330
		// org.eclipse.core.tests.internal.databinding.observable.masterdetail
334
		// org.eclipse.core.tests.internal.databinding.observable.masterdetail
331
		addTest(DetailObservableListTest.suite());
335
		addTest(DetailObservableListTest.suite());
332
		addTest(DetailObservableSetTest.suite());
336
		addTest(DetailObservableSetTest.suite());
Lines 353-376 Link Here
353
		addTest(BindingScenariosTestSuite.suite());
357
		addTest(BindingScenariosTestSuite.suite());
354
		// The files in this package are in the above test suite
358
		// The files in this package are in the above test suite
355
359
356
		//org.eclipse.jface.tests.databinding.swt
360
		// org.eclipse.jface.tests.databinding.swt
357
		addTestSuite(SWTObservablesTest.class);
361
		addTestSuite(SWTObservablesTest.class);
358
		
362
359
		// org.eclipse.jface.tests.databinding.viewers
363
		// org.eclipse.jface.tests.databinding.viewers
360
		addTestSuite(ObservableListTreeContentProviderTest.class);
364
		addTestSuite(ObservableListTreeContentProviderTest.class);
361
		addTestSuite(ObservableMapLabelProviderTest.class);
365
		addTestSuite(ObservableMapLabelProviderTest.class);
362
		addTestSuite(ObservableSetContentProviderTest.class);
366
		addTestSuite(ObservableSetContentProviderTest.class);
363
		addTestSuite(ObservableSetTreeContentProviderTest.class);
367
		addTestSuite(ObservableSetTreeContentProviderTest.class);
364
		addTestSuite(ViewersObservablesTest.class);
368
		addTestSuite(ViewersObservablesTest.class);
365
		
369
366
		// org.eclipse.jface.tests.databinding.wizard
370
		// org.eclipse.jface.tests.databinding.wizard
367
		addTestSuite(WizardPageSupportTest.class);
371
		addTestSuite(WizardPageSupportTest.class);
368
		
372
369
		//org.eclipse.jface.tests.example.databinding.mask.internal
373
		// org.eclipse.jface.tests.example.databinding.mask.internal
370
		addTestSuite(EditMaskLexerAndTokenTest.class);
374
		addTestSuite(EditMaskLexerAndTokenTest.class);
371
		addTestSuite(EditMaskParserTest.class);
375
		addTestSuite(EditMaskParserTest.class);
372
376
373
		//org.eclipse.jface.tests.internal.databinding.internal.swt
377
		// org.eclipse.jface.tests.internal.databinding.internal.swt
374
		addTest(ButtonObservableValueTest.suite());
378
		addTest(ButtonObservableValueTest.suite());
375
		addTestSuite(CComboObservableValueTest.class);
379
		addTestSuite(CComboObservableValueTest.class);
376
		addTest(CComboObservableValueSelectionTest.suite());
380
		addTest(CComboObservableValueSelectionTest.suite());
Lines 383-413 Link Here
383
		addTest(ComboObservableValueTextTest.suite());
387
		addTest(ComboObservableValueTextTest.suite());
384
		addTestSuite(ComboSingleSelectionObservableValueTest.class);
388
		addTestSuite(ComboSingleSelectionObservableValueTest.class);
385
		addTest(SWTDelayedObservableValueDecoratorTest.suite());
389
		addTest(SWTDelayedObservableValueDecoratorTest.suite());
386
		
390
387
		addTest(SWTObservableListTest.suite());
388
		
389
		addTestSuite(ControlObservableValueTest.class);
391
		addTestSuite(ControlObservableValueTest.class);
390
		addTest(LabelObservableValueTest.suite());
392
		addTest(LabelObservableValueTest.suite());
391
		addTestSuite(ListSingleSelectionObservableValueTest.class);
393
		addTestSuite(ListSingleSelectionObservableValueTest.class);
392
		addTest(ScaleObservableValueMinTest.suite());
394
		addTest(ScaleObservableValueMinTest.suite());
393
		addTest(ScaleObservableValueMaxTest.suite());
395
		addTest(ScaleObservableValueMaxTest.suite());
394
		addTest(ScaleObservableValueSelectionTest.suite());
396
		addTest(ScaleObservableValueSelectionTest.suite());
395
		
397
396
		addTest(ShellObservableValueTest.suite());
398
		addTest(ShellObservableValueTest.suite());
397
		
399
398
		addTestSuite(SpinnerObservableValueTest.class);
400
		addTestSuite(SpinnerObservableValueTest.class);
399
		addTest(SpinnerObservableValueMinTest.suite());
401
		addTest(SpinnerObservableValueMinTest.suite());
400
		addTest(SpinnerObservableValueMaxTest.suite());
402
		addTest(SpinnerObservableValueMaxTest.suite());
401
		addTest(SpinnerObservableValueSelectionTest.suite());
403
		addTest(SpinnerObservableValueSelectionTest.suite());
402
		
404
403
		addTestSuite(TableObservableValueTest.class);
405
		addTestSuite(TableObservableValueTest.class);
404
		addTest(TableSingleSelectionObservableValueTest.suite());
406
		addTest(TableSingleSelectionObservableValueTest.suite());
405
		addTest(TextEditableObservableValueTest.suite());
407
		addTest(TextEditableObservableValueTest.suite());
406
		addTest(TextObservableValueFocusOutTest.suite());
408
		addTest(TextObservableValueFocusOutTest.suite());
407
		addTest(TextObservableValueModifyTest.suite());
409
		addTest(TextObservableValueModifyTest.suite());
408
		addTestSuite(TextObservableValueTest.class);
410
		addTestSuite(TextObservableValueTest.class);
409
		
411
		addTest(StyledTextObservableValueFocusOutTest.suite());
410
		//org.eclipse.jface.tests.internal.databinding.internal.viewers
412
		addTest(StyledTextObservableValueModifyTest.suite());
413
		addTestSuite(StyledTextObservableValueTest.class);
414
415
		// org.eclipse.jface.tests.internal.databinding.internal.viewers
411
		addTest(ObservableViewerElementSetTest.suite());
416
		addTest(ObservableViewerElementSetTest.suite());
412
		addTestSuite(ObservableCollectionTreeContentProviderTest.class);
417
		addTestSuite(ObservableCollectionTreeContentProviderTest.class);
413
		addTestSuite(SelectionProviderMultiSelectionObservableListTest.class);
418
		addTestSuite(SelectionProviderMultiSelectionObservableListTest.class);
(-)src/org/eclipse/core/tests/databinding/beans/PojoObservablesTest.java (-18 / +16 lines)
Lines 7-16 Link Here
7
 *
7
 *
8
 * Contributors:
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
9
 *     IBM Corporation - initial API and implementation
10
 *     Matthew Hall - bug 194734
10
 *******************************************************************************/
11
 *******************************************************************************/
11
12
12
package org.eclipse.core.tests.databinding.beans;
13
package org.eclipse.core.tests.databinding.beans;
13
14
15
import org.eclipse.core.databinding.beans.IBeanObservable;
14
import org.eclipse.core.databinding.beans.PojoObservables;
16
import org.eclipse.core.databinding.beans.PojoObservables;
15
import org.eclipse.core.databinding.observable.Realm;
17
import org.eclipse.core.databinding.observable.Realm;
16
import org.eclipse.core.databinding.observable.list.IObservableList;
18
import org.eclipse.core.databinding.observable.list.IObservableList;
Lines 19-28 Link Here
19
import org.eclipse.core.databinding.observable.set.IObservableSet;
21
import org.eclipse.core.databinding.observable.set.IObservableSet;
20
import org.eclipse.core.databinding.observable.set.WritableSet;
22
import org.eclipse.core.databinding.observable.set.WritableSet;
21
import org.eclipse.core.databinding.observable.value.IObservableValue;
23
import org.eclipse.core.databinding.observable.value.IObservableValue;
22
import org.eclipse.core.internal.databinding.beans.JavaBeanObservableList;
23
import org.eclipse.core.internal.databinding.beans.JavaBeanObservableMap;
24
import org.eclipse.core.internal.databinding.beans.JavaBeanObservableSet;
25
import org.eclipse.core.internal.databinding.beans.JavaBeanObservableValue;
26
import org.eclipse.core.tests.internal.databinding.beans.Bean;
24
import org.eclipse.core.tests.internal.databinding.beans.Bean;
27
import org.eclipse.jface.databinding.conformance.util.ChangeEventTracker;
25
import org.eclipse.jface.databinding.conformance.util.ChangeEventTracker;
28
import org.eclipse.jface.databinding.conformance.util.CurrentRealm;
26
import org.eclipse.jface.databinding.conformance.util.CurrentRealm;
Lines 47-58 Link Here
47
		propertyName = "value";
45
		propertyName = "value";
48
	}
46
	}
49
47
50
	public void testObserveValue_ReturnsJavaBeanObservableValue()
48
	public void testObserveValue_ReturnsIBeanObservable()
51
			throws Exception {
49
			throws Exception {
52
		IObservableValue value = PojoObservables.observeValue(pojo, propertyName);
50
		IObservableValue value = PojoObservables.observeValue(pojo, propertyName);
53
51
54
		assertNotNull(value);
52
		assertNotNull(value);
55
		assertTrue(value instanceof JavaBeanObservableValue);
53
		assertTrue(value instanceof IBeanObservable);
56
	}
54
	}
57
55
58
	public void testObserveValue_DoesNotAttachListeners() throws Exception {
56
	public void testObserveValue_DoesNotAttachListeners() throws Exception {
Lines 62-78 Link Here
62
		assertFalse(pojo.hasListeners(propertyName));
60
		assertFalse(pojo.hasListeners(propertyName));
63
	}
61
	}
64
62
65
	public void testObservableValueWithRealm_ReturnsJavaBeanObservable()
63
	public void testObservableValueWithRealm_ReturnsIBeanObservable()
66
			throws Exception {
64
			throws Exception {
67
		CurrentRealm realm = new CurrentRealm(true);
65
		CurrentRealm realm = new CurrentRealm(true);
68
		IObservableValue value = PojoObservables.observeValue(realm, pojo,
66
		IObservableValue value = PojoObservables.observeValue(realm, pojo,
69
				propertyName);
67
				propertyName);
70
68
71
		assertNotNull(value);
69
		assertNotNull(value);
72
		assertTrue(value instanceof JavaBeanObservableValue);
70
		assertTrue(value instanceof IBeanObservable);
73
	}
71
	}
74
72
75
	public void testObservableMap_ReturnsJavaBeanObservableMap()
73
	public void testObservableMap_ReturnsIBeanObservable()
76
			throws Exception {
74
			throws Exception {
77
		IObservableSet set = new WritableSet();
75
		IObservableSet set = new WritableSet();
78
		set.add(new Bean());
76
		set.add(new Bean());
Lines 80-86 Link Here
80
		IObservableMap map = PojoObservables.observeMap(set, Bean.class,
78
		IObservableMap map = PojoObservables.observeMap(set, Bean.class,
81
				propertyName);
79
				propertyName);
82
		assertNotNull(map);
80
		assertNotNull(map);
83
		assertTrue(map instanceof JavaBeanObservableMap);
81
		assertTrue(map instanceof IBeanObservable);
84
	}
82
	}
85
	
83
	
86
	public void testObservableMap_DoesNotAttachListeners() throws Exception {
84
	public void testObservableMap_DoesNotAttachListeners() throws Exception {
Lines 101-109 Link Here
101
		assertEquals(2, maps.length);
99
		assertEquals(2, maps.length);
102
	}
100
	}
103
	
101
	
104
	public void testObserveListWithElementType_ReturnsJavaBeanObservableList() throws Exception {
102
	public void testObserveListWithElementType_ReturnsIBeanObservable() throws Exception {
105
		IObservableList list = PojoObservables.observeList(Realm.getDefault(), pojo, "list", String.class);
103
		IObservableList list = PojoObservables.observeList(Realm.getDefault(), pojo, "list", String.class);
106
		assertTrue(list instanceof JavaBeanObservableList);
104
		assertTrue(list instanceof IBeanObservable);
107
	}
105
	}
108
	
106
	
109
	public void testObserveListWithElementType_DoesNotAttachListeners() throws Exception {
107
	public void testObserveListWithElementType_DoesNotAttachListeners() throws Exception {
Lines 113-121 Link Here
113
		assertFalse(pojo.hasListeners("list"));
111
		assertFalse(pojo.hasListeners("list"));
114
	}
112
	}
115
	
113
	
116
	public void testObserveList_ReturnsJavaBeanObservableList() throws Exception {
114
	public void testObserveList_ReturnsIBeanObservable() throws Exception {
117
		IObservableList observable = PojoObservables.observeList(Realm.getDefault(), pojo, "list");
115
		IObservableList observable = PojoObservables.observeList(Realm.getDefault(), pojo, "list");
118
		assertTrue(observable instanceof JavaBeanObservableList);
116
		assertTrue(observable instanceof IBeanObservable);
119
	}
117
	}
120
	
118
	
121
	public void testObserveList_DoesNotAttachListeners() throws Exception {
119
	public void testObserveList_DoesNotAttachListeners() throws Exception {
Lines 125-133 Link Here
125
		assertFalse(pojo.hasListeners("list"));
123
		assertFalse(pojo.hasListeners("list"));
126
	}
124
	}
127
	
125
	
128
	public void testObserveSetWithElementType_ReturnsJavaBeanObservableList() throws Exception {
126
	public void testObserveSetWithElementType_ReturnsIBeanObservable() throws Exception {
129
		IObservableSet list = PojoObservables.observeSet(Realm.getDefault(), pojo, "set", String.class);
127
		IObservableSet list = PojoObservables.observeSet(Realm.getDefault(), pojo, "set", String.class);
130
		assertTrue(list instanceof JavaBeanObservableSet);
128
		assertTrue(list instanceof IBeanObservable);
131
	}
129
	}
132
	
130
	
133
	public void testObserveSetWithElementType_DoesNotAttachListeners() throws Exception {
131
	public void testObserveSetWithElementType_DoesNotAttachListeners() throws Exception {
Lines 137-145 Link Here
137
		assertFalse(pojo.hasListeners("set"));
135
		assertFalse(pojo.hasListeners("set"));
138
	}
136
	}
139
	
137
	
140
	public void testObserveSet_ReturnsJavaBeanObservableList() throws Exception {
138
	public void testObserveSet_ReturnsIBeanObservable() throws Exception {
141
		IObservableSet list = PojoObservables.observeSet(Realm.getDefault(), pojo, "set");
139
		IObservableSet list = PojoObservables.observeSet(Realm.getDefault(), pojo, "set");
142
		assertTrue(list instanceof JavaBeanObservableSet);
140
		assertTrue(list instanceof IBeanObservable);
143
	}
141
	}
144
	
142
	
145
	public void testObserveSet_DoesNotAttachListeners() throws Exception {
143
	public void testObserveSet_DoesNotAttachListeners() throws Exception {
(-)src/org/eclipse/jface/tests/databinding/viewers/ViewersObservablesTest.java (-4 / +11 lines)
Lines 7-21 Link Here
7
 *
7
 *
8
 * Contributors:
8
 * Contributors:
9
 *     Matthew Hall - initial API and implementation (bug 206839)
9
 *     Matthew Hall - initial API and implementation (bug 206839)
10
 *     Matthew Hall - bug 194734
10
 ******************************************************************************/
11
 ******************************************************************************/
11
12
12
package org.eclipse.jface.tests.databinding.viewers;
13
package org.eclipse.jface.tests.databinding.viewers;
13
14
15
import org.eclipse.core.databinding.observable.IDecoratingObservable;
14
import org.eclipse.core.databinding.observable.Realm;
16
import org.eclipse.core.databinding.observable.Realm;
15
import org.eclipse.core.databinding.observable.value.IObservableValue;
17
import org.eclipse.core.databinding.property.IPropertyObservable;
16
import org.eclipse.jface.databinding.swt.SWTObservables;
18
import org.eclipse.jface.databinding.swt.SWTObservables;
19
import org.eclipse.jface.databinding.viewers.IViewerObservableValue;
17
import org.eclipse.jface.databinding.viewers.ViewersObservables;
20
import org.eclipse.jface.databinding.viewers.ViewersObservables;
18
import org.eclipse.jface.internal.databinding.viewers.ViewerInputObservableValue;
21
import org.eclipse.jface.internal.databinding.viewers.ViewerInputProperty;
19
import org.eclipse.jface.tests.databinding.AbstractDefaultRealmTestCase;
22
import org.eclipse.jface.tests.databinding.AbstractDefaultRealmTestCase;
20
import org.eclipse.jface.viewers.TableViewer;
23
import org.eclipse.jface.viewers.TableViewer;
21
import org.eclipse.swt.SWT;
24
import org.eclipse.swt.SWT;
Lines 48-54 Link Here
48
	}
51
	}
49
52
50
	public void testObserveInput_InstanceOfViewerInputObservableValue() {
53
	public void testObserveInput_InstanceOfViewerInputObservableValue() {
51
		IObservableValue observable = ViewersObservables.observeInput(viewer);
54
		IViewerObservableValue observable = (IViewerObservableValue) ViewersObservables
52
		assertTrue(observable instanceof ViewerInputObservableValue);
55
				.observeInput(viewer);
56
		assertTrue(observable.getViewer() == viewer);
57
		IPropertyObservable propertyObservable = (IPropertyObservable) ((IDecoratingObservable) observable)
58
				.getDecorated();
59
		assertTrue(propertyObservable.getProperty() instanceof ViewerInputProperty);
53
	}
60
	}
54
}
61
}
(-)src/org/eclipse/jface/tests/internal/databinding/viewers/ViewerInputObservableValueTest.java (-18 / +22 lines)
Lines 7-13 Link Here
7
 *
7
 *
8
 * Contributors:
8
 * Contributors:
9
 *    Matthew Hall - initial API and implementation (bug 206839)
9
 *    Matthew Hall - initial API and implementation (bug 206839)
10
 *     Matthew Hall - bug 213145
10
 *     Matthew Hall - bug 213145, 194734
11
 *******************************************************************************/
11
 *******************************************************************************/
12
package org.eclipse.jface.tests.internal.databinding.viewers;
12
package org.eclipse.jface.tests.internal.databinding.viewers;
13
13
Lines 21-27 Link Here
21
import org.eclipse.jface.databinding.conformance.MutableObservableValueContractTest;
21
import org.eclipse.jface.databinding.conformance.MutableObservableValueContractTest;
22
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
22
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
23
import org.eclipse.jface.databinding.conformance.util.ValueChangeEventTracker;
23
import org.eclipse.jface.databinding.conformance.util.ValueChangeEventTracker;
24
import org.eclipse.jface.internal.databinding.viewers.ViewerInputObservableValue;
24
import org.eclipse.jface.databinding.viewers.ViewerProperties;
25
import org.eclipse.jface.databinding.viewers.ViewersObservables;
25
import org.eclipse.jface.tests.databinding.AbstractDefaultRealmTestCase;
26
import org.eclipse.jface.tests.databinding.AbstractDefaultRealmTestCase;
26
import org.eclipse.jface.viewers.IStructuredContentProvider;
27
import org.eclipse.jface.viewers.IStructuredContentProvider;
27
import org.eclipse.jface.viewers.TableViewer;
28
import org.eclipse.jface.viewers.TableViewer;
Lines 55-88 Link Here
55
56
56
	public void testConstructor_IllegalArgumentException() {
57
	public void testConstructor_IllegalArgumentException() {
57
		try {
58
		try {
58
			new ViewerInputObservableValue(Realm.getDefault(), null);
59
			ViewersObservables.observeInput(null);
59
			fail("Expected IllegalArgumentException for null argument");
60
			fail("Expected IllegalArgumentException for null argument");
60
		} catch (IllegalArgumentException expected) {
61
		} catch (IllegalArgumentException expected) {
61
		}
62
		}
62
	}
63
	}
63
64
64
	public void testSetInputOnViewer_FiresNoChangeEvents() {
65
	public void testSetInputOnViewer_FiresChangeEventOnGetValue() {
65
		IObservableValue observable = new ViewerInputObservableValue(Realm
66
		IObservableValue observable = ViewersObservables.observeInput(viewer);
66
				.getDefault(), viewer);
67
		ValueChangeEventTracker listener = ValueChangeEventTracker
67
		ValueChangeEventTracker listener = ValueChangeEventTracker.observe(observable);
68
				.observe(observable);
68
69
69
		assertNull(viewer.getInput());
70
		assertNull(viewer.getInput());
70
		assertEquals(0, listener.count);
71
		assertEquals(0, listener.count);
71
72
72
		viewer.setInput(model);
73
		viewer.setInput(model);
73
74
74
		assertEquals(model, observable.getValue());
75
		assertEquals(model, viewer.getInput());
75
		assertEquals(0, listener.count);
76
		assertEquals(0, listener.count);
76
77
78
		// Call to getValue() causes observable to discover change
79
		assertEquals(model, observable.getValue());
80
		assertEquals(1, listener.count);
81
77
		viewer.setInput(null);
82
		viewer.setInput(null);
83
		assertEquals(null, viewer.getInput());
78
84
79
		assertEquals(null, observable.getValue());
85
		assertEquals(null, observable.getValue());
80
		assertEquals(0, listener.count);
86
		assertEquals(2, listener.count);
81
	}
87
	}
82
88
83
	public void testGetSetValue_FiresChangeEvents() {
89
	public void testGetSetValue_FiresChangeEvents() {
84
		IObservableValue observable = new ViewerInputObservableValue(Realm
90
		IObservableValue observable = ViewersObservables.observeInput(viewer);
85
				.getDefault(), viewer);
86
		ValueChangeEventTracker listener = new ValueChangeEventTracker();
91
		ValueChangeEventTracker listener = new ValueChangeEventTracker();
87
		observable.addValueChangeListener(listener);
92
		observable.addValueChangeListener(listener);
88
93
Lines 103-116 Link Here
103
	}
108
	}
104
109
105
	public void testGetValueType_AlwaysNull() throws Exception {
110
	public void testGetValueType_AlwaysNull() throws Exception {
106
		IObservableValue observable = new ViewerInputObservableValue(Realm
111
		IObservableValue observable = ViewersObservables.observeInput(viewer);
107
				.getDefault(), viewer);
108
		assertEquals(null, observable.getValueType());
112
		assertEquals(null, observable.getValueType());
109
	}
113
	}
110
114
111
	public void testDispose() throws Exception {
115
	public void testDispose() throws Exception {
112
		IObservableValue observable = new ViewerInputObservableValue(Realm
116
		IObservableValue observable = ViewersObservables.observeInput(viewer);
113
				.getDefault(), viewer);
114
		observable.dispose();
117
		observable.dispose();
115
		assertNull(observable.getRealm());
118
		assertNull(observable.getRealm());
116
		try {
119
		try {
Lines 141-147 Link Here
141
	}
144
	}
142
145
143
	public static Test suite() {
146
	public static Test suite() {
144
		TestSuite suite = new TestSuite(ViewerInputObservableValueTest.class.getName());
147
		TestSuite suite = new TestSuite(ViewerInputObservableValueTest.class
148
				.getName());
145
		suite.addTestSuite(ViewerInputObservableValueTest.class);
149
		suite.addTestSuite(ViewerInputObservableValueTest.class);
146
		suite.addTest(MutableObservableValueContractTest.suite(new Delegate()));
150
		suite.addTest(MutableObservableValueContractTest.suite(new Delegate()));
147
		return suite;
151
		return suite;
Lines 165-175 Link Here
165
		}
169
		}
166
170
167
		public IObservableValue createObservableValue(Realm realm) {
171
		public IObservableValue createObservableValue(Realm realm) {
168
			return new ViewerInputObservableValue(realm, viewer);
172
			return ViewerProperties.input().observeValue(realm, viewer);
169
		}
173
		}
170
174
171
		public void change(IObservable observable) {
175
		public void change(IObservable observable) {
172
			IObservableValue value = (IObservableValue)observable;
176
			IObservableValue value = (IObservableValue) observable;
173
			value.setValue(createValue(value));
177
			value.setValue(createValue(value));
174
		}
178
		}
175
179
(-)src/org/eclipse/jface/tests/internal/databinding/viewers/SelectionProviderMultiSelectionObservableListTest.java (-43 / +46 lines)
Lines 8-22 Link Here
8
 * Contributors:
8
 * Contributors:
9
 *    Brad Reynolds - initial API and implementation
9
 *    Brad Reynolds - initial API and implementation
10
 *     Brad Reynolds - bug 116920
10
 *     Brad Reynolds - bug 116920
11
 *     Matthew Hall - bug 194734
11
 *******************************************************************************/
12
 *******************************************************************************/
12
package org.eclipse.jface.tests.internal.databinding.viewers;
13
package org.eclipse.jface.tests.internal.databinding.viewers;
13
14
15
import java.util.ArrayList;
16
import java.util.Arrays;
17
import java.util.Collections;
18
import java.util.List;
19
14
import junit.framework.TestCase;
20
import junit.framework.TestCase;
15
21
16
import org.eclipse.core.databinding.observable.list.ListDiffEntry;
22
import org.eclipse.core.databinding.observable.list.IObservableList;
23
import org.eclipse.core.databinding.observable.list.ListDiff;
17
import org.eclipse.jface.databinding.conformance.util.ListChangeEventTracker;
24
import org.eclipse.jface.databinding.conformance.util.ListChangeEventTracker;
18
import org.eclipse.jface.databinding.swt.SWTObservables;
25
import org.eclipse.jface.databinding.viewers.ViewersObservables;
19
import org.eclipse.jface.internal.databinding.viewers.SelectionProviderMultipleSelectionObservableList;
20
import org.eclipse.jface.viewers.ISelectionProvider;
26
import org.eclipse.jface.viewers.ISelectionProvider;
21
import org.eclipse.jface.viewers.IStructuredContentProvider;
27
import org.eclipse.jface.viewers.IStructuredContentProvider;
22
import org.eclipse.jface.viewers.IStructuredSelection;
28
import org.eclipse.jface.viewers.IStructuredSelection;
Lines 24-30 Link Here
24
import org.eclipse.jface.viewers.TableViewer;
30
import org.eclipse.jface.viewers.TableViewer;
25
import org.eclipse.jface.viewers.Viewer;
31
import org.eclipse.jface.viewers.Viewer;
26
import org.eclipse.swt.SWT;
32
import org.eclipse.swt.SWT;
27
import org.eclipse.swt.widgets.Display;
28
import org.eclipse.swt.widgets.Shell;
33
import org.eclipse.swt.widgets.Shell;
29
34
30
/**
35
/**
Lines 37-43 Link Here
37
42
38
	private TableViewer viewer;
43
	private TableViewer viewer;
39
44
40
	private static String[] model = new String[] { "0", "1", "2", "3" };
45
	private static String[] model = new String[] { "element0", "element1",
46
			"element2", "element3" };
41
47
42
	protected void setUp() throws Exception {
48
	protected void setUp() throws Exception {
43
		Shell shell = new Shell();
49
		Shell shell = new Shell();
Lines 55-62 Link Here
55
61
56
	public void testConstructorIllegalArgumentException() {
62
	public void testConstructorIllegalArgumentException() {
57
		try {
63
		try {
58
			new SelectionProviderMultipleSelectionObservableList(SWTObservables
64
			ViewersObservables.observeMultiSelection(null);
59
					.getRealm(Display.getDefault()), null, Object.class);
60
			fail();
65
			fail();
61
		} catch (IllegalArgumentException e) {
66
		} catch (IllegalArgumentException e) {
62
		}
67
		}
Lines 70-86 Link Here
70
	 * </ul>
75
	 * </ul>
71
	 */
76
	 */
72
	public void testAddRemove() {
77
	public void testAddRemove() {
73
		SelectionProviderMultipleSelectionObservableList observable = new SelectionProviderMultipleSelectionObservableList(
78
		IObservableList observable = ViewersObservables
74
				SWTObservables.getRealm(Display.getDefault()),
79
				.observeMultiSelection(selectionProvider);
75
				selectionProvider, Object.class);
76
		ListChangeEventTracker listener = new ListChangeEventTracker();
80
		ListChangeEventTracker listener = new ListChangeEventTracker();
77
		observable.addListChangeListener(listener);
81
		observable.addListChangeListener(listener);
78
		assertEquals(0, observable.size());
82
		assertEquals(0, observable.size());
79
83
80
		selectionProvider.setSelection(new StructuredSelection(model[0]));
84
		selectionProvider.setSelection(new StructuredSelection(model[0]));
81
		assertEquals(1, listener.count);
85
		assertEquals(1, listener.count);
82
		assertEquals(1, listener.event.diff.getDifferences().length);
86
		assertDiff(listener.event.diff, Collections.EMPTY_LIST, Collections
83
		assertDiffEntry(listener.event.diff.getDifferences()[0], 0, model[0], true);
87
				.singletonList(model[0]));
84
		assertEquals(observable, listener.event.getObservableList());
88
		assertEquals(observable, listener.event.getObservableList());
85
		assertEquals(1, observable.size());
89
		assertEquals(1, observable.size());
86
		assertEquals(model[0], observable.get(0));
90
		assertEquals(model[0], observable.get(0));
Lines 88-155 Link Here
88
		selectionProvider.setSelection(new StructuredSelection(model[1]));
92
		selectionProvider.setSelection(new StructuredSelection(model[1]));
89
		assertEquals(2, listener.count);
93
		assertEquals(2, listener.count);
90
		assertEquals(2, listener.event.diff.getDifferences().length);
94
		assertEquals(2, listener.event.diff.getDifferences().length);
91
		assertDiffEntry(listener.event.diff.getDifferences()[0], 0, model[1], true);
95
		assertDiff(listener.event.diff, Collections.singletonList(model[0]),
92
		assertDiffEntry(listener.event.diff.getDifferences()[1], 1, model[0], false);
96
				Collections.singletonList(model[1]));
93
		assertEquals(observable, listener.event.getObservableList());
97
		assertEquals(observable, listener.event.getObservableList());
94
		assertEquals(1, observable.size());
98
		assertEquals(1, observable.size());
95
		assertEquals(model[1], observable.get(0));
99
		assertEquals(model[1], observable.get(0));
96
100
97
		selectionProvider.setSelection(new StructuredSelection(new Object[]{model[2],model[3]}));
101
		selectionProvider.setSelection(new StructuredSelection(new Object[] {
102
				model[2], model[3] }));
98
		assertEquals(3, listener.count);
103
		assertEquals(3, listener.count);
99
		assertEquals(3, listener.event.diff.getDifferences().length);
104
		assertEquals(3, listener.event.diff.getDifferences().length);
100
		assertDiffEntry(listener.event.diff.getDifferences()[0], 0, model[2], true);
105
		assertDiff(listener.event.diff, Collections.singletonList(model[1]),
101
		assertDiffEntry(listener.event.diff.getDifferences()[1], 1, model[3], true);
106
				Arrays.asList(new Object[] { model[2], model[3] }));
102
		assertDiffEntry(listener.event.diff.getDifferences()[2], 2, model[1], false);
103
		assertEquals(observable, listener.event.getObservableList());
107
		assertEquals(observable, listener.event.getObservableList());
104
		assertEquals(2, observable.size());
108
		assertEquals(2, observable.size());
105
		assertEquals(model[2], observable.get(0));
109
		assertEquals(model[2], observable.get(0));
106
		assertEquals(model[3], observable.get(1));
110
		assertEquals(model[3], observable.get(1));
107
		
111
108
		selectionProvider.setSelection(StructuredSelection.EMPTY);
112
		selectionProvider.setSelection(StructuredSelection.EMPTY);
109
		assertEquals(4, listener.count);
113
		assertEquals(4, listener.count);
110
		assertEquals(2, listener.event.diff.getDifferences().length);
114
		assertEquals(2, listener.event.diff.getDifferences().length);
111
		assertDiffEntry(listener.event.diff.getDifferences()[0], 1, model[3], false);
115
		assertDiff(listener.event.diff, Arrays.asList(new Object[] { model[2],
112
		assertDiffEntry(listener.event.diff.getDifferences()[1], 0, model[2], false);
116
				model[3] }), Collections.EMPTY_LIST);
113
		assertEquals(observable, listener.event.getObservableList());
117
		assertEquals(observable, listener.event.getObservableList());
114
		assertEquals(0, observable.size());
118
		assertEquals(0, observable.size());
115
		
119
116
		observable.add(model[1]);
120
		observable.add(model[1]);
117
		assertEquals(5, listener.count);
121
		assertEquals(5, listener.count);
118
		assertEquals(1, listener.event.diff.getDifferences().length);
122
		assertEquals(1, listener.event.diff.getDifferences().length);
119
		assertDiffEntry(listener.event.diff.getDifferences()[0], 0, model[1], true);
123
		assertDiff(listener.event.diff, Collections.EMPTY_LIST, Collections
124
				.singletonList(model[1]));
120
		assertEquals(observable, listener.event.getObservableList());
125
		assertEquals(observable, listener.event.getObservableList());
121
		assertEquals(1, ((IStructuredSelection)viewer.getSelection()).size());
126
		assertEquals(1, ((IStructuredSelection) viewer.getSelection()).size());
122
127
123
		observable.add(0, model[2]);
128
		observable.add(0, model[2]);
124
		assertEquals(6, listener.count);
129
		assertEquals(6, listener.count);
125
		assertEquals(1, listener.event.diff.getDifferences().length);
130
		assertEquals(1, listener.event.diff.getDifferences().length);
126
		// This is a bit surprising (we added at index 0 but the event says index 1).
131
		// This is a bit surprising (we added at index 0 but the event says
127
		// It is to the fact that the observable list tracks the underlying selection
132
		// index 1).
133
		// It is to the fact that the observable list tracks the underlying
134
		// selection
128
		// provider's notion of which element is at which index.
135
		// provider's notion of which element is at which index.
129
		assertDiffEntry(listener.event.diff.getDifferences()[0], 1, model[2], true);
136
		assertDiff(listener.event.diff, Collections.singletonList(model[1]),
137
				Arrays.asList(new Object[] { model[2], model[1] }));
130
		assertEquals(observable, listener.event.getObservableList());
138
		assertEquals(observable, listener.event.getObservableList());
131
		assertEquals(2, ((IStructuredSelection)viewer.getSelection()).size());
139
		assertEquals(2, ((IStructuredSelection) viewer.getSelection()).size());
132
140
133
		observable.clear();
141
		observable.clear();
134
		assertEquals(7, listener.count);
142
		assertEquals(7, listener.count);
135
		assertEquals(2, listener.event.diff.getDifferences().length);
143
		assertEquals(2, listener.event.diff.getDifferences().length);
136
		assertDiffEntry(listener.event.diff.getDifferences()[0], 1, model[2], false);
144
		assertDiff(listener.event.diff, Arrays.asList(new Object[] { model[1],
137
		assertDiffEntry(listener.event.diff.getDifferences()[1], 0, model[1], false);
145
				model[2] }), Collections.EMPTY_LIST);
138
		assertEquals(observable, listener.event.getObservableList());
146
		assertEquals(observable, listener.event.getObservableList());
139
		assertEquals(0, ((IStructuredSelection)viewer.getSelection()).size());
147
		assertEquals(0, ((IStructuredSelection) viewer.getSelection()).size());
140
}
148
	}
141
149
142
	/**
150
	private void assertDiff(ListDiff diff, List oldList, List newList) {
143
	 * @param diffEntry
151
		// defensive copy in case arg is unmodifiable
144
	 * @param position
152
		oldList = new ArrayList(oldList);
145
	 * @param element
153
		diff.applyTo(oldList);
146
	 * @param isAddition
154
		assertEquals("applying diff to list did not produce expected result",
147
	 */
155
				newList, oldList);
148
	private void assertDiffEntry(ListDiffEntry diffEntry, int position,
149
			String element, boolean isAddition) {
150
		assertEquals(isAddition, diffEntry.isAddition());
151
		assertEquals(position, diffEntry.getPosition());
152
		assertEquals(element, diffEntry.getElement());
153
	}
156
	}
154
157
155
	private class ContentProvider implements IStructuredContentProvider {
158
	private class ContentProvider implements IStructuredContentProvider {
(-)src/org/eclipse/jface/tests/internal/databinding/viewers/SelectionProviderSingleSelectionObservableValueTest.java (-11 / +8 lines)
Lines 9-29 Link Here
9
 *    Brad Reynolds - initial API and implementation
9
 *    Brad Reynolds - initial API and implementation
10
 *    Brad Reynolds - bug 116920
10
 *    Brad Reynolds - bug 116920
11
 *    Ashley Cambrell - bug 198906
11
 *    Ashley Cambrell - bug 198906
12
 *    Matthew Hall - bug 194734
12
 *******************************************************************************/
13
 *******************************************************************************/
13
package org.eclipse.jface.tests.internal.databinding.viewers;
14
package org.eclipse.jface.tests.internal.databinding.viewers;
14
15
15
import junit.framework.TestCase;
16
import junit.framework.TestCase;
16
17
18
import org.eclipse.core.databinding.observable.value.IObservableValue;
17
import org.eclipse.jface.databinding.conformance.util.ValueChangeEventTracker;
19
import org.eclipse.jface.databinding.conformance.util.ValueChangeEventTracker;
18
import org.eclipse.jface.databinding.swt.SWTObservables;
20
import org.eclipse.jface.databinding.viewers.ViewersObservables;
19
import org.eclipse.jface.internal.databinding.viewers.SelectionProviderSingleSelectionObservableValue;
20
import org.eclipse.jface.viewers.ISelectionProvider;
21
import org.eclipse.jface.viewers.ISelectionProvider;
21
import org.eclipse.jface.viewers.IStructuredContentProvider;
22
import org.eclipse.jface.viewers.IStructuredContentProvider;
22
import org.eclipse.jface.viewers.StructuredSelection;
23
import org.eclipse.jface.viewers.StructuredSelection;
23
import org.eclipse.jface.viewers.TableViewer;
24
import org.eclipse.jface.viewers.TableViewer;
24
import org.eclipse.jface.viewers.Viewer;
25
import org.eclipse.jface.viewers.Viewer;
25
import org.eclipse.swt.SWT;
26
import org.eclipse.swt.SWT;
26
import org.eclipse.swt.widgets.Display;
27
import org.eclipse.swt.widgets.Shell;
27
import org.eclipse.swt.widgets.Shell;
28
28
29
/**
29
/**
Lines 65-72 Link Here
65
65
66
	public void testConstructorIllegalArgumentException() {
66
	public void testConstructorIllegalArgumentException() {
67
		try {
67
		try {
68
			new SelectionProviderSingleSelectionObservableValue(SWTObservables
68
			ViewersObservables.observeSingleSelection(null);
69
					.getRealm(Display.getDefault()), null);
70
			fail();
69
			fail();
71
		} catch (IllegalArgumentException e) {
70
		} catch (IllegalArgumentException e) {
72
		}
71
		}
Lines 80-88 Link Here
80
	 * </ul>
79
	 * </ul>
81
	 */
80
	 */
82
	public void testGetSetValue() {
81
	public void testGetSetValue() {
83
		SelectionProviderSingleSelectionObservableValue observable = new SelectionProviderSingleSelectionObservableValue(
82
		IObservableValue observable = ViewersObservables
84
				SWTObservables.getRealm(Display.getDefault()),
83
				.observeSingleSelection(selectionProvider);
85
				selectionProvider);
86
		ValueChangeEventTracker listener = new ValueChangeEventTracker();
84
		ValueChangeEventTracker listener = new ValueChangeEventTracker();
87
		observable.addValueChangeListener(listener);
85
		observable.addValueChangeListener(listener);
88
		assertNull(observable.getValue());
86
		assertNull(observable.getValue());
Lines 110-118 Link Here
110
	}
108
	}
111
109
112
	public void testDispose() throws Exception {
110
	public void testDispose() throws Exception {
113
		SelectionProviderSingleSelectionObservableValue observable = new SelectionProviderSingleSelectionObservableValue(
111
		IObservableValue observable = ViewersObservables
114
				SWTObservables.getRealm(Display.getDefault()),
112
				.observeSingleSelection(selectionProvider);
115
				selectionProvider);
116
		ValueChangeEventTracker listener = new ValueChangeEventTracker();
113
		ValueChangeEventTracker listener = new ValueChangeEventTracker();
117
		observable.addValueChangeListener(listener);
114
		observable.addValueChangeListener(listener);
118
115
(-)src/org/eclipse/core/tests/databinding/conversion/StringToNumberConverterTest.java (-1 / +1 lines)
Lines 112-118 Link Here
112
		assertEquals("Non-integer BigDecimal", input, result);
112
		assertEquals("Non-integer BigDecimal", input, result);
113
113
114
		// Test 2: Long
114
		// Test 2: Long
115
		input = new BigDecimal((long) (Integer.MAX_VALUE + 100));
115
		input = new BigDecimal(Integer.MAX_VALUE + 100L);
116
		result = (BigDecimal) converter.convert(formatBigDecimal(input));
116
		result = (BigDecimal) converter.convert(formatBigDecimal(input));
117
		assertEquals("Integral BigDecimal in long range", input, result);
117
		assertEquals("Integral BigDecimal in long range", input, result);
118
118
(-)src/org/eclipse/jface/tests/internal/databinding/swt/StyledTextObservableValueFocusOutTest.java (+80 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Code 9 Corporation and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Code 9 Corporation - initial API and implementation
10
 *     Chris Aniszczyk <zx@code9.com> - bug 131435
11
 *     Matthew Hall - bug 194734
12
 *******************************************************************************/
13
14
package org.eclipse.jface.tests.internal.databinding.swt;
15
16
import junit.framework.Test;
17
import junit.framework.TestCase;
18
import junit.framework.TestSuite;
19
20
import org.eclipse.core.databinding.observable.IObservable;
21
import org.eclipse.core.databinding.observable.Realm;
22
import org.eclipse.core.databinding.observable.value.IObservableValue;
23
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
24
import org.eclipse.jface.databinding.conformance.swt.SWTMutableObservableValueContractTest;
25
import org.eclipse.jface.databinding.swt.StyledTextProperties;
26
import org.eclipse.swt.SWT;
27
import org.eclipse.swt.custom.StyledText;
28
import org.eclipse.swt.widgets.Shell;
29
30
/**
31
 * Tests for the FocusOut version of StyledTextObservableValue.
32
 */
33
public class StyledTextObservableValueFocusOutTest extends TestCase {
34
	public static Test suite() {
35
		TestSuite suite = new TestSuite(
36
				StyledTextObservableValueFocusOutTest.class.toString());
37
		suite.addTest(SWTMutableObservableValueContractTest
38
				.suite(new Delegate()));
39
		return suite;
40
	}
41
42
	/* package */static class Delegate extends
43
			AbstractObservableValueContractDelegate {
44
		private Shell shell;
45
46
		private StyledText text;
47
48
		public void setUp() {
49
			shell = new Shell();
50
			text = new StyledText(shell, SWT.NONE);
51
		}
52
53
		public void tearDown() {
54
			shell.dispose();
55
		}
56
57
		public IObservableValue createObservableValue(Realm realm) {
58
			return StyledTextProperties.text(SWT.FocusOut).observeValue(realm,
59
					text);
60
		}
61
62
		public Object getValueType(IObservableValue observable) {
63
			return String.class;
64
		}
65
66
		public void change(IObservable observable) {
67
			text.setFocus();
68
69
			IObservableValue observableValue = (IObservableValue) observable;
70
			text.setText((String) createValue(observableValue));
71
72
			text.notifyListeners(SWT.FocusOut, null);
73
		}
74
75
		public Object createValue(IObservableValue observable) {
76
			String value = (String) observable.getValue();
77
			return value + "a";
78
		}
79
	}
80
}
(-)src/org/eclipse/jface/tests/internal/databinding/swt/StyledTextObservableValueTest.java (+112 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Code 9 Corporation and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Code 9 Corporation - initial API and implementation
10
 *     Chris Aniszczyk <zx@code9.com> - bug 131435
11
 *     Matthew Hall - bug 194734
12
 *******************************************************************************/
13
14
package org.eclipse.jface.tests.internal.databinding.swt;
15
16
import org.eclipse.core.databinding.observable.value.IObservableValue;
17
import org.eclipse.jface.databinding.conformance.util.ValueChangeEventTracker;
18
import org.eclipse.jface.databinding.swt.SWTObservables;
19
import org.eclipse.jface.internal.databinding.swt.StyledTextTextProperty;
20
import org.eclipse.jface.tests.databinding.AbstractDefaultRealmTestCase;
21
import org.eclipse.swt.SWT;
22
import org.eclipse.swt.custom.StyledText;
23
import org.eclipse.swt.widgets.Shell;
24
25
/**
26
 * Tests to assert the inputs of the StyledTextObservableValue constructor.
27
 */
28
public class StyledTextObservableValueTest extends AbstractDefaultRealmTestCase {
29
	private StyledText text;
30
	private ValueChangeEventTracker listener;
31
32
	protected void setUp() throws Exception {
33
		super.setUp();
34
35
		Shell shell = new Shell();
36
		text = new StyledText(shell, SWT.NONE);
37
38
		listener = new ValueChangeEventTracker();
39
	}
40
41
	/**
42
	 * Asserts that only valid SWT event types are accepted on construction of
43
	 * StyledTextObservableValue.
44
	 */
45
	public void testConstructorUpdateEventTypes() {
46
		try {
47
			new StyledTextTextProperty(SWT.NONE);
48
			new StyledTextTextProperty(SWT.FocusOut);
49
			new StyledTextTextProperty(SWT.Modify);
50
			assertTrue(true);
51
		} catch (IllegalArgumentException e) {
52
			fail();
53
		}
54
55
		try {
56
			new StyledTextTextProperty(SWT.Verify);
57
			fail();
58
		} catch (IllegalArgumentException e) {
59
			assertTrue(true);
60
		}
61
	}
62
63
	/**
64
	 * s
65
	 * 
66
	 * @throws Exception
67
	 */
68
	public void testGetValueBeforeFocusOutChangeEventsFire() throws Exception {
69
		IObservableValue observableValue = SWTObservables.observeText(text,
70
				SWT.FocusOut);
71
		observableValue.addValueChangeListener(listener);
72
73
		String a = "a";
74
		String b = "b";
75
76
		text.setText(a);
77
		
78
		// fetching the value updates the buffered value
79
		assertEquals(a, observableValue.getValue()); 
80
		assertEquals(1, listener.count);
81
82
		text.setText(b);
83
84
		text.notifyListeners(SWT.FocusOut, null);
85
86
		assertEquals(2, listener.count);
87
		assertEquals(a, listener.event.diff.getOldValue());
88
		assertEquals(b, listener.event.diff.getNewValue());
89
	}
90
91
	public void testDispose() throws Exception {
92
		IObservableValue observableValue = SWTObservables.observeText(text,
93
				SWT.Modify);
94
		ValueChangeEventTracker testCounterValueChangeListener = new ValueChangeEventTracker();
95
		observableValue.addValueChangeListener(testCounterValueChangeListener);
96
97
		String expected1 = "Test123";
98
		text.setText(expected1);
99
100
		assertEquals(1, testCounterValueChangeListener.count);
101
		assertEquals(expected1, text.getText());
102
		assertEquals(expected1, observableValue.getValue());
103
104
		observableValue.dispose();
105
106
		String expected2 = "NewValue123";
107
		text.setText(expected2);
108
109
		assertEquals(1, testCounterValueChangeListener.count);
110
		assertEquals(expected2, text.getText());
111
	}
112
}
(-)src/org/eclipse/core/tests/internal/databinding/beans/BeanValuePropertyTest.java (+52 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 IBM Corporation and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
10
 ******************************************************************************/
11
12
package org.eclipse.core.tests.internal.databinding.beans;
13
14
import org.eclipse.core.databinding.beans.BeanProperties;
15
import org.eclipse.core.databinding.observable.value.IObservableValue;
16
import org.eclipse.core.databinding.observable.value.IValueChangeListener;
17
import org.eclipse.core.databinding.observable.value.ValueChangeEvent;
18
import org.eclipse.core.databinding.property.value.IValueProperty;
19
import org.eclipse.core.tests.internal.databinding.beans.BeanPropertyListenerSupportTest.GenericListenerBean;
20
import org.eclipse.jface.databinding.conformance.util.CurrentRealm;
21
import org.eclipse.jface.tests.databinding.AbstractDefaultRealmTestCase;
22
23
/**
24
 * @since 3.2
25
 * 
26
 */
27
public class BeanValuePropertyTest extends AbstractDefaultRealmTestCase {
28
	public void testChangeListenerIsOnlyNotifiedWhenWatchedPropertyChanges()
29
			throws Exception {
30
		GenericListenerBean bean = new GenericListenerBean();
31
		IValueProperty property = BeanProperties
32
				.value(GenericListenerBean.class, "value");
33
		class Listener implements IValueChangeListener {
34
			private int count = 0;
35
36
			public void handleValueChange(ValueChangeEvent event) {
37
				count++;
38
			}
39
		}
40
		Listener listener = new Listener();
41
42
		IObservableValue observable = property.observeValue(new CurrentRealm(true), bean);
43
		observable.addValueChangeListener(listener);
44
45
		assertEquals(0, listener.count);
46
		bean.setValue("1");
47
		assertEquals(1, listener.count);
48
49
		bean.setOther("2");
50
		assertEquals(1, listener.count);
51
	}
52
}
(-)src/org/eclipse/jface/tests/internal/databinding/swt/StyledTextObservableValueModifyTest.java (+78 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2008 Code 9 Corporation and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     Code 9 Corporation - initial API and implementation
10
 *     Chris Aniszczyk <zx@code9.com> - bug 131435
11
 *     Matthew Hall - bug 194734
12
 *******************************************************************************/
13
14
package org.eclipse.jface.tests.internal.databinding.swt;
15
16
import junit.framework.Test;
17
import junit.framework.TestCase;
18
import junit.framework.TestSuite;
19
20
import org.eclipse.core.databinding.observable.IObservable;
21
import org.eclipse.core.databinding.observable.Realm;
22
import org.eclipse.core.databinding.observable.value.IObservableValue;
23
import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate;
24
import org.eclipse.jface.databinding.conformance.swt.SWTMutableObservableValueContractTest;
25
import org.eclipse.jface.databinding.swt.StyledTextProperties;
26
import org.eclipse.swt.SWT;
27
import org.eclipse.swt.custom.StyledText;
28
import org.eclipse.swt.widgets.Shell;
29
30
/**
31
 * Tests for the Modify version of StyledTextObservableValue.
32
 */
33
public class StyledTextObservableValueModifyTest extends TestCase {
34
	public static Test suite() {
35
		TestSuite suite = new TestSuite(
36
				StyledTextObservableValueModifyTest.class.toString());
37
		suite.addTest(SWTMutableObservableValueContractTest
38
				.suite(new Delegate()));
39
		return suite;
40
	}
41
42
	/* package */static class Delegate extends
43
			AbstractObservableValueContractDelegate {
44
		private Shell shell;
45
46
		private StyledText text;
47
48
		public void setUp() {
49
			shell = new Shell();
50
			text = new StyledText(shell, SWT.NONE);
51
		}
52
53
		public void tearDown() {
54
			shell.dispose();
55
		}
56
57
		public IObservableValue createObservableValue(Realm realm) {
58
			return StyledTextProperties.text(SWT.Modify).observeValue(realm,
59
					text);
60
		}
61
62
		public Object getValueType(IObservableValue observable) {
63
			return String.class;
64
		}
65
66
		public void change(IObservable observable) {
67
			text.setFocus();
68
69
			IObservableValue observableValue = (IObservableValue) observable;
70
			text.setText((String) createValue(observableValue));
71
		}
72
73
		public Object createValue(IObservableValue observable) {
74
			String value = (String) observable.getValue();
75
			return value + "a";
76
		}
77
	}
78
}
(-)src/org/eclipse/core/tests/internal/databinding/beans/BeanPropertyListenerSupportTest.java (+208 lines)
Added Link Here
1
/*******************************************************************************
2
 * Copyright (c) 2007, 2008 IBM Corporation and others.
3
 * All rights reserved. This program and the accompanying materials
4
 * are made available under the terms of the Eclipse Public License v1.0
5
 * which accompanies this distribution, and is available at
6
 * http://www.eclipse.org/legal/epl-v10.html
7
 *
8
 * Contributors:
9
 *     IBM Corporation - initial API and implementation
10
 *******************************************************************************/
11
12
package org.eclipse.core.tests.internal.databinding.beans;
13
14
import java.beans.PropertyChangeEvent;
15
import java.beans.PropertyChangeListener;
16
import java.beans.PropertyChangeSupport;
17
18
import org.eclipse.core.databinding.util.ILogger;
19
import org.eclipse.core.databinding.util.Policy;
20
import org.eclipse.core.internal.databinding.beans.BeanPropertyListenerSupport;
21
import org.eclipse.core.runtime.IStatus;
22
import org.eclipse.jface.tests.databinding.AbstractDefaultRealmTestCase;
23
24
/**
25
 * @since 1.1
26
 */
27
public class BeanPropertyListenerSupportTest extends
28
		AbstractDefaultRealmTestCase {
29
	private PropertyChangeListenerStub listener;
30
	private String propertyName;
31
32
	protected void setUp() throws Exception {
33
		super.setUp();
34
35
		listener = new PropertyChangeListenerStub();
36
		propertyName = "value";
37
	}
38
39
	public void testAddPropertyChangeListenerWithPropertyName()
40
			throws Exception {
41
		SpecificListenerBean bean = new SpecificListenerBean();
42
43
		assertFalse(bean.changeSupport.hasListeners(propertyName));
44
45
		BeanPropertyListenerSupport.hookListener(bean, propertyName, listener);
46
		assertTrue("has listeners", bean.changeSupport
47
				.hasListeners(propertyName));
48
	}
49
50
	public void testAddPropertyChangeListenerWithoutPropertyName()
51
			throws Exception {
52
		GenericListenerBean bean = new GenericListenerBean();
53
54
		assertFalse(bean.changeSupport.hasListeners(propertyName));
55
56
		BeanPropertyListenerSupport.hookListener(bean, propertyName, listener);
57
		assertTrue("has listeners", bean.changeSupport
58
				.hasListeners(propertyName));
59
	}
60
61
	public void testLogStatusWhenAddPropertyChangeListenerMethodIsNotFound()
62
			throws Exception {
63
		class BeanStub {
64
		}
65
66
		class Log implements ILogger {
67
			int count;
68
			IStatus status;
69
70
			public void log(IStatus status) {
71
				count++;
72
				this.status = status;
73
			}
74
		}
75
76
		Log log = new Log();
77
		Policy.setLog(log);
78
79
		BeanStub bean = new BeanStub();
80
81
		assertEquals(0, log.count);
82
		BeanPropertyListenerSupport.hookListener(bean, "value", listener);
83
		assertEquals(1, log.count);
84
		assertEquals(IStatus.WARNING, log.status.getSeverity());
85
	}
86
87
	public void testRemovePropertyChangeListenerWithPropertyName()
88
			throws Exception {
89
		SpecificListenerBean bean = new SpecificListenerBean();
90
		BeanPropertyListenerSupport.hookListener(bean, propertyName, listener);
91
92
		assertTrue(bean.changeSupport.hasListeners(propertyName));
93
94
		BeanPropertyListenerSupport
95
				.unhookListener(bean, propertyName, listener);
96
		assertFalse("has listeners", bean.changeSupport
97
				.hasListeners(propertyName));
98
	}
99
100
	public void testRemovePropertyChangeListenerWithoutPropertyName()
101
			throws Exception {
102
		GenericListenerBean bean = new GenericListenerBean();
103
		BeanPropertyListenerSupport.hookListener(bean, propertyName, listener);
104
105
		assertTrue(bean.changeSupport.hasListeners(propertyName));
106
107
		BeanPropertyListenerSupport
108
				.unhookListener(bean, propertyName, listener);
109
		assertFalse("has listeners", bean.changeSupport
110
				.hasListeners(propertyName));
111
	}
112
113
	public void testLogStatusWhenRemovePropertyChangeListenerMethodIsNotFound()
114
			throws Exception {
115
		class InvalidBean {
116
		}
117
118
		class Log implements ILogger {
119
			int count;
120
			IStatus status;
121
122
			public void log(IStatus status) {
123
				count++;
124
				this.status = status;
125
			}
126
		}
127
128
		Log log = new Log();
129
		Policy.setLog(log);
130
131
		InvalidBean bean = new InvalidBean();
132
133
		BeanPropertyListenerSupport.hookListener(bean, "value", listener);
134
		log.count = 0;
135
		log.status = null;
136
		assertEquals(0, log.count);
137
		BeanPropertyListenerSupport.unhookListener(bean, "value", listener);
138
		assertEquals(1, log.count);
139
		assertEquals(IStatus.WARNING, log.status.getSeverity());
140
	}
141
142
	static class GenericListenerBean {
143
		private String other;
144
		PropertyChangeSupport changeSupport = new PropertyChangeSupport(this);
145
		private String value;
146
147
		public String getValue() {
148
			return value;
149
		}
150
151
		public void setValue(String value) {
152
			changeSupport.firePropertyChange("value", this.value,
153
					this.value = value);
154
		}
155
156
		public String getOther() {
157
			return other;
158
		}
159
160
		public void setOther(String other) {
161
			changeSupport.firePropertyChange("other", this.other,
162
					this.other = other);
163
		}
164
165
		public void addPropertyChangeListener(PropertyChangeListener listener) {
166
			changeSupport.addPropertyChangeListener(listener);
167
		}
168
169
		public void removePropertyChangeListener(PropertyChangeListener listener) {
170
			changeSupport.removePropertyChangeListener(listener);
171
		}
172
	}
173
174
	static class SpecificListenerBean {
175
		PropertyChangeSupport changeSupport = new PropertyChangeSupport(this);
176
		String propertyName;
177
		String value;
178
179
		public void addPropertyChangeListener(String name,
180
				PropertyChangeListener listener) {
181
			this.propertyName = name;
182
			changeSupport.addPropertyChangeListener(name, listener);
183
		}
184
185
		public void removePropertyChangeListener(String name,
186
				PropertyChangeListener listener) {
187
			changeSupport.removePropertyChangeListener(name, listener);
188
		}
189
190
		public String getValue() {
191
			return value;
192
		}
193
194
		public void setValue(String value) {
195
			this.value = value;
196
		}
197
	}
198
199
	static class PropertyChangeListenerStub implements PropertyChangeListener {
200
		PropertyChangeEvent event;
201
		int count;
202
203
		public void propertyChange(PropertyChangeEvent evt) {
204
			count++;
205
			this.event = evt;
206
		}
207
	}
208
}
(-)src/org/eclipse/jface/databinding/conformance/MutableObservableListContractTest.java (-227 / +138 lines)
Lines 21-33 Link Here
21
import junit.framework.Test;
21
import junit.framework.Test;
22
22
23
import org.eclipse.core.databinding.observable.list.IObservableList;
23
import org.eclipse.core.databinding.observable.list.IObservableList;
24
import org.eclipse.core.databinding.observable.list.ListDiffEntry;
24
import org.eclipse.core.databinding.observable.list.ListDiff;
25
import org.eclipse.jface.databinding.conformance.delegate.IObservableCollectionContractDelegate;
25
import org.eclipse.jface.databinding.conformance.delegate.IObservableCollectionContractDelegate;
26
import org.eclipse.jface.databinding.conformance.util.ChangeEventTracker;
26
import org.eclipse.jface.databinding.conformance.util.ChangeEventTracker;
27
import org.eclipse.jface.databinding.conformance.util.ListChangeEventTracker;
27
import org.eclipse.jface.databinding.conformance.util.ListChangeEventTracker;
28
import org.eclipse.jface.databinding.conformance.util.SuiteBuilder;
28
import org.eclipse.jface.databinding.conformance.util.SuiteBuilder;
29
29
30
31
/**
30
/**
32
 * Mutability tests for IObservableList.
31
 * Mutability tests for IObservableList.
33
 * 
32
 * 
Lines 68-89 Link Here
68
	}
67
	}
69
68
70
	public void testAdd_ListChangeEvent() throws Exception {
69
	public void testAdd_ListChangeEvent() throws Exception {
70
		final Object element = delegate.createElement(list);
71
		assertListChangeEventFired(new Runnable() {
71
		assertListChangeEventFired(new Runnable() {
72
			public void run() {
72
			public void run() {
73
				list.add(delegate.createElement(list));
73
				list.add(element);
74
			}
74
			}
75
		}, "List.add(Object)", list);
75
		}, "List.add(Object)", list, Collections.singletonList(element));
76
	}
76
	}
77
77
78
	public void testAdd_ListDiffEntry() throws Exception {
78
	public void testAdd_ListDiffEntry() throws Exception {
79
		list.add(delegate.createElement(list));
79
		Object element0 = delegate.createElement(list);
80
		final Object element = delegate.createElement(list);
80
		list.add(element0);
81
		final Object element1 = delegate.createElement(list);
81
82
82
		assertAddDiffEntry(new Runnable() {
83
		assertListChangeEventFired(new Runnable() {
83
			public void run() {
84
			public void run() {
84
				list.add(element);
85
				list.add(element1);
85
			}
86
			}
86
		}, "List.add(Object)", list, element, 1);
87
		}, "List.add(Object)", list, Arrays.asList(new Object[] { element0,
88
				element1 }));
87
	}
89
	}
88
90
89
	public void testAddAtIndex_ChangeEvent() throws Exception {
91
	public void testAddAtIndex_ChangeEvent() throws Exception {
Lines 95-105 Link Here
95
	}
97
	}
96
98
97
	public void testAddAtIndex_ListChangeEvent() throws Exception {
99
	public void testAddAtIndex_ListChangeEvent() throws Exception {
100
		final Object element = delegate.createElement(list);
98
		assertListChangeEventFired(new Runnable() {
101
		assertListChangeEventFired(new Runnable() {
99
			public void run() {
102
			public void run() {
100
				list.add(0, delegate.createElement(list));
103
				list.add(0, element);
101
			}
104
			}
102
		}, "List.add(int, Object)", list);
105
		}, "List.add(int, Object)", list, Collections.singletonList(element));
103
	}
106
	}
104
107
105
	public void testAddAtIndex_ChangeEventFiredAfterElementIsAdded()
108
	public void testAddAtIndex_ChangeEventFiredAfterElementIsAdded()
Lines 114-157 Link Here
114
	}
117
	}
115
118
116
	public void testAddAtIndex_ListDiffEntry() throws Exception {
119
	public void testAddAtIndex_ListDiffEntry() throws Exception {
117
		list.add(delegate.createElement(list));
120
		Object element0 = delegate.createElement(list);
118
		final Object element = delegate.createElement(list);
121
		list.add(element0);
122
		final Object element1 = delegate.createElement(list);
119
123
120
		assertAddDiffEntry(new Runnable() {
124
		assertListChangeEventFired(new Runnable() {
121
			public void run() {
125
			public void run() {
122
				list.add(1, element);
126
				list.add(1, element1);
123
			}
127
			}
124
		}, "List.add(int, Object)", list, element, 1);
128
		}, "List.add(int, Object)", list, Arrays.asList(new Object[] {
129
				element0, element1 }));
125
	}
130
	}
126
131
127
	public void testAddAll_ListChangeEvent() throws Exception {
132
	public void testAddAll_ListChangeEvent() throws Exception {
133
		final Object element = delegate.createElement(list);
128
		assertListChangeEventFired(new Runnable() {
134
		assertListChangeEventFired(new Runnable() {
129
			public void run() {
135
			public void run() {
130
				list.addAll(Arrays.asList(new Object[] { delegate
136
				list.addAll(Collections.singletonList(element));
131
						.createElement(list) }));
132
			}
137
			}
133
		}, "List.addAll(Collection", list);
138
		}, "List.addAll(Collection", list, Collections.singletonList(element));
134
	}
139
	}
135
140
136
	public void testAddAll_ListDiffEntry() throws Exception {
141
	public void testAddAll_ListDiffEntry() throws Exception {
137
		final Object element = delegate.createElement(list);
142
		final Object element = delegate.createElement(list);
138
143
139
		assertAddDiffEntry(new Runnable() {
144
		assertListChangeEventFired(new Runnable() {
140
			public void run() {
145
			public void run() {
141
				list.addAll(Arrays.asList(new Object[] { element }));
146
				list.addAll(Collections.singletonList(element));
142
			}
147
			}
143
		}, "List.addAll(Collection)", list, element, 0);
148
		}, "List.addAll(Collection)", list, Collections.singletonList(element));
144
	}
149
	}
145
150
146
	public void testAddAll_ListDiffEntry2() throws Exception {
151
	public void testAddAll_ListDiffEntry2() throws Exception {
147
		list.add(delegate.createElement(list));
152
		final Object element0 = delegate.createElement(list);
148
		final Object element = delegate.createElement(list);
153
		list.add(element0);
154
		final Object element1 = delegate.createElement(list);
149
155
150
		assertAddDiffEntry(new Runnable() {
156
		assertListChangeEventFired(new Runnable() {
151
			public void run() {
157
			public void run() {
152
				list.addAll(Collections.singletonList(element));
158
				list.addAll(Collections.singletonList(element1));
153
			}
159
			}
154
		}, "List.addAll(Collection)", list, element, 1);
160
		}, "List.addAll(Collection)", list, Arrays.asList(new Object[] {
161
				element0, element1 }));
155
	}
162
	}
156
163
157
	public void testAddAllAtIndex_ChangeEvent() throws Exception {
164
	public void testAddAllAtIndex_ChangeEvent() throws Exception {
Lines 164-175 Link Here
164
	}
171
	}
165
172
166
	public void testAddAllAtIndex_ListChangeEvent() throws Exception {
173
	public void testAddAllAtIndex_ListChangeEvent() throws Exception {
174
		final Object element = delegate.createElement(list);
167
		assertListChangeEventFired(new Runnable() {
175
		assertListChangeEventFired(new Runnable() {
168
			public void run() {
176
			public void run() {
169
				list.addAll(0, Arrays.asList(new Object[] { delegate
177
				list.addAll(0, Collections.singletonList(element));
170
						.createElement(list) }));
171
			}
178
			}
172
		}, "List.addAll(int, Collection)", list);
179
		}, "List.addAll(int, Collection)", list, Collections
180
				.singletonList(element));
173
	}
181
	}
174
182
175
	public void testAddAllAtIndex_ChangeEventFiredAfterElementIsAdded()
183
	public void testAddAllAtIndex_ChangeEventFiredAfterElementIsAdded()
Lines 184-197 Link Here
184
	}
192
	}
185
193
186
	public void testAddAllAtIndex_ListDiffEntry() throws Exception {
194
	public void testAddAllAtIndex_ListDiffEntry() throws Exception {
187
		list.add(delegate.createElement(list));
195
		Object element0 = delegate.createElement(list);
188
		final Object element = delegate.createElement(list);
196
		list.add(element0);
197
		final Object element1 = delegate.createElement(list);
189
198
190
		assertAddDiffEntry(new Runnable() {
199
		assertListChangeEventFired(new Runnable() {
191
			public void run() {
200
			public void run() {
192
				list.addAll(1, Arrays.asList(new Object[] { element }));
201
				list.addAll(1, Collections.singletonList(element1));
193
			}
202
			}
194
		}, "List.addAll(int, Collection)", list, element, 1);
203
		}, "List.addAll(int, Collection)", list, Arrays.asList(new Object[] {
204
				element0, element1 }));
195
	}
205
	}
196
206
197
	public void testSet_ChangeEvent() throws Exception {
207
	public void testSet_ChangeEvent() throws Exception {
Lines 205-263 Link Here
205
	}
215
	}
206
216
207
	public void testSet_ListChangeEvent() throws Exception {
217
	public void testSet_ListChangeEvent() throws Exception {
208
		list.add(delegate.createElement(list));
218
		final Object element0 = delegate.createElement(list);
219
		list.add(element0);
220
		final Object element1 = delegate.createElement(list);
209
221
210
		assertListChangeEventFired(new Runnable() {
222
		assertListChangeEventFired(new Runnable() {
211
			public void run() {
223
			public void run() {
212
				list.set(0, delegate.createElement(list));
224
				assertSame(element0, list.set(0, element1));
213
			}
225
			}
214
		}, "List.set(int, Object)", list);
226
		}, "List.set(int, Object)", list, Arrays
227
				.asList(new Object[] { element1 }));
215
	}
228
	}
216
229
217
	public void testSet_ChangeEventFiredAfterElementIsSet() throws Exception {
230
	public void testSet_ChangeEventFiredAfterElementIsSet() throws Exception {
218
		Object element1 = delegate.createElement(list);
231
		final Object element1 = delegate.createElement(list);
219
		list.add(element1);
232
		list.add(element1);
220
		final Object element2 = delegate.createElement(list);
233
		final Object element2 = delegate.createElement(list);
221
234
222
		assertContainsDuringChangeEvent(new Runnable() {
235
		assertContainsDuringChangeEvent(new Runnable() {
223
			public void run() {
236
			public void run() {
224
				list.set(0, element2);
237
				assertSame(element1, list.set(0, element2));
225
			}
238
			}
226
		}, "List.set(int, Object)", list, element2);
239
		}, "List.set(int, Object)", list, element2);
227
	}
240
	}
228
241
229
	public void testSet_ListDiffEntry() throws Exception {
242
	public void testSet_ListChangeEvent2() throws Exception {
230
		list.add(delegate.createElement(list));
243
		Object element0 = delegate.createElement(list);
231
		Object oldElement = delegate.createElement(list);
244
		list.add(element0);
232
		list.add(oldElement);
245
		Object oldElement1 = delegate.createElement(list);
233
246
		list.add(oldElement1);
234
		ListChangeEventTracker listener = ListChangeEventTracker.observe(list);
247
		final Object newElement1 = delegate.createElement(list);
235
236
		Object newElement = delegate.createElement(list);
237
		list.set(1, newElement);
238
239
		ListDiffEntry[] entries = listener.event.diff.getDifferences();
240
		assertEquals(
241
				"List.set(int, Object) should result in 2 list diff entries.",
242
				2, entries.length);
243
244
		ListDiffEntry remove = entries[0];
245
		assertFalse(remove.isAddition());
246
		assertEquals(
247
				"List.set(int, Object) removed element should be the old element.",
248
				oldElement, remove.getElement());
249
		assertEquals(
250
				"List.set(int, Object) removed index should be the index the new element was set at.",
251
				1, remove.getPosition());
252
248
253
		ListDiffEntry add = entries[1];
249
		assertListChangeEventFired(new Runnable() {
254
		assertTrue(add.isAddition());
250
			public void run() {
255
		assertEquals(
251
				list.set(1, newElement1);
256
				"List.set(int, Object) added element should be the set element.",
252
			}
257
				newElement, add.getElement());
253
		}, "List.set(int, Object)", list, Arrays.asList(new Object[] {
258
		assertEquals(
254
				element0, newElement1 }));
259
				"List.set(int, Object) add index should be the index the new element was set at.",
260
				1, add.getPosition());
261
	}
255
	}
262
256
263
	public void testMove_ChangeEvent() throws Exception {
257
	public void testMove_ChangeEvent() throws Exception {
Lines 289-304 Link Here
289
	}
283
	}
290
284
291
	public void testMove_ListChangeEvent() throws Exception {
285
	public void testMove_ListChangeEvent() throws Exception {
292
		final Object element = delegate.createElement(list);
286
		final Object element0 = delegate.createElement(list);
293
		list.add(element);
287
		list.add(element0);
294
		list.add(delegate.createElement(list));
288
		final Object element1 = delegate.createElement(list);
289
		list.add(element1);
295
290
296
		assertListChangeEventFired(new Runnable() {
291
		assertListChangeEventFired(new Runnable() {
297
			public void run() {
292
			public void run() {
298
				Object movedElement = list.move(0, 1);
293
				assertSame(element0, list.move(0, 1));
299
				assertEquals(element, movedElement);
300
			}
294
			}
301
		}, "IObservableList.move(int, int)", list);
295
		}, "IObservableList.move(int, int)", list, Arrays.asList(new Object[] {
296
				element1, element0 }));
302
	}
297
	}
303
298
304
	public void testMove_ChangeEventFiredAfterElementIsMoved() throws Exception {
299
	public void testMove_ChangeEventFiredAfterElementIsMoved() throws Exception {
Lines 316-357 Link Here
316
		assertSame(element0, list.get(1));
311
		assertSame(element0, list.get(1));
317
	}
312
	}
318
313
319
	public void testMove_ListDiffEntry() {
314
	public void testMove_ListChangeEvent2() {
320
		Object element = delegate.createElement(list);
315
		Object element0 = delegate.createElement(list);
321
		list.add(element);
316
		list.add(element0);
322
		list.add(delegate.createElement(list));
317
		Object element1 = delegate.createElement(list);
323
318
		list.add(element1);
324
		ListChangeEventTracker listener = ListChangeEventTracker.observe(list);
325
326
		list.move(0, 1);
327
328
		ListDiffEntry[] entries = listener.event.diff.getDifferences();
329
		assertEquals(
330
				"List.set(int, Object) should result in 2 list diff entries.",
331
				2, entries.length);
332
333
		ListDiffEntry remove = entries[0];
334
		ListDiffEntry add = entries[1];
335
		assertFalse(
336
				"IObservableList.move(int, int) removed element should be first in list diff",
337
				remove.isAddition());
338
		assertTrue(
339
				"IObservableList.move(int, int) added element should be second in list diff",
340
				add.isAddition());
341
342
		assertEquals(
343
				"IObservableList.move(int, int) remove entry contains incorrect element",
344
				element, remove.getElement());
345
		assertEquals(
346
				"IObservableList.move(int, int) add entry contains incorrect element",
347
				element, add.getElement());
348
319
349
		assertEquals(
320
		assertListChangeEventFired(new Runnable() {
350
				"IObservableList.move(int, int) remove entry should be the old element index",
321
			public void run() {
351
				0, remove.getPosition());
322
				list.move(0, 1);
352
		assertEquals(
323
			}
353
				"IObservableList.move(int, int) add entry should be the new element index",
324
		}, "IObservableList.move(int, int)", list, Arrays.asList(new Object[] {
354
				1, add.getPosition());
325
				element1, element0 }));
355
	}
326
	}
356
327
357
	public void testRemove_ListChangeEvent() throws Exception {
328
	public void testRemove_ListChangeEvent() throws Exception {
Lines 362-380 Link Here
362
			public void run() {
333
			public void run() {
363
				list.remove(element);
334
				list.remove(element);
364
			}
335
			}
365
		}, "List.remove(Object)", list);
336
		}, "List.remove(Object)", list, Collections.EMPTY_LIST);
366
	}
337
	}
367
338
368
	public void testRemove_ListDiffEntry() throws Exception {
339
	public void testRemove_ListDiffEntry() throws Exception {
369
		list.add(delegate.createElement(list));
340
		final Object element0 = delegate.createElement(list);
370
		final Object element = delegate.createElement(list);
341
		list.add(element0);
371
		list.add(element);
342
		final Object element1 = delegate.createElement(list);
343
		list.add(element1);
372
344
373
		assertRemoveDiffEntry(new Runnable() {
345
		assertListChangeEventFired(new Runnable() {
374
			public void run() {
346
			public void run() {
375
				list.remove(element);
347
				list.remove(element1);
376
			}
348
			}
377
		}, "List.remove(Object)", list, element, 1);
349
		}, "List.remove(Object)", list, Collections.singletonList(element0));
378
	}
350
	}
379
351
380
	public void testRemoveAtIndex_ChangeEvent() throws Exception {
352
	public void testRemoveAtIndex_ChangeEvent() throws Exception {
Lines 394-400 Link Here
394
			public void run() {
366
			public void run() {
395
				list.remove(0);
367
				list.remove(0);
396
			}
368
			}
397
		}, "List.remove(int)", list);
369
		}, "List.remove(int)", list, Collections.EMPTY_LIST);
398
	}
370
	}
399
371
400
	public void testRemoveAtIndex_ChangeEventFiredAfterElementIsRemoved()
372
	public void testRemoveAtIndex_ChangeEventFiredAfterElementIsRemoved()
Lines 410-424 Link Here
410
	}
382
	}
411
383
412
	public void testRemoveAtIndex_ListDiffEntry() throws Exception {
384
	public void testRemoveAtIndex_ListDiffEntry() throws Exception {
413
		list.add(delegate.createElement(list));
385
		Object element0 = delegate.createElement(list);
414
		Object element = delegate.createElement(list);
386
		list.add(element0);
415
		list.add(element);
387
		Object element1 = delegate.createElement(list);
388
		list.add(element1);
416
389
417
		assertRemoveDiffEntry(new Runnable() {
390
		assertListChangeEventFired(new Runnable() {
418
			public void run() {
391
			public void run() {
419
				list.remove(1);
392
				list.remove(1);
420
			}
393
			}
421
		}, "List.remove(int)", list, element, 1);
394
		}, "List.remove(int)", list, Collections.singletonList(element0));
422
	}
395
	}
423
396
424
	public void testRemoveAll_ListChangeEvent() throws Exception {
397
	public void testRemoveAll_ListChangeEvent() throws Exception {
Lines 427-483 Link Here
427
400
428
		assertListChangeEventFired(new Runnable() {
401
		assertListChangeEventFired(new Runnable() {
429
			public void run() {
402
			public void run() {
430
				list.removeAll(Arrays.asList(new Object[] { element }));
403
				list.removeAll(Collections.singletonList(element));
431
			}
404
			}
432
		}, "List.removeAll(Collection)", list);
405
		}, "List.removeAll(Collection)", list, Collections.EMPTY_LIST);
433
	}
406
	}
434
407
435
	public void testRemoveAll_ListDiffEntry() throws Exception {
408
	public void testRemoveAll_ListDiffEntry() throws Exception {
436
		final Object element = delegate.createElement(list);
409
		final Object element = delegate.createElement(list);
437
		list.add(element);
410
		list.add(element);
438
411
439
		assertRemoveDiffEntry(new Runnable() {
412
		assertListChangeEventFired(new Runnable() {
440
			public void run() {
413
			public void run() {
441
				list.removeAll(Arrays.asList(new Object[] { element }));
414
				list.removeAll(Collections.singletonList(element));
442
			}
415
			}
443
		}, "List.removeAll(Collection)", list, element, 0);
416
		}, "List.removeAll(Collection)", list, Collections.EMPTY_LIST);
444
	}
417
	}
445
418
446
	public void testRemoveAll_ListDiffEntry2() throws Exception {
419
	public void testRemoveAll_ListDiffEntry2() throws Exception {
447
		list.add(delegate.createElement(list));
420
		Object element0 = delegate.createElement(list);
448
		final Object element = delegate.createElement(list);
421
		list.add(element0);
449
		list.add(element);
422
		final Object element1 = delegate.createElement(list);
423
		list.add(element1);
450
424
451
		assertRemoveDiffEntry(new Runnable() {
425
		assertListChangeEventFired(new Runnable() {
452
			public void run() {
426
			public void run() {
453
				list.removeAll(Arrays.asList(new Object[] { element }));
427
				list.removeAll(Arrays.asList(new Object[] { element1 }));
454
			}
428
			}
455
		}, "List.removeAll(Collection)", list, element, 1);
429
		}, "List.removeAll(Collection)", list, Collections
430
				.singletonList(element0));
456
	}
431
	}
457
432
458
	public void testRetainAll_ListChangeEvent() throws Exception {
433
	public void testRetainAll_ListChangeEvent() throws Exception {
459
		final Object element1 = delegate.createElement(list);
434
		final Object element0 = delegate.createElement(list);
460
		list.add(element1);
435
		list.add(element0);
461
		list.add(delegate.createElement(list));
436
		list.add(delegate.createElement(list));
462
437
463
		assertListChangeEventFired(new Runnable() {
438
		assertListChangeEventFired(new Runnable() {
464
			public void run() {
439
			public void run() {
465
				list.retainAll(Arrays.asList(new Object[] { element1 }));
440
				list.retainAll(Arrays.asList(new Object[] { element0 }));
466
			}
441
			}
467
		}, "List.retainAll(Collection", list);
442
		}, "List.retainAll(Collection", list, Collections
443
				.singletonList(element0));
468
	}
444
	}
469
445
470
	public void testRetainAll_ListDiffEntry() throws Exception {
446
	public void testRetainAll_ListDiffEntry() throws Exception {
471
		final Object element1 = delegate.createElement(list);
447
		final Object element = delegate.createElement(list);
472
		list.add(element1);
448
		list.add(element);
473
		Object element2 = delegate.createElement(list);
449
		list.add(delegate.createElement(list));
474
		list.add(element2);
475
450
476
		assertRemoveDiffEntry(new Runnable() {
451
		assertListChangeEventFired(new Runnable() {
477
			public void run() {
452
			public void run() {
478
				list.retainAll(Arrays.asList(new Object[] { element1 }));
453
				list.retainAll(Arrays.asList(new Object[] { element }));
479
			}
454
			}
480
		}, "List.retainAll(Collection)", list, element2, 1);
455
		}, "List.retainAll(Collection)", list, Collections
456
				.singletonList(element));
481
	}
457
	}
482
458
483
	public void testClear_ListChangeEvent() throws Exception {
459
	public void testClear_ListChangeEvent() throws Exception {
Lines 487-504 Link Here
487
			public void run() {
463
			public void run() {
488
				list.clear();
464
				list.clear();
489
			}
465
			}
490
		}, "List.clear()", list);
466
		}, "List.clear()", list, Collections.EMPTY_LIST);
491
	}
467
	}
492
468
493
	public void testClear_ListDiffEntry() throws Exception {
469
	public void testClear_ListDiffEntry() throws Exception {
494
		Object element = delegate.createElement(list);
470
		list.add(delegate.createElement(list));
495
		list.add(element);
496
471
497
		assertRemoveDiffEntry(new Runnable() {
472
		assertListChangeEventFired(new Runnable() {
498
			public void run() {
473
			public void run() {
499
				list.clear();
474
				list.clear();
500
			}
475
			}
501
		}, "List.clear()", list, element, 0);
476
		}, "List.clear()", list, Collections.EMPTY_LIST);
502
	}
477
	}
503
478
504
	public void testClear_ClearsList() {
479
	public void testClear_ClearsList() {
Lines 509-528 Link Here
509
		Assert.assertEquals(Collections.EMPTY_LIST, list);
484
		Assert.assertEquals(Collections.EMPTY_LIST, list);
510
	}
485
	}
511
486
512
	/**
513
	 * Asserts standard behaviors of firing list change events.
514
	 * <ul>
515
	 * <li>Event fires once.</li>
516
	 * <li>Source of the event is the provided <code>list</code>.
517
	 * <li>The list change event is fired after the change event.</li>
518
	 * </ul>
519
	 * 
520
	 * @param runnable
521
	 * @param methodName
522
	 * @param list
523
	 */
524
	private void assertListChangeEventFired(Runnable runnable,
487
	private void assertListChangeEventFired(Runnable runnable,
525
			String methodName, IObservableList list) {
488
			String methodName, IObservableList list, List newList) {
489
		List oldList = new ArrayList(list);
490
526
		List queue = new ArrayList();
491
		List queue = new ArrayList();
527
		ListChangeEventTracker listListener = new ListChangeEventTracker(queue);
492
		ListChangeEventTracker listListener = new ListChangeEventTracker(queue);
528
		ChangeEventTracker changeListener = new ChangeEventTracker(queue);
493
		ChangeEventTracker changeListener = new ChangeEventTracker(queue);
Lines 546-617 Link Here
546
		assertEquals("ListChangeEvent of " + methodName
511
		assertEquals("ListChangeEvent of " + methodName
547
				+ " should have fired after the ChangeEvent.", listListener,
512
				+ " should have fired after the ChangeEvent.", listListener,
548
				queue.get(1));
513
				queue.get(1));
549
	}
550
551
	/**
552
	 * Asserts the list diff entry for a remove operation.
553
	 * 
554
	 * @param runnable
555
	 * @param methodName
556
	 * @param list
557
	 * @param element
558
	 * @param index
559
	 */
560
	private void assertRemoveDiffEntry(Runnable runnable, String methodName,
561
			IObservableList list, Object element, int index) {
562
		ListChangeEventTracker listener = new ListChangeEventTracker();
563
		list.addListChangeListener(listener);
564
514
565
		runnable.run();
515
		assertEquals(formatFail(methodName
516
				+ " did not leave observable list with the expected contents"),
517
				newList, list);
566
518
567
		ListDiffEntry[] entries = listener.event.diff.getDifferences();
519
		ListDiff diff = listListener.event.diff;
568
		assertEquals(methodName + " should result in one diff entry.", 1,
520
		diff.applyTo(oldList);
569
				entries.length);
570
571
		ListDiffEntry entry = entries[0];
572
		assertFalse(methodName
573
				+ " should result in a diff entry that is an removal.", entry
574
				.isAddition());
575
		assertEquals(methodName
576
				+ " remove diff entry should have removed the element.",
577
				element, entry.getElement());
578
		assertEquals(
521
		assertEquals(
579
				methodName
522
				formatFail(methodName
580
						+ " remove diff entry should have removed the element from the provided index.",
523
						+ " fired a diff which does not represent the expected list change"),
581
				index, entry.getPosition());
524
				newList, oldList);
582
	}
583
525
584
	/**
585
	 * Asserts the list diff entry for an add operation.
586
	 * 
587
	 * @param runnable
588
	 * @param methodName
589
	 * @param list
590
	 * @param element
591
	 * @param index
592
	 */
593
	private void assertAddDiffEntry(Runnable runnable, String methodName,
594
			IObservableList list, Object element, int index) {
595
		ListChangeEventTracker listener = new ListChangeEventTracker();
596
		list.addListChangeListener(listener);
597
598
		runnable.run();
599
600
		ListDiffEntry[] entries = listener.event.diff.getDifferences();
601
		assertEquals(methodName + " should result in one diff entry.", 1,
602
				entries.length);
603
604
		ListDiffEntry entry = entries[0];
605
		assertTrue(methodName
606
				+ " should result in a diff entry that is an addition.", entry
607
				.isAddition());
608
		assertEquals(methodName
609
				+ " add diff entry should have added the element.", element,
610
				entry.getElement());
611
		assertEquals(
612
				methodName
613
						+ "add diff entry should have added the element at the provided index.",
614
				index, entry.getPosition());
615
	}
526
	}
616
527
617
	public static Test suite(IObservableCollectionContractDelegate delegate) {
528
	public static Test suite(IObservableCollectionContractDelegate delegate) {

Return to bug 194734