X-Git-Url: https://git.sesse.net/?a=blobdiff_plain;f=modules%2Fgui%2Fmacosx%2Fprefs.m;h=cce4386f19e6e037f24e76dfe435c58813baafc3;hb=6ee1e193fd896ab9a4729fde14f009d9ce629815;hp=928efce5abc6d83672a59bfe277ab7862cf7213b;hpb=fa95d6e996e1913209a6e0a01aacc384285c64b8;p=vlc diff --git a/modules/gui/macosx/prefs.m b/modules/gui/macosx/prefs.m index 928efce5ab..cce4386f19 100644 --- a/modules/gui/macosx/prefs.m +++ b/modules/gui/macosx/prefs.m @@ -1,11 +1,11 @@ /***************************************************************************** - * prefs.m: MacOS X plugin for vlc + * prefs.m: MacOS X module for vlc ***************************************************************************** - * Copyright (C) 2002-2003 VideoLAN - * $Id: prefs.m,v 1.23 2003/05/20 18:53:03 hartman Exp $ + * Copyright (C) 2002-2006 the VideoLAN team + * $Id$ * - * Authors: Jon Lech Johansen - * Derk-Jan Hartman + * Authors: Jon Lech Johansen + * Derk-Jan Hartman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -19,9 +19,26 @@ * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111, USA. + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA. *****************************************************************************/ +/* VLCPrefs manages the main preferences dialog + the class is related to wxwindows intf, PrefsPanel */ +/* VLCTreeItem should contain: + - the children of the treeitem + - the associated prefs widgets + - the documentview with all the prefs widgets in it + - a saveChanges action + - a revertChanges action + - an advanced action (to hide/show advanced options) + - a redraw view action + - the children action should generate a list of the treeitems children (to be used by VLCPrefs datasource) + + The class is sort of a mix of wxwindows intfs, PrefsTreeCtrl and ConfigTreeData +*/ +/* VLCConfigControl are subclassed NSView's containing and managing individual config items + the classes are VERY closely related to wxwindows ConfigControls */ + /***************************************************************************** * Preamble *****************************************************************************/ @@ -29,24 +46,39 @@ #include /* for MAXPATHLEN */ #include +#include +#include + #include "intf.h" #include "prefs.h" +#include "prefs_widgets.h" +#include "vlc_keys.h" /***************************************************************************** * VLCPrefs implementation *****************************************************************************/ @implementation VLCPrefs -- (id)init +static VLCPrefs *_o_sharedMainInstance = nil; + ++ (VLCPrefs *)sharedInstance { - self = [super init]; + return _o_sharedMainInstance ? _o_sharedMainInstance : [[self alloc] init]; +} - if( self != nil ) +- (id)init +{ + if( _o_sharedMainInstance ) { + [self dealloc]; + } + else { + _o_sharedMainInstance = [super init]; + p_intf = VLCIntf; o_empty_view = [[NSView alloc] init]; } - return( self ); + return _o_sharedMainInstance; } - (void)dealloc @@ -57,7 +89,7 @@ - (void)awakeFromNib { - p_intf = [NSApp getIntf]; + p_intf = VLCIntf; b_advanced = config_GetInt( p_intf, "advanced" ); [self initStrings]; @@ -65,29 +97,37 @@ [o_prefs_view setBorderType: NSGrooveBorder]; [o_prefs_view setHasVerticalScroller: YES]; [o_prefs_view setDrawsBackground: NO]; - [o_prefs_view setRulersVisible: YES]; [o_prefs_view setDocumentView: o_empty_view]; [o_tree selectRow:0 byExtendingSelection:NO]; - //[self loadConfigTree]; } -- (void)initStrings +- (void)setTitle: (NSString *) o_title_name { - [o_prefs_window setTitle: _NS("Preferences")]; - [o_save_btn setTitle: _NS("Save")]; - [o_cancel_btn setTitle: _NS("Cancel")]; - [o_reset_btn setTitle: _NS("Reset All")]; - [o_advanced_ckb setTitle: _NS("Advanced")]; + [o_title setStringValue: o_title_name]; } - (void)showPrefs { + /* load our nib (if not already loaded) */ + [NSBundle loadNibNamed:@"Preferences" owner:self]; + [o_prefs_window center]; [o_prefs_window makeKeyAndOrderFront:self]; } +- (void)initStrings +{ + [o_prefs_window setTitle: _NS("Preferences")]; + [o_save_btn setTitle: _NS("Save")]; + [o_cancel_btn setTitle: _NS("Cancel")]; + [o_reset_btn setTitle: _NS("Reset All")]; + [o_advanced_ckb setTitle: _NS("Advanced")]; +} + - (IBAction)savePrefs: (id)sender { + /* TODO: call savePrefs on Root item */ + [[VLCTreeItem rootItem] applyChanges]; config_SaveConfigFile( p_intf, NULL ); [o_prefs_window orderOut:self]; } @@ -99,425 +139,75 @@ - (IBAction)resetAll: (id)sender { - config_ResetAll( p_intf ); + NSBeginInformationalAlertSheet(_NS("Reset Preferences"), _NS("Cancel"), + _NS("Continue"), nil, o_prefs_window, self, + @selector(sheetDidEnd: returnCode: contextInfo:), NULL, nil, + _NS("Beware this will reset the VLC media player preferences.\n" + "Are you sure you want to continue?") ); +} + +- (void)sheetDidEnd:(NSWindow *)o_sheet returnCode:(int)i_return + contextInfo:(void *)o_context +{ + if( i_return == NSAlertAlternateReturn ) + { + [o_prefs_view setDocumentView: o_empty_view]; + config_ResetAll( p_intf ); + [[VLCTreeItem rootItem] resetView]; + [[o_tree itemAtRow:[o_tree selectedRow]] + showView:o_prefs_view advancedView: + ( [o_advanced_ckb state] == NSOnState ) ? VLC_TRUE : VLC_FALSE]; + } } - (IBAction)advancedToggle: (id)sender { b_advanced = !b_advanced; [o_advanced_ckb setState: b_advanced]; - [o_tree selectRow: [o_tree selectedRow] byExtendingSelection:NO]; + /* refresh the view of the current treeitem */ + [[o_tree itemAtRow:[o_tree selectedRow]] showView:o_prefs_view advancedView: + ( [o_advanced_ckb state] == NSOnState ) ? VLC_TRUE : VLC_FALSE]; } - (void)loadConfigTree { - } - (void)outlineViewSelectionIsChanging:(NSNotification *)o_notification { } +/* update the document view to the view of the selected tree item */ - (void)outlineViewSelectionDidChange:(NSNotification *)o_notification { - [self showViewForID: [[o_tree itemAtRow:[o_tree selectedRow]] getObjectID] andName: [[o_tree itemAtRow:[o_tree selectedRow]] getName]]; -} - -- (void)configChanged:(id)o_unknown -{ - id o_vlc_config = [o_unknown isKindOfClass: [NSNotification class]] ? - [o_unknown object] : o_unknown; - - int i_type = [o_vlc_config configType]; - NSString *o_name = [o_vlc_config configName]; - char *psz_name = (char *)[o_name UTF8String]; - - switch( i_type ) - { - - case CONFIG_ITEM_MODULE: - { - char *psz_value; - NSString *o_value; - - o_value = [o_vlc_config titleOfSelectedItem]; - psz_value = (char *)[o_value UTF8String]; - - config_PutPsz( p_intf, psz_name, psz_value ); - } - break; - - case CONFIG_ITEM_STRING: - case CONFIG_ITEM_FILE: - case CONFIG_ITEM_DIRECTORY: - { - char *psz_value; - NSString *o_value; - - o_value = [o_vlc_config stringValue]; - psz_value = (char *)[o_value UTF8String]; - - config_PutPsz( p_intf, psz_name, psz_value ); - } - break; - - case CONFIG_ITEM_INTEGER: - case CONFIG_ITEM_BOOL: - { - int i_value = [o_vlc_config intValue]; - - config_PutInt( p_intf, psz_name, i_value ); - } - break; - - case CONFIG_ITEM_FLOAT: - { - float f_value = [o_vlc_config floatValue]; - - config_PutFloat( p_intf, psz_name, f_value ); - } - break; - - } -} - -- (void)showViewForID: (int)i_id andName: (NSString *)o_item_name -{ - vlc_list_t *p_list; - module_t *p_parser; - module_config_t *p_item; - - int i_pos, i_module_tag, i_index; - - NSString *o_module_name; - NSRect s_rc; /* rect */ - NSView *o_view; /* view */ - NSRect s_vrc; /* view rect */ - VLCTextField *o_text_field; /* input field / label */ - - p_list = vlc_list_find( p_intf, VLC_OBJECT_MODULE, FIND_ANYWHERE ); - - /* Get a pointer to the module */ - p_parser = (module_t *)vlc_object_get( p_intf, i_id ); - if( p_parser->i_object_type != VLC_OBJECT_MODULE ) - { - /* 0OOoo something went really bad */ - return; - } - - /* Enumerate config options and add corresponding config boxes */ - o_module_name = [NSString stringWithUTF8String: p_parser->psz_object_name]; - p_item = p_parser->p_config; - - i_pos = 0; - o_view = nil; - i_module_tag = 3; - -#define X_ORIGIN 20 -#define Y_ORIGIN (X_ORIGIN - 10) - -#define CHECK_VIEW_HEIGHT \ - { \ - float f_new_pos = s_rc.origin.y + s_rc.size.height + X_ORIGIN; \ - if( f_new_pos > s_vrc.size.height ) \ - { \ - s_vrc.size.height = f_new_pos; \ - [o_view setFrame: s_vrc]; \ - } \ - } - -#define CONTROL_LABEL( label ) \ - { \ - s_rc.origin.x += s_rc.size.width + 10; \ - s_rc.size.width = s_vrc.size.width - s_rc.origin.x - X_ORIGIN - 20; \ - o_text_field = [[NSTextField alloc] initWithFrame: s_rc]; \ - [o_text_field setDrawsBackground: NO]; \ - [o_text_field setBordered: NO]; \ - [o_text_field setEditable: NO]; \ - [o_text_field setSelectable: NO]; \ - if ( label ) \ - { \ - [o_text_field setStringValue: \ - [NSApp localizedString: label]]; \ - } \ - [o_text_field sizeToFit]; \ - [o_view addSubview: [o_text_field autorelease]]; \ - } - -#define INPUT_FIELD( ctype, cname, label, w, msg, param, tip ) \ - { \ - char * psz_duptip = NULL; \ - if ( p_item->psz_longtext != NULL && [NSApp getEncoding] == NSISOLatin1StringEncoding ) \ - psz_duptip = strdup(p_item->psz_longtext); \ - s_rc.size.height = 25; \ - s_rc.size.width = w; \ - s_rc.origin.y += 10; \ - CHECK_VIEW_HEIGHT; \ - o_text_field = [[VLCTextField alloc] initWithFrame: s_rc]; \ - [o_text_field setAlignment: NSRightTextAlignment]; \ - CONTROL_CONFIG( o_text_field, o_module_name, ctype, cname ); \ - [o_text_field msg: param]; \ - if ( psz_duptip != NULL ) \ - { \ - [o_text_field setToolTip: [NSApp localizedString: \ - vlc_wraptext(psz_duptip, PREFS_WRAP)]]; \ - free(psz_duptip);\ - } \ - [o_view addSubview: [o_text_field autorelease]]; \ - [[NSNotificationCenter defaultCenter] addObserver: self \ - selector: @selector(configChanged:) \ - name: NSControlTextDidChangeNotification \ - object: o_text_field]; \ - CONTROL_LABEL( label ); \ - s_rc.origin.y += s_rc.size.height; \ - s_rc.origin.x = X_ORIGIN; \ - } - -#define INPUT_FIELD_INTEGER( name, label, w, param, tip ) \ - INPUT_FIELD( CONFIG_ITEM_INTEGER, name, label, w, setIntValue, param, tip ) -#define INPUT_FIELD_FLOAT( name, label, w, param, tip ) \ - INPUT_FIELD( CONFIG_ITEM_FLOAT, name, label, w, setFloatValue, param, tip ) -#define INPUT_FIELD_STRING( name, label, w, param, tip ) \ - INPUT_FIELD( CONFIG_ITEM_STRING, name, label, w, setStringValue, param, tip ) - - /* Init View */ - s_vrc = [[o_prefs_view contentView] bounds]; s_vrc.size.height -= 4; - o_view = [[VLCFlippedView alloc] initWithFrame: s_vrc]; - s_rc.origin.x = X_ORIGIN; - s_rc.origin.y = Y_ORIGIN; - BOOL b_right_cat = FALSE; - - if( p_item ) do - { - if( p_item->i_type == CONFIG_HINT_CATEGORY ) - { - if( !strcmp( p_parser->psz_object_name, "main" ) && - [o_item_name isEqualToString: [NSApp localizedString: p_item->psz_text]] ) - { - b_right_cat = TRUE; - } else if( strcmp( p_parser->psz_object_name, "main" ) ) - { - b_right_cat = TRUE; - } else b_right_cat = FALSE; - } else if( p_item->i_type == CONFIG_HINT_END && !strcmp( p_parser->psz_object_name, "main" ) ) - { - b_right_cat = FALSE; - } - - if( (p_item->b_advanced && !b_advanced ) || !b_right_cat ) - { - continue; - } - switch( p_item->i_type ) - { - case CONFIG_ITEM_MODULE: - { - VLCPopUpButton *o_modules; - module_t *p_a_module; - char * psz_duptip = NULL; - if ( p_item->psz_longtext != NULL && [NSApp getEncoding] == NSISOLatin1StringEncoding ) - psz_duptip = strdup(p_item->psz_longtext); - - s_rc.size.height = 30; - s_rc.size.width = 200; - s_rc.origin.y += 10; - - CHECK_VIEW_HEIGHT; - - o_modules = [[VLCPopUpButton alloc] initWithFrame: s_rc]; - CONTROL_CONFIG( o_modules, o_module_name, - CONFIG_ITEM_MODULE, p_item->psz_name ); - [o_modules setTarget: self]; - [o_modules setAction: @selector(configChanged:)]; - [o_modules sendActionOn:NSLeftMouseUpMask]; - if ( psz_duptip != NULL ) - { - [o_modules setToolTip: [NSApp localizedString: - vlc_wraptext(psz_duptip, PREFS_WRAP)]]; - free( psz_duptip ); - } - [o_view addSubview: [o_modules autorelease]]; - - [o_modules addItemWithTitle: _NS("Auto")]; - - /* build a list of available modules */ - { - for( i_index = 0; i_index < p_list->i_count; i_index++ ) - { - p_a_module = (module_t *)p_list->p_values[i_index].p_object ; - - if( !strcmp( p_a_module->psz_capability, - p_item->psz_type ) ) - { - NSString *o_object_name = [NSString - stringWithCString: p_a_module->psz_object_name]; - [o_modules addItemWithTitle: o_object_name]; - } - } - } - - if( p_item->psz_value != NULL ) - { - NSString *o_value = - [NSString stringWithUTF8String: p_item->psz_value]; - - [o_modules selectItemWithTitle: o_value]; - } - else - { - [o_modules selectItemWithTitle: _NS("Auto")]; - } - - CONTROL_LABEL( p_item->psz_text ); - s_rc.origin.y += s_rc.size.height; - s_rc.origin.x = X_ORIGIN; - } - break; - - case CONFIG_ITEM_STRING: - case CONFIG_ITEM_FILE: - case CONFIG_ITEM_DIRECTORY: - { - - if( !p_item->ppsz_list ) - { - char *psz_value = p_item->psz_value ? - p_item->psz_value : ""; - - INPUT_FIELD_STRING( p_item->psz_name, p_item->psz_text, 200, - [NSString stringWithCString: psz_value], - p_item->psz_longtext ); - } - else - { - int i; - VLCComboBox *o_combo_box; - char * psz_duptip = NULL; - if ( p_item->psz_longtext != NULL && [NSApp getEncoding] == NSISOLatin1StringEncoding ) - psz_duptip = strdup(p_item->psz_longtext); - - s_rc.size.height = 27; - s_rc.size.width = 200; - s_rc.origin.y += 10; - - CHECK_VIEW_HEIGHT; - - o_combo_box = [[VLCComboBox alloc] initWithFrame: s_rc]; - CONTROL_CONFIG( o_combo_box, o_module_name, - CONFIG_ITEM_STRING, p_item->psz_name ); - [o_combo_box setTarget: self]; - [o_combo_box setAction: @selector(configChanged:)]; - [o_combo_box sendActionOn:NSLeftMouseUpMask]; - - if ( psz_duptip != NULL ) - { - [o_combo_box setToolTip: [NSApp localizedString: - vlc_wraptext(psz_duptip, PREFS_WRAP)]]; - free( psz_duptip ); - } - [o_view addSubview: [o_combo_box autorelease]]; - - for( i=0; p_item->ppsz_list[i]; i++ ) - { - [o_combo_box addItemWithObjectValue: - [NSString stringWithCString: p_item->ppsz_list[i]]]; - } - [o_combo_box setStringValue: [NSString stringWithCString: - p_item->psz_value ? p_item->psz_value : ""]]; - - CONTROL_LABEL( p_item->psz_text ); - - s_rc.origin.y += s_rc.size.height; - s_rc.origin.x = X_ORIGIN; - } - - } - break; - - case CONFIG_ITEM_INTEGER: - { - INPUT_FIELD_INTEGER( p_item->psz_name, p_item->psz_text, 70, - p_item->i_value, p_item->psz_longtext ); - } - break; - - case CONFIG_ITEM_FLOAT: - { - INPUT_FIELD_FLOAT( p_item->psz_name, p_item->psz_text, 70, - p_item->f_value, p_item->psz_longtext ); - } - break; - - case CONFIG_ITEM_BOOL: - { - VLCButton *o_btn_bool; - char * psz_duptip = NULL; - if ( p_item->psz_longtext != NULL && [NSApp getEncoding] == NSISOLatin1StringEncoding ) - psz_duptip = strdup(p_item->psz_longtext); - - s_rc.size.height = 27; - s_rc.size.width = s_vrc.size.width - X_ORIGIN * 2 - 20; - s_rc.origin.y += 10; - - CHECK_VIEW_HEIGHT; - - o_btn_bool = [[VLCButton alloc] initWithFrame: s_rc]; - [o_btn_bool setButtonType: NSSwitchButton]; - [o_btn_bool setIntValue: p_item->i_value]; - [o_btn_bool setTitle: - [NSApp localizedString: p_item->psz_text]]; - if ( psz_duptip != NULL ) - { - [o_btn_bool setToolTip: [NSApp localizedString: - vlc_wraptext(psz_duptip, PREFS_WRAP)]]; - free( psz_duptip ); - } - [o_btn_bool setTarget: self]; - [o_btn_bool setAction: @selector(configChanged:)]; - CONTROL_CONFIG( o_btn_bool, o_module_name, - CONFIG_ITEM_BOOL, p_item->psz_name ); - [o_view addSubview: [o_btn_bool autorelease]]; - - s_rc.origin.y += s_rc.size.height; - } - break; - - } - - #undef INPUT_FIELD_INTEGER - #undef INPUT_FIELD_FLOAT - #undef INPUT_FIELD_STRING - #undef INPUT_FIELD - #undef CHECK_VIEW_HEIGHT - #undef CONTROL_LABEL - #undef Y_ORIGIN - #undef X_ORIGIN - } - while( p_item->i_type != CONFIG_HINT_END && p_item++ ); - vlc_list_release( p_list ); - - [o_prefs_view setDocumentView: o_view]; - [o_prefs_view setNeedsDisplay: TRUE]; + [[o_tree itemAtRow:[o_tree selectedRow]] showView: o_prefs_view + advancedView:( [o_advanced_ckb state] == NSOnState ) ? + VLC_TRUE : VLC_FALSE]; } - @end @implementation VLCPrefs (NSTableDataSource) - (int)outlineView:(NSOutlineView *)outlineView numberOfChildrenOfItem:(id)item { - return (item == nil) ? [[VLCTreeItem rootItem] numberOfChildren] : [item numberOfChildren]; + return (item == nil) ? [[VLCTreeItem rootItem] numberOfChildren] : + [item numberOfChildren]; } -- (BOOL)outlineView:(NSOutlineView *)outlineView isItemExpandable:(id)item { - return (item == nil) ? YES : ([item numberOfChildren] != -1); +- (BOOL)outlineView:(NSOutlineView *)outlineView isItemExpandable:(id)item +{ + return (item == nil) ? YES : ( ([item numberOfChildren] != -1) && + ([item numberOfChildren] != 0)); } - (id)outlineView:(NSOutlineView *)outlineView child:(int)index ofItem:(id)item { - return (item == nil) ? [[VLCTreeItem rootItem] childAtIndex:index] : [item childAtIndex:index]; + return (item == nil) ? [[VLCTreeItem rootItem] childAtIndex:index] : + (id)[item childAtIndex:index]; } -- (id)outlineView:(NSOutlineView *)outlineView objectValueForTableColumn:(NSTableColumn *)tableColumn byItem:(id)item { +- (id)outlineView:(NSOutlineView *)outlineView + objectValueForTableColumn:(NSTableColumn *)tableColumn byItem:(id)item +{ return (item == nil) ? @"" : (id)[item getName]; } @@ -529,49 +219,76 @@ static VLCTreeItem *o_root_item = nil; #define IsALeafNode ((id)-1) -- (id)initWithName: (NSString *)o_item_name ID: (int)i_id parent:(VLCTreeItem *)o_parent_item +- (id)initWithName: (NSString *)o_item_name + withTitle: (NSString *)o_item_title + withHelp: (NSString *)o_item_help + ID: (int)i_id + parent:(VLCTreeItem *)o_parent_item + children:(NSMutableArray *)o_children_array + whithCategory: (int) i_category { self = [super init]; if( self != nil ) { o_name = [o_item_name copy]; + o_title= [o_item_title copy]; + o_help= [o_item_help copy]; i_object_id = i_id; o_parent = o_parent_item; + o_children = o_children_array; + i_object_category = i_category; + o_subviews = nil; } return( self ); } -+ (VLCTreeItem *)rootItem { - if (o_root_item == nil) o_root_item = [[VLCTreeItem alloc] initWithName:@"main" ID: 0 parent:nil]; - return o_root_item; ++ (VLCTreeItem *)rootItem +{ + if (o_root_item == nil) + o_root_item = [[VLCTreeItem alloc] initWithName:@"main" withTitle:@"main" withHelp:@"" ID:0 + parent:nil children:[[NSMutableArray alloc] initWithCapacity:10] + whithCategory: -1]; + return o_root_item; } - (void)dealloc { if (o_children != IsALeafNode) [o_children release]; [o_name release]; + [o_title release]; + [o_help release]; [super dealloc]; } /* Creates and returns the array of children * Loads children incrementally */ -- (NSArray *)children { - if (o_children == NULL) { - intf_thread_t *p_intf = [NSApp getIntf]; +- (NSArray *)children +{ + if( o_children == IsALeafNode ) + return o_children; + if( [ o_children count] == 0 ) + { + intf_thread_t *p_intf = VLCIntf; vlc_list_t *p_list; - module_t *p_module; - module_config_t *p_item; - int i_index,j; + module_t *p_module = NULL; + module_t *p_parser; + module_config_t *p_item, + *p_end; + int i_index = 0; - /* List the plugins */ + /* List the modules */ p_list = vlc_list_find( p_intf, VLC_OBJECT_MODULE, FIND_ANYWHERE ); if( !p_list ) return nil; + /* get parser */ + p_parser = (module_t *)p_list->p_values[i_index].p_object; + p_end = p_parser->p_config + p_parser->confsize; + if( [[self getName] isEqualToString: @"main"] ) { /* - * Build a tree of the main options + * Find the main module */ for( i_index = 0; i_index < p_list->i_count; i_index++ ) { @@ -579,167 +296,165 @@ static VLCTreeItem *o_root_item = nil; if( !strcmp( p_module->psz_object_name, "main" ) ) break; } + if( p_module == NULL ) + { + msg_Err( p_intf, + "could not load the preferences" ); + return nil; + } if( i_index < p_list->i_count ) { /* We found the main module */ - /* Enumerate config categories and store a reference so we can * generate their config panel them when it is asked by the user. */ + VLCTreeItem *p_last_category = NULL; p_item = p_module->p_config; o_children = [[NSMutableArray alloc] initWithCapacity:10]; - if( p_item ) do { NSString *o_child_name; - + NSString *o_child_title; + NSString *o_child_help; switch( p_item->i_type ) { - case CONFIG_HINT_CATEGORY: - o_child_name = [NSString stringWithUTF8String: p_item->psz_text]; - [o_children addObject:[[VLCTreeItem alloc] initWithName: o_child_name - ID: p_module->i_object_id parent:self]]; + case CONFIG_CATEGORY: + if( p_item->value.i == -1 ) break; + + o_child_name = [[VLCMain sharedInstance] + localizedString: config_CategoryNameGet( p_item->value.i )]; + o_child_title = o_child_name; + o_child_help = [[VLCMain sharedInstance] + localizedString: config_CategoryHelpGet( p_item->value.i )]; + p_last_category = [VLCTreeItem alloc]; + [o_children addObject:[p_last_category + initWithName: o_child_name + withTitle: o_child_title + withHelp: o_child_help + ID: p_item->value.i + parent:self + children:[[NSMutableArray alloc] + initWithCapacity:10] + whithCategory: p_item - p_module->p_config]]; + break; + case CONFIG_SUBCATEGORY: + if( p_item->value.i == -1 ) break; + + if( p_item->value.i != SUBCAT_PLAYLIST_GENERAL && + p_item->value.i != SUBCAT_VIDEO_GENERAL && + p_item->value.i != SUBCAT_INPUT_GENERAL && + p_item->value.i != SUBCAT_INTERFACE_GENERAL && + p_item->value.i != SUBCAT_SOUT_GENERAL && + p_item->value.i != SUBCAT_ADVANCED_MISC && + p_item->value.i != SUBCAT_AUDIO_GENERAL ) + { + o_child_name = [[VLCMain sharedInstance] + localizedString: config_CategoryNameGet( p_item->value.i ) ]; + o_child_title = o_child_name; + o_child_help = [[VLCMain sharedInstance] + localizedString: config_CategoryHelpGet( p_item->value.i ) ]; + + [p_last_category->o_children + addObject:[[VLCTreeItem alloc] + initWithName: o_child_name + withTitle: o_child_title + withHelp: o_child_help + ID: p_item->value.i + parent:p_last_category + children:[[NSMutableArray alloc] + initWithCapacity:10] + whithCategory: p_item - p_module->p_config]]; + } + + break; + default: break; } - } - while( p_item->i_type != CONFIG_HINT_END && p_item++ ); - - /* Add the plugins item */ - [o_children addObject:[[VLCTreeItem alloc] initWithName: _NS("Modules") - ID: 0 parent:self]]; + } while( p_item < p_end && p_item++ ); } - else - { - o_children = IsALeafNode; - } - } - else if( [[self getName] isEqualToString: _NS("Modules")] ) - { + + /* Build a tree of the plugins */ /* Add the capabilities */ - o_children = [[NSMutableArray alloc] initWithCapacity:10]; for( i_index = 0; i_index < p_list->i_count; i_index++ ) { p_module = (module_t *)p_list->p_values[i_index].p_object; - + /* Exclude the main module */ if( !strcmp( p_module->psz_object_name, "main" ) ) continue; - - /* Exclude empty plugins */ - p_item = p_module->p_config; + + /* Exclude empty plugins (submodules don't have config */ + /* options, they are stored in the parent module) */ + if( p_module->b_submodule ) + continue; + else + p_item = p_module->p_config; + if( !p_item ) continue; + int i_category = -1; + int i_subcategory = -1; + int i_options = 0; do { + if( p_item->i_type == CONFIG_CATEGORY ) + i_category = p_item->value.i; + else if( p_item->i_type == CONFIG_SUBCATEGORY ) + i_subcategory = p_item->value.i; + if( p_item->i_type & CONFIG_ITEM ) + i_options ++; + if( i_options > 0 && i_category >= 0 && i_subcategory >= 0 ) break; - } - while( p_item->i_type != CONFIG_HINT_END && p_item++ ); - if( p_item->i_type == CONFIG_HINT_END ) continue; - - /* Create the capability tree if it doesn't already exist */ - NSString *o_capability; - o_capability = [NSString stringWithUTF8String: p_module->psz_capability]; - if( !p_module->psz_capability || !*p_module->psz_capability ) + } while( p_item < p_end && p_item++ ); + if( !i_options ) continue; + + /* Find the right category item */ + + long cookie; + vlc_bool_t b_found = VLC_FALSE; + unsigned int i; + VLCTreeItem* p_category_item, * p_subcategory_item; + for (i = 0 ; i < [o_children count] ; i++) { - /* Empty capability ? Let's look at the submodules */ - module_t * p_submodule; - for( j = 0; j < p_module->i_children; j++ ) + p_category_item = [o_children objectAtIndex: i]; + if( p_category_item->i_object_id == i_category ) { - p_submodule = (module_t*)p_module->pp_children[ j ]; - if( p_submodule->psz_capability && *p_submodule->psz_capability ) - { - o_capability = [NSString stringWithUTF8String: p_submodule->psz_capability]; - BOOL b_found = FALSE; - for( j = 0; j < [o_children count]; j++ ) - { - if( [[[o_children objectAtIndex:j] getName] isEqualToString: o_capability] ) - { - b_found = TRUE; - break; - } - } - if( !b_found ) - { - [o_children addObject:[[VLCTreeItem alloc] initWithName: o_capability - ID: 0 parent:self]]; - } - } + b_found = VLC_TRUE; + break; } } + if( !b_found ) continue; - BOOL b_found = FALSE; - for( j = 0; j < [o_children count]; j++ ) + /* Find subcategory item */ + b_found = VLC_FALSE; + cookie = -1; + for (i = 0 ; i < [p_category_item->o_children count] ; i++) { - if( [[[o_children objectAtIndex:j] getName] isEqualToString: o_capability] ) + p_subcategory_item = [p_category_item->o_children + objectAtIndex: i]; + if( p_subcategory_item->i_object_id == i_subcategory ) { - b_found = TRUE; + b_found = VLC_TRUE; break; } } if( !b_found ) - { - [o_children addObject:[[VLCTreeItem alloc] initWithName: o_capability - ID: 0 parent:self]]; - } - } - } - else if( [[o_parent getName] isEqualToString: _NS("Modules")] ) - { - /* Now add the modules */ - o_children = [[NSMutableArray alloc] initWithCapacity:10]; - for( i_index = 0; i_index < p_list->i_count; i_index++ ) - { - p_module = (module_t *)p_list->p_values[i_index].p_object; - - /* Exclude the main module */ - if( !strcmp( p_module->psz_object_name, "main" ) ) - continue; - - /* Exclude empty plugins */ - p_item = p_module->p_config; - if( !p_item ) continue; - do - { - if( p_item->i_type & CONFIG_ITEM ) - break; - } - while( p_item->i_type != CONFIG_HINT_END && p_item++ ); - if( p_item->i_type == CONFIG_HINT_END ) continue; - - /* Check the capability */ - NSString *o_capability; - o_capability = [NSString stringWithUTF8String: p_module->psz_capability]; - if( !p_module->psz_capability || !*p_module->psz_capability ) - { - /* Empty capability ? Let's look at the submodules */ - module_t * p_submodule; - for( j = 0; j < p_module->i_children; j++ ) - { - p_submodule = (module_t*)p_module->pp_children[ j ]; - if( p_submodule->psz_capability && *p_submodule->psz_capability ) - { - o_capability = [NSString stringWithUTF8String: p_submodule->psz_capability]; - if( [o_capability isEqualToString: [self getName]] ) - { - [o_children addObject:[[VLCTreeItem alloc] initWithName: - [NSString stringWithUTF8String: p_module->psz_object_name ] - ID: p_module->i_object_id parent:self]]; - } - } - } - } - else if( [o_capability isEqualToString: [self getName]] ) - { - [o_children addObject:[[VLCTreeItem alloc] initWithName: - [NSString stringWithUTF8String: p_module->psz_object_name ] - ID: p_module->i_object_id parent:self]]; + p_subcategory_item = p_category_item; + + [p_subcategory_item->o_children addObject:[[VLCTreeItem alloc] + initWithName:[[VLCMain sharedInstance] + localizedString: (char *)p_module->psz_shortname ? + (char *)p_module->psz_shortname : (char *)p_module->psz_object_name ] + withTitle:[[VLCMain sharedInstance] + localizedString: (char *)p_module->psz_longname ? + (char *)p_module->psz_longname : (char *)p_module->psz_object_name ] + withHelp: @"" + ID: p_module->i_object_id + parent:p_subcategory_item + children:IsALeafNode + whithCategory: -1]]; } - } - } - else - { - /* all the other stuff are leafs */ - o_children = IsALeafNode; } + vlc_list_release( p_list ); } return o_children; } @@ -754,24 +469,35 @@ static VLCTreeItem *o_root_item = nil; return o_name; } -- (VLCTreeItem *)childAtIndex:(int)i_index { +- (NSString *)getTitle +{ + return o_title; +} + +- (NSString *)getHelp +{ + return o_help; +} + +- (VLCTreeItem *)childAtIndex:(int)i_index +{ return [[self children] objectAtIndex:i_index]; } - (int)numberOfChildren { id i_tmp = [self children]; - return (i_tmp == IsALeafNode) ? (-1) : [i_tmp count]; + return (i_tmp == IsALeafNode) ? (-1) : (int)[i_tmp count]; } - (BOOL)hasPrefs:(NSString *)o_module_name { - intf_thread_t *p_intf = [NSApp getIntf]; + intf_thread_t *p_intf = VLCIntf; module_t *p_parser; vlc_list_t *p_list; char *psz_module_name; int i_index; - psz_module_name = (char *)[o_module_name lossyCString]; + psz_module_name = (char *)[o_module_name UTF8String]; /* look for module */ p_list = vlc_list_find( p_intf, VLC_OBJECT_MODULE, FIND_ANYWHERE ); @@ -793,6 +519,259 @@ static VLCTreeItem *o_root_item = nil; return( NO ); } +- (NSView *)showView:(NSScrollView *)o_prefs_view + advancedView:(vlc_bool_t) b_advanced +{ + NSRect s_vrc; + NSView *o_view; + + [[VLCPrefs sharedInstance] setTitle: [self getTitle]]; + /* NSLog( [self getHelp] ); */ + s_vrc = [[o_prefs_view contentView] bounds]; s_vrc.size.height -= 4; + o_view = [[VLCFlippedView alloc] initWithFrame: s_vrc]; + [o_view setAutoresizingMask: NSViewWidthSizable | NSViewMinYMargin | + NSViewMaxYMargin]; + +/* Create all subviews if it isn't already done because we cannot use */ +/* setHiden for MacOS < 10.3*/ + if( o_subviews == nil ) + { + intf_thread_t *p_intf = VLCIntf; + vlc_list_t *p_list; + module_t *p_parser = NULL; + module_config_t *p_item, + *p_end; + + o_subviews = [[NSMutableArray alloc] initWithCapacity:10]; + /* Get a pointer to the module */ + if( i_object_category == -1 ) + { + p_parser = (module_t *) vlc_object_get( p_intf, i_object_id ); + if( !p_parser || p_parser->i_object_type != VLC_OBJECT_MODULE ) + { + /* 0OOoo something went really bad */ + return nil; + } + + p_end = p_parser->p_config + p_parser->confsize; + + p_item = p_parser->p_config; + + p_item = p_parser->p_config + 1; + + do + { + if( !p_item ) + { + msg_Err( p_intf, "invalid preference item found" ); + break; + } + if( p_item > p_end ) + break; + switch(p_item->i_type) + { + case CONFIG_SUBCATEGORY: + break; + case CONFIG_CATEGORY: + break; + case CONFIG_SECTION: + break; + case CONFIG_HINT_USAGE: + break; + default: + { + VLCConfigControl *o_control = nil; + o_control = [VLCConfigControl newControl:p_item + withView:o_view]; + if( o_control != nil ) + { + [o_control setAutoresizingMask: NSViewMaxYMargin | + NSViewWidthSizable]; + [o_subviews addObject: o_control]; + } + } + break; + } + } while( p_item < p_end && p_item++ ); + + vlc_object_release( p_parser ); + } + else + { + int i_index; + p_list = vlc_list_find( p_intf, VLC_OBJECT_MODULE, FIND_ANYWHERE ); + if( !p_list ) return o_view; + + /* + * Find the main module + */ + for( i_index = 0; i_index < p_list->i_count; i_index++ ) + { + p_parser = (module_t *)p_list->p_values[i_index].p_object; + if( !strcmp( p_parser->psz_object_name, "main" ) ) + break; + } + if( p_parser == NULL ) + { + msg_Err( p_intf, "could not load preferences" ); + return o_view; + } + p_end = p_parser->p_config + p_parser->confsize; + + p_item = (p_parser->p_config + i_object_category); + if( ( p_item->i_type == CONFIG_CATEGORY ) && + ( ( p_item->value.i == CAT_PLAYLIST ) || + ( p_item->value.i == CAT_AUDIO ) || + ( p_item->value.i == CAT_VIDEO ) || + ( p_item->value.i == CAT_INTERFACE ) || + ( p_item->value.i == CAT_INPUT ) || + ( p_item->value.i == CAT_SOUT ) ) ) + p_item++; + + do + { + p_item++; + if( !p_item ) + { + msg_Err( p_intf, "invalid preference item found" ); + break; + } + if( p_item > p_end ) + break; + switch( p_item->i_type ) + { + case CONFIG_SUBCATEGORY: + break; + case CONFIG_CATEGORY: + break; + case CONFIG_SECTION: + break; + case CONFIG_HINT_USAGE: + break; + default: + { + VLCConfigControl *o_control = nil; + if( p_item->b_internal == VLC_TRUE ) + { + break; + } + o_control = [VLCConfigControl newControl:p_item + withView:o_view]; + if( o_control != nil ) + { + [o_control setAutoresizingMask: NSViewMaxYMargin | + NSViewWidthSizable]; + [o_subviews addObject: o_control]; + } + break; + } + } + } while ( ( p_item < p_end ) && + ( p_item->i_type != CONFIG_SUBCATEGORY ) ); + + vlc_list_release( p_list ); + } + } + + if( o_view != nil ) + { + int i_lastItem = 0; + int i_yPos = -2; + int i_max_label = 0; + int i_show_advanced = 0; + + NSEnumerator *enumerator = [o_subviews objectEnumerator]; + VLCConfigControl *o_widget; + NSRect o_frame; + + while( ( o_widget = [enumerator nextObject] ) ) + if( ( [o_widget isAdvanced] ) && (! b_advanced) ) + continue; + else if( i_max_label < [o_widget getLabelSize] ) + i_max_label = [o_widget getLabelSize]; + + enumerator = [o_subviews objectEnumerator]; + while( ( o_widget = [enumerator nextObject] ) ) + { + int i_widget; + if( ( [o_widget isAdvanced] ) && (! b_advanced) ) + { + i_show_advanced++; + continue; + } + + i_widget = [o_widget getViewType]; + i_yPos += [VLCConfigControl calcVerticalMargin:i_widget + lastItem:i_lastItem]; + [o_widget setYPos:i_yPos]; + o_frame = [o_widget frame]; + o_frame.size.width = [o_view frame].size.width - + LEFTMARGIN - RIGHTMARGIN; + [o_widget setFrame:o_frame]; + [o_widget alignWithXPosition: i_max_label]; + i_yPos += [o_widget frame].size.height; + i_lastItem = i_widget; + [o_view addSubview:o_widget]; + } + if( i_show_advanced != 0 ) + { + /* We add the advanced notice... */ + NSRect s_rc = [o_view frame]; + NSTextField *o_label; + s_rc.size.height = 17; + s_rc.origin.x = LEFTMARGIN; + s_rc.origin.y = i_yPos += [VLCConfigControl + calcVerticalMargin:CONFIG_ITEM_STRING + lastItem:i_lastItem]; + o_label = [[[NSTextField alloc] initWithFrame: s_rc] retain]; + [o_label setDrawsBackground: NO]; + [o_label setBordered: NO]; + [o_label setEditable: NO]; + [o_label setSelectable: NO]; + [o_label setStringValue: _NS("Some options are hidden. " \ + "Check \"Advanced\" to display them.")]; + [o_label setFont:[NSFont systemFontOfSize:10]]; + [o_label sizeToFit]; + [o_view addSubview:o_label]; + i_yPos += [o_label frame].size.height; + } + o_frame = [o_view frame]; + o_frame.size.height = i_yPos; + [o_view setFrame:o_frame]; + [o_prefs_view setDocumentView:o_view]; + + } + return o_view; +} + +- (void)applyChanges +{ + unsigned int i; + if( o_subviews != nil ) + //Item has been shown + for( i = 0 ; i < [o_subviews count] ; i++ ) + [[o_subviews objectAtIndex:i] applyChanges]; + + if( o_children != IsALeafNode ) + for( i = 0 ; i < [o_children count] ; i++ ) + [[o_children objectAtIndex:i] applyChanges]; +} + +- (void)resetView +{ + unsigned int i; + if( o_subviews != nil ) + { + //Item has been shown + [o_subviews release]; + o_subviews = nil; + } + + if( o_children != IsALeafNode ) + for( i = 0 ; i < [o_children count] ; i++ ) + [[o_children objectAtIndex:i] resetView]; +} + @end @@ -804,8 +783,3 @@ static VLCTreeItem *o_root_item = nil; } @end - -IMPL_CONTROL_CONFIG(Button); -IMPL_CONTROL_CONFIG(PopUpButton); -IMPL_CONTROL_CONFIG(ComboBox); -IMPL_CONTROL_CONFIG(TextField);