AbstractProperty.java
package org.opentrafficsim.base.modelproperties;
import java.io.Serializable;
import java.util.ArrayList;
import java.util.Iterator;
/**
* Abstract property.
* <p>
* Copyright (c) 2013-2018 Delft University of Technology, PO Box 5, 2600 AA, Delft, the Netherlands. All rights reserved. <br>
* BSD-style license. See <a href="http://opentrafficsim.org/docs/license.html">OpenTrafficSim License</a>.
* <p>
* $LastChangedDate: 2016-05-28 11:33:31 +0200 (Sat, 28 May 2016) $, @version $Revision: 2051 $, by $Author: averbraeck $,
* initial version 18 dec. 2014 <br>
* @author <a href="http://www.tudelft.nl/pknoppers">Peter Knoppers</a>
* @param <T> type of the property
*/
public abstract class AbstractProperty<T> implements Property<T>, Serializable
{
/** */
private static final long serialVersionUID = 20150000L;
/** Key of this property. */
private final String key;
/** Determines sorting order when properties are displayed to the user. */
private final int displayPriority;
/** The shortName of the property. */
private String shortName;
/** The description of the property. */
private String description;
/** The property is read-only. */
private Boolean readOnly = null;
/** Parent of this AbstractProperty. */
private CompoundProperty parentProperty = null;
/**
* Construct a new AbstractProperty.
* @param key String; unique (within this property tree) name of the new AbstractProperty
* @param displayPriority sorting order when properties are displayed to the user
* @param shortName String; concise description of the property
* @param description String; long description of the property (may use HTML markup)
*/
public AbstractProperty(final String key, final int displayPriority, final String shortName, final String description)
{
this.key = key;
this.displayPriority = displayPriority;
this.shortName = shortName;
this.description = description;
}
/**
* Finalize the readOnly flag.
* @param readOnlyValue boolean; the new value for the readonly flag
*/
// XXX Made this method public to allow changes in e.g., tests; it should really be private
public final void setReadOnly(final boolean readOnlyValue)
{
this.readOnly = readOnlyValue;
}
/** {@inheritDoc} */
@Override
public final int getDisplayPriority()
{
return this.displayPriority;
}
/** {@inheritDoc} */
@Override
public abstract String htmlStateDescription();
/** {@inheritDoc} */
@Override
public final Iterator<Property<?>> iterator()
{
return new PropertyIterator(this);
}
/** {@inheritDoc} */
@Override
public final String getShortName()
{
return this.shortName;
}
/** {@inheritDoc} */
@Override
public final String getDescription()
{
return this.description;
}
/** {@inheritDoc} */
@Override
public final boolean isReadOnly()
{
return null != this.readOnly && this.readOnly;
}
/**
* Retrieve the key of this AbstractProperty.
* @return String; the key of this AbstractProperty
*/
@Override
public final String getKey()
{
return this.key;
}
/** {@inheritDoc} */
@Override
public final Property<?> findByKey(final String propertyKey)
{
if (this.key.equals(propertyKey))
{
return this;
}
if (this instanceof CompoundProperty)
{
return ((CompoundProperty) this).getPropertyGroup().get(propertyKey);
}
if (null == getParent())
{
return null;
}
return getParent().getPropertyGroup().get(propertyKey);
}
/**
* Set the parent of this AbstractProperty.
* @param newParent AbstractProperty<?>; the new parent of this AbstractProperty
*/
protected final void setParent(final CompoundProperty newParent)
{
this.parentProperty = newParent;
}
/** {@inheritDoc} */
@Override
public final CompoundProperty getParent()
{
return this.parentProperty;
}
/** {@inheritDoc} */
@Override
public final String toString()
{
return this.getShortName();
}
/**
* Really simple iterator for properties.
* <p>
* Copyright (c) 2013-2018 Delft University of Technology, PO Box 5, 2600 AA, Delft, the Netherlands. All rights reserved.
* <br>
* BSD-style license. See <a href="http://opentrafficsim.org/docs/license.html">OpenTrafficSim License</a>.
* <p>
* $LastChangedDate: 2016-05-28 11:33:31 +0200 (Sat, 28 May 2016) $, @version $Revision: 2051 $, by $Author: averbraeck $,
* initial version jan. 2015 <br>
* @author <a href="http://www.tudelft.nl/pknoppers">Peter Knoppers</a>
*/
class PropertyIterator implements Iterator<Property<?>>, Serializable
{
/** */
private static final long serialVersionUID = 20150000L;
/** Next in line in the main CompoundProperty. */
private int currentIndex;
/** Full list of Properties. */
private final ArrayList<Property<?>> list;
/**
* Construct a new PropertyIterator.
* @param ap AbstractProperty; root of the tree to iterate over
*/
PropertyIterator(final Property<T> ap)
{
this.currentIndex = 0;
this.list = new ArrayList<Property<?>>();
addToList(ap);
}
/**
* Recursively add all properties to the list. <br>
* Compound properties are included <b>right before</b> their contents.
* @param cp AbstractProperty<T>; the property to add (if compound it and all it's children are added)
*/
private void addToList(final Property<?> cp)
{
this.list.add(cp);
if (cp instanceof CompoundProperty)
{
for (Property<?> ap : ((CompoundProperty) cp).getValue())
{
addToList(ap);
}
}
}
/** {@inheritDoc} */
@Override
public boolean hasNext()
{
return this.currentIndex < this.list.size();
}
/** {@inheritDoc} */
@Override
public Property<?> next()
{
return this.list.get(this.currentIndex++);
}
/** {@inheritDoc} */
@Override
public void remove()
{
throw new UnsupportedOperationException();
}
/** {@inheritDoc} */
@Override
public String toString()
{
return "PropertyIterator [currentIndex=" + this.currentIndex + ", list=" + this.list + "]";
}
}
}