|
|||||||||||
PREV CLASS NEXT CLASS | FRAMES NO FRAMES | ||||||||||
SUMMARY: NESTED | FIELD | CONSTR | METHOD | DETAIL: FIELD | CONSTR | METHOD |
This interface implements part of the visitor pattern for colors.
In object-oriented design a pattern has been established to let one class
react on the type of some object. Consider different color models represented
in color objects of different types. All share a common base interface. This
is the situation for
Color
s for which several
types exist.
The original idea was to attach the desired functionality to the nodes and
let it have one common method to invoke it. This turns out not to be
practical for modular components where the algorithm might be exchanged.
This is the case for the
ColorConverter
which might produce any converted Color in any other model. Any new
implementation of the color interface would have the need to extend all Color
classes.
The other simplistic solution is to use a large switch, or cascaded if-then-else, to differentiate the cases. This kind of code is cumbersome to maintain. Whenever a new type of node is added you have to remember all places which need adaption.
This problem is solved in the visitor pattern. Each class or interface of the colors has to provide one method called visit() here. This method has as one argument the visitor which should be called back. The visitor is defined by this interface. He has to provide a set of methods which allow him to differentiate the types of the colors.
Each color has to implement the method visit() in a way that the appropriate method from the visitor interface is invoked. Thus as a result the colors and the algorithm are decoupled.
A detailed description of the mechanics of a visitor can be found in the
documentation for the NodeVisitor
.
Consider you have a class implementing DocumentWriter with a method which needs to react differently on different color types. The first approximation looks as follows:
public class MyDocumentWriter implements DocumentWriter { public void myMethod(final Color color) { // Do something with color depending on its type } }
Now we can add the ColorVisitor interface. Thus we are forced to define a bunch of methods declared in this interface:
public class MyDocumentWriter implements DocumentWriter, ColorVisitor { public void myMethod(final Color color) { // Do something with color depending on its type } public Object visitRgb(final RgbColor color, final Object arg) { // do something for RGB colors } public Object visitGray(final GrayscaleColor color, final Object arg) { // do something for grayscale colors } // and many others.. }
Now we just have to make sure that those methods are invoked. This is done with the method visit() of the Color. The signature allows us to provide one additional argument and receive a return value. Since we want to do something with the color itself, this color is provided with the correct type to the color visitor. The second argument can be casted to the appropriate type.
public class MyDocumentWriter implements DocumentWriter, ColorVisitor { public void myMethod(final Color color) { color.visit(this, "some value"); } public Object visitRgb(final RgbColor color, final Object arg) { String s = (String) arg; // do something for RGB colors } public Object visitGray(final GrayscaleColor color, final Object arg) { String s = (String) arg; // do something for grayscale colors } // and many others.. }
In the example above we have not used the additional argument or the return value. In the visit methods we are free to use them in all ways we like.
The definition of the parameters and the return value are rather general. Thus it is possible to use the visitor pattern in several different situations.
The visitor is not necessarily the class MyDocumentWriter. If this class contains several methods which need to distinguish the types of the colors it is possible to use another class as visitor, e.g. an inner class.
Method Summary | |
java.lang.Object |
visitCmyk(CmykColor color,
java.lang.Object value)
This method is called when an CmykColor
has been encountered. |
java.lang.Object |
visitGray(GrayscaleColor color,
java.lang.Object value)
This method is called when an GrayscaleColor
has been encountered. |
java.lang.Object |
visitHsv(HsvColor color,
java.lang.Object value)
This method is called when an HsvColor
has been encountered. |
java.lang.Object |
visitRgb(RgbColor color,
java.lang.Object value)
This method is called when an RgbColor
has been encountered. |
Method Detail |
public java.lang.Object visitCmyk(CmykColor color, java.lang.Object value) throws GeneralException
CmykColor
has been encountered.
color
- the first parameter for the visitor is the color visitedvalue
- the second parameter is a visitor specific object
GeneralException
- in case of an errorpublic java.lang.Object visitGray(GrayscaleColor color, java.lang.Object value) throws GeneralException
GrayscaleColor
has been encountered.
color
- the first parameter for the visitor is the color visitedvalue
- the second parameter is a visitor specific object
GeneralException
- in case of an errorpublic java.lang.Object visitHsv(HsvColor color, java.lang.Object value) throws GeneralException
HsvColor
has been encountered.
color
- the first parameter for the visitor is the color visitedvalue
- the second parameter is a visitor specific object
GeneralException
- in case of an errorpublic java.lang.Object visitRgb(RgbColor color, java.lang.Object value) throws GeneralException
RgbColor
has been encountered.
color
- the first parameter for the visitor is the color visitedvalue
- the second parameter is a visitor specific object
GeneralException
- in case of an error
|
|||||||||||
PREV CLASS NEXT CLASS | FRAMES NO FRAMES | ||||||||||
SUMMARY: NESTED | FIELD | CONSTR | METHOD | DETAIL: FIELD | CONSTR | METHOD |