[vlc-commits] input: add input_item_node_Sort
Thomas Guillem
git at videolan.org
Wed May 20 16:10:25 CEST 2015
vlc | branch: master | Thomas Guillem <thomas at gllm.fr> | Wed May 20 15:14:02 2015 +0200| [0b79f865b6e49194f156e693135aaf561cb4ba22] | committer: Thomas Guillem
input: add input_item_node_Sort
Sort all p_item children of the node recursively.
> http://git.videolan.org/gitweb.cgi/vlc.git/?a=commit;h=0b79f865b6e49194f156e693135aaf561cb4ba22
---
include/vlc_input_item.h | 9 +++++++++
src/input/item.c | 46 ++++++++++++++++++++++++++++++++++++++++++++++
src/libvlccore.sym | 1 +
3 files changed, 56 insertions(+)
diff --git a/include/vlc_input_item.h b/include/vlc_input_item.h
index 48dcd32..60dce6e 100644
--- a/include/vlc_input_item.h
+++ b/include/vlc_input_item.h
@@ -113,12 +113,15 @@ enum input_item_type_e
ITEM_TYPE_NUMBER
};
+typedef int (*input_item_compar_cb)( input_item_t *, input_item_t * );
+
struct input_item_node_t
{
input_item_t * p_item;
int i_children;
input_item_node_t **pp_children;
input_item_node_t *p_parent;
+ input_item_compar_cb compar_cb;
};
VLC_API void input_item_CopyOptions( input_item_t *p_parent, input_item_t *p_child );
@@ -154,6 +157,12 @@ VLC_API input_item_node_t * input_item_node_AppendItem( input_item_node_t *p_nod
VLC_API void input_item_node_AppendNode( input_item_node_t *p_parent, input_item_node_t *p_child );
/**
+ * Sort all p_item children of the node recursively.
+ */
+VLC_API void input_item_node_Sort( input_item_node_t *p_node,
+ input_item_compar_cb compar_cb );
+
+/**
* Delete a node created with input_item_node_Create() and all its children.
*/
VLC_API void input_item_node_Delete( input_item_node_t *p_node );
diff --git a/src/input/item.c b/src/input/item.c
index d357c25..10e7216 100644
--- a/src/input/item.c
+++ b/src/input/item.c
@@ -1160,6 +1160,52 @@ void input_item_node_AppendNode( input_item_node_t *p_parent, input_item_node_t
p_child->p_parent = p_parent;
}
+static int compar_node( const void *p1, const void *p2 )
+{
+ input_item_node_t *p_node1 = *((input_item_node_t **) p1);
+ input_item_node_t *p_node2 = *((input_item_node_t **) p2);
+
+ assert( p_node1->p_parent && p_node1->p_parent == p_node2->p_parent &&
+ p_node1->p_parent->compar_cb );
+
+ input_item_compar_cb compar_cb = p_node1->p_parent->compar_cb;
+ return compar_cb( p_node1->p_item, p_node2->p_item );
+}
+
+static void sort_subitems( input_item_node_t *p_node,
+ input_item_compar_cb compar_cb )
+{
+ if( p_node->i_children < 0 || !compar_cb )
+ return;
+
+ p_node->compar_cb = compar_cb;
+
+ /* Lock first all children. This avoids to lock/unlock them from each
+ * compar callback call */
+ for( int i = 0; i < p_node->i_children; i++ )
+ vlc_mutex_lock( &p_node->pp_children[i]->p_item->lock );
+
+ /* Sort current node */
+ qsort( p_node->pp_children, p_node->i_children,
+ sizeof(input_item_node_t *), compar_node );
+
+ /* Unlock all children */
+ for( int i = 0; i < p_node->i_children; i++ )
+ vlc_mutex_unlock( &p_node->pp_children[i]->p_item->lock );
+
+ p_node->compar_cb = NULL;
+
+ /* Sort all children */
+ for( int i = 0; i < p_node->i_children; i++ )
+ sort_subitems( p_node->pp_children[i], compar_cb );
+}
+
+void input_item_node_Sort( input_item_node_t *p_node,
+ input_item_compar_cb compar_cb )
+{
+ sort_subitems( p_node, compar_cb );
+}
+
void input_item_node_PostAndDelete( input_item_node_t *p_root )
{
post_subitems( p_root );
diff --git a/src/libvlccore.sym b/src/libvlccore.sym
index 5350f96..86a3a82 100644
--- a/src/libvlccore.sym
+++ b/src/libvlccore.sym
@@ -208,6 +208,7 @@ input_item_node_AppendNode
input_item_node_Create
input_item_node_Delete
input_item_node_PostAndDelete
+input_item_node_Sort
input_item_PostSubItem
input_item_ReplaceInfos
input_item_SetDuration
More information about the vlc-commits
mailing list