]> git.sesse.net Git - mlt/commitdiff
added filter_channelcopy.
authorddennedy <ddennedy@d19143bc-622f-0410-bfdd-b5b2a6649095>
Wed, 17 Mar 2004 21:36:59 +0000 (21:36 +0000)
committerddennedy <ddennedy@d19143bc-622f-0410-bfdd-b5b2a6649095>
Wed, 17 Mar 2004 21:36:59 +0000 (21:36 +0000)
enhance filter_resample to reproduce channels when producer does not create as many as consumer requested.

git-svn-id: https://mlt.svn.sourceforge.net/svnroot/mlt/trunk/mlt@217 d19143bc-622f-0410-bfdd-b5b2a6649095

docs/services.txt
src/modules/avformat/producer_avformat.c
src/modules/core/Makefile
src/modules/core/configure
src/modules/core/factory.c
src/modules/core/filter_channelcopy.c [new file with mode: 0644]
src/modules/core/filter_channelcopy.h [new file with mode: 0644]
src/modules/resample/filter_resample.c

index 10d25a03ba63cdeafe2498f707c7252152e4d597..74672b9f9e770ccb51b66c53b0d2079d4fbea574 100644 (file)
@@ -518,6 +518,31 @@ Filters
                Known Bugs
                
                        Does not go completely to black or white.
+                       
+       
+       channelcopy
+       
+               Description
+               
+                       Copy audio from one channel to another channel.
+                       
+               Constructor Argument
+               
+                       to - the 0-indexed channel to copy into, default is 1.
+                       
+               Mutable Properties
+               
+                       int to - see above
+                       int from - the channel from which to copy, default is 0.
+                       
+               Dependencies
+               
+                       none
+                       
+               Known Bugs
+               
+                       none
+                       
 
 
        deinterlace
@@ -754,7 +779,9 @@ Filters
 
                Description
 
-                       Adjust an audio stream's sampling rate.
+                       Adjust an audio stream's sampling rate, and duplicate channels if 
+                       producer provides less than consumer requested.
+                       
                        This filter is automatically invoked by Fezzik for the sake of
                        normalisation over inputs and with the consumer.
 
@@ -777,7 +804,8 @@ Filters
 
                Known Bugs
 
-                       none
+                       Assumes 2 channels during libsamplerate initialisation. Untested
+                       with >2 channels.
 
        rescale
 
index 773632ab94523b9bff351d702c463b8fa5cd2d6a..6ebd5683a63de1cc609d07329631fb72b12926b8 100644 (file)
@@ -41,6 +41,7 @@ static int producer_get_frame( mlt_producer this, mlt_frame_ptr frame, int index
 static int avformat_initialised = 0;
 static pthread_mutex_t avformat_mutex;
 
+#if 0
 void *av_malloc( unsigned int size )
 {
        return mlt_pool_alloc( size );
@@ -55,6 +56,7 @@ void av_free( void *ptr )
 {
        return mlt_pool_release( ptr );
 }
+#endif
 
 /** Constructor for libavformat.
 */
@@ -297,7 +299,7 @@ static int producer_open( mlt_producer this, char *file )
                        // Store selected audio and video indexes on properties
                        mlt_properties_set_int( properties, "audio_index", audio_index );
                        mlt_properties_set_int( properties, "video_index", video_index );
-
+                       
                        // We're going to cheat here - for a/v files, we will have two contexts (reasoning will be clear later)
                        if ( audio_index != -1 && video_index != -1 )
                        {
index fd7d0dff91d3e13d6a3dfafe517083d902bf0521..ac79e0a89ddd5e163f1edbf902e27fba89079690 100644 (file)
@@ -4,6 +4,7 @@ TARGET = ../libmltcore.so
 OBJS = factory.o \
           producer_ppm.o \
           filter_brightness.o \
+          filter_channelcopy.o \
           filter_greyscale.o \
           filter_gamma.o \
           filter_luma.o \
index 4660916f603ea012cc0b681915e8bb75fc29081a..ee29e18430aabcf8cdf69f7cbe385c84508cf4b5 100755 (executable)
@@ -10,6 +10,7 @@ EOF
 
 cat << EOF >> ../filters.dat
 brightness             libmltcore.so
+channelcopy            libmltcore.so
 gamma                  libmltcore.so
 greyscale              libmltcore.so
 luma                   libmltcore.so
@@ -28,4 +29,3 @@ region                        libmltcore.so
 EOF
 
 fi
-
index 1d037a0685f75237a381b273218080cd4a266bea..43f45913a212e802f75b6d546946e45a8a693e2d 100644 (file)
@@ -22,6 +22,7 @@
 
 #include "producer_ppm.h"
 #include "filter_brightness.h"
+#include "filter_channelcopy.h"
 #include "filter_gamma.h"
 #include "filter_luma.h"
 #include "filter_greyscale.h"
@@ -49,6 +50,8 @@ void *mlt_create_filter( char *id, void *arg )
 {
        if ( !strcmp( id, "brightness" ) )
                return filter_brightness_init( arg );
+       if ( !strcmp( id, "channelcopy" ) )
+               return filter_channelcopy_init( arg );
        if ( !strcmp( id, "gamma" ) )
                return filter_gamma_init( arg );
        if ( !strcmp( id, "greyscale" ) )
@@ -85,4 +88,3 @@ void *mlt_create_consumer( char *id, void *arg )
 {
        return NULL;
 }
-
diff --git a/src/modules/core/filter_channelcopy.c b/src/modules/core/filter_channelcopy.c
new file mode 100644 (file)
index 0000000..fd49d12
--- /dev/null
@@ -0,0 +1,103 @@
+/*
+ * filter_channelcopy.c -- copy one audio channel to another
+ * Copyright (C) 2003-2004 Ushodaya Enterprises Limited
+ * Author: Dan Dennedy <dan@dennedy.org>
+ *
+ * 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
+ * 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
+ * GNU General Public License for more details.
+ *
+ * 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-1307, USA.
+ */
+
+#include "filter_channelcopy.h"
+
+#include <framework/mlt_frame.h>
+
+#include <stdio.h>
+#include <stdlib.h>
+#define __USE_ISOC99 1
+#include <math.h>
+
+/** Get the audio.
+*/
+
+static int filter_get_audio( mlt_frame frame, int16_t **buffer, mlt_audio_format *format, int *frequency, int *channels, int *samples )
+{
+       // Get the properties of the a frame
+       mlt_properties properties = mlt_frame_properties( frame );
+       int i, j;
+       int from = mlt_properties_get_int( properties, "channelcopy.from" );
+       int to = mlt_properties_get_int( properties, "channelcopy.to" );
+
+       // Restore the original get_audio
+       frame->get_audio = mlt_properties_get_data( properties, "channelcopy.get_audio", NULL );
+
+       // Get the producer's audio
+       mlt_frame_get_audio( frame, buffer, format, frequency, channels, samples );
+
+       // Duplicate channels as necessary
+       {
+               int size = *channels * *samples * 2;
+               int16_t *new_buffer = mlt_pool_alloc( size );
+               
+               mlt_properties_set_data( properties, "audio", new_buffer, size, ( mlt_destructor )mlt_pool_release, NULL );
+               
+               // Duplicate the existing channels
+               for ( i = 0; i < *samples; i++ )
+               {
+                       for ( j = 0; j < *channels; j++ )
+                       {
+                               new_buffer[ ( i * *channels ) + j ] = (*buffer)[ ( i * *channels ) + ( j == to ? from : j ) ];
+                       }
+               }
+               *buffer = new_buffer;
+       }
+       return 0;
+}
+
+/** Filter processing.
+*/
+
+static mlt_frame filter_process( mlt_filter this, mlt_frame frame )
+{
+       mlt_properties properties = mlt_filter_properties( this );
+       mlt_properties frame_props = mlt_frame_properties( frame );
+
+       // Propogate the parameters
+       mlt_properties_set_int( frame_props, "channelcopy.to", mlt_properties_get_int( properties, "to" ) );
+       mlt_properties_set_int( frame_props, "channelcopy.from", mlt_properties_get_int( properties, "from" ) );
+
+       // Backup the original get_audio (it's still needed)
+       mlt_properties_set_data( frame_props, "channelcopy.get_audio", frame->get_audio, 0, NULL, NULL );
+
+       // Override the get_audio method
+       frame->get_audio = filter_get_audio;
+
+       return frame;
+}
+
+/** Constructor for the filter.
+*/
+
+mlt_filter filter_channelcopy_init( char *arg )
+{
+       mlt_filter this = mlt_filter_new( );
+       if ( this != NULL )
+       {
+               this->process = filter_process;
+               if ( arg != NULL )
+                       mlt_properties_set_int( mlt_filter_properties( this ), "to", atoi( arg ) );
+               else
+                       mlt_properties_set_int( mlt_filter_properties( this ), "to", 1 );
+       }
+       return this;
+}
diff --git a/src/modules/core/filter_channelcopy.h b/src/modules/core/filter_channelcopy.h
new file mode 100644 (file)
index 0000000..c958583
--- /dev/null
@@ -0,0 +1,28 @@
+/*
+ * filter_channelcopy.h -- copy audio channel from one to another
+ * Copyright (C) 2003-2004 Ushodaya Enterprises Limited
+ * Author: Dan Dennedy <dan@dennedy.org>
+ *
+ * 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
+ * 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
+ * GNU General Public License for more details.
+ *
+ * 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-1307, USA.
+ */
+
+#ifndef _FILTER_CHANNELCOPY_H_
+#define _FILTER_CHANNELCOPY_H_
+
+#include <framework/mlt_filter.h>
+
+extern mlt_filter filter_channelcopy_init( char *arg );
+
+#endif
index b8da7605d04672ffa1e639bb2e8f140a6c503bbd..57f9aadcc21304c470f9d597ede022f24107a66d 100644 (file)
@@ -43,6 +43,7 @@ static int resample_get_audio( mlt_frame frame, int16_t **buffer, mlt_audio_form
        SRC_DATA data;
        float *input_buffer = mlt_properties_get_data( properties, "resample.input_buffer", NULL );
        float *output_buffer = mlt_properties_get_data( properties, "resample.output_buffer", NULL );
+       int channels_avail = *channels;
        int i;
 
        if ( output_rate == 0 )
@@ -52,7 +53,29 @@ static int resample_get_audio( mlt_frame frame, int16_t **buffer, mlt_audio_form
        frame->get_audio = mlt_properties_get_data( properties, "resample.get_audio", NULL );
 
        // Get the producer's audio
-       mlt_frame_get_audio( frame, buffer, format, frequency, channels, samples );
+       mlt_frame_get_audio( frame, buffer, format, frequency, &channels_avail, samples );
+
+       // Duplicate channels as necessary
+       if ( channels_avail < *channels )
+       {
+               int size = *channels * *samples * 2;
+               int16_t *new_buffer = mlt_pool_alloc( size );
+               
+               mlt_properties_set_data( properties, "audio", new_buffer, size, ( mlt_destructor )mlt_pool_release, NULL );
+               
+               // Duplicate the existing channels
+               for ( i = 0; i < *samples; i++ )
+               {
+                       int j, k = 0;
+                       for ( j = 0; j < *channels; j++ )
+                       {
+                               new_buffer[ ( i * *channels ) + j ] = (*buffer)[ ( i * channels_avail ) + k ];
+                               k = ( k + 1 ) % channels_avail;
+                       }
+               }
+               
+               *buffer = new_buffer;
+       }
 
        // Return now if now work to do
        if ( output_rate == *frequency )
@@ -158,4 +181,3 @@ mlt_filter filter_resample_init( char *arg )
        }
        return this;
 }
-