Mercurial > hg > camir-aes2014
comparison core/magnatagatune/xml_parse_mtt.m @ 0:e9a9cd732c1e tip
first hg version after svn
author | wolffd |
---|---|
date | Tue, 10 Feb 2015 15:05:51 +0000 |
parents | |
children |
comparison
equal
deleted
inserted
replaced
-1:000000000000 | 0:e9a9cd732c1e |
---|---|
1 function features = xml_parse_mtt(file) | |
2 % features = xml_parse_mtt(file) | |
3 % | |
4 % parses the magnatagatune xml file to retrieve the audio | |
5 % analysis results. The file isexpected to use the deprecated | |
6 % EchoNest XML format | |
7 % | |
8 % time always travels an the horizontal axis | |
9 | |
10 % --- | |
11 % TODO: Add Error checking to certan tags as chroma number, | |
12 % loudness max etc. | |
13 % --- | |
14 | |
15 fdata = fileread(file); | |
16 try | |
17 % --- | |
18 % TODO: check for other than the p-code exceptions | |
19 % --- | |
20 | |
21 data = xml_parseany(fdata); | |
22 catch exception | |
23 end | |
24 %% ------------------------------------------------------------------------ | |
25 % --- | |
26 % copy general track data | |
27 % --- | |
28 | |
29 fields = fieldnames(data.track{1}.ATTRIBUTE); | |
30 for i = 1:length(fields) | |
31 features.(fields{i}) = str2double(data.track{1}.ATTRIBUTE.(fields{i})); | |
32 end | |
33 | |
34 %% ------------------------------------------------------------------------ | |
35 % --- | |
36 % get harmonic analysis. this is stored in segments | |
37 % --- | |
38 dsegments = data.track{1}.segments{1}.segment; | |
39 | |
40 for i = 1:numel(dsegments) | |
41 | |
42 % get start and duration | |
43 segments(i).start = str2double(dsegments{i}.ATTRIBUTE.start); | |
44 segments(i).duration = str2double(dsegments{i}.ATTRIBUTE.duration); | |
45 | |
46 % --- | |
47 % NOTE: for the chroma and mfcc features, we assume that the classes | |
48 % are always saved and parsed in correct order, thus we can afford to | |
49 % refrain from saving the class number with the class | |
50 % --- | |
51 | |
52 % assemble chroma features | |
53 segments(i).pitches = zeros(12,1); | |
54 for j = 1:12 | |
55 | |
56 segments(i).pitches(j) = str2double(... | |
57 dsegments{i}.pitches{1}.pitch{j}.CONTENT); | |
58 end | |
59 | |
60 % assemble mfcc features; | |
61 segments(i).timbre = zeros(numel(dsegments{i}.timbre{1}.coeff),1); | |
62 for j = 1:numel(dsegments{i}.timbre{1}.coeff) | |
63 | |
64 segments(i).timbre(j) = str2double(... | |
65 dsegments{i}.timbre{1}.coeff{j}.CONTENT); | |
66 end | |
67 | |
68 % get loudness measurements in dB and time | |
69 segments(i).loudness = str2double(... | |
70 dsegments{i}.loudness{1}.dB{1}.CONTENT); | |
71 | |
72 segments(i).loudness_time = str2double(... | |
73 dsegments{i}.loudness{1}.dB{1}.ATTRIBUTE.time); | |
74 | |
75 segments(i).loudness_max = str2double(... | |
76 dsegments{i}.loudness{1}.dB{2}.CONTENT); | |
77 | |
78 segments(i).loudness_max_time = str2double(... | |
79 dsegments{i}.loudness{1}.dB{2}.ATTRIBUTE.time); | |
80 end | |
81 | |
82 features.segments = segments; | |
83 | |
84 %% ------------------------------------------------------------------------ | |
85 % --- | |
86 % get sections | |
87 % --- | |
88 dsections = data.track{1}.sections{1}.section; | |
89 | |
90 secstart = zeros(1,numel(dsections)); | |
91 secduration = zeros(1,numel(dsections)); | |
92 for i = 1:numel(dsections) | |
93 sections(i).start = str2double(dsections{i}.ATTRIBUTE.start); | |
94 sections(i).duration = str2double(dsections{i}.ATTRIBUTE.duration); | |
95 end | |
96 | |
97 features.sections = sections; | |
98 | |
99 %% ------------------------------------------------------------------------ | |
100 % --- | |
101 % get beat and rythm data. the metric data is structured | |
102 % hierarchically, as each bar contains several beats, | |
103 % which contaisn several tatums. | |
104 % NOTE: Although the metrum and tempo have been evaluated and fixed | |
105 % on a global scale, the number of bars and tatum vary greatly. | |
106 % --- | |
107 dbars = data.track{1}.meter{1}.bar; | |
108 | |
109 for i = 1:numel(dbars) | |
110 | |
111 % get bar information | |
112 bars(i).confidence = str2double(dbars{i}.ATTRIBUTE.conf); | |
113 for j = 1:numel(dbars{i}.beat) | |
114 | |
115 % get beat information | |
116 bars(i).beat(j).confidence = str2double(dbars{i}.beat{j}.ATTRIBUTE.conf); | |
117 | |
118 for k = 1:numel(dbars{i}.beat{j}.tatum) | |
119 | |
120 % get tatum information | |
121 if ~isempty(dbars{i}.beat{j}.tatum{k}.ATTRIBUTE) | |
122 bars(i).beat(j).tatum(k).time = str2double(dbars{i}.beat{j}.tatum{k}.CONTENT); | |
123 bars(i).beat(j).tatum(k).confidence = str2double(dbars{i}.beat{j}.tatum{k}.ATTRIBUTE.conf); | |
124 | |
125 else | |
126 % save empty struct | |
127 bars(i).beat(j).tatum = struct([]); | |
128 end | |
129 | |
130 end | |
131 end | |
132 end | |
133 | |
134 features.bars = bars; | |
135 |