--- /dev/null
+.. This file is part of TimeSide
+ @author: Thomas Fillon
+
+=============================
+ New analyzer Result example
+=============================
+
+Example of use of the new analyzerResult structure
+
+Usage : AnalyzerResult(data_mode=None, time_mode=None)
+
+See : :class:`timeside.analyzer.core.AnalyzerResult`
+
+Default
+=======
+
+Create a new analyzer result without arguments
+
+ >>> import timeside.analyzer.core as coreA
+ >>> res = coreA.AnalyzerResult()
+
+This default result has all the metadata and dataObject attribute
+
+ >>> res.keys()
+ ['data_mode', 'time_mode', 'id_metadata', 'data', 'audio_metadata', 'frame_metadata', 'label_metadata', 'parameters']
+
+ >>> for key,value in res.items():
+ ... print '%s : %s' % (key, value)
+ ...
+ data_mode : None
+ time_mode : None
+ id_metadata : {'description': '', 'author': '', 'version': '', 'date': '', 'id': '', 'unit': '', 'name': ''}
+ dataObject : {'duration': array([], dtype=float64), 'time': array([], dtype=float64), 'value': None, 'label': array([], dtype=int64)}
+ audio_metadata : {'duration': None, 'start': 0, 'channelsManagement': '', 'uri': '', 'channels': None}
+ frame_metadata : {'blocksize': None, 'samplerate': None, 'stepsize': None}
+ label_metadata : {'label_type': 'mono', 'description': None, 'label': None}
+ parameters : {}
+
+
+Specification of time_mode
+=========================
+Four different time_mode can be specified :
+
+- 'framewise' : Data are returned on a frame basis (i.e. with specified blocksize, stepsize and framerate)
+- 'global' : A global data value is return for the entire audio item
+- 'segment' : Data are returned on a segmnet basis (i.e. with specified start time and duration)
+- 'event' : Data are returned on a segment basis (i.e. with specified start time)
+
+
+Framewise
+---------
+
+>>> res = coreA.AnalyzerResult(time_mode='framewise')
+>>> res.keys()
+['data_mode', 'time_mode', 'id_metadata', 'data', 'audio_metadata', 'frame_metadata', 'label_metadata', 'parameters']
+
+Global
+------
+
+No frame metadata information is needed for these modes.
+The 'frame_metadata' key/attribute is deleted.
+
+>>> res = coreA.AnalyzerResult(time_mode='global')
+>>> res.keys()
+['data_mode', 'time_mode', 'id_metadata', 'data', 'audio_metadata', 'label_metadata', 'parameters']
+>>> res.data
+DataObject(value=None, label=array([], dtype=int64))
+
+Segment
+-------
+
+>>> res = coreA.AnalyzerResult(time_mode='segment')
+>>> res.keys()
+['data_mode', 'time_mode', 'id_metadata', 'data', 'audio_metadata', 'label_metadata', 'parameters']
+>>> res.data
+DataObject(value=None, label=array([], dtype=int64), time=array([], dtype=float64), duration=array([], dtype=float64))
+
+Event
+-----
+
+>>> res = coreA.AnalyzerResult(time_mode='event')
+>>> res.keys()
+['data_mode', 'time_mode', 'id_metadata', 'data', 'audio_metadata', 'label_metadata', 'parameters']
+>>> res.data
+DataObject(value=None, label=array([], dtype=int64), time=array([], dtype=float64))
+
+Specification of data_mode
+=========================
+Two different data_mode can be specified :
+
+- 'value' : Data are returned as numpy Array of arbitrary type
+- 'label' : Data are returned as label indexes (specified by the label_metadata key)
+
+Value
+-----
+The label_metadata key is deleted.
+
+>>> res = coreA.AnalyzerResult(data_mode='value')
+>>> res.keys()
+['data_mode', 'time_mode', 'id_metadata', 'data', 'audio_metadata', 'frame_metadata', 'parameters']
+
+In the dataObject key, the 'value' key is kept and the 'label' key is deleted.
+
+>>> res.data
+DataObject(value=None, time=array([], dtype=float64), duration=array([], dtype=float64))
+
+Label
+-----
+>>> res = coreA.AnalyzerResult(data_mode='label')
+>>> res.keys()
+['data_mode', 'time_mode', 'id_metadata', 'data', 'audio_metadata', 'frame_metadata', 'label_metadata', 'parameters']
+
+In the dataObject key, the 'label' key is kept and the 'value' key is deleted.
+
+
+>>> res.data
+DataObject(label=array([], dtype=int64), time=array([], dtype=float64), duration=array([], dtype=float64))
--- /dev/null
+# -*- coding: utf-8 -*-
+"""
+Created on Fri Oct 11 13:22:37 2013
+
+@author: thomas
+"""
+
+from __future__ import division
+import timeside.decoder
+import timeside.encoder
+import timeside.grapher
+import timeside.analyzer
+import matplotlib.pyplot as plt
+import numpy as np
+
+wavFile = 'TimeSide/tests/samples/sweep.mp3'
+wavFile = '/home/thomas/data/CNRSMH_E_1985_001_001_001_04.wav'
+# normal
+d = timeside.decoder.FileDecoder(wavFile, start=10, duration=15)
+
+specgram = timeside.analyzer.Spectrogram()
+waveform = timeside.analyzer.Waveform()
+
+# Get available Vamp plugins list
+from timeside.analyzer.vamp_plugin import VampSimpleHost
+plugins_list = VampSimpleHost.get_plugins_list()
+
+# Display avalaible plugins
+print 'index \t soname \t \t identifier \t output '
+print '------ \t \t ---------- \t ------ '
+for index, line in zip(xrange(len(plugins_list)),plugins_list):
+ print '%d : %s \t %s \t %s' % (index,line[0],line[1],line[2])
+
+# Let's choose #7
+my_plugin = plugins_list[7]
+print my_plugin
+
+#
+# Vamp plugin Analyzer
+vamp = timeside.analyzer.VampSimpleHost(my_plugin)
+
+#
+myPipe = (d | vamp | specgram | waveform).run()
+
+# Get spectrogram result and plot the spectrogram
+spec_res = specgram.results['spectrogram_analyzer']
+N = spec_res.parameters['FFT_SIZE']
+max_freq = (N // 2 + 1) / N * spec_res.frame_metadata.samplerate
+
+
+
+# Get the vamp plugin result and plot it
+vamp.results.keys()
+
+res_vamp = vamp.results['vamp_simple_host.percussiononsets.detectionfunction']
+
+plt.figure(1)
+
+plt.subplot(2,1,1)
+plt.plot(res_vamp.time, res_vamp.data)
+plt.xlabel('time in s')
+plt.grid
+plt.title(res_vamp.name)
+
+plt.subplot(2,1,2)
+plt.imshow(20 * np.log10(spec_res.data.T),
+ origin='lower',
+ extent=[spec_res.time[0], spec_res.time[-1], 0,
+ max_freq],
+ aspect='auto')
+
+data = res_vamp.data - res_vamp.data.mean()
+plt.plot(res_vamp.time, abs(data / data.max() * max_freq))
+
+
+plt.xlabel('time in s')
+plt.show()
\ No newline at end of file
from aubio_specdesc import *
from yaafe import * # TF : add Yaafe analyzer
from spectrogram import Spectrogram
-from waveform import Waveform
\ No newline at end of file
+from waveform import Waveform
+from vamp_plugin import VampSimpleHost
\ No newline at end of file
if self.time_mode == 'global':
return self.audio_metadata.duration
elif self.time_mode == 'framewise':
- return (self.frame_metadata.blockwise /
+ return (self.frame_metadata.blocksize /
self.frame_metadata.samplerate
* numpy.ones(len(self)))
elif self.time_mode == 'event':
--- /dev/null
+# -*- coding: utf-8 -*-
+#
+# Copyright (c) 2013 Paul Brossier <piem@piem.org>
+
+# This file is part of TimeSide.
+
+# TimeSide 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.
+
+# TimeSide 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 TimeSide. If not, see <http://www.gnu.org/licenses/>.
+
+# Author: Paul Brossier <piem@piem.org>
+
+from timeside.core import implements, interfacedoc
+from timeside.analyzer.core import Analyzer
+from timeside.api import IAnalyzer
+
+import subprocess
+import numpy as np
+
+
+class VampSimpleHost(Analyzer):
+ implements(IAnalyzer)
+
+ def __init__(self, plugin):
+ self.plugin = ':'.join(plugin)
+
+ @interfacedoc
+ def setup(self, channels=None, samplerate=None,
+ blocksize=None, totalframes=None):
+ super(VampSimpleHost, self).setup(
+ channels, samplerate, blocksize, totalframes)
+
+ @staticmethod
+ @interfacedoc
+ def id():
+ return "vamp_simple_host"
+
+ @staticmethod
+ @interfacedoc
+ def name():
+ return "Vamp Plugins host"
+
+ @staticmethod
+ @interfacedoc
+ def unit():
+ return ""
+
+ def process(self, frames, eod=False):
+ pass
+ return frames, eod
+
+ def release(self):
+ #plugin = 'vamp-example-plugins:amplitudefollower:amplitude'
+
+ wavfile = self.mediainfo()['uri'].split('file://')[-1]
+
+ (blocksize, stepsize, values) = self.vamp_plugin(self.plugin, wavfile)
+
+ self.result_blocksize = blocksize
+ self.result_stepsize = stepsize
+ self.result_samplerate = self.mediainfo()['samplerate']
+
+ plugin_res = self.new_result(data_mode='value', time_mode='framewise')
+
+ # Fix strat, duration issues if audio is a segment
+ if self.mediainfo()['is_segment']:
+ start_index = np.floor(self.mediainfo()['start'] *
+ self.result_samplerate /
+ self.result_stepsize)
+ new_start = start_index * self.result_stepsize
+
+ stop_index = np.ceil((self.mediainfo()['start'] +
+ self.mediainfo()['duration']) *
+ self.result_samplerate /
+ self.result_stepsize)
+
+ fixed_start = (start_index * self.result_stepsize /
+ self.result_samplerate)
+ fixed_duration = ((stop_index - start_index) * self.result_stepsize /
+ self.result_samplerate)
+
+ plugin_res.audio_metadata.start = fixed_start
+ plugin_res.audio_metadata.duration = fixed_duration
+
+ values = values[start_index:stop_index + 1]
+
+ plugin_res.id_metadata.id += '.' + '.'.join(self.plugin.split(':')[1:])
+ plugin_res.id_metadata.name += ' ' + \
+ ' '.join(self.plugin.split(':')[1:])
+ plugin_res.data_object.value = values
+
+ self._results.add(plugin_res)
+
+ @staticmethod
+ def vamp_plugin(plugin, wavfile):
+
+ args = [plugin, wavfile]
+
+ stdout = VampSimpleHost.SimpleHostProcess(args) # run vamp-simple-host
+
+ stderr = stdout[0:8] # stderr containing file and process information
+ res = stdout[8:] # stdout containg the feature data
+
+ # Parse stderr to get blocksize and stepsize
+ blocksize_info = stderr[4]
+
+ import re
+ # Match agianst pattern 'Using block size = %d, step size = %d'
+ m = re.match(
+ 'Using block size = (\d+), step size = (\d+)', blocksize_info)
+
+ blocksize = int(m.groups()[0])
+ stepsize = int(m.groups()[1])
+
+ # Get the results
+ values = np.asfarray([line.split(': ')[1] for line in res])
+ # TODO int support ?
+
+ return (blocksize, stepsize, values)
+
+ @staticmethod
+ def get_plugins_list():
+ arg = ['--list-outputs']
+ stdout = VampSimpleHost.SimpleHostProcess(arg)
+
+ return [line.split(':')[1:] for line in stdout]
+
+ @staticmethod
+ def SimpleHostProcess(argslist):
+ """Call vamp-simple-host"""
+
+ vamp_host = 'vamp-simple-host'
+ command = [vamp_host]
+ command.extend(argslist)
+ # try ?
+ stdout = subprocess.check_output(
+ command, stderr=subprocess.STDOUT).splitlines()
+
+ return stdout
return dict(uri=self.uri,
duration=self.uri_duration,
start=self.uri_start,
- is_segment=self.is_segment)
+ is_segment=self.is_segment,
+ samplerate=self.input_samplerate)
def __del__(self):
self.release()