NegotiableCapability
represents the capabilities of an object. These capabilities can be used to negotiate with the capabilities of a similar object. Each NegotiableCapability
is characterized by the category it belongs to, as returned by the getCategory()
method, by the actual name of the capability it represents, as returned by the getCapabilityName()
method and by a list of parameter name-value pairs that define the NegotiableCapability
. Every NegotiableCapability
object also holds references to a representation of the objects that generated it. These can be accessed via the getGenerators()
method. The creator or generator of a NegotiableCapability
can supply any representation of itself while constructing the NegotiableCapability
. No interpretation is forced by this class, that is left upto the generating class and to the class that utilizes the NegotiableCapability
to get the negotiated results. The negotiation is performed by the negotiate()
method. Since this method returns a NegotiableCapability
, this method can be used repeatedly to perform multiple negotiations. If the negotiation fails, null will be returned from the negotiate()
method. Every successful negotiation will add the generator of the NegotiableCapability
negotiated with, to the set of generators of the resultant NegotiableCapability
. The generators are intended to help the user of NegotiableCapability
identify the object that created the NegotiableCapability
and therefore the object that can be relied on to be able to handle the parameters agreed on during negotiation. For example, if the negotiation is to be performed to choose a compatible TileEncoder
, TileDecoder
pair for data compression/decompression, the category would be "tileCodec", the capabilityName would be a specific tile encoding format, say "jpeg" and the generator for the NegotiableCapability
could be the TileDecoderFactory
/TileEncoderFactory
object that generated that NegotiableCapability
. After a successful negotiation, the NegotiableCapability
that is the result of the negotiation will contain a TileEncoderFactory
and a TileDecoderFactory
object as the generators for that NegotiableCapability
. These two objects can then be retrieved using the getGenerators
method and used to do the encoding and decoding and can be relied to be compatible, since the negotiation was successful between their respective NegotiableCapability
objects. The number, name, Class type and default values for the parameters in this class is specified by the ParameterListDescriptor
returned from getParameterListDescriptor
method. Each parameter value in this class must be a class that implements the Negotiable
interface. It is for this reason that all of the ParameterList
set methods that take primitive data types as arguments and all the ParameterList
get methods that return primitive data types are overridden in this class to throw an IllegalArgumentException, as this class only accepts Negotiable
's as parameter values in order to facilitate negotiation on parameters. It may be noted that the implementation of the version of ParameterList.setParameter
that takes an Object
as the parameter value, in this class throws an IllegalArgumentException
if the supplied Object
to be set does not implement the Negotiable
interface. If no Negotiable
value is available as the value for a particular parameter, null
should be set as the value. A null value returned from the getNegotiatedValue(String)
method is however valid, since the single value result of the negotiation can be null. Similarly the Object
returned from the ParameterList.getObjectParameter
implementation in this class is always a class that implements the Negotiable
interface, and not a wrapper class of a primitive data type, as documented for this method in ParameterList
. The getParamValueRange(String parameterName)
and the getEnumeratedParameterValues(String parameterName)
methods of the ParameterListDescriptor
returned from getParameterListDescriptor
method of this class should be implemented to return null, since these methods are not meaningful when the parameter values are Negotiable
.
In order for the negotiation to be successful, the category and the capabilityName of the two NegotiableCapability
objects must be the same. In addition, negotiation on each of the parameters must be successful. Since each parameter is represented as a Negotiable
, negotiation on it can be performed using the Negotiable.negotiate(Negotiable negotiable)
method. The NegotiableCapability
returned from the negotiate(NegotiableCapability capability)
method contains the same category and capabilityName as that of the NegotiableCapability
objects being negotiated as well as including the negotiated values for each parameter. If the negotiation fails for any one parameter, the negotiation for the NegotiableCapability
s as a whole is said to fail (unless preference NegotiableCapability
objects are involved in the negotiation, as described below) and a null is returned.
In order to get a single negotiated value from the set of valid values represented as the Negotiable
value for a parameter, the getNegotiatedValue(String parameterName)
method can be called. If the negotiation was successful, an Object
which is the negotiated result will be returned, otherwise a null
(signifying that the negotiation failed) will be returned.
NegotiableCapability
objects can be classified as being either preferences or non-preferences. A non-preference describes the capabilities of an object completely by specifying Negotiable
values for each and every parameter defined in the ParameterListDescriptor
returned from getParameterListDescriptor
method. A non-preference is allowed to not specify the value of a particular parameter, if a default value for that parameter exists (i.e. the default value is not null
). When a non-preference is created, all parameter values are initialized to their default values, and therefore if any parameter value is left unset at the time of the negotiation, the default value that was set at time of initialization will be used for the negotiation. If the default value happened to be null
, the negotiation in this case would fail. Note that all references to values in this paragraph, whether default or not, refered to the objects implementing the Negotiable
interface that are the values set for a particular parameter name. A preference on the other hand specifies preferences for the selection of a prefered set of (maybe even a single) parameter value from the set of valid ones at negotiation time. A preference is allowed to specify Negotiable
parameter values for a subset of parameters, if it so wishes. For those parameters for whom the preference does not specify values, the preference is indicating a don't-care attitude, and the result of the negotiation for such a parameter will be the Negotiable
value from the non-preference object the preference is negotiating with. Note that the default value is not substituted for a parameter whose value has not been specified in a preference. A NegotiableCapability
which is a preference should return true from the isPreference
method, a non-preference object that defines values for all the parameters (or relies on defaults) should return false from this method. As a rule, the result of negotiation between one non-preference and another is a non-preference, between a preference and a non-preference is a non-preference and that between two preferences is a preference, if the negotiation is successful. It may be noted that preferences are not expected to specify their generators, since in general, preferences don't come from objects that can support them. However if generators are specified within a preference, they will be added to the set of generators of the resultant NegotiableCapability
in the event of a successful negotiation.
Negotiation between a preference and a non-preference NegotiableCapability
results in a non-preference NegotiableCapability
. For each parameter, if a value is specified (i.e the value is not null
) in both the preference and the non-preference, then if these values have a common subset, the negotiation will succeed on this parameter, if there is no commonality, then the negotiation will fail on this parameter and thus also fail as a whole. If the preference doesn't specify a value for a parameter (i.e the value is null
), then the value specified by the non-preference for that same parameter is chosen as a result of the successful negotiation on that parameter.
Negotiation between two preference NegotiableCapability
objects results in a preference NegotiableCapability
. For each parameter, if a value is specified (i.e the value is not null
) in both the preference objects, the negotiation on that parameter will have a value which is the portion that is common to both. If there is no commonality, negotiation will fail on this parameter (null
will be returned) and thus also fail as a whole. If the value for a particular parameter is specified in one preference and not in the other, the negotiated value will be the one specified. If for a particular parameter, no value is specified in either preference, the negotiated value for that parameter will be null
, and the negotiation as a whole on the NegotiableCapability
will not fail.
When a preference NegotiableCapability
is constructed, the values of all the parameters defined in the ParameterListDescriptor
returned from getParameterListDescriptor
method, are initialized to null
. null
within this class represents a value that has not been specified. Such values are only allowed on a preference NegotiableCapability
. On the other hand when a non-preference NegotiableCapability
is constructed, all the values are initialized to their default values.
All names are treated in a case-retentive and case-insensitive manner. @since JAI 1.1
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|