r10856 jmb - in /trunk/libcss: src/select/properties.c test/data/parse/properties.dat
by netsurf@semichrome.net
Author: jmb
Date: Tue Sep 28 13:29:33 2010
New Revision: 10856
URL: http://source.netsurf-browser.org?rev=10856&view=rev
Log:
Fix destruction of bytecode for the clip property.
Modified:
trunk/libcss/src/select/properties.c
trunk/libcss/test/data/parse/properties.dat
Modified: trunk/libcss/src/select/properties.c
URL: http://source.netsurf-browser.org/trunk/libcss/src/select/properties.c?re...
==============================================================================
--- trunk/libcss/src/select/properties.c (original)
+++ trunk/libcss/src/select/properties.c Tue Sep 28 13:29:33 2010
@@ -1368,7 +1368,7 @@
{
uint32_t value = getValue(*((uint32_t*)bytecode));
bool has_rect = value & CLIP_SHAPE_RECT;
- bool nonautos = 0;
+ int nonautos = 0;
if (has_rect) {
if ((value & CLIP_RECT_TOP_AUTO) == 0)
Modified: trunk/libcss/test/data/parse/properties.dat
URL: http://source.netsurf-browser.org/trunk/libcss/test/data/parse/properties...
==============================================================================
--- trunk/libcss/test/data/parse/properties.dat (original)
+++ trunk/libcss/test/data/parse/properties.dat Tue Sep 28 13:29:33 2010
@@ -755,6 +755,14 @@
| 0x03200017 0x00000400 0x00000002 0x00000400 0x00000002
#reset
+#data
+* { clip: rect(0px, 220px, 1.7em, 0px) }
+#errors
+#expected
+| 1 *
+| 0x02000017 0x00000000 0x00000000 0x00037000 0x00000000 0x000006cd 0x00000002 0x00000000 0x00000000
+#reset
+
##
## 18 - color
##
12 years, 11 months
r10855 chris_y - in /trunk/netsurf/amiga: clipboard.c gui.c menu.c theme.c
by netsurf@semichrome.net
Author: chris_y
Date: Tue Sep 28 13:03:03 2010
New Revision: 10855
URL: http://source.netsurf-browser.org?rev=10855&view=rev
Log:
Ensure kiosk_mode and frame windows are (a) handled the same wrt menus and (b) not
trying to manipulate non-existant menus
Modified:
trunk/netsurf/amiga/clipboard.c
trunk/netsurf/amiga/gui.c
trunk/netsurf/amiga/menu.c
trunk/netsurf/amiga/theme.c
Modified: trunk/netsurf/amiga/clipboard.c
URL: http://source.netsurf-browser.org/trunk/netsurf/amiga/clipboard.c?rev=108...
==============================================================================
--- trunk/netsurf/amiga/clipboard.c (original)
+++ trunk/netsurf/amiga/clipboard.c Tue Sep 28 13:03:03 2010
@@ -64,6 +64,8 @@
{
if(!g) return;
if(!g->shared->win) return;
+ if(g->shared->bw->browser_window_type != BROWSER_WINDOW_NORMAL) return;
+ if(option_kiosk_mode == true) return;
OnMenu(g->shared->win, AMI_MENU_CLEAR);
OnMenu(g->shared->win, AMI_MENU_COPY);
@@ -76,6 +78,8 @@
{
if(!g) return;
if(!g->shared->win) return;
+ if(g->shared->bw->browser_window_type != BROWSER_WINDOW_NORMAL) return;
+ if(option_kiosk_mode == true) return;
OffMenu(g->shared->win, AMI_MENU_CLEAR);
OffMenu(g->shared->win, AMI_MENU_CUT);
Modified: trunk/netsurf/amiga/gui.c
URL: http://source.netsurf-browser.org/trunk/netsurf/amiga/gui.c?rev=10855&r1=...
==============================================================================
--- trunk/netsurf/amiga/gui.c (original)
+++ trunk/netsurf/amiga/gui.c Tue Sep 28 13:03:03 2010
@@ -1274,19 +1274,22 @@
switch(nskey)
{
case 'n':
- if(option_kiosk_mode == false)
+ if((option_kiosk_mode == false) &&
+ (gwin->bw->browser_window_type == BROWSER_WINDOW_NORMAL))
browser_window_create(NULL, gwin->bw,
0, true, false);
break;
case 't':
- if(option_kiosk_mode == false)
+ if((option_kiosk_mode == false) &&
+ (gwin->bw->browser_window_type == BROWSER_WINDOW_NORMAL))
browser_window_create(NULL, gwin->bw,
0, true, true);
break;
case 'k':
- if(option_kiosk_mode == false)
+ if((option_kiosk_mode == false) &&
+ (gwin->bw->browser_window_type == BROWSER_WINDOW_NORMAL))
browser_window_destroy(gwin->bw);
break;
@@ -1295,7 +1298,8 @@
break;
case 'q':
- if(option_kiosk_mode == false)
+ if((option_kiosk_mode == false) &&
+ (gwin->bw->browser_window_type == BROWSER_WINDOW_NORMAL))
ami_quit_netsurf();
break;
@@ -1325,7 +1329,8 @@
break;
case 'h':
- if(option_kiosk_mode == false)
+ if((option_kiosk_mode == false) &&
+ (gwin->bw->browser_window_type == BROWSER_WINDOW_NORMAL))
ami_open_tree(hotlist,AMI_TREE_HOTLIST);
break;
@@ -1337,7 +1342,8 @@
break;
case 'u': // open url
- if(option_kiosk_mode == false)
+ if((option_kiosk_mode == false) &&
+ (gwin->bw->browser_window_type == BROWSER_WINDOW_NORMAL))
ActivateGadget((struct Gadget *)gwin->objects[GID_URL],
gwin->win, NULL);
break;
@@ -3490,6 +3496,7 @@
if(option_kiosk_mode == true) return;
if(!g) return;
+ if(g->shared->bw->browser_window_type != BROWSER_WINDOW_NORMAL) return;
if(g->tab_node && (g->shared->tabs > 1)) GetAttr(CLICKTAB_Current,
g->shared->objects[GID_TABS],
@@ -3638,7 +3645,8 @@
g->c_y = y;
g->c_h = height;
- if(option_kiosk_mode == false)
+ if((option_kiosk_mode == false) &&
+ (g->shared->bw->browser_window_type == BROWSER_WINDOW_NORMAL))
OnMenu(g->shared->win, AMI_MENU_PASTE);
}
@@ -3650,7 +3658,8 @@
if(!g) return;
if(g->c_h == 0) return;
- if(option_kiosk_mode == false)
+ if((option_kiosk_mode == false) &&
+ (g->shared->bw->browser_window_type == BROWSER_WINDOW_NORMAL))
OffMenu(g->shared->win, AMI_MENU_PASTE);
GetAttr(SPACE_AreaBox, g->shared->objects[GID_BROWSER], (ULONG *)&bbox);
@@ -3678,9 +3687,6 @@
g->shared->oldv = 0;
g->favicon = NULL;
- if(g->shared->bw->browser_window_type != BROWSER_WINDOW_NORMAL ||
- option_kiosk_mode == true) return;
-
ami_menu_update_disabled(g, c);
}
Modified: trunk/netsurf/amiga/menu.c
URL: http://source.netsurf-browser.org/trunk/netsurf/amiga/menu.c?rev=10855&r1...
==============================================================================
--- trunk/netsurf/amiga/menu.c (original)
+++ trunk/netsurf/amiga/menu.c Tue Sep 28 13:03:03 2010
@@ -847,6 +847,9 @@
{
struct Window *win = g->shared->win;
+ if(g->shared->bw->browser_window_type != BROWSER_WINDOW_NORMAL) return;
+ if(option_kiosk_mode == true) return;
+
OffMenu(win,AMI_MENU_CUT);
OffMenu(win,AMI_MENU_COPY);
OffMenu(win,AMI_MENU_PASTE);
Modified: trunk/netsurf/amiga/theme.c
URL: http://source.netsurf-browser.org/trunk/netsurf/amiga/theme.c?rev=10855&r...
==============================================================================
--- trunk/netsurf/amiga/theme.c (original)
+++ trunk/netsurf/amiga/theme.c Tue Sep 28 13:03:03 2010
@@ -390,6 +390,7 @@
if(!g) return;
if(option_kiosk_mode) return;
+ if(g->shared->bw->browser_window_type != BROWSER_WINDOW_NORMAL) return;
if(g->tab_node && (g->shared->tabs > 1))
{
@@ -420,6 +421,7 @@
if(!g) return;
if(option_kiosk_mode) return;
+ if(g->shared->bw->browser_window_type != BROWSER_WINDOW_NORMAL) return;
if(g->tab_node && (g->shared->tabs > 1))
{
12 years, 11 months
r10853 chris_y - /trunk/netsurf/amiga/options.h
by netsurf@semichrome.net
Author: chris_y
Date: Tue Sep 28 11:54:39 2010
New Revision: 10853
URL: http://source.netsurf-browser.org?rev=10853&view=rev
Log:
Change "cache native bitmaps" default back to 0. The userbase's graphics cards are
worse than anticipated.
Modified:
trunk/netsurf/amiga/options.h
Modified: trunk/netsurf/amiga/options.h
URL: http://source.netsurf-browser.org/trunk/netsurf/amiga/options.h?rev=10853...
==============================================================================
--- trunk/netsurf/amiga/options.h (original)
+++ trunk/netsurf/amiga/options.h Tue Sep 28 11:54:39 2010
@@ -58,7 +58,7 @@
char *option_hotlist_file = 0; \
char *option_use_pubscreen = 0; \
char *option_modeid = 0; \
-int option_cache_bitmaps = 2; \
+int option_cache_bitmaps = 0; \
char *option_theme = 0; \
bool option_no_iframes = false; \
bool option_utf8_clipboard = false; \
12 years, 11 months
r10852 vince - /branches/jmb/treeview-redux/desktop/tree.c
by netsurf@semichrome.net
Author: vince
Date: Mon Sep 27 19:04:32 2010
New Revision: 10852
URL: http://source.netsurf-browser.org?rev=10852&view=rev
Log:
review comments and cleanup in tree.c
Modified:
branches/jmb/treeview-redux/desktop/tree.c
Modified: branches/jmb/treeview-redux/desktop/tree.c
URL: http://source.netsurf-browser.org/branches/jmb/treeview-redux/desktop/tre...
==============================================================================
--- branches/jmb/treeview-redux/desktop/tree.c (original)
+++ branches/jmb/treeview-redux/desktop/tree.c Mon Sep 27 19:04:32 2010
@@ -144,61 +144,6 @@
callbacks */
};
-static void tree_delete_node_internal(struct tree *tree, struct node *node,
- bool siblings);
-static void tree_sort_insert(struct node *parent, struct node *node);
-static void tree_set_node_expanded_all(struct tree *tree, struct node *node,
- bool expanded);
-static bool tree_set_node_expanded_internal(struct tree *tree,
- struct node *node, bool expanded, bool folder, bool leaf);
-
-static void tree_draw_node(struct tree *tree, struct node *node,
- int tree_x, int tree_y,
- int clip_x, int clip_y, int clip_width, int clip_height);
-static void tree_draw_node_expansion(struct tree *tree, struct node *node,
- int tree_x, int tree_y);
-static void tree_draw_node_element(struct tree *tree,
- struct node_element *element, int tree_x, int tree_y);
-
-void tree_launch_selected_internal(struct tree *tree, struct node *node);
-
-static void tree_handle_node_changed(struct tree *tree, struct node *node,
- bool recalculate_sizes, bool expansion);
-static void tree_handle_node_element_changed(struct tree *tree,
- struct node_element *element);
-
-static void tree_recalculate_node_element(struct tree *tree,
- struct node_element *element);
-static void tree_recalculate_node_sizes(struct tree *tree, struct node *node,
- bool recalculate_sizes);
-static void tree_recalculate_node_positions(struct tree *tree,
- struct node *root);
-static void tree_recalculate_size(struct tree *tree);
-static int tree_get_node_width(struct node *node);
-static int tree_get_node_height(struct node *node);
-
-
-static void tree_handle_selection_area(struct tree *tree, int y, int height,
- bool invert);
-static void tree_handle_selection_area_node(struct tree *tree,
- struct node *node, int y, int height, bool invert);
-static struct node *tree_get_node_at(struct node *root, int x, int y,
- bool *furniture);
-static struct node_element *tree_get_node_element_at(struct node *node,
- int x, int y, bool *furniture);
-
-static void tree_move_selected_nodes(struct tree *tree,
- struct node *destination, bool before);
-static void tree_selected_to_processing(struct node *node);
-void tree_clear_processing(struct node *node);
-static struct node *tree_move_processing_node(struct tree *tree,
- struct node *node, struct node *link, bool before, bool first);
-
-static void tree_stop_edit(struct tree *tree, bool keep_changes);
-static nserror tree_icon_callback(hlcache_handle *handle,
- const hlcache_event *event, void *pw);
-static void tree_textarea_redraw_request(void *data, int x, int y,
- int width, int height);
/**
* Creates and initialises a new tree.
@@ -212,8 +157,7 @@
* \return the newly created tree, or NULL on memory exhaustion
*/
struct tree *tree_create(unsigned int flags,
- const struct treeview_table *callbacks,
- void *client_data)
+ const struct treeview_table *callbacks, void *client_data)
{
struct tree *tree;
char *title;
@@ -233,7 +177,7 @@
return NULL;
}
tree->root = tree_create_folder_node(NULL, NULL, title,
- false, false, false);
+ false, false, false);
if (tree->root == NULL) {
free(title);
free(tree);
@@ -255,6 +199,245 @@
return tree;
}
+
+/**
+ * Recalculates the dimensions of a node element.
+ *
+ * \param tree the tree to which the element belongs, may be NULL
+ * \param element the element to recalculate
+ */
+static void tree_recalculate_node_element(struct tree *tree,
+ struct node_element *element)
+{
+ struct bitmap *bitmap = NULL;
+ int width, height;
+
+ assert(element != NULL);
+
+ switch (element->type) {
+ case NODE_ELEMENT_TEXT_PLUS_ICON:
+ case NODE_ELEMENT_TEXT:
+ if(element->text == NULL)
+ break;
+
+ if (tree != NULL && element == tree->editing) {
+ textarea_get_dimensions(tree->textarea,
+ &element->box.width, NULL);
+ } else {
+ nsfont.font_width(&plot_fstyle,
+ element->text,
+ strlen(element->text),
+ &element->box.width);
+ }
+
+ element->box.width += 8;
+ element->box.height = TREE_TEXT_HEIGHT;
+
+ if (element->type == NODE_ELEMENT_TEXT_PLUS_ICON)
+ element->box.width += NODE_INSTEP;
+
+ break;
+
+ case NODE_ELEMENT_BITMAP:
+ bitmap = element->bitmap;
+ if (bitmap != NULL) {
+ width = bitmap_get_width(bitmap);
+ height = bitmap_get_height(bitmap);
+ element->box.width = width + 1;
+ element->box.height = height + 2;
+ } else {
+ element->box.width = 0;
+ element->box.height = 0;
+ }
+ break;
+ }
+}
+
+
+/**
+ * Calculates the height of a node including any children
+ *
+ * \param node the node to calculate the height of
+ * \return the total height of the node and children
+ */
+static int tree_get_node_height(struct node *node)
+{
+ int y1;
+
+ assert(node != NULL);
+
+ if ((node->child == NULL) || (node->expanded == false)) {
+ return node->box.height;
+ }
+
+ y1 = node->box.y;
+ if (y1 < 0) {
+ y1 = 0;
+ }
+ node = node->child;
+
+ while ((node->next != NULL) ||
+ ((node->child != NULL) && (node->expanded))) {
+ for (; node->next != NULL; node = node->next);
+
+ if ((node->child != NULL) && (node->expanded)) {
+ node = node->child;
+ }
+ }
+ return node->box.y + node->box.height - y1;
+}
+
+
+/**
+ * Calculates the width of a node including any children
+ *
+ * \param node the node to calculate the height of
+ * \return the total width of the node and children
+ */
+static int tree_get_node_width(struct node *node)
+{
+ int width = 0;
+ int child_width;
+
+ assert(node != NULL);
+
+ for (; node != NULL; node = node->next) {
+ if (width < (node->box.x + node->box.width)) {
+ width = node->box.x + node->box.width;
+ }
+
+ if ((node->child != NULL) && (node->expanded)) {
+ child_width = tree_get_node_width(node->child);
+ if (width < child_width) {
+ width = child_width;
+ }
+ }
+ }
+ return width;
+}
+
+
+/**
+ * Recalculates the position of a node, its siblings and children.
+ *
+ * \param tree the tree to which 'root' belongs
+ * \param root the root node to update from
+ */
+static void tree_recalculate_node_positions(struct tree *tree,
+ struct node *root)
+{
+ struct node *parent;
+ struct node *node;
+ struct node *child;
+ struct node_element *element;
+ int y;
+ bool has_icon;
+
+ for (node = root; node != NULL; node = node->next) {
+
+ parent = node->parent;
+
+ if (node->previous != NULL) {
+ node->box.x = node->previous->box.x;
+ node->box.y = node->previous->box.y +
+ tree_get_node_height(node->previous);
+ } else if (parent != NULL) {
+ node->box.x = parent->box.x + NODE_INSTEP;
+ node->box.y = parent->box.y +
+ parent->box.height;
+ for (child = parent->child; child != node;
+ child = child->next)
+ node->box.y += child->box.height;
+ } else {
+ node->box.x = tree->flags & TREE_NO_FURNITURE
+ ? -NODE_INSTEP + 4 : 0;
+ node->box.y = -20;
+ }
+
+ if (!node->expanded) {
+ node->data.box.x = node->box.x;
+ node->data.box.y = node->box.y;
+ continue;
+ }
+
+ if (node->folder) {
+ node->data.box.x = node->box.x;
+ node->data.box.y = node->box.y;
+ tree_recalculate_node_positions(tree, node->child);
+ } else {
+ y = node->box.y;
+ has_icon = false;
+ for (element = &node->data; element != NULL;
+ element = element->next)
+ if (element->type ==
+ NODE_ELEMENT_TEXT_PLUS_ICON) {
+ has_icon = true;
+ break;
+ }
+
+ for (element = &node->data; element != NULL;
+ element = element->next) {
+ element->box.x = node->box.x;
+ if (element->type !=
+ NODE_ELEMENT_TEXT_PLUS_ICON &&
+ has_icon)
+ element->box.x += NODE_INSTEP;
+ element->box.y = y;
+ y += element->box.height;
+ }
+ }
+
+ }
+}
+
+
+/**
+ * Recalculates the size of a node.
+ *
+ * \param tree the tree to which node belongs, may be NULL
+ * \param node the node to update
+ * \param recalculate_sizes whether the node elements have changed
+ */
+static void tree_recalculate_node_sizes(struct tree *tree, struct node *node,
+ bool recalculate_sizes)
+{
+ struct node_element *element;
+ int width, height;
+
+ assert(node != NULL);
+
+ width = node->box.width;
+ height = node->box.height;
+ node->box.width = 0;
+ node->box.height = 0;
+ if (node->expanded) {
+ for (element = &node->data; element != NULL;
+ element = element->next) {
+ if (recalculate_sizes)
+ tree_recalculate_node_element(tree, element);
+ node->box.width = (node->box.width > element->box.x +
+ element->box.width - node->box.x) ?
+ node->box.width :
+ element->box.width + element->box.x -
+ node->box.x;
+ node->box.height += element->box.height;
+ }
+ } else {
+ if (recalculate_sizes)
+ for (element = &node->data; element != NULL;
+ element = element->next)
+ tree_recalculate_node_element(tree, element);
+ else
+ tree_recalculate_node_element(tree, &node->data);
+ node->box.width = node->data.box.width;
+ node->box.height = node->data.box.height;
+ }
+
+ if (tree != NULL && height != node->box.height)
+ tree_recalculate_node_positions(tree, tree->root);
+}
+
+
/**
* Creates a folder node with the specified title, and optionally links it into
* the tree.
@@ -269,7 +452,7 @@
*/
struct node *tree_create_folder_node(struct tree *tree, struct node *parent,
const char *title, bool editable, bool retain_in_memory,
- bool deleted)
+ bool deleted)
{
struct node *node;
@@ -314,11 +497,11 @@
*/
struct node *tree_create_leaf_node(struct tree *tree, struct node *parent,
const char *title, bool editable, bool retain_in_memory,
- bool deleted)
+ bool deleted)
{
struct node *node;
- assert(title);
+ assert(title != NULL);
node = calloc(sizeof(struct node), 1);
if (node == NULL) {
@@ -326,6 +509,7 @@
warn_user("NoMemory", 0);
return NULL;
}
+
node->folder = false;
node->retain_in_memory = retain_in_memory;
node->deleted = deleted;
@@ -359,14 +543,131 @@
struct node_element *element;
element = calloc(sizeof(struct node_element), 1);
- if (element == NULL) return NULL;
+ if (element == NULL)
+ return NULL;
+
element->parent = parent;
element->flag = flag;
element->type = type;
element->editable = editable;
element->next = parent->data.next;
parent->data.next = element;
+
return element;
+}
+
+
+/**
+ * Inserts a node into the correct place according to the parent's sort function
+ *
+ * \param parent the node whose child node 'node' becomes
+ * \param node the node to be inserted
+ */
+static void tree_sort_insert(struct node *parent, struct node *node)
+{
+ struct node *after;
+
+ assert(node != NULL);
+ assert(parent != NULL);
+ assert(parent->sort != NULL);
+
+ after = parent->last_child;
+ while ((after != NULL) &&
+ (parent->sort(node, after) == -1))
+ after = after->previous;
+
+ if (after != NULL) {
+ if (after->next != NULL)
+ after->next->previous = node;
+ node->next = after->next;
+ node->previous = after;
+ after->next = node;
+ } else {
+ node->previous = NULL;
+ node->next = parent->child;
+ if (parent->child != NULL) {
+ parent->child->previous = node;
+ }
+ parent->child = node;
+ }
+
+ if (node->next == NULL)
+ parent->last_child = node;
+
+ node->parent = parent;
+}
+
+
+/**
+ * Recalculates the size of a tree.
+ *
+ * \param tree the tree to recalculate
+ */
+static void tree_recalculate_size(struct tree *tree)
+{
+ int width, height;
+
+ assert(tree != NULL);
+
+ width = tree->width;
+ height = tree->height;
+
+ tree->width = tree_get_node_width(tree->root);
+ tree->height = tree_get_node_height(tree->root);
+
+ if ((width != tree->width) || (height != tree->height))
+ tree->callbacks->resized(tree, tree->width, tree->height,
+ tree->client_data);
+}
+
+/**
+ * Recalculate the node data and redraw the relevant section of the tree.
+ *
+ * \param tree the tree to redraw, may be NULL
+ * \param node the node to update
+ * \param recalculate_sizes whether the elements have changed
+ * \param expansion the request is the result of a node expansion
+ */
+static void tree_handle_node_changed(struct tree *tree, struct node *node,
+ bool recalculate_sizes, bool expansion)
+{
+ int width, height, tree_height;
+
+ assert(node != NULL);
+
+ width = node->box.width;
+ height = node->box.height;
+ tree_height = tree->height;
+
+ if ((recalculate_sizes) || (expansion)) {
+ tree_recalculate_node_sizes(tree, node, true);
+ }
+
+ if (tree != NULL) {
+ if ((node->box.height != height) || (expansion)) {
+ tree_recalculate_node_positions(tree, tree->root);
+ tree_recalculate_size(tree);
+ tree_height = (tree_height > tree->height) ?
+ tree_height : tree->height;
+ if (tree->redraw) {
+ tree->callbacks->redraw_request(0, node->box.y,
+ tree->width,
+ tree_height - node->box.y,
+ tree->client_data);
+ }
+ } else {
+ width = (width > node->box.width) ?
+ width : node->box.width;
+ if (tree->redraw)
+ tree->callbacks->redraw_request(node->box.x,
+ node->box.y,
+ width, node->box.height,
+ tree->client_data);
+ if (recalculate_sizes) {
+ tree_recalculate_size(tree);
+ }
+ }
+ }
}
@@ -391,9 +692,9 @@
if ((link->folder == 0) || (before)) {
parent = node->parent = link->parent;
- if (parent->sort)
+ if (parent->sort) {
sort = true;
- else {
+ } else {
if (before) {
node->next = link;
node->previous = link->previous;
@@ -409,15 +710,15 @@
link->next->previous = node;
link->next = node;
if ((parent != NULL) &&
- (parent->last_child == link))
+ (parent->last_child == link))
parent->last_child = node;
}
}
} else {
parent = node->parent = link;
- if (parent->sort != NULL)
+ if (parent->sort != NULL) {
sort = true;
- else {
+ } else {
node->next = NULL;
if (link->child == NULL) {
link->child = link->last_child = node;
@@ -431,12 +732,144 @@
}
- if (sort)
+ if (sort) {
tree_sort_insert(parent, node);
+ }
tree_handle_node_changed(tree, link, false, true);
node->deleted = false;
+}
+
+
+/**
+ * Recalculate the node element and redraw the relevant section of the tree.
+ * The tree size is not updated.
+ *
+ * \param tree the tree to redraw, may be NULL
+ * \param element the node element to update
+ */
+static void tree_handle_node_element_changed(struct tree *tree,
+ struct node_element *element)
+{
+ int width, height;
+
+ assert(element != NULL);
+
+ width = element->box.width;
+ height = element->box.height;
+ tree_recalculate_node_element(tree, element);
+
+ if (element->box.height != height) {
+ tree_recalculate_node_sizes(tree, element->parent, false);
+ if ((tree != NULL) && (tree->redraw)) {
+ tree->callbacks->redraw_request(0, element->box.y,
+ tree->width + element->box.width -
+ width,
+ tree->height - element->box.y +
+ element->box.height - height,
+ tree->client_data);
+ }
+ } else {
+ if (element->box.width != width) {
+ tree_recalculate_node_sizes(tree, element->parent,
+ false);
+ }
+
+ if (tree != NULL) {
+ width = (width > element->box.width) ? width :
+ element->box.width;
+ if (tree->redraw) {
+ tree->callbacks->redraw_request(element->box.x,
+ element->box.y,
+ width,
+ element->box.height,
+ tree->client_data);
+ }
+ }
+ }
+}
+
+
+/**
+ * Stops editing a node_element
+ *
+ * \param tree The tree to stop editing for
+ * \param keep_changes If true the changes made to the text will be kept,
+ * if false they will be dropped
+ */
+static void tree_stop_edit(struct tree *tree, bool keep_changes)
+{
+ int text_len;
+ char *text = NULL;
+ struct node_element *element;
+ struct node_msg_data msg_data;
+ node_callback_resp response;
+
+ assert(tree != NULL);
+
+ if (tree->editing == NULL || tree->textarea == NULL)
+ return;
+
+ element = tree->editing;
+
+ if (keep_changes) {
+ text_len = textarea_get_text(tree->textarea, NULL, 0);
+ text = malloc(text_len * sizeof(char));
+ if (text == NULL) {
+ LOG(("malloc failed"));
+ warn_user("NoMemory", 0);
+ textarea_destroy(tree->textarea);
+ tree->textarea = NULL;
+ return;
+ }
+ textarea_get_text(tree->textarea, text, text_len);
+ }
+
+
+ if (keep_changes && element->parent->user_callback != NULL) {
+ msg_data.msg = NODE_ELEMENT_EDIT_FINISHING;
+ msg_data.flag = element->flag;
+ msg_data.node = element->parent;
+ msg_data.data.text = text;
+ response = element->parent->user_callback(
+ element->parent->callback_data,
+ &msg_data);
+
+ switch (response) {
+ case NODE_CALLBACK_REJECT:
+ free(text);
+ text = NULL;
+ break;
+ case NODE_CALLBACK_CONTINUE:
+ free(text);
+ text = NULL;
+ return;
+ case NODE_CALLBACK_HANDLED:
+ case NODE_CALLBACK_NOT_HANDLED:
+ text = msg_data.data.text;
+ break;
+ }
+ }
+
+ textarea_destroy(tree->textarea);
+ tree->textarea = NULL;
+ tree->editing = NULL;
+
+ if (text != NULL)
+ tree_update_node_element(tree, element, text, NULL);
+ else
+ tree_handle_node_element_changed(tree, element);
+
+
+ tree_recalculate_size(tree);
+ if (element->parent->user_callback != NULL) {
+ msg_data.msg = NODE_ELEMENT_EDIT_FINISHED;
+ msg_data.flag = element->flag;
+ msg_data.node = element->parent;
+ element->parent->user_callback(element->parent->callback_data,
+ &msg_data);
+ }
}
@@ -483,34 +916,6 @@
tree_handle_node_changed(tree, parent, false, true);
}
-/**
- * Deletes all nodes of a tree and the tree itself.
- *
- * \param tree the tree to be deleted
- */
-void tree_delete(struct tree *tree)
-{
- tree_set_redraw(tree, false);
- if (tree->root->child != NULL)
- tree_delete_node_internal(tree, tree->root->child, true);
-
- free((void *)tree->root->data.text);
- free(tree->root);
- free(tree);
-}
-
-
-/**
- * Gets the redraw property of the given tree.
- *
- * \param tree the tree for which to retrieve the property
- * \return the redraw property of the tree
- */
-bool tree_get_redraw(struct tree *tree)
-{
- return tree->redraw;
-}
-
/**
* Deletes a node from the tree.
@@ -519,26 +924,7 @@
* \param node the node to delete
* \param siblings whether to delete all siblings
*/
-void tree_delete_node(struct tree *tree, struct node *node, bool siblings)
-{
- int y = node->box.y;
- tree_delete_node_internal(tree, node, siblings);
- tree_recalculate_node_positions(tree, tree->root);
- if (tree->redraw)
- tree->callbacks->redraw_request(0, y, tree->width, tree->height,
- tree->client_data);
- tree_recalculate_size(tree);
-}
-
-
-/**
- * Deletes a node from the tree.
- *
- * \param tree the tree to delete from, may be NULL
- * \param node the node to delete
- * \param siblings whether to delete all siblings
- */
-void tree_delete_node_internal(struct tree *tree, struct node *node,
+static void tree_delete_node_internal(struct tree *tree, struct node *node,
bool siblings)
{
struct node *next, *child, *parent;
@@ -569,14 +955,14 @@
if (e->text != NULL) {
response = NODE_CALLBACK_NOT_HANDLED;
if (!e->editable &&
- node->user_callback != NULL) {
+ node->user_callback != NULL) {
msg_data.msg = NODE_DELETE_ELEMENT_TXT;
msg_data.flag = e->flag;
msg_data.node = node;
msg_data.data.text = (void *)e->text;
response = node->user_callback(
- node->callback_data,
- &msg_data);
+ node->callback_data,
+ &msg_data);
}
if (response != NODE_CALLBACK_HANDLED)
free((void *)e->text);
@@ -589,13 +975,13 @@
msg_data.flag = e->flag;
msg_data.node = node;
msg_data.data.bitmap =
- (void *)e->bitmap;
+ (void *)e->bitmap;
response = node->user_callback(
- node->callback_data,
- &msg_data);
+ node->callback_data,
+ &msg_data);
}
/* TODO the type of this field is platform
- dependent */
+ dependent */
if (response != NODE_CALLBACK_HANDLED)
free(e->bitmap);
e->bitmap = NULL;
@@ -610,8 +996,56 @@
if (siblings && next)
tree_delete_node_internal(tree, next, true);
if ((tree->flags & TREE_DELETE_EMPTY_DIRS) && parent != NULL &&
- parent->child == NULL && !parent->deleted)
+ parent->child == NULL && !parent->deleted)
tree_delete_node_internal(tree, parent, false);
+}
+
+
+/**
+ * Deletes all nodes of a tree and the tree itself.
+ *
+ * \param tree the tree to be deleted
+ */
+void tree_delete(struct tree *tree)
+{
+ tree_set_redraw(tree, false);
+ if (tree->root->child != NULL)
+ tree_delete_node_internal(tree, tree->root->child, true);
+
+ free((void *)tree->root->data.text);
+ free(tree->root);
+ free(tree);
+}
+
+
+/**
+ * Gets the redraw property of the given tree.
+ *
+ * \param tree the tree for which to retrieve the property
+ * \return the redraw property of the tree
+ */
+bool tree_get_redraw(struct tree *tree)
+{
+ return tree->redraw;
+}
+
+
+/**
+ * Deletes a node from the tree.
+ *
+ * \param tree the tree to delete from, may be NULL
+ * \param node the node to delete
+ * \param siblings whether to delete all siblings
+ */
+void tree_delete_node(struct tree *tree, struct node *node, bool siblings)
+{
+ int y = node->box.y;
+ tree_delete_node_internal(tree, node, siblings);
+ tree_recalculate_node_positions(tree, tree->root);
+ if (tree->redraw)
+ tree->callbacks->redraw_request(0, y, tree->width, tree->height,
+ tree->client_data);
+ tree_recalculate_size(tree);
}
@@ -620,63 +1054,13 @@
*
* \param tree The tree to which node belongs, may be NULL
* \param node The node for which the icon is set
- * \param icon the image to use
+ * \param icon the image to use
*/
void tree_set_node_icon(struct tree *tree, struct node *node,
hlcache_handle *icon)
{
node->data.type = NODE_ELEMENT_TEXT_PLUS_ICON;
tree_update_node_element(tree, &(node->data), NULL, icon);
-}
-
-/**
- * Update the text of a node element if it has changed.
- *
- * \param element The node element to update.
- * \param text The text to update the element with. The ownership of
- * this string is taken by this function and must not be
- * referred to after the function exits.
- */
-bool tree_update_element_text(struct tree *tree,
- struct node_element *element, char *text)
-{
- const char *node_text; /* existing node text */
-
- if (text == NULL)
- return false;
-
- if (element == NULL) {
- free(text);
- return false;
- }
-
- node_text = tree_node_element_get_text(element);
-
- if ((node_text == NULL) || (strcmp(node_text, text) != 0)) {
- tree_update_node_element(tree, element, text, NULL);
- } else {
- /* text does not need changing, free it */
- free(text);
- }
- return true;
-}
-
-
-/**
- * Updates [all siblings and descendants of] a node to an expansion state.
- *
- * \param tree the tree to update
- * \param node the node to set [all siblings and descendants of]
- * \param expanded the expansion state to set
- * \param folder whether to update folders, if this together with leaf
- * will be false only 'node' will be updated
- * \param leaf whether to update leaves (check also description for folder)
- */
-void tree_set_node_expanded(struct tree *tree, struct node *node, bool expanded,
- bool folder, bool leaf)
-{
- if (tree_set_node_expanded_internal(tree, node, expanded, folder, leaf))
- tree_handle_node_changed(tree, node, false, true);
}
@@ -688,7 +1072,7 @@
* \param node the node to set all siblings and descendants of
* \param expanded the expansion state to set
*/
-void tree_set_node_expanded_all(struct tree *tree, struct node *node,
+static void tree_set_node_expanded_all(struct tree *tree, struct node *node,
bool expanded)
{
for (; node != NULL; node = node->next) {
@@ -713,38 +1097,56 @@
* \param leaf whether to update leaves (check also description for folder)
* \return whether any changes were made
*/
-bool tree_set_node_expanded_internal(struct tree *tree, struct node *node,
- bool expanded, bool folder, bool leaf)
+static bool tree_set_node_expanded_internal(struct tree *tree,
+ struct node *node, bool expanded, bool folder, bool leaf)
{
bool redraw = false;
struct node *end = (folder == false && leaf == false) ?
- node->next : NULL;
+ node->next : NULL;
if (tree->editing != NULL && node == tree->editing->parent)
tree_stop_edit(tree, false);
for (; node != end; node = node->next) {
if ((node->expanded != expanded) && (node != tree->root) &&
- ((folder && (node->folder)) ||
- (leaf && (!node->folder)) ||
- (!folder && !leaf))) {
+ ((folder && (node->folder)) ||
+ (leaf && (!node->folder)) ||
+ (!folder && !leaf))) {
node->expanded = expanded;
if (node->child != NULL)
tree_set_node_expanded_all(tree,
- node->child, false);
+ node->child, false);
if ((node->data.next != NULL) &&
- (node->data.next->box.height == 0))
+ (node->data.next->box.height == 0))
tree_recalculate_node_sizes(tree, node, true);
else
tree_recalculate_node_sizes(tree, node, false);
redraw = true;
}
if ((folder || leaf) && (node->child != NULL) &&
- (node->expanded))
+ (node->expanded))
redraw |= tree_set_node_expanded_internal(tree,
- node->child, expanded, folder, leaf);
+ node->child, expanded, folder, leaf);
}
return redraw;
+}
+
+
+/**
+ * Updates [all siblings and descendants of] a node to an expansion state.
+ *
+ * \param tree the tree to update
+ * \param node the node to set [all siblings and descendants of]
+ * \param expanded the expansion state to set
+ * \param folder whether to update folders, if this together with leaf
+ * will be false only 'node' will be updated
+ * \param leaf whether to update leaves (check also description for folder)
+ */
+void tree_set_node_expanded(struct tree *tree, struct node *node, bool expanded,
+ bool folder, bool leaf)
+{
+ if (tree_set_node_expanded_internal(tree, node, expanded, folder, leaf))
+ tree_handle_node_changed(tree, node, false, true);
}
@@ -775,14 +1177,14 @@
node->selected = selected;
if (tree != NULL && tree->redraw)
tree->callbacks->redraw_request(node->box.x,
- node->box.y,
- node->box.width,
- node->data.box.height,
- tree->client_data);
+ node->box.y,
+ node->box.width,
+ node->data.box.height,
+ tree->client_data);
}
if (all && (node->child != NULL) && (node->expanded))
tree_set_node_selected(tree, node->child, all,
- selected);
+ selected);
}
}
@@ -821,6 +1223,7 @@
tree_recalculate_node_positions(tree, node->child);
}
+
/**
* Sets the delete callback for a node.
*
@@ -833,48 +1236,6 @@
{
node->user_callback = callback;
node->callback_data = data;
-}
-
-
-/**
- * Inserts a node into the correct place according to the parent's sort function
- *
- * \param parent the node whose child node 'node' becomes
- * \param node the node to be inserted
- */
-void tree_sort_insert(struct node *parent, struct node *node)
-{
- struct node *after;
-
- assert(node != NULL);
- assert(parent != NULL);
- assert(parent->sort != NULL);
-
- after = parent->last_child;
- while ((after != NULL) &&
- (parent->sort(node, after) == -1))
- after = after->previous;
-
- if (after != NULL) {
- if (after->next != NULL)
- after->next->previous = node;
- node->next = after->next;
- node->previous = after;
- after->next = node;
- } else {
- node->previous = NULL;
- node->next = parent->child;
- if (parent->child != NULL) {
- parent->child->previous = node;
- }
- parent->child = node;
- }
-
- if (node->next == NULL)
- parent->last_child = node;
-
- node->parent = parent;
-
}
@@ -907,7 +1268,7 @@
if (node->selected)
return true;
if ((node->child != NULL) && (node->expanded) &&
- (tree_node_has_selection(node->child)))
+ (tree_node_has_selection(node->child)))
return true;
}
return false;
@@ -935,6 +1296,39 @@
bool tree_node_is_folder(struct node *node)
{
return node->folder;
+}
+
+
+/**
+ * Update the text of a node element if it has changed.
+ *
+ * \param element The node element to update.
+ * \param text The text to update the element with. The ownership of
+ * this string is taken by this function and must not be
+ * referred to after the function exits.
+ */
+bool tree_update_element_text(struct tree *tree,
+ struct node_element *element, char *text)
+{
+ const char *node_text; /* existing node text */
+
+ if (text == NULL)
+ return false;
+
+ if (element == NULL) {
+ free(text);
+ return false;
+ }
+
+ node_text = tree_node_element_get_text(element);
+
+ if ((node_text == NULL) || (strcmp(node_text, text) != 0)) {
+ tree_update_node_element(tree, element, text, NULL);
+ } else {
+ /* text does not need changing, free it */
+ free(text);
+ }
+ return true;
}
@@ -958,19 +1352,19 @@
tree_stop_edit(tree, false);
if (text != NULL && (element->type == NODE_ELEMENT_TEXT ||
- element->type == NODE_ELEMENT_TEXT_PLUS_ICON)) {
+ element->type == NODE_ELEMENT_TEXT_PLUS_ICON)) {
if (element->text != NULL) {
response = NODE_CALLBACK_NOT_HANDLED;
if (!element->editable &&
- element->parent->user_callback !=
- NULL) {
+ element->parent->user_callback !=
+ NULL) {
msg_data.msg = NODE_DELETE_ELEMENT_TXT;
msg_data.flag = element->flag;
msg_data.node = element->parent;
msg_data.data.text = (void *)element->text;
response = element->parent->user_callback(
- element->parent->callback_data,
- &msg_data);
+ element->parent->callback_data,
+ &msg_data);
}
if (response != NODE_CALLBACK_HANDLED)
free((void *)element->text);
@@ -979,7 +1373,7 @@
}
if (bitmap != NULL && (element->type == NODE_ELEMENT_BITMAP ||
- element->type == NODE_ELEMENT_TEXT_PLUS_ICON)) {
+ element->type == NODE_ELEMENT_TEXT_PLUS_ICON)) {
if (element->bitmap != NULL) {
response = NODE_CALLBACK_NOT_HANDLED;
if (element->parent->user_callback != NULL) {
@@ -988,8 +1382,8 @@
msg_data.node = element->parent;
msg_data.data.bitmap = (void *)element->bitmap;
response = element->parent->user_callback(
- element->parent->callback_data,
- &msg_data);
+ element->parent->callback_data,
+ &msg_data);
}
if (response != NODE_CALLBACK_HANDLED)
free(element->bitmap);
@@ -1057,6 +1451,223 @@
struct node *tree_node_get_next(struct node *node)
{
return node->next;
+}
+
+
+/**
+ * Draws an elements expansion icon
+ *
+ * \param tree the tree to draw the expansion for
+ * \param element the element to draw the expansion for
+ * \param tree_x X coordinate of the tree
+ * \param tree_y Y coordinate of the tree
+ */
+static void tree_draw_node_expansion(struct tree *tree, struct node *node,
+ int tree_x, int tree_y)
+{
+ int x, y;
+
+ assert(tree != NULL);
+ assert(node != NULL);
+
+ if ((node->child != NULL) || (node->data.next != NULL)) {
+ x = tree_x + node->box.x - (NODE_INSTEP / 2) - 4;
+ y = tree_y + node->box.y - (TREE_TEXT_HEIGHT / 2) + 16;
+ plot.rectangle(x, y, x + 9, y + 9, plot_style_fill_white);
+ plot.rectangle(x , y, x + 8, y + 8,
+ plot_style_stroke_darkwbasec);
+ plot.line(x + 2, y + 4, x + 7, y + 4,
+ plot_style_stroke_darkwbasec);
+ if (!node->expanded)
+ plot.line(x + 4, y + 2, x + 4, y + 7,
+ plot_style_stroke_darkwbasec);
+
+ }
+
+}
+
+
+/**
+ * Draws an element, including any expansion icons
+ *
+ * \param tree the tree to draw an element for
+ * \param element the element to draw
+ * \param tree_x X coordinate of the tree
+ * \param tree_y Y coordinate of the tree
+ */
+static void tree_draw_node_element(struct tree *tree,
+ struct node_element *element, int tree_x, int tree_y)
+{
+
+ struct bitmap *bitmap = NULL;
+ int x, y, width;
+ bool selected = false;
+ hlcache_handle *icon;
+ plot_font_style_t *fstyle;
+
+ assert(tree != NULL);
+ assert(element != NULL);
+ assert(element->parent != NULL);
+
+ x = tree_x + element->box.x;
+ y = tree_y + element->box.y;
+ width = element->box.width;
+ if (&element->parent->data == element)
+ if (element->parent->selected)
+ selected = true;
+
+ switch (element->type) {
+ case NODE_ELEMENT_TEXT_PLUS_ICON:
+ icon = element->bitmap;
+ if (icon != NULL &&
+ (content_get_status(icon) ==
+ CONTENT_STATUS_READY ||
+ content_get_status(icon) ==
+ CONTENT_STATUS_DONE)) {
+ content_redraw(icon , x, y + 3,
+ TREE_ICON_SIZE, TREE_ICON_SIZE,
+ x, y, x + TREE_ICON_SIZE,
+ y + TREE_ICON_SIZE, 1, 0);
+ }
+
+ x += NODE_INSTEP;
+ width -= NODE_INSTEP;
+
+ /* fall through */
+ case NODE_ELEMENT_TEXT:
+ if (element->text == NULL)
+ break;
+
+ if (element == tree->editing)
+ return;
+
+ if (selected) {
+ fstyle = &plot_fstyle_selected;
+ plot.rectangle(x, y, x + width,
+ y + element->box.height,
+ plot_style_fill_black);
+ } else {
+ fstyle = &plot_fstyle;
+ plot.rectangle(x, y, x + width,
+ y + element->box.height,
+ plot_style_fill_white);
+ }
+
+ plot.text(x + 4, y + TREE_TEXT_HEIGHT * 0.75,
+ element->text, strlen(element->text),
+ fstyle);
+ break;
+ case NODE_ELEMENT_BITMAP:
+ bitmap = element->bitmap;
+ if (bitmap == NULL)
+ break;
+ plot.bitmap(x, y, element->box.width - 1,
+ element->box.height - 2,
+ bitmap, 0xFFFFFF, BITMAPF_NONE);
+ if (!(tree->flags & TREE_NO_FURNITURE))
+ plot.rectangle(x, y, x + element->box.width - 1,
+ y + element->box.height - 3,
+ plot_style_stroke_darkwbasec);
+
+ break;
+ }
+
+}
+
+
+/**
+ * Redraws a node.
+ *
+ * \param tree the tree to draw
+ * \param node the node to draw children and siblings of
+ * \param tree_x X coordinate of the tree
+ * \param tree_y Y coordinate of the tree
+ * \param clip_x the minimum x of the clipping rectangle
+ * \param clip_y the minimum y of the clipping rectangle
+ * \param clip_width the width of the clipping rectangle
+ * \param clip_height the height of the clipping rectangle
+ */
+static void tree_draw_node(struct tree *tree, struct node *node,
+ int tree_x, int tree_y,
+ int clip_x, int clip_y,
+ int clip_width, int clip_height)
+{
+ struct node_element *element;
+ struct node *parent;
+ int x_max, y_max;
+ int x0, y0, x1, y1;
+
+ assert(tree != NULL);
+ assert(node != NULL);
+
+
+ x_max = clip_x + clip_width + NODE_INSTEP;
+ y_max = clip_y + clip_height;
+
+ if ((node->parent->next != NULL) &&
+ (node->parent->next->box.y < clip_y))
+ return;
+
+ for (; node != NULL; node = node->next) {
+ if (node->box.y > y_max) return;
+ if ((node->next != NULL) &&
+ (!(tree->flags & TREE_NO_FURNITURE))) {
+ x0 = x1 = tree_x + node->box.x - (NODE_INSTEP / 2);
+ y0 = tree_y + node->box.y + (20 / 2);
+ y1 = y0 + node->next->box.y - node->box.y;
+ plot.line(x0, y0, x1, y1, plot_style_stroke_darkwbasec);
+ }
+ if ((node->box.x < x_max) && (node->box.y < y_max) &&
+ (node->box.x + node->box.width
+ + NODE_INSTEP >= clip_x) &&
+ (node->box.y + node->box.height >= clip_y)) {
+ if (!(tree->flags & TREE_NO_FURNITURE)) {
+ if ((node->expanded) && (node->child != NULL)) {
+ x0 = x1 = tree_x + node->box.x +
+ (NODE_INSTEP / 2);
+ y0 = tree_y + node->data.box.y
+ + node->data.box.height;
+ y1 = y0 + (20 / 2);
+ plot.line(x0, y0, x1, y1,
+ plot_style_stroke_darkwbasec);
+
+ }
+ parent = node->parent;
+ if ((parent != NULL) &&
+ (parent != tree->root) &&
+ (parent->child == node)) {
+ x0 = x1 = tree_x + parent->box.x +
+ (NODE_INSTEP / 2);
+ y0 = tree_y + parent->data.box.y +
+ parent->data.box.height;
+ y1 = y0 + (20 / 2);
+ plot.line(x0, y0, x1, y1,
+ plot_style_stroke_darkwbasec);
+ }
+ x0 = tree_x + node->box.x - (NODE_INSTEP / 2);
+ x1 = x0 + (NODE_INSTEP / 2) - 2;
+ y0 = y1 = tree_y + node->data.box.y +
+ node->data.box.height -
+ (20 / 2);
+ plot.line(x0, y0, x1, y1,
+ plot_style_stroke_darkwbasec);
+ tree_draw_node_expansion(tree, node,
+ tree_x, tree_y);
+ }
+ if (node->expanded)
+ for (element = &node->data; element != NULL;
+ element = element->next)
+ tree_draw_node_element(tree, element,
+ tree_x, tree_y);
+ else
+ tree_draw_node_element(tree, &node->data,
+ tree_x, tree_y);
+ }
+ if ((node->child != NULL) && (node->expanded))
+ tree_draw_node(tree, node->child, tree_x, tree_y,
+ clip_x, clip_y,
+ clip_width, clip_height);
+ }
}
@@ -1074,7 +1685,7 @@
* \param clip_height the height of the clipping rectangle
*/
void tree_draw(struct tree *tree, int x, int y,
- int clip_x, int clip_y, int clip_width, int clip_height)
+ int clip_x, int clip_y, int clip_width, int clip_height)
{
int absolute_x, absolute_y;
assert(tree != NULL);
@@ -1086,12 +1697,12 @@
absolute_x = x + clip_x;
absolute_y = y + clip_y;
plot.rectangle(absolute_x, absolute_y,
- absolute_x + clip_width, absolute_y + clip_height,
- plot_style_fill_white);
+ absolute_x + clip_width, absolute_y + clip_height,
+ plot_style_fill_white);
plot.clip(absolute_x, absolute_y,
- absolute_x + clip_width, absolute_y + clip_height);
+ absolute_x + clip_width, absolute_y + clip_height);
tree_draw_node(tree, tree->root->child, x, y, clip_x,
- clip_y, clip_width, clip_height);
+ clip_y, clip_width, clip_height);
if (tree->editing != NULL) {
x = x + tree->editing->box.x;
y = y + tree->editing->box.y;
@@ -1105,222 +1716,6 @@
/**
- * Redraws a node.
- *
- * \param tree the tree to draw
- * \param node the node to draw children and siblings of
- * \param tree_x X coordinate of the tree
- * \param tree_y Y coordinate of the tree
- * \param clip_x the minimum x of the clipping rectangle
- * \param clip_y the minimum y of the clipping rectangle
- * \param clip_width the width of the clipping rectangle
- * \param clip_height the height of the clipping rectangle
- */
-void tree_draw_node(struct tree *tree, struct node *node,
- int tree_x, int tree_y,
- int clip_x, int clip_y, int clip_width, int clip_height) {
-
- struct node_element *element;
- struct node *parent;
- int x_max, y_max;
- int x0, y0, x1, y1;
-
- assert(tree != NULL);
- assert(node != NULL);
-
-
- x_max = clip_x + clip_width + NODE_INSTEP;
- y_max = clip_y + clip_height;
-
- if ((node->parent->next != NULL) &&
- (node->parent->next->box.y < clip_y))
- return;
-
- for (; node != NULL; node = node->next) {
- if (node->box.y > y_max) return;
- if ((node->next != NULL) &&
- (!(tree->flags & TREE_NO_FURNITURE))) {
- x0 = x1 = tree_x + node->box.x - (NODE_INSTEP / 2);
- y0 = tree_y + node->box.y + (20 / 2);
- y1 = y0 + node->next->box.y - node->box.y;
- plot.line(x0, y0, x1, y1, plot_style_stroke_darkwbasec);
- }
- if ((node->box.x < x_max) && (node->box.y < y_max) &&
- (node->box.x + node->box.width
- + NODE_INSTEP >= clip_x) &&
- (node->box.y + node->box.height >= clip_y)) {
- if (!(tree->flags & TREE_NO_FURNITURE)) {
- if ((node->expanded) && (node->child != NULL)) {
- x0 = x1 = tree_x + node->box.x +
- (NODE_INSTEP / 2);
- y0 = tree_y + node->data.box.y
- + node->data.box.height;
- y1 = y0 + (20 / 2);
- plot.line(x0, y0, x1, y1,
- plot_style_stroke_darkwbasec);
-
- }
- parent = node->parent;
- if ((parent != NULL) &&
- (parent != tree->root) &&
- (parent->child == node)) {
- x0 = x1 = tree_x + parent->box.x +
- (NODE_INSTEP / 2);
- y0 = tree_y + parent->data.box.y +
- parent->data.box.height;
- y1 = y0 + (20 / 2);
- plot.line(x0, y0, x1, y1,
- plot_style_stroke_darkwbasec);
- }
- x0 = tree_x + node->box.x - (NODE_INSTEP / 2);
- x1 = x0 + (NODE_INSTEP / 2) - 2;
- y0 = y1 = tree_y + node->data.box.y +
- node->data.box.height -
- (20 / 2);
- plot.line(x0, y0, x1, y1,
- plot_style_stroke_darkwbasec);
- tree_draw_node_expansion(tree, node,
- tree_x, tree_y);
- }
- if (node->expanded)
- for (element = &node->data; element != NULL;
- element = element->next)
- tree_draw_node_element(tree, element,
- tree_x, tree_y);
- else
- tree_draw_node_element(tree, &node->data,
- tree_x, tree_y);
- }
- if ((node->child != NULL) && (node->expanded))
- tree_draw_node(tree, node->child, tree_x, tree_y,
- clip_x, clip_y,
- clip_width, clip_height);
- }
-}
-
-
-/**
- * Draws an elements expansion icon
- *
- * \param tree the tree to draw the expansion for
- * \param element the element to draw the expansion for
- * \param tree_x X coordinate of the tree
- * \param tree_y Y coordinate of the tree
- */
-void tree_draw_node_expansion(struct tree *tree, struct node *node,
- int tree_x, int tree_y)
-{
- int x, y;
-
- assert(tree != NULL);
- assert(node != NULL);
-
- if ((node->child != NULL) || (node->data.next != NULL)) {
- x = tree_x + node->box.x - (NODE_INSTEP / 2) - 4;
- y = tree_y + node->box.y - (TREE_TEXT_HEIGHT / 2) + 16;
- plot.rectangle(x, y, x + 9, y + 9, plot_style_fill_white);
- plot.rectangle(x , y, x + 8, y + 8,
- plot_style_stroke_darkwbasec);
- plot.line(x + 2, y + 4, x + 7, y + 4,
- plot_style_stroke_darkwbasec);
- if (!node->expanded)
- plot.line(x + 4, y + 2, x + 4, y + 7,
- plot_style_stroke_darkwbasec);
-
- }
-
-}
-
-
-/**
- * Draws an element, including any expansion icons
- *
- * \param tree the tree to draw an element for
- * \param element the element to draw
- * \param tree_x X coordinate of the tree
- * \param tree_y Y coordinate of the tree
- */
-void tree_draw_node_element(struct tree *tree, struct node_element *element,
- int tree_x, int tree_y)
-{
-
- struct bitmap *bitmap = NULL;
- int x, y, width;
- bool selected = false;
- hlcache_handle *icon;
- plot_font_style_t *fstyle;
-
- assert(tree != NULL);
- assert(element != NULL);
- assert(element->parent != NULL);
-
- x = tree_x + element->box.x;
- y = tree_y + element->box.y;
- width = element->box.width;
- if (&element->parent->data == element)
- if (element->parent->selected)
- selected = true;
-
- switch (element->type) {
- case NODE_ELEMENT_TEXT_PLUS_ICON:
- icon = element->bitmap;
- if (icon != NULL &&
- (content_get_status(icon) ==
- CONTENT_STATUS_READY ||
- content_get_status(icon) ==
- CONTENT_STATUS_DONE)) {
- content_redraw(icon , x, y + 3,
- TREE_ICON_SIZE, TREE_ICON_SIZE,
- x, y, x + TREE_ICON_SIZE,
- y + TREE_ICON_SIZE, 1, 0);
- }
-
- x += NODE_INSTEP;
- width -= NODE_INSTEP;
-
- /* fall through */
- case NODE_ELEMENT_TEXT:
- if (element->text == NULL)
- break;
-
- if (element == tree->editing)
- return;
-
- if (selected) {
- fstyle = &plot_fstyle_selected;
- plot.rectangle(x, y, x + width,
- y + element->box.height,
- plot_style_fill_black);
- } else {
- fstyle = &plot_fstyle;
- plot.rectangle(x, y, x + width,
- y + element->box.height,
- plot_style_fill_white);
- }
-
- plot.text(x + 4, y + TREE_TEXT_HEIGHT * 0.75,
- element->text, strlen(element->text),
- fstyle);
- break;
- case NODE_ELEMENT_BITMAP:
- bitmap = element->bitmap;
- if (bitmap == NULL)
- break;
- plot.bitmap(x, y, element->box.width - 1,
- element->box.height - 2,
- bitmap, 0xFFFFFF, BITMAPF_NONE);
- if (!(tree->flags & TREE_NO_FURNITURE))
- plot.rectangle(x, y, x + element->box.width - 1,
- y + element->box.height - 3,
- plot_style_stroke_darkwbasec);
-
- break;
- }
-
-}
-
-
-/**
* Finds a node element from a node with a specific user_type
*
* \param node the node to examine
@@ -1407,6 +1802,90 @@
/**
+ * Finds a node element at a specific location.
+ *
+ * \param node the root node to check from
+ * \param x the x co-ordinate
+ * \param y the y co-ordinate
+ * \param furniture whether the returned area was in an elements furniture
+ * \return the node at the specified position, or NULL for none
+ */
+static struct node_element *tree_get_node_element_at(struct node *node,
+ int x, int y, bool *furniture)
+{
+ struct node_element *element;
+ int x0, x1, y0, y1;
+
+ *furniture = false;
+ for (; node != NULL; node = node->next) {
+ if (node->box.y > y) return NULL;
+ if ((node->box.x - NODE_INSTEP < x) && (node->box.y < y) &&
+ (node->box.x + node->box.width >= x) &&
+ (node->box.y + node->box.height >= y)) {
+ if (node->expanded) {
+ for (element = &node->data; element != NULL;
+ element = element->next) {
+ x0 = element->box.x;
+ y0 = element->box.y;
+ x1 = element->box.x +
+ element->box.width;
+ y1 = element->box.y +
+ element->box.height;
+ if ((x0 < x) && (y0 < y) && (x1 >= x)
+ && (y1 >= y))
+ return element;
+ }
+ } else {
+ x0 = node->data.box.x;
+ y0 = node->data.box.y;
+ x1 = node->data.box.x + node->data.box.width;
+ y1 = node->data.box.y + node->data.box.height;
+ if ((x0 < x) && (y0 < y) && (x1 >= x) &&
+ (y1>= y))
+ return &node->data;
+ }
+ if (((node->child != NULL) ||
+ (node->data.next != NULL)) &&
+ (node->data.box.x - NODE_INSTEP + 4 < x)
+ && (node->data.box.y + 4 < y) &&
+ (node->data.box.x > x) &&
+ (node->data.box.y + 20 > y)) {
+ *furniture = true;
+ return &node->data;
+ }
+ }
+
+ element = tree_get_node_element_at(node->child, x, y,
+ furniture);
+ if ((node->child != NULL) && (node->expanded) &&
+ (element != NULL))
+ return element;
+ }
+ return NULL;
+}
+
+
+/**
+ * Finds a node at a specific location.
+ *
+ * \param root the root node to check from
+ * \param x the x co-ordinate
+ * \param y the y co-ordinate
+ * \param furniture whether the returned area was in an elements furniture
+ * \return the node at the specified position, or NULL for none
+ */
+static struct node *tree_get_node_at(struct node *root, int x, int y,
+ bool *furniture)
+{
+ struct node_element *result;
+
+ if ((result = tree_get_node_element_at(root, x, y, furniture)))
+ return result->parent;
+ return NULL;
+}
+
+
+/**
* Gets link characteristics to insert a node at a specified position.
*
* \param tree the tree to find link information for
@@ -1433,7 +1912,7 @@
if (y < (node->box.y + (node->box.height / 2))) {
*before = true;
} else if ((node->folder) && (node->expanded) &&
- (node->child != NULL)) {
+ (node->child != NULL)) {
node = node->child;
*before = true;
}
@@ -1445,21 +1924,9 @@
* Launches all the selected nodes of the tree
*
* \param tree the tree for which all nodes will be launched
- */
-void tree_launch_selected(struct tree *tree)
-{
- if (tree->root->child != NULL)
- tree_launch_selected_internal(tree, tree->root->child);
-}
-
-
-/**
- * Launches all the selected nodes of the tree
- *
- * \param tree the tree for which all nodes will be launched
* \param node the node which will be checked together with its children
*/
-void tree_launch_selected_internal(struct tree *tree, struct node *node)
+static void tree_launch_selected_internal(struct tree *tree, struct node *node)
{
struct node_msg_data msg_data;
@@ -1473,6 +1940,18 @@
if (node->child != NULL)
tree_launch_selected_internal(tree, node->child);
}
+}
+
+
+/**
+ * Launches all the selected nodes of the tree
+ *
+ * \param tree the tree for which all nodes will be launched
+ */
+void tree_launch_selected(struct tree *tree)
+{
+ if (tree->root->child != NULL)
+ tree_launch_selected_internal(tree, tree->root->child);
}
@@ -1514,11 +1993,11 @@
y1 = tree->editing->box.y + tree->editing->box.height;
if (tree->textarea_drag_start &&
- (mouse & (BROWSER_MOUSE_HOLDING_1 |
- BROWSER_MOUSE_HOLDING_2))) {
+ (mouse & (BROWSER_MOUSE_HOLDING_1 |
+ BROWSER_MOUSE_HOLDING_2))) {
textarea_mouse_action(tree->textarea, mouse,
- x - x0, y - y0);
+ x - x0, y - y0);
return true;
}
@@ -1527,12 +2006,12 @@
if ((x >= x0) && (x < x1) && (y >= y0) && (y < y1)) {
if (mouse & (BROWSER_MOUSE_DRAG_1 |
- BROWSER_MOUSE_DRAG_2))
+ BROWSER_MOUSE_DRAG_2))
tree->textarea_drag_start = true;
else
tree->textarea_drag_start = false;
textarea_mouse_action(tree->textarea, mouse,
- x - x0, y - y0);
+ x - x0, y - y0);
return true;
}
@@ -1542,7 +2021,7 @@
/* we are not interested in the drag path or in mouse presses, return */
if (mouse & (BROWSER_MOUSE_HOLDING_1 | BROWSER_MOUSE_HOLDING_2 |
- BROWSER_MOUSE_PRESS_1 | BROWSER_MOUSE_PRESS_2))
+ BROWSER_MOUSE_PRESS_1 | BROWSER_MOUSE_PRESS_2))
return true;
/* cancel edit */
@@ -1555,12 +2034,12 @@
if (element == NULL) {
if (tree->flags & TREE_SINGLE_SELECT) {
tree_set_node_selected(tree, tree->root->child, true,
- false);
+ false);
return true;
}
if (mouse & (BROWSER_MOUSE_CLICK_1 | BROWSER_MOUSE_DRAG_1))
tree_set_node_selected(tree, tree->root->child, true,
- false);
+ false);
if (mouse & (BROWSER_MOUSE_DRAG_1 | BROWSER_MOUSE_DRAG_2)) {
/** @todo the tree window has to scroll the tree when
@@ -1577,24 +2056,24 @@
/* click on furniture or double click on folder toggles node expansion
*/
if (((furniture) && (mouse & (BROWSER_MOUSE_CLICK_1 |
- BROWSER_MOUSE_CLICK_2))) ||
- ((!furniture) && (node->child != NULL) &&
- (mouse & BROWSER_MOUSE_DOUBLE_CLICK))) {
+ BROWSER_MOUSE_CLICK_2))) ||
+ ((!furniture) && (node->child != NULL) &&
+ (mouse & BROWSER_MOUSE_DOUBLE_CLICK))) {
/* clear any selection */
tree_set_node_selected(tree, tree->root->child, true, false);
/* expand / contract node and redraw */
tree_set_node_expanded(tree, node, !node->expanded,
- false, false);
+ false, false);
/* find the last child node if expanded */
last = node;
if ((last->child != NULL) && (last->expanded)) {
last = last->child;
while ((last->next != NULL) ||
- ((last->child != NULL) &&
- (last->expanded))) {
+ ((last->child != NULL) &&
+ (last->expanded))) {
if (last->next != NULL)
last = last->next;
else
@@ -1606,11 +2085,11 @@
if (last->expanded)
for (; element->next != NULL; element = element->next);
tree->callbacks->scroll_visible(element->box.y,
- element->box.height,
- tree->client_data);
+ element->box.height,
+ tree->client_data);
tree->callbacks->scroll_visible(node->data.box.y,
- node->data.box.height,
- tree->client_data);
+ node->data.box.height,
+ tree->client_data);
return true;
}
@@ -1620,12 +2099,12 @@
/* single/double ctrl+click or alt+click starts editing */
if ((element->editable) && (!tree->editing) &&
- ((element->type == NODE_ELEMENT_TEXT) ||
- (element->type == NODE_ELEMENT_TEXT_PLUS_ICON)) &&
- (mouse & (BROWSER_MOUSE_CLICK_1 |
- BROWSER_MOUSE_DOUBLE_CLICK)) &&
- (mouse & BROWSER_MOUSE_MOD_2 ||
- mouse & BROWSER_MOUSE_MOD_3)) {
+ ((element->type == NODE_ELEMENT_TEXT) ||
+ (element->type == NODE_ELEMENT_TEXT_PLUS_ICON)) &&
+ (mouse & (BROWSER_MOUSE_CLICK_1 |
+ BROWSER_MOUSE_DOUBLE_CLICK)) &&
+ (mouse & BROWSER_MOUSE_MOD_2 ||
+ mouse & BROWSER_MOUSE_MOD_3)) {
tree_set_node_selected(tree, tree->root->child, true, false);
tree_start_edit(tree, element);
return true;
@@ -1639,7 +2118,7 @@
msg_data.flag = TREE_ELEMENT_TITLE;
msg_data.node = node;
if (node->user_callback(node->callback_data, &msg_data) !=
- NODE_CALLBACK_HANDLED)
+ NODE_CALLBACK_HANDLED)
return false;
return true;
@@ -1647,12 +2126,12 @@
/* single click (select) cancels current selection and selects item */
if (mouse & BROWSER_MOUSE_CLICK_1 || (mouse & BROWSER_MOUSE_CLICK_2 &&
- tree->flags & TREE_SINGLE_SELECT)) {
+ tree->flags & TREE_SINGLE_SELECT)) {
if (tree->flags & TREE_NO_SELECT)
return true;
if (!node->selected) {
tree_set_node_selected(tree, tree->root->child, true,
- false);
+ false);
node->selected = true;
tree_handle_node_element_changed(tree, &node->data);
}
@@ -1670,13 +2149,13 @@
/* drag starts a drag operation */
if ((!tree->editing) && (mouse & (BROWSER_MOUSE_DRAG_1 |
- BROWSER_MOUSE_DRAG_2))) {
+ BROWSER_MOUSE_DRAG_2))) {
if (tree->flags & TREE_NO_DRAGS)
return true;
if (!node->selected) {
tree_set_node_selected(tree, tree->root->child, true,
- false);
+ false);
node->selected = true;
tree_handle_node_element_changed(tree, &node->data);
}
@@ -1688,457 +2167,6 @@
return false;
-}
-
-
-/**
- * Handle the end of a drag operation
- *
- * \param tree the tree on which the drag was performed
- * \param mouse mouse state during drag end
- * \param x0 x coordinate of drag start
- * \param y0 y coordinate of drag start
- * \param x1 x coordinate of drag end
- * \param y1 y coordinate of drag end
- */
-void tree_drag_end(struct tree *tree, browser_mouse_state mouse, int x0, int y0,
- int x1, int y1)
-{
-
- bool before;
- struct node *node;
- int x, y;
-
- if (tree->textarea_drag_start) {
- x = tree->editing->box.x;
- y = tree->editing->box.y;
- if (tree->editing->type == NODE_ELEMENT_TEXT_PLUS_ICON)
- x += NODE_INSTEP;
- textarea_drag_end(tree->textarea, mouse, x1 - x, y1 - y);
- }
-
- tree->textarea_drag_start = false;
-
- switch (tree->drag) {
- case TREE_NO_DRAG:
- break;
- case TREE_SELECT_DRAG:
- tree_handle_selection_area(tree, y0, y1 - y0,
- (mouse | BROWSER_MOUSE_HOLDING_2));
- break;
- case TREE_MOVE_DRAG:
- if (!(tree->flags & TREE_MOVABLE))
- return;
- node = tree_get_link_details(tree, x1, y1, &before);
- tree_move_selected_nodes(tree, node, before);
- break;
- }
-
- tree->drag = TREE_NO_DRAG;
-}
-
-
-/**
- * Key press handling for a tree.
- *
- * \param tree The tree which got the keypress
- * \param key The ucs4 character codepoint
- * \return true if the keypress is dealt with, false otherwise.
- */
-bool tree_keypress(struct tree *tree, uint32_t key)
-{
-
- if (tree->editing != NULL)
- switch (key) {
- case KEY_ESCAPE:
- tree_stop_edit(tree, false);
- return true;
- case KEY_NL:
- tree_stop_edit(tree, true);
- return true;
- default:
- return textarea_keypress(tree->textarea, key);
- }
-
- return false;
-}
-
-
-/**
- * Alphabetical comparison function for nodes
- *
- * \param n1 first node to compare
- * \param n2 first node to compare
- * \return 0 if equal, greater then zero if n1 > n2,
- * less then zero if n2 < n1
- */
-int tree_alphabetical_sort(struct node *n1, struct node *n2)
-{
- return strcmp(n1->data.text, n2->data.text);
-}
-
-
-/**
- * Recalculate the node data and redraw the relevant section of the tree.
- *
- * \param tree the tree to redraw, may be NULL
- * \param node the node to update
- * \param recalculate_sizes whether the elements have changed
- * \param expansion the request is the result of a node expansion
- */
-void tree_handle_node_changed(struct tree *tree, struct node *node,
- bool recalculate_sizes, bool expansion)
-{
- int width, height, tree_height;
-
- assert(node != NULL);
-
- width = node->box.width;
- height = node->box.height;
- tree_height = tree->height;
- if ((recalculate_sizes) || (expansion))
- tree_recalculate_node_sizes(tree, node, true);
- if (tree != NULL) {
- if ((node->box.height != height) || (expansion)) {
- tree_recalculate_node_positions(tree, tree->root);
- tree_recalculate_size(tree);
- tree_height = (tree_height > tree->height) ?
- tree_height : tree->height;
- if (tree->redraw)
- tree->callbacks->redraw_request(0, node->box.y,
- tree->width,
- tree_height - node->box.y,
- tree->client_data);
- } else {
- width = (width > node->box.width) ?
- width : node->box.width;
- if (tree->redraw)
- tree->callbacks->redraw_request(node->box.x,
- node->box.y,
- width, node->box.height,
- tree->client_data);
- if (recalculate_sizes)
- tree_recalculate_size(tree);
- }
- }
-}
-
-
-/**
- * Recalculate the node element and redraw the relevant section of the tree.
- * The tree size is not updated.
- *
- * \param tree the tree to redraw, may be NULL
- * \param element the node element to update
- */
-void tree_handle_node_element_changed(struct tree *tree,
- struct node_element *element)
-{
- int width, height;
-
- assert(element != NULL);
-
- width = element->box.width;
- height = element->box.height;
- tree_recalculate_node_element(tree, element);
-
- if (element->box.height != height) {
- tree_recalculate_node_sizes(tree, element->parent, false);
- if (tree != NULL && tree->redraw)
- tree->callbacks->redraw_request(0, element->box.y,
- tree->width + element->box.width -
- width,
- tree->height - element->box.y +
- element->box.height - height,
- tree->client_data);
- } else {
- if (element->box.width != width)
- tree_recalculate_node_sizes(tree, element->parent,
- false);
- if (tree != NULL) {
- width = (width > element->box.width) ? width :
- element->box.width;
- if (tree->redraw)
- tree->callbacks->redraw_request(element->box.x,
- element->box.y,
- width, element->box.height,
- tree->client_data);
- }
- }
-}
-
-
-/**
- * Recalculates the dimensions of a node element.
- *
- * \param tree the tree to which the element belongs, may be NULL
- * \param element the element to recalculate
- */
-void tree_recalculate_node_element(struct tree *tree,
- struct node_element *element)
-{
- struct bitmap *bitmap = NULL;
- int width, height;
-
- assert(element != NULL);
-
- switch (element->type) {
- case NODE_ELEMENT_TEXT_PLUS_ICON:
- case NODE_ELEMENT_TEXT:
- if(element->text == NULL)
- break;
- if (tree != NULL && element == tree->editing)
- textarea_get_dimensions(tree->textarea,
- &element->box.width, NULL);
- else
- nsfont.font_width(&plot_fstyle,
- element->text,
- strlen(element->text),
- &element->box.width);
- element->box.width += 8;
- element->box.height = TREE_TEXT_HEIGHT;
- if (element->type == NODE_ELEMENT_TEXT_PLUS_ICON)
- element->box.width += NODE_INSTEP;
- break;
- case NODE_ELEMENT_BITMAP:
- bitmap = element->bitmap;
- if (bitmap != NULL) {
- width = bitmap_get_width(bitmap);
- height = bitmap_get_height(bitmap);
- element->box.width = width + 1;
- element->box.height = height + 2;
- } else {
- element->box.width = 0;
- element->box.height = 0;
- }
- break;
- }
-}
-
-
-/**
- * Recalculates the size of a node.
- *
- * \param tree the tree to which node belongs, may be NULL
- * \param node the node to update
- * \param recalculate_sizes whether the node elements have changed
- */
-void tree_recalculate_node_sizes(struct tree *tree, struct node *node,
- bool recalculate_sizes)
-{
- struct node_element *element;
- int width, height;
-
- assert(node != NULL);
-
- width = node->box.width;
- height = node->box.height;
- node->box.width = 0;
- node->box.height = 0;
- if (node->expanded) {
- for (element = &node->data; element != NULL;
- element = element->next) {
- if (recalculate_sizes)
- tree_recalculate_node_element(tree, element);
- node->box.width = (node->box.width > element->box.x +
- element->box.width - node->box.x) ?
- node->box.width :
- element->box.width + element->box.x -
- node->box.x;
- node->box.height += element->box.height;
- }
- } else {
- if (recalculate_sizes)
- for (element = &node->data; element != NULL;
- element = element->next)
- tree_recalculate_node_element(tree, element);
- else
- tree_recalculate_node_element(tree, &node->data);
- node->box.width = node->data.box.width;
- node->box.height = node->data.box.height;
- }
-
- if (tree != NULL && height != node->box.height)
- tree_recalculate_node_positions(tree, tree->root);
-}
-
-
-/**
- * Recalculates the position of a node, its siblings and children.
- *
- * \param tree the tree to which 'root' belongs
- * \param root the root node to update from
- */
-void tree_recalculate_node_positions(struct tree *tree, struct node *root)
-{
- struct node *parent;
- struct node *node;
- struct node *child;
- struct node_element *element;
- int y;
- bool has_icon;
-
- for (node = root; node != NULL; node = node->next) {
-
- parent = node->parent;
-
- if (node->previous != NULL) {
- node->box.x = node->previous->box.x;
- node->box.y = node->previous->box.y +
- tree_get_node_height(node->previous);
- } else if (parent != NULL) {
- node->box.x = parent->box.x + NODE_INSTEP;
- node->box.y = parent->box.y +
- parent->box.height;
- for (child = parent->child; child != node;
- child = child->next)
- node->box.y += child->box.height;
- } else {
- node->box.x = tree->flags & TREE_NO_FURNITURE
- ? -NODE_INSTEP + 4 : 0;
- node->box.y = -20;
- }
-
- if (!node->expanded) {
- node->data.box.x = node->box.x;
- node->data.box.y = node->box.y;
- continue;
- }
-
- if (node->folder) {
- node->data.box.x = node->box.x;
- node->data.box.y = node->box.y;
- tree_recalculate_node_positions(tree,
- node->child);
- } else {
- y = node->box.y;
- has_icon = false;
- for (element = &node->data; element != NULL;
- element = element->next)
- if (element->type ==
- NODE_ELEMENT_TEXT_PLUS_ICON) {
- has_icon = true;
- break;
- }
-
- for (element = &node->data; element != NULL;
- element = element->next) {
- element->box.x = node->box.x;
- if (element->type !=
- NODE_ELEMENT_TEXT_PLUS_ICON &&
- has_icon)
- element->box.x += NODE_INSTEP;
- element->box.y = y;
- y += element->box.height;
- }
- }
-
- }
-}
-
-
-/**
- * Recalculates the size of a tree.
- *
- * \param tree the tree to recalculate
- */
-void tree_recalculate_size(struct tree *tree)
-{
- int width, height;
-
- assert(tree != NULL);
-
-
- width = tree->width;
- height = tree->height;
-
- tree->width = tree_get_node_width(tree->root);
- tree->height = tree_get_node_height(tree->root);
-
- if ((width != tree->width) || (height != tree->height))
- tree->callbacks->resized(tree, tree->width, tree->height,
- tree->client_data);
-}
-
-
-/**
- * Calculates the width of a node including any children
- *
- * \param node the node to calculate the height of
- * \return the total width of the node and children
- */
-int tree_get_node_width(struct node *node)
-{
- int width = 0;
- int child_width;
-
- assert(node != NULL);
-
- for (; node != NULL; node = node->next) {
- if (width < (node->box.x + node->box.width))
- width = node->box.x + node->box.width;
- if ((node->child != NULL) && (node->expanded)) {
- child_width = tree_get_node_width(node->child);
- if (width < child_width)
- width = child_width;
- }
- }
- return width;
-}
-
-
-/**
- * Calculates the height of a node including any children
- *
- * \param node the node to calculate the height of
- * \return the total height of the node and children
- */
-int tree_get_node_height(struct node *node) {
- int y1;
-
- assert(node != NULL);
-
- if ((node->child != NULL) && (node->expanded)) {
- y1 = node->box.y;
- if (y1 < 0)
- y1 = 0;
- node = node->child;
- while ((node->next != NULL) || ((node->child != NULL) &&
- (node->expanded))) {
- for (; node->next != NULL; node = node->next);
- if ((node->child != NULL) && (node->expanded))
- node = node->child;
- }
- return node->box.y + node->box.height - y1;
- } else {
- return node->box.height;
- }
-}
-
-
-/**
- * Updates the selected state for a region of nodes.
- *
- * \param tree the tree to update
- * \param y the minimum y of the selection rectangle
- * \param height the height of the selection rectangle
- * \param invert whether to invert the selected state
- */
-void tree_handle_selection_area(struct tree *tree, int y, int height,
- bool invert)
-{
- assert(tree != NULL);
- assert(tree->root != NULL);
-
- if (tree->root->child == NULL)
- return;
-
- if (height < 0) {
- y += height;
- height = -height;
- }
- tree_handle_selection_area_node(tree, tree->root->child, y, height,
- invert);
}
@@ -2151,10 +2179,9 @@
* \param height the height of the selection rectangle
* \param invert whether to invert the selected state
*/
-void tree_handle_selection_area_node(struct tree *tree, struct node *node,
- int y, int height, bool invert)
-{
-
+static void tree_handle_selection_area_node(struct tree *tree,
+ struct node *node, int y, int height, bool invert)
+{
struct node_element *element;
struct node *update;
int y_max;
@@ -2173,10 +2200,10 @@
update = NULL;
if (node->expanded) {
for (element = &node->data; element != NULL;
- element = element->next) {
+ element = element->next) {
y0 = element->box.y;
y1 = element->box.y +
- element->box.height;
+ element->box.height;
if ((y0 < y_max) && (y1 >= y)) {
update = element->parent;
break;
@@ -2202,137 +2229,49 @@
}
if ((node->child != NULL) && (node->expanded))
tree_handle_selection_area_node(tree, node->child, y,
- height, invert);
- }
-}
-
-
-/**
- * Finds a node at a specific location.
- *
- * \param root the root node to check from
- * \param x the x co-ordinate
- * \param y the y co-ordinate
- * \param furniture whether the returned area was in an elements furniture
- * \return the node at the specified position, or NULL for none
- */
-struct node *tree_get_node_at(struct node *root, int x, int y, bool *furniture)
-{
- struct node_element *result;
-
- if ((result = tree_get_node_element_at(root, x, y, furniture)))
- return result->parent;
- return NULL;
-}
-
-
-/**
- * Finds a node element at a specific location.
- *
- * \param node the root node to check from
- * \param x the x co-ordinate
- * \param y the y co-ordinate
- * \param furniture whether the returned area was in an elements furniture
- * \return the node at the specified position, or NULL for none
- */
-struct node_element *tree_get_node_element_at(struct node *node, int x, int y,
- bool *furniture)
-{
- struct node_element *element;
- int x0, x1, y0, y1;
-
- *furniture = false;
+ height, invert);
+ }
+}
+
+
+/**
+ * Updates the selected state for a region of nodes.
+ *
+ * \param tree the tree to update
+ * \param y the minimum y of the selection rectangle
+ * \param height the height of the selection rectangle
+ * \param invert whether to invert the selected state
+ */
+static void tree_handle_selection_area(struct tree *tree, int y, int height,
+ bool invert)
+{
+ assert(tree != NULL);
+ assert(tree->root != NULL);
+
+ if (tree->root->child == NULL)
+ return;
+
+ if (height < 0) {
+ y += height;
+ height = -height;
+ }
+ tree_handle_selection_area_node(tree, tree->root->child, y, height,
+ invert);
+}
+
+
+/**
+ * Clears the processing flag.
+ *
+ * \param node the node to process siblings and children of
+ */
+static void tree_clear_processing(struct node *node)
+{
for (; node != NULL; node = node->next) {
- if (node->box.y > y) return NULL;
- if ((node->box.x - NODE_INSTEP < x) && (node->box.y < y) &&
- (node->box.x + node->box.width >= x) &&
- (node->box.y + node->box.height >= y)) {
- if (node->expanded) {
- for (element = &node->data; element != NULL;
- element = element->next) {
- x0 = element->box.x;
- y0 = element->box.y;
- x1 = element->box.x +
- element->box.width;
- y1 = element->box.y +
- element->box.height;
- if ((x0 < x) && (y0 < y) && (x1 >= x)
- && (y1 >= y))
- return element;
- }
- } else {
- x0 = node->data.box.x;
- y0 = node->data.box.y;
- x1 = node->data.box.x + node->data.box.width;
- y1 = node->data.box.y + node->data.box.height;
- if ((x0 < x) && (y0 < y) && (x1 >= x) &&
- (y1>= y))
- return &node->data;
- }
- if (((node->child != NULL) ||
- (node->data.next != NULL)) &&
- (node->data.box.x - NODE_INSTEP + 4 < x)
- && (node->data.box.y + 4 < y) &&
- (node->data.box.x > x) &&
- (node->data.box.y + 20 > y)) {
- *furniture = true;
- return &node->data;
- }
- }
-
- element = tree_get_node_element_at(node->child, x, y,
- furniture);
- if ((node->child != NULL) && (node->expanded) &&
- (element != NULL))
- return element;
- }
- return NULL;
-}
-
-
-
-/**
- * Moves nodes within a tree.
- *
- * \param tree the tree to process
- * \param destination the node to link before/as a child (folders)
- * or before/after (link)
- * \param before whether to link siblings before or after the supplied
- * node
- */
-void tree_move_selected_nodes(struct tree *tree, struct node *destination,
- bool before)
-{
- struct node *link;
- struct node *test;
- bool error;
-
- tree_clear_processing(tree->root);
- tree_selected_to_processing(tree->root);
-
- /* the destination node cannot be a child of any node with
- the processing flag set */
- error = destination->processing;
- for (test = destination; test != NULL; test = test->parent)
- error |= test->processing;
- if (error) {
- tree_clear_processing(tree->root);
- return;
- }
- if ((destination->folder) && (!destination->expanded) && (!before)) {
- tree_set_node_expanded(tree, destination, true, false, false);
- }
- link = tree_move_processing_node(tree, tree->root, destination, before,
- true);
- while (link != NULL)
- link = tree_move_processing_node(tree, tree->root, link, false,
- false);
-
- tree_clear_processing(tree->root);
- tree_recalculate_node_positions(tree, tree->root);
- if (tree->redraw)
- tree->callbacks->redraw_request(0, 0, tree->width, tree->height,
- tree->client_data);
+ node->processing = false;
+ if (node->child != NULL)
+ tree_clear_processing(node->child);
+ }
}
@@ -2341,27 +2280,12 @@
*
* \param node the node to process siblings and children of
*/
-void tree_selected_to_processing(struct node *node)
+static void tree_selected_to_processing(struct node *node)
{
for (; node != NULL; node = node->next) {
node->processing = node->selected;
if ((node->child != NULL) && (node->expanded))
tree_selected_to_processing(node->child);
- }
-}
-
-
-/**
- * Clears the processing flag.
- *
- * \param node the node to process siblings and children of
- */
-void tree_clear_processing(struct node *node)
-{
- for (; node != NULL; node = node->next) {
- node->processing = false;
- if (node->child != NULL)
- tree_clear_processing(node->child);
}
}
@@ -2378,8 +2302,8 @@
* inside of folders)
* \return the node moved
*/
-struct node *tree_move_processing_node(struct tree *tree, struct node *node,
- struct node *link, bool before, bool first)
+static struct node *tree_move_processing_node(struct tree *tree,
+ struct node *node, struct node *link, bool before, bool first)
{
struct node *result;
@@ -2397,12 +2321,165 @@
}
if (node->child != NULL) {
result = tree_move_processing_node(tree, node->child,
- link, before, first);
+ link, before, first);
if (result != NULL)
return result;
}
}
return NULL;
+}
+
+
+/**
+ * Moves nodes within a tree.
+ *
+ * \param tree the tree to process
+ * \param destination the node to link before/as a child (folders)
+ * or before/after (link)
+ * \param before whether to link siblings before or after the supplied
+ * node
+ */
+static void tree_move_selected_nodes(struct tree *tree,
+ struct node *destination, bool before)
+{
+ struct node *link;
+ struct node *test;
+ bool error;
+
+ tree_clear_processing(tree->root);
+ tree_selected_to_processing(tree->root);
+
+ /* the destination node cannot be a child of any node with
+ the processing flag set */
+ error = destination->processing;
+ for (test = destination; test != NULL; test = test->parent)
+ error |= test->processing;
+ if (error) {
+ tree_clear_processing(tree->root);
+ return;
+ }
+ if ((destination->folder) && (!destination->expanded) && (!before)) {
+ tree_set_node_expanded(tree, destination, true, false, false);
+ }
+ link = tree_move_processing_node(tree, tree->root, destination, before,
+ true);
+ while (link != NULL)
+ link = tree_move_processing_node(tree, tree->root, link, false,
+ false);
+
+ tree_clear_processing(tree->root);
+ tree_recalculate_node_positions(tree, tree->root);
+ if (tree->redraw)
+ tree->callbacks->redraw_request(0, 0, tree->width, tree->height,
+ tree->client_data);
+}
+
+
+/**
+ * Handle the end of a drag operation
+ *
+ * \param tree the tree on which the drag was performed
+ * \param mouse mouse state during drag end
+ * \param x0 x coordinate of drag start
+ * \param y0 y coordinate of drag start
+ * \param x1 x coordinate of drag end
+ * \param y1 y coordinate of drag end
+ */
+void tree_drag_end(struct tree *tree, browser_mouse_state mouse, int x0, int y0,
+ int x1, int y1)
+{
+
+ bool before;
+ struct node *node;
+ int x, y;
+
+ if (tree->textarea_drag_start) {
+ x = tree->editing->box.x;
+ y = tree->editing->box.y;
+ if (tree->editing->type == NODE_ELEMENT_TEXT_PLUS_ICON)
+ x += NODE_INSTEP;
+ textarea_drag_end(tree->textarea, mouse, x1 - x, y1 - y);
+ }
+
+ tree->textarea_drag_start = false;
+
+ switch (tree->drag) {
+ case TREE_NO_DRAG:
+ break;
+ case TREE_SELECT_DRAG:
+ tree_handle_selection_area(tree, y0, y1 - y0,
+ (mouse | BROWSER_MOUSE_HOLDING_2));
+ break;
+ case TREE_MOVE_DRAG:
+ if (!(tree->flags & TREE_MOVABLE))
+ return;
+ node = tree_get_link_details(tree, x1, y1, &before);
+ tree_move_selected_nodes(tree, node, before);
+ break;
+ }
+
+ tree->drag = TREE_NO_DRAG;
+}
+
+
+/**
+ * Key press handling for a tree.
+ *
+ * \param tree The tree which got the keypress
+ * \param key The ucs4 character codepoint
+ * \return true if the keypress is dealt with, false otherwise.
+ */
+bool tree_keypress(struct tree *tree, uint32_t key)
+{
+
+ if (tree->editing != NULL)
+ switch (key) {
+ case KEY_ESCAPE:
+ tree_stop_edit(tree, false);
+ return true;
+ case KEY_NL:
+ tree_stop_edit(tree, true);
+ return true;
+ default:
+ return textarea_keypress(tree->textarea, key);
+ }
+
+ return false;
+}
+
+
+/**
+ * Alphabetical comparison function for nodes
+ *
+ * \param n1 first node to compare
+ * \param n2 first node to compare
+ * \return 0 if equal, greater then zero if n1 > n2,
+ * less then zero if n2 < n1
+ */
+int tree_alphabetical_sort(struct node *n1, struct node *n2)
+{
+ return strcmp(n1->data.text, n2->data.text);
+}
+
+
+/**
+ * Redraw requests from the textarea are piped through this because we have to
+ * check the redraw flag of the tree before requesting a redraw and change the
+ * position to tree origin relative.
+ */
+static void tree_textarea_redraw_request(void *data, int x, int y,
+ int width, int height)
+{
+ struct tree *tree = data;
+ x = x + tree->editing->box.x;
+ y = y + tree->editing->box.y;
+ if (tree->editing->type == NODE_ELEMENT_TEXT_PLUS_ICON)
+ x += NODE_INSTEP;
+
+ if (tree->redraw)
+ tree->callbacks->redraw_request(x, y,
+ width, height,
+ tree->client_data);
}
@@ -2429,7 +2506,7 @@
for (; parent != NULL; parent = parent->parent) {
if (!parent->expanded) {
tree_set_node_expanded(tree, parent, true,
- false, false);
+ false, false);
}
}
@@ -2441,8 +2518,7 @@
width -= NODE_INSTEP;
tree->textarea = textarea_create(width, height, 0,
- &plot_fstyle, tree_textarea_redraw_request,
- tree);
+ &plot_fstyle, tree_textarea_redraw_request, tree);
if (tree->textarea == NULL) {
tree_stop_edit(tree, false);
return;
@@ -2452,90 +2528,20 @@
tree_handle_node_element_changed(tree, element);
tree_recalculate_size(tree);
tree->callbacks->scroll_visible(element->box.y, element->box.height,
- tree->client_data);
-}
-
-
-/**
- * Stops editing a node_element
- *
- * \param tree The tree to stop editing for
- * \param keep_changes If true the changes made to the text will be kept,
- * if false they will be dropped
- */
-void tree_stop_edit(struct tree *tree, bool keep_changes)
-{
- int text_len;
- char *text = NULL;
- struct node_element *element;
- struct node_msg_data msg_data;
- node_callback_resp response;
-
- assert(tree != NULL);
-
- if (tree->editing == NULL || tree->textarea == NULL)
- return;
-
- element = tree->editing;
-
- if (keep_changes) {
- text_len = textarea_get_text(tree->textarea, NULL, 0);
- text = malloc(text_len * sizeof(char));
- if (text == NULL) {
- LOG(("malloc failed"));
- warn_user("NoMemory", 0);
- textarea_destroy(tree->textarea);
- tree->textarea = NULL;
- return;
- }
- textarea_get_text(tree->textarea, text, text_len);
- }
-
-
- if (keep_changes && element->parent->user_callback != NULL) {
- msg_data.msg = NODE_ELEMENT_EDIT_FINISHING;
- msg_data.flag = element->flag;
- msg_data.node = element->parent;
- msg_data.data.text = text;
- response = element->parent->user_callback(
- element->parent->callback_data,
- &msg_data);
-
- switch (response) {
- case NODE_CALLBACK_REJECT:
- free(text);
- text = NULL;
- break;
- case NODE_CALLBACK_CONTINUE:
- free(text);
- text = NULL;
- return;
- case NODE_CALLBACK_HANDLED:
- case NODE_CALLBACK_NOT_HANDLED:
- text = msg_data.data.text;
- break;
- }
- }
-
- textarea_destroy(tree->textarea);
- tree->textarea = NULL;
- tree->editing = NULL;
-
- if (text != NULL)
- tree_update_node_element(tree, element, text, NULL);
- else
- tree_handle_node_element_changed(tree, element);
-
-
- tree_recalculate_size(tree);
- if (element->parent->user_callback != NULL) {
- msg_data.msg = NODE_ELEMENT_EDIT_FINISHED;
- msg_data.flag = element->flag;
- msg_data.node = element->parent;
- element->parent->user_callback(element->parent->callback_data,
- &msg_data);
- }
-}
+ tree->client_data);
+}
+
+
+/**
+ * Callback for fetchcache(). Should be removed once bitmaps get loaded directly
+ * from disc
+ */
+static nserror tree_icon_callback(hlcache_handle *handle,
+ const hlcache_event *event, void *pw)
+{
+ return NSERROR_OK;
+}
+
/**
* Tree utility function. Placed here so that this code doesn't have to be
@@ -2574,7 +2580,7 @@
/* Build native path */
memcpy(native_path, option_tree_icons_dir,
- strlen(option_tree_icons_dir) + 1);
+ strlen(option_tree_icons_dir) + 1);
path_add_part(native_path, len, name);
/* Convert native path to URL */
@@ -2585,10 +2591,10 @@
}
/* Fetch the icon */
- err = hlcache_handle_retrieve(icon_url, 0, 0, 0,
- tree_icon_callback, 0, 0, 0, &c);
-
-
+ err = hlcache_handle_retrieve(icon_url, 0, 0, 0,
+ tree_icon_callback, 0, 0, 0, &c);
+
+
/* If we built the URL here, free it */
if (url != NULL)
free(url);
@@ -2599,34 +2605,3 @@
return c;
}
-
-
-/**
- * Callback for fetchcache(). Should be removed once bitmaps get loaded directly
- * from disc
- */
-nserror tree_icon_callback(hlcache_handle *handle,
- const hlcache_event *event, void *pw)
-{
- return NSERROR_OK;
-}
-
-/**
- * Redraw requests from the textarea are piped through this because we have to
- * check the redraw flag of the tree before requesting a redraw and change the
- * position to tree origin relative.
- */
-void tree_textarea_redraw_request(void *data, int x, int y,
- int width, int height)
-{
- struct tree *tree = data;
- x = x + tree->editing->box.x;
- y = y + tree->editing->box.y;
- if (tree->editing->type == NODE_ELEMENT_TEXT_PLUS_ICON)
- x += NODE_INSTEP;
-
- if (tree->redraw)
- tree->callbacks->redraw_request(x, y,
- width, height,
- tree->client_data);
-}
12 years, 12 months
r10850 vince - in /branches/jmb/treeview-redux: content/urldb.c desktop/tree.h
by netsurf@semichrome.net
Author: vince
Date: Mon Sep 27 08:39:52 2010
New Revision: 10850
URL: http://source.netsurf-browser.org?rev=10850&view=rev
Log:
final core review updates
Modified:
branches/jmb/treeview-redux/content/urldb.c
branches/jmb/treeview-redux/desktop/tree.h
Modified: branches/jmb/treeview-redux/content/urldb.c
URL: http://source.netsurf-browser.org/branches/jmb/treeview-redux/content/url...
==============================================================================
--- branches/jmb/treeview-redux/content/urldb.c (original)
+++ branches/jmb/treeview-redux/content/urldb.c Mon Sep 27 08:39:52 2010
@@ -2442,9 +2442,7 @@
url_func_result res;
int i;
- assert(url);
-
-// LOG(("%s", url));
+ assert(url != NULL);
urldb_add_url(url);
@@ -2529,8 +2527,6 @@
}
}
-// LOG(("%s", ret));
-
/* Now consider cookies whose paths prefix-match ours */
for (p = p->parent; p; p = p->parent) {
/* Find directory's path entry(ies) */
@@ -2540,7 +2536,6 @@
continue;
for (c = q->cookies; c; c = c->next) {
-// LOG(("%p: %s=%s", c, c->name, c->value));
if (c->expires != 1 && c->expires < now)
/* cookie has expired => ignore */
continue;
@@ -2604,8 +2599,6 @@
}
-// LOG(("%s", ret));
-
/* Finally consider domain cookies for hosts which domain match ours */
for (h = (const struct host_part *)p; h && h != &db_root;
h = h->parent) {
@@ -2634,8 +2627,6 @@
cookies_schedule_update((struct cookie_data *)c);
}
}
-
-// LOG(("%s", ret));
if (count == 0) {
/* No cookies found */
@@ -2704,8 +2695,6 @@
url_func_result res;
assert(url && header);
-
-// LOG(("'%s' : '%s'", url, header));
/* strip fragment */
urlt = strdup(url);
@@ -3392,7 +3381,6 @@
urldb_free_cookie(d);
cookies_schedule_update((struct cookie_data *)c);
-// LOG(("%p: %s=%s", c, c->name, c->value));
}
} else {
c->prev = p->cookies_end;
@@ -3402,7 +3390,6 @@
else
p->cookies = c;
p->cookies_end = c;
-// LOG(("%p: %s=%s", c, c->name, c->value));
}
return true;
Modified: branches/jmb/treeview-redux/desktop/tree.h
URL: http://source.netsurf-browser.org/branches/jmb/treeview-redux/desktop/tre...
==============================================================================
--- branches/jmb/treeview-redux/desktop/tree.h (original)
+++ branches/jmb/treeview-redux/desktop/tree.h Mon Sep 27 08:39:52 2010
@@ -33,18 +33,26 @@
struct hlcache_handle;
/* Tree flags */
-#define TREE_NO_FLAGS 0
-#define TREE_NO_DRAGS 1
-#define TREE_NO_FURNITURE 2
-#define TREE_SINGLE_SELECT 4
-#define TREE_NO_SELECT 8
-#define TREE_MOVABLE 16
-/* if the last child of a directory is deleted the directory will be deleted
- too */
-#define TREE_DELETE_EMPTY_DIRS 16
+enum tree_flags {
+ TREE_NO_FLAGS = 0,
+ TREE_NO_DRAGS = 1,
+ TREE_NO_FURNITURE = 2,
+ TREE_SINGLE_SELECT = 4,
+ TREE_NO_SELECT = 8,
+ TREE_MOVABLE = 16,
+ TREE_DELETE_EMPTY_DIRS = 32, /**< if the last child of a
+ * directory is deleted the
+ * directory will be deleted
+ * too.
+ */
+};
-/* the flag for the first node_element in every node, all other flags should
- be different than this one */
+/** A "flag" value to indicate the element data contains title
+ * text. This value should be the first node_element in every
+ * node. All other values should be different than this one. The term
+ * flag is misused as it is actually a value used by the API consumer
+ * to indicate teh type of data a node element contains.
+ */
#define TREE_ELEMENT_TITLE 0x00
/* these should be defined in front end code */
@@ -56,48 +64,50 @@
struct node_element;
typedef enum {
- NODE_ELEMENT_TEXT, /* Text only */
- NODE_ELEMENT_TEXT_PLUS_ICON, /* Text and icon */
- NODE_ELEMENT_BITMAP /* Bitmap only */
+ NODE_ELEMENT_TEXT, /**< Text only */
+ NODE_ELEMENT_TEXT_PLUS_ICON, /**< Text and icon */
+ NODE_ELEMENT_BITMAP /**< Bitmap only */
} node_element_type;
typedef enum {
- NODE_DELETE_ELEMENT_TXT, /* The text of an element of the node
- is being deleted */
- NODE_DELETE_ELEMENT_IMG, /* The bitmap or icon of a node is being
- deleted */
- NODE_LAUNCH, /* The node has been launched */
- NODE_ELEMENT_EDIT_FINISHING, /* New text has to be accepted or
- rejected */
- NODE_ELEMENT_EDIT_FINISHED /* Editing of a node_element has been
- finished */
+ NODE_DELETE_ELEMENT_TXT, /**< The text of an element of the
+ * node is being deleted */
+ NODE_DELETE_ELEMENT_IMG, /**< The bitmap or icon of a node is
+ * being deleted */
+ NODE_LAUNCH, /**< The node has been launched */
+ NODE_ELEMENT_EDIT_FINISHING, /**< New text has to be accepted
+ * or rejected. */
+ NODE_ELEMENT_EDIT_FINISHED /**< Editing of a node_element has
+ * been finished. */
} node_msg;
typedef enum {
NODE_CALLBACK_HANDLED,
NODE_CALLBACK_NOT_HANDLED,
- NODE_CALLBACK_REJECT, /* reject new text for node element and
- leave editing mode */
- NODE_CALLBACK_CONTINUE /* don't leave editig mode */
+ NODE_CALLBACK_REJECT, /**< reject new text for node element
+ * and leave editing mode. */
+ NODE_CALLBACK_CONTINUE /**< don't leave editig mode. */
} node_callback_resp;
+/** Internal node message. */
struct node_msg_data {
- node_msg msg;
- unsigned int flag;
- struct node *node;
+ node_msg msg; /**< The type of message. */
+ unsigned int flag; /**< message flags. */
+ struct node *node; /**< tree node messsage concerns. */
union {
- char *text;
- void *bitmap;
- } data;
+ char *text; /**< textural data. */
+ void *bitmap; /**< bitmap data. */
+ } data; /**< The message data. */
};
+/** callbacks to perform necessary operations on treeview. */
struct treeview_table {
void (*redraw_request)(int x, int y, int width, int height,
- void *data);
+ void *data); /**< request a redraw. */
void (*resized)(struct tree *tree, int width, int height,
- void *data);
- void (*scroll_visible)(int y, int height, void *data);
- void (*get_window_dimensions)(int *width, int *height, void *data);
+ void *data); /**< resize treeview area. */
+ void (*scroll_visible)(int y, int height, void *data); /**< scroll visible treeview area. */
+ void (*get_window_dimensions)(int *width, int *height, void *data); /**< get dimensions of window */
};
/**
12 years, 12 months
r10849 vince - in /branches/jmb/treeview-redux/desktop: cookies.c tree.c tree.h tree_url_node.c
by netsurf@semichrome.net
Author: vince
Date: Sun Sep 26 18:27:50 2010
New Revision: 10849
URL: http://source.netsurf-browser.org?rev=10849&view=rev
Log:
most of the core review done
Modified:
branches/jmb/treeview-redux/desktop/cookies.c
branches/jmb/treeview-redux/desktop/tree.c
branches/jmb/treeview-redux/desktop/tree.h
branches/jmb/treeview-redux/desktop/tree_url_node.c
Modified: branches/jmb/treeview-redux/desktop/cookies.c
URL: http://source.netsurf-browser.org/branches/jmb/treeview-redux/desktop/coo...
==============================================================================
--- branches/jmb/treeview-redux/desktop/cookies.c (original)
+++ branches/jmb/treeview-redux/desktop/cookies.c Sun Sep 26 18:27:50 2010
@@ -140,36 +140,6 @@
return NODE_CALLBACK_HANDLED;
}
-/**
- * Helper to update the text of a node if it has changed.
- *
- * \param element The node element to update.
- * \param text The text to update the element with. The ownership of
- * this string is taken by this function and must not be
- * referred to after the function exits.
- */
-static bool update_element_text(struct node_element *element, char *text)
-{
- const char *node_text; /* existing node text */
-
- if (text == NULL)
- return false;
-
- if (element == NULL) {
- free(text);
- return false;
- }
-
- node_text = tree_node_element_get_text(element);
-
- if ((node_text == NULL) || (strcmp(node_text, text) != 0)) {
- tree_update_node_element(cookies_tree, element, text, NULL);
- } else {
- /* text does not need changing, free it */
- free(text);
- }
- return true;
-}
/**
* Updates a tree entry for a cookie.
@@ -191,7 +161,8 @@
/* update the value text */
element = tree_node_find_element(node, TREE_ELEMENT_VALUE, NULL);
- update_element_text(element,
+ tree_update_element_text(cookies_tree,
+ element,
messages_get_buff("TreeValue",
data->value != NULL ?
data->value :
@@ -202,14 +173,16 @@
if ((data->comment != NULL) &&
(strcmp(data->comment, "") != 0)) {
element = tree_node_find_element(node, TREE_ELEMENT_COMMENT, NULL);
- update_element_text(element,
+ tree_update_element_text(cookies_tree,
+ element,
messages_get_buff("TreeComment",
data->comment));
}
/* update domain text */
element = tree_node_find_element(node, TREE_ELEMENT_DOMAIN, element);
- update_element_text(element,
+ tree_update_element_text(cookies_tree,
+ element,
messages_get_buff("TreeDomain",
data->domain,
data->domain_from_set ?
@@ -218,7 +191,8 @@
/* update path text */
element = tree_node_find_element(node, TREE_ELEMENT_PATH, element);
- update_element_text(element,
+ tree_update_element_text(cookies_tree,
+ element,
messages_get_buff("TreePath", data->path,
data->path_from_set ?
messages_get("TreeHeaders") :
@@ -226,7 +200,8 @@
/* update expiry text */
element = tree_node_find_element(node, TREE_ELEMENT_EXPIRES, element);
- update_element_text(element,
+ tree_update_element_text(cookies_tree,
+ element,
messages_get_buff("TreeExpires",
(data->expires > 0)
? (data->expires == 1)
@@ -236,7 +211,8 @@
/* update last used text */
element = tree_node_find_element(node, TREE_ELEMENT_LAST_USED, element);
- update_element_text(element,
+ tree_update_element_text(cookies_tree,
+ element,
messages_get_buff("TreeLastUsed",
(data->last_used > 0) ?
ctime(&data->last_used) :
@@ -244,7 +220,8 @@
/* update secure text */
element = tree_node_find_element(node, TREE_ELEMENT_SECURE, element);
- update_element_text(element,
+ tree_update_element_text(cookies_tree,
+ element,
messages_get_buff("TreeSecure",
data->secure ?
messages_get("Yes") :
@@ -253,13 +230,15 @@
/* update version text */
element = tree_node_find_element(node, TREE_ELEMENT_VERSION, element);
snprintf(buffer, sizeof(buffer), "TreeVersion%i", data->version);
- update_element_text(element,
+ tree_update_element_text(cookies_tree,
+ element,
messages_get_buff("TreeVersion",
messages_get(buffer)));
/* update persistant text */
element = tree_node_find_element(node, TREE_ELEMENT_PERSISTENT, element);
- update_element_text(element,
+ tree_update_element_text(cookies_tree,
+ element,
messages_get_buff("TreePersistent",
data->no_destroy ?
messages_get("Yes") :
Modified: branches/jmb/treeview-redux/desktop/tree.c
URL: http://source.netsurf-browser.org/branches/jmb/treeview-redux/desktop/tre...
==============================================================================
--- branches/jmb/treeview-redux/desktop/tree.c (original)
+++ branches/jmb/treeview-redux/desktop/tree.c Sun Sep 26 18:27:50 2010
@@ -76,49 +76,49 @@
struct tree;
struct node_element_box {
- int x; /* X offset from origin */
- int y; /* Y offset from origin */
- int width; /* Element width */
- int height; /* Element height */
+ int x; /**< X offset from origin */
+ int y; /**< Y offset from origin */
+ int width; /**< Element width */
+ int height; /**< Element height */
};
struct node_element {
- struct node *parent; /* Parent node */
- node_element_type type; /* Element type */
- struct node_element_box box; /* Element bounding box */
- const char *text; /* Text for the element */
- void *bitmap; /* Bitmap for the element */
- struct node_element *next; /* Next node element */
- unsigned int flag; /* Client specified flag for data
+ struct node *parent; /**< Parent node */
+ node_element_type type; /**< Element type */
+ struct node_element_box box; /**< Element bounding box */
+ const char *text; /**< Text for the element */
+ void *bitmap; /**< Bitmap for the element */
+ struct node_element *next; /**< Next node element */
+ unsigned int flag; /**< Client specified flag for data
being represented */
- bool editable; /* Whether the node text can be
+ bool editable; /**< Whether the node text can be
* modified, editable text is deleted
* without noticing the tree user
*/
};
struct node {
- bool selected; /* Whether the node is selected */
- bool expanded; /* Whether the node is expanded */
- bool folder; /* Whether the node is a folder */
- bool retain_in_memory; /* Whether the node remains
+ bool selected; /**< Whether the node is selected */
+ bool expanded; /**< Whether the node is expanded */
+ bool folder; /**< Whether the node is a folder */
+ bool retain_in_memory; /**< Whether the node remains
in memory after deletion */
- bool deleted; /* Whether the node is currently
+ bool deleted; /**< Whether the node is currently
deleted */
- bool processing; /* Internal flag used when moving */
- struct node_element_box box; /* Bounding box of all elements */
- struct node_element data; /* Data to display */
- struct node *parent; /* Parent entry (NULL for root) */
- struct node *child; /* First child */
- struct node *last_child; /* Last child */
- struct node *previous; /* Previous child of the parent */
- struct node *next; /* Next child of the parent */
-
- /* Sorting function for the node (for folder nodes only) */
+ bool processing; /**< Internal flag used when moving */
+ struct node_element_box box; /**< Bounding box of all elements */
+ struct node_element data; /**< Data to display */
+ struct node *parent; /**< Parent entry (NULL for root) */
+ struct node *child; /**< First child */
+ struct node *last_child; /**< Last child */
+ struct node *previous; /**< Previous child of the parent */
+ struct node *next; /**< Next child of the parent */
+
+ /** Sorting function for the node (for folder nodes only) */
int (*sort) (struct node *, struct node *);
- /* Gets called for each deleted node_element and on node launch */
+ /** Gets called for each deleted node_element and on node launch */
tree_node_user_callback user_callback;
- /* User data to be passed to delete_callback */
+ /** User data to be passed to delete_callback */
void *callback_data;
};
@@ -273,7 +273,7 @@
{
struct node *node;
- assert(title);
+ assert(title != NULL);
node = calloc(sizeof(struct node), 1);
if (node == NULL) {
@@ -386,10 +386,10 @@
struct node *parent;
bool sort = false;
- assert(link);
- assert(node);
-
- if ((!link->folder) || (before)) {
+ assert(link != NULL);
+ assert(node != NULL);
+
+ if ((link->folder == 0) || (before)) {
parent = node->parent = link->parent;
if (parent->sort)
sort = true;
@@ -629,6 +629,38 @@
tree_update_node_element(tree, &(node->data), NULL, icon);
}
+/**
+ * Update the text of a node element if it has changed.
+ *
+ * \param element The node element to update.
+ * \param text The text to update the element with. The ownership of
+ * this string is taken by this function and must not be
+ * referred to after the function exits.
+ */
+bool tree_update_element_text(struct tree *tree,
+ struct node_element *element, char *text)
+{
+ const char *node_text; /* existing node text */
+
+ if (text == NULL)
+ return false;
+
+ if (element == NULL) {
+ free(text);
+ return false;
+ }
+
+ node_text = tree_node_element_get_text(element);
+
+ if ((node_text == NULL) || (strcmp(node_text, text) != 0)) {
+ tree_update_node_element(tree, element, text, NULL);
+ } else {
+ /* text does not need changing, free it */
+ free(text);
+ }
+ return true;
+}
+
/**
* Updates [all siblings and descendants of] a node to an expansion state.
@@ -643,10 +675,7 @@
void tree_set_node_expanded(struct tree *tree, struct node *node, bool expanded,
bool folder, bool leaf)
{
- bool change = tree_set_node_expanded_internal(tree, node, expanded,
- folder, leaf);
-
- if (change)
+ if (tree_set_node_expanded_internal(tree, node, expanded, folder, leaf))
tree_handle_node_changed(tree, node, false, true);
}
@@ -781,7 +810,7 @@
child = node->child;
node->child = NULL;
- while (child) {
+ while (child != NULL) {
tree_sort_insert(node, child);
child = child->next;
}
@@ -808,7 +837,7 @@
/**
- * Inserts a node into the correct place according to the parents sort function
+ * Inserts a node into the correct place according to the parent's sort function
*
* \param parent the node whose child node 'node' becomes
* \param node the node to be inserted
@@ -822,7 +851,8 @@
assert(parent->sort != NULL);
after = parent->last_child;
- while (after && parent->sort(node, after) == -1)
+ while ((after != NULL) &&
+ (parent->sort(node, after) == -1))
after = after->previous;
if (after != NULL) {
@@ -831,12 +861,12 @@
node->next = after->next;
node->previous = after;
after->next = node;
- }
- else {
+ } else {
node->previous = NULL;
node->next = parent->child;
- if (parent->child)
+ if (parent->child != NULL) {
parent->child->previous = node;
+ }
parent->child = node;
}
@@ -919,11 +949,10 @@
void tree_update_node_element(struct tree *tree, struct node_element *element,
const char *text, void *bitmap)
{
-
node_callback_resp response;
struct node_msg_data msg_data;
- assert(element);
+ assert(element != NULL);
if (tree != NULL && element == tree->editing)
tree_stop_edit(tree, false);
@@ -996,14 +1025,14 @@
/**
- * Returns true if the tree is currently being edited
+ * Returns whether the current tree is being edited at this time
*
* \param tree the tree to be checked
* \return true if the tree is currently being edited
*/
bool tree_is_edited(struct tree *tree)
{
- return tree->editing == NULL ? false:true;
+ return tree->editing == NULL ? false : true;
}
@@ -1534,10 +1563,10 @@
false);
if (mouse & (BROWSER_MOUSE_DRAG_1 | BROWSER_MOUSE_DRAG_2)) {
- /* TODO: the tree window has to scroll the tree when
- mouse reaches border while dragging this isn't
- solved for the browser window too.
- */
+ /** @todo the tree window has to scroll the tree when
+ * mouse reaches border while dragging this isn't
+ * solved for the browser window too.
+ */
tree->drag = TREE_SELECT_DRAG;
}
return true;
@@ -1762,7 +1791,7 @@
{
int width, height, tree_height;
- assert(node);
+ assert(node != NULL);
width = node->box.width;
height = node->box.height;
@@ -1900,7 +1929,7 @@
struct node_element *element;
int width, height;
- assert(node);
+ assert(node != NULL);
width = node->box.width;
height = node->box.height;
@@ -2522,8 +2551,9 @@
const char *icon_url = NULL;
int len;
hlcache_handle *c;
-
- /* TODO: something like bitmap_from_disc is needed here */
+ nserror err;
+
+ /** @todo something like bitmap_from_disc is needed here */
if (!strncmp(name, "file://", 7)) {
icon_url = name;
@@ -2555,12 +2585,17 @@
}
/* Fetch the icon */
- hlcache_handle_retrieve(icon_url, 0, 0, 0,
+ err = hlcache_handle_retrieve(icon_url, 0, 0, 0,
tree_icon_callback, 0, 0, 0, &c);
+
/* If we built the URL here, free it */
if (url != NULL)
free(url);
+
+ if (err != NSERROR_OK) {
+ return NULL;
+ }
return c;
}
Modified: branches/jmb/treeview-redux/desktop/tree.h
URL: http://source.netsurf-browser.org/branches/jmb/treeview-redux/desktop/tre...
==============================================================================
--- branches/jmb/treeview-redux/desktop/tree.h (original)
+++ branches/jmb/treeview-redux/desktop/tree.h Sun Sep 26 18:27:50 2010
@@ -149,6 +149,7 @@
bool tree_node_is_folder(struct node *node);
void tree_update_node_element(struct tree *tree, struct node_element *element,
const char *text, void *bitmap);
+bool tree_update_element_text(struct tree *tree, struct node_element *element, char *text);
const char *tree_node_element_get_text(struct node_element *element);
struct node *tree_get_root(struct tree *tree);
bool tree_is_edited(struct tree *tree);
Modified: branches/jmb/treeview-redux/desktop/tree_url_node.c
URL: http://source.netsurf-browser.org/branches/jmb/treeview-redux/desktop/tre...
==============================================================================
--- branches/jmb/treeview-redux/desktop/tree_url_node.c (original)
+++ branches/jmb/treeview-redux/desktop/tree_url_node.c Sun Sep 26 18:27:50 2010
@@ -231,37 +231,6 @@
return node;
}
-/**
- * Helper to update the text of a node if it has changed.
- *
- * \param element The node element to update.
- * \param text The text to update the element with. The ownership of
- * this string is taken by this function and must not be
- * referred to after the function exits.
- */
-static bool update_element_text(struct tree *tree,
- struct node_element *element, char *text)
-{
- const char *node_text; /* existing node text */
-
- if (text == NULL)
- return false;
-
- if (element == NULL) {
- free(text);
- return false;
- }
-
- node_text = tree_node_element_get_text(element);
-
- if ((node_text == NULL) || (strcmp(node_text, text) != 0)) {
- tree_update_node_element(tree, element, text, NULL);
- } else {
- /* text does not need changing, free it */
- free(text);
- }
- return true;
-}
/**
* Updates the node details for a URL node.
@@ -321,19 +290,19 @@
/* update last visit text */
element = tree_node_find_element(node, TREE_ELEMENT_LAST_VISIT, element);
- update_element_text(tree,
- element,
- messages_get_buff("TreeLast",
- (data->last_visit > 0) ?
- ctime((time_t *)&data->last_visit) :
- messages_get("TreeUnknown")));
+ tree_update_element_text(tree,
+ element,
+ messages_get_buff("TreeLast",
+ (data->last_visit > 0) ?
+ ctime((time_t *)&data->last_visit) :
+ messages_get("TreeUnknown")));
/* update number of visits text */
element = tree_node_find_element(node, TREE_ELEMENT_VISITS, element);
- update_element_text(tree,
- element,
- messages_get_buff("TreeVisits", data->visits));
+ tree_update_element_text(tree,
+ element,
+ messages_get_buff("TreeVisits", data->visits));
/* update thumbnail */
@@ -495,15 +464,17 @@
*/
static xmlNode *tree_url_find_xml_element(xmlNode *node, const char *name)
{
- xmlNode *n;
- if (!node)
- return 0;
- for (n = node->children;
- n && !(n->type == XML_ELEMENT_NODE &&
- strcmp((const char *) n->name, name) == 0);
- n = n->next)
+ xmlNode *xmlnode;
+ if (node == NULL)
+ return NULL;
+
+ for (xmlnode = node->children;
+ xmlnode && !(xmlnode->type == XML_ELEMENT_NODE &&
+ strcmp((const char *) xmlnode->name, name) == 0);
+ xmlnode = xmlnode->next)
;
- return n;
+
+ return xmlnode;
}
/**
@@ -513,26 +484,26 @@
* \param directory directory to add this entry to
*/
static void tree_url_load_entry(xmlNode *li, struct tree *tree,
- struct node *directory, tree_node_user_callback callback,
- void *callback_data)
+ struct node *directory, tree_node_user_callback callback,
+ void *callback_data)
{
char *url = NULL, *url1 = NULL;
char *title = NULL;
struct node *entry;
- xmlNode *n;
+ xmlNode *xmlnode;
const struct url_data *data;
url_func_result res;
- for (n = li->children; n; n = n->next) {
+ for (xmlnode = li->children; xmlnode; xmlnode = xmlnode->next) {
/* The li must contain an "a" element */
- if (n->type == XML_ELEMENT_NODE &&
- strcmp((const char *) n->name, "a") == 0) {
- url1 = (char *) xmlGetProp(n, (const xmlChar *) "href");
- title = (char *) xmlNodeGetContent(n);
- }
- }
-
- if (!url1 || !title) {
+ if (xmlnode->type == XML_ELEMENT_NODE &&
+ strcmp((const char *)xmlnode->name, "a") == 0) {
+ url1 = (char *)xmlGetProp(xmlnode, (const xmlChar *) "href");
+ title = (char *)xmlNodeGetContent(xmlnode);
+ }
+ }
+
+ if ((url1 == NULL) || (title == NULL)) {
warn_user("TreeLoadError", "(Missing <a> in <li> or "
"memory exhausted.)");
return;
@@ -583,9 +554,9 @@
if (entry == NULL) {
/** \todo why isn't this fatal? */
warn_user("NoMemory", 0);
- }
- else
+ } else {
tree_update_URL_node(tree, entry, url, data, false);
+ }
xmlFree(title);
@@ -599,43 +570,44 @@
* \param directory directory to add this directory to
*/
static void tree_url_load_directory(xmlNode *ul, struct tree *tree,
- struct node *directory, tree_node_user_callback callback,
- void *callback_data)
+ struct node *directory, tree_node_user_callback callback,
+ void *callback_data)
{
char *title;
struct node *dir;
- xmlNode *n;
-
- assert(ul);
- assert(directory);
-
- for (n = ul->children; n; n = n->next) {
+ xmlNode *xmlnode;
+
+ assert(ul != NULL);
+ assert(directory != NULL);
+
+ for (xmlnode = ul->children; xmlnode; xmlnode = xmlnode->next) {
/* The ul may contain entries as a li, or directories as
* an h4 followed by a ul. Non-element nodes may be present
* (eg. text, comments), and are ignored. */
- if (n->type != XML_ELEMENT_NODE)
+ if (xmlnode->type != XML_ELEMENT_NODE)
continue;
- if (strcmp((const char *) n->name, "li") == 0) {
+ if (strcmp((const char *)xmlnode->name, "li") == 0) {
/* entry */
- tree_url_load_entry(n, tree, directory, callback,
+ tree_url_load_entry(xmlnode, tree, directory, callback,
callback_data);
- } else if (strcmp((const char *) n->name, "h4") == 0) {
+ } else if (strcmp((const char *)xmlnode->name, "h4") == 0) {
/* directory */
- title = (char *) xmlNodeGetContent(n);
+ title = (char *) xmlNodeGetContent(xmlnode );
if (!title) {
warn_user("TreeLoadError", "(Empty <h4> "
"or memory exhausted.)");
return;
}
- for (n = n->next;
- n && n->type != XML_ELEMENT_NODE;
- n = n->next)
+ for (xmlnode = xmlnode->next;
+ xmlnode && xmlnode->type != XML_ELEMENT_NODE;
+ xmlnode = xmlnode->next)
;
- if (!n || strcmp((const char *) n->name, "ul") != 0) {
+ if ((xmlnode == NULL) ||
+ strcmp((const char *)xmlnode->name, "ul") != 0) {
/* next element isn't expected ul */
free(title);
warn_user("TreeLoadError", "(Expected "
@@ -657,7 +629,7 @@
if (folder_icon != NULL)
tree_set_node_icon(tree, dir, folder_icon);
- tree_url_load_directory(n, tree, dir, callback,
+ tree_url_load_directory(xmlnode, tree, dir, callback,
callback_data);
}
}
@@ -728,7 +700,7 @@
const char *text;
li = xmlNewChild(node, NULL, (const xmlChar *) "li", NULL);
- if (!li)
+ if (li == NULL)
return false;
@@ -737,14 +709,15 @@
return false;
a = xmlNewTextChild(li, NULL, (const xmlChar *) "a",
(const xmlChar *) text);
- if (!a)
+ if (a == NULL)
return false;
text = tree_url_node_get_url(entry);
if (text == NULL)
return false;
+
href = xmlNewProp(a, (const xmlChar *) "href", (const xmlChar *) text);
- if (!href)
+ if (href == NULL)
return false;
return true;
}
@@ -762,8 +735,8 @@
xmlNode *ul, *h4;
const char *text;
- ul = xmlNewChild(node, NULL, (const xmlChar *) "ul", NULL);
- if (!ul)
+ ul = xmlNewChild(node, NULL, (const xmlChar *)"ul", NULL);
+ if (ul == NULL)
return false;
for (child = tree_node_get_child(directory); child;
@@ -783,7 +756,7 @@
h4 = xmlNewTextChild(ul, NULL,
(const xmlChar *) "h4",
(const xmlChar *) text);
- if (!h4)
+ if (h4 == NULL)
return false;
if (!tree_url_save_directory(child, ul))
@@ -814,7 +787,8 @@
xmlNode *html, *head, *title, *body;
/* Unfortunately the Browse Hotlist format is invalid HTML,
- * so this is a lie. */
+ * so this is a lie.
+ */
doc = htmlNewDoc(
(const xmlChar *) "http://www.w3.org/TR/html4/strict.dtd",
(const xmlChar *) "-//W3C//DTD HTML 4.01//EN");
12 years, 12 months
r10848 vince - /branches/jmb/treeview-redux/desktop/tree_url_node.c
by netsurf@semichrome.net
Author: vince
Date: Sun Sep 26 16:01:57 2010
New Revision: 10848
URL: http://source.netsurf-browser.org?rev=10848&view=rev
Log:
review comments for url tree
Modified:
branches/jmb/treeview-redux/desktop/tree_url_node.c
Modified: branches/jmb/treeview-redux/desktop/tree_url_node.c
URL: http://source.netsurf-browser.org/branches/jmb/treeview-redux/desktop/tre...
==============================================================================
--- branches/jmb/treeview-redux/desktop/tree_url_node.c (original)
+++ branches/jmb/treeview-redux/desktop/tree_url_node.c Sun Sep 26 16:01:57 2010
@@ -16,11 +16,11 @@
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
-
+
/** \file
* Creation of URL nodes with use of trees (implementation)
*/
-
+
#include <assert.h>
#include <ctype.h>
@@ -38,14 +38,19 @@
#include "utils/url.h"
#include "utils/utils.h"
-#define TREE_ELEMENT_URL 0x01
-#define TREE_ELEMENT_LAST_VISIT 0x02
-#define TREE_ELEMENT_VISITS 0x03
-#define TREE_ELEMENT_THUMBNAIL 0x04
+/** Flags for each type of url tree node. */
+enum tree_element_url {
+ TREE_ELEMENT_URL = 0x01,
+ TREE_ELEMENT_LAST_VISIT = 0x02,
+ TREE_ELEMENT_VISITS = 0x03,
+ TREE_ELEMENT_THUMBNAIL = 0x04,
+};
#define MAX_ICON_NAME_LEN 256
static bool initialised = false;
+
+static hlcache_handle *folder_icon;
struct icon_entry {
content_type type;
@@ -86,34 +91,23 @@
{CONTENT_SVG, NULL},
#endif
{CONTENT_UNKNOWN, NULL},
-
+
/* this serves as a sentinel */
{CONTENT_HTML, NULL}
};
-static hlcache_handle *folder_icon;
-
-static void tree_url_load_directory(xmlNode *ul, struct tree *tree,
- struct node *directory, tree_node_user_callback callback,
- void *callback_data);
-static void tree_url_load_entry(xmlNode *li, struct tree *tree,
- struct node *directory,
- tree_node_user_callback callback, void *callback_data);
-static xmlNode *tree_url_find_xml_element(xmlNode *node, const char *name);
-static bool tree_url_save_directory(struct node *directory, xmlNode *node);
-static bool tree_url_save_entry(struct node *entry, xmlNode *node);
void tree_url_node_init(void)
{
struct icon_entry *entry;
char icon_name[MAX_ICON_NAME_LEN];
-
+
if (initialised || option_tree_icons_dir == NULL)
return;
initialised = true;
-
+
folder_icon = tree_load_icon(tree_directory_icon_name);
-
+
entry = icon_table;
do {
@@ -122,7 +116,7 @@
++entry;
} while (entry->type != CONTENT_HTML);
-
+
}
@@ -137,12 +131,12 @@
*/
struct node *tree_create_URL_node(struct tree *tree, struct node *parent,
const char *url, const char *title,
- tree_node_user_callback user_callback, void *callback_data)
+ tree_node_user_callback user_callback, void *callback_data)
{
struct node *node;
struct node_element *element;
char *text_cp, *squashed;
-
+
squashed = squash_whitespace(title ? title : url);
text_cp = strdup(squashed);
if (text_cp == NULL) {
@@ -152,7 +146,7 @@
}
free(squashed);
node = tree_create_leaf_node(tree, parent, text_cp, true, false,
- false);
+ false);
if (node == NULL) {
free(text_cp);
return NULL;
@@ -160,17 +154,17 @@
if (user_callback != NULL)
tree_set_node_user_callback(node, user_callback,
- callback_data);
-
+ callback_data);
+
tree_create_node_element(node, NODE_ELEMENT_BITMAP,
- TREE_ELEMENT_THUMBNAIL, false);
+ TREE_ELEMENT_THUMBNAIL, false);
tree_create_node_element(node, NODE_ELEMENT_TEXT, TREE_ELEMENT_VISITS,
- false);
+ false);
tree_create_node_element(node, NODE_ELEMENT_TEXT,
- TREE_ELEMENT_LAST_VISIT, false);
+ TREE_ELEMENT_LAST_VISIT, false);
element = tree_create_node_element(node, NODE_ELEMENT_TEXT,
- TREE_ELEMENT_URL, true);
- if (element) {
+ TREE_ELEMENT_URL, true);
+ if (element != NULL) {
text_cp = strdup(url);
if (text_cp == NULL) {
tree_delete_node(tree, node, false);
@@ -198,41 +192,77 @@
*/
struct node *tree_create_URL_node_shared(struct tree *tree, struct node *parent,
const char *url, const struct url_data *data,
- tree_node_user_callback user_callback, void *callback_data)
- {
+ tree_node_user_callback user_callback, void *callback_data)
+{
struct node *node;
struct node_element *element;
const char *title;
assert(url && data);
-
- if (data->title)
+
+ if (data->title != NULL) {
title = data->title;
- else
+ } else {
title = url;
+ }
+
node = tree_create_leaf_node(tree, parent, title, false, false, false);
- if (!node)
+ if (node == NULL)
return NULL;
-
- if (user_callback != NULL)
+
+ if (user_callback != NULL) {
tree_set_node_user_callback(node, user_callback,
- callback_data);
-
+ callback_data);
+ }
+
tree_create_node_element(node, NODE_ELEMENT_BITMAP,
- TREE_ELEMENT_THUMBNAIL, false);
+ TREE_ELEMENT_THUMBNAIL, false);
tree_create_node_element(node, NODE_ELEMENT_TEXT, TREE_ELEMENT_VISITS,
- false);
+ false);
tree_create_node_element(node, NODE_ELEMENT_TEXT,
- TREE_ELEMENT_LAST_VISIT, false);
+ TREE_ELEMENT_LAST_VISIT, false);
element = tree_create_node_element(node, NODE_ELEMENT_TEXT,
- TREE_ELEMENT_URL, false);
- if (element)
+ TREE_ELEMENT_URL, false);
+ if (element != NULL) {
tree_update_node_element(tree, element, url, NULL);
+ }
tree_update_URL_node(tree, node, url, data, true);
return node;
}
+/**
+ * Helper to update the text of a node if it has changed.
+ *
+ * \param element The node element to update.
+ * \param text The text to update the element with. The ownership of
+ * this string is taken by this function and must not be
+ * referred to after the function exits.
+ */
+static bool update_element_text(struct tree *tree,
+ struct node_element *element, char *text)
+{
+ const char *node_text; /* existing node text */
+
+ if (text == NULL)
+ return false;
+
+ if (element == NULL) {
+ free(text);
+ return false;
+ }
+
+ node_text = tree_node_element_get_text(element);
+
+ if ((node_text == NULL) || (strcmp(node_text, text) != 0)) {
+ tree_update_node_element(tree, element, text, NULL);
+ } else {
+ /* text does not need changing, free it */
+ free(text);
+ }
+ return true;
+}
+
/**
* Updates the node details for a URL node.
*
@@ -242,17 +272,16 @@
const char *url, const struct url_data *data, bool shared)
{
struct node_element *element;
- char buffer[256];
struct bitmap *bitmap = NULL;
struct icon_entry *entry;
char *text_cp;
-
- assert(node);
+
+ assert(node != NULL);
element = tree_node_find_element(node, TREE_ELEMENT_URL, NULL);
if (element == NULL)
return;
-
+
if (data != NULL) {
if (data->title == NULL)
urldb_set_url_title(url, url);
@@ -261,10 +290,10 @@
return;
element = tree_node_find_element(node, TREE_ELEMENT_TITLE,
- NULL);
+ NULL);
if (shared)
tree_update_node_element(tree, element, data->title,
- NULL);
+ NULL);
else {
text_cp = strdup(data->title);
if (text_cp == NULL) {
@@ -290,41 +319,28 @@
++entry;
} while (entry->type != CONTENT_HTML);
- element = tree_node_find_element(node, TREE_ELEMENT_LAST_VISIT,
- element);
- if (element != NULL) {
- snprintf(buffer, 256, messages_get("TreeLast"),
- (data->last_visit > 0) ?
- ctime((time_t *)&data->last_visit) :
- messages_get("TreeUnknown"));
- if (data->last_visit > 0)
- buffer[strlen(buffer) - 1] = '\0';
- text_cp = strdup(buffer);
- if (text_cp == NULL) {
- LOG(("malloc failed"));
- warn_user("NoMemory", 0);
- return;
- }
- tree_update_node_element(tree, element, text_cp, NULL);
- }
-
+ /* update last visit text */
+ element = tree_node_find_element(node, TREE_ELEMENT_LAST_VISIT, element);
+ update_element_text(tree,
+ element,
+ messages_get_buff("TreeLast",
+ (data->last_visit > 0) ?
+ ctime((time_t *)&data->last_visit) :
+ messages_get("TreeUnknown")));
+
+
+ /* update number of visits text */
element = tree_node_find_element(node, TREE_ELEMENT_VISITS, element);
- if (element != NULL) {
- snprintf(buffer, 256, messages_get("TreeVisits"),
- data->visits);
- text_cp = strdup(buffer);
- if (text_cp == NULL) {
- LOG(("malloc failed"));
- warn_user("NoMemory", 0);
- return;
- }
- tree_update_node_element(tree, element, text_cp, NULL);
- }
-
+ update_element_text(tree,
+ element,
+ messages_get_buff("TreeVisits", data->visits));
+
+
+ /* update thumbnail */
element = tree_node_find_element(node, TREE_ELEMENT_THUMBNAIL, element);
if (element != NULL) {
bitmap = urldb_get_thumbnail(url);
-
+
if (bitmap != NULL) {
tree_update_node_element(tree, element, NULL, bitmap);
}
@@ -366,7 +382,7 @@
}
node_callback_resp tree_url_node_callback(void *user_data,
- struct node_msg_data *msg_data)
+ struct node_msg_data *msg_data)
{
struct tree *tree;
struct node_element *element;
@@ -375,100 +391,277 @@
char *norm_text, *escaped_text;
const struct url_data *data;
- /* TODO: memory leaks on non-shared folder deletion */
+ /** @todo memory leaks on non-shared folder deletion. */
switch (msg_data->msg) {
- case NODE_DELETE_ELEMENT_TXT:
- switch (msg_data->flag) {
- /* only history is using non-editable url
- * elements so only history deletion will run
- * this code
- */
- case TREE_ELEMENT_URL:
- /* reset URL characteristics */
- urldb_reset_url_visit_data(
- msg_data->data.text);
- return NODE_CALLBACK_HANDLED;
- case TREE_ELEMENT_TITLE:
- return NODE_CALLBACK_HANDLED;
- }
- break;
- case NODE_DELETE_ELEMENT_IMG:
- if (msg_data->flag == TREE_ELEMENT_THUMBNAIL ||
- msg_data->flag == TREE_ELEMENT_TITLE)
- return NODE_CALLBACK_HANDLED;
- break;
- case NODE_LAUNCH:
- element = tree_node_find_element(msg_data->node,
- TREE_ELEMENT_URL, NULL);
- if (element != NULL) {
- text = tree_node_element_get_text(element);
- browser_window_create(text, NULL, 0,
- true, false);
- return NODE_CALLBACK_HANDLED;
- }
- break;
- case NODE_ELEMENT_EDIT_FINISHING:
-
- text = msg_data->data.text;
-
- if (msg_data->flag == TREE_ELEMENT_URL) {
- res = url_escape(text, 0, false, NULL,
- &escaped_text);
- if (res == URL_FUNC_OK)
- res = url_normalize(escaped_text,
- &norm_text);
- if (res != URL_FUNC_OK) {
- if (res == URL_FUNC_FAILED) {
- warn_user("NoURLError", 0);
- return NODE_CALLBACK_CONTINUE;
- }
- else {
- warn_user("NoMemory", 0);
- return NODE_CALLBACK_REJECT;
- }
-
+ case NODE_DELETE_ELEMENT_TXT:
+ switch (msg_data->flag) {
+ /* only history is using non-editable url
+ * elements so only history deletion will run
+ * this code
+ */
+ case TREE_ELEMENT_URL:
+ /* reset URL characteristics */
+ urldb_reset_url_visit_data(
+ msg_data->data.text);
+ return NODE_CALLBACK_HANDLED;
+ case TREE_ELEMENT_TITLE:
+ return NODE_CALLBACK_HANDLED;
+ }
+ break;
+ case NODE_DELETE_ELEMENT_IMG:
+ if (msg_data->flag == TREE_ELEMENT_THUMBNAIL ||
+ msg_data->flag == TREE_ELEMENT_TITLE)
+ return NODE_CALLBACK_HANDLED;
+ break;
+ case NODE_LAUNCH:
+ element = tree_node_find_element(msg_data->node,
+ TREE_ELEMENT_URL, NULL);
+ if (element != NULL) {
+ text = tree_node_element_get_text(element);
+ browser_window_create(text, NULL, 0,
+ true, false);
+ return NODE_CALLBACK_HANDLED;
+ }
+ break;
+ case NODE_ELEMENT_EDIT_FINISHING:
+
+ text = msg_data->data.text;
+
+ if (msg_data->flag == TREE_ELEMENT_URL) {
+ res = url_escape(text, 0, false, NULL,
+ &escaped_text);
+ if (res == URL_FUNC_OK)
+ res = url_normalize(escaped_text,
+ &norm_text);
+ if (res != URL_FUNC_OK) {
+ if (res == URL_FUNC_FAILED) {
+ warn_user("NoURLError", 0);
+ return NODE_CALLBACK_CONTINUE;
}
- msg_data->data.text = norm_text;
-
- data = urldb_get_url_data(norm_text);
- if (data == NULL) {
- urldb_add_url(norm_text);
- urldb_set_url_persistence(norm_text,
- true);
- data = urldb_get_url_data(norm_text);
- if (data == NULL)
- return NODE_CALLBACK_REJECT;
- }
- tree = user_data;
- tree_update_URL_node(tree, msg_data->node,
- norm_text, NULL, false);
- }
- else if (msg_data->flag == TREE_ELEMENT_TITLE) {
- while (isspace(*text))
- text++;
- norm_text = strdup(text);
- if (norm_text == NULL) {
- LOG(("malloc failed"));
+ else {
warn_user("NoMemory", 0);
return NODE_CALLBACK_REJECT;
}
- /* don't allow zero length entry text, return
- false */
- if (norm_text[0] == '\0') {
- warn_user("NoNameError", 0);
- msg_data->data.text = NULL;
- return NODE_CALLBACK_CONTINUE;
- }
- msg_data->data.text = norm_text;
+
}
-
- return NODE_CALLBACK_HANDLED;
- default:
- break;
+ msg_data->data.text = norm_text;
+
+ data = urldb_get_url_data(norm_text);
+ if (data == NULL) {
+ urldb_add_url(norm_text);
+ urldb_set_url_persistence(norm_text,
+ true);
+ data = urldb_get_url_data(norm_text);
+ if (data == NULL)
+ return NODE_CALLBACK_REJECT;
+ }
+ tree = user_data;
+ tree_update_URL_node(tree, msg_data->node,
+ norm_text, NULL, false);
+ }
+ else if (msg_data->flag == TREE_ELEMENT_TITLE) {
+ while (isspace(*text))
+ text++;
+ norm_text = strdup(text);
+ if (norm_text == NULL) {
+ LOG(("malloc failed"));
+ warn_user("NoMemory", 0);
+ return NODE_CALLBACK_REJECT;
+ }
+ /* don't allow zero length entry text, return
+ false */
+ if (norm_text[0] == '\0') {
+ warn_user("NoNameError", 0);
+ msg_data->data.text = NULL;
+ return NODE_CALLBACK_CONTINUE;
+ }
+ msg_data->data.text = norm_text;
+ }
+
+ return NODE_CALLBACK_HANDLED;
+ default:
+ break;
}
return NODE_CALLBACK_NOT_HANDLED;
}
+/**
+ * Search the children of an xmlNode for an element.
+ *
+ * \param node xmlNode to search children of, or 0
+ * \param name name of element to find
+ * \return first child of node which is an element and matches name, or
+ * 0 if not found or parameter node is 0
+ */
+static xmlNode *tree_url_find_xml_element(xmlNode *node, const char *name)
+{
+ xmlNode *n;
+ if (!node)
+ return 0;
+ for (n = node->children;
+ n && !(n->type == XML_ELEMENT_NODE &&
+ strcmp((const char *) n->name, name) == 0);
+ n = n->next)
+ ;
+ return n;
+}
+
+/**
+ * Parse an entry represented as a li.
+ *
+ * \param li xmlNode for parsed li
+ * \param directory directory to add this entry to
+ */
+static void tree_url_load_entry(xmlNode *li, struct tree *tree,
+ struct node *directory, tree_node_user_callback callback,
+ void *callback_data)
+{
+ char *url = NULL, *url1 = NULL;
+ char *title = NULL;
+ struct node *entry;
+ xmlNode *n;
+ const struct url_data *data;
+ url_func_result res;
+
+ for (n = li->children; n; n = n->next) {
+ /* The li must contain an "a" element */
+ if (n->type == XML_ELEMENT_NODE &&
+ strcmp((const char *) n->name, "a") == 0) {
+ url1 = (char *) xmlGetProp(n, (const xmlChar *) "href");
+ title = (char *) xmlNodeGetContent(n);
+ }
+ }
+
+ if (!url1 || !title) {
+ warn_user("TreeLoadError", "(Missing <a> in <li> or "
+ "memory exhausted.)");
+ return;
+ }
+
+ /* We're loading external input.
+ * This may be garbage, so attempt to normalise
+ */
+ res = url_normalize(url1, &url);
+ if (res != URL_FUNC_OK) {
+ LOG(("Failed normalising '%s'", url1));
+
+ if (res == URL_FUNC_NOMEM)
+ warn_user("NoMemory", NULL);
+
+ xmlFree(url1);
+ xmlFree(title);
+
+ return;
+ }
+
+ /* No longer need this */
+ xmlFree(url1);
+
+ data = urldb_get_url_data(url);
+ if (data == NULL) {
+ /* No entry in database, so add one */
+ urldb_add_url(url);
+ /* now attempt to get url data */
+ data = urldb_get_url_data(url);
+ }
+ if (data == NULL) {
+ xmlFree(title);
+ free(url);
+
+ return;
+ }
+
+ /* Make this URL persistent */
+ urldb_set_url_persistence(url, true);
+
+ if (data->title == NULL)
+ urldb_set_url_title(url, title);
+
+ entry = tree_create_URL_node(tree, directory, url, title,
+ callback, callback_data);
+
+ if (entry == NULL) {
+ /** \todo why isn't this fatal? */
+ warn_user("NoMemory", 0);
+ }
+ else
+ tree_update_URL_node(tree, entry, url, data, false);
+
+
+ xmlFree(title);
+ free(url);
+}
+
+/**
+ * Parse a directory represented as a ul.
+ *
+ * \param ul xmlNode for parsed ul
+ * \param directory directory to add this directory to
+ */
+static void tree_url_load_directory(xmlNode *ul, struct tree *tree,
+ struct node *directory, tree_node_user_callback callback,
+ void *callback_data)
+{
+ char *title;
+ struct node *dir;
+ xmlNode *n;
+
+ assert(ul);
+ assert(directory);
+
+ for (n = ul->children; n; n = n->next) {
+ /* The ul may contain entries as a li, or directories as
+ * an h4 followed by a ul. Non-element nodes may be present
+ * (eg. text, comments), and are ignored. */
+
+ if (n->type != XML_ELEMENT_NODE)
+ continue;
+
+ if (strcmp((const char *) n->name, "li") == 0) {
+ /* entry */
+ tree_url_load_entry(n, tree, directory, callback,
+ callback_data);
+
+ } else if (strcmp((const char *) n->name, "h4") == 0) {
+ /* directory */
+ title = (char *) xmlNodeGetContent(n);
+ if (!title) {
+ warn_user("TreeLoadError", "(Empty <h4> "
+ "or memory exhausted.)");
+ return;
+ }
+
+ for (n = n->next;
+ n && n->type != XML_ELEMENT_NODE;
+ n = n->next)
+ ;
+ if (!n || strcmp((const char *) n->name, "ul") != 0) {
+ /* next element isn't expected ul */
+ free(title);
+ warn_user("TreeLoadError", "(Expected "
+ "<ul> not present.)");
+ return;
+ }
+
+ dir = tree_create_folder_node(tree, directory, title,
+ true, false, false);
+ if (dir == NULL) {
+ free(title);
+ return;
+ }
+
+ if (callback != NULL)
+ tree_set_node_user_callback(dir, callback,
+ callback_data);
+
+ if (folder_icon != NULL)
+ tree_set_node_icon(tree, dir, folder_icon);
+
+ tree_url_load_directory(n, tree, dir, callback,
+ callback_data);
+ }
+ }
+}
/**
* Loads an url tree from a specified file.
@@ -478,7 +671,7 @@
* \return the file represented as a tree, or NULL on failure
*/
bool tree_urlfile_load(const char *filename, struct tree *tree,
- tree_node_user_callback callback, void *callback_data)
+ tree_node_user_callback callback, void *callback_data)
{
xmlDoc *doc;
xmlNode *html, *body, *ul;
@@ -486,15 +679,15 @@
FILE *fp = NULL;
if (filename == NULL) {
- return false;
+ return false;
}
fp = fopen(filename, "r");
if (fp == NULL) {
- return false;
+ return false;
}
fclose(fp);
-
+
doc = htmlParseFile(filename, "iso-8859-1");
if (doc == NULL) {
warn_user("TreeLoadError", messages_get("ParsingFail"));
@@ -507,7 +700,7 @@
if (ul == NULL) {
xmlFreeDoc(doc);
warn_user("TreeLoadError",
- "(<html>...<body>...<ul> not found.)");
+ "(<html>...<body>...<ul> not found.)");
return false;
}
@@ -519,186 +712,91 @@
return true;
}
-
-/**
- * Parse a directory represented as a ul.
- *
- * \param ul xmlNode for parsed ul
- * \param directory directory to add this directory to
- */
-void tree_url_load_directory(xmlNode *ul, struct tree *tree,
- struct node *directory, tree_node_user_callback callback,
- void *callback_data)
-{
- char *title;
- struct node *dir;
- xmlNode *n;
-
- assert(ul);
- assert(directory);
-
- for (n = ul->children; n; n = n->next) {
- /* The ul may contain entries as a li, or directories as
- * an h4 followed by a ul. Non-element nodes may be present
- * (eg. text, comments), and are ignored. */
-
- if (n->type != XML_ELEMENT_NODE)
- continue;
-
- if (strcmp((const char *) n->name, "li") == 0) {
+/**
+ * Add an entry to the HTML tree for saving.
+ *
+ * The node must contain a sequence of node_elements in the following order:
+ *
+ * \param entry hotlist entry to add
+ * \param node node to add li to
+ * \return true on success, false on memory exhaustion
+ */
+static bool tree_url_save_entry(struct node *entry, xmlNode *node)
+{
+ xmlNode *li, *a;
+ xmlAttr *href;
+ const char *text;
+
+ li = xmlNewChild(node, NULL, (const xmlChar *) "li", NULL);
+ if (!li)
+ return false;
+
+
+ text = tree_url_node_get_title(entry);
+ if (text == NULL)
+ return false;
+ a = xmlNewTextChild(li, NULL, (const xmlChar *) "a",
+ (const xmlChar *) text);
+ if (!a)
+ return false;
+
+ text = tree_url_node_get_url(entry);
+ if (text == NULL)
+ return false;
+ href = xmlNewProp(a, (const xmlChar *) "href", (const xmlChar *) text);
+ if (!href)
+ return false;
+ return true;
+}
+
+/**
+ * Add a directory to the HTML tree for saving.
+ *
+ * \param directory hotlist directory to add
+ * \param node node to add ul to
+ * \return true on success, false on memory exhaustion
+ */
+static bool tree_url_save_directory(struct node *directory, xmlNode *node)
+{
+ struct node *child;
+ xmlNode *ul, *h4;
+ const char *text;
+
+ ul = xmlNewChild(node, NULL, (const xmlChar *) "ul", NULL);
+ if (!ul)
+ return false;
+
+ for (child = tree_node_get_child(directory); child;
+ child = tree_node_get_next(child)) {
+ if (!tree_node_is_folder(child)) {
/* entry */
- tree_url_load_entry(n, tree, directory, callback,
- callback_data);
-
- } else if (strcmp((const char *) n->name, "h4") == 0) {
+ if (!tree_url_save_entry(child, ul))
+ return false;
+ } else {
/* directory */
- title = (char *) xmlNodeGetContent(n);
- if (!title) {
- warn_user("TreeLoadError", "(Empty <h4> "
- "or memory exhausted.)");
- return;
- }
-
- for (n = n->next;
- n && n->type != XML_ELEMENT_NODE;
- n = n->next)
- ;
- if (!n || strcmp((const char *) n->name, "ul") != 0) {
- /* next element isn't expected ul */
- free(title);
- warn_user("TreeLoadError", "(Expected "
- "<ul> not present.)");
- return;
- }
-
- dir = tree_create_folder_node(tree, directory, title,
- true, false, false);
- if (dir == NULL) {
- free(title);
- return;
- }
-
- if (callback != NULL)
- tree_set_node_user_callback(dir, callback,
- callback_data);
-
- if (folder_icon != NULL)
- tree_set_node_icon(tree, dir, folder_icon);
-
- tree_url_load_directory(n, tree, dir, callback,
- callback_data);
- }
- }
-}
-
-
-/**
- * Parse an entry represented as a li.
- *
- * \param li xmlNode for parsed li
- * \param directory directory to add this entry to
- */
-void tree_url_load_entry(xmlNode *li, struct tree *tree,
- struct node *directory, tree_node_user_callback callback,
- void *callback_data)
-{
- char *url = NULL, *url1 = NULL;
- char *title = NULL;
- struct node *entry;
- xmlNode *n;
- const struct url_data *data;
- url_func_result res;
-
- for (n = li->children; n; n = n->next) {
- /* The li must contain an "a" element */
- if (n->type == XML_ELEMENT_NODE &&
- strcmp((const char *) n->name, "a") == 0) {
- url1 = (char *) xmlGetProp(n, (const xmlChar *) "href");
- title = (char *) xmlNodeGetContent(n);
- }
- }
-
- if (!url1 || !title) {
- warn_user("TreeLoadError", "(Missing <a> in <li> or "
- "memory exhausted.)");
- return;
- }
-
- /* We're loading external input.
- * This may be garbage, so attempt to normalise
- */
- res = url_normalize(url1, &url);
- if (res != URL_FUNC_OK) {
- LOG(("Failed normalising '%s'", url1));
-
- if (res == URL_FUNC_NOMEM)
- warn_user("NoMemory", NULL);
-
- xmlFree(url1);
- xmlFree(title);
-
- return;
- }
-
- /* No longer need this */
- xmlFree(url1);
-
- data = urldb_get_url_data(url);
- if (data == NULL) {
- /* No entry in database, so add one */
- urldb_add_url(url);
- /* now attempt to get url data */
- data = urldb_get_url_data(url);
- }
- if (data == NULL) {
- xmlFree(title);
- free(url);
-
- return;
- }
-
- /* Make this URL persistent */
- urldb_set_url_persistence(url, true);
-
- if (data->title == NULL)
- urldb_set_url_title(url, title);
-
- entry = tree_create_URL_node(tree, directory, url, title,
- callback, callback_data);
-
- if (entry == NULL) {
- /** \todo why isn't this fatal? */
- warn_user("NoMemory", 0);
- }
- else
- tree_update_URL_node(tree, entry, url, data, false);
-
-
- xmlFree(title);
- free(url);
-}
-
-
-/**
- * Search the children of an xmlNode for an element.
- *
- * \param node xmlNode to search children of, or 0
- * \param name name of element to find
- * \return first child of node which is an element and matches name, or
- * 0 if not found or parameter node is 0
- */
-xmlNode *tree_url_find_xml_element(xmlNode *node, const char *name)
-{
- xmlNode *n;
- if (!node)
- return 0;
- for (n = node->children;
- n && !(n->type == XML_ELEMENT_NODE &&
- strcmp((const char *) n->name, name) == 0);
- n = n->next)
- ;
- return n;
-}
+ /* invalid HTML */
+
+ text = tree_url_node_get_title(child);
+ if (text == NULL)
+ return false;
+
+ h4 = xmlNewTextChild(ul, NULL,
+ (const xmlChar *) "h4",
+ (const xmlChar *) text);
+ if (!h4)
+ return false;
+
+ if (!tree_url_save_directory(child, ul))
+ return false;
+ } }
+
+ return true;
+}
+
+
+
+
+
@@ -709,7 +807,7 @@
* \param page_title title of the page
*/
bool tree_urlfile_save(struct tree *tree, const char *filename,
- const char *page_title)
+ const char *page_title)
{
int res;
xmlDoc *doc;
@@ -741,7 +839,7 @@
}
title = xmlNewTextChild(head, NULL, (const xmlChar *) "title",
- (const xmlChar *) page_title);
+ (const xmlChar *) page_title);
if (title == NULL) {
warn_user("NoMemory", 0);
xmlFreeDoc(doc);
@@ -772,86 +870,3 @@
xmlFreeDoc(doc);
return true;
}
-
-
-/**
- * Add a directory to the HTML tree for saving.
- *
- * \param directory hotlist directory to add
- * \param node node to add ul to
- * \return true on success, false on memory exhaustion
- */
-bool tree_url_save_directory(struct node *directory, xmlNode *node)
-{
- struct node *child;
- xmlNode *ul, *h4;
- const char *text;
-
- ul = xmlNewChild(node, NULL, (const xmlChar *) "ul", NULL);
- if (!ul)
- return false;
-
- for (child = tree_node_get_child(directory); child;
- child = tree_node_get_next(child)) {
- if (!tree_node_is_folder(child)) {
- /* entry */
- if (!tree_url_save_entry(child, ul))
- return false;
- } else {
- /* directory */
- /* invalid HTML */
-
- text = tree_url_node_get_title(child);
- if (text == NULL)
- return false;
-
- h4 = xmlNewTextChild(ul, NULL,
- (const xmlChar *) "h4",
- (const xmlChar *) text);
- if (!h4)
- return false;
-
- if (!tree_url_save_directory(child, ul))
- return false;
- } }
-
- return true;
-}
-
-
-/**
- * Add an entry to the HTML tree for saving.
- *
- * The node must contain a sequence of node_elements in the following order:
- *
- * \param entry hotlist entry to add
- * \param node node to add li to
- * \return true on success, false on memory exhaustion
- */
-bool tree_url_save_entry(struct node *entry, xmlNode *node)
-{
- xmlNode *li, *a;
- xmlAttr *href;
- const char *text;
-
- li = xmlNewChild(node, NULL, (const xmlChar *) "li", NULL);
- if (!li)
- return false;
-
-
- text = tree_url_node_get_title(entry);
- if (text == NULL)
- return false;
- a = xmlNewTextChild(li, NULL, (const xmlChar *) "a",
- (const xmlChar *) text);
- if (!a)
- return false;
-
- text = tree_url_node_get_url(entry);
- if (text == NULL)
- return false;
- href = xmlNewProp(a, (const xmlChar *) "href", (const xmlChar *) text);
- if (!href)
- return false;
- return true;
-}
12 years, 12 months
r10847 chris_y - in /branches/jmb/treeview-redux/amiga: gui.c hotlist.c hotlist.h
by netsurf@semichrome.net
Author: chris_y
Date: Sun Sep 26 15:21:55 2010
New Revision: 10847
URL: http://source.netsurf-browser.org?rev=10847&view=rev
Log:
Don't probe options from hotlist.c
Modified:
branches/jmb/treeview-redux/amiga/gui.c
branches/jmb/treeview-redux/amiga/hotlist.c
branches/jmb/treeview-redux/amiga/hotlist.h
Modified: branches/jmb/treeview-redux/amiga/gui.c
URL: http://source.netsurf-browser.org/branches/jmb/treeview-redux/amiga/gui.c...
==============================================================================
--- branches/jmb/treeview-redux/amiga/gui.c (original)
+++ branches/jmb/treeview-redux/amiga/gui.c Sun Sep 26 15:21:55 2010
@@ -564,7 +564,7 @@
ami_get_theme_filename(&tree_directory_icon_name,"theme_list_folder",true);
ami_get_theme_filename(&tree_content_icon_name,"theme_list_content",true);
- ami_hotlist_initialise();
+ ami_hotlist_initialise(option_hotlist_file);
ami_cookies_initialise();
ami_global_history_initialise();
sslcert_init();
@@ -1998,7 +1998,7 @@
urldb_save(option_url_file);
urldb_save_cookies(option_cookie_file);
- ami_hotlist_free();
+ ami_hotlist_free(option_hotlist_file);
ami_cookies_free();
ami_global_history_free();
sslcert_cleanup();
Modified: branches/jmb/treeview-redux/amiga/hotlist.c
URL: http://source.netsurf-browser.org/branches/jmb/treeview-redux/amiga/hotli...
==============================================================================
--- branches/jmb/treeview-redux/amiga/hotlist.c (original)
+++ branches/jmb/treeview-redux/amiga/hotlist.c Sun Sep 26 15:21:55 2010
@@ -19,22 +19,21 @@
#include <proto/exec.h>
#include "amiga/hotlist.h"
#include "desktop/hotlist.h"
-#include "amiga/options.h"
#include "amiga/tree.h"
-void ami_hotlist_initialise(void)
+void ami_hotlist_initialise(const char *hotlist_file)
{
hotlist_window = ami_tree_create(hotlist_get_tree_flags(), NULL);
if(!hotlist_window) return;
hotlist_initialise(ami_tree_get_tree(hotlist_window),
- option_hotlist_file);
+ hotlist_file);
}
-void ami_hotlist_free()
+void ami_hotlist_free(const char *hotlist_file)
{
- hotlist_cleanup(option_hotlist_file);
+ hotlist_cleanup(hotlist_file);
ami_tree_destroy(hotlist_window);
hotlist_window = NULL;
}
Modified: branches/jmb/treeview-redux/amiga/hotlist.h
URL: http://source.netsurf-browser.org/branches/jmb/treeview-redux/amiga/hotli...
==============================================================================
--- branches/jmb/treeview-redux/amiga/hotlist.h (original)
+++ branches/jmb/treeview-redux/amiga/hotlist.h Sun Sep 26 15:21:55 2010
@@ -21,8 +21,8 @@
#include "desktop/tree.h"
#include "amiga/tree.h"
-void ami_hotlist_initialise(void);
-void ami_hotlist_free(void);
+void ami_hotlist_initialise(const char *hotlist_file);
+void ami_hotlist_free(const char *hotlist_file);
struct treeview_window *hotlist_window;
#endif
12 years, 12 months