dooapp / xstreamfx Goto Github PK
View Code? Open in Web Editor NEWConverters collection for JavaFX types
Converters collection for JavaFX types
Starting with a simple class for a person
package xstreamfxextensions;
import com.thoughtworks.xstream.annotations.XStreamAlias;
import com.thoughtworks.xstream.annotations.XStreamImplicit;
import javafx.beans.property.IntegerProperty;
import javafx.beans.property.ObjectProperty;
import javafx.beans.property.SimpleIntegerProperty;
import javafx.beans.property.SimpleObjectProperty;
import javafx.beans.property.SimpleStringProperty;
import javafx.beans.property.StringProperty;
import javafx.collections.FXCollections;
import javafx.collections.ObservableList;
@XStreamAlias("Person") //define class level alias
public class Person {
@XStreamAlias("Sex")
public enum Sex {
MALE, FEMALE, UNKNOWN, OTHER
};
public StringProperty name = new SimpleStringProperty(this, "name", "nameless");
public IntegerProperty age = new SimpleIntegerProperty(this, "age", 0);
public ObjectProperty<Sex> sex = new SimpleObjectProperty<>(this, "sex", Sex.MALE);
public ObservableList<Person> children = FXCollections.<Person>observableArrayList();
public Person(String name, int age, Sex sex) {
this.name.set(name);
this.age.set(age);
this.sex.set(sex);
}
@Override
public String toString() {
return "Person{"
+ "name=" + name.get()
+ ", age=" + age.get()
+ ", sex=" + sex.get()
+ ", children=" + children
+ '}';
}
}
A simple test class to use XStream and XStreamFX to externalise and internalise some people.
package xstreamfxextensions;
import com.dooapp.xstreamfx.FXConverters;
import com.sun.javafx.collections.ObservableListWrapper;
import com.thoughtworks.xstream.XStream;
import com.thoughtworks.xstream.io.xml.StaxDriver;
import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.nio.file.Files;
import java.nio.file.Paths;
import javafx.beans.property.SimpleBooleanProperty;
import javafx.beans.property.SimpleFloatProperty;
import javafx.beans.property.SimpleIntegerProperty;
import javafx.beans.property.SimpleListProperty;
import javafx.beans.property.SimpleLongProperty;
import javafx.beans.property.SimpleMapProperty;
import javafx.beans.property.SimpleObjectProperty;
import javafx.beans.property.SimpleSetProperty;
import javafx.beans.property.SimpleStringProperty;
import javax.xml.transform.OutputKeys;
import javax.xml.transform.Source;
import javax.xml.transform.Transformer;
import javax.xml.transform.sax.SAXSource;
import javax.xml.transform.sax.SAXTransformerFactory;
import javax.xml.transform.stream.StreamResult;
import org.junit.Test;
import org.xml.sax.InputSource;
import xstreamfxextensions.Person.Sex;
public class XStreamFXExtensionsTest {
/**
* Add XStream aliases for common JavaFX types
*
* @param xstream
*/
public static void addFXAliases(XStream xstream) {
Class[] cs = new Class[]{
ObservableListWrapper.class,
// The Simple... properties
SimpleStringProperty.class,
SimpleIntegerProperty.class,
SimpleObjectProperty.class,
SimpleFloatProperty.class,
SimpleBooleanProperty.class,
SimpleListProperty.class,
SimpleLongProperty.class,
SimpleMapProperty.class,
SimpleSetProperty.class,
SimpleFloatProperty.class,};
for (Class c : cs) { //
// Alias the class's simple name to its pull name
xstream.alias(c.getSimpleName(), c);
}
}
@Test
public void testSXtreamPerson() throws IOException {
XStream xstream = new XStream(new StaxDriver());
Person fred = new Person("Fred", 71, Sex.MALE);
fred.children.add(new Person("Paul", 21, Sex.MALE));
fred.children.add(new Person("James", 20, Sex.MALE));
fred.children.add(new Person("Angela", 20, Sex.FEMALE));
xstream.autodetectAnnotations(true);
FXConverters.configure(xstream);
addFXAliases(xstream);
//Object to XML Conversion
String xml = formatXml(xstream.toXML(fred));
Files.write(Paths.get("PeopleImplicit.xml"), xml.getBytes());
//XML to Object Conversion
Person a = (Person) xstream.fromXML(xml);
System.out.println(a);
}
public static String formatXml(String xml) {
try {
Transformer serializer = SAXTransformerFactory.newInstance().newTransformer();
serializer.setOutputProperty(OutputKeys.INDENT, "yes");
serializer.setOutputProperty("{http://xml.apache.org/xslt}indent-amount", "2");
Source xmlSource = new SAXSource(new InputSource(new ByteArrayInputStream(xml.getBytes())));
StreamResult res = new StreamResult(new ByteArrayOutputStream());
serializer.transform(xmlSource, res);
return new String(((ByteArrayOutputStream) res.getOutputStream()).toByteArray());
} catch (Exception e) {
return xml;
}
}
}
Running this results in error:
Testcase: testSXtreamPerson(xstreamfxextensions.XStreamFXExtensionsTest): Caused an ERROR
Cannot instantiate com.sun.javafx.collections.ObservableListWrapper : com.sun.javafx.collections.ObservableListWrapper
---- Debugging information ----
message : Cannot instantiate com.sun.javafx.collections.ObservableListWrapper
cause-exception : java.lang.InstantiationException
cause-message : com.sun.javafx.collections.ObservableListWrapper
class : com.sun.javafx.collections.ObservableListWrapper
required-type : com.sun.javafx.collections.ObservableListWrapper
converter-type : com.dooapp.xstreamfx.ObservableListConverter
path : /Person/children
line number : 5
class[1] : xstreamfxextensions.Person
converter-type[1] : com.thoughtworks.xstream.converters.reflection.ReflectionConverter
version : 1.4.8
-------------------------------
com.thoughtworks.xstream.converters.ConversionException: Cannot instantiate com.sun.javafx.collections.ObservableListWrapper : com.sun.javafx.collections.ObservableListWrapper
---- Debugging information ----
message : Cannot instantiate com.sun.javafx.collections.ObservableListWrapper
cause-exception : java.lang.InstantiationException
cause-message : com.sun.javafx.collections.ObservableListWrapper
class : com.sun.javafx.collections.ObservableListWrapper
required-type : com.sun.javafx.collections.ObservableListWrapper
converter-type : com.dooapp.xstreamfx.ObservableListConverter
path : /Person/children
line number : 5
class[1] : xstreamfxextensions.Person
converter-type[1] : com.thoughtworks.xstream.converters.reflection.ReflectionConverter
version : 1.4.8
-------------------------------
at com.thoughtworks.xstream.converters.collections.AbstractCollectionConverter.createCollection(AbstractCollectionConverter.java:79)
at com.thoughtworks.xstream.converters.collections.CollectionConverter.createCollection(CollectionConverter.java:103)
at com.dooapp.xstreamfx.ObservableListConverter.createCollection(ObservableListConverter.java:40)
at com.thoughtworks.xstream.converters.collections.CollectionConverter.unmarshal(CollectionConverter.java:79)
at com.thoughtworks.xstream.core.TreeUnmarshaller.convert(TreeUnmarshaller.java:72)
at com.thoughtworks.xstream.core.AbstractReferenceUnmarshaller.convert(AbstractReferenceUnmarshaller.java:65)
at com.thoughtworks.xstream.core.TreeUnmarshaller.convertAnother(TreeUnmarshaller.java:66)
at com.thoughtworks.xstream.converters.reflection.AbstractReflectionConverter.unmarshallField(AbstractReflectionConverter.java:480)
at com.thoughtworks.xstream.converters.reflection.AbstractReflectionConverter.doUnmarshal(AbstractReflectionConverter.java:412)
at com.thoughtworks.xstream.converters.reflection.AbstractReflectionConverter.unmarshal(AbstractReflectionConverter.java:263)
at com.thoughtworks.xstream.core.TreeUnmarshaller.convert(TreeUnmarshaller.java:72)
at com.thoughtworks.xstream.core.AbstractReferenceUnmarshaller.convert(AbstractReferenceUnmarshaller.java:65)
at com.thoughtworks.xstream.core.TreeUnmarshaller.convertAnother(TreeUnmarshaller.java:66)
at com.thoughtworks.xstream.core.TreeUnmarshaller.convertAnother(TreeUnmarshaller.java:50)
at com.thoughtworks.xstream.core.TreeUnmarshaller.start(TreeUnmarshaller.java:134)
at com.thoughtworks.xstream.core.AbstractTreeMarshallingStrategy.unmarshal(AbstractTreeMarshallingStrategy.java:32)
at com.thoughtworks.xstream.XStream.unmarshal(XStream.java:1206)
at com.thoughtworks.xstream.XStream.unmarshal(XStream.java:1190)
at com.thoughtworks.xstream.XStream.fromXML(XStream.java:1061)
at com.thoughtworks.xstream.XStream.fromXML(XStream.java:1052)
at xstreamfxextensions.XStreamFXExtensionsTest.testSXtreamPerson(XStreamFXExtensionsTest.java:77)
Caused by: java.lang.InstantiationException: com.sun.javafx.collections.ObservableListWrapper
at java.lang.Class.newInstance(Class.java:427)
at com.thoughtworks.xstream.converters.collections.AbstractCollectionConverter.createCollection(AbstractCollectionConverter.java:77)
Caused by: java.lang.NoSuchMethodException: com.sun.javafx.collections.ObservableListWrapper.<init>()
at java.lang.Class.getConstructor0(Class.java:3082)
at java.lang.Class.newInstance(Class.java:412)
I found modifying ObservableListConverter to
package com.dooapp.xstreamfx;
import com.sun.javafx.collections.ObservableListWrapper;
import com.thoughtworks.xstream.converters.Converter;
import com.thoughtworks.xstream.converters.collections.CollectionConverter;
import com.thoughtworks.xstream.mapper.Mapper;
import javafx.collections.FXCollections;
import javafx.collections.ObservableList;
import xstreamfxextensions.Person;
/**
* TODO write documentation<br>
* <br>
* Created at 21/09/11 09:32.<br>
*
* @author Antoine Mischler <[email protected]>
* @since 2.2
*/
public class ObservableListConverter extends CollectionConverter implements Converter {
public ObservableListConverter(Mapper mapper) {
super(mapper);
}
@Override
public boolean canConvert(Class type) {
return ObservableList.class.isAssignableFrom(type);
}
@Override
protected Object createCollection(Class type) {
if (type == ObservableListWrapper.class) {
return FXCollections.<Person>observableArrayList();
}
return super.createCollection(type);
}
}
Explanation: ObservableListWrapper does not have a no argument constructor but has to be created with the FXCollections.observableArrayList() factory method.
So all well and good...
Until you try to to mark the collection with @XStreamImplicit In which case you get the same problem.
Any help with this gratefully appreciated!
A declarative, efficient, and flexible JavaScript library for building user interfaces.
๐ Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. ๐๐๐
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google โค๏ธ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.