Skip to main content
summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorTom Schindl2013-04-13 09:50:25 +0000
committerTom Schindl2013-04-13 09:50:25 +0000
commite5d523417f5fb78a9dc709c2543afc4b0c760e9e (patch)
treeaf9f06978524e0b41cd15ba25bbe33f89706b8d5 /bundles
parent99780bf8fba2d33ac5f3ec04e18bf78ae7c5b436 (diff)
downloadorg.eclipse.efxclipse-e5d523417f5fb78a9dc709c2543afc4b0c760e9e.tar.gz
org.eclipse.efxclipse-e5d523417f5fb78a9dc709c2543afc4b0c760e9e.tar.xz
org.eclipse.efxclipse-e5d523417f5fb78a9dc709c2543afc4b0c760e9e.zip
initial checkin
Diffstat (limited to 'bundles')
-rwxr-xr-xbundles/runtime/org.eclipse.fx.databinding/.classpath7
-rwxr-xr-xbundles/runtime/org.eclipse.fx.databinding/.gitignore2
-rwxr-xr-xbundles/runtime/org.eclipse.fx.databinding/.project28
-rwxr-xr-xbundles/runtime/org.eclipse.fx.databinding/.settings/org.eclipse.core.resources.prefs2
-rwxr-xr-xbundles/runtime/org.eclipse.fx.databinding/.settings/org.eclipse.core.runtime.prefs2
-rwxr-xr-xbundles/runtime/org.eclipse.fx.databinding/.settings/org.eclipse.jdt.core.prefs7
-rwxr-xr-xbundles/runtime/org.eclipse.fx.databinding/META-INF/MANIFEST.MF39
-rwxr-xr-xbundles/runtime/org.eclipse.fx.databinding/OSGI-INF/l10n/bundle.properties3
-rwxr-xr-xbundles/runtime/org.eclipse.fx.databinding/about.html28
-rwxr-xr-xbundles/runtime/org.eclipse.fx.databinding/build.properties6
-rwxr-xr-xbundles/runtime/org.eclipse.fx.databinding/pom.xml34
-rwxr-xr-xbundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/AdapterFactory.java518
-rwxr-xr-xbundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/IJFXBeanObservable.java34
-rwxr-xr-xbundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/IJFXBeanProperty.java19
-rwxr-xr-xbundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/IJFXBeanValueProperty.java21
-rwxr-xr-xbundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/JFXBeanProperties.java75
-rwxr-xr-xbundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/JFXRealm.java40
-rwxr-xr-xbundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/JFXUIProperties.java17
-rwxr-xr-xbundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/ObservableWritableValue.java18
-rwxr-xr-xbundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/TreeUtil.java104
-rwxr-xr-xbundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/internal/AnonymousFXBeanValueProperty.java86
-rwxr-xr-xbundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/internal/FXBeanObservableValueDecorator.java58
-rwxr-xr-xbundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/internal/FXBeanPropertyHelper.java241
-rwxr-xr-xbundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/internal/FXBeanPropertyListener.java88
-rwxr-xr-xbundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/internal/FXBeanPropertyListenerSupport.java119
-rwxr-xr-xbundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/internal/FXBeanValueProperty.java69
-rwxr-xr-xbundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/internal/FXBeanValuePropertyDecorator.java154
27 files changed, 1819 insertions, 0 deletions
diff --git a/bundles/runtime/org.eclipse.fx.databinding/.classpath b/bundles/runtime/org.eclipse.fx.databinding/.classpath
new file mode 100755
index 000000000..b1dabee38
--- /dev/null
+++ b/bundles/runtime/org.eclipse.fx.databinding/.classpath
@@ -0,0 +1,7 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<classpath>
+ <classpathentry kind="con" path="org.eclipse.jdt.launching.JRE_CONTAINER/org.eclipse.jdt.internal.debug.ui.launcher.StandardVMType/JavaSE-1.7"/>
+ <classpathentry kind="con" path="org.eclipse.pde.core.requiredPlugins"/>
+ <classpathentry kind="src" path="src"/>
+ <classpathentry kind="output" path="bin"/>
+</classpath>
diff --git a/bundles/runtime/org.eclipse.fx.databinding/.gitignore b/bundles/runtime/org.eclipse.fx.databinding/.gitignore
new file mode 100755
index 000000000..4dc009173
--- /dev/null
+++ b/bundles/runtime/org.eclipse.fx.databinding/.gitignore
@@ -0,0 +1,2 @@
+/target
+/bin
diff --git a/bundles/runtime/org.eclipse.fx.databinding/.project b/bundles/runtime/org.eclipse.fx.databinding/.project
new file mode 100755
index 000000000..615e24b53
--- /dev/null
+++ b/bundles/runtime/org.eclipse.fx.databinding/.project
@@ -0,0 +1,28 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<projectDescription>
+ <name>org.eclipse.fx.databinding</name>
+ <comment></comment>
+ <projects>
+ </projects>
+ <buildSpec>
+ <buildCommand>
+ <name>org.eclipse.jdt.core.javabuilder</name>
+ <arguments>
+ </arguments>
+ </buildCommand>
+ <buildCommand>
+ <name>org.eclipse.pde.ManifestBuilder</name>
+ <arguments>
+ </arguments>
+ </buildCommand>
+ <buildCommand>
+ <name>org.eclipse.pde.SchemaBuilder</name>
+ <arguments>
+ </arguments>
+ </buildCommand>
+ </buildSpec>
+ <natures>
+ <nature>org.eclipse.pde.PluginNature</nature>
+ <nature>org.eclipse.jdt.core.javanature</nature>
+ </natures>
+</projectDescription>
diff --git a/bundles/runtime/org.eclipse.fx.databinding/.settings/org.eclipse.core.resources.prefs b/bundles/runtime/org.eclipse.fx.databinding/.settings/org.eclipse.core.resources.prefs
new file mode 100755
index 000000000..4824b8026
--- /dev/null
+++ b/bundles/runtime/org.eclipse.fx.databinding/.settings/org.eclipse.core.resources.prefs
@@ -0,0 +1,2 @@
+eclipse.preferences.version=1
+encoding/<project>=UTF-8
diff --git a/bundles/runtime/org.eclipse.fx.databinding/.settings/org.eclipse.core.runtime.prefs b/bundles/runtime/org.eclipse.fx.databinding/.settings/org.eclipse.core.runtime.prefs
new file mode 100755
index 000000000..deae05a97
--- /dev/null
+++ b/bundles/runtime/org.eclipse.fx.databinding/.settings/org.eclipse.core.runtime.prefs
@@ -0,0 +1,2 @@
+eclipse.preferences.version=1
+line.separator=\r\n
diff --git a/bundles/runtime/org.eclipse.fx.databinding/.settings/org.eclipse.jdt.core.prefs b/bundles/runtime/org.eclipse.fx.databinding/.settings/org.eclipse.jdt.core.prefs
new file mode 100755
index 000000000..f42de363a
--- /dev/null
+++ b/bundles/runtime/org.eclipse.fx.databinding/.settings/org.eclipse.jdt.core.prefs
@@ -0,0 +1,7 @@
+eclipse.preferences.version=1
+org.eclipse.jdt.core.compiler.codegen.inlineJsrBytecode=enabled
+org.eclipse.jdt.core.compiler.codegen.targetPlatform=1.7
+org.eclipse.jdt.core.compiler.compliance=1.7
+org.eclipse.jdt.core.compiler.problem.assertIdentifier=error
+org.eclipse.jdt.core.compiler.problem.enumIdentifier=error
+org.eclipse.jdt.core.compiler.source=1.7
diff --git a/bundles/runtime/org.eclipse.fx.databinding/META-INF/MANIFEST.MF b/bundles/runtime/org.eclipse.fx.databinding/META-INF/MANIFEST.MF
new file mode 100755
index 000000000..c1dd2b394
--- /dev/null
+++ b/bundles/runtime/org.eclipse.fx.databinding/META-INF/MANIFEST.MF
@@ -0,0 +1,39 @@
+Manifest-Version: 1.0
+Bundle-ManifestVersion: 2
+Bundle-Name: %Bundle-Name
+Bundle-SymbolicName: org.eclipse.fx.databinding
+Bundle-Version: 0.8.1.qualifier
+Bundle-RequiredExecutionEnvironment: JavaSE-1.7
+Require-Bundle: org.eclipse.core.databinding.observable;bundle-version="1.4.0",
+ org.eclipse.core.databinding.property;bundle-version="1.4.0",
+ org.eclipse.equinox.common;bundle-version="3.6.0"
+Import-Package: javafx.animation;version="2.0.0",
+ javafx.application;version="2.0.0",
+ javafx.beans;version="2.0.0",
+ javafx.beans.binding;version="2.0.0",
+ javafx.beans.property;version="2.0.0",
+ javafx.beans.value;version="2.0.0",
+ javafx.collections;version="2.0.0",
+ javafx.concurrent;version="2.0.0",
+ javafx.embed.swing;version="2.0.0",
+ javafx.event;version="2.0.0",
+ javafx.fxml;version="2.0.0",
+ javafx.geometry;version="2.0.0",
+ javafx.scene;version="2.0.0",
+ javafx.scene.chart;version="2.0.0",
+ javafx.scene.control;version="2.0.0",
+ javafx.scene.control.cell;version="2.0.0",
+ javafx.scene.effect;version="2.0.0",
+ javafx.scene.image;version="2.0.0",
+ javafx.scene.input;version="2.0.0",
+ javafx.scene.layout;version="2.0.0",
+ javafx.scene.media;version="2.0.0",
+ javafx.scene.paint;version="2.0.0",
+ javafx.scene.shape;version="2.0.0",
+ javafx.scene.text;version="2.0.0",
+ javafx.scene.transform;version="2.0.0",
+ javafx.scene.web;version="2.0.0",
+ javafx.stage;version="2.0.0",
+ javafx.util;version="2.0.0"
+Export-Package: org.eclipse.fx.databinding
+Bundle-Vendor: %Bundle-Vendor
diff --git a/bundles/runtime/org.eclipse.fx.databinding/OSGI-INF/l10n/bundle.properties b/bundles/runtime/org.eclipse.fx.databinding/OSGI-INF/l10n/bundle.properties
new file mode 100755
index 000000000..3db214f6e
--- /dev/null
+++ b/bundles/runtime/org.eclipse.fx.databinding/OSGI-INF/l10n/bundle.properties
@@ -0,0 +1,3 @@
+#Properties file for org.eclipse.fx.databinding
+Bundle-Vendor = BestSolution.at
+Bundle-Name = JavaFX Eclipse Databinding \ No newline at end of file
diff --git a/bundles/runtime/org.eclipse.fx.databinding/about.html b/bundles/runtime/org.eclipse.fx.databinding/about.html
new file mode 100755
index 000000000..ecd1378e9
--- /dev/null
+++ b/bundles/runtime/org.eclipse.fx.databinding/about.html
@@ -0,0 +1,28 @@
+<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN"
+ "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
+<html xmlns="http://www.w3.org/1999/xhtml">
+<head>
+<meta http-equiv="Content-Type" content="text/html; charset=ISO-8859-1"/>
+<title>About</title>
+</head>
+<body lang="EN-US">
+<h2>About This Content</h2>
+
+<p>June 2, 2006</p>
+<h3>License</h3>
+
+<p>The BestSolution.at makes available all content in this plug-in (&quot;Content&quot;). Unless otherwise
+indicated below, the Content is provided to you under the terms and conditions of the
+Eclipse Public License Version 1.0 (&quot;EPL&quot;). A copy of the EPL is available
+at <a href="http://www.eclipse.org/legal/epl-v10.html">http://www.eclipse.org/legal/epl-v10.html</a>.
+For purposes of the EPL, &quot;Program&quot; will mean the Content.</p>
+
+<p>If you did not receive this Content directly from the BestSolution.at, the Content is
+being redistributed by another party (&quot;Redistributor&quot;) and different terms and conditions may
+apply to your use of any object code in the Content. Check the Redistributor's license that was
+provided with the Content. If no such license exists, contact the Redistributor. Unless otherwise
+indicated below, the terms and conditions of the EPL still apply to any source code in the Content
+and such source code may be obtained at <a href="http://www.eclipse.org">http://www.eclipse.org</a>.</p>
+
+</body>
+</html> \ No newline at end of file
diff --git a/bundles/runtime/org.eclipse.fx.databinding/build.properties b/bundles/runtime/org.eclipse.fx.databinding/build.properties
new file mode 100755
index 000000000..bad151d65
--- /dev/null
+++ b/bundles/runtime/org.eclipse.fx.databinding/build.properties
@@ -0,0 +1,6 @@
+source.. = src/
+output.. = bin/
+bin.includes = META-INF/,\
+ .,\
+ about.html,\
+ OSGI-INF/
diff --git a/bundles/runtime/org.eclipse.fx.databinding/pom.xml b/bundles/runtime/org.eclipse.fx.databinding/pom.xml
new file mode 100755
index 000000000..2a2285ebd
--- /dev/null
+++ b/bundles/runtime/org.eclipse.fx.databinding/pom.xml
@@ -0,0 +1,34 @@
+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
+ <modelVersion>4.0.0</modelVersion>
+ <name>e(fx)clipse - Runtime - Eclipse Databinding Support</name>
+ <groupId>org.eclipse.fx.runtime</groupId>
+ <artifactId>org.eclipse.fx.databinding</artifactId>
+ <packaging>eclipse-plugin</packaging>
+
+ <parent>
+ <groupId>org.eclipse.fx</groupId>
+ <artifactId>releng</artifactId>
+ <relativePath>../../../releng/org.eclipse.fx.releng/pom.xml</relativePath>
+ <version>0.8.1-SNAPSHOT</version>
+ </parent>
+
+ <build>
+ <resources>
+ <!-- to ensure that the feature lookup of the ui test works -->
+ <resource>
+ <directory>.</directory>
+ <includes>
+ <include>META-INF/</include>
+ </includes>
+ </resource>
+ </resources>
+ <plugins>
+ <plugin>
+ <groupId>org.eclipse.tycho</groupId>
+ <artifactId>tycho-source-plugin</artifactId>
+ </plugin>
+ </plugins>
+ </build>
+
+</project> \ No newline at end of file
diff --git a/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/AdapterFactory.java b/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/AdapterFactory.java
new file mode 100755
index 000000000..d4a6f7bb4
--- /dev/null
+++ b/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/AdapterFactory.java
@@ -0,0 +1,518 @@
+/*******************************************************************************
+ * Copyright (c) 2012 BestSolution.at and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Tom Schindl<tom.schindl@bestsolution.at> - initial API and implementation
+ *******************************************************************************/
+package org.eclipse.fx.databinding;
+
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.Collection;
+import java.util.Collections;
+import java.util.Iterator;
+import java.util.List;
+import java.util.ListIterator;
+
+import javafx.beans.InvalidationListener;
+import javafx.beans.binding.Bindings;
+import javafx.beans.value.ChangeListener;
+import javafx.beans.value.ObservableValue;
+import javafx.beans.value.WritableValue;
+import javafx.collections.ListChangeListener;
+import javafx.collections.ListChangeListener.Change;
+import javafx.collections.ObservableList;
+
+import org.eclipse.core.databinding.observable.ChangeEvent;
+import org.eclipse.core.databinding.observable.DisposeEvent;
+import org.eclipse.core.databinding.observable.IChangeListener;
+import org.eclipse.core.databinding.observable.IDisposeListener;
+import org.eclipse.core.databinding.observable.list.IListChangeListener;
+import org.eclipse.core.databinding.observable.list.IObservableList;
+import org.eclipse.core.databinding.observable.list.ListChangeEvent;
+import org.eclipse.core.databinding.observable.list.ListDiffEntry;
+import org.eclipse.core.databinding.observable.value.IObservableValue;
+import org.eclipse.core.databinding.observable.value.IValueChangeListener;
+import org.eclipse.core.databinding.observable.value.ValueChangeEvent;
+
+public class AdapterFactory {
+ static class WrappedList<E> implements ObservableList<E> {
+
+ private List<InvalidationListener> fxInvalidationListeners;
+ private List<ListChangeListener<? super E>> fxChangeListeners;
+
+ private final IObservableList list;
+ private IChangeListener dbInvalidationListener;
+ private IListChangeListener dbChangeListener;
+
+ public WrappedList(IObservableList list) {
+ this.list = list;
+ this.list.addDisposeListener(new IDisposeListener() {
+
+ @Override
+ public void handleDispose(DisposeEvent event) {
+ fxInvalidationListeners.clear();
+ dbInvalidationListener = null;
+
+ fxChangeListeners.clear();
+ dbChangeListener = null;
+ }
+ });
+ }
+
+ @Override
+ public int size() {
+ return list.size();
+ }
+
+ @Override
+ public boolean isEmpty() {
+ return list.isEmpty();
+ }
+
+ @Override
+ public boolean contains(Object o) {
+ return list.contains(o);
+ }
+
+ @SuppressWarnings("unchecked")
+ @Override
+ public Iterator<E> iterator() {
+ return list.iterator();
+ }
+
+ @Override
+ public Object[] toArray() {
+ return list.toArray();
+ }
+
+ @SuppressWarnings("unchecked")
+ @Override
+ public <T> T[] toArray(T[] a) {
+ return (T[]) list.toArray(a);
+ }
+
+ @Override
+ public boolean add(E e) {
+ return list.add(e);
+ }
+
+ @Override
+ public boolean remove(Object o) {
+ return list.remove(o);
+ }
+
+ @Override
+ public boolean containsAll(Collection<?> c) {
+ return list.containsAll(c);
+ }
+
+ @Override
+ public boolean addAll(Collection<? extends E> c) {
+ return list.addAll(c);
+ }
+
+ @Override
+ public boolean addAll(int index, Collection<? extends E> c) {
+ return list.addAll(index, c);
+ }
+
+ @Override
+ public boolean removeAll(Collection<?> c) {
+ return list.removeAll(c);
+ }
+
+ @Override
+ public boolean retainAll(Collection<?> c) {
+ return list.retainAll(c);
+ }
+
+ @Override
+ public void clear() {
+ list.clear();
+ }
+
+ @SuppressWarnings("unchecked")
+ @Override
+ public E get(int index) {
+ return (E) list.get(index);
+ }
+
+ @SuppressWarnings("unchecked")
+ @Override
+ public E set(int index, E element) {
+ return (E) list.set(index, element);
+ }
+
+ @SuppressWarnings("unchecked")
+ @Override
+ public void add(int index, E element) {
+ list.add(index, element);
+ }
+
+ @SuppressWarnings("unchecked")
+ @Override
+ public E remove(int index) {
+ return (E) list.remove(index);
+ }
+
+ @Override
+ public int indexOf(Object o) {
+ return list.indexOf(o);
+ }
+
+ @Override
+ public int lastIndexOf(Object o) {
+ return list.lastIndexOf(o);
+ }
+
+ @SuppressWarnings("unchecked")
+ @Override
+ public ListIterator<E> listIterator() {
+ return list.listIterator();
+ }
+
+ @SuppressWarnings("unchecked")
+ @Override
+ public ListIterator<E> listIterator(int index) {
+ return list.listIterator(index);
+ }
+
+ @SuppressWarnings("unchecked")
+ @Override
+ public List<E> subList(int fromIndex, int toIndex) {
+ return list.subList(fromIndex, toIndex);
+ }
+
+ @Override
+ public void addListener(InvalidationListener listener) {
+ if( fxInvalidationListeners == null ) {
+ fxInvalidationListeners = new ArrayList<InvalidationListener>();
+ dbInvalidationListener = new IChangeListener() {
+
+ @Override
+ public void handleChange(ChangeEvent event) {
+ for( InvalidationListener l : fxInvalidationListeners.toArray(new InvalidationListener[0]) ) {
+ l.invalidated(WrappedList.this);
+ }
+ }
+ };
+ list.addChangeListener(dbInvalidationListener);
+ }
+
+ fxInvalidationListeners.add(listener);
+ }
+
+ @Override
+ public void removeListener(InvalidationListener listener) {
+ if( fxInvalidationListeners != null ) {
+ fxInvalidationListeners.remove(listener);
+ if( fxInvalidationListeners.isEmpty() ) {
+ list.removeChangeListener(dbInvalidationListener);
+ dbInvalidationListener = null;
+ fxInvalidationListeners = null;
+ }
+ }
+ }
+
+ @Override
+ public boolean addAll(E... elements) {
+ return list.addAll(Arrays.asList(elements));
+ }
+
+ @Override
+ public void addListener(ListChangeListener<? super E> listener) {
+ if( fxChangeListeners == null ) {
+ fxChangeListeners = new ArrayList<ListChangeListener<? super E>>();
+ dbChangeListener = new IListChangeListener() {
+
+ @SuppressWarnings("unchecked")
+ @Override
+ public void handleListChange(ListChangeEvent event) {
+ final ListDiffEntry[] differences = event.diff.getDifferences();
+
+ if( differences.length == 0 ) {
+ return;
+ }
+
+ //TODO We need to make this perform a lot better by calculating range changes
+ for( ListChangeListener<? super E> l : fxChangeListeners.toArray(new ListChangeListener[0]) ) {
+ Change<E> change = new Change<E>(WrappedList.this) {
+ private int index = -1;
+ private ListDiffEntry current;
+
+ @Override
+ public int getFrom() {
+ return current.getPosition();
+ }
+
+ @Override
+ protected int[] getPermutation() {
+ return new int[0];
+ }
+
+ @Override
+ public List<E> getRemoved() {
+ if( ! current.isAddition() ) {
+ return Collections.singletonList((E)current.getElement());
+ }
+ return Collections.emptyList();
+ }
+
+ @Override
+ public int getTo() {
+ if( current.isAddition() ) {
+ return current.getPosition() + 1;
+ } else {
+ return current.getPosition();
+ }
+ }
+
+ public boolean wasAdded() {
+ return current.isAddition();
+ }
+
+ public boolean wasRemoved() {
+ return ! current.isAddition();
+ }
+
+ public boolean wasPermutated() {
+ return false;
+ }
+
+ public boolean wasReplaced() {
+ return false;
+ }
+
+ @Override
+ public boolean next() {
+ index++;
+ if( index < differences.length ) {
+ current = differences[index];
+ return true;
+ }
+ return false;
+ }
+
+ @Override
+ public void reset() {
+ index = 0;
+ }
+ };
+ l.onChanged(change);
+ }
+ }
+ };
+ list.addListChangeListener(dbChangeListener);
+ }
+
+ fxChangeListeners.add(listener);
+ }
+
+ @Override
+ public void removeListener(ListChangeListener<? super E> listener) {
+ if( fxChangeListeners != null ) {
+ fxChangeListeners.remove(listener);
+ if( fxChangeListeners.isEmpty() ) {
+ list.removeListChangeListener(dbChangeListener);
+ dbChangeListener = null;
+ fxChangeListeners = null;
+ }
+ }
+ }
+
+ @Override
+ public void remove(int from, int to) {
+ //TODO Improve performance??
+ for( int idx = to; idx >= from; idx-- ) {
+ list.remove(idx);
+ }
+ }
+
+ @Override
+ public boolean removeAll(E... elements) {
+ return list.removeAll(Arrays.asList(elements));
+ }
+
+
+ @Override
+ public boolean retainAll(E... elements) {
+ return list.retainAll(Arrays.asList(elements));
+ }
+
+ @Override
+ public boolean setAll(E... elements) {
+ //TODO Improve performance
+ list.clear();
+ return list.addAll(Arrays.asList(elements));
+ }
+
+ @Override
+ public boolean setAll(Collection<? extends E> col) {
+ //TODO Improve performance
+ list.clear();
+ return list.addAll(col);
+ }
+ }
+
+ static class WrappedValue<E> implements ObservableWritableValue<E> {
+
+ private List<InvalidationListener> fxInvalidationListeners;
+ private List<ChangeListener<? super E>> fxChangeListeners;
+
+ private final IObservableValue value;
+ private IChangeListener dbInvalidationListener;
+ private IValueChangeListener dbChangeListener;
+
+
+ public WrappedValue(IObservableValue value) {
+ this.value = value;
+ this.value.addDisposeListener(new IDisposeListener() {
+
+ @Override
+ public void handleDispose(DisposeEvent event) {
+ fxInvalidationListeners.clear();
+ dbInvalidationListener = null;
+
+ fxChangeListeners.clear();
+ dbChangeListener = null;
+ }
+ });
+ }
+
+ @Override
+ public void addListener(InvalidationListener listener) {
+ if( fxInvalidationListeners == null ) {
+ fxInvalidationListeners = new ArrayList<InvalidationListener>();
+ dbInvalidationListener = new IChangeListener() {
+
+ @Override
+ public void handleChange(ChangeEvent event) {
+ for( InvalidationListener l : fxInvalidationListeners.toArray(new InvalidationListener[0]) ) {
+ l.invalidated(WrappedValue.this);
+ }
+ }
+ };
+ value.addChangeListener(dbInvalidationListener);
+ }
+
+ fxInvalidationListeners.add(listener);
+ }
+
+ @Override
+ public void removeListener(InvalidationListener listener) {
+ if( fxInvalidationListeners != null ) {
+ fxInvalidationListeners.remove(listener);
+ if( fxInvalidationListeners.isEmpty() ) {
+ value.removeChangeListener(dbInvalidationListener);
+ dbInvalidationListener = null;
+ fxInvalidationListeners = null;
+ }
+ }
+ }
+
+ @Override
+ public void addListener(ChangeListener<? super E> listener) {
+ if( fxChangeListeners == null ) {
+ fxChangeListeners = new ArrayList<ChangeListener<? super E>>();
+ dbChangeListener = new IValueChangeListener() {
+
+ @SuppressWarnings("unchecked")
+ @Override
+ public void handleValueChange(ValueChangeEvent event) {
+ for( ChangeListener<? super E> l : fxChangeListeners.toArray(new ChangeListener[0]) ) {
+ l.changed(WrappedValue.this, (E)event.diff.getOldValue(), (E)event.diff.getNewValue());
+ }
+ }
+ };
+ value.addValueChangeListener(dbChangeListener);
+ }
+
+ fxChangeListeners.add(listener);
+ }
+
+ @Override
+ public void removeListener(ChangeListener<? super E> listener) {
+ if( fxChangeListeners != null ) {
+ fxChangeListeners.remove(listener);
+ if( fxChangeListeners.isEmpty() ) {
+ value.removeValueChangeListener(dbChangeListener);
+ dbChangeListener = null;
+ fxChangeListeners = null;
+ }
+ }
+ }
+
+ @SuppressWarnings("unchecked")
+ @Override
+ public E getValue() {
+ return (E) value.getValue();
+ }
+
+ @Override
+ public void setValue(E value) {
+ this.value.setValue(value);
+ }
+ }
+
+ public static <E> ObservableWritableValue<E> adapt(IObservableValue value) {
+ return new WrappedValue<E>(value);
+ }
+
+ public static <E> ObservableList<E> adapt(IObservableList list) {
+ return new WrappedList<E>(list);
+ }
+
+ enum InitialSync {
+ FX_TO_DB,
+ DB_TO_FX
+ }
+
+ public static <E> void bind(ObservableList<E> fxObs, IObservableList dbObs, InitialSync initialSync) {
+ ObservableList<E> dbList = adapt(dbObs);
+ if( initialSync == InitialSync.FX_TO_DB ) {
+ Bindings.bindContent(dbList, fxObs);
+ } else {
+ Bindings.bindContentBidirectional(fxObs, dbList);
+ }
+
+ }
+
+ @SuppressWarnings("unchecked")
+ public static <E, F extends ObservableValue<E> & WritableValue<E>> void bind(F fxObs, IObservableValue dbObs, InitialSync initialSync) {
+ if( initialSync == InitialSync.FX_TO_DB ) {
+ dbObs.setValue(fxObs.getValue());
+ } else {
+ fxObs.setValue((E) dbObs.getValue());
+ }
+ ObservableWritableValue<E> wrapped = adapt(dbObs);
+ do_bind(fxObs, wrapped);
+ }
+
+ private static <E, F extends ObservableValue<E> & WritableValue<E>> void do_bind(final F fxObs, final F dbObs) {
+ fxObs.addListener(new ChangeListener<E>() {
+ boolean syncing;
+ @Override
+ public void changed(ObservableValue<? extends E> observable, E oldValue, E newValue) {
+ if( syncing ) {
+ return;
+ }
+
+ try {
+ syncing = true;
+ if( observable == fxObs ) {
+ dbObs.setValue(newValue);
+ } else {
+ fxObs.setValue(newValue);
+ }
+ } finally {
+ syncing = false;
+ }
+ }
+ });
+ }
+}
diff --git a/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/IJFXBeanObservable.java b/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/IJFXBeanObservable.java
new file mode 100755
index 000000000..30a1fa1da
--- /dev/null
+++ b/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/IJFXBeanObservable.java
@@ -0,0 +1,34 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Brad Reynolds and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Brad Reynolds - initial API and implementation
+ * Brad Reynolds - bug 147515
+ ******************************************************************************/
+
+package org.eclipse.fx.databinding;
+
+import java.beans.PropertyDescriptor;
+
+import org.eclipse.core.databinding.observable.IObserving;
+
+/**
+ * Provides access to details of bean observables.
+ * <p>
+ * This interface is not meant to be implemented by clients.
+ * </p>
+ *
+ * @since 3.3
+ */
+public interface IJFXBeanObservable extends IObserving {
+ /**
+ * @return property descriptor of the property being observed,
+ * <code>null</code> if the runtime time information was not
+ * provided on construction of the observable
+ */
+ public PropertyDescriptor getPropertyDescriptor();
+}
diff --git a/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/IJFXBeanProperty.java b/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/IJFXBeanProperty.java
new file mode 100755
index 000000000..c334121f5
--- /dev/null
+++ b/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/IJFXBeanProperty.java
@@ -0,0 +1,19 @@
+/*******************************************************************************
+ * Copyright (c) 2012 BestSolution.at and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Tom Schindl<tom.schindl@bestsolution.at> - initial API and implementation
+ *******************************************************************************/
+package org.eclipse.fx.databinding;
+
+import java.beans.PropertyDescriptor;
+
+import org.eclipse.core.databinding.property.IProperty;
+
+public interface IJFXBeanProperty extends IProperty {
+ public PropertyDescriptor getPropertyDescriptor();
+}
diff --git a/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/IJFXBeanValueProperty.java b/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/IJFXBeanValueProperty.java
new file mode 100755
index 000000000..f4ec4573c
--- /dev/null
+++ b/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/IJFXBeanValueProperty.java
@@ -0,0 +1,21 @@
+/*******************************************************************************
+ * Copyright (c) 2012 BestSolution.at and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Tom Schindl<tom.schindl@bestsolution.at> - initial API and implementation
+ *******************************************************************************/
+package org.eclipse.fx.databinding;
+
+import org.eclipse.core.databinding.property.value.IValueProperty;
+
+public interface IJFXBeanValueProperty extends IJFXBeanProperty, IValueProperty {
+ public IJFXBeanValueProperty value(String propertyName);
+
+ public IJFXBeanValueProperty value(String propertyName, Class<?> valueType);
+
+ public IJFXBeanValueProperty value(IJFXBeanValueProperty property);
+}
diff --git a/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/JFXBeanProperties.java b/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/JFXBeanProperties.java
new file mode 100755
index 000000000..2f97d220d
--- /dev/null
+++ b/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/JFXBeanProperties.java
@@ -0,0 +1,75 @@
+/*******************************************************************************
+ * Copyright (c) 2012 BestSolution.at and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Tom Schindl<tom.schindl@bestsolution.at> - initial API and implementation
+ *******************************************************************************/
+package org.eclipse.fx.databinding;
+
+import java.beans.PropertyDescriptor;
+import java.util.ArrayList;
+import java.util.List;
+
+import org.eclipse.core.databinding.property.value.IValueProperty;
+import org.eclipse.fx.databinding.internal.AnonymousFXBeanValueProperty;
+import org.eclipse.fx.databinding.internal.FXBeanPropertyHelper;
+import org.eclipse.fx.databinding.internal.FXBeanValueProperty;
+import org.eclipse.fx.databinding.internal.FXBeanValuePropertyDecorator;
+
+
+import javafx.beans.property.Property;
+
+
+public class JFXBeanProperties {
+ public static IJFXBeanValueProperty value(String propertyName) {
+ return value(null, propertyName, null);
+ }
+
+ public static IJFXBeanValueProperty value(String propertyName, Class valueType) {
+ return value(null, propertyName, valueType);
+ }
+
+ public static IJFXBeanValueProperty value(Class beanClass,
+ String propertyName, Class valueType) {
+ String[] propertyNames = split(propertyName);
+ if (propertyNames.length > 1)
+ valueType = null;
+
+ PropertyDescriptor propertyDescriptor;
+ IValueProperty property;
+ if (beanClass == null) {
+ propertyDescriptor = null;
+ property = new AnonymousFXBeanValueProperty(propertyNames[0],
+ valueType);
+ } else {
+ propertyDescriptor = FXBeanPropertyHelper.getPropertyDescriptor(
+ beanClass, propertyNames[0]);
+ property = new FXBeanValueProperty(propertyDescriptor, valueType);
+ }
+
+ IJFXBeanValueProperty beanProperty = new FXBeanValuePropertyDecorator(
+ property, propertyDescriptor);
+ for (int i = 1; i < propertyNames.length; i++) {
+ beanProperty = beanProperty.value(propertyNames[i]);
+ }
+ return beanProperty;
+ }
+
+ private static String[] split(String propertyName) {
+ if (propertyName.indexOf('.') == -1)
+ return new String[] { propertyName };
+ List<String> propertyNames = new ArrayList<String>();
+ int index;
+ while ((index = propertyName.indexOf('.')) != -1) {
+ propertyNames.add(propertyName.substring(0, index));
+ propertyName = propertyName.substring(index + 1);
+ }
+ propertyNames.add(propertyName);
+ return (String[]) propertyNames
+ .toArray(new String[propertyNames.size()]);
+ }
+}
diff --git a/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/JFXRealm.java b/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/JFXRealm.java
new file mode 100755
index 000000000..50835bf5c
--- /dev/null
+++ b/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/JFXRealm.java
@@ -0,0 +1,40 @@
+/*******************************************************************************
+ * Copyright (c) 2012 BestSolution.at and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Tom Schindl<tom.schindl@bestsolution.at> - initial API and implementation
+ *******************************************************************************/
+package org.eclipse.fx.databinding;
+
+import javafx.application.Platform;
+
+import org.eclipse.core.databinding.observable.Realm;
+
+public class JFXRealm extends Realm {
+ public static void createDefault() {
+ setDefault(new JFXRealm());
+ }
+
+ @Override
+ public boolean isCurrent() {
+ return Platform.isFxApplicationThread();
+ }
+
+ @Override
+ public void asyncExec(Runnable runnable) {
+ Platform.runLater(runnable);
+ }
+
+ @Override
+ public void exec(Runnable runnable) {
+ if( isCurrent() ) {
+ runnable.run();
+ } else {
+ Platform.runLater(runnable);
+ }
+ }
+} \ No newline at end of file
diff --git a/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/JFXUIProperties.java b/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/JFXUIProperties.java
new file mode 100755
index 000000000..15dcaa7d4
--- /dev/null
+++ b/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/JFXUIProperties.java
@@ -0,0 +1,17 @@
+/*******************************************************************************
+ * Copyright (c) 2012 BestSolution.at and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Tom Schindl<tom.schindl@bestsolution.at> - initial API and implementation
+ *******************************************************************************/
+package org.eclipse.fx.databinding;
+
+public class JFXUIProperties {
+ public static IJFXBeanValueProperty singleListViewSelection() {
+ return JFXBeanProperties.value("selectionModel.selectedItem");
+ }
+}
diff --git a/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/ObservableWritableValue.java b/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/ObservableWritableValue.java
new file mode 100755
index 000000000..6af0fb838
--- /dev/null
+++ b/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/ObservableWritableValue.java
@@ -0,0 +1,18 @@
+/*******************************************************************************
+ * Copyright (c) 2012 BestSolution.at and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Tom Schindl<tom.schindl@bestsolution.at> - initial API and implementation
+ *******************************************************************************/
+package org.eclipse.fx.databinding;
+
+import javafx.beans.value.ObservableValue;
+import javafx.beans.value.WritableValue;
+
+public interface ObservableWritableValue<E> extends ObservableValue<E>, WritableValue<E> {
+
+}
diff --git a/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/TreeUtil.java b/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/TreeUtil.java
new file mode 100755
index 000000000..49fc1f5bb
--- /dev/null
+++ b/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/TreeUtil.java
@@ -0,0 +1,104 @@
+/*******************************************************************************
+ * Copyright (c) 2012 BestSolution.at and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Tom Schindl<tom.schindl@bestsolution.at> - initial API and implementation
+ *******************************************************************************/
+package org.eclipse.fx.databinding;
+
+import java.util.Iterator;
+
+import org.eclipse.core.databinding.observable.list.IListChangeListener;
+import org.eclipse.core.databinding.observable.list.IObservableList;
+import org.eclipse.core.databinding.observable.list.ListChangeEvent;
+import org.eclipse.core.databinding.observable.list.ListDiffVisitor;
+
+import javafx.collections.ObservableList;
+import javafx.scene.control.TreeItem;
+
+public class TreeUtil {
+ public static <T> TreeItem<T> createModel(T root, ObservableFactory<T> factory) {
+ return new TreeItemImpl<T>(root,factory);
+ }
+
+ public interface ObservableFactory<T> {
+ public IObservableList createObservable(T parent);
+ }
+
+ static class TreeItemImpl<T> extends TreeItem<T> {
+ private IObservableList list;
+ private ObservableFactory<T> factory;
+ private boolean hasLoadedChildren = false;
+
+ public TreeItemImpl(T element, ObservableFactory<T> factory) {
+ setValue(element);
+ this.factory = factory;
+ this.list = factory.createObservable(element);
+ }
+
+ @Override
+ public ObservableList<TreeItem<T>> getChildren() {
+ if (hasLoadedChildren == false) {
+ loadChildren();
+ }
+ return super.getChildren();
+ }
+
+ public boolean isLeaf() {
+ if (hasLoadedChildren == false) {
+ loadChildren();
+ }
+ return super.getChildren().isEmpty();
+ }
+
+ private void loadChildren() {
+ hasLoadedChildren = true;
+ if( list != null ) {
+ final ObservableList<TreeItem<T>> itemList = getChildren();
+ list.addListChangeListener(new IListChangeListener() {
+
+ @Override
+ public void handleListChange(ListChangeEvent event) {
+ event.diff.accept(new ListDiffVisitor() {
+
+ @Override
+ public void handleRemove(int index, Object element) {
+ if( itemList.size() < index ) {
+ TreeItem<T> t = itemList.get(index);
+ if( t.getValue() == element ) {
+ itemList.remove(index);
+ } else {
+ Iterator<TreeItem<T>> it = itemList.iterator();
+ while(it.hasNext()) {
+ if( it.next().getValue() == element ) {
+ it.remove();
+ break;
+ }
+ }
+ }
+ }
+ }
+
+ @Override
+ public void handleAdd(int index, Object element) {
+ if( itemList.size() > index ) {
+ itemList.add(index, new TreeItemImpl<T>((T) element, factory));
+ } else {
+ itemList.add(new TreeItemImpl<T>((T) element, factory));
+ }
+ }
+ });
+ }
+ });
+ for( Object o : list ) {
+ itemList.add(new TreeItemImpl<T>((T) o, factory));
+ }
+ }
+ }
+
+ }
+}
diff --git a/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/internal/AnonymousFXBeanValueProperty.java b/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/internal/AnonymousFXBeanValueProperty.java
new file mode 100755
index 000000000..f6e799622
--- /dev/null
+++ b/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/internal/AnonymousFXBeanValueProperty.java
@@ -0,0 +1,86 @@
+/*******************************************************************************
+ * Copyright (c) 2008, 2009 Matthew Hall and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Matthew Hall - initial API and implementation (bug 247997)
+ * Matthew Hall - bugs 264307, 264619
+ ******************************************************************************/
+
+package org.eclipse.fx.databinding.internal;
+
+import java.util.HashMap;
+import java.util.Map;
+
+import org.eclipse.core.databinding.observable.masterdetail.MasterDetailObservables;
+import org.eclipse.core.databinding.observable.value.IObservableValue;
+import org.eclipse.core.databinding.property.value.DelegatingValueProperty;
+import org.eclipse.core.databinding.property.value.IValueProperty;
+import org.eclipse.fx.databinding.JFXBeanProperties;
+
+
+/**
+ * @since 3.3
+ *
+ */
+public class AnonymousFXBeanValueProperty extends DelegatingValueProperty {
+ private final String propertyName;
+
+ private Map<Class<?>,IValueProperty> delegates;
+
+ /**
+ * @param propertyName
+ * @param valueType
+ */
+ public AnonymousFXBeanValueProperty(String propertyName, Class<?> valueType) {
+ super(valueType);
+ this.propertyName = propertyName;
+ this.delegates = new HashMap<Class<?>,IValueProperty>();
+ }
+
+ protected IValueProperty doGetDelegate(Object source) {
+ return getClassDelegate(source.getClass());
+ }
+
+ private IValueProperty getClassDelegate(Class<?> beanClass) {
+ if (delegates.containsKey(beanClass))
+ return delegates.get(beanClass);
+
+ IValueProperty delegate;
+ try {
+ delegate = JFXBeanProperties.value(beanClass, propertyName,
+ (Class<?>) getValueType());
+ } catch (IllegalArgumentException noSuchProperty) {
+ delegate = null;
+ }
+ delegates.put(beanClass, delegate);
+ return delegate;
+ }
+
+ public IObservableValue observeDetail(IObservableValue master) {
+ Object valueType = getValueType();
+ if (valueType == null)
+ valueType = inferValueType(master.getValueType());
+ return MasterDetailObservables.detailValue(master, valueFactory(master
+ .getRealm()), valueType);
+ }
+
+ private Object inferValueType(Object masterObservableValueType) {
+ if (masterObservableValueType instanceof Class) {
+ return getClassDelegate((Class<?>) masterObservableValueType)
+ .getValueType();
+ }
+ return null;
+ }
+
+ public String toString() {
+ String s = "?." + propertyName; //$NON-NLS-1$
+ Class<?> valueType = (Class<?>) getValueType();
+ if (valueType != null)
+ s += "<" + FXBeanPropertyHelper.shortClassName(valueType) + ">"; //$NON-NLS-1$//$NON-NLS-2$
+ return s;
+ }
+}
diff --git a/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/internal/FXBeanObservableValueDecorator.java b/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/internal/FXBeanObservableValueDecorator.java
new file mode 100755
index 000000000..71124468d
--- /dev/null
+++ b/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/internal/FXBeanObservableValueDecorator.java
@@ -0,0 +1,58 @@
+/*******************************************************************************
+ * Copyright (c) 2007, 2008 Brad Reynolds and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Brad Reynolds - initial API and implementation
+ * Matthew Hall - bug 246625
+ ******************************************************************************/
+
+package org.eclipse.fx.databinding.internal;
+
+import java.beans.PropertyDescriptor;
+
+import org.eclipse.core.databinding.observable.IObservable;
+import org.eclipse.core.databinding.observable.IObserving;
+import org.eclipse.core.databinding.observable.value.DecoratingObservableValue;
+import org.eclipse.core.databinding.observable.value.IObservableValue;
+import org.eclipse.fx.databinding.IJFXBeanObservable;
+
+
+/**
+ * {@link IJFXBeanObservable} decorator for an {@link IObservableValue}.
+ *
+ * @since 3.3
+ */
+public class FXBeanObservableValueDecorator extends DecoratingObservableValue
+ implements IJFXBeanObservable {
+ private PropertyDescriptor propertyDescriptor;
+
+ /**
+ * @param decorated
+ * @param propertyDescriptor
+ */
+ public FXBeanObservableValueDecorator(IObservableValue decorated,
+ PropertyDescriptor propertyDescriptor) {
+ super(decorated, true);
+ this.propertyDescriptor = propertyDescriptor;
+ }
+
+ public synchronized void dispose() {
+ this.propertyDescriptor = null;
+ super.dispose();
+ }
+
+ public Object getObserved() {
+ IObservable decorated = getDecorated();
+ if (decorated instanceof IObserving)
+ return ((IObserving) decorated).getObserved();
+ return null;
+ }
+
+ public PropertyDescriptor getPropertyDescriptor() {
+ return propertyDescriptor;
+ }
+}
diff --git a/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/internal/FXBeanPropertyHelper.java b/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/internal/FXBeanPropertyHelper.java
new file mode 100755
index 000000000..c9ac47a7a
--- /dev/null
+++ b/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/internal/FXBeanPropertyHelper.java
@@ -0,0 +1,241 @@
+/*******************************************************************************
+ * Copyright (c) 2009 Matthew Hall and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Matthew Hall - initial API and implementation
+ ******************************************************************************/
+package org.eclipse.fx.databinding.internal;
+
+import java.beans.BeanInfo;
+import java.beans.IntrospectionException;
+import java.beans.Introspector;
+import java.beans.PropertyDescriptor;
+import java.lang.reflect.InvocationTargetException;
+import java.lang.reflect.Method;
+import java.util.ArrayList;
+import java.util.List;
+
+import org.eclipse.core.databinding.observable.value.IObservableValue;
+
+public class FXBeanPropertyHelper {
+ /**
+ * Sets the contents of the given property on the given source object to the
+ * given value.
+ *
+ * @param source
+ * the source object which has the property being updated
+ * @param propertyDescriptor
+ * the property being changed
+ * @param value
+ * the new value of the property
+ */
+ public static void writeProperty(Object source,
+ PropertyDescriptor propertyDescriptor, Object value) {
+ try {
+ Method writeMethod = propertyDescriptor.getWriteMethod();
+ if (null == writeMethod) {
+ throw new IllegalArgumentException(
+ "Missing public setter method for " //$NON-NLS-1$
+ + propertyDescriptor.getName() + " property"); //$NON-NLS-1$
+ }
+ if (!writeMethod.isAccessible()) {
+ writeMethod.setAccessible(true);
+ }
+
+ writeMethod.invoke(source, new Object[] { value });
+ } catch (InvocationTargetException e) {
+ /*
+ * InvocationTargetException wraps any exception thrown by the
+ * invoked method.
+ */
+ throw new RuntimeException(e.getCause());
+ } catch (Exception e) {
+//TODO Problems with primitive values
+ /*if (BeansObservables.DEBUG) {
+ Policy
+ .getLog()
+ .log(
+ new Status(
+ IStatus.WARNING,
+ Policy.JFACE_DATABINDING,
+ IStatus.OK,
+ "Could not change value of " + source + "." + propertyDescriptor.getName(), e)); //$NON-NLS-1$ //$NON-NLS-2$
+ }*/
+ }
+ }
+
+ /**
+ * Returns the contents of the given property for the given bean.
+ *
+ * @param source
+ * the source bean
+ * @param propertyDescriptor
+ * the property to retrieve
+ * @return the contents of the given property for the given bean.
+ */
+ public static Object readProperty(Object source,
+ PropertyDescriptor propertyDescriptor) {
+ try {
+ Method readMethod = propertyDescriptor.getReadMethod();
+ if (readMethod == null) {
+ throw new IllegalArgumentException(propertyDescriptor.getName()
+ + " property does not have a read method."); //$NON-NLS-1$
+ }
+ if (!readMethod.isAccessible()) {
+ readMethod.setAccessible(true);
+ }
+ return readMethod.invoke(source);
+ } catch (InvocationTargetException e) {
+ /*
+ * InvocationTargetException wraps any exception thrown by the
+ * invoked method.
+ */
+ throw new RuntimeException(e.getCause());
+ } catch (Exception e) {
+ e.printStackTrace();
+ /*if (BeansObservables.DEBUG) {
+ Policy
+ .getLog()
+ .log(
+ new Status(
+ IStatus.WARNING,
+ Policy.JFACE_DATABINDING,
+ IStatus.OK,
+ "Could not read value of " + source + "." + propertyDescriptor.getName(), e)); //$NON-NLS-1$ //$NON-NLS-2$
+ }*/
+ return null;
+ }
+ }
+
+ /**
+ * Returns the element type of the given collection-typed property for the
+ * given bean.
+ *
+ * @param descriptor
+ * the property being inspected
+ * @return the element type of the given collection-typed property if it is
+ * an array property, or Object.class otherwise.
+ */
+ public static Class getCollectionPropertyElementType(
+ PropertyDescriptor descriptor) {
+ Class propertyType = descriptor.getPropertyType();
+ return propertyType.isArray() ? propertyType.getComponentType()
+ : Object.class;
+ }
+
+ /**
+ * @param beanClass
+ * @param propertyName
+ * @return the PropertyDescriptor for the named property on the given bean
+ * class
+ */
+ public static PropertyDescriptor getPropertyDescriptor(Class beanClass,
+ String propertyName) {
+ if (!beanClass.isInterface()) {
+ BeanInfo beanInfo;
+ try {
+ beanInfo = Introspector.getBeanInfo(beanClass);
+ } catch (IntrospectionException e) {
+ // cannot introspect, give up
+ return null;
+ }
+ PropertyDescriptor[] propertyDescriptors = beanInfo
+ .getPropertyDescriptors();
+ for (int i = 0; i < propertyDescriptors.length; i++) {
+ PropertyDescriptor descriptor = propertyDescriptors[i];
+ if (descriptor.getName().equals(propertyName)) {
+ return descriptor;
+ }
+ }
+ } else {
+ try {
+ PropertyDescriptor propertyDescriptors[];
+ List pds = new ArrayList();
+ getInterfacePropertyDescriptors(pds, beanClass);
+ if (pds.size() > 0) {
+ propertyDescriptors = (PropertyDescriptor[]) pds
+ .toArray(new PropertyDescriptor[pds.size()]);
+ PropertyDescriptor descriptor;
+ for (int i = 0; i < propertyDescriptors.length; i++) {
+ descriptor = propertyDescriptors[i];
+ if (descriptor.getName().equals(propertyName))
+ return descriptor;
+ }
+ }
+ } catch (IntrospectionException e) {
+ // cannot introspect, give up
+ return null;
+ }
+ }
+ throw new IllegalArgumentException(
+ "Could not find property with name " + propertyName + " in class " + beanClass); //$NON-NLS-1$ //$NON-NLS-2$
+ }
+
+ /**
+ * Goes recursively into the interface and gets all defined
+ * propertyDescriptors
+ *
+ * @param propertyDescriptors
+ * The result list of all PropertyDescriptors the given interface
+ * defines (hierarchical)
+ * @param iface
+ * The interface to fetch the PropertyDescriptors
+ * @throws IntrospectionException
+ */
+ private static void getInterfacePropertyDescriptors(
+ List propertyDescriptors, Class iface)
+ throws IntrospectionException {
+ BeanInfo beanInfo = Introspector.getBeanInfo(iface);
+ PropertyDescriptor[] pds = beanInfo.getPropertyDescriptors();
+ for (int i = 0; i < pds.length; i++) {
+ PropertyDescriptor pd = pds[i];
+ propertyDescriptors.add(pd);
+ }
+ Class[] subIntfs = iface.getInterfaces();
+ for (int j = 0; j < subIntfs.length; j++) {
+ getInterfacePropertyDescriptors(propertyDescriptors, subIntfs[j]);
+ }
+ }
+
+ /**
+ * @param observable
+ * @param propertyName
+ * @return property descriptor or <code>null</code>
+ */
+ /* package */public static PropertyDescriptor getValueTypePropertyDescriptor(
+ IObservableValue observable, String propertyName) {
+ if (observable.getValueType() != null)
+ return getPropertyDescriptor((Class) observable.getValueType(),
+ propertyName);
+ return null;
+ }
+
+ /**
+ * @param propertyDescriptor
+ * @return String description of property descriptor
+ */
+ public static String propertyName(PropertyDescriptor propertyDescriptor) {
+ Class beanClass = propertyDescriptor.getReadMethod()
+ .getDeclaringClass();
+ return shortClassName(beanClass)
+ + "." + propertyDescriptor.getName() + ""; //$NON-NLS-1$ //$NON-NLS-2$
+ }
+
+ /**
+ * @param beanClass
+ * @return class name excluding package
+ */
+ public static String shortClassName(Class beanClass) {
+ if (beanClass == null)
+ return "?"; //$NON-NLS-1$
+ String className = beanClass.getName();
+ int lastDot = className.lastIndexOf('.');
+ if (lastDot != -1)
+ className = className.substring(lastDot + 1);
+ return className;
+ }
+}
diff --git a/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/internal/FXBeanPropertyListener.java b/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/internal/FXBeanPropertyListener.java
new file mode 100755
index 000000000..c7579dbfe
--- /dev/null
+++ b/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/internal/FXBeanPropertyListener.java
@@ -0,0 +1,88 @@
+/*******************************************************************************
+ * Copyright (c) 2009 Matthew Hall and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Matthew Hall - initial API and implementation (bug 265561)
+ * Matthew Hall - bug 268336
+ ******************************************************************************/
+
+package org.eclipse.fx.databinding.internal;
+
+import java.beans.PropertyDescriptor;
+import java.util.HashMap;
+import java.util.Map;
+
+import javafx.beans.value.ChangeListener;
+import javafx.beans.value.ObservableValue;
+
+import org.eclipse.core.databinding.observable.IDiff;
+import org.eclipse.core.databinding.property.IProperty;
+import org.eclipse.core.databinding.property.ISimplePropertyListener;
+import org.eclipse.core.databinding.property.NativePropertyListener;
+
+/**
+ * @since 3.3
+ *
+ */
+public abstract class FXBeanPropertyListener extends NativePropertyListener {
+ private final PropertyDescriptor propertyDescriptor;
+ private final Map<Object, ChangeListener<Object>> map = new HashMap<Object, ChangeListener<Object>>();
+
+ protected FXBeanPropertyListener(IProperty property,
+ PropertyDescriptor propertyDescriptor,
+ ISimplePropertyListener listener) {
+ super(property, listener);
+ this.propertyDescriptor = propertyDescriptor;
+ }
+
+ public void propertyChange(java.beans.PropertyChangeEvent evt) {
+ if (evt.getPropertyName() == null
+ || propertyDescriptor.getName().equals(evt.getPropertyName())) {
+ Object oldValue = evt.getOldValue();
+ Object newValue = evt.getNewValue();
+ IDiff diff;
+ if (evt.getPropertyName() == null || oldValue == null
+ || newValue == null)
+ diff = null;
+ else
+ diff = computeDiff(oldValue, newValue);
+ fireChange(evt.getSource(), diff);
+ }
+ }
+
+ protected abstract IDiff computeDiff(Object oldValue, Object newValue);
+
+ protected void doAddTo(Object source) {
+ if( ! map.containsKey(source) ) {
+ ChangeListener<Object> l = new ChangeListener<Object>() {
+
+ @Override
+ public void changed(ObservableValue<? extends Object> source,
+ Object oldValue, Object newValue) {
+ IDiff diff;
+ if (oldValue == null || newValue == null)
+ diff = null;
+ else
+ diff = computeDiff(oldValue, newValue);
+ fireChange(source, diff);
+ }
+ };
+ map.put(source, l);
+ FXBeanPropertyListenerSupport.hookListener(source,
+ propertyDescriptor.getName(), l);
+ }
+
+ }
+
+ protected void doRemoveFrom(Object source) {
+ ChangeListener<Object> l = map.get(source);
+ if (l != null) {
+ FXBeanPropertyListenerSupport.unhookListener(source,
+ propertyDescriptor.getName(), l);
+ }
+ }
+} \ No newline at end of file
diff --git a/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/internal/FXBeanPropertyListenerSupport.java b/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/internal/FXBeanPropertyListenerSupport.java
new file mode 100755
index 000000000..0770c21bc
--- /dev/null
+++ b/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/internal/FXBeanPropertyListenerSupport.java
@@ -0,0 +1,119 @@
+/*******************************************************************************
+ * Copyright (c) 2005, 2009 IBM Corporation and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * IBM Corporation - initial API and implementation
+ * Matthew Hall - bug 118516
+ *******************************************************************************/
+package org.eclipse.fx.databinding.internal;
+
+import java.lang.reflect.InvocationTargetException;
+import java.lang.reflect.Method;
+
+import javafx.beans.value.ChangeListener;
+import javafx.beans.value.ObservableValue;
+
+import org.eclipse.core.runtime.Assert;
+import org.eclipse.core.runtime.IStatus;
+
+/**
+ * This is a helper that will hook up and listen for
+ * <code>PropertyChangeEvent</code> events for a set of target JavaBeans
+ *
+ * @since 1.0
+ */
+public class FXBeanPropertyListenerSupport {
+ /**
+ * Start listen to target (if it supports the JavaBean property change
+ * listener pattern)
+ *
+ * @param bean
+ * @param propertyName
+ * @param listener
+ */
+ public static void hookListener(Object bean, String propertyName,
+ ChangeListener<Object> listener) {
+ Assert.isNotNull(bean, "Bean cannot be null"); //$NON-NLS-1$
+ Assert.isNotNull(listener, "Listener cannot be null"); //$NON-NLS-1$
+ Assert.isNotNull(propertyName, "Property name cannot be null"); //$NON-NLS-1$
+ processListener(bean, propertyName, listener,
+ /*"addPropertyChangeListener",*/ "Could not attach listener to ");//$NON-NLS-1$ //$NON-NLS-2$
+ }
+
+ /**
+ * Stop listen to target
+ *
+ * @param bean
+ * @param propertyName
+ * @param listener
+ */
+ public static void unhookListener(Object bean, String propertyName,
+ ChangeListener<Object> listener) {
+ Assert.isNotNull(bean, "Bean cannot be null"); //$NON-NLS-1$
+ Assert.isNotNull(listener, "Listener cannot be null"); //$NON-NLS-1$
+ Assert.isNotNull(propertyName, "Property name cannot be null"); //$NON-NLS-1$
+
+ processListener(
+ bean,
+ propertyName,
+ listener,
+ /*"removePropertyChangeListener",*/ "Cound not remove listener from "); //$NON-NLS-1$ //$NON-NLS-2$
+ }
+
+ /**
+ * Invokes the method for the provided <code>methodName</code> attempting to
+ * first use the method with the property name and then the unnamed version.
+ *
+ * @param bean
+ * object to invoke the method on
+ * @param methodName
+ * either addPropertyChangeListener or
+ * removePropertyChangeListener
+ * @param message
+ * string that will be prefixed to the target in an error message
+ *
+ * @return <code>true</code> if the method was invoked successfully
+ */
+ @SuppressWarnings("unchecked")
+ private static boolean processListener(Object bean, String propertyName,
+ ChangeListener<Object> listener, /*String methodName,*/ String message) {
+ try {
+ Method method = bean.getClass().getMethod(propertyName+"Property");
+ Object observable = method.invoke(bean);
+ if( observable instanceof ObservableValue<?> ) {
+ ((ObservableValue<Object>) observable).addListener(listener);
+ return true;
+ } else {
+ log(IStatus.WARNING, message, null);
+ }
+
+ } catch (SecurityException e) {
+ // ignore
+ } catch (NoSuchMethodException e) {
+ log(IStatus.WARNING, message + bean, e);
+ } catch (IllegalArgumentException e) {
+ log(IStatus.WARNING, message + bean, e);
+ } catch (IllegalAccessException e) {
+ log(IStatus.WARNING, message + bean, e);
+ } catch (InvocationTargetException e) {
+ log(IStatus.WARNING, message + bean, e);
+ }
+
+ return false;
+ }
+
+ /**
+ * Logs a message to the Data Binding logger.
+ */
+ private static void log(int severity, String message, Throwable throwable) {
+ /*if (BeansObservables.DEBUG) {
+ Policy.getLog().log(
+ new Status(severity, Policy.JFACE_DATABINDING, IStatus.OK,
+ message, throwable));
+ }*/
+ }
+}
diff --git a/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/internal/FXBeanValueProperty.java b/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/internal/FXBeanValueProperty.java
new file mode 100755
index 000000000..fc6541e72
--- /dev/null
+++ b/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/internal/FXBeanValueProperty.java
@@ -0,0 +1,69 @@
+/*******************************************************************************
+ * Copyright (c) 2008, 2009 Matthew Hall and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Matthew Hall - initial API and implementation (bug 194734)
+ * Matthew Hall - bug 195222, 264307, 265561
+ ******************************************************************************/
+
+package org.eclipse.fx.databinding.internal;
+
+import java.beans.PropertyDescriptor;
+
+import org.eclipse.core.databinding.observable.Diffs;
+import org.eclipse.core.databinding.observable.IDiff;
+import org.eclipse.core.databinding.property.INativePropertyListener;
+import org.eclipse.core.databinding.property.ISimplePropertyListener;
+import org.eclipse.core.databinding.property.value.SimpleValueProperty;
+
+/**
+ * @since 3.3
+ *
+ */
+public class FXBeanValueProperty extends SimpleValueProperty {
+ private final PropertyDescriptor propertyDescriptor;
+ private final Class valueType;
+
+ /**
+ * @param propertyDescriptor
+ * @param valueType
+ */
+ public FXBeanValueProperty(PropertyDescriptor propertyDescriptor,
+ Class valueType) {
+ this.propertyDescriptor = propertyDescriptor;
+ this.valueType = valueType == null ? propertyDescriptor
+ .getPropertyType() : valueType;
+ }
+
+ public Object getValueType() {
+ return valueType;
+ }
+
+ protected Object doGetValue(Object source) {
+ return FXBeanPropertyHelper.readProperty(source, propertyDescriptor);
+ }
+
+ protected void doSetValue(Object source, Object value) {
+ FXBeanPropertyHelper.writeProperty(source, propertyDescriptor, value);
+ }
+
+ public INativePropertyListener adaptListener(
+ final ISimplePropertyListener listener) {
+ return new FXBeanPropertyListener(this, propertyDescriptor, listener) {
+ protected IDiff computeDiff(Object oldValue, Object newValue) {
+ return Diffs.createValueDiff(oldValue, newValue);
+ }
+ };
+ }
+
+ public String toString() {
+ String s = FXBeanPropertyHelper.propertyName(propertyDescriptor);
+ if (valueType != null)
+ s += "<" + FXBeanPropertyHelper.shortClassName(valueType) + ">"; //$NON-NLS-1$//$NON-NLS-2$
+ return s;
+ }
+}
diff --git a/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/internal/FXBeanValuePropertyDecorator.java b/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/internal/FXBeanValuePropertyDecorator.java
new file mode 100755
index 000000000..20b1db402
--- /dev/null
+++ b/bundles/runtime/org.eclipse.fx.databinding/src/org/eclipse/fx/databinding/internal/FXBeanValuePropertyDecorator.java
@@ -0,0 +1,154 @@
+/*******************************************************************************
+ * Copyright (c) 2008, 2010 Matthew Hall and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Matthew Hall - initial API and implementation (bug 195222)
+ * Matthew Hall - bug 264307
+ ******************************************************************************/
+
+package org.eclipse.fx.databinding.internal;
+
+import java.beans.PropertyDescriptor;
+
+import org.eclipse.core.databinding.observable.Realm;
+import org.eclipse.core.databinding.observable.list.IObservableList;
+import org.eclipse.core.databinding.observable.map.IObservableMap;
+import org.eclipse.core.databinding.observable.set.IObservableSet;
+import org.eclipse.core.databinding.observable.value.IObservableValue;
+import org.eclipse.core.databinding.property.value.IValueProperty;
+import org.eclipse.core.databinding.property.value.ValueProperty;
+import org.eclipse.fx.databinding.IJFXBeanValueProperty;
+import org.eclipse.fx.databinding.JFXBeanProperties;
+
+
+/**
+ * @since 3.3
+ *
+ */
+public class FXBeanValuePropertyDecorator extends ValueProperty implements
+ IJFXBeanValueProperty {
+ private final IValueProperty delegate;
+ private final PropertyDescriptor propertyDescriptor;
+
+ /**
+ * @param delegate
+ * @param propertyDescriptor
+ */
+ public FXBeanValuePropertyDecorator(IValueProperty delegate,
+ PropertyDescriptor propertyDescriptor) {
+ this.delegate = delegate;
+ this.propertyDescriptor = propertyDescriptor;
+ }
+
+ public PropertyDescriptor getPropertyDescriptor() {
+ return propertyDescriptor;
+ }
+
+ public Object getValueType() {
+ return delegate.getValueType();
+ }
+
+ protected Object doGetValue(Object source) {
+ return delegate.getValue(source);
+ }
+
+ protected void doSetValue(Object source, Object value) {
+ delegate.setValue(source, value);
+ }
+
+ public IJFXBeanValueProperty value(String propertyName) {
+ return value(propertyName, null);
+ }
+
+ public IJFXBeanValueProperty value(String propertyName, Class valueType) {
+ Class beanClass = (Class) delegate.getValueType();
+ return value(JFXBeanProperties.value(beanClass, propertyName, valueType));
+ }
+
+ public IJFXBeanValueProperty value(IJFXBeanValueProperty property) {
+ return new FXBeanValuePropertyDecorator(super.value(property),
+ property.getPropertyDescriptor());
+ }
+
+ /*public IBeanListProperty list(String propertyName) {
+ return list(propertyName, null);
+ }
+
+ public IBeanListProperty list(String propertyName, Class elementType) {
+ Class beanClass = (Class) delegate.getValueType();
+ return list(BeanProperties.list(beanClass, propertyName, elementType));
+ }
+
+ public IBeanListProperty list(IBeanListProperty property) {
+ return new BeanListPropertyDecorator(super.list(property),
+ property.getPropertyDescriptor());
+ }
+
+ public IBeanSetProperty set(String propertyName) {
+ return set(propertyName, null);
+ }
+
+ public IBeanSetProperty set(String propertyName, Class elementType) {
+ Class beanClass = (Class) delegate.getValueType();
+ return set(BeanProperties.set(beanClass, propertyName, elementType));
+ }
+
+ public IBeanSetProperty set(IBeanSetProperty property) {
+ return new BeanSetPropertyDecorator(super.set(property),
+ property.getPropertyDescriptor());
+ }
+
+ public IBeanMapProperty map(String propertyName) {
+ return map(propertyName, null, null);
+ }
+
+ public IBeanMapProperty map(String propertyName, Class keyType,
+ Class valueType) {
+ Class beanClass = (Class) delegate.getValueType();
+ return map(BeanProperties.map(beanClass, propertyName, keyType,
+ valueType));
+ }
+
+ public IBeanMapProperty map(IBeanMapProperty property) {
+ return new BeanMapPropertyDecorator(super.map(property),
+ property.getPropertyDescriptor());
+ }*/
+
+ public IObservableValue observe(Object source) {
+ return new FXBeanObservableValueDecorator(delegate.observe(source),
+ propertyDescriptor);
+ }
+
+ public IObservableValue observe(Realm realm, Object source) {
+ return new FXBeanObservableValueDecorator(
+ delegate.observe(realm, source), propertyDescriptor);
+ }
+
+ public IObservableValue observeDetail(IObservableValue master) {
+ return new FXBeanObservableValueDecorator(delegate.observeDetail(master),
+ propertyDescriptor);
+ }
+
+ /*public IObservableList observeDetail(IObservableList master) {
+ return new FXBeanObservableListDecorator(delegate.observeDetail(master),
+ propertyDescriptor);
+ }
+
+ public IObservableMap observeDetail(IObservableSet master) {
+ return new FXBeanObservableMapDecorator(delegate.observeDetail(master),
+ propertyDescriptor);
+ }
+
+ public IObservableMap observeDetail(IObservableMap master) {
+ return new FXBeanObservableMapDecorator(delegate.observeDetail(master),
+ propertyDescriptor);
+ }*/
+
+ public String toString() {
+ return delegate.toString();
+ }
+}

Back to the top