]> git.sesse.net Git - vlc/blobdiff - modules/access/dvdplay/access.c
* modules/access/dvd*: changed some errors in warnings because the directory
[vlc] / modules / access / dvdplay / access.c
index 325cfd1760df349103614143c8e3a04f7ca02446..f0787d7050e3b57649299d011c8b4154d1d8079f 100644 (file)
@@ -2,7 +2,7 @@
  * access.c: access capabilities for dvdplay plugin.
  *****************************************************************************
  * Copyright (C) 2001 VideoLAN
- * $Id: access.c,v 1.5 2002/11/06 18:07:57 sam Exp $
+ * $Id: access.c,v 1.14 2003/03/24 14:18:28 hartman Exp $
  *
  * Author: Stéphane Borel <stef@via.ecp.fr>
  *
@@ -10,7 +10,7 @@
  * it under the terms of the GNU General Public License as published by
  * the Free Software Foundation; either version 2 of the License, or
  * (at your option) any later version.
- * 
+ *
  * This program is distributed in the hope that it will be useful,
  * but WITHOUT ANY WARRANTY; without even the implied warranty of
  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 #   include <strings.h>
 #endif
 
-#if defined( WIN32 )
-#   include <io.h>                                                 /* read() */
-#endif
-
 #include "dvd.h"
 #include "es.h"
 #include "tools.h"
@@ -78,12 +74,12 @@ int E_(OpenDVD) ( vlc_object_t *p_this )
     char *                  psz_source;
     dvd_data_t *            p_dvd;
     input_area_t *          p_area;
-    int                     i_title_nr;
-    int                     i_title;
-    int                     i_chapter;
-    int                     i_angle;
-    int                     i;
-    
+    unsigned int            i_title_nr;
+    unsigned int            i_title;
+    unsigned int            i_chapter;
+    unsigned int            i_angle;
+    unsigned int            i;
+
     p_dvd = malloc( sizeof(dvd_data_t) );
     if( p_dvd == NULL )
     {
@@ -99,7 +95,7 @@ int E_(OpenDVD) ( vlc_object_t *p_this )
     p_input->pf_set_program = dvdplay_SetProgram;
 
     /* command line */
-    if( ( psz_source = dvdplay_ParseCL( p_input, 
+    if( ( psz_source = dvdplay_ParseCL( p_input,
                         &i_title, &i_chapter, &i_angle ) ) == NULL )
     {
         free( p_dvd );
@@ -109,20 +105,21 @@ int E_(OpenDVD) ( vlc_object_t *p_this )
     /* Open libdvdplay */
     p_dvd->vmg = dvdplay_open( psz_source, pf_vmg_callback, (void*)p_input );
 
-    /* free allocated strings */
-    free( psz_source );
-
     if( p_dvd->vmg == NULL )
     {
-        msg_Err( p_input, "cannot open %s", psz_source );
+        msg_Warn( p_input, "cannot open %s", psz_source );
+        free( psz_source );
         free( p_dvd );
         return -1;
     }
 
+    /* free allocated strings */
+    free( psz_source );
+
     p_dvd->p_intf = NULL;
 
     p_dvd->i_still_time = 0;
-    
+
     /* set up input  */
     p_input->i_mtu = 0;
 
@@ -133,7 +130,8 @@ int E_(OpenDVD) ( vlc_object_t *p_this )
     p_input->stream.b_pace_control = 1;
     /* seek is only allowed when we have size info */
     p_input->stream.b_seekable = 0;
-    
+    p_input->stream.b_connected = 1;
+
     /* Initialize ES structures */
     input_InitStream( p_input, sizeof( stream_ps_data_t ) );
 
@@ -145,17 +143,12 @@ int E_(OpenDVD) ( vlc_object_t *p_this )
 
     /* Area 0 for menu */
     area[0]->i_plugin_data = 0;
-    
+    input_DelArea( p_input, p_input->stream.pp_areas[0] );
+    input_AddArea( p_input, 0, 1 );
+
     for( i = 1 ; i <= i_title_nr ; i++ )
     {
-        input_AddArea( p_input );
-        
-        /* Titles id */
-        area[i]->i_id = i;
-
-        /* Number of chapters */
-        area[i]->i_part_nb = dvdplay_chapter_nr( p_dvd->vmg, i );
-
+        input_AddArea( p_input, i, dvdplay_chapter_nr( p_dvd->vmg, i ) );
         area[i]->i_plugin_data = 0;
     }
 #undef area
@@ -173,7 +166,7 @@ int E_(OpenDVD) ( vlc_object_t *p_this )
         vlc_mutex_unlock( &p_input->stream.stream_lock );
         return -1;
     }
-    
+
     if( i_angle <= p_input->stream.i_pgrm_number )
     {
         dvdplay_SetProgram( p_input,
@@ -182,7 +175,10 @@ int E_(OpenDVD) ( vlc_object_t *p_this )
 
     vlc_mutex_unlock( &p_input->stream.stream_lock );
 
-    p_input->psz_demux = "dvdplay";
+    if( !p_input->psz_demux || !*p_input->psz_demux )
+    {
+        p_input->psz_demux = "dvdplay";
+    }
 
     /* FIXME: we might lose variables here */
     var_Create( p_input, "x-start", VLC_VAR_INTEGER );
@@ -239,7 +235,8 @@ static int dvdplay_SetProgram( input_thread_t *     p_input,
     {
         dvd_data_t *    p_dvd;
         int             i_angle;
-    
+        vlc_value_t     val;
+
         p_dvd = (dvd_data_t*)(p_input->p_access_data);
         i_angle = p_program->i_number;
 
@@ -252,6 +249,10 @@ static int dvdplay_SetProgram( input_thread_t *     p_input,
 
             msg_Dbg( p_input, "angle %d selected", i_angle );
         }
+
+        /* Update the navigation variables without triggering a callback */
+        val.i_int = p_program->i_number;
+        var_Change( p_input, "program", VLC_VAR_SETVALUE, &val );
     }
 
     return 0;
@@ -267,6 +268,7 @@ static int dvdplay_SetProgram( input_thread_t *     p_input,
 static int dvdplay_SetArea( input_thread_t * p_input, input_area_t * p_area )
 {
     dvd_data_t *    p_dvd;
+    vlc_value_t     val;
 
     p_dvd = (dvd_data_t*)p_input->p_access_data;
 
@@ -276,18 +278,22 @@ static int dvdplay_SetArea( input_thread_t * p_input, input_area_t * p_area )
     if( p_area != p_input->stream.p_selected_area )
     {
         int i_chapter;
-        
+
         /* prevent intf to try to seek */
         p_input->stream.b_seekable = 0;
-        
+
         /* Store selected chapter */
         i_chapter = p_area->i_part;
 
         dvdNewArea( p_input, p_area );
-        
+
+        /* Reinit ES */
+        dvdNewPGC( p_input );
+
         dvdplay_start( p_dvd->vmg, p_area->i_id );
-        
+
         p_area->i_part = i_chapter;
+
     } /* i_title >= 0 */
     else
     {
@@ -298,7 +304,7 @@ static int dvdplay_SetArea( input_thread_t * p_input, input_area_t * p_area )
      * Chapter selection
      */
 
-    if( p_area->i_part != dvdplay_chapter_cur( p_dvd->vmg ) )
+    if( (int)p_area->i_part != dvdplay_chapter_cur( p_dvd->vmg ) )
     {
         if( ( p_area->i_part > 0 ) &&
             ( p_area->i_part <= p_area->i_part_nb ))
@@ -313,6 +319,10 @@ static int dvdplay_SetArea( input_thread_t * p_input, input_area_t * p_area )
         LB2OFF( dvdplay_position( p_dvd->vmg ) ) - p_area->i_start;
     p_input->stream.b_changed = 1;
 
+    /* Update the navigation variables without triggering a callback */
+    val.i_int = p_area->i_part;
+    var_Change( p_input, "chapter", VLC_VAR_SETVALUE, &val );
+
     return 0;
 }
 
@@ -347,7 +357,7 @@ static int dvdplay_Read( input_thread_t * p_input,
 static void dvdplay_Seek( input_thread_t * p_input, off_t i_off )
 {
     dvd_data_t *     p_dvd;
-    
+
     p_dvd = (dvd_data_t *)p_input->p_access_data;
 
     vlc_mutex_lock( &p_input->stream.stream_lock );
@@ -374,11 +384,11 @@ static void pf_vmg_callback( void* p_args, dvdplay_event_t event )
     input_thread_t *    p_input;
     dvd_data_t *        p_dvd;
     vlc_value_t         val;
-    int                 i;
+    unsigned int        i;
 
     p_input = (input_thread_t*)p_args;
     p_dvd   = (dvd_data_t*)p_input->p_access_data;
-    
+
     switch( event )
     {
     case NEW_DOMAIN:
@@ -386,14 +396,13 @@ static void pf_vmg_callback( void* p_args, dvdplay_event_t event )
     case NEW_VTS:
         break;
     case NEW_FILE:
-
         break;
     case NEW_PGC:
         /* prevent intf to try to seek  by default */
         p_input->stream.b_seekable = 0;
 
-        if( ( i = dvdplay_title_cur( p_dvd->vmg ) ) != 
-                p_input->stream.p_selected_area->i_id )
+        i = dvdplay_title_cur( p_dvd->vmg );
+        if( i != p_input->stream.p_selected_area->i_id )
         {
             /* the title number has changed: update area */
             msg_Warn( p_input, "new title %d (%d)", i,
@@ -404,7 +413,7 @@ static void pf_vmg_callback( void* p_args, dvdplay_event_t event )
 
         /* new pgc in same title: reinit ES */
         dvdNewPGC( p_input );
-        
+
         p_input->stream.b_changed = 1;
 
         break;
@@ -412,6 +421,17 @@ static void pf_vmg_callback( void* p_args, dvdplay_event_t event )
         /* update current chapter */
         p_input->stream.p_selected_area->i_part =
             dvdplay_chapter_cur( p_dvd->vmg );
+
+        p_input->stream.p_selected_area->i_tell =
+            LB2OFF( dvdplay_position( p_dvd->vmg ) ) -
+            p_input->stream.p_selected_area->i_start;
+
+        /* warn interface that something has changed */
+        p_input->stream.b_changed = 1;
+
+        /* Update the navigation variables without triggering a callback */
+        val.i_int = p_input->stream.p_selected_area->i_part;
+        var_Change( p_input, "chapter", VLC_VAR_SETVALUE, &val );
         break;
     case NEW_CELL:
         p_dvd->b_end_of_cell = 0;
@@ -439,23 +459,32 @@ static void pf_vmg_callback( void* p_args, dvdplay_event_t event )
             /* Retrieve the highlight from dvdplay */
             dvdplay_highlight( p_dvd->vmg, &p_dvd->hli );
 
-            /* Fill our internal variables with this data */
-            val.i_int = p_dvd->hli.i_x_start;
-            var_Set( p_input, "x-start", val );
-            val.i_int = p_dvd->hli.i_y_start;
-            var_Set( p_input, "y-start", val );
-            val.i_int = p_dvd->hli.i_x_end;
-            var_Set( p_input, "x-end", val );
-            val.i_int = p_dvd->hli.i_y_end;
-            var_Set( p_input, "y-end", val );
-
-            val.p_address = (void *)p_dvd->hli.pi_color;
-            var_Set( p_input, "color", val );
-            val.p_address = (void *)p_dvd->hli.pi_contrast;
-            var_Set( p_input, "contrast", val );
-
-            /* Tell the SPU decoder that there's a new highlight */
-            val.b_bool = VLC_TRUE;
+            if( p_dvd->hli.i_x_start || p_dvd->hli.i_y_start ||
+                p_dvd->hli.i_x_end || p_dvd->hli.i_y_end )
+            {
+                /* Fill our internal variables with this data */
+                val.i_int = p_dvd->hli.i_x_start;
+                var_Set( p_input, "x-start", val );
+                val.i_int = p_dvd->hli.i_y_start;
+                var_Set( p_input, "y-start", val );
+                val.i_int = p_dvd->hli.i_x_end;
+                var_Set( p_input, "x-end", val );
+                val.i_int = p_dvd->hli.i_y_end;
+                var_Set( p_input, "y-end", val );
+
+                val.p_address = (void *)p_dvd->hli.pi_color;
+                var_Set( p_input, "color", val );
+                val.p_address = (void *)p_dvd->hli.pi_contrast;
+                var_Set( p_input, "contrast", val );
+
+                /* Tell the SPU decoder that there's a new highlight */
+                val.b_bool = VLC_TRUE;
+            }
+            else
+            {
+                /* Turn off the highlight */
+                val.b_bool = VLC_FALSE;
+            }
             var_Set( p_input, "highlight", val );
 
             vlc_mutex_unlock( p_mutex );
@@ -472,6 +501,7 @@ static int dvdNewArea( input_thread_t * p_input, input_area_t * p_area )
 {
     dvd_data_t *    p_dvd;
     int             i_angle_nb, i_angle;
+    vlc_value_t     val;
     int             i;
 
     p_dvd = (dvd_data_t*)p_input->p_access_data;
@@ -494,15 +524,27 @@ static int dvdNewArea( input_thread_t * p_input, input_area_t * p_area )
     {
         input_AddProgram( p_input, i+1, 0 );
     }
-    
-    dvdplay_SetProgram( p_input,
-                        p_input->stream.pp_programs[i_angle-1] ); 
 
-//    dvdNewPGC( p_input );
+    dvdplay_SetProgram( p_input,
+                        p_input->stream.pp_programs[i_angle-1] );
 
     /* No PSM to read in DVD mode, we already have all information */
     p_input->stream.p_selected_program->b_is_ok = 1;
 
+    /* Update the navigation variables without triggering a callback */
+    val.i_int = p_area->i_id;
+    var_Change( p_input, "title", VLC_VAR_SETVALUE, &val );
+    var_Change( p_input, "chapter", VLC_VAR_CLEARCHOICES, NULL );
+    for( i = 1; (unsigned int)i <= p_area->i_part_nb; i++ )
+    {
+        val.i_int = i;
+        var_Change( p_input, "chapter", VLC_VAR_ADDCHOICE, &val );
+    }
+
+    /* Update the navigation variables without triggering a callback */
+    val.i_int = p_area->i_part;
+    var_Change( p_input, "chapter", VLC_VAR_SETVALUE, &val );
+
     return 0;
 }
 
@@ -514,7 +556,7 @@ static int dvdNewPGC( input_thread_t * p_input )
 //    int             i_subp_nr   = -1;
 //    int             i_subp      = -1;
 //    int             i_sec;
-    
+
     p_dvd = (dvd_data_t*)p_input->p_access_data;
 
 //    dvdplay_audio_info( p_dvd->vmg, &i_audio_nr, &i_audio );
@@ -536,7 +578,7 @@ static int dvdNewPGC( input_thread_t * p_input )
     {
         p_input->stream.b_seekable = 0;
     }
-    
+
 #if 0
     i_sec = dvdplay_title_time( p_dvd->vmg );
     msg_Dbg( p_input, "title time: %d:%02d:%02d (%d)",
@@ -545,4 +587,3 @@ static int dvdNewPGC( input_thread_t * p_input )
 
     return 0;
 }
-