audeering / opensmile-python

Python package for openSMILE
https://audeering.github.io/opensmile-python/
Other
241 stars 32 forks source link

How to adapt a opensmile config to pyopensmile? #20

Open zyznull opened 3 years ago

zyznull commented 3 years ago

I want to adapt the "embose2010" config to pyopensmile now. But I meet an error:

Traceback (most recent call last): File "D:\cocde\pratt\PraatScripts-master\opensimle_feature.py", line 12, in smile = opensmile.Smile( File "D:\software\conda\lib\site-packages\opensmile\core\smile.py", line 116, in init self._feature_names(), File "D:\software\conda\lib\site-packages\opensmile\core\smile.py", line 275, in _feature_names smile = self._smile(options=options) File "D:\software\conda\lib\site-packages\opensmile\core\smile.py", line 366, in _smile smile.initialize( File "D:\software\conda\lib\site-packages\opensmile\core\SMILEapi.py", line 240, in initialize self._check_smile_result(smileapi.smile_initialize(self._smileobj, File "D:\software\conda\lib\site-packages\opensmile\core\SMILEapi.py", line 478, in _check_smile_result raise OpenSmileException(result) opensmile.core.SMILEapi.OpenSmileException: Code: 1

I only add a source and sink at the begining and end of the original config,like this:

///////////////////////////////////////////////////////////////////////////////////////
///////// > openSMILE configuration file for live emotion recognition < ///////////////
/////////   base set of 988 features, 1st level functionals          //////////////////
/////////   of low-level descriptors such as MFCC, Pitch, LSP, ...   //////////////////
/////////                                                            //////////////////
/////////  * written 2009 by Florian Eyben *                         //////////////////
/////////                                                            //////////////////
///////// (c) 2014 audEERING UG (haftungsbeschränkt),                //////////////////
/////////     All rights reserverd.                                  //////////////////
///////////////////////////////////////////////////////////////////////////////////////

//  Modified version:
//   - compatibility of newest 2.1 openSMILE code with openEAR 0.1.0 models

///////////////////////////////////////////////////////////////////////////////////////
;
; This section is always required in openSMILE configuration files
;   it configures the componentManager and gives a list of all components which are to be loaded
; The order in which the components are listed should match 
;   the order of the data flow for most efficient processing
;
///////////////////////////////////////////////////////////////////////////////////////

[componentInstances:cComponentManager]
instance[dataMemory].type=cDataMemory

;;; default source
[componentInstances:cComponentManager]
instance[dataMemory].type=cDataMemory

;;; source

\{\cm[source{?}:include external source]}

;;; main section

[componentInstances:cComponentManager]
 ;this line configures the default data memory:
instance[dataMemory].type=cDataMemory
instance[waveIn].type=cWaveSource
instance[fr25].type=cFramer
 ;;; 40 ms frames features:
instance[fr40].type=cFramer
instance[w40].type=cWindower
instance[fft40].type=cTransformFFT
instance[fftmagphase40].type=cFFTmagphase
instance[acf40].type=cAcf
instance[cepstrum40].type=cAcf
 ; Pitch...
instance[pitchACF].type=cPitchACF
 ;;; 25 ms frames features:
instance[pe].type=cVectorPreemphasis
instance[win].type=cWindower
instance[fft].type=cTransformFFT
instance[fftmagphase].type=cFFTmagphase
instance[mspec].type=cMelspec
 ; MFCC
instance[mfcc].type=cMfcc
instance[lpc].type=cLpc
 ; Line Spectral Frequencies
instance[lsp].type=cLsp
 ; Zero-Crossings
instance[mzcr].type=cMZcr
 ; Intensity and Loudness (narrow-band approximation)
instance[intens].type=cIntensity
 ;;; all LLD concattenated and smoothed using a moving average filter
instance[lld].type=cContourSmoother
 ; delta coefficients of LLD
instance[delta1].type=cDeltaRegression
 ;;; functionals over FULL input (e.g. turns)
instance[functL1].type=cFunctionals
 ;;; write instances to a Weka ARFF file (comment out to disable)
instance[arffsink].type=cArffSink
 ;;; live classification of emotion (comment out lines to disable them):
;; run single threaded (nThreads=1)
; NOTE: a single thread is more efficient for processing small files, since multi-threaded processing involves more 
;       overhead during startup, which will make the system slower in the end
nThreads=1
;; do not show any internal dataMemory level settings 
; (if you want to see them set the value to 1, 2, 3, or 4, depending on the amount of detail you wish)
printLevelStats=0

/////////////////////////////////////////////////////////////////////////////////////////////
/////////////////////////   component configuration  ////////////////////////////////////////
/////////////////////////////////////////////////////////////////////////////////////////////
; the following sections configure the components listed above
; a help on configuration parameters can be obtained with 
;  SMILExtract -H
; or
;  SMILExtract -H configTypeName (= componentTypeName)
/////////////////////////////////////////////////////////////////////////////////////////////

[waveIn:cWaveSource]
 ; this sets the level this component writes to
 ; the level will be created by this component
 ; no other components may write to a level having the same name
writer.dmLevel=wave
 ; this defines a new commandline option "-I" or "-inputfile", which can be used to specify 
 ; the filename on the commandline instead of having it "hard-coded" in the config file
filename=\cm[inputfile(I){test.wav}:name of input file]
 ; mix stereo files down to mono for analysis
monoMixdown = 1
properTimestamps = 1
start = 0.0
end = -1

[fr40:cFramer]
reader.dmLevel=wave
writer.dmLevel=frames40
frameSize = 0.040
frameStep = 0.010
frameMode = fixed
frameCenterSpecial = center

[w40:cWindower]
reader.dmLevel=frames40
writer.dmLevel=win40frame
copyInputName = 1
processArrayFields = 1
winFunc = ham
gain = 1.0
offset = 0

[fft40:cTransformFFT]
reader.dmLevel=win40frame
writer.dmLevel=fftc40
copyInputName = 1
processArrayFields = 1
inverse = 0
 ; for compatibility with 2.2.0 and older versions
zeroPadSymmetric = 0

[fftmagphase40:cFFTmagphase]
reader.dmLevel=fftc40
writer.dmLevel=fftmag40
copyInputName = 1
processArrayFields = 1
inverse = 0
magnitude = 1
phase = 0

[acf40:cAcf]
reader.dmLevel=fftmag40
writer.dmLevel=acf40
nameAppend = acf
copyInputName = 1
processArrayFields = 1
usePower = 1
cepstrum = 0
acfCepsNormOutput = 0

[cepstrum40:cAcf]
reader.dmLevel=fftmag40
writer.dmLevel=cepstrum40
nameAppend = acf
copyInputName = 1
processArrayFields = 1
usePower = 1
cepstrum = 1
acfCepsNormOutput = 0
oldCompatCepstrum = 1
absCepstrum = 1

[pitchACF:cPitchACF]
  ; the pitchACF component must ALWAYS read from acf AND cepstrum in the given order!
reader.dmLevel=acf40;cepstrum40
writer.dmLevel=pitch
processArrayFields=0
maxPitch = 500
voiceProb = 1
voiceQual = 0
HNR = 0
F0 = 1
F0raw = 0
F0env = 1
voicingCutoff = 0.550000

[fr25:cFramer]
reader.dmLevel=wave
writer.dmLevel=frames
frameSize = 0.025
frameStep = 0.010
frameMode = fixed
frameCenterSpecial = center

[pe:cVectorPreemphasis]
reader.dmLevel=frames
writer.dmLevel=framespe
copyInputName = 1
processArrayFields = 1
k=0.97

[win:cWindower]
reader.dmLevel=framespe
writer.dmLevel=winframe
copyInputName = 1
processArrayFields = 1
winFunc = ham
gain = 1.0
offset = 0

[fft:cTransformFFT]
reader.dmLevel=winframe
writer.dmLevel=fftc
copyInputName = 1
processArrayFields = 1
inverse = 0
 ; for compatibility with 2.2.0 and older versions
zeroPadSymmetric = 0

[fftmagphase:cFFTmagphase]
reader.dmLevel=fftc
writer.dmLevel=fftmag
copyInputName = 1
processArrayFields = 1
inverse = 0
magnitude = 1
phase = 0

[mspec:cMelspec]
reader.dmLevel=fftmag
writer.dmLevel=mspec1
copyInputName = 1
processArrayFields = 1
htkcompatible = 1
nBands = 26
lofreq = 0
hifreq = 8000
usePower = 1
inverse = 0
specScale = mel

[mfcc:cMfcc]
reader.dmLevel=mspec1
writer.dmLevel=mfcc1
copyInputName = 0
processArrayFields = 1
firstMfcc = 1
lastMfcc =  12
cepLifter = 22.0
htkcompatible = 1

[lpc:cLpc]
reader.dmLevel=framespe
writer.dmLevel=lpc
copyInputName = 1
processArrayFields = 1
method = acf
p = 8
saveLPCoeff = 1
lpGain = 0
saveRefCoeff = 0
residual = 0
forwardFilter = 0
lpSpectrum = 0

[lsp:cLsp]
reader.dmLevel=lpc
writer.dmLevel=lsp
copyInputName = 1
processArrayFields = 0

[intens:cIntensity]
reader.dmLevel=frames
writer.dmLevel=intens
copyInputName = 1
processArrayFields = 1
intensity=1
loudness =1

[mzcr:cMZcr]
reader.dmLevel=frames
writer.dmLevel=mzcr
copyInputName = 1
processArrayFields = 1
zcr = 1
amax = 0
mcr = 0
maxmin = 0
dc = 0

[lld:cContourSmoother]
reader.dmLevel=intens;mfcc1;lsp;mzcr;pitch
writer.dmLevel=lld
writer.levelconf.nT = 2500
writer.levelconf.isRb=0
writer.levelconf.growDyn=1
nameAppend = sma
copyInputName = 1
noPostEOIprocessing = 0
smaWin = 3

// ---- delta regression of LLD ----
[delta1:cDeltaRegression]
reader.dmLevel=lld
writer.dmLevel=lld_de
blocksize=1
writer.levelconf.nT = 2500
writer.levelconf.isRb=0
writer.levelconf.growDyn=1
nameAppend = de
copyInputName = 1
noPostEOIprocessing = 0
deltawin=2

// statistical functionals
[functL1:cFunctionals]
reader.dmLevel=lld;lld_de
writer.dmLevel=func
copyInputName = 1
 ; frameMode = var will enable the functionals component to listen for messages from the turn detector
frameMode = full
functionalsEnabled=Extremes;Regression;Moments;Percentiles
Extremes.max = 1
Extremes.min = 1
Extremes.range = 1
Extremes.maxpos = 1
Extremes.minpos = 1
Extremes.amean = 1
Extremes.maxameandist = 0
Extremes.minameandist = 0
 ; Note: the much better way to normalise the times of maxpos and minpos
 ; is 'turn', however for compatibility with old files the default 'frame' 
 ; is kept here:
Extremes.norm = frame
Regression.linregc1 = 1
Regression.linregc2 = 1
Regression.linregerrA = 1
Regression.linregerrQ = 1
Regression.qregc1 = 0
Regression.qregc2 = 0
Regression.qregc3 = 0
Regression.qregerrA = 0
Regression.qregerrQ = 0
Regression.centroid = 0
Regression.doRatioLimit = 0
Regression.centroidRatioLimit = 0

Moments.doRatioLimit = 0
Moments.variance = 0
Moments.stddev = 1
Moments.skewness = 1
Moments.kurtosis = 1
Moments.amean = 0
Percentiles.quartiles = 1
Percentiles.iqr = 1

  //////////////////////////////////////////////////////////////////////
 ///////////////////  data output configuration  //////////////////////
//////////////////////////////////////////////////////////////////////

// ----- you can use this to save the features extracted  ------
[arffsink:cArffSink]
reader.dmLevel=func
 ; do not print "frameNumber" attribute to ARFF file
number=0
 ; name of output file as commandline option
filename=\cm[arffout(O){output.arff}:name of WEKA Arff output file]
 ; name of @relation in the ARFF file
relation=\cm[corpus{SMILEfeaturesLive}:corpus name, arff relation]
 ; base name of the current instance, turn number will be appended
instanceBase=liveturn
 ; name of class label
class[0].name = emotion
 ; list of nominal classes OR "numeric"
class[0].type = \cm[classes{unknown}:all classes for arff file attribute]
 ; the class label or value for the current instance
target[0].all = \cm[classlabel{unassigned}:instance class label]
 ; ** NOTE: theoretically the classified class label could be assigned here, however this would require 
 ; ** saving the class label along with the frame in the dataMemory
 ; ** or sending this meta-data via a message (including frame number)
 ; ** neither solution is currently implemented.... :-(
 ;
append=0

//////---------------------- END -------------------------///////

;;; sink

\{\cm[sink{?}:include external sink]}

What else should I do? Thanks a lot !

frankenjoe commented 3 years ago

You still have the old cWaveSource in your script. Here is the fixed script:

///////////////////////////////////////////////////////////////////////////////////////
///////// > openSMILE configuration file for live emotion recognition < ///////////////
/////////   base set of 988 features, 1st level functionals          //////////////////
/////////   of low-level descriptors such as MFCC, Pitch, LSP, ...   //////////////////
/////////                                                            //////////////////
/////////  * written 2009 by Florian Eyben *                         //////////////////
/////////                                                            //////////////////
///////// (c) 2014 audEERING UG (haftungsbeschränkt),                //////////////////
/////////     All rights reserverd.                                  //////////////////
///////////////////////////////////////////////////////////////////////////////////////

//  Modified version:
//   - compatibility of newest 2.1 openSMILE code with openEAR 0.1.0 models

///////////////////////////////////////////////////////////////////////////////////////
;
; This section is always required in openSMILE configuration files
;   it configures the componentManager and gives a list of all components which are to be loaded
; The order in which the components are listed should match
;   the order of the data flow for most efficient processing
;
///////////////////////////////////////////////////////////////////////////////////////

[componentInstances:cComponentManager]
instance[dataMemory].type=cDataMemory

;;; default source
[componentInstances:cComponentManager]
instance[dataMemory].type=cDataMemory

;;; source

\{\cm[source{?}:include external source]}

;;; main section

[componentInstances:cComponentManager]
 ;this line configures the default data memory:
instance[dataMemory].type=cDataMemory
instance[fr25].type=cFramer
 ;;; 40 ms frames features:
instance[fr40].type=cFramer
instance[w40].type=cWindower
instance[fft40].type=cTransformFFT
instance[fftmagphase40].type=cFFTmagphase
instance[acf40].type=cAcf
instance[cepstrum40].type=cAcf
 ; Pitch...
instance[pitchACF].type=cPitchACF
 ;;; 25 ms frames features:
instance[pe].type=cVectorPreemphasis
instance[win].type=cWindower
instance[fft].type=cTransformFFT
instance[fftmagphase].type=cFFTmagphase
instance[mspec].type=cMelspec
 ; MFCC
instance[mfcc].type=cMfcc
instance[lpc].type=cLpc
 ; Line Spectral Frequencies
instance[lsp].type=cLsp
 ; Zero-Crossings
instance[mzcr].type=cMZcr
 ; Intensity and Loudness (narrow-band approximation)
instance[intens].type=cIntensity
 ;;; all LLD concattenated and smoothed using a moving average filter
instance[lld].type=cContourSmoother
 ; delta coefficients of LLD
instance[delta1].type=cDeltaRegression
 ;;; functionals over FULL input (e.g. turns)
instance[functL1].type=cFunctionals
 ;;; write instances to a Weka ARFF file (comment out to disable)
instance[arffsink].type=cArffSink
 ;;; live classification of emotion (comment out lines to disable them):
;; run single threaded (nThreads=1)
; NOTE: a single thread is more efficient for processing small files, since multi-threaded processing involves more
;       overhead during startup, which will make the system slower in the end
nThreads=1
;; do not show any internal dataMemory level settings
; (if you want to see them set the value to 1, 2, 3, or 4, depending on the amount of detail you wish)
printLevelStats=0

/////////////////////////////////////////////////////////////////////////////////////////////
/////////////////////////   component configuration  ////////////////////////////////////////
/////////////////////////////////////////////////////////////////////////////////////////////
; the following sections configure the components listed above
; a help on configuration parameters can be obtained with
;  SMILExtract -H
; or
;  SMILExtract -H configTypeName (= componentTypeName)
/////////////////////////////////////////////////////////////////////////////////////////////

[fr40:cFramer]
reader.dmLevel=wave
writer.dmLevel=frames40
frameSize = 0.040
frameStep = 0.010
frameMode = fixed
frameCenterSpecial = center

[w40:cWindower]
reader.dmLevel=frames40
writer.dmLevel=win40frame
copyInputName = 1
processArrayFields = 1
winFunc = ham
gain = 1.0
offset = 0

[fft40:cTransformFFT]
reader.dmLevel=win40frame
writer.dmLevel=fftc40
copyInputName = 1
processArrayFields = 1
inverse = 0
 ; for compatibility with 2.2.0 and older versions
zeroPadSymmetric = 0

[fftmagphase40:cFFTmagphase]
reader.dmLevel=fftc40
writer.dmLevel=fftmag40
copyInputName = 1
processArrayFields = 1
inverse = 0
magnitude = 1
phase = 0

[acf40:cAcf]
reader.dmLevel=fftmag40
writer.dmLevel=acf40
nameAppend = acf
copyInputName = 1
processArrayFields = 1
usePower = 1
cepstrum = 0
acfCepsNormOutput = 0

[cepstrum40:cAcf]
reader.dmLevel=fftmag40
writer.dmLevel=cepstrum40
nameAppend = acf
copyInputName = 1
processArrayFields = 1
usePower = 1
cepstrum = 1
acfCepsNormOutput = 0
oldCompatCepstrum = 1
absCepstrum = 1

[pitchACF:cPitchACF]
  ; the pitchACF component must ALWAYS read from acf AND cepstrum in the given order!
reader.dmLevel=acf40;cepstrum40
writer.dmLevel=pitch
processArrayFields=0
maxPitch = 500
voiceProb = 1
voiceQual = 0
HNR = 0
F0 = 1
F0raw = 0
F0env = 1
voicingCutoff = 0.550000

[fr25:cFramer]
reader.dmLevel=wave
writer.dmLevel=frames
frameSize = 0.025
frameStep = 0.010
frameMode = fixed
frameCenterSpecial = center

[pe:cVectorPreemphasis]
reader.dmLevel=frames
writer.dmLevel=framespe
copyInputName = 1
processArrayFields = 1
k=0.97

[win:cWindower]
reader.dmLevel=framespe
writer.dmLevel=winframe
copyInputName = 1
processArrayFields = 1
winFunc = ham
gain = 1.0
offset = 0

[fft:cTransformFFT]
reader.dmLevel=winframe
writer.dmLevel=fftc
copyInputName = 1
processArrayFields = 1
inverse = 0
 ; for compatibility with 2.2.0 and older versions
zeroPadSymmetric = 0

[fftmagphase:cFFTmagphase]
reader.dmLevel=fftc
writer.dmLevel=fftmag
copyInputName = 1
processArrayFields = 1
inverse = 0
magnitude = 1
phase = 0

[mspec:cMelspec]
reader.dmLevel=fftmag
writer.dmLevel=mspec1
copyInputName = 1
processArrayFields = 1
htkcompatible = 1
nBands = 26
lofreq = 0
hifreq = 8000
usePower = 1
inverse = 0
specScale = mel

[mfcc:cMfcc]
reader.dmLevel=mspec1
writer.dmLevel=mfcc1
copyInputName = 0
processArrayFields = 1
firstMfcc = 1
lastMfcc =  12
cepLifter = 22.0
htkcompatible = 1

[lpc:cLpc]
reader.dmLevel=framespe
writer.dmLevel=lpc
copyInputName = 1
processArrayFields = 1
method = acf
p = 8
saveLPCoeff = 1
lpGain = 0
saveRefCoeff = 0
residual = 0
forwardFilter = 0
lpSpectrum = 0

[lsp:cLsp]
reader.dmLevel=lpc
writer.dmLevel=lsp
copyInputName = 1
processArrayFields = 0

[intens:cIntensity]
reader.dmLevel=frames
writer.dmLevel=intens
copyInputName = 1
processArrayFields = 1
intensity=1
loudness =1

[mzcr:cMZcr]
reader.dmLevel=frames
writer.dmLevel=mzcr
copyInputName = 1
processArrayFields = 1
zcr = 1
amax = 0
mcr = 0
maxmin = 0
dc = 0

[lld:cContourSmoother]
reader.dmLevel=intens;mfcc1;lsp;mzcr;pitch
writer.dmLevel=lld
writer.levelconf.nT = 2500
writer.levelconf.isRb=0
writer.levelconf.growDyn=1
nameAppend = sma
copyInputName = 1
noPostEOIprocessing = 0
smaWin = 3

// ---- delta regression of LLD ----
[delta1:cDeltaRegression]
reader.dmLevel=lld
writer.dmLevel=lld_de
blocksize=1
writer.levelconf.nT = 2500
writer.levelconf.isRb=0
writer.levelconf.growDyn=1
nameAppend = de
copyInputName = 1
noPostEOIprocessing = 0
deltawin=2

// statistical functionals
[functL1:cFunctionals]
reader.dmLevel=lld;lld_de
writer.dmLevel=func
copyInputName = 1
 ; frameMode = var will enable the functionals component to listen for messages from the turn detector
frameMode = full
functionalsEnabled=Extremes;Regression;Moments;Percentiles
Extremes.max = 1
Extremes.min = 1
Extremes.range = 1
Extremes.maxpos = 1
Extremes.minpos = 1
Extremes.amean = 1
Extremes.maxameandist = 0
Extremes.minameandist = 0
 ; Note: the much better way to normalise the times of maxpos and minpos
 ; is 'turn', however for compatibility with old files the default 'frame'
 ; is kept here:
Extremes.norm = frame
Regression.linregc1 = 1
Regression.linregc2 = 1
Regression.linregerrA = 1
Regression.linregerrQ = 1
Regression.qregc1 = 0
Regression.qregc2 = 0
Regression.qregc3 = 0
Regression.qregerrA = 0
Regression.qregerrQ = 0
Regression.centroid = 0
Regression.doRatioLimit = 0
Regression.centroidRatioLimit = 0

Moments.doRatioLimit = 0
Moments.variance = 0
Moments.stddev = 1
Moments.skewness = 1
Moments.kurtosis = 1
Moments.amean = 0
Percentiles.quartiles = 1
Percentiles.iqr = 1

  //////////////////////////////////////////////////////////////////////
 ///////////////////  data output configuration  //////////////////////
//////////////////////////////////////////////////////////////////////

// ----- you can use this to save the features extracted  ------
[arffsink:cArffSink]
reader.dmLevel=func
 ; do not print "frameNumber" attribute to ARFF file
number=0
 ; name of output file as commandline option
filename=\cm[arffout(O){output.arff}:name of WEKA Arff output file]
 ; name of @relation in the ARFF file
relation=\cm[corpus{SMILEfeaturesLive}:corpus name, arff relation]
 ; base name of the current instance, turn number will be appended
instanceBase=liveturn
 ; name of class label
class[0].name = emotion
 ; list of nominal classes OR "numeric"
class[0].type = \cm[classes{unknown}:all classes for arff file attribute]
 ; the class label or value for the current instance
target[0].all = \cm[classlabel{unassigned}:instance class label]
 ; ** NOTE: theoretically the classified class label could be assigned here, however this would require
 ; ** saving the class label along with the frame in the dataMemory
 ; ** or sending this meta-data via a message (including frame number)
 ; ** neither solution is currently implemented.... :-(
 ;
append=0

//////---------------------- END -------------------------///////

;;; sink

\{\cm[sink{?}:include external sink]}
frankenjoe commented 3 years ago

Btw: when you get opensmile.core.SMILEapi.OpenSmileException: Code: 1, it's always a good idea to create a log file using the logfile argument. For your script it would print:

[ 17.02.2021 - 11:14:34 ]
    (MSG) [2] SMILEapi: openSMILE starting!
[ 17.02.2021 - 11:14:34 ]
    (MSG) [2] SMILEapi: config file is: /media/jwagner/Data/Git/pysmile-public/my/test.conf
[ 17.02.2021 - 11:14:34 ]
    (MSG) [2] cComponentManager: successfully registered 103 component types.
[ 17.02.2021 - 11:14:34 ]
    (ERR) [0] commandlineParser: parse: unknown option '-bufferModeRbConf' on commandline!
[ 17.02.2021 - 11:14:34 ]
    (ERR) [0] commandlineParser: parse: unknown option '-frameModeFunctionalsConf' on commandline!
[ 17.02.2021 - 11:14:34 ]
    (ERR) [1] dataMemory: two components cannot write to the same level: 'wave', component1='extsource.writer', component2='waveIn.writer'
zyznull commented 3 years ago

You still have the old cWaveSource in your script. Here is the fixed script:

///////////////////////////////////////////////////////////////////////////////////////
///////// > openSMILE configuration file for live emotion recognition < ///////////////
/////////   base set of 988 features, 1st level functionals          //////////////////
/////////   of low-level descriptors such as MFCC, Pitch, LSP, ...   //////////////////
/////////                                                            //////////////////
/////////  * written 2009 by Florian Eyben *                         //////////////////
/////////                                                            //////////////////
///////// (c) 2014 audEERING UG (haftungsbeschränkt),                //////////////////
/////////     All rights reserverd.                                  //////////////////
///////////////////////////////////////////////////////////////////////////////////////

//  Modified version:
//   - compatibility of newest 2.1 openSMILE code with openEAR 0.1.0 models

///////////////////////////////////////////////////////////////////////////////////////
;
; This section is always required in openSMILE configuration files
;   it configures the componentManager and gives a list of all components which are to be loaded
; The order in which the components are listed should match
;   the order of the data flow for most efficient processing
;
///////////////////////////////////////////////////////////////////////////////////////

[componentInstances:cComponentManager]
instance[dataMemory].type=cDataMemory

;;; default source
[componentInstances:cComponentManager]
instance[dataMemory].type=cDataMemory

;;; source

\{\cm[source{?}:include external source]}

;;; main section

[componentInstances:cComponentManager]
 ;this line configures the default data memory:
instance[dataMemory].type=cDataMemory
instance[fr25].type=cFramer
 ;;; 40 ms frames features:
instance[fr40].type=cFramer
instance[w40].type=cWindower
instance[fft40].type=cTransformFFT
instance[fftmagphase40].type=cFFTmagphase
instance[acf40].type=cAcf
instance[cepstrum40].type=cAcf
 ; Pitch...
instance[pitchACF].type=cPitchACF
 ;;; 25 ms frames features:
instance[pe].type=cVectorPreemphasis
instance[win].type=cWindower
instance[fft].type=cTransformFFT
instance[fftmagphase].type=cFFTmagphase
instance[mspec].type=cMelspec
 ; MFCC
instance[mfcc].type=cMfcc
instance[lpc].type=cLpc
 ; Line Spectral Frequencies
instance[lsp].type=cLsp
 ; Zero-Crossings
instance[mzcr].type=cMZcr
 ; Intensity and Loudness (narrow-band approximation)
instance[intens].type=cIntensity
 ;;; all LLD concattenated and smoothed using a moving average filter
instance[lld].type=cContourSmoother
 ; delta coefficients of LLD
instance[delta1].type=cDeltaRegression
 ;;; functionals over FULL input (e.g. turns)
instance[functL1].type=cFunctionals
 ;;; write instances to a Weka ARFF file (comment out to disable)
instance[arffsink].type=cArffSink
 ;;; live classification of emotion (comment out lines to disable them):
;; run single threaded (nThreads=1)
; NOTE: a single thread is more efficient for processing small files, since multi-threaded processing involves more
;       overhead during startup, which will make the system slower in the end
nThreads=1
;; do not show any internal dataMemory level settings
; (if you want to see them set the value to 1, 2, 3, or 4, depending on the amount of detail you wish)
printLevelStats=0

/////////////////////////////////////////////////////////////////////////////////////////////
/////////////////////////   component configuration  ////////////////////////////////////////
/////////////////////////////////////////////////////////////////////////////////////////////
; the following sections configure the components listed above
; a help on configuration parameters can be obtained with
;  SMILExtract -H
; or
;  SMILExtract -H configTypeName (= componentTypeName)
/////////////////////////////////////////////////////////////////////////////////////////////

[fr40:cFramer]
reader.dmLevel=wave
writer.dmLevel=frames40
frameSize = 0.040
frameStep = 0.010
frameMode = fixed
frameCenterSpecial = center

[w40:cWindower]
reader.dmLevel=frames40
writer.dmLevel=win40frame
copyInputName = 1
processArrayFields = 1
winFunc = ham
gain = 1.0
offset = 0

[fft40:cTransformFFT]
reader.dmLevel=win40frame
writer.dmLevel=fftc40
copyInputName = 1
processArrayFields = 1
inverse = 0
 ; for compatibility with 2.2.0 and older versions
zeroPadSymmetric = 0

[fftmagphase40:cFFTmagphase]
reader.dmLevel=fftc40
writer.dmLevel=fftmag40
copyInputName = 1
processArrayFields = 1
inverse = 0
magnitude = 1
phase = 0

[acf40:cAcf]
reader.dmLevel=fftmag40
writer.dmLevel=acf40
nameAppend = acf
copyInputName = 1
processArrayFields = 1
usePower = 1
cepstrum = 0
acfCepsNormOutput = 0

[cepstrum40:cAcf]
reader.dmLevel=fftmag40
writer.dmLevel=cepstrum40
nameAppend = acf
copyInputName = 1
processArrayFields = 1
usePower = 1
cepstrum = 1
acfCepsNormOutput = 0
oldCompatCepstrum = 1
absCepstrum = 1

[pitchACF:cPitchACF]
  ; the pitchACF component must ALWAYS read from acf AND cepstrum in the given order!
reader.dmLevel=acf40;cepstrum40
writer.dmLevel=pitch
processArrayFields=0
maxPitch = 500
voiceProb = 1
voiceQual = 0
HNR = 0
F0 = 1
F0raw = 0
F0env = 1
voicingCutoff = 0.550000

[fr25:cFramer]
reader.dmLevel=wave
writer.dmLevel=frames
frameSize = 0.025
frameStep = 0.010
frameMode = fixed
frameCenterSpecial = center

[pe:cVectorPreemphasis]
reader.dmLevel=frames
writer.dmLevel=framespe
copyInputName = 1
processArrayFields = 1
k=0.97

[win:cWindower]
reader.dmLevel=framespe
writer.dmLevel=winframe
copyInputName = 1
processArrayFields = 1
winFunc = ham
gain = 1.0
offset = 0

[fft:cTransformFFT]
reader.dmLevel=winframe
writer.dmLevel=fftc
copyInputName = 1
processArrayFields = 1
inverse = 0
 ; for compatibility with 2.2.0 and older versions
zeroPadSymmetric = 0

[fftmagphase:cFFTmagphase]
reader.dmLevel=fftc
writer.dmLevel=fftmag
copyInputName = 1
processArrayFields = 1
inverse = 0
magnitude = 1
phase = 0

[mspec:cMelspec]
reader.dmLevel=fftmag
writer.dmLevel=mspec1
copyInputName = 1
processArrayFields = 1
htkcompatible = 1
nBands = 26
lofreq = 0
hifreq = 8000
usePower = 1
inverse = 0
specScale = mel

[mfcc:cMfcc]
reader.dmLevel=mspec1
writer.dmLevel=mfcc1
copyInputName = 0
processArrayFields = 1
firstMfcc = 1
lastMfcc =  12
cepLifter = 22.0
htkcompatible = 1

[lpc:cLpc]
reader.dmLevel=framespe
writer.dmLevel=lpc
copyInputName = 1
processArrayFields = 1
method = acf
p = 8
saveLPCoeff = 1
lpGain = 0
saveRefCoeff = 0
residual = 0
forwardFilter = 0
lpSpectrum = 0

[lsp:cLsp]
reader.dmLevel=lpc
writer.dmLevel=lsp
copyInputName = 1
processArrayFields = 0

[intens:cIntensity]
reader.dmLevel=frames
writer.dmLevel=intens
copyInputName = 1
processArrayFields = 1
intensity=1
loudness =1

[mzcr:cMZcr]
reader.dmLevel=frames
writer.dmLevel=mzcr
copyInputName = 1
processArrayFields = 1
zcr = 1
amax = 0
mcr = 0
maxmin = 0
dc = 0

[lld:cContourSmoother]
reader.dmLevel=intens;mfcc1;lsp;mzcr;pitch
writer.dmLevel=lld
writer.levelconf.nT = 2500
writer.levelconf.isRb=0
writer.levelconf.growDyn=1
nameAppend = sma
copyInputName = 1
noPostEOIprocessing = 0
smaWin = 3

// ---- delta regression of LLD ----
[delta1:cDeltaRegression]
reader.dmLevel=lld
writer.dmLevel=lld_de
blocksize=1
writer.levelconf.nT = 2500
writer.levelconf.isRb=0
writer.levelconf.growDyn=1
nameAppend = de
copyInputName = 1
noPostEOIprocessing = 0
deltawin=2

// statistical functionals
[functL1:cFunctionals]
reader.dmLevel=lld;lld_de
writer.dmLevel=func
copyInputName = 1
 ; frameMode = var will enable the functionals component to listen for messages from the turn detector
frameMode = full
functionalsEnabled=Extremes;Regression;Moments;Percentiles
Extremes.max = 1
Extremes.min = 1
Extremes.range = 1
Extremes.maxpos = 1
Extremes.minpos = 1
Extremes.amean = 1
Extremes.maxameandist = 0
Extremes.minameandist = 0
 ; Note: the much better way to normalise the times of maxpos and minpos
 ; is 'turn', however for compatibility with old files the default 'frame'
 ; is kept here:
Extremes.norm = frame
Regression.linregc1 = 1
Regression.linregc2 = 1
Regression.linregerrA = 1
Regression.linregerrQ = 1
Regression.qregc1 = 0
Regression.qregc2 = 0
Regression.qregc3 = 0
Regression.qregerrA = 0
Regression.qregerrQ = 0
Regression.centroid = 0
Regression.doRatioLimit = 0
Regression.centroidRatioLimit = 0

Moments.doRatioLimit = 0
Moments.variance = 0
Moments.stddev = 1
Moments.skewness = 1
Moments.kurtosis = 1
Moments.amean = 0
Percentiles.quartiles = 1
Percentiles.iqr = 1

  //////////////////////////////////////////////////////////////////////
 ///////////////////  data output configuration  //////////////////////
//////////////////////////////////////////////////////////////////////

// ----- you can use this to save the features extracted  ------
[arffsink:cArffSink]
reader.dmLevel=func
 ; do not print "frameNumber" attribute to ARFF file
number=0
 ; name of output file as commandline option
filename=\cm[arffout(O){output.arff}:name of WEKA Arff output file]
 ; name of @relation in the ARFF file
relation=\cm[corpus{SMILEfeaturesLive}:corpus name, arff relation]
 ; base name of the current instance, turn number will be appended
instanceBase=liveturn
 ; name of class label
class[0].name = emotion
 ; list of nominal classes OR "numeric"
class[0].type = \cm[classes{unknown}:all classes for arff file attribute]
 ; the class label or value for the current instance
target[0].all = \cm[classlabel{unassigned}:instance class label]
 ; ** NOTE: theoretically the classified class label could be assigned here, however this would require
 ; ** saving the class label along with the frame in the dataMemory
 ; ** or sending this meta-data via a message (including frame number)
 ; ** neither solution is currently implemented.... :-(
 ;
append=0

//////---------------------- END -------------------------///////

;;; sink

\{\cm[sink{?}:include external sink]}

Thanks! It really help me !!

gutowskitomasz commented 3 years ago

Is there a simple way to adapt any of the config files compatible woth the executable version to the Python version?

frankenjoe commented 3 years ago

In most cases replacing:

[waveIn:cWaveSource]
writer.dmLevel=wave

with

\{\cm[source{?}:include external source]}

and adding

\{\cm[sink{?}:include external sink]}

should work.