Implements PXEGeek's http://wiki.synfig.com/Wish_list entry: "Optionally display...
[synfig.git] / synfig-studio / trunk / src / gtkmm / duck.cpp
1 /* === S Y N F I G ========================================================= */
2 /*!     \file duck.cpp
3 **      \brief Template File
4 **
5 **      $Id$
6 **
7 **      \legal
8 **      Copyright (c) 2002-2005 Robert B. Quattlebaum Jr., Adrian Bentley
9 **
10 **      This package is free software; you can redistribute it and/or
11 **      modify it under the terms of the GNU General Public License as
12 **      published by the Free Software Foundation; either version 2 of
13 **      the License, or (at your option) any later version.
14 **
15 **      This package is distributed in the hope that it will be useful,
16 **      but WITHOUT ANY WARRANTY; without even the implied warranty of
17 **      MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
18 **      General Public License for more details.
19 **      \endlegal
20 */
21 /* ========================================================================= */
22
23 /* === H E A D E R S ======================================================= */
24
25 #ifdef USING_PCH
26 #       include "pch.h"
27 #else
28 #ifdef HAVE_CONFIG_H
29 #       include <config.h>
30 #endif
31
32 #include "duck.h"
33
34 #endif
35
36 /* === U S I N G =========================================================== */
37
38 using namespace std;
39 using namespace etl;
40 using namespace synfig;
41 using namespace studio;
42
43 /* === M A C R O S ========================================================= */
44
45 /* === G L O B A L S ======================================================= */
46
47 int studio::Duck::duck_count(0);
48
49 struct _DuckCounter
50 {
51         static int counter;
52         ~_DuckCounter()
53         {
54                 if(counter)
55                         synfig::error("%d ducks not yet deleted!",counter);
56         }
57 } _duck_counter;
58
59 int _DuckCounter::counter(0);
60
61
62 /* === P R O C E D U R E S ================================================= */
63
64 /* === M E T H O D S ======================================================= */
65
66 Duck::Duck():
67         origin(0,0),
68         scalar(1),
69         editable(false),
70         radius_(false),
71         tangent_(false)
72 { duck_count++; _DuckCounter::counter++; }
73
74 Duck::Duck(const synfig::Point &point):
75         type_(TYPE_NONE),
76         point(point),
77         origin(0,0),
78         scalar(1),
79         guid_(0),
80         editable(false),
81         radius_(false),
82         tangent_(false)
83 { duck_count++; _DuckCounter::counter++;}
84
85 Duck::Duck(const synfig::Point &point,const synfig::Point &origin):
86         point(point),
87         origin(origin),
88         scalar(1),
89         guid_(0),
90         editable(false),
91         radius_(true),
92         tangent_(false)
93 { duck_count++; _DuckCounter::counter++;}
94
95 Duck::~Duck() { duck_count--; _DuckCounter::counter--;}
96
97 synfig::GUID
98 Duck::get_data_guid()const
99 {
100         if(value_desc_.is_value_node())
101                 return value_desc_.get_value_node()->get_guid();
102         return GUID::hasher(get_name());
103 }
104
105 void
106 Duck::set_name(const synfig::String &x)
107 {
108         name=x;
109         if(guid_==GUID::zero())
110         {
111                 guid_=GUID::hasher(name);
112         }
113 }
114
115
116 bool
117 Duck::operator==(const Duck &rhs)const
118 {
119         if(this==&rhs)
120                 return true;
121         return
122                 name==rhs.name &&
123                 scalar==rhs.scalar &&
124                 type_==rhs.type_ &&
125                 transform_stack_.size()==rhs.transform_stack_.size();
126                 //true;
127                 //(origin_duck?*origin_duck==*rhs.origin_duck:origin==rhs.origin) &&
128                 //(shared_point?*shared_point==*rhs.shared_point:point==rhs.point) ;
129 }
130
131 synfig::Point
132 Duck::get_trans_point()const
133 {
134         return transform_stack_.perform(get_sub_trans_point());
135 }
136
137 void
138 Duck::set_trans_point(const synfig::Point &x)
139 {
140         set_sub_trans_point(transform_stack_.unperform(x));
141 }
142
143 //! Sets the origin point.
144 void
145 Duck::set_origin(const synfig::Point &x)
146 {
147         origin=x; origin_duck=0;
148 }
149
150 //! Sets the origin point as another duck
151 void
152 Duck::set_origin(const etl::handle<Duck> &x)
153 {
154         origin_duck=x;
155 }
156
157 //! Retrieves the origin location
158 synfig::Point
159 Duck::get_origin()const
160 {
161         return origin_duck?origin_duck->get_point():origin;
162 }
163
164 //! Retrieves the origin duck
165 const etl::handle<Duck> &
166 Duck::get_origin_duck() const
167 {
168         return origin_duck;
169 }
170
171 //! Retrieves the origin location
172 synfig::Point
173 Duck::get_trans_origin()const
174 {
175         return transform_stack_.perform(get_sub_trans_origin());
176 }
177
178 synfig::Point
179 Duck::get_sub_trans_point()const
180 {
181         return get_point()*get_scalar()+get_sub_trans_origin();
182 }
183
184 void
185 Duck::set_sub_trans_point(const synfig::Point &x)
186 {
187         set_point((x-get_sub_trans_origin())/get_scalar());
188 }
189
190 synfig::Point
191 Duck::get_sub_trans_origin()const
192 {
193         return origin_duck?origin_duck->get_sub_trans_point():origin;
194 }