00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021 #ifndef __GP_Xform_h__
00022 #define __GP_Xform_h__
00023
00024 #include "GP_API.h"
00025 #include <UT/UT_Vector2.h>
00026 #include <UT/UT_RefMatrix.h>
00027
00028 class UT_BoundingRect;
00029
00030
00031 typedef UT_Vector2 GP_Point;
00032 typedef UT_RefMatrix<GP_Point> GP_PointMatrix;
00033
00034
00035 #define GP_LINEAR_XFORM 0x00001
00036 #define GP_BILINEAR_XFORM 0x00002
00037
00038 #define GP_LINEAR_XFORM_N "Linear"
00039 #define GP_BILINEAR_XFORM_N "Bilinear"
00040
00041
00042 class GP_API GP_Xform
00043 {
00044 public:
00045
00046 GP_Xform(void) { myRefCount = 0; }
00047 virtual ~GP_Xform(void);
00048
00049
00050
00051 virtual int forward (GP_Point &p) const = 0;
00052 virtual int forward (GP_PointMatrix &m) const = 0;
00053 virtual int backward(GP_Point &p) const = 0;
00054 virtual int backward(GP_PointMatrix &m) const = 0;
00055
00056
00057 virtual void reset(void) = 0;
00058
00059
00060 virtual void translate(float dx, float dy) = 0;
00061
00062
00063
00064
00065 virtual GP_Xform *compose(const GP_Xform &xform,
00066 const UT_BoundingRect *brect = 0) = 0;
00067 virtual GP_Xform *composeInverse(const GP_Xform &xform,
00068 const UT_BoundingRect *brect = 0) = 0;
00069
00070
00071
00072 virtual int copyFrom(const GP_Xform &xform) = 0;
00073
00074
00075
00076
00077
00078
00079 virtual GP_Xform *inverse(void) = 0;
00080 virtual int inverse(GP_Xform &) = 0;
00081
00082
00083 virtual const char *getName(void) const = 0;
00084 virtual unsigned int getType(void) const = 0;
00085
00086
00087 virtual int save(ostream &os, int binary = 0) const = 0;
00088 virtual bool load(UT_IStream &is) = 0;
00089
00090
00091 int addReference(void) { return ++myRefCount; }
00092 int delReference(void) { return --myRefCount; }
00093
00094
00095 GP_Xform *copy(void) const { return newSpecies(*this); }
00096
00097
00098
00099 static GP_Xform *newSpecies(const char *name);
00100 static GP_Xform *newSpecies(unsigned int type);
00101 static GP_Xform *newSpecies(const GP_Xform &xform);
00102
00103
00104 static GP_Xform *read(UT_IStream &is);
00105
00106
00107 static int saveIdentity(ostream &os, int binary = 0);
00108
00109
00110 protected:
00111
00112 int saveHeader(ostream &os, int binary = 0) const;
00113
00114 private:
00115 int myRefCount;
00116 };
00117
00118
00119
00120 class GP_API GP_XformHandle
00121 {
00122 public:
00123
00124 GP_XformHandle(GP_Xform *xform = 0)
00125 {
00126 if (myXform = xform) myXform->addReference();
00127 }
00128 GP_XformHandle(const GP_XformHandle &handle)
00129 {
00130 if (myXform = handle.myXform) myXform->addReference();
00131 }
00132 ~GP_XformHandle(void)
00133 {
00134 if (myXform && !myXform->delReference()) delete myXform;
00135 }
00136
00137
00138 GP_XformHandle &operator=(const GP_XformHandle &h)
00139 {
00140 if (this != &h)
00141 {
00142 if (myXform && !myXform->delReference())
00143 delete myXform;
00144 if (myXform = h.myXform)
00145 myXform->addReference();
00146 }
00147 return *this;
00148 }
00149
00150
00151
00152
00153 GP_XformHandle &operator=(const GP_Xform &xform)
00154 {
00155 if (myXform != &xform)
00156 {
00157
00158 if (!myXform || myXform->copyFrom(xform))
00159 {
00160 if (myXform && !myXform->delReference())
00161 delete myXform;
00162
00163 myXform = xform.copy();
00164 myXform->addReference();
00165 }
00166 else
00167 {
00168 if (!myXform->delReference())
00169 delete myXform;
00170 myXform = xform.copy();
00171 myXform->addReference();
00172 }
00173 }
00174 return *this;
00175 }
00176
00177
00178 int save(ostream &os, int binary = 0) const
00179 {
00180 return myXform ? myXform->save(os,binary)
00181 : GP_Xform::saveIdentity(os,binary);
00182 }
00183
00184 bool load(UT_IStream &is)
00185 {
00186 if (myXform && !myXform->delReference())
00187 delete myXform;
00188 if (myXform = GP_Xform::read(is))
00189 myXform->addReference();
00190 return myXform != NULL;
00191 }
00192
00193
00194
00195 void compose(const GP_XformHandle &handle,
00196 const UT_BoundingRect *brect = 0)
00197 {
00198 if (handle.myXform)
00199 {
00200 if (myXform)
00201 {
00202 GP_Xform *newxf;
00203 newxf = myXform->compose(*handle.myXform,
00204 brect);
00205
00206 if (newxf != myXform)
00207 {
00208 if (!myXform->delReference())
00209 delete myXform;
00210 myXform = newxf;
00211 myXform->addReference();
00212 }
00213 }
00214 else
00215 {
00216 myXform = handle.myXform->copy();
00217 myXform->addReference();
00218 }
00219 }
00220 }
00221
00222 void composeInverse(const GP_XformHandle &handle,
00223 const UT_BoundingRect *brect = 0)
00224 {
00225 if (handle.myXform)
00226 {
00227 if (myXform)
00228 {
00229 GP_Xform *newxf;
00230 newxf = myXform->composeInverse(
00231 *handle.myXform, brect);
00232
00233 if (newxf != myXform)
00234 {
00235 if (!myXform->delReference())
00236 delete myXform;
00237 myXform = newxf;
00238 myXform->addReference();
00239 }
00240 }
00241 else
00242 {
00243 myXform = handle.myXform->copy();
00244 myXform->addReference();
00245 }
00246 }
00247 }
00248
00249
00250 GP_Xform *operator->(void) const { return myXform; }
00251 GP_Xform *operator* (void) const { return myXform; }
00252
00253
00254 int isDefined(void) const { return myXform != 0; }
00255
00256
00257 private:
00258 GP_Xform *myXform;
00259 };
00260
00261 #endif