cfgitemi.cpp 5.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274
  1. #include <precomp.h>
  2. #include "cfgitemi.h"
  3. #include <api/config/items/attrcb.h>
  4. #include <api/config/items/attribs.h>
  5. #include <bfc/wasabi_std.h>
  6. #include <bfc/memblock.h>
  7. CfgItemI::CfgItemI(const wchar_t *name, GUID guid)
  8. :NamedW(name), myguid(guid), parent_guid(INVALID_GUID) { }
  9. CfgItemI::~CfgItemI()
  10. {
  11. deregisterAll();
  12. }
  13. const wchar_t *CfgItemI::cfgitem_getName()
  14. {
  15. return NamedW::getName();
  16. }
  17. GUID CfgItemI::cfgitem_getGuid()
  18. {
  19. return myguid;
  20. }
  21. void CfgItemI::cfgitem_setPrefix(const wchar_t *_prefix)
  22. {
  23. prefix = _prefix;
  24. }
  25. const wchar_t *CfgItemI::cfgitem_getPrefix()
  26. {
  27. return prefix.c_str();
  28. }
  29. int CfgItemI::cfgitem_getNumAttributes()
  30. {
  31. return attributes.getNumItems();
  32. }
  33. const wchar_t *CfgItemI::cfgitem_enumAttribute(int n)
  34. {
  35. Attribute *attr = attributes[n];
  36. if (attr) return attr->getAttributeName();
  37. return NULL;
  38. }
  39. const wchar_t *CfgItemI::cfgitem_getConfigXML()
  40. {
  41. return cfgxml.c_str();
  42. }
  43. int CfgItemI::cfgitem_getNumChildren()
  44. {
  45. return children.getNumItems();
  46. }
  47. CfgItem *CfgItemI::cfgitem_enumChild(int n)
  48. {
  49. return children[n];
  50. }
  51. GUID CfgItemI::cfgitem_getParentGuid()
  52. {
  53. return parent_guid;
  54. }
  55. void CfgItemI::cfgitem_onRegister()
  56. {
  57. foreach(children)
  58. WASABI_API_CONFIG->config_registerCfgItem(children.getfor());
  59. endfor
  60. }
  61. void CfgItemI::cfgitem_onDeregister()
  62. {
  63. foreach(children)
  64. WASABI_API_CONFIG->config_deregisterCfgItem(children.getfor());
  65. endfor
  66. }
  67. Attribute *CfgItemI::getAttributeByName(const wchar_t *name)
  68. {
  69. Attribute *attr;
  70. foreach(attributes)
  71. attr = attributes.getfor();
  72. if (!WCSICMP(name, attr->getAttributeName())) return attr;
  73. endfor
  74. return NULL;
  75. }
  76. int CfgItemI::cfgitem_getAttributeType(const wchar_t *name)
  77. {
  78. Attribute *attr = getAttributeByName(name);
  79. if (attr == NULL) return AttributeType::NONE;
  80. return attr->getAttributeType();
  81. }
  82. const wchar_t *CfgItemI::cfgitem_getAttributeConfigGroup(const wchar_t *name)
  83. {
  84. Attribute *attr = getAttributeByName(name);
  85. if (attr == NULL) return NULL;
  86. return attr->getConfigGroup();
  87. }
  88. int CfgItemI::cfgitem_getDataLen(const wchar_t *name)
  89. {
  90. Attribute *attr = getAttributeByName(name);
  91. if (attr == NULL) return -1;
  92. return attr->getDataLen();
  93. }
  94. int CfgItemI::cfgitem_getData(const wchar_t *name, wchar_t *data, int data_len)
  95. {
  96. Attribute *attr = getAttributeByName(name);
  97. if (attr == NULL) return -1;
  98. return attr->getData(data, data_len);
  99. }
  100. int CfgItemI::cfgitem_setData(const wchar_t *name, const wchar_t *data)
  101. {
  102. Attribute *attr = getAttributeByName(name);
  103. if (attr == NULL) return -1;
  104. int ret = attr->setDataNoCB(data);
  105. if (ret) cfgitem_onAttribSetValue(attr);
  106. return ret;
  107. }
  108. int CfgItemI::cfgitem_onAttribSetValue(Attribute *attr)
  109. {
  110. // notify dependency watchers that an attribute changed
  111. dependent_sendEvent(CfgItem::depend_getClassGuid(), Event_ATTRIBUTE_CHANGED, 0, (void*)attr->getAttributeName());
  112. //for (int i = 0; ; i++)
  113. //{
  114. // AttrCallback *acb;
  115. // if (!callbacks.multiGetItem(attr, i, &acb))
  116. // break;
  117. //
  118. // acb->onValueChange(attr);
  119. //}
  120. auto elements = callbacks.equal_range(attr);
  121. for (auto& it = elements.first; it != elements.second; ++it)
  122. {
  123. AttrCallback* acb = it->second;
  124. if (acb)
  125. {
  126. acb->onValueChange(attr);
  127. }
  128. }
  129. return 0;
  130. }
  131. void CfgItemI::cfgitem_setGUID(GUID guid)
  132. {
  133. myguid = guid;
  134. }
  135. int CfgItemI::setName(const wchar_t *name)
  136. {
  137. NamedW::setName(name);
  138. // notify dependency watchers that name changed?
  139. dependent_sendEvent(CfgItem::depend_getClassGuid(), Event_NAMECHANGE);
  140. return 1;
  141. }
  142. int CfgItemI::registerAttribute(Attribute *attr, AttrCallback *acb)
  143. {
  144. if (attributes.haveItem(attr)) return 0;
  145. int ret = attributes.addItem(attr) != NULL;
  146. if (!ret) return ret;
  147. attr->setCfgItem(this);
  148. // set optional callback
  149. if (acb != NULL)
  150. {
  151. addCallback(attr, acb);
  152. }
  153. // notify dependency watchers of new attribute
  154. dependent_sendEvent(CfgItem::depend_getClassGuid(), Event_ATTRIBUTE_ADDED, 0, (void*)attr->getAttributeName());
  155. return ret;
  156. }
  157. int CfgItemI::deregisterAttribute(Attribute *attr)
  158. {
  159. if (!attributes.haveItem(attr)) return 0;
  160. int ret = attributes.removeItem(attr);
  161. // notify dependency watchers of attribute going away
  162. dependent_sendEvent(CfgItem::depend_getClassGuid(), Event_ATTRIBUTE_REMOVED, 0, (void*)attr->getAttributeName());
  163. // remove callbacks
  164. //callbacks.multiDelAllForItem(attr, TRUE);
  165. auto elements = callbacks.equal_range(attr);
  166. for (auto& it = elements.first; it != elements.second; ++it)
  167. {
  168. AttrCallback* acb = it->second;
  169. if (acb)
  170. {
  171. delete acb;
  172. }
  173. }
  174. callbacks.erase(attr);
  175. attr->disconnect();
  176. return ret;
  177. }
  178. void CfgItemI::addCallback(Attribute *attr, AttrCallback *acb)
  179. {
  180. ASSERT(attr != NULL);
  181. ASSERT(acb != NULL);
  182. //callbacks.multiAddItem(attr, acb);
  183. callbacks.insert({ attr, acb });
  184. }
  185. void CfgItemI::deregisterAll()
  186. {
  187. foreach(children)
  188. children.getfor()->deregisterAll();
  189. endfor
  190. while (attributes.getNumItems()) deregisterAttribute(attributes[0]);
  191. }
  192. void CfgItemI::addChildItem(CfgItemI *child)
  193. {
  194. ASSERT(child != NULL);
  195. if (!children.haveItem(child))
  196. {
  197. children.addItem(child);
  198. child->setParentGuid(myguid);
  199. }
  200. }
  201. void CfgItemI::setCfgXml(const wchar_t *groupname)
  202. {
  203. cfgxml = groupname;
  204. }
  205. void CfgItemI::setParentGuid(GUID guid)
  206. {
  207. parent_guid = guid;
  208. }
  209. void *CfgItemI::dependent_getInterface(const GUID *classguid)
  210. {
  211. HANDLEGETINTERFACE(CfgItem);
  212. return NULL;
  213. }
  214. int CfgItemI::cfgitem_addAttribute(const wchar_t *name, const wchar_t *defval)
  215. {
  216. if (getAttributeByName(name)) return 0;
  217. registerAttribute(newattribs.addItem(new _string(name, defval)));
  218. return 1;
  219. }
  220. int CfgItemI::cfgitem_delAttribute(const wchar_t *name)
  221. {
  222. Attribute *attr = getAttributeByName(name);
  223. if (!newattribs.haveItem(attr)) return 0;
  224. deregisterAttribute(attr);
  225. delete attr;
  226. newattribs.removeItem(attr);
  227. return 1;
  228. }