コード例 #1
0
ファイル: decssasub.c プロジェクト: pylam/HandBrake
/*
 * Decodes a single SSA packet to one or more TEXTSUB or PICTURESUB subtitle packets.
 *
 * SSA packet format:
 * ( Dialogue: Marked,Start,End,Style,Name,MarginL,MarginR,MarginV,Effect,Text CR LF ) +
 *             1      2     3   4     5    6       7       8       9      10
 */
static hb_buffer_t *ssa_decode_packet( hb_work_object_t * w, hb_buffer_t *in )
{
    // Store NULL after the end of the buffer to make using string processing safe
    hb_buffer_realloc(in, ++in->size);
    in->data[in->size - 1] = '\0';

    hb_buffer_list_t list;
    hb_buffer_t *buf;

    hb_buffer_list_clear(&list);
    const char *EOL = "\r\n";
    char *curLine, *curLine_parserData;
    for ( curLine = strtok_r( (char *) in->data, EOL, &curLine_parserData );
          curLine;
          curLine = strtok_r( NULL, EOL, &curLine_parserData ) )
    {
        // Skip empty lines and spaces between adjacent CR and LF
        if (curLine[0] == '\0')
            continue;

        // Decode an individual SSA line
        buf = ssa_decode_line_to_mkv_ssa(w, in,
                                         (uint8_t *)curLine, strlen(curLine));
        hb_buffer_list_append(&list, buf);
    }

    return hb_buffer_list_clear(&list);
}
コード例 #2
0
ファイル: decssasub.c プロジェクト: LiminWang/HandBrake
static int decssaWork( hb_work_object_t * w, hb_buffer_t ** buf_in,
                        hb_buffer_t ** buf_out )
{
    hb_buffer_t * in = *buf_in;

#if SSA_VERBOSE_PACKETS
    printf("\nPACKET(%"PRId64",%"PRId64"): %.*s\n", in->s.start/90, in->s.stop/90, in->size, in->data);
#endif

    *buf_in = NULL;
    *buf_out = in;
    if (in->s.flags & HB_BUF_FLAG_EOF)
    {
        return HB_WORK_DONE;
    }

    // Not much to do here.  ffmpeg already supplies SSA subtitles in the
    // requried matroska packet format.
    //
    // We require string termination of the buffer
    hb_buffer_realloc(in, ++in->size);
    in->data[in->size - 1] = '\0';

    return HB_WORK_OK;
}
コード例 #3
0
ファイル: decssasub.c プロジェクト: Inner-room/HandBrake
static hb_buffer_t * ssa_to_mkv_ssa( hb_work_object_t * w,  hb_buffer_t * in )
{
    hb_buffer_t * out_last = NULL;
    hb_buffer_t * out_first = NULL;

    // Store NULL after the end of the buffer to make using string processing safe
    hb_buffer_realloc(in, ++in->size);
    in->data[in->size - 1] = '\0';

    const char *EOL = "\r\n";
    char *curLine, *curLine_parserData;
    for ( curLine = strtok_r( (char *) in->data, EOL, &curLine_parserData );
          curLine;
          curLine = strtok_r( NULL, EOL, &curLine_parserData ) )
    {
        hb_buffer_t * out;

        out = ssa_decode_line_to_mkv_ssa( w, (uint8_t *) curLine, strlen( curLine ), in->sequence );
        if( out )
        {
            if ( out_last == NULL )
            {
                out_last = out_first = out;
            }
            else
            {
                out_last->next = out;
                out_last = out;
            }
        }
    }

    return out_first;
}
コード例 #4
0
ファイル: muxavi.c プロジェクト: 273657127/HandBrake
static void IndexAddInt32( hb_buffer_t * b, uint32_t val )
{
    if( b->size + 16 > b->alloc )
    {
        hb_log( "muxavi: reallocing index (%d MB)",
                1 + b->alloc / 1024 / 1024 );
        hb_buffer_realloc( b, b->alloc + 1024 * 1024 );
    }

    b->data[b->size++] = val & 0xFF;
    b->data[b->size++] = ( val >> 8 ) & 0xFF;
    b->data[b->size++] = ( val >> 16 ) & 0xFF;
    b->data[b->size++] = val >> 24;
}
コード例 #5
0
ファイル: dectx3gsub.c プロジェクト: betabot7/HandBrakeMirror
static int dectx3gWork( hb_work_object_t * w, hb_buffer_t ** buf_in,
                        hb_buffer_t ** buf_out )
{
    hb_buffer_t * in = *buf_in;
    hb_buffer_t * out = NULL;
    
    // Warn if the subtitle's duration has not been passed through by the demuxer,
    // which will prevent the subtitle from displaying at all
    if ( in->s.stop == 0 ) {
        hb_log( "dectx3gsub: subtitle packet lacks duration" );
    }
    
    if ( in->size > 0 ) {
        out = tx3g_decode_to_utf8(in);
    } else {
        out = hb_buffer_init( 0 );
    }
    
    if ( out != NULL ) {
        // We shouldn't be storing the extra NULL character,
        // but the MP4 muxer expects this, unfortunately.
        if (out->size > 0 && out->data[out->size - 1] != '\0')
        {
            hb_buffer_realloc(out, ++out->size);
            out->data[out->size - 1] = '\0';
        }
        
        // If the input packet was non-empty, do not pass through
        // an empty output packet (even if the subtitle was empty),
        // as this would be interpreted as an end-of-stream
        if ( in->size > 0 && out->size == 0 ) {
            hb_buffer_close(&out);
        }
    }
    
    // Dispose the input packet, as it is no longer needed
    hb_buffer_close(&in);
    
    *buf_in = NULL;
    *buf_out = out;
    return HB_WORK_OK;
}
コード例 #6
0
void hb_srt_to_ssa(hb_buffer_t *sub_in, int line)
{
    if (sub_in->size == 0)
        return;

    // null terminate input if not already terminated
    if (sub_in->data[sub_in->size-1] != 0)
    {
        hb_buffer_realloc(sub_in, ++sub_in->size);
        sub_in->data[sub_in->size - 1] = 0;
    }
    char * srt = (char*)sub_in->data;
    // SSA markup expands a little over SRT, so allocate a bit of extra
    // space.  More will be realloc'd if needed.
    hb_buffer_t * sub = hb_buffer_init(sub_in->size + 80);
    char * ssa, *ssa_markup;
    int skip, len, pos, ii;

    // Exchange data between input sub and new ssa_sub
    // After this, sub_in contains ssa data
    hb_buffer_swap_copy(sub_in, sub);
    ssa = (char*)sub_in->data;

    sprintf((char*)sub_in->data, "%d,,Default,,0,0,0,,", line);
    pos = strlen((char*)sub_in->data);

    ii = 0;
    while (srt[ii] != '\0')
    {
        if ((ssa_markup = srt_markup_to_ssa(srt + ii, &skip)) != NULL)
        {
            len = strlen(ssa_markup);
            hb_buffer_realloc(sub_in, pos + len + 1);
            // After realloc, sub_in->data may change
            ssa = (char*)sub_in->data;
            sprintf(ssa + pos, "%s", ssa_markup);
            free(ssa_markup);
            pos += len;
            ii += skip;
        }
        else
        {
            hb_buffer_realloc(sub_in, pos + 4);
            // After realloc, sub_in->data may change
            ssa = (char*)sub_in->data;
            if (srt[ii] == '\r')
            {
                ssa[pos++] = '\\';
                ssa[pos++] = 'N';
                ii++;
                if (srt[ii] == '\n')
                {
                    ii++;
                }
            }
            else if (srt[ii] == '\n')
            {
                ssa[pos++] = '\\';
                ssa[pos++] = 'N';
                ii++;
            }
            else
            {
                ssa[pos++] = srt[ii++];
            }
        }
    }
    ssa[pos] = '\0';
    sub_in->size = pos + 1;
    hb_buffer_close(&sub);
}
コード例 #7
0
ファイル: decssasub.c プロジェクト: Inner-room/HandBrake
/*
 * Decodes a single SSA packet to one or more TEXTSUB or PICTURESUB subtitle packets.
 * 
 * SSA packet format:
 * ( Dialogue: Marked,Start,End,Style,Name,MarginL,MarginR,MarginV,Effect,Text CR LF ) +
 *             1      2     3   4     5    6       7       8       9      10
 */
static hb_buffer_t *ssa_decode_packet( hb_work_object_t * w, hb_buffer_t *in )
{
    // Store NULL after the end of the buffer to make using string processing safe
    hb_buffer_realloc(in, ++in->size);
    in->data[in->size - 1] = '\0';
    
    hb_buffer_t *out_list = NULL;
    hb_buffer_t **nextPtr = &out_list;

    const char *EOL = "\r\n";
    char *curLine, *curLine_parserData;
    for ( curLine = strtok_r( (char *) in->data, EOL, &curLine_parserData );
          curLine;
          curLine = strtok_r( NULL, EOL, &curLine_parserData ) )
    {
        // Skip empty lines and spaces between adjacent CR and LF
        if (curLine[0] == '\0')
            continue;
        
        // Decode an individual SSA line
        hb_buffer_t *out;
        if ( w->subtitle->config.dest == PASSTHRUSUB ) {
            out = ssa_decode_line_to_utf8( (uint8_t *) curLine, strlen( curLine ), in->sequence );
            if ( out == NULL )
                continue;
            
            // We shouldn't be storing the extra NULL character,
            // but the MP4 muxer expects this, unfortunately.
            if (out->size > 0 && out->data[out->size - 1] != '\0')
            {
                hb_buffer_realloc(out, ++out->size);
                out->data[out->size - 1] = '\0';
            }
            
            // If the input packet was non-empty, do not pass through
            // an empty output packet (even if the subtitle was empty),
            // as this would be interpreted as an end-of-stream
            if ( in->size > 0 && out->size == 0 ) {
                hb_buffer_close(&out);
                continue;
            }
        } else if ( w->subtitle->config.dest == RENDERSUB ) {
            out = ssa_decode_line_to_mkv_ssa( w, (uint8_t *) curLine, strlen( curLine ), in->sequence );
            if ( out == NULL )
                continue;
        }
        
        // Append 'out' to 'out_list'
        *nextPtr = out;
        nextPtr = &out->next;
    }

    // For point-to-point encoding, when the start time of the stream 
    // may be offset, the timestamps of the subtitles must be offset as well.
    //
    // HACK: Here we are making the assumption that, under normal circumstances,
    //       the output display time of the first output packet is equal to the
    //       display time of the input packet.
    //      
    //       During point-to-point encoding, the display time of the input 
    //       packet will be offset to compensate.
    //      
    //       Therefore we offset all of the output packets by a slip amount 
    //       such that first output packet's display time aligns with the 
    //       input packet's display time. This should give the correct time 
    //       when point-to-point encoding is in effect.
    if (out_list && out_list->s.start > in->s.start)
    {
        int64_t slip = out_list->s.start - in->s.start;
        hb_buffer_t *out;

        out = out_list;
        while (out)
        {
            out->s.start -= slip;
            out->s.stop -= slip;
            out = out->next;
        }
    }
    
    return out_list;
}