Jamoma API  0.6.0.a19
TTReceiver.cpp
Go to the documentation of this file.
1 /** @file
2  *
3  * @ingroup modularLibrary
4  *
5  * @brief A Receiver Object
6  *
7  * @details
8  *
9  * @authors Théo de la Hogue
10  *
11  * @copyright © 2010, Théo de la Hogue @n
12  * This code is licensed under the terms of the "New BSD License" @n
13  * http://creativecommons.org/licenses/BSD/
14  */
15 
16 
17 #include "TTReceiver.h"
18 
19 #define thisTTClass TTReceiver
20 #define thisTTClassName "Receiver"
21 #define thisTTClassTags "node, receiver"
22 
23 TT_MODULAR_CONSTRUCTOR,
24 mAddress(kTTAdrsEmpty),
25 mActive(YES),
26 mObjectCache(NULL)
27 {
28  if (arguments.size() >= 1)
29  mReturnAddressCallback = arguments[0];
30 
31  if (arguments.size() >= 2)
32  mReturnValueCallback = arguments[1];
33 
34  if (arguments.size() >= 3)
35  mSignal = arguments[2];
36 
39 
40  addAttribute(ObjectCache, kTypePointer);
41  addAttributeProperty(ObjectCache, hidden, YES);
42  addAttributeProperty(ObjectCache, readOnly, YES);
43 
44  addMessage(Get);
45  addMessageProperty(Get, hidden, YES);
46 
48  addMessageProperty(Grab, hidden, YES);
49 
50  mNodesObserversCache.setThreadProtection(true);
51 
52  mObjectCache = new TTList();
53  mObjectCache->setThreadProtection(true);
54 }
55 
56 TTReceiver::~TTReceiver()
57 {
58  // disable reception to avoid crash
59  mActive = NO;
60 
61  unbindAddress(accessApplicationDirectoryFrom(mAddress));
62  unbindApplication();
63 
64  delete mObjectCache;
65 }
66 
67 TTErr TTReceiver::setAddress(const TTValue& newValue)
68 {
69  TTErr err = kTTErrGeneric;
70  TTBoolean memoActive = mActive;
71 
72  // disable reception to avoid crash
73  mActive = NO;
74 
75  unbindAddress(accessApplicationDirectoryFrom(mAddress));
76  unbindApplication();
77 
78  mAddress = newValue[0];
79 
80  if (mAddress != kTTAdrsEmpty)
81  err = bindAddress(accessApplicationDirectoryFrom(mAddress));
82 
83  // enable reception
84  mActive = memoActive;
85 
86  return err;
87 }
88 
89 TTErr TTReceiver::setActive(const TTValue& newValue)
90 {
91  TTNodePtr aNode;
92  TTObject anObject;
93  TTAttributePtr anAttribute = NULL;
94  TTSymbol ttAttributeName;
95  TTValue data, v;
96  TTErr err;
97 
98  mActive = newValue;
99 
100  // enable/disable listening (for Mirror object only)
101  if (!mNodesObserversCache.isEmpty()) {
102 
103  ttAttributeName = ToTTName(mAddress.getAttribute());
104 
105  // default attribute to bind is value
106  if (ttAttributeName == NO_ATTRIBUTE)
107  ttAttributeName = kTTSym_value;
108 
109  // for each node of the selection
110  for (mNodesObserversCache.begin(); mNodesObserversCache.end(); mNodesObserversCache.next()) {
111 
112  // get a node from the selection
113  aNode = TTNodePtr((TTPtr)mNodesObserversCache.current()[0]);
114 
115  // get the type and the attribute of the object
116  anObject = aNode->getObject();
117  if (anObject.valid()) {
118 
119  err = anObject.instance()->findAttribute(ttAttributeName, &anAttribute);
120 
121  if (!err) {
122 
123  TTObject anObserver = mNodesObserversCache.current()[1];
124 
125  if (mActive)
126  anAttribute->registerObserverForNotifications(anObserver);
127  else
128  anAttribute->unregisterObserverForNotifications(anObserver);
129 
130  if (anObject.name() == kTTSym_Mirror)
131  TTMirrorPtr(anObject.instance())->enableListening(*anAttribute, mActive);
132  }
133  }
134  }
135  }
136 
137  return kTTErrNone;
138 }
139 
140 #if 0
141 #pragma mark -
142 #pragma mark Some Methods
143 #endif
144 
145 TTErr TTReceiver::Get()
146 {
147  TTNodePtr aNode;
148  TTObject anObject;
149  TTAddress anAddress;
150  TTSymbol ttAttributeName;
151  TTValue data, v, none;
152  TTErr err;
153 
154  if (!mNodesObserversCache.isEmpty()) {
155 
156  ttAttributeName = ToTTName(mAddress.getAttribute());
157 
158  // default attribute to bind is value
159  if (ttAttributeName == NO_ATTRIBUTE)
160  ttAttributeName = kTTSym_value;
161 
162  // for each node of the selection
163  for (mNodesObserversCache.begin(); mNodesObserversCache.end(); mNodesObserversCache.next()) {
164 
165  // get a node from the selection
166  aNode = TTNodePtr((TTPtr)mNodesObserversCache.current()[0]);
167 
168  // get the value of the attribute
169  anObject = aNode->getObject();
170 
171  if (anObject.valid()) {
172 
173  err = anObject.get(ttAttributeName, data);
174 
175  if (!err) {
176 
177  // don't return empty value
178  if (data.size()) {
179 
180  // output the address of the node (in case we use * inside the binded address)
181  aNode->getAddress(anAddress);
182 
183  // return the address
184  if (mReturnAddressCallback.valid())
185  {
186  if (ttAttributeName == kTTSym_value)
187  mReturnAddressCallback.send("notify", anAddress);
188  else
189  mReturnAddressCallback.send("notify", anAddress.appendAttribute(ToAppName(ttAttributeName)));
190  }
191 
192  // return the value
193  if (mReturnValueCallback.valid())
194  mReturnValueCallback.send("notify", data);
195 
196  }
197  else
198  return kTTErrGeneric;
199  }
200  }
201  }
202 
203  return kTTErrNone;
204  }
205 
206  return kTTErrGeneric;
207 }
208 
209 TTErr TTReceiver::Grab(const TTValue& inputValue, TTValue& outputValue)
210 {
211  TTNodePtr aNode;
212  TTObject anObject;
213  TTSymbol ttAttributeName;
214  TTValue v;
215 
216  if (!mNodesObserversCache.isEmpty()) {
217 
218  ttAttributeName = ToTTName(mAddress.getAttribute());
219 
220  // default attribute to bind is value
221  if (ttAttributeName == NO_ATTRIBUTE)
222  ttAttributeName = kTTSym_value;
223 
224  // grab the value for the first node only
225  mNodesObserversCache.begin();
226  aNode = TTNodePtr((TTPtr)mNodesObserversCache.current()[0]);
227 
228  // get the value of the attribute
229  anObject = aNode->getObject();
230 
231  return anObject.get(ttAttributeName, outputValue);
232  }
233 
234  return kTTErrGeneric;
235 }
236 
237 TTErr TTReceiver::bindAddress(TTNodeDirectoryPtr aDirectory)
238 {
239  TTAddress anAddress;
240  TTSymbol ttAttributeName;
241  TTList aNodeList;
242  TTNodePtr aNode;
243  TTErr err;
244 
245  if (!aDirectory)
246  return bindApplication();
247 
248  // for any attribute observation except created, destroyed
249  ttAttributeName = ToTTName(mAddress.getAttribute());
250 
251  // default attribute to bind is value
252  if (ttAttributeName == NO_ATTRIBUTE)
253  ttAttributeName = kTTSym_value;
254 
255  if ((ttAttributeName != kTTSym_created) && (ttAttributeName != kTTSym_destroyed))
256  {
257  // Look for node(s) into the directory
258  err = aDirectory->Lookup(mAddress, aNodeList, &aNode);
259 
260  // Start attribute observation on each existing node of the selection
261  if (!err) {
262 
263  for (aNodeList.begin(); aNodeList.end(); aNodeList.next())
264  {
265  // get a node from the selection
266  aNode = TTNodePtr((TTPtr)aNodeList.current()[0]);
267 
268  // prepare the callback mechanism to be notified about changing value attribute if the attribute exist
269  aNode->getAddress(anAddress);
270  cacheNodeObserver(aNode, anAddress, ttAttributeName);
271  }
272  }
273  }
274 
275  // observe any creation or destruction below the attr_name address
276  mAddressObserver = TTObject("callback");
277 
278  mAddressObserver.set(kTTSym_baton, TTPtr(this)); // théo -- we have to register our self as a #TTPtr to not reference this instance otherwhise the destructor will never be called
279  mAddressObserver.set(kTTSym_function, TTPtr(&TTReceiverDirectoryCallback));
280 
281  aDirectory->addObserverForNotifications(mAddress, mAddressObserver, 0); // ask for notification only for equal addresses
282 
283  return kTTErrNone;
284 }
285 
286 void TTReceiver::cacheNodeObserver(TTNodePtr aNode, TTAddress& anAddress, TTSymbol& anAttributeName)
287 {
288  TTObject anObject = aNode->getObject();
289 
290  if (anObject.valid()) {
291 
292  TTAttributePtr anAttribute = NULL;
293 
294  TTErr err = anObject.instance()->findAttribute(anAttributeName, &anAttribute);
295 
296  if (!err) {
297 
298  TTValue baton, newElement, none, data;
299  TTObject newObserver = TTObject("callback");
300 
301  baton = TTValue(TTObject(this));
302  if (anAttributeName == kTTSym_value)
303  baton.append(anAddress);
304  else
305  baton.append(anAddress.appendAttribute(ToAppName(anAttributeName)));
306 
307  newObserver.set(kTTSym_baton, baton);
308  newObserver.set(kTTSym_function, TTPtr(&TTReceiverAttributeCallback));
309 
310  anAttribute->registerObserverForNotifications(newObserver);
311 
312  // for Mirror object : enable listening
313  if (anObject.name() == kTTSym_Mirror)
314  TTMirrorPtr(anObject.instance())->enableListening(*anAttribute, YES);
315 
316  // memorize the node and his attribute observer
317  newElement = (TTPtr)aNode;
318  newElement.append(newObserver);
319  mNodesObserversCache.appendUnique(newElement);
320 
321  // cache the object for quick access
322  mObjectCache->appendUnique(anObject);
323 
324  // return address and value if possible (except for signal case)
325  if (anAttributeName != kTTSym_signal) {
326 
327  err = anObject.get(anAttributeName, data);
328 
329  if (!err) {
330 
331  // don't return empty value
332  if (data.size()) {
333 
334  // return the address of the node (in case we use * inside the binded address)
335  if (mReturnAddressCallback.valid())
336  {
337  if (anAttributeName == kTTSym_value)
338  mReturnAddressCallback.send("notify", anAddress);
339  else
340  mReturnAddressCallback.send("notify", anAddress.appendAttribute(ToAppName(anAttributeName)));
341  }
342 
343  // return the value
344  if (mReturnValueCallback.valid())
345  mReturnValueCallback.send("notify", data);
346 
347  }
348  }
349  }
350  }
351  }
352 }
353 
354 TTErr TTReceiver::unbindAddress(TTNodeDirectoryPtr aDirectory)
355 {
356  TTValue oldElement;
357  TTNodePtr aNode;
358  TTObject oldObserver;
359  TTSymbol ttAttributeName;
360 
361  if (mAddress != kTTAdrsEmpty) {
362 
363  // stop attribute obeservation
364  // for each node of the selection
365  ttAttributeName = ToTTName(mAddress.getAttribute());
366 
367  // default attribute to bind is value
368  if (ttAttributeName == NO_ATTRIBUTE)
369  ttAttributeName = kTTSym_value;
370 
371  for (mNodesObserversCache.begin(); mNodesObserversCache.end(); mNodesObserversCache.next()){
372 
373  // get a cache element
374  oldElement = mNodesObserversCache.current();
375 
376  // get the node
377  aNode = TTNodePtr((TTPtr)oldElement[0]);
378 
379  // get the observer
380  oldObserver = oldElement[1];
381 
382  // stop attribute observation of the node if the attribute exist
383  uncacheNodeObserver(aNode, oldObserver, ttAttributeName);
384  }
385 
386  // clear observer cache
387  mNodesObserversCache.clear();
388 
389  // clear object cache
390  mObjectCache->clear();
391 
392  // stop life cycle observation
393  if (mAddressObserver.valid() && aDirectory) {
394 
395  aDirectory->removeObserverForNotifications(mAddress, mAddressObserver);
396 
397  mAddressObserver = TTObject();
398  }
399  }
400 
401  return kTTErrNone;
402 }
403 
404 void TTReceiver::uncacheNodeObserver(TTNodePtr aNode, TTObject& oldObserver, TTSymbol& anAttributeName)
405 {
406  TTObject anObject = aNode->getObject();
407 
408  if (anObject.valid()) {
409 
410  TTAttributePtr anAttribute = NULL;
411 
412  TTErr err = anObject.instance()->findAttribute(anAttributeName, &anAttribute);
413 
414  if (!err) {
415 
416  anAttribute->unregisterObserverForNotifications(oldObserver);
417 
418  // for Mirror object : disable listening
419  if (anObject.name() == kTTSym_Mirror)
420  TTMirrorPtr(anObject.instance())->enableListening(*anAttribute, NO);
421  }
422  }
423 }
424 
425 TTErr TTReceiver::bindApplication()
426 {
427  if (!mApplicationObserver.valid()) {
428 
429  mApplicationObserver = TTObject("callback");
430 
431  mApplicationObserver.set(kTTSym_baton, TTPtr(this)); // théo -- we have to register our self as a #TTPtr to not reference this instance otherwhise the destructor will never be called
432  mApplicationObserver.set(kTTSym_function, TTPtr(&TTReceiverApplicationManagerCallback));
433 
434  return TTApplicationManagerAddApplicationObserver(mAddress.getDirectory(), mApplicationObserver);
435  }
436 
437  return kTTErrGeneric;
438 }
439 
440 TTErr TTReceiver::unbindApplication()
441 {
442  if (mApplicationObserver.valid()) {
443 
444  TTApplicationManagerRemoveApplicationObserver(mAddress.getDirectory(), mApplicationObserver);
445 
446  mApplicationObserver = TTObject();
447  }
448 
449  return kTTErrNone;
450 }
451 
453 {
454  TTReceiverPtr aReceiver;
455  TTAddress anAddress;
456  TTSymbol ttAttributeName;
457  TTObject oldObserver, o;
458  TTNodePtr aNode, p_node;
459  TTValue oldElement, v, b, none;
460  TTUInt8 flag;
461  TTBoolean found;
462 
463  // unpack baton (a #TTReceiverPtr)
464  aReceiver = TTReceiverPtr((TTPtr)baton[0]); // théo -- we have to register our self as a #TTPtr to not reference this instance otherwhise the destructor will never be called
465 
466  // Unpack data (anAddress, aNode, flag, anObserver)
467  anAddress = data[0];
468  aNode = TTNodePtr((TTPtr)data[1]);
469  flag = data[2];
470 
471  ttAttributeName = ToTTName(aReceiver->mAddress.getAttribute());
472 
473  // default attribute to bind is value
474  if (ttAttributeName == NO_ATTRIBUTE)
475  ttAttributeName = kTTSym_value;
476 
477  switch (flag) {
478 
479  case kAddressCreated :
480  {
481 
482  if (ttAttributeName == kTTSym_created)
483  {
484  // return the address
485  v = aReceiver->mAddress.removeAttribute();
486 
487  if (aReceiver->mReturnAddressCallback.valid())
488  aReceiver->mReturnAddressCallback.send("notify", v);
489  }
490  else if (ttAttributeName != kTTSym_destroyed)
491  {
492  // is the observer already exist ?
493  found = false;
494 
495  // for each node of the selection
496  for(aReceiver->mNodesObserversCache.begin(); aReceiver->mNodesObserversCache.end(); aReceiver->mNodesObserversCache.next()) {
497 
498  // get the node of the couple
499  p_node = TTNodePtr((TTPtr)aReceiver->mNodesObserversCache.current()[0]);
500 
501  // compare it to the receive node
502  if(p_node == aNode)
503  found = true;
504  }
505 
506  // prepare the callback mecanism to be notified about changing value attribute if the attribute exist
507  if (!found)
508  aReceiver->cacheNodeObserver(aNode, anAddress, ttAttributeName);
509 
510  }
511 
512  break;
513  }
514 
515  case kAddressDestroyed :
516  {
517  if (ttAttributeName == kTTSym_destroyed)
518  {
519  // return the address
520  v = aReceiver->mAddress.removeAttribute();
521 
522  if (aReceiver->mReturnAddressCallback.valid())
523  aReceiver->mReturnAddressCallback.send("notify", v);
524  }
525  else if (ttAttributeName != kTTSym_created)
526  {
527  // look at the node among memorized <node, observer>
528 
529  // for each node of the selection
530  found = false;
531  for(aReceiver->mNodesObserversCache.begin(); aReceiver->mNodesObserversCache.end(); aReceiver->mNodesObserversCache.next()){
532 
533  // get a oldElement
534  oldElement = aReceiver->mNodesObserversCache.current();
535 
536  // get the node
537  p_node = TTNodePtr((TTPtr)oldElement[0]);
538 
539  // compare it to the receive node
540  if(p_node == aNode){
541  found = true;
542  break;
543  }
544  }
545 
546  if (found) {
547 
548  // get the observer
549  oldObserver = oldElement[1];
550 
551  // stop attribute observation of the node if the attribute exist
552  aReceiver->uncacheNodeObserver(aNode, oldObserver, ttAttributeName);
553 
554  // forget this oldElement
555  aReceiver->mNodesObserversCache.remove(oldElement);
556 
557  // forget the object
558  aReceiver->mObjectCache->remove(aNode->getObject());
559  }
560  }
561  break;
562  }
563 
564  default:
565  break;
566  }
567 
568  return kTTErrNone;
569 }
570 
572 {
573  TTObject o;
574  TTReceiverPtr aReceiver;
575  TTValue v, none;
576 
577  // unpack baton (a #TTReceiver, address)
578  o = baton[0];
579  aReceiver = (TTReceiverPtr)o.instance();
580 
581  if (aReceiver->mActive) {
582 
583  // return address to the owner of #TTReceiver
584  if (aReceiver->mReturnAddressCallback.valid())
585  aReceiver->mReturnAddressCallback.send("notify", baton[1]);
586 
587  // return the value to the owner of #TTReceiver
588  if (aReceiver->mReturnValueCallback.valid())
589  aReceiver->mReturnValueCallback.send("notify", data);
590  }
591 
592  return kTTErrNone;
593 }
594 
596 {
597  TTReceiverPtr aReceiver;
598  TTSymbol anApplicationName;
599  TTObject anApplication;
600  TTValue v;
601  TTUInt8 flag;
602 
603  // unpack baton (a #TTReceiverPtr)
604  aReceiver = TTReceiverPtr((TTPtr)baton[0]); // théo -- we have to register our self as a #TTPtr to not reference this instance otherwhise the destructor will never be called
605 
606  // Unpack data (applicationName, application, flag, observer)
607  anApplicationName = data[0];
608  anApplication = data[1];
609  flag = data[2];
610 
611  switch (flag) {
612 
614  {
615  aReceiver->bindAddress(accessApplicationDirectoryFrom(aReceiver->mAddress));
616  break;
617  }
618 
620  {
621  aReceiver->setActive(YES);
622  break;
623  }
624 
626  {
627  aReceiver->setActive(NO);
628  break;
629  }
630 
631  case kApplicationReleased :
632  {
633  aReceiver->unbindAddress(accessApplicationDirectoryFrom(aReceiver->mAddress));
634  break;
635  }
636 
637  default:
638  break;
639  }
640 
641  return kTTErrNone;
642 }
an application have been released by the application manager
bool TTBoolean
Boolean flag, same as Boolean on the Mac.
Definition: TTBase.h:167
#define accessApplicationDirectoryFrom(anAddress)
Access to an application directory using an address.
TTErr registerObserverForNotifications(const TTObject &observingObject)
Register an observer.
friend TTErr TTMODULAR_EXPORT TTReceiverDirectoryCallback(const TTValue &baton, const TTValue &data)
Definition: TTReceiver.cpp:452
this flag means that a TTNode have been destroyed in the tree structure
Definition: TTAddressBase.h:56
TTErr send(const TTSymbol aName)
Send a message to this object with no arguments.
Definition: TTObject.cpp:135
TTAddress appendAttribute(TTSymbol anAttribute)
Return a new TTAddress with attribute part.
Definition: TTAddress.h:161
TTErr unregisterObserverForNotifications(const TTObject &observingObject)
Unregister an observer for notifications.
TTErr TTReceiverAttributeCallback(const TTValue &baton, const TTValue &data)
Definition: TTReceiver.cpp:571
TTSymbol & getDirectory()
Get the directory part.
Definition: TTAddress.h:106
#define addAttribute(name, type)
A convenience macro to be used by subclasses for registering attributes with a custom getter...
Definition: TTAttribute.h:29
We build a directory of TTNodes, and you can request a pointer for any TTNode, or add an observer to ...
Definition: TTNode.h:59
application's protocol will be stopped
TTReceiver ...
Definition: TTReceiver.h:27
A Receiver Object.
The TTAddress class is used to represent a string and efficiently pass and compare that string...
Definition: TTAddress.h:29
Create and use Jamoma object instances.
Definition: TTObject.h:29
TTObject & getObject()
Get the object binded by this node.
Definition: TTNode.cpp:468
size_type size() const noexcept
Return the number of elements.
This class represents a single attribute, as used by the TTObjectBase class.
Definition: TTAttribute.h:79
Symbol type.
Definition: TTBase.h:282
TTErr Lookup(TTAddress anAddress, TTList &returnedTTNodes, TTNodePtr *firstReturnedTTNode)
Find TTNodes by address.
#define ToAppName(ttName)
Convert a local application TTSymbol into a tt name.
TTErr TTMODULAR_EXPORT TTApplicationManagerAddApplicationObserver(TTSymbol anApplicationName, const TTObject anObserver)
Add a TTCallback as observer of application creation/destruction note : it uses the extern TTModularA...
void append(const T &anElementValueToAppend)
Insert a single TTElement at the end.
Definition: TTValue.h:243
void * TTPtr
A generic pointer.
Definition: TTBase.h:248
TTErr get(const TTSymbol aName, T &aReturnedValue) const
Get an attribute value for an object.
application's protocol have been started
TTSymbol name() const
Return the name of this class.
Definition: TTObject.cpp:129
#define addAttributeProperty(attributeName, propertyName, initialValue)
A convenience macro to be used for registering properties of attributes.
Definition: TTAttribute.h:68
TTErr set(const TTSymbol aName, T aValue)
Set an attribute value for an object.
The TTSymbol class is used to represent a string and efficiently pass and compare that string...
Definition: TTSymbol.h:26
TTErr TTReceiverDirectoryCallback(const TTValue &baton, const TTValue &data)
Definition: TTReceiver.cpp:452
TTErr addObserverForNotifications(TTAddress anAddress, TTObject &anObserver, TTInt8 maxDepthDifference=-1)
Add a TTCallback as a life cycle observer of all nodes below this one.
#define ToTTName(appName)
Convert a tt name TTSymbol into a local application name.
Boolean (1/0) or (true/false) flag.
Definition: TTBase.h:281
TTErr TTMODULAR_EXPORT TTApplicationManagerRemoveApplicationObserver(TTSymbol anApplicationName, const TTObject anObserver)
Remove a TTCallback as observer of application creation/destruction note : it uses the extern TTModul...
friend TTErr TTMODULAR_EXPORT TTReceiverAttributeCallback(const TTValue &baton, const TTValue &data)
Definition: TTReceiver.cpp:571
TTSymbol & getAttribute()
Get the attribute part.
Definition: TTAddress.h:130
#define addMessageWithArguments(name)
A convenience macro to be used by subclasses for registering messages.
Definition: TTMessage.h:27
an application have been intantiated by the application manager
friend TTErr TTMODULAR_EXPORT TTReceiverApplicationManagerCallback(const TTValue &baton, const TTValue &data)
Definition: TTReceiver.cpp:595
TTErr getAddress(TTAddress &returnedAddress, TTAddress from=kTTAdrsEmpty)
Get the address of the node.
Definition: TTNode.cpp:478
Something went wrong, but what exactly is not known. Typically used for context-specific problems...
Definition: TTBase.h:344
TTErr
Jamoma Error Codes Enumeration of error codes that might be returned by any of the TTBlue functions a...
Definition: TTBase.h:342
this flag means that a TTNode have been created in the tree structure
Definition: TTAddressBase.h:57
TTErr removeObserverForNotifications(TTAddress anAddress, TTObject &anObserver)
Remove a TTCallback as a life cycle observer of all nodes below this one.
Pointer type.
Definition: TTBase.h:284
#define addAttributeWithSetter(name, type)
A convenience macro to be used by subclasses for registering attributes with a custom setter...
Definition: TTAttribute.h:47
#define addMessage(name)
A convenience macro to be used by subclasses for registering messages.
Definition: TTMessage.h:19
TODO : how to have TTGetterMethod and TTSetterMethod for Mirror message Property ?
Definition: TTMirror.h:70
TTObjectBase * instance() const
Return a direct pointer to the internal instance.
Definition: TTObject.cpp:105
No Error.
Definition: TTBase.h:343
TTAddress removeAttribute()
Return a new TTAddress without attribute part.
Definition: TTAddress.h:155
TTBoolean valid() const
Determine if the object contained by this TTObject is truly ready for use.
Definition: TTObject.cpp:179
We build a tree of TTNodes, and you can request a pointer for any TTNode, or add an observer to any T...
[doxygenAppendixC_copyExample]
Definition: TTValue.h:34
TTErr TTReceiverApplicationManagerCallback(const TTValue &baton, const TTValue &data)
Definition: TTReceiver.cpp:595
TTErr findAttribute(const TTSymbol name, TTAttribute **attr)
Find an attribute.
unsigned char TTUInt8
8 bit unsigned integer (char)
Definition: TTBase.h:174
#define addMessageProperty(messageName, propertyName, initialValue)
A convenience macro to be used for registering properties of messages.
Definition: TTMessage.h:37