How to create new data types

From Endrov

This section describes the specifics of a new data type. If you want to know how to put it in a plugin, see How to make plugins.

Overview

One of the largest improvement in Endrov over past systems is the easy addition of new types of data beyond raw image data. While it is possible to use a Custom data object to store any type of data, if you want to toss around the data and write special tools to work with it, you should write a new class.

Anatomy

All objects has to extend the class EvObject. Internally such classes are called "First class Endrov objects". EvObject contains the most up to date documentation, this is mainly meant as an introduction.

public class ExampleObject extends EvObject
	{
	private static final String metaType="exampleObject";

	public static void initPlugin() {}
	static
		{
		EvData.supportedMetadataFormats.put(metaType,ExampleObject.class);
		}

First you have to tell that this object exists. metaType is the name of the object once stored on disk. May not contain spaces or any funny characters. Then when you create a plugin, you have to register this object or it will be loaded as just a random heap of XML (CustomObject).

	public String myValue="";

	public int valueLength()
		{
		return myValue.length();
		}

Then you create all the variables and function you need. This is the meat of the class. There must be a constructor which takes no arguments (if you do not create any constructors then this is fulfilled).

	@Override
	public void buildMetamenu(JMenu menu)
		{
		}

If you wish to extend the data menu for this object then you can add menu items here.

	@Override
	public String getMetaTypeDesc()
		{
		return "Example object";
		}

This is a short human-readable text description of the object. It will be used in menus etc.

	@Override
	public void loadMetadata(Element e)
		{
		myValue=e.getChild("extendedData").getAttributeValue("foo");
		}

	@Override
	public void saveMetadata(Element e)
		{
		e.setName(metaType); //Minimal requirement

		Element someData=new Element("extendedData");
		someData.setAttribute("foo",myValue);
		e.addContent(someData);
		}
	}

You have to take care of saving down and loading the variables yourself ("serializing"). You do so by working directly with the XML document model. There are no DTDs or anything, you can just write the tags you want. It is important that you set the name to be the metatype or your object will not load again.

Documentation about the XML API: JDOM

Design notes

  • There are ways of providing automatic load/save. The reason Endrov does not use it is that the optimal data layout on disk might be nothing like the layout in memory. The minimal effort of writing this functionality manually may make up for faster code and saved disk space (up to gigabytes!).
  • This design is not friendly toward backends that write the data into relational databases (SQL). On the other hand, OO-mappers tend to be unfriendly as well. I consider mixing OO (tree data) and SQL to be a major mistake.