/*****************************************************************************
- * VLCMediaList.m: VLC.framework VLCMediaList implementation
+ * VLCMediaListAspect.m: VLCKit.framework VLCMediaListAspect implementation
*****************************************************************************
* Copyright (C) 2007 Pierre d'Herbemont
* Copyright (C) 2007 the VideoLAN team
@end
@implementation VLCMediaListAspectNode
+- (id)init
+{
+ if(self = [super init])
+ {
+ media = nil;
+ children = nil;
+ }
+ return self;
+}
+- (void)dealloc
+{
+ [media release];
+ [children release];
+ [super dealloc];
+}
+
@synthesize media;
@synthesize children;
- (BOOL)isLeaf
{
- return self.children == NULL;
+ return self.children == nil;
}
--(void)dealloc
-{
- [self.children release];
- [super dealloc];
-}
@end
@implementation VLCMediaListAspect (KeyValueCodingCompliance)
/* For the @"media" key */
-- (int) countOfMedia
+- (NSInteger) countOfMedia
{
return [cachedNode count];
}
-- (id) objectInMediaAtIndex:(int)i
+- (id) objectInMediaAtIndex:(NSInteger)i
{
return [[cachedNode objectAtIndex:i] media];
}
/* For the @"node" key */
-- (int) countOfNode
+- (NSInteger) countOfNode
{
return [cachedNode count];
}
-- (id) objectInNodeAtIndex:(int)i
+- (id) objectInNodeAtIndex:(NSInteger)i
{
return [cachedNode objectAtIndex:i];
}
{
NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init];
id self = user_data;
- [[VLCEventManager sharedManager] callOnMainThreadObject:self
- withMethod:@selector(mediaListViewItemAdded:)
+ [[VLCEventManager sharedManager] callOnMainThreadObject:self
+ withMethod:@selector(mediaListViewItemAdded:)
withArgumentAsObject:[NSArray arrayWithObject:[NSDictionary dictionaryWithObjectsAndKeys:
[VLCMedia mediaWithLibVLCMediaDescriptor:event->u.media_list_item_added.item], @"media",
[NSNumber numberWithInt:event->u.media_list_item_added.index], @"index",
{
NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init];
id self = user_data;
- [[VLCEventManager sharedManager] callOnMainThreadObject:self
- withMethod:@selector(mediaListViewItemRemoved:)
+ [[VLCEventManager sharedManager] callOnMainThreadObject:self
+ withMethod:@selector(mediaListViewItemRemoved:)
withArgumentAsObject:[NSNumber numberWithInt:event->u.media_list_item_deleted.index]];
[pool release];
}
[parentMediaList release];
[super dealloc];
}
+
+- (void)release
+{
+ @synchronized(self)
+ {
+ if([self retainCount] <= 1)
+ {
+ /* We must make sure we won't receive new event after an upcoming dealloc
+ * We also may receive a -retain in some event callback that may occcur
+ * Before libvlc_event_detach. So this can't happen in dealloc */
+ libvlc_event_manager_t * p_em = libvlc_media_list_view_event_manager(p_mlv);
+ libvlc_event_detach(p_em, libvlc_MediaListViewItemDeleted, HandleMediaListViewItemDeleted, self);
+ libvlc_event_detach(p_em, libvlc_MediaListViewItemAdded, HandleMediaListViewItemAdded, self);
+ }
+ [super release];
+ }
+}
+
- (NSString *)description
{
NSMutableString * content = [NSMutableString string];
- int i;
+ NSUInteger i;
for( i = 0; i < [self count]; i++)
{
[content appendFormat:@"%@\n", [self mediaAtIndex: i]];
return [NSString stringWithFormat:@"<%@ %p> {\n%@}", [self className], self, content];
}
-- (VLCMedia *)mediaAtIndex:(int)index
+- (VLCMedia *)mediaAtIndex:(NSInteger)index
{
libvlc_exception_t p_e;
libvlc_exception_init( &p_e );
- libvlc_media_descriptor_t * p_md = libvlc_media_list_view_item_at_index( p_mlv, index, &p_e );
+ libvlc_media_t * p_md = libvlc_media_list_view_item_at_index( p_mlv, index, &p_e );
catch_exception( &p_e );
-
- // Returns local object for media descriptor, searchs for user data first. If not found it creates a
+
+ // Returns local object for media descriptor, searchs for user data first. If not found it creates a
// new cocoa object representation of the media descriptor.
return [VLCMedia mediaWithLibVLCMediaDescriptor:p_md];
}
-- (VLCMediaListAspect *)childrenAtIndex:(int)index
+- (VLCMediaListAspect *)childrenAtIndex:(NSInteger)index
{
libvlc_exception_t p_e;
libvlc_exception_init( &p_e );
if( !p_sub_mlv )
return nil;
- // Returns local object for media descriptor, searchs for user data first. If not found it creates a
+ // Returns local object for media descriptor, searchs for user data first. If not found it creates a
// new cocoa object representation of the media descriptor.
return [VLCMediaListAspect mediaListAspectWithLibVLCMediaListView:p_sub_mlv];
}
-- (VLCMediaListAspectNode *)nodeAtIndex:(int)index
+- (VLCMediaListAspectNode *)nodeAtIndex:(NSInteger)index
{
VLCMediaListAspectNode * node = [[[VLCMediaListAspectNode alloc] init] autorelease];
[node setMedia:[self mediaAtIndex: index]];
+ libvlc_media_list_view_t * p_sub_mlv = libvlc_media_list_view_children_for_item([self libVLCMediaListView], [node.media libVLCMediaDescriptor], NULL);
+ if( p_sub_mlv )
+ {
+ [node setChildren:[VLCMediaListAspect mediaListAspectWithLibVLCMediaListView: p_sub_mlv]];
+ libvlc_media_list_view_release(p_sub_mlv);
+ }
return node;
}
-- (int)count
+- (NSInteger)count
{
libvlc_exception_t p_e;
libvlc_exception_init( &p_e );
- int result = libvlc_media_list_view_count( p_mlv, &p_e );
+ NSInteger result = libvlc_media_list_view_count( p_mlv, &p_e );
catch_exception( &p_e );
return result;
libvlc_media_list_t * p_mlist;
p_mlist = libvlc_media_list_view_parent_media_list( p_mlv, NULL );
libvlc_media_list_lock( p_mlist );
- int i, count = libvlc_media_list_view_count(p_mlv, NULL);
+ NSUInteger i, count = libvlc_media_list_view_count(p_mlv, NULL);
for( i = 0; i < count; i++ )
{
- libvlc_media_descriptor_t * p_md = libvlc_media_list_view_item_at_index(p_mlv, i, NULL);
+ libvlc_media_t * p_md = libvlc_media_list_view_item_at_index(p_mlv, i, NULL);
libvlc_media_list_view_t * p_sub_mlv = libvlc_media_list_view_children_at_index(p_mlv, i, NULL);
VLCMediaListAspectNode * node = [[[VLCMediaListAspectNode alloc] init] autorelease];
[node setMedia:[VLCMedia mediaWithLibVLCMediaDescriptor: p_md]];
[node setChildren: p_sub_mlv ? [VLCMediaListAspect mediaListAspectWithLibVLCMediaListView: p_sub_mlv] : nil];
+ if( p_sub_mlv ) NSAssert(![node isLeaf], @"Not leaf");
+
[cachedNode addObject:node];
- libvlc_media_descriptor_release(p_md);
+ libvlc_media_release(p_md);
if( p_sub_mlv ) libvlc_media_list_view_release(p_sub_mlv);
}
[self initInternalMediaListView];
@implementation VLCMediaListAspect (Private)
- (void)initInternalMediaListView
{
- libvlc_exception_t e;
- libvlc_exception_init( &e );
-
- libvlc_event_manager_t * p_em = libvlc_media_list_event_manager( p_mlv, &e );
+ libvlc_event_manager_t * p_em = libvlc_media_list_event_manager(p_mlv);
/* Add internal callback */
- libvlc_event_attach( p_em, libvlc_MediaListViewItemAdded, HandleMediaListViewItemAdded, self, &e );
- libvlc_event_attach( p_em, libvlc_MediaListViewItemDeleted, HandleMediaListViewItemDeleted, self, &e );
- catch_exception( &e );
+ libvlc_event_attach(p_em, libvlc_MediaListViewItemAdded, HandleMediaListViewItemAdded, self);
+ libvlc_event_attach(p_em, libvlc_MediaListViewItemDeleted, HandleMediaListViewItemDeleted, self);
}
- (void)mediaListViewItemAdded:(NSArray *)arrayOfArgs
NSAssert([NSThread isMainThread], @"We are not on main thread");
/* We hope to receive index in a nide range, that could change one day */
- int start = [[[arrayOfArgs objectAtIndex: 0] objectForKey:@"index"] intValue];
- int end = [[[arrayOfArgs objectAtIndex: [arrayOfArgs count]-1] objectForKey:@"index"] intValue];
+ NSInteger start = [[[arrayOfArgs objectAtIndex: 0] objectForKey:@"index"] intValue];
+ NSInteger end = [[[arrayOfArgs objectAtIndex: [arrayOfArgs count]-1] objectForKey:@"index"] intValue];
NSRange range = NSMakeRange(start, end-start);
[self willChange:NSKeyValueChangeInsertion valuesAtIndexes:[NSIndexSet indexSetWithIndexesInRange:range] forKey:@"media"];
[self willChange:NSKeyValueChangeInsertion valuesAtIndexes:[NSIndexSet indexSetWithIndexesInRange:range] forKey:@"node"];
for( NSDictionary * args in arrayOfArgs )
{
- int index = [[args objectForKey:@"index"] intValue];
+ NSInteger index = [[args objectForKey:@"index"] intValue];
VLCMedia * media = [args objectForKey:@"media"];
VLCMediaListAspectNode * node = [[[VLCMediaListAspectNode alloc] init] autorelease];
[node setMedia:media];
- [node setChildren:[self childrenAtIndex:index]];
+
+ /* Set the sub media list view we enventually have */
+ libvlc_media_list_view_t * p_sub_mlv = libvlc_media_list_view_children_for_item([self libVLCMediaListView], [media libVLCMediaDescriptor], NULL);
+
+ if( p_sub_mlv )
+ {
+ [node setChildren:[VLCMediaListAspect mediaListAspectWithLibVLCMediaListView: p_sub_mlv]];
+ libvlc_media_list_view_release(p_sub_mlv);
+ NSAssert(![node isLeaf], @"Not leaf");
+ }
+
/* Sanity check */
if( index && index > [cachedNode count] )
index = [cachedNode count];