xref: /AOO41X/main/svx/inc/svx/svdoedge.hxx (revision 8e8ee8fefdac26d905672cc573c35fd0ae1f9356)
1 /**************************************************************
2  *
3  * Licensed to the Apache Software Foundation (ASF) under one
4  * or more contributor license agreements.  See the NOTICE file
5  * distributed with this work for additional information
6  * regarding copyright ownership.  The ASF licenses this file
7  * to you under the Apache License, Version 2.0 (the
8  * "License"); you may not use this file except in compliance
9  * with the License.  You may obtain a copy of the License at
10  *
11  *   http://www.apache.org/licenses/LICENSE-2.0
12  *
13  * Unless required by applicable law or agreed to in writing,
14  * software distributed under the License is distributed on an
15  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16  * KIND, either express or implied.  See the License for the
17  * specific language governing permissions and limitations
18  * under the License.
19  *
20  *************************************************************/
21 
22 
23 
24 #ifndef _SVDOEDGE_HXX
25 #define _SVDOEDGE_HXX
26 
27 #include <svx/svdotext.hxx>
28 #include <svx/svdglue.hxx>
29 #include "svx/svxdllapi.h"
30 
31 //************************************************************
32 //   Vorausdeklarationen
33 //************************************************************
34 
35 class SdrDragMethod;
36 class SdrPageView;
37 
38 namespace sdr { namespace properties {
39     class ConnectorProperties;
40 }}
41 
42 //************************************************************
43 //   Hilfsklasse SdrObjConnection
44 //************************************************************
45 
46 class SdrObjConnection
47 {
48     friend class                SdrEdgeObj;
49     friend class                ImpEdgeHdl;
50     friend class                SdrCreateView;
51 
52 protected:
53     Point                       aObjOfs;       // Wird beim Draggen eines Knotens gesetzt
54     SdrObject*                  pObj;          // Referenziertes Objekt
55     long                        nXDist;        // Hor. Objektabstand wenn bXDistOvr=TRUE
56     long                        nYDist;        // Vert. Objektabstand wenn bYDistOvr=TRUE
57     sal_uInt16                      nConId;        // Konnektornummer
58 
59     // bitfield
60     unsigned                    bBestConn : 1;   // sal_True= es wird der guenstigste Konnektor gesucht
61     unsigned                    bBestVertex : 1; // sal_True= es wird der guenstigste Scheitelpunkt zum konnekten gesucht
62     unsigned                    bXDistOvr : 1;   // sal_True= Hor. Objektabstand wurde gedragt (Overwrite)
63     unsigned                    bYDistOvr : 1;   // sal_True= Vert. Objektabstand wurde gedragt (Overwrite)
64     unsigned                    bAutoVertex : 1; // AutoConnector am Scheitelpunkt nCon
65     unsigned                    bAutoCorner : 1; // AutoConnector am Eckpunkt nCon
66 
67 public:
SdrObjConnection()68     SdrObjConnection() { ResetVars(); }
69     SVX_DLLPUBLIC ~SdrObjConnection();
70 
71     void ResetVars();
72     FASTBOOL TakeGluePoint(SdrGluePoint& rGP, FASTBOOL bSetAbsolutePos) const;
73 
SetBestConnection(sal_Bool rB)74     inline void SetBestConnection( sal_Bool rB ) { bBestConn = rB; };
SetBestVertex(sal_Bool rB)75     inline void SetBestVertex( sal_Bool rB ) { bBestVertex = rB; };
SetAutoVertex(sal_Bool rB)76     inline void SetAutoVertex( sal_Bool rB ) { bAutoVertex = rB; };
SetConnectorId(sal_uInt16 nId)77     inline void SetConnectorId( sal_uInt16 nId ) { nConId = nId; };
78 
IsBestConnection() const79     inline sal_Bool IsBestConnection() const { return bBestConn; };
IsBestVertex() const80     inline sal_Bool IsBestVertex() const { return bBestVertex; };
IsAutoVertex() const81     inline sal_Bool IsAutoVertex() const { return bAutoVertex; };
GetConnectorId() const82     inline sal_uInt16 GetConnectorId() const { return nConId; };
GetObject() const83     inline SdrObject* GetObject() const { return pObj; }
84 };
85 
86 //************************************************************
87 //   Hilfsklasse SdrEdgeInfoRec
88 //************************************************************
89 
90 enum SdrEdgeLineCode {OBJ1LINE2,OBJ1LINE3,OBJ2LINE2,OBJ2LINE3,MIDDLELINE};
91 
92 class SdrEdgeInfoRec
93 {
94 public:
95     // Die 5 Distanzen werden beim draggen bzw. per SetAttr gesetzt und von
96     // ImpCalcEdgeTrack ausgewertet. Per Get/SetAttr/Get/SetStyleSh werden
97     // jedoch nur 0-3 longs transportiert.
98     Point                       aObj1Line2;
99     Point                       aObj1Line3;
100     Point                       aObj2Line2;
101     Point                       aObj2Line3;
102     Point                       aMiddleLine;
103 
104     // Nachfolgende Werte werden von ImpCalcEdgeTrack gesetzt
105     long                        nAngle1;           // Austrittswinkel am Obj1
106     long                        nAngle2;           // Austrittswinkel am Obj2
107     sal_uInt16                      nObj1Lines;        // 1..3
108     sal_uInt16                      nObj2Lines;        // 1..3
109     sal_uInt16                      nMiddleLine;       // 0xFFFF=keine, sonst Punktnummer des Linienbeginns
110     char                        cOrthoForm;        // Form des Ortho-Verbindes, z.B. 'Z','U',I','L','S',...
111 
112 public:
SdrEdgeInfoRec()113     SdrEdgeInfoRec()
114     :   nAngle1(0),
115         nAngle2(0),
116         nObj1Lines(0),
117         nObj2Lines(0),
118         nMiddleLine(0xFFFF),
119         cOrthoForm(0)
120     {}
121 
122     Point& ImpGetLineVersatzPoint(SdrEdgeLineCode eLineCode);
ImpGetLineVersatzPoint(SdrEdgeLineCode eLineCode) const123     const Point& ImpGetLineVersatzPoint(SdrEdgeLineCode eLineCode) const { return ((SdrEdgeInfoRec*)this)->ImpGetLineVersatzPoint(eLineCode); }
124     sal_uInt16 ImpGetPolyIdx(SdrEdgeLineCode eLineCode, const XPolygon& rXP) const;
125     FASTBOOL ImpIsHorzLine(SdrEdgeLineCode eLineCode, const XPolygon& rXP) const;
126     void ImpSetLineVersatz(SdrEdgeLineCode eLineCode, const XPolygon& rXP, long nVal);
127     long ImpGetLineVersatz(SdrEdgeLineCode eLineCode, const XPolygon& rXP) const;
128 };
129 
130 //************************************************************
131 //   Hilfsklasse SdrEdgeObjGeoData
132 //************************************************************
133 
134 class SdrEdgeObjGeoData : public SdrTextObjGeoData
135 {
136 public:
137     SdrObjConnection            aCon1;  // Verbindungszustand des Linienanfangs
138     SdrObjConnection            aCon2;  // Verbindungszustand des Linienendes
139     XPolygon*                   pEdgeTrack;
140     sal_Bool                    bEdgeTrackDirty;// sal_True=Verbindungsverlauf muss neu berechnet werden.
141     sal_Bool                    bEdgeTrackUserDefined;
142     SdrEdgeInfoRec              aEdgeInfo;
143 
144 public:
145     SdrEdgeObjGeoData();
146     virtual ~SdrEdgeObjGeoData();
147 };
148 
149 //************************************************************
150 //   Hilfsklasse SdrEdgeObj
151 //************************************************************
152 
153 class SVX_DLLPUBLIC SdrEdgeObj : public SdrTextObj
154 {
155 private:
156     // to allow sdr::properties::ConnectorProperties access to ImpSetAttrToEdgeInfo()
157     friend class sdr::properties::ConnectorProperties;
158 
159     friend class                SdrCreateView;
160     friend class                ImpEdgeHdl;
161 
162 protected:
163     virtual sdr::contact::ViewContact* CreateObjectSpecificViewContact();
164     virtual sdr::properties::BaseProperties* CreateObjectSpecificProperties();
165 
166     SdrObjConnection            aCon1;  // Verbindungszustand des Linienanfangs
167     SdrObjConnection            aCon2;  // Verbindungszustand des Linienendes
168 
169     XPolygon*                   pEdgeTrack;
170     sal_uInt16                  nNotifyingCount; // Verrieglung
171     SdrEdgeInfoRec              aEdgeInfo;
172 
173     // bitfield
174     unsigned                    bEdgeTrackDirty : 1; // sal_True=Verbindungsverlauf muss neu berechnet werden.
175     unsigned                    bEdgeTrackUserDefined : 1;
176 
177     // #109007#
178     // Bool to allow supporession of default connects at object
179     // inside test (HitTest) and object center test (see ImpFindConnector())
180     unsigned                    mbSuppressDefaultConnect : 1;
181 
182     // #110649#
183     // Flag value for avoiding death loops when calculating BoundRects
184     // from circularly connected connectors. A coloring algorythm is used
185     // here. When the GetCurrentBoundRect() calculation of a SdrEdgeObj
186     // is running, the flag is set, else it is always sal_False.
187     unsigned                    mbBoundRectCalculationRunning : 1;
188 
189     // #123048# need to remember if layouting was suppressed before to get
190     // to a correct state for first real layouting
191     unsigned                    mbSuppressed : 1;
192 
193 public:
194     // #109007#
195     // Interface to default connect suppression
SetSuppressDefaultConnect(sal_Bool bNew)196     void SetSuppressDefaultConnect(sal_Bool bNew) { mbSuppressDefaultConnect = bNew; }
GetSuppressDefaultConnect() const197     sal_Bool GetSuppressDefaultConnect() const { return mbSuppressDefaultConnect; }
198 
199     // #110649#
IsBoundRectCalculationRunning() const200     sal_Bool IsBoundRectCalculationRunning() const { return mbBoundRectCalculationRunning; }
201 
202 protected:
203     virtual void Notify(SfxBroadcaster& rBC, const SfxHint& rHint);
204 
205     XPolygon ImpCalcObjToCenter(const Point& rStPt, long nEscAngle, const Rectangle& rRect, const Point& rCenter) const;
206     void ImpRecalcEdgeTrack();  // Neuberechnung des Verbindungsverlaufs
207     XPolygon ImpCalcEdgeTrack(const XPolygon& rTrack0, SdrObjConnection& rCon1, SdrObjConnection& rCon2, SdrEdgeInfoRec* pInfo) const;
208     XPolygon ImpCalcEdgeTrack(const Point& rPt1, long nAngle1, const Rectangle& rBoundRect1, const Rectangle& rBewareRect1,
209         const Point& rPt2, long nAngle2, const Rectangle& rBoundRect2, const Rectangle& rBewareRect2,
210         sal_uIntPtr* pnQuality, SdrEdgeInfoRec* pInfo) const;
211     static FASTBOOL ImpFindConnector(const Point& rPt, const SdrPageView& rPV, SdrObjConnection& rCon, const SdrEdgeObj* pThis, OutputDevice* pOut=NULL);
212     sal_uInt16 ImpCalcEscAngle(SdrObject* pObj, const Point& aPt2) const;
213     FASTBOOL ImpStripPolyPoints(XPolygon& rXP) const; // entfernen ueberfluessiger Punkte
214     void ImpSetTailPoint(FASTBOOL bTail1, const Point& rPt);
215     void ImpUndirtyEdgeTrack();  // eventuelle Neuberechnung des Verbindungsverlaufs
216     void ImpDirtyEdgeTrack();   // invalidate connector path, so it will be recalculated next time
217     void ImpSetAttrToEdgeInfo(); // Werte vom Pool nach aEdgeInfo kopieren
218     void ImpSetEdgeInfoToAttr(); // Werte vom aEdgeInfo in den Pool kopieren
219 
220 public:
221     TYPEINFO();
222 
223     SdrEdgeObj();
224     virtual ~SdrEdgeObj();
225 
GetConnection(FASTBOOL bTail1)226     SdrObjConnection& GetConnection(FASTBOOL bTail1) { return *(bTail1 ? &aCon1 : &aCon2); }
227     virtual void TakeObjInfo(SdrObjTransformInfoRec& rInfo) const;
228     virtual sal_uInt16 GetObjIdentifier() const;
229     virtual const Rectangle& GetCurrentBoundRect() const;
230     virtual const Rectangle& GetSnapRect() const;
231     virtual FASTBOOL IsNode() const;
232     virtual SdrGluePoint GetVertexGluePoint(sal_uInt16 nNum) const;
233     virtual SdrGluePoint GetCornerGluePoint(sal_uInt16 nNum) const;
234     virtual const SdrGluePointList* GetGluePointList() const;
235     virtual SdrGluePointList* ForceGluePointList();
236     virtual FASTBOOL IsEdge() const;
237 
238     // bTail1=TRUE: Linienanfang, sonst LinienEnde
239     // pObj=NULL: Disconnect
SetEdgeTrackDirty()240     void SetEdgeTrackDirty() { bEdgeTrackDirty=sal_True; }
241     void ConnectToNode(FASTBOOL bTail1, SdrObject* pObj);
242     void DisconnectFromNode(FASTBOOL bTail1);
243     SdrObject* GetConnectedNode(FASTBOOL bTail1) const;
GetConnection(FASTBOOL bTail1) const244     const SdrObjConnection& GetConnection(FASTBOOL bTail1) const { return *(bTail1 ? &aCon1 : &aCon2); }
245     FASTBOOL CheckNodeConnection(FASTBOOL bTail1) const;
246 
247     virtual void RecalcSnapRect();
248     virtual void TakeUnrotatedSnapRect(Rectangle& rRect) const;
249     virtual void operator=(const SdrObject& rObj);
250     virtual void TakeObjNameSingul(String& rName) const;
251     virtual void TakeObjNamePlural(String& rName) const;
252 
253     void    SetEdgeTrackPath( const basegfx::B2DPolyPolygon& rPoly );
254     basegfx::B2DPolyPolygon GetEdgeTrackPath() const;
255 
256     virtual basegfx::B2DPolyPolygon TakeXorPoly() const;
257     virtual sal_uInt32 GetHdlCount() const;
258     virtual SdrHdl* GetHdl(sal_uInt32 nHdlNum) const;
259 
260     // special drag methods
261     virtual bool hasSpecialDrag() const;
262     virtual bool beginSpecialDrag(SdrDragStat& rDrag) const;
263     virtual bool applySpecialDrag(SdrDragStat& rDrag);
264     virtual String getSpecialDragComment(const SdrDragStat& rDrag) const;
265 
266     // FullDrag support
267     virtual SdrObject* getFullDragClone() const;
268 
269     virtual void NbcSetSnapRect(const Rectangle& rRect);
270     virtual void NbcMove(const Size& aSize);
271     virtual void NbcResize(const Point& rRefPnt, const Fraction& aXFact, const Fraction& aYFact);
272 
273     // #54102# added rotate, mirrorn and shear support
274     virtual void NbcRotate(const Point& rRef, long nWink, double sn, double cs);
275     virtual void NbcMirror(const Point& rRef1, const Point& rRef2);
276     virtual void NbcShear(const Point& rRef, long nWink, double tn, FASTBOOL bVShear);
277 
278     // #102344# Added missing implementation
279     virtual void NbcSetAnchorPos(const Point& rPnt);
280 
281     virtual FASTBOOL BegCreate(SdrDragStat& rStat);
282     virtual FASTBOOL MovCreate(SdrDragStat& rStat);
283     virtual FASTBOOL EndCreate(SdrDragStat& rStat, SdrCreateCmd eCmd);
284     virtual FASTBOOL BckCreate(SdrDragStat& rStat);
285     virtual void BrkCreate(SdrDragStat& rStat);
286     virtual basegfx::B2DPolyPolygon TakeCreatePoly(const SdrDragStat& rDrag) const;
287     virtual Pointer GetCreatePointer() const;
288     virtual SdrObject* DoConvertToPolyObj(sal_Bool bBezier, bool bAddText) const;
289 
290     virtual sal_uInt32 GetSnapPointCount() const;
291     virtual Point GetSnapPoint(sal_uInt32 i) const;
292     virtual sal_Bool IsPolyObj() const;
293     virtual sal_uInt32 GetPointCount() const;
294     virtual Point GetPoint(sal_uInt32 i) const;
295     virtual void NbcSetPoint(const Point& rPnt, sal_uInt32 i);
296 
297     virtual SdrObjGeoData* NewGeoData() const;
298     virtual void SaveGeoData(SdrObjGeoData& rGeo) const;
299     virtual void RestGeoData(const SdrObjGeoData& rGeo);
300 
301     /** updates edges that are connected to the edges of this object
302         as if the connected objects send a repaint broadcast
303         #103122#
304     */
305     void Reformat();
306 
307     // helper methods for the StarOffice api
308     Point GetTailPoint( sal_Bool bTail ) const;
309     void SetTailPoint( sal_Bool bTail, const Point& rPt );
310     void setGluePointIndex( sal_Bool bTail, sal_Int32 nId = -1 );
311     sal_Int32 getGluePointIndex( sal_Bool bTail );
312 
313     virtual sal_Bool TRGetBaseGeometry(basegfx::B2DHomMatrix& rMatrix, basegfx::B2DPolyPolygon& rPolyPolygon) const;
314     virtual void TRSetBaseGeometry(const basegfx::B2DHomMatrix& rMatrix, const basegfx::B2DPolyPolygon& rPolyPolygon);
315 
316     // for geometry access
317     ::basegfx::B2DPolygon getEdgeTrack() const;
318 
319     // helper method for SdrDragMethod::AddConnectorOverlays. Adds a overlay polygon for
320     // this connector to rResult.
321     basegfx::B2DPolygon ImplAddConnectorOverlay(SdrDragMethod& rDragMethod, bool bTail1, bool bTail2, bool bDetail) const;
322 };
323 
324 ////////////////////////////////////////////////////////////////////////////////////////////////////
325 //
326 // Zur Bestimmung der Verlaufslinie werden folgende Item-Parameter des SdrItemPool verwendet:
327 //
328 //  sal_uInt16 EdgeFlowAngle       Default 9000 (=90.00 Deg), min 0, max 9000
329 //      Verlauffreiheitswinkel.
330 //      Der Winkel, in dem die Verbindungslinie verlaufen darf.
331 //
332 //  sal_uInt16 EdgeEscAngle        Default 9000 (=90.00 Deg), min 0, max 9000
333 //      Objektaustrittswinkel.
334 //      Der Winkel, in dem die Verbindungslinie aus dem Objekt austreten darf.
335 //
336 //  sal_Bool   EdgeEscAsRay        Default FALSE
337 //      sal_True= die Verbindungslinie tritt aus dem Obj Strahlenfoermig aus.
338 //      Also Winkelvorgabe durch die Strecke ObjMitte/Konnektor.
339 //
340 //  sal_Bool   EdgeEscUseObjAngle  Default FALSE
341 //      Objektdrehwinkelberuecksichtigung.
342 //      sal_True= Bei der Bestimmung des Objektaustrittswinkels wird der
343 //      Drehwinkel des Objekts als Offset beruecksichtigt.
344 //
345 //  sal_uIntPtr  EdgeFlowDefDist     Default 0, min 0, max ?
346 //      Das ist der Default-Mindestabstand der bei der Berechnung der
347 //      Verbindungslinie zu den angedockten Objekten in logischen Einheiten.
348 //      Dieser Abstand wird innerhalb des Objektes "ueberschrieben", sobald
349 //      der User an den Linien draggd. Beim Andocken an ein neues Objekt wird
350 //      dann jedoch wieder dieser Default verwendet.
351 //
352 //
353 // Allgemeines zu Konnektoren:
354 //
355 // Es gibt Knoten und Kantenobjekte. Zwei Knoten koennen durch eine Kante
356 // miteinander verbunden werden. Ist eine Kante nur an einem Ende an einen
357 // Knoten geklebt, ist das andere Ende auf einer absoluten Position im Doc
358 // fixiert. Ebenso ist es natuerlich auch moeglich, dass eine Kante an beiden
359 // Enden "frei", also nicht mit einem Knotenobjekt verbunden ist.
360 //
361 // Ein Kantenobjekt kann theoretisch auch gleichzeitig Knotenobjekt sein. In
362 // der ersten Version wird das jedoch noch nicht realisiert werden.
363 //
364 // Eine Verbindung zwischen Knoten und Kante kann hergestellt werden durch:
365 // - Interaktives erzeugen eines neuen Kantenobjekts an der SdrView wobei
366 //   Anfangs- bzw. Endpunkt der Kante auf ein Konnektor (Klebestelle) eines
367 //   bereits vorhandenen Knotenobjekts gelegt wird.
368 // - Interaktives draggen des Anfangs- bzw. Endpunkts eines bestehenden
369 //   Kantenobjekts an der SdrView auf ein Konnektor (Klebestelle) eines
370 //   bereits vorhandenen Knotenobjekts.
371 // - Undo/Redo
372 // Verschieben von Knotenobjekten stellt keine Verbindungen her. Ebenso auch
373 // nicht das direkte Verschieben von Kantenendpunkten am SdrModel...
374 // Verbindungen koennen auch hergestellt werden, wenn die Konnektoren an der
375 // View nicht sichtbar geschaltet sind.
376 //
377 // Eine vorhandene Verbindung zwischen Knoten und Kante bleibt erhalten bei:
378 // - Draggen (Move/Resize/Rotate/...) des Knotenobjekts
379 // - Verschieben einer Konnektorposition im Knotemobjekt
380 // - gleichzeitiges Draggen (Move/Resize/Rotate/...) von Knoten und Kante
381 //
382 // Eine Verbindung zwischen Knoten und Kante kann geloesst werden durch:
383 // - Loeschen eines der Objekte
384 // - Draggen des Kantenobjekts ohne gleichzeitiges Draggen des Knotens
385 // - Loeschen des Konnektors am Knotenobjekt
386 // - Undo/Redo/Repeat
387 // Beim Draggen muss die Aufforderung zum loesen der Verbindung von ausserhalb
388 // des Models befohlen werden (z.B. von der SdrView). SdrEdgeObj::Move() loesst
389 // die Verbindung nicht selbsttaetig.
390 //
391 // Jedes Knotenobjekt kann Konnektoren, sog. Klebestellen besitzen. Das sind die
392 // geometrischen Punkte, an denen das verbindende Kantenobjekt bei hergestellter
393 // Verbindung endet. Defaultmaessig hat jedes Objekt keine Konnektoren. Trotzdem
394 // kann man bei bestimmten View-Einstellungen eine Kante andocken, da dann z.B.
395 // an den 4 Scheitelpunkten des Knotenobjekts bei Bedarf automatisch Konnektoren
396 // generiert werden. Jedes Objekt liefert dafuer 2x4 sog. Default-Konnektorposi-
397 // tionen, 4 an den Scheitelpunkten und 4 an den Eckpositionen. Im Normalfall
398 // liegen diese an den 8 Handlepositionen; Ausnahmen bilden hier Ellipsen,
399 // Parallelogramme, ... . Darueberhinaus koennen auch an jedem Knotenobjekt
400 // anwenderspeziefische Konnektoren gesetzt werden.
401 //
402 // Dann gibt es noch die Moeglichkeit, ein Kante an einem Objekt mit dem
403 // Attribut "bUseBestConnector" anzudocken. Es wird dann aus dem Angebot der
404 // Konnektoren des Objekts oder/und der Scheitelpunkte, jeweils die fuer den
405 // Verlauf der Verbindungslinie guenstigste Konnektorposition verwendet. Der
406 // Anwender vergibt dieses Attribut, indem er den Knoten in seiner Mitte
407 // andockt (siehe z.B. Visio).
408 // 09-06-1996: bUseBestConnector verwendet nur Scheitelpunktklebepunkte.
409 //
410 // Und hier noch etwas Begriffsdefinition:
411 //   Verbinder : Eben das Verbinderobjekt (Kantenobjekt)
412 //   Knoten    : Ein beliebiges Objekt, an dem ein Verbinder drangeklebt
413 //               werden kann, z.B. ein Rechteck, ...
414 //   Klebepunkt: Der Punkt, an dem der Verbinder an das Knotenobjekt
415 //               geklebt wird. Hierbei gibt es:
416 //                 Scheitelpunktklebepunkte: Jedes Knotenobjekt hat diese
417 //                     Klebepunkte von Natur aus. Moeglicherweise gibt es
418 //                     im Draw bereits die Option "Automatisch ankleben an
419 //                     Objektscheitelpunkte" (default an)
420 //                 Eckpunktklebepunkte: Auch diese Klebepunkte sind den
421 //                     Objekten von mir bereits mitgegeben. Wie die oben
422 //                     erwaehnten gibt es fuer diese moeglicherweise
423 //                     bereits auch eine Option im Draw. (default aus)
424 //                 Scheitelpunktklebepunkte und Eckpunktklebepunkte sind
425 //                     im Gegensatz zu Visio nicht optisch sichtbar; sie
426 //                     sind eben einfach da (wenn Option eingeschaltet).
427 //                 Benutzerdefinierte Klebepunkte: Gibt es an jedem
428 //                     Knotenobjekt beliebig viele. Per Option koennen sie
429 //                     sichtbar geschaltet werden (beim editieren immer
430 //                     sichtbar). Zur Zeit sind die jedoch noch nicht ganz
431 //                     fertigimplementiert.
432 //                 Automatische Klebepunktwahl: Wird der Verbinder so an
433 //                     das Knotenobjekt gedockt, dass der schwarke Rahmen
434 //                     das gesamte Objekt umfasst, so versucht der
435 //                     Verbinder von den 4 Scheitelpunktklebepunkten (und
436 //                     zwar nur von denen) den guenstigsten herauszufinden.
437 //
438 //////////////////////////////////////////////////////////////////////////////////////////////////
439 
440 #endif //_SVDOEDGE_HXX
441 
442