[MPlayer-dev-eng] [PATCH] fix -subcc for TiVo/tystreams

Doug Swarin dswarin at gmail.com
Wed Sep 27 17:17:47 CEST 2006


Some time ago I wrote a patch that fixed -subcc to work for TiVo
streams, so that closed captions would display properly.

I sent the patch in to the list, but other than some comments about
the patch itself (which I attempted to rectify) I received no mail
about the actual fixes.

If possible, I would like to have this patch integrated into the main
trunk. Without it, closed caption display simply does not work on
streams extracted from a TiVo.

The patch does change -subcc to take an argument (specifying which
caption streams to display). I have updated the documentation to the
best of my ability.

Thank you very much for your time,
Doug Swarin
-------------- next part --------------
Index: DOCS/man/zh/mplayer.1
===================================================================
--- DOCS/man/zh/mplayer.1	(revision 19993)
+++ DOCS/man/zh/mplayer.1	(working copy)
@@ -854,7 +854,7 @@
 ??????????OSD????????????. ????????????????????????????????????????????.
 255????????0????????.
 .TP
-.B \-subcc \
+.B \-subcc 1 \
 ????DVD????????????????(CC)????.
 ????????VOB????, ????????????????????????????????ASCII????,
 ??????????????????1??VOB??????????????.
Index: DOCS/man/en/mplayer.1
===================================================================
--- DOCS/man/en/mplayer.1	(revision 19993)
+++ DOCS/man/en/mplayer.1	(working copy)
@@ -2145,13 +2145,16 @@
 .PD 1
 .
 .TP
-.B "\-subcc \ "
-Display DVD Closed Caption (CC) subtitles.
+.B "\-subcc <0\-3> \ "
+Display Closed Caption (CC) or Extended Data Service (XDS) subtitles.
 These are
 .B not
 the VOB subtitles, these are special ASCII subtitles for the
 hearing impaired encoded in the VOB userdata stream on most region 1 DVDs.
 CC subtitles have not been spotted on DVDs from other regions so far.
+.
+Passing -subcc 1 will show Closed Caption subtitles. Passing -subcc 2 will
+show XDS subtitles. Passing -subcc 3 will show both types.
 .
 .TP
 .B \-subcp <codepage> (iconv only)
Index: DOCS/man/cs/mplayer.1
===================================================================
--- DOCS/man/cs/mplayer.1	(revision 19993)
+++ DOCS/man/cs/mplayer.1	(working copy)
@@ -2009,7 +2009,7 @@
 .PD 1
 .
 .TP
-.B "\-subcc \ "
+.B "\-subcc 1 \ "
 Zobrazovat DVD Closed Caption (CC) titulky.
 Toto
 .B nejsou
Index: DOCS/man/es/mplayer.1
===================================================================
--- DOCS/man/es/mplayer.1	(revision 19993)
+++ DOCS/man/es/mplayer.1	(working copy)
@@ -1535,7 +1535,7 @@
 .PD 1
 .
 .TP
-.B "\-subcc \ "
+.B "\-subcc 1 \ "
 Muestra subt?culos de DVD Closed Caption (CC).
 Esto no es los subt?tulos VOB, son subt?tulos especiales ASCII codificados
 para el que no oye bien en el flujo de datos de usuario VOB en la mayor?a de los
Index: DOCS/man/fr/mplayer.1
===================================================================
--- DOCS/man/fr/mplayer.1	(revision 19993)
+++ DOCS/man/fr/mplayer.1	(working copy)
@@ -2245,7 +2245,7 @@
 .PD 1
 .
 .TP
-.B "\-subcc \ "
+.B "\-subcc 1 \ "
 Affiche les sous-titres DVD Closed Caption (CC).
 Ce ne sont
 .B pas
Index: DOCS/man/de/mplayer.1
===================================================================
--- DOCS/man/de/mplayer.1	(revision 19993)
+++ DOCS/man/de/mplayer.1	(working copy)
@@ -2252,7 +2252,7 @@
 .PD 1
 .
 .TP
-.B "\-subcc \ "
+.B "\-subcc 1 \ "
 Zeigt DVD-Closed-Caption-Untertitel (CC) an.
 Diese sind
 .B keine
Index: DOCS/man/sv/mplayer.1
===================================================================
--- DOCS/man/sv/mplayer.1	(revision 19993)
+++ DOCS/man/sv/mplayer.1	(working copy)
@@ -1513,7 +1513,7 @@
 .PD 1
 .
 .TP
-.B "\-subcc \ "
+.B "\-subcc 1 \ "
 Display DVD Closed Caption (CC) subtitles.
 These are NOT the VOB subtitles, these are special ASCII subtitles for the
 hearing impaired encoded in the VOB userdata stream on most region 1 DVDs.
Index: DOCS/man/pl/mplayer.1
===================================================================
--- DOCS/man/pl/mplayer.1	(revision 19993)
+++ DOCS/man/pl/mplayer.1	(working copy)
@@ -1651,7 +1651,7 @@
 .PD 1
 .
 .TP
-.B "\-subcc \ "
+.B "\-subcc 1 \ "
 Wy?wietla napisy DVD Closed Caption (CC).
 To
 .B nie
Index: DOCS/man/hu/mplayer.1
===================================================================
--- DOCS/man/hu/mplayer.1	(revision 19993)
+++ DOCS/man/hu/mplayer.1	(working copy)
@@ -2131,7 +2131,7 @@
 .PD 1
 .
 .TP
-.B "\-subcc \ "
+.B "\-subcc 1 \ "
 DVD Closed Caption (CC) feliratok megjelen?t?se.
 Ezek
 .B nem
Index: DOCS/man/it/mplayer.1
===================================================================
--- DOCS/man/it/mplayer.1	(revision 19993)
+++ DOCS/man/it/mplayer.1	(working copy)
@@ -2035,7 +2035,7 @@
 .PD 1
 .
 .TP
-.B "\-subcc \ "
+.B "\-subcc 1 \ "
 Visualizza i sottotitoli Close Caption (CC) dei DVD.
 Questi
 .B non
Index: cfg-common.h
===================================================================
--- cfg-common.h	(revision 19993)
+++ cfg-common.h	(working copy)
@@ -281,8 +281,7 @@
 	// specify IFO file for VOBSUB subtitle
 	{"ifo", &spudec_ifo, CONF_TYPE_STRING, 0, 0, 0, NULL},
 	// enable Closed Captioning display
-	{"subcc", &subcc_enabled, CONF_TYPE_FLAG, 0, 0, 1, NULL},
-	{"nosubcc", &subcc_enabled, CONF_TYPE_FLAG, 0, 1, 0, NULL},
+	{"subcc", &subcc_enabled, CONF_TYPE_INT, 0, 0, 1, NULL},
 	{"overlapsub", &suboverlap_enabled, CONF_TYPE_FLAG, 0, 0, 2, NULL},
 	{"nooverlapsub", &suboverlap_enabled, CONF_TYPE_FLAG, 0, 0, 0, NULL},
 	{"sub-bg-color", &sub_bg_color, CONF_TYPE_INT, CONF_RANGE, 0, 255, NULL},
Index: libmpdemux/demux_ty.c
===================================================================
--- libmpdemux/demux_ty.c	(revision 19993)
+++ libmpdemux/demux_ty.c	(working copy)
@@ -116,7 +116,7 @@
 } TiVoInfo;
 
 off_t vstream_streamsize( );
-void ty_ClearOSD( int start );
+void ty_ClearOSD( int start, int osd );
 
 // ===========================================================================
 #define TMF_SIG "showing.xml"
@@ -1332,7 +1332,7 @@
    }
 	if ( subcc_enabled )
 	{
-	   ty_ClearOSD( 0 );
+	   ty_ClearOSD( 0, 0 );
 	}
 }
 
Index: libmpdemux/demux_ty_osd.c
===================================================================
--- libmpdemux/demux_ty_osd.c	(revision 19993)
+++ libmpdemux/demux_ty_osd.c	(working copy)
@@ -46,6 +46,7 @@
 #define TY_CCPAINTON  (  1 )
 
 #define TY_CC_MAX_X   ( 45 )
+#define TY_CC_MAX_Y   (  4 )
 
 static int      TY_CC_CUR_X;
 static int      TY_CC_CUR_Y;
@@ -65,21 +66,33 @@
 
 static void ty_DrawOSD(void)
 {
+	int index;
 	// printf( "Calling ty_DrawOSD()\n" );
+    for ( index = 1; index < SUB_MAX_TEXT ; index++ )
+	{
+		memcpy( ty_OSD1.text[ index ], ty_OSD2.text[ index ], TY_CC_MAX_X - 1 );
+		ty_OSD1.text[ index ][ TY_CC_MAX_X - 1 ] = 0;
+	}
 	tyOSDUpdate = 1;
 }
 
-void ty_ClearOSD( int start )
+void ty_ClearOSD( int start, int osd )
 {
 	int index;
 	// printf( "Calling ty_ClearOSD()\n" );
    for ( index = start ; index < SUB_MAX_TEXT ; index++ )
 	{
+		if ( osd == 0 || osd == 1 )
+		{
 		memset( ty_OSD1.text[ index ], ' ', TY_CC_MAX_X - 1 );
 		ty_OSD1.text[ index ][ TY_CC_MAX_X - 1 ] = 0;
+		}
+		if ( osd == 0 || osd == 2 )
+		{
 		memset( ty_OSD2.text[ index ], ' ', TY_CC_MAX_X - 1 );
 		ty_OSD2.text[ index ][ TY_CC_MAX_X - 1 ] = 0;
 	}
+	}
 }
 
 static void ty_DrawChar( int *x, int *y, char disChar, int fgColor, int bgColor )
@@ -99,11 +112,11 @@
 	   cy = SUB_MAX_TEXT - TY_CC_Y_Offset - 1;
    }
 
-	// printf( "Calling ty_DrawChar() x:%d y:%d %c fg:%d bg:%d\n",
+	// printf( "Calling ty_DrawChar() x:%d y:%d '%c' fg:%d bg:%d\n",
 	// 	cx, cy, disChar, fgColor, bgColor );
 
-   ty_OSD1.text[ TY_CC_Y_Offset + cy ][ cx ] = disChar;
-   memset( &( ty_OSD1.text[ TY_CC_Y_Offset + cy ][ cx + 1 ] ), ' ',
+   ty_OSD2.text[ TY_CC_Y_Offset + cy ][ cx ] = disChar;
+   memset( &( ty_OSD2.text[ TY_CC_Y_Offset + cy ][ cx + 1 ] ), ' ',
       TY_CC_MAX_X - cx - 2 );
 	( *x )++;
 }
@@ -117,31 +130,31 @@
 	//
 	if ( ( source + TY_CC_Y_Offset + numLines ) > SUB_MAX_TEXT )
 	{
-      ty_ClearOSD( 1 );
+      ty_ClearOSD( 1, 1 );
 		return;
 	}
 
 	if ( ( source + TY_CC_Y_Offset + numLines ) < 0 )
 	{
-      ty_ClearOSD( 1 );
+      ty_ClearOSD( 1, 1 );
 		return;
 	}
 
 	if ( numLines > SUB_MAX_TEXT )
 	{
-      ty_ClearOSD( 1 );
+      ty_ClearOSD( 1, 1 );
 		return;
 	}
 
 	for ( index = 0 ; index < numLines ; index++ )
 	{
-		strcpy( ty_OSD1.text[ TY_CC_Y_Offset + dest ],
-			ty_OSD1.text[ TY_CC_Y_Offset + source ] );
+		strcpy( ty_OSD2.text[ TY_CC_Y_Offset + dest ],
+			ty_OSD2.text[ TY_CC_Y_Offset + source ] );
 	   dest++;
 		source++;
 	}
-	memset( ty_OSD1.text[ TY_CC_Y_Offset + source - 1 ], ' ', TY_CC_MAX_X - 1 );
-	ty_OSD1.text[ TY_CC_Y_Offset + source - 1 ][ TY_CC_MAX_X - 1 ] = 0;
+	memset( ty_OSD2.text[ TY_CC_Y_Offset + source - 1 ], ' ', TY_CC_MAX_X - 1 );
+	ty_OSD2.text[ TY_CC_Y_Offset + source - 1 ][ TY_CC_MAX_X - 1 ] = 0;
 }
 
 static void ty_drawchar( char c )
@@ -185,6 +198,8 @@
    11, -1, 1, 2, 3, 4, 12, 13, 14, 15, 5, 6, 7, 8, 9, 10 
 };
 
+// these are kind of poor substitutes for the actual special characters
+char specialchar[] = { 'R', 'o', '/', '?', '*', 'c', 'E', '/', 'a', ' ', 'e', 'a', 'e', 'i', 'o', 'u' };
 // char specialchar[] = { '??', '??', '??', '??', '*', '??', '??', 14, '??', ' ', '??', '??', '??', '??', '??', '??' };
 
 static int ty_CCdecode( char b1, char b2 )
@@ -235,15 +250,19 @@
          TY_CC_CUR_Y = CC_row[ ( ( b1 << 1 ) & 14 ) | ( ( b2 >> 5 ) & 1 ) ];
 
 			// Offset into MPlayer's Buffer
-			if ( ( TY_CC_CUR_Y >= 1 ) && ( TY_CC_CUR_Y <= 4 ) )
+         		if ( TY_CC_stat > TY_CCPAINTON ) {
+				TY_CC_CUR_Y = TY_CC_MAX_Y;
+				TY_CC_Y_Offset = SUB_MAX_TEXT - 5 - 1;
+			}
+			else if ( ( TY_CC_CUR_Y >= 1 ) && ( TY_CC_CUR_Y <= 4 ) )
 			{
 				TY_CC_Y_Offset = SUB_MAX_TEXT - 5 - 1;
 			}
-			if ( ( TY_CC_CUR_Y >= 5 ) && ( TY_CC_CUR_Y <= 10 ) )
+			else if ( ( TY_CC_CUR_Y >= 5 ) && ( TY_CC_CUR_Y <= 10 ) )
 			{
 				TY_CC_Y_Offset = SUB_MAX_TEXT - 5 - 5;
 			}
-			if ( ( TY_CC_CUR_Y >= 12 ) && ( TY_CC_CUR_Y <= 15 ) )
+			else if ( ( TY_CC_CUR_Y >= 12 ) && ( TY_CC_CUR_Y <= 15 ) )
 			{
 				TY_CC_Y_Offset = SUB_MAX_TEXT - 5 - 12;
 			}
@@ -332,8 +351,8 @@
                      } 
                      else 
                      {
-                        // ty_drawchar(specialchar[ b2 & 0x0f ] );
-                        ty_drawchar( ' ' );
+                        ty_drawchar( specialchar[ b2 & 0x0f ] );
+                        // ty_drawchar( ' ' );
                      }
                      break;
                   }
@@ -352,7 +371,7 @@
                   {
                      if ( TY_OSD_flags & TY_OSD_MODE && 
                         TY_CC_stat != TY_CCPOPUP ) 
-								ty_ClearOSD( 1 );
+								ty_ClearOSD( 1, 2 );
                      TY_CC_stat = TY_CCPOPUP;
                      break;
                   }
@@ -365,9 +384,10 @@
               
                   case 0x25 ... 0x27:       // 2-4 row captions
                   {
-                     if ( TY_CC_stat == TY_CCPOPUP ) ty_ClearOSD( 1 );
+                     if ( TY_CC_stat == TY_CCPOPUP ) ty_ClearOSD( 1, 2 );
                      TY_CC_stat = b2 - 0x23;
-                     if ( TY_CC_CUR_Y < TY_CC_stat ) TY_CC_CUR_Y = TY_CC_stat;
+		     TY_CC_CUR_Y = TY_CC_MAX_Y;
+		     TY_CC_Y_Offset = SUB_MAX_TEXT - 5 - 1;
                      break;
                   }
 
@@ -396,12 +416,12 @@
                      {
                         if ( TY_CC_stat > TY_CCPOPUP || TY_CC_ptr == TY_CC_buf ) 
                         {
-                           ty_ClearOSD( 1 );
+                           ty_ClearOSD( 1, 1 );
                            ty_draw();
                         } 
                         else 
                         { 
-                           ty_ClearOSD( 1 );
+                           ty_ClearOSD( 1, 1 );
 
                            // CRW - 
                            // new buffer
@@ -441,7 +461,7 @@
                      if ( TY_OSD_debug && TY_CC_ptr != TY_CC_buf )
                         mp_msg( MSGT_DEMUX, MSGL_DBG3, "(TY_OSD_debug) %s\n", 
                            TY_CC_buf );
-                     if ( TY_OSD_flags & TY_OSD_MODE ) ty_ClearOSD( 1 );
+                     if ( TY_OSD_flags & TY_OSD_MODE ) ty_ClearOSD( 1, 2 );
 
                      TY_CC_CUR_X = 1;
                      TY_CC_CUR_Y = -1;
@@ -870,7 +890,7 @@
 				ty_OSD1.text[ index ] = malloc( TY_CC_MAX_X );
 				ty_OSD2.text[ index ] = malloc( TY_CC_MAX_X );
 			}
-			ty_ClearOSD( 0 );
+			ty_ClearOSD( 0, 0 );
 			ty_OSD1.lines = SUB_MAX_TEXT;
 			ty_OSD2.lines = SUB_MAX_TEXT;
 			ty_pOSD1 = &ty_OSD1;
@@ -879,11 +899,11 @@
 			tyOSDInited = 1;
 		}
 
-		if ( buf[ 0 ] == 0x01 )
+		if ( buf[ 0 ] == 0x01 && ( subcc_enabled & 0x01 ) )
 		{
 			ty_CCdecode( buf[ 1 ], buf[ 2 ] );
 		}
-		if ( buf[ 0 ] == 0x02 )
+		if ( buf[ 0 ] == 0x02 && ( subcc_enabled & 0x02 ) )
 		{
 			ty_XDSdecode( buf[ 1 ], buf[ 2 ] );
 		}


More information about the MPlayer-dev-eng mailing list