1
0
mirror of https://github.com/gryf/wmaker.git synced 2025-12-19 04:20:27 +01:00

Finished the generic tree node data type

This commit is contained in:
dan
2001-01-18 16:59:15 +00:00
parent bb886be82e
commit 6a3b06e609
2 changed files with 187 additions and 97 deletions

View File

@@ -582,23 +582,37 @@ WMTreeNode* WMCreateTreeNodeWithDestructor(void *data, WMFreeDataProc *destructo
WMTreeNode* WMInsertItemInTree(WMTreeNode *parent, int index, void *item);
WMTreeNode* WMAddItemToTree(WMTreeNode *parent, void *item);
#define WMAddItemToTree(parent, item) WMInsertItemInTree(parent, -1, item)
WMTreeNode* WMInsertNodeInTree(WMTreeNode *parent, int index, WMTreeNode *node);
WMTreeNode* WMInsertNodeInTree(WMTreeNode *parent, int index, WMTreeNode *aNode);
WMTreeNode* WMAddNodeToTree(WMTreeNode *parent, WMTreeNode *node);
#define WMAddNodeToTree(parent, aNode) WMInsertNodeInTree(parent, -1, aNode)
int WMGetTreeNodeDepth(WMTreeNode *node);
void WMDestroyTreeNode(WMTreeNode *aNode);
void WMDestroyTreeNode(WMTreeNode *node);
void WMDeleteLeafForTreeNode(WMTreeNode *aNode, int index);
void* WMGetDataForTreeNode(WMTreeNode *node);
void WMRemoveLeafForTreeNode(WMTreeNode *aNode, void *leaf);
WMTreeNode* WMGetParentForTreeNode(WMTreeNode *node);
void* WMReplaceDataForTreeNode(WMTreeNode *aNode, void *newData);
void WMSortLeavesForTreeNode(WMTreeNode *node, WMCompareDataProc *comparer);
void* WMGetDataForTreeNode(WMTreeNode *aNode);
void WMSortTree(WMTreeNode *root, WMCompareDataProc *comparer);
int WMGetTreeNodeDepth(WMTreeNode *aNode);
WMTreeNode* WMGetParentForTreeNode(WMTreeNode *aNode);
/* Sort only the leaves of the passed node */
void WMSortLeavesForTreeNode(WMTreeNode *aNode, WMCompareDataProc *comparer);
/* Sort all tree recursively starting from the passed node */
void WMSortTree(WMTreeNode *aNode, WMCompareDataProc *comparer);
/* Returns the first node which matches node's data with cdata by 'match' */
WMTreeNode* WMFindInTree(WMTreeNode *aTree, WMMatchDataProc *match, void *cdata);
/* Returns first tree node that has data == cdata */
#define WMGetFirstInTree(aTree, cdata) WMFindInTree(atree, NULL, cdata)
/*--------------------------------------------------------------------------*/

View File

@@ -22,18 +22,19 @@ typedef struct W_TreeNode {
void
destroyNode(void *data)
{
WMTreeNode *node = (WMTreeNode*) data;
WMTreeNode *aNode = (WMTreeNode*) data;
if (node->destructor) {
(*node->destructor)(node->data);
if (aNode->destructor) {
(*aNode->destructor)(aNode->data);
}
if (node->leaves) {
WMFreeArray(node->leaves);
if (aNode->leaves) {
WMFreeArray(aNode->leaves);
}
wfree(node);
wfree(aNode);
}
@@ -47,157 +48,232 @@ WMCreateTreeNode(void *data)
WMTreeNode*
WMCreateTreeNodeWithDestructor(void *data, WMFreeDataProc *destructor)
{
WMTreeNode *node;
WMTreeNode *aNode;
node = (WMTreeNode*) wmalloc(sizeof(W_TreeNode));
memset(node, 0, sizeof(W_TreeNode));
aNode = (WMTreeNode*) wmalloc(sizeof(W_TreeNode));
memset(aNode, 0, sizeof(W_TreeNode));
node->destructor = destructor;
aNode->destructor = destructor;
node->data = data;
node->parent = NULL;
node->depth = 0;
node->leaves = WMCreateArrayWithDestructor(1, destroyNode);
aNode->data = data;
aNode->parent = NULL;
aNode->depth = 0;
aNode->leaves = NULL;
/*aNode->leaves = WMCreateArrayWithDestructor(1, destroyNode);*/
return node;
return aNode;
}
WMTreeNode*
WMInsertItemInTree(WMTreeNode *parent, int index, void *item)
{
WMTreeNode *node;
WMTreeNode *aNode;
wassertrv(parent!=NULL, NULL);
node = WMCreateTreeNodeWithDestructor(item, parent->destructor);
node->parent = parent;
node->depth = parent->depth+1;
if (index < 0 || index > WMGetArrayItemCount(parent->leaves)) {
WMAddToArray(parent->leaves, node);
aNode = WMCreateTreeNodeWithDestructor(item, parent->destructor);
aNode->parent = parent;
aNode->depth = parent->depth+1;
if (!parent->leaves) {
parent->leaves = WMCreateArrayWithDestructor(1, destroyNode);
}
if (index < 0) {
WMAddToArray(parent->leaves, aNode);
} else {
WMInsertInArray(parent->leaves, index, node);
WMInsertInArray(parent->leaves, index, aNode);
}
return node;
}
WMTreeNode*
WMAddItemToTree(WMTreeNode *parent, void *item)
{
WMTreeNode *node;
wassertrv(parent!=NULL, NULL);
node = WMCreateTreeNodeWithDestructor(item, parent->destructor);
node->parent = parent;
node->depth = parent->depth+1;
WMAddToArray(parent->leaves, node);
return node;
return aNode;
}
static void
updateNodeDepth(WMTreeNode *node, int depth)
updateNodeDepth(WMTreeNode *aNode, int depth)
{
int i;
node->depth = depth;
for (i=0; i<WMGetArrayItemCount(node->leaves); i++) {
updateNodeDepth(WMGetFromArray(node->leaves, i), depth+1);
aNode->depth = depth;
if (aNode->leaves) {
for (i=0; i<WMGetArrayItemCount(aNode->leaves); i++) {
updateNodeDepth(WMGetFromArray(aNode->leaves, i), depth+1);
}
}
}
WMTreeNode*
WMInsertNodeInTree(WMTreeNode *parent, int index, WMTreeNode *node)
WMInsertNodeInTree(WMTreeNode *parent, int index, WMTreeNode *aNode)
{
wassertrv(parent!=NULL, NULL);
wassertrv(node!=NULL, NULL);
wassertrv(aNode!=NULL, NULL);
node->parent = parent;
updateNodeDepth(node, parent->depth+1);
if (index < 0 || index > WMGetArrayItemCount(parent->leaves)) {
WMAddToArray(parent->leaves, node);
aNode->parent = parent;
updateNodeDepth(aNode, parent->depth+1);
if (!parent->leaves) {
parent->leaves = WMCreateArrayWithDestructor(1, destroyNode);
}
if (index < 0) {
WMAddToArray(parent->leaves, aNode);
} else {
WMInsertInArray(parent->leaves, index, node);
WMInsertInArray(parent->leaves, index, aNode);
}
return node;
}
WMTreeNode*
WMAddNodeToTree(WMTreeNode *parent, WMTreeNode *node)
{
wassertrv(parent!=NULL, NULL);
wassertrv(node!=NULL, NULL);
node->parent = parent;
updateNodeDepth(node, parent->depth+1);
WMAddToArray(parent->leaves, node);
return node;
}
int
WMGetTreeNodeDepth(WMTreeNode *node)
{
return node->depth;
return aNode;
}
void
WMDestroyTreeNode(WMTreeNode *node)
WMDestroyTreeNode(WMTreeNode *aNode)
{
destroyNode(node);
wassertr(aNode!=NULL);
if (aNode->parent && aNode->parent->leaves) {
WMRemoveFromArray(aNode->parent->leaves, aNode);
} else {
destroyNode(aNode);
}
}
void
WMDeleteLeafForTreeNode(WMTreeNode *aNode, int index)
{
wassertr(aNode!=NULL);
wassertr(aNode->leaves!=NULL);
WMDeleteFromArray(aNode->leaves, index);
}
static int
sameData(void *item, void *data)
{
return (((WMTreeNode*)item)->data == data);
}
void
WMRemoveLeafForTreeNode(WMTreeNode *aNode, void *leaf)
{
int index;
wassertr(aNode!=NULL);
wassertr(aNode->leaves!=NULL);
index = WMFindInArray(aNode->leaves, sameData, leaf);
if (index != WANotFound) {
WMDeleteFromArray(aNode->leaves, index);
}
}
void*
WMGetDataForTreeNode(WMTreeNode *node)
WMReplaceDataForTreeNode(WMTreeNode *aNode, void *newData)
{
return node->data;
void *old;
wassertrv(aNode!=NULL, NULL);
old = aNode->data;
aNode->data = newData;
return old;
}
void*
WMGetDataForTreeNode(WMTreeNode *aNode)
{
return aNode->data;
}
int
WMGetTreeNodeDepth(WMTreeNode *aNode)
{
return aNode->depth;
}
WMTreeNode*
WMGetParentForTreeNode(WMTreeNode *node)
WMGetParentForTreeNode(WMTreeNode *aNode)
{
return node->parent;
return aNode->parent;
}
void
WMSortLeavesForTreeNode(WMTreeNode *node, WMCompareDataProc *comparer)
WMSortLeavesForTreeNode(WMTreeNode *aNode, WMCompareDataProc *comparer)
{
wassertr(node!=NULL);
wassertr(aNode!=NULL);
WMSortArray(node->leaves, comparer);
if (aNode->leaves) {
WMSortArray(aNode->leaves, comparer);
}
}
static void
sortLeavesForNode(WMTreeNode *node, WMCompareDataProc *comparer)
sortLeavesForNode(WMTreeNode *aNode, WMCompareDataProc *comparer)
{
int i;
WMSortArray(node->leaves, comparer);
for (i=0; i<WMGetArrayItemCount(node->leaves); i++) {
sortLeavesForNode(WMGetFromArray(node->leaves, i), comparer);
if (!aNode->leaves)
return;
WMSortArray(aNode->leaves, comparer);
for (i=0; i<WMGetArrayItemCount(aNode->leaves); i++) {
sortLeavesForNode(WMGetFromArray(aNode->leaves, i), comparer);
}
}
void
WMSortTree(WMTreeNode *root, WMCompareDataProc *comparer)
WMSortTree(WMTreeNode *aNode, WMCompareDataProc *comparer)
{
wassertr(root!=NULL);
wassertr(aNode!=NULL);
sortLeavesForNode(root, comparer);
sortLeavesForNode(aNode, comparer);
}
static WMTreeNode*
findNodeInTree(WMTreeNode *aNode, WMMatchDataProc *match, void *cdata)
{
if (match==NULL) {
if (aNode->data == cdata) {
return aNode;
}
} else {
if ((*match)(aNode->data, cdata)) {
return aNode;
}
}
if (aNode->leaves) {
WMTreeNode *leaf;
int i;
for (i=0; i<WMGetArrayItemCount(aNode->leaves); i++) {
leaf = findNodeInTree(WMGetFromArray(aNode->leaves, i), match, cdata);
if (leaf) {
return leaf;
}
}
}
return NULL;
}
WMTreeNode*
WMFindInTree(WMTreeNode *aTree, WMMatchDataProc *match, void *cdata)
{
wassertrv(aTree!=NULL, NULL);
return findNodeInTree(aTree, match, cdata);
}