]> git.sesse.net Git - mlt/commitdiff
Fix waveform generation.
authorDan Dennedy <dan@dennedy.org>
Thu, 19 Aug 2010 04:45:02 +0000 (21:45 -0700)
committerDan Dennedy <dan@dennedy.org>
Thu, 19 Aug 2010 04:45:02 +0000 (21:45 -0700)
It was not obtaining a valid fps. Also, changed rendering to something
more expected - negative as negative and channels stacked.
Also, add a Python binding to this call to return 8-bit grayscale image
as a Python string. Finally, add a Python example.

src/framework/mlt_frame.c
src/swig/mlt.i
src/swig/python/waveforms.py [new file with mode: 0755]

index 4f394ca6ba88511e551d2e29dab230d4cbc6ca48..6630af5c4e97e7c250f0d10d6af3f3c489e74604 100644 (file)
@@ -694,7 +694,8 @@ unsigned char *mlt_frame_get_waveform( mlt_frame this, int w, int h )
        mlt_audio_format format = mlt_audio_s16;
        int frequency = 32000; // lower frequency available?
        int channels = 2;
-       double fps = mlt_profile_fps( NULL );
+       mlt_producer producer = mlt_frame_get_original_producer( this );
+       double fps = mlt_producer_get_fps( producer );
        int samples = mlt_sample_calculator( fps, frequency, mlt_frame_get_position( this ) );
 
        // Get the pcm data
@@ -721,13 +722,12 @@ unsigned char *mlt_frame_get_waveform( mlt_frame this, int w, int h )
                        // Determine sample's magnitude from 2s complement;
                        int pcm_magnitude = *pcm < 0 ? ~(*pcm) + 1 : *pcm;
                        // The height of a line is the ratio of the magnitude multiplied by
-                       // half the vertical resolution
-                       int height = ( int )( ( double )( pcm_magnitude ) / 32768 * h / 2 );
-                       // Determine the starting y coordinate - left channel above center,
-                       // right channel below - currently assumes 2 channels
-                       int displacement = ( h / 2 ) - ( 1 - j ) * height;
+                       // the vertical resolution of a single channel
+                       int height = h * pcm_magnitude / channels / 2 / 32768;
+                       // Determine the starting y coordinate - left top, right bottom
+                       int displacement = h * (j * 2 + 1) / channels / 2 - ( *pcm < 0 ? 0 : height );
                        // Position buffer pointer using y coordinate, stride, and x coordinate
-                       unsigned char *p = &bitmap[ i + displacement * w ];
+                       unsigned char *p = bitmap + i + displacement * w;
 
                        // Draw vertical line
                        for ( k = 0; k < height; k++ )
index 745ba59858264268be7e1f36e2c0e91101c707b4..61c4a47030f933528e6e7bd58c646f8b55c85357 100644 (file)
@@ -149,3 +149,28 @@ class RubyListener
 
 #endif
 
+#if defined(SWIGPYTHON)
+%{
+typedef struct {
+       int size;
+       char* data;
+} binary_data;
+
+binary_data frame_get_waveform( Mlt::Frame &frame, int w, int h )
+{
+       binary_data result = {
+               w * h,
+               (char*) frame.get_waveform( w, h )
+       };
+       return result;
+}
+
+%}
+
+%typemap(out) binary_data {
+       $result = PyString_FromStringAndSize( $1.data, $1.size );
+}
+
+binary_data frame_get_waveform(Mlt::Frame&, int, int);
+
+#endif
diff --git a/src/swig/python/waveforms.py b/src/swig/python/waveforms.py
new file mode 100755 (executable)
index 0000000..c65fdd7
--- /dev/null
@@ -0,0 +1,14 @@
+#!/usr/bin/env python
+# -*- coding: utf-8 -*-
+import mlt
+from PIL import Image
+
+mlt.Factory.init()
+profile = mlt.Profile()
+prod = mlt.Producer(profile, 'test.wav')
+size = (320, 240)
+for i in range(0, prod.get_length()):
+  frm = prod.get_frame()
+  wav = mlt.frame_get_waveform(frm, size[0], size[1])
+  img = Image.fromstring('L', size, wav)
+  img.save('test-%04d.pgm' % (i))