From 277b1da1b4b6aa602c4eb1900cabaf427eb64a7f Mon Sep 17 00:00:00 2001 From: Michael Drake Date: Sun, 2 Aug 2015 17:04:57 +0100 Subject: Improve documentation and naming for DOM change watcher. --- src/dom/Makefile | 2 +- src/dom/event.c | 164 -------------------------------------------------- src/dom/event.h | 19 ------ src/dom/watcher.c | 176 ++++++++++++++++++++++++++++++++++++++++++++++++++++++ src/dom/watcher.h | 32 ++++++++++ src/layout.c | 6 +- 6 files changed, 212 insertions(+), 187 deletions(-) delete mode 100644 src/dom/event.c delete mode 100644 src/dom/event.h create mode 100644 src/dom/watcher.c create mode 100644 src/dom/watcher.h diff --git a/src/dom/Makefile b/src/dom/Makefile index 30e1847..0baa497 100644 --- a/src/dom/Makefile +++ b/src/dom/Makefile @@ -6,6 +6,6 @@ # Released under the ISC License (see COPYING file) # Sources -DIR_SOURCES := event.c +DIR_SOURCES := watcher.c include $(NSBUILD)/Makefile.subdir diff --git a/src/dom/event.c b/src/dom/event.c deleted file mode 100644 index e24b699..0000000 --- a/src/dom/event.c +++ /dev/null @@ -1,164 +0,0 @@ -/* - * This file is part of LibNSLayout - * Licensed under the ISC License, http://opensource.org/licenses/ISC - * Copyright 2015 Michael Drake - */ - -/** \file src/dom/event.c - * DOM mutation handling - */ - -#include -#include -#include -#include - -#include "layout.h" -#include "dom/event.h" -#include "util/dom-str.h" -#include "util/util.h" - -static const char *nsl__dom_node_type_to_string(dom_node_type type) -{ - const char *str[] = { - "ELEMENT_NODE", - "ATTRIBUTE_NODE", - "TEXT_NODE", - "CDATA_SECTION_NODE", - "ENTITY_REFERENCE_NODE", - "ENTITY_NODE", - "PROCESSING_INSTRUCTION_NODE", - "COMMENT_NODE", - "DOCUMENT_NODE", - "DOCUMENT_TYPE_NODE", - "DOCUMENT_FRAGMENT_NODE", - "NOTATION_NODE" - }; - assert(DOM_NODE_TYPE_COUNT == 12); - - return str[type - 1]; -} - -static void nsl__dom_event_handler(struct dom_event *evt, void *pw) -{ - dom_event_target *node = NULL; - dom_node_type node_type; - dom_string *name = NULL; - dom_string *type = NULL; - dom_exception exc; - - UNUSED(pw); - - printf(" DOM Event: "); - - /* Ugly test to see what events come out */ - exc = dom_event_get_target(evt, &node); - if ((exc != DOM_NO_ERR) || (node == NULL)) { - printf("FAILED to get target node!\n"); - goto fail; - } - - exc = dom_node_get_node_type(node, &node_type); - if (exc != DOM_NO_ERR) { - printf("FAILED to get target node type!\n"); - goto fail; - } - - if (node_type == DOM_ELEMENT_NODE) { - exc = dom_node_get_node_name(node, &name); - if ((exc != DOM_NO_ERR) || (name == NULL)) { - printf("FAILED to get target node name!\n"); - goto fail; - } - } - - exc = dom_event_get_type(evt, &type); - if ((exc != DOM_NO_ERR) || (type == NULL)) { - printf("FAILED to get event type!\n"); - goto fail; - } - - if (node_type == DOM_ELEMENT_NODE) { - printf("<%s> %s", - dom_string_data(name), - dom_string_data(type)); - } else { - printf("%s %s", - nsl__dom_node_type_to_string(node_type), - dom_string_data(type)); - } - -fail: - if (type != NULL) dom_string_unref(type); - if (name != NULL) dom_string_unref(name); - if (node != NULL) dom_node_unref(node); - - printf("\n"); -} - -/* Exported function, documented in src/dom/event.h */ -nslayout_error nsl_dom_event_layout_init(nslayout_layout *layout) -{ - nslayout_error err; - dom_exception exc; - - /* TODO: LibDOM event listeners are really slow. Need to find a better - * way to get DOM change notifications. - */ - - exc = dom_event_listener_create(layout->doc, nsl__dom_event_handler, - layout, &layout->listener); - if (exc != DOM_NO_ERR) { - return NSL_DOM_ERR(exc); - } - exc = dom_event_target_add_event_listener( - layout->doc, nsl_dom_str_node_inserted, - layout->listener, false); - if (exc != DOM_NO_ERR) { - err = NSL_DOM_ERR(exc); - goto fail; - } - exc = dom_event_target_add_event_listener( - layout->doc, nsl_dom_str_subtree_modified, - layout->listener, false); - if (exc != DOM_NO_ERR) { - (void) dom_event_target_remove_event_listener( - layout->doc, nsl_dom_str_node_inserted, - layout->listener, false); - err = NSL_DOM_ERR(exc); - goto fail; - } - - return NSLAYOUT_OK; - -fail: - dom_event_listener_unref(layout->listener); - layout->listener = NULL; - - return err; -} - -/* Exported function, documented in src/dom/event.h */ -nslayout_error nsl_dom_event_layout_fini(nslayout_layout *layout) -{ - dom_exception exc1, exc2; - - exc1 = dom_event_target_remove_event_listener( - layout->doc, nsl_dom_str_node_inserted, - layout->listener, false); - exc2 = dom_event_target_remove_event_listener( - layout->doc, nsl_dom_str_subtree_modified, - layout->listener, false); - - if (exc1 != DOM_NO_ERR) { - return NSL_DOM_ERR(exc1); - } - if (exc2 != DOM_NO_ERR) { - return NSL_DOM_ERR(exc2); - } - - dom_event_listener_unref(layout->listener); - layout->listener = NULL; - - return NSLAYOUT_OK; -} diff --git a/src/dom/event.h b/src/dom/event.h deleted file mode 100644 index f519f40..0000000 --- a/src/dom/event.h +++ /dev/null @@ -1,19 +0,0 @@ -/* - * This file is part of LibNSLayout - * Licensed under the ISC License, http://opensource.org/licenses/ISC - * Copyright 2015 Michael Drake - */ - -/** \file src/dom/event.h - * Layout object handling - */ - -#ifndef nslayout_dom_event_h_ -#define nslayout_dom_event_h_ - -#include - -nslayout_error nsl_dom_event_layout_init(nslayout_layout *layout); -nslayout_error nsl_dom_event_layout_fini(nslayout_layout *layout); - -#endif diff --git a/src/dom/watcher.c b/src/dom/watcher.c new file mode 100644 index 0000000..a4e8d64 --- /dev/null +++ b/src/dom/watcher.c @@ -0,0 +1,176 @@ +/* + * This file is part of LibNSLayout + * Licensed under the ISC License, http://opensource.org/licenses/ISC + * Copyright 2015 Michael Drake + */ + +/** \file src/dom/watcher.c + * DOM mutation handling + */ + +#include +#include +#include +#include + +#include "layout.h" +#include "dom/watcher.h" +#include "util/dom-str.h" +#include "util/util.h" + +/** + * Convert a dom node type to a string + * + * \param[in] type DOM node type + * \return appropriate string. + */ +static const char *nsl__dom_node_type_to_string(dom_node_type type) +{ + const char *str[] = { + "ELEMENT_NODE", + "ATTRIBUTE_NODE", + "TEXT_NODE", + "CDATA_SECTION_NODE", + "ENTITY_REFERENCE_NODE", + "ENTITY_NODE", + "PROCESSING_INSTRUCTION_NODE", + "COMMENT_NODE", + "DOCUMENT_NODE", + "DOCUMENT_TYPE_NODE", + "DOCUMENT_FRAGMENT_NODE", + "NOTATION_NODE" + }; + assert(DOM_NODE_TYPE_COUNT == 12); + + return str[type - 1]; +} + +/** + * LibDOM event handler + * + * \param[in] evt The LibDOM event object + * \param[in] pw Pointer to our nslayout_layout object + */ +static void nsl__dom_event_handler(struct dom_event *evt, void *pw) +{ + dom_event_target *node = NULL; + dom_node_type node_type; + dom_string *name = NULL; + dom_string *type = NULL; + dom_exception exc; + + UNUSED(pw); + + printf(" DOM Event: "); + + /* Ugly test to see what events come out */ + exc = dom_event_get_target(evt, &node); + if ((exc != DOM_NO_ERR) || (node == NULL)) { + printf("FAILED to get target node!\n"); + goto fail; + } + + exc = dom_node_get_node_type(node, &node_type); + if (exc != DOM_NO_ERR) { + printf("FAILED to get target node type!\n"); + goto fail; + } + + if (node_type == DOM_ELEMENT_NODE) { + exc = dom_node_get_node_name(node, &name); + if ((exc != DOM_NO_ERR) || (name == NULL)) { + printf("FAILED to get target node name!\n"); + goto fail; + } + } + + exc = dom_event_get_type(evt, &type); + if ((exc != DOM_NO_ERR) || (type == NULL)) { + printf("FAILED to get event type!\n"); + goto fail; + } + + if (node_type == DOM_ELEMENT_NODE) { + printf("<%s> %s", + dom_string_data(name), + dom_string_data(type)); + } else { + printf("%s %s", + nsl__dom_node_type_to_string(node_type), + dom_string_data(type)); + } + +fail: + if (type != NULL) dom_string_unref(type); + if (name != NULL) dom_string_unref(name); + if (node != NULL) dom_node_unref(node); + + printf("\n"); +} + +/* Exported function, documented in src/dom/event.h */ +nslayout_error nsl_dom_watcher_add_for_layout(nslayout_layout *layout) +{ + nslayout_error err; + dom_exception exc; + + /* TODO: LibDOM event listeners are really slow. Need to find a better + * way to get DOM change notifications. + */ + + exc = dom_event_listener_create(layout->doc, nsl__dom_event_handler, + layout, &layout->listener); + if (exc != DOM_NO_ERR) { + return NSL_DOM_ERR(exc); + } + exc = dom_event_target_add_event_listener( + layout->doc, nsl_dom_str_node_inserted, + layout->listener, false); + if (exc != DOM_NO_ERR) { + err = NSL_DOM_ERR(exc); + goto fail; + } + exc = dom_event_target_add_event_listener( + layout->doc, nsl_dom_str_subtree_modified, + layout->listener, false); + if (exc != DOM_NO_ERR) { + (void) dom_event_target_remove_event_listener( + layout->doc, nsl_dom_str_node_inserted, + layout->listener, false); + err = NSL_DOM_ERR(exc); + goto fail; + } + + return NSLAYOUT_OK; + +fail: + dom_event_listener_unref(layout->listener); + layout->listener = NULL; + + return err; +} + +/* Exported function, documented in src/dom/event.h */ +nslayout_error nsl_dom_watcher_remove_for_layout(nslayout_layout *layout) +{ + dom_exception exc1, exc2; + + exc1 = dom_event_target_remove_event_listener( + layout->doc, nsl_dom_str_node_inserted, + layout->listener, false); + exc2 = dom_event_target_remove_event_listener( + layout->doc, nsl_dom_str_subtree_modified, + layout->listener, false); + + if (exc1 != DOM_NO_ERR) { + return NSL_DOM_ERR(exc1); + } + if (exc2 != DOM_NO_ERR) { + return NSL_DOM_ERR(exc2); + } + + dom_event_listener_unref(layout->listener); + layout->listener = NULL; + + return NSLAYOUT_OK; +} diff --git a/src/dom/watcher.h b/src/dom/watcher.h new file mode 100644 index 0000000..87f0a1b --- /dev/null +++ b/src/dom/watcher.h @@ -0,0 +1,32 @@ +/* + * This file is part of LibNSLayout + * Licensed under the ISC License, http://opensource.org/licenses/ISC + * Copyright 2015 Michael Drake + */ + +/** \file src/dom/watcher.h + * Layout object handling + */ + +#ifndef nslayout_dom_watcher_h_ +#define nslayout_dom_watcher_h_ + +#include + +/** + * Add DOM change watchers to the layout's document.' + * + * \param[in] layout nslayout_layout object to set watchers for. + * \return NSLAYOUT_OK on success, appropriate error otherwise. + */ +nslayout_error nsl_dom_watcher_add_for_layout(nslayout_layout *layout); + +/** + * Remove DOM change watchers from the layout's document. + * + * \param[in] layout nslayout_layout object remove watchers from. + * \return NSLAYOUT_OK on success, appropriate error otherwise. + */ +nslayout_error nsl_dom_watcher_remove_for_layout(nslayout_layout *layout); + +#endif diff --git a/src/layout.c b/src/layout.c index f1a1490..1c341b6 100644 --- a/src/layout.c +++ b/src/layout.c @@ -13,7 +13,7 @@ #include #include "layout.h" -#include "dom/event.h" +#include "dom/watcher.h" #include "util/dom-str.h" @@ -62,7 +62,7 @@ nslayout_error nslayout_layout_create( l->pw = pw; /* TODO: error handling */ - nsl_dom_event_layout_init(l); + nsl_dom_watcher_add_for_layout(l); *layout = l; return NSLAYOUT_OK; @@ -77,7 +77,7 @@ nslayout_error nslayout_layout_destroy( /* TODO: free/unref the stuff we own in the layout */ /* TODO: error handling */ - nsl_dom_event_layout_fini(layout); + nsl_dom_watcher_remove_for_layout(layout); free(layout); return NSLAYOUT_OK; -- cgit v1.2.3