LabelMaker.cpp 50 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697989910010110210310410510610710810911011111211311411511611711811912012112212312412512612712812913013113213313413513613713813914014114214314414514614714814915015115215315415515615715815916016116216316416516616716816917017117217317417517617717817918018118218318418518618718818919019119219319419519619719819920020120220320420520620720820921021121221321421521621721821922022122222322422522622722822923023123223323423523623723823924024124224324424524624724824925025125225325425525625725825926026126226326426526626726826927027127227327427527627727827928028128228328428528628728828929029129229329429529629729829930030130230330430530630730830931031131231331431531631731831932032132232332432532632732832933033133233333433533633733833934034134234334434534634734834935035135235335435535635735835936036136236336436536636736836937037137237337437537637737837938038138238338438538638738838939039139239339439539639739839940040140240340440540640740840941041141241341441541641741841942042142242342442542642742842943043143243343443543643743843944044144244344444544644744844945045145245345445545645745845946046146246346446546646746846947047147247347447547647747847948048148248348448548648748848949049149249349449549649749849950050150250350450550650750850951051151251351451551651751851952052152252352452552652752852953053153253353453553653753853954054154254354454554654754854955055155255355455555655755855956056156256356456556656756856957057157257357457557657757857958058158258358458558658758858959059159259359459559659759859960060160260360460560660760860961061161261361461561661761861962062162262362462562662762862963063163263363463563663763863964064164264364464564664764864965065165265365465565665765865966066166266366466566666766866967067167267367467567667767867968068168268368468568668768868969069169269369469569669769869970070170270370470570670770870971071171271371471571671771871972072172272372472572672772872973073173273373473573673773873974074174274374474574674774874975075175275375475575675775875976076176276376476576676776876977077177277377477577677777877978078178278378478578678778878979079179279379479579679779879980080180280380480580680780880981081181281381481581681781881982082182282382482582682782882983083183283383483583683783883984084184284384484584684784884985085185285385485585685785885986086186286386486586686786886987087187287387487587687787887988088188288388488588688788888989089189289389489589689789889990090190290390490590690790890991091191291391491591691791891992092192292392492592692792892993093193293393493593693793893994094194294394494594694794894995095195295395495595695795895996096196296396496596696796896997097197297397497597697797897998098198298398498598698798898999099199299399499599699799899910001001100210031004100510061007100810091010101110121013101410151016101710181019102010211022102310241025102610271028102910301031103210331034103510361037103810391040104110421043104410451046104710481049105010511052105310541055105610571058105910601061106210631064106510661067106810691070107110721073107410751076107710781079108010811082108310841085108610871088108910901091109210931094109510961097109810991100110111021103110411051106110711081109111011111112111311141115111611171118111911201121112211231124112511261127112811291130113111321133113411351136113711381139114011411142114311441145114611471148114911501151115211531154115511561157115811591160116111621163116411651166116711681169117011711172117311741175117611771178117911801181118211831184118511861187118811891190119111921193119411951196119711981199120012011202120312041205120612071208120912101211121212131214121512161217121812191220122112221223122412251226122712281229123012311232123312341235123612371238123912401241124212431244124512461247124812491250125112521253125412551256125712581259126012611262126312641265126612671268126912701271127212731274127512761277127812791280128112821283128412851286128712881289129012911292129312941295129612971298129913001301130213031304130513061307130813091310131113121313131413151316131713181319132013211322132313241325132613271328132913301331133213331334133513361337133813391340134113421343134413451346134713481349135013511352135313541355135613571358135913601361136213631364136513661367136813691370137113721373137413751376137713781379138013811382138313841385138613871388138913901391139213931394139513961397139813991400140114021403140414051406140714081409141014111412141314141415141614171418141914201421142214231424142514261427142814291430143114321433143414351436143714381439144014411442144314441445144614471448144914501451145214531454145514561457145814591460146114621463146414651466146714681469147014711472147314741475147614771478147914801481148214831484148514861487148814891490149114921493149414951496149714981499150015011502150315041505150615071508150915101511151215131514151515161517151815191520152115221523152415251526152715281529153015311532153315341535153615371538153915401541154215431544154515461547154815491550155115521553155415551556155715581559156015611562156315641565156615671568156915701571157215731574157515761577157815791580158115821583158415851586158715881589159015911592159315941595159615971598159916001601160216031604160516061607160816091610161116121613161416151616161716181619162016211622162316241625162616271628162916301631163216331634163516361637163816391640164116421643164416451646164716481649165016511652165316541655165616571658165916601661166216631664166516661667166816691670167116721673167416751676167716781679168016811682168316841685168616871688168916901691169216931694169516961697169816991700170117021703170417051706170717081709171017111712171317141715171617171718171917201721172217231724172517261727172817291730173117321733173417351736173717381739174017411742174317441745174617471748174917501751175217531754175517561757175817591760176117621763176417651766176717681769177017711772177317741775177617771778177917801781178217831784
  1. /* ----------------------------------------------------------------- */
  2. /* The HMM-Based Singing Voice Synthesis System "Sinsy" */
  3. /* developed by Sinsy Working Group */
  4. /* http://sinsy.sourceforge.net/ */
  5. /* ----------------------------------------------------------------- */
  6. /* */
  7. /* Copyright (c) 2009-2015 Nagoya Institute of Technology */
  8. /* Department of Computer Science */
  9. /* */
  10. /* All rights reserved. */
  11. /* */
  12. /* Redistribution and use in source and binary forms, with or */
  13. /* without modification, are permitted provided that the following */
  14. /* conditions are met: */
  15. /* */
  16. /* - Redistributions of source code must retain the above copyright */
  17. /* notice, this list of conditions and the following disclaimer. */
  18. /* - Redistributions in binary form must reproduce the above */
  19. /* copyright notice, this list of conditions and the following */
  20. /* disclaimer in the documentation and/or other materials provided */
  21. /* with the distribution. */
  22. /* - Neither the name of the Sinsy working group nor the names of */
  23. /* its contributors may be used to endorse or promote products */
  24. /* derived from this software without specific prior written */
  25. /* permission. */
  26. /* */
  27. /* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND */
  28. /* CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, */
  29. /* INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF */
  30. /* MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE */
  31. /* DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS */
  32. /* BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, */
  33. /* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED */
  34. /* TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, */
  35. /* DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON */
  36. /* ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, */
  37. /* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY */
  38. /* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE */
  39. /* POSSIBILITY OF SUCH DAMAGE. */
  40. /* ----------------------------------------------------------------- */
  41. #include <algorithm>
  42. #include <sstream>
  43. #include <limits>
  44. #include "LabelMaker.h"
  45. #include "util_string.h"
  46. #include "util_log.h"
  47. #include "util_score.h"
  48. #include "Note.h"
  49. #include "Deleter.h"
  50. #include "NoteGroup.h"
  51. #include "ILabelOutput.h"
  52. #include "LabelData.h"
  53. #include "LabelPosition.h"
  54. #include "LabelMeasure.h"
  55. #include "ScorePosition.h"
  56. #include "util_score.h"
  57. namespace sinsy
  58. {
  59. namespace
  60. {
  61. const std::string DEFAULT_ENCODING = "utf-8";
  62. class Copier
  63. {
  64. public:
  65. //! constructor
  66. Copier(IConf::ConvertableList& c);
  67. //! destructor
  68. virtual ~Copier();
  69. //! ...
  70. void operator()(NoteLabeler* n);
  71. private:
  72. //! list of IConvertable
  73. IConf::ConvertableList& cList;
  74. };
  75. /*!
  76. constructor
  77. */
  78. Copier::Copier(IConf::ConvertableList& c) : cList(c)
  79. {
  80. }
  81. /*!
  82. destructor
  83. */
  84. Copier::~Copier()
  85. {
  86. }
  87. /*!
  88. ...
  89. */
  90. void Copier::operator()(NoteLabeler* n)
  91. {
  92. cList.push_back(n);
  93. }
  94. class PhonemeLabel : public IPhonemeLabel
  95. {
  96. public:
  97. //! constructor
  98. PhonemeLabel(LabelData& ld, int d) : labelData(ld), diff(d) {}
  99. //! destructor
  100. virtual ~PhonemeLabel() {}
  101. //! set type
  102. virtual void setType(const std::string& value) {}
  103. //! set name
  104. virtual void setName(const std::string& value) {
  105. if (!value.empty()) {
  106. labelData.set('p', 4 + diff, value);
  107. }
  108. }
  109. //! set flag
  110. virtual void setFlag(const std::string& value) {
  111. if (!value.empty()) {
  112. labelData.set('p', 9 + diff, value);
  113. }
  114. }
  115. //! set position in syllable
  116. virtual void setPositionInSyllable(size_t idx, size_t max) {}
  117. //! set count from previous vowel
  118. virtual void setCountFromPrevVowel(size_t count) {}
  119. //! set count to next vowel
  120. virtual void setCountToNextVowel(size_t count) {}
  121. protected:
  122. //! label data
  123. LabelData& labelData;
  124. //! diff from current phoneme
  125. int diff;
  126. };
  127. class PrevPrevPhonemeLabel : public PhonemeLabel
  128. {
  129. public:
  130. //! constructor
  131. PrevPrevPhonemeLabel(LabelData& ld) : PhonemeLabel(ld, -2) {}
  132. //! destructor
  133. virtual ~PrevPrevPhonemeLabel() {}
  134. };
  135. class PrevPhonemeLabel : public PhonemeLabel
  136. {
  137. public:
  138. //! constructor
  139. PrevPhonemeLabel(LabelData& ld) : PhonemeLabel(ld, -1) {}
  140. //! destructor
  141. virtual ~PrevPhonemeLabel() {}
  142. };
  143. class CurrentPhonemeLabel : public PhonemeLabel
  144. {
  145. public:
  146. //! constructor
  147. CurrentPhonemeLabel(LabelData& ld) : PhonemeLabel(ld, 0) {}
  148. //! destructor
  149. virtual ~CurrentPhonemeLabel() {}
  150. //! set type
  151. virtual void setType(const std::string& value) {
  152. if (!value.empty()) {
  153. labelData.set('p', 1, value);
  154. }
  155. }
  156. //! set position in syllable
  157. virtual void setPositionInSyllable(size_t idx, size_t max) {
  158. labelData.set('p', 12, std::min<size_t>(idx + 1, 9));
  159. labelData.set('p', 13, std::min<size_t>(max - idx, 9));
  160. }
  161. //! set count from previous vowel
  162. virtual void setCountFromPrevVowel(size_t count) {
  163. if (0 < count) {
  164. labelData.set('p', 14, std::min<size_t>(count, 9));
  165. }
  166. }
  167. //! set count to next vowel
  168. virtual void setCountToNextVowel(size_t count) {
  169. if (0 < count) {
  170. labelData.set('p', 15, std::min<size_t>(count, 9));
  171. }
  172. }
  173. };
  174. class NextPhonemeLabel : public PhonemeLabel
  175. {
  176. public:
  177. //! constructor
  178. NextPhonemeLabel(LabelData& ld) : PhonemeLabel(ld, 1) {}
  179. //! destructor
  180. virtual ~NextPhonemeLabel() {}
  181. };
  182. class NextNextPhonemeLabel : public PhonemeLabel
  183. {
  184. public:
  185. //! constructor
  186. NextNextPhonemeLabel(LabelData& ld) : PhonemeLabel(ld, 2) {}
  187. //! destructor
  188. virtual ~NextNextPhonemeLabel() {}
  189. };
  190. class SyllableLabel : public ISyllableLabel
  191. {
  192. public:
  193. //! constructor
  194. SyllableLabel(LabelData& ld, char c) : labelData(ld), category(c) {}
  195. //! destructor
  196. virtual ~SyllableLabel() {}
  197. //! set phoneme number
  198. virtual void setPhonemeNum(size_t value) {
  199. labelData.set(category, 1, std::min<size_t>(value, 9));
  200. }
  201. //! set position in note
  202. virtual void setPositionInNote(size_t idx, size_t max) {
  203. labelData.set(category, 2, std::min<size_t>(idx + 1, 9));
  204. labelData.set(category, 3, std::min<size_t>(max - idx, 9));
  205. }
  206. //! set language
  207. virtual void setLanguage(const std::string& value) {
  208. labelData.set(category, 4, value);
  209. }
  210. //! set language dependent information
  211. virtual void setLangDependentInfo(const std::string& value) {
  212. labelData.set(category, 5, value);
  213. }
  214. protected:
  215. //! label data
  216. LabelData& labelData;
  217. //! category
  218. const char category;
  219. };
  220. class PrevSyllableLabel : public SyllableLabel
  221. {
  222. public:
  223. //! constructor
  224. PrevSyllableLabel(LabelData& ld) : SyllableLabel(ld, 'a') {}
  225. //! destructor
  226. virtual ~PrevSyllableLabel() {}
  227. };
  228. class CurrentSyllableLabel : public SyllableLabel
  229. {
  230. public:
  231. //! constructor
  232. CurrentSyllableLabel(LabelData& ld) : SyllableLabel(ld, 'b') {}
  233. //! destructor
  234. virtual ~CurrentSyllableLabel() {}
  235. };
  236. class NextSyllableLabel : public SyllableLabel
  237. {
  238. public:
  239. //! constructor
  240. NextSyllableLabel(LabelData& ld) : SyllableLabel(ld, 'c') {}
  241. //! destructor
  242. virtual ~NextSyllableLabel() {}
  243. };
  244. class _NoteLabel : public INoteLabel
  245. {
  246. public:
  247. //! constructor
  248. _NoteLabel(LabelData& ld, char c) : labelData(ld), category(c) {}
  249. //! destructor
  250. virtual ~_NoteLabel() {}
  251. //! set absolute pitch
  252. virtual void setAbsolutePitch(const Pitch& value) {
  253. labelData.set(category, 1, value);
  254. }
  255. //! set relative pitch
  256. virtual void setRelativePitch(size_t value) {
  257. labelData.set(category, 2, value);
  258. }
  259. //! set key
  260. virtual void setKey(size_t value) {
  261. labelData.set(category, 3, value);
  262. }
  263. //! set beat
  264. virtual void setBeat(const Beat& value) {
  265. labelData.set(category, 4, value);
  266. }
  267. //! set tempo
  268. virtual void setTempo(double value);
  269. //! set syllable number
  270. virtual void setSyllableNum(size_t value);
  271. //! set length
  272. virtual void setLength(const LabelPosition& value);
  273. //! set position in measure
  274. virtual void setPositionInMeasure(const LabelPosition&, const LabelPosition&) {}
  275. //! set position in phrase
  276. virtual void setPositionInPhrase(const LabelPosition&, const LabelPosition&) {}
  277. //! set slur from previous note
  278. virtual void setSlurFromPrev(bool) {}
  279. //! set slur to next note
  280. virtual void setSlurToNext(bool) {}
  281. //! set dynamics
  282. virtual void setDynamics(const Dynamics&) {}
  283. //! set length from previous accent
  284. virtual void setLengthFromPrevAccent(const LabelPosition&) {}
  285. //! set length to next accent
  286. virtual void setLengthToNextAccent(const LabelPosition&) {}
  287. //! set length from previous staccato
  288. virtual void setLengthFromPrevStaccato(const LabelPosition&) {}
  289. //! set length to next staccato
  290. virtual void setLengthToNextStaccato(const LabelPosition&) {}
  291. //! set position in creshendo
  292. virtual void setPositionInCrescendo(const LabelPosition&, const LabelPosition&) {}
  293. //! set position in diminuendo
  294. virtual void setPositionInDiminuendo(const LabelPosition&, const LabelPosition&) {}
  295. //! set pitch difference from previous note
  296. virtual void setPitchDifferenceFromPrev(int) {}
  297. //! set pitch difference to next note
  298. virtual void setPitchDifferenceToNext(int) {}
  299. //! set breath between previous and this notes
  300. virtual void setBreathFromPrev(bool) {}
  301. //! set breath between this and next notes
  302. virtual void setBreathToNext(bool) {}
  303. //! set prevous phrase information
  304. virtual void setPrevPhraseInfo(size_t, size_t) {}
  305. //! set phrase information
  306. virtual void setPhraseInfo(size_t, size_t) {}
  307. //! set next phrase information
  308. virtual void setNextPhraseInfo(size_t, size_t) {}
  309. protected:
  310. //! label data
  311. LabelData& labelData;
  312. //! category
  313. const char category;
  314. };
  315. /*!
  316. set tempo
  317. */
  318. void _NoteLabel::setTempo(double value)
  319. {
  320. if (value <= 0) {
  321. throw std::range_error("_NoteLabel::setTempo()");
  322. }
  323. size_t bpm(static_cast<size_t>(value + 0.5));
  324. labelData.set(category, 5, std::min<size_t>(bpm, 199));
  325. }
  326. /*!
  327. set syllable number
  328. */
  329. void _NoteLabel::setSyllableNum(size_t value)
  330. {
  331. labelData.set(category, 6, std::min<size_t>(value, 3));
  332. }
  333. /*!
  334. set length
  335. */
  336. void _NoteLabel::setLength(const LabelPosition& value)
  337. {
  338. {
  339. size_t time(static_cast<size_t>(value.getTime() * 100));
  340. labelData.set(category, 7, std::min<size_t>(time, 499));
  341. }
  342. {
  343. if (value.getPoint() < 0) {
  344. throw std::range_error("setLength() point is out of range");
  345. }
  346. size_t point(static_cast<size_t>(value.getPoint()));
  347. labelData.set(category, 8, std::min<size_t>(point, 199));
  348. }
  349. }
  350. class PrevNoteLabel : public _NoteLabel
  351. {
  352. public:
  353. //! constructor
  354. PrevNoteLabel(LabelData& ld) : _NoteLabel(ld, 'd') {}
  355. //! destructor
  356. virtual ~PrevNoteLabel() {}
  357. };
  358. class NoteLabel : public _NoteLabel
  359. {
  360. public:
  361. //! constructor
  362. NoteLabel(LabelData& ld) : _NoteLabel(ld, 'e') {}
  363. //! destructor
  364. virtual ~NoteLabel() {}
  365. //! set position in measure
  366. virtual void setPositionInMeasure(const LabelPosition& idx, const LabelPosition& max);
  367. //! set position in phrase
  368. virtual void setPositionInPhrase(const LabelPosition& idx, const LabelPosition& max);
  369. //! set slur from previous note
  370. virtual void setSlurFromPrev(bool value) {
  371. labelData.set(category, 26, value);
  372. }
  373. //! set slur to next note
  374. virtual void setSlurToNext(bool value) {
  375. labelData.set(category, 27, value);
  376. }
  377. //! set dynamics
  378. virtual void setDynamics(const Dynamics& value) {
  379. labelData.set(category, 28, value);
  380. }
  381. //! set length to next accent
  382. virtual void setLengthToNextAccent(const LabelPosition& value);
  383. //! set length from previous accent
  384. virtual void setLengthFromPrevAccent(const LabelPosition& value);
  385. //! set length to next staccato
  386. virtual void setLengthToNextStaccato(const LabelPosition& value);
  387. //! set length from provious staccato
  388. virtual void setLengthFromPrevStaccato(const LabelPosition& value);
  389. //! set position in crescendo
  390. virtual void setPositionInCrescendo(const LabelPosition& idx, const LabelPosition& max);
  391. //! set position in diminuendo
  392. virtual void setPositionInDiminuendo(const LabelPosition& idx, const LabelPosition& max);
  393. //! set pitch difference from previous note
  394. virtual void setPitchDifferenceFromPrev(int value);
  395. //! set pitch difference to next note
  396. virtual void setPitchDifferenceToNext(int value);
  397. //! set breath from previous note
  398. virtual void setBreathFromPrev(bool value) {
  399. labelData.set(category, 59, value);
  400. }
  401. //! set breath to next note
  402. virtual void setBreathToNext(bool value) {
  403. labelData.set(category, 60, value);
  404. }
  405. //! set prevous phrase information
  406. virtual void setPrevPhraseInfo(size_t syllableNum, size_t noteNum) {
  407. labelData.set('g', 1, syllableNum);
  408. labelData.set('g', 2, noteNum);
  409. }
  410. //! set phrase information
  411. virtual void setPhraseInfo(size_t syllableNum, size_t noteNum) {
  412. labelData.set('h', 1, syllableNum);
  413. labelData.set('h', 2, noteNum);
  414. }
  415. //! set next phrase information
  416. virtual void setNextPhraseInfo(size_t syllableNum, size_t noteNum) {
  417. labelData.set('i', 1, syllableNum);
  418. labelData.set('i', 2, noteNum);
  419. }
  420. };
  421. /*!
  422. set position in measure
  423. */
  424. void NoteLabel::setPositionInMeasure(const LabelPosition& idx, const LabelPosition& max)
  425. {
  426. LabelPosition diff(max - idx);
  427. {
  428. if (idx.getCount() < 0) {
  429. throw std::range_error("setPositionInMeasure() count is out of range");
  430. }
  431. size_t count(static_cast<size_t>(idx.getCount()) + 1);
  432. labelData.set(category, 10, std::min<size_t>(count, 49));
  433. }
  434. {
  435. if (diff.getCount() < 0) {
  436. throw std::range_error("setPositionInMeasure() count is out of range");
  437. }
  438. size_t count(static_cast<size_t>(diff.getCount()));
  439. labelData.set(category, 11, std::min<size_t>(count, 49));
  440. }
  441. {
  442. if (idx.getTime() < 0.0) {
  443. throw std::range_error("setPositionInMeasure() time is out of range");
  444. }
  445. size_t time(static_cast<size_t>(idx.getTime() * 10));
  446. labelData.set(category, 12, std::min<size_t>(time, 49));
  447. }
  448. {
  449. if (diff.getTime() < 0.0) {
  450. WARN_MSG("Wrong position in a measure : position[" << idx << " / " << max << "] (probably calculation error)");
  451. }
  452. size_t time(static_cast<size_t>(diff.getTime() * 10));
  453. labelData.set(category, 13, std::min<size_t>(time, 49));
  454. }
  455. {
  456. if (idx.getPoint() < 0) {
  457. throw std::range_error("setPositionInMeasure() point is out of range");
  458. }
  459. size_t point(static_cast<size_t>(idx.getPoint()));
  460. labelData.set(category, 14, std::min<size_t>(point, 96));
  461. }
  462. {
  463. if (diff.getPoint() < 0) {
  464. throw std::range_error("setPositionInMeasure() point is out of range");
  465. }
  466. size_t point(static_cast<size_t>(diff.getPoint()));
  467. labelData.set(category, 15, std::min<size_t>(point, 96));
  468. }
  469. size_t persent(static_cast<size_t>(idx.getTime() * 100 / max.getTime()));
  470. labelData.set(category, 16, persent);
  471. labelData.set(category, 17, 100 - persent);
  472. }
  473. /*!
  474. set position in phrase
  475. */
  476. void NoteLabel::setPositionInPhrase(const LabelPosition& idx, const LabelPosition& max)
  477. {
  478. LabelPosition diff(max - idx);
  479. {
  480. if (idx.getCount() < 0) {
  481. throw std::range_error("setPositionInPhrase() count is out of range");
  482. }
  483. size_t count(static_cast<size_t>(idx.getCount()) + 1);
  484. labelData.set(category, 18, std::min<size_t>(count, 49));
  485. }
  486. {
  487. if (diff.getCount() < 0) {
  488. throw std::range_error("setPositionInPhrase() count is out of range");
  489. }
  490. size_t count(static_cast<size_t>(diff.getCount()));
  491. labelData.set(category, 19, std::min<size_t>(count, 49));
  492. }
  493. {
  494. if (idx.getTime() < 0.0) {
  495. throw std::range_error("setPositionInPhrase() time is out of range");
  496. }
  497. size_t time(static_cast<size_t>(idx.getTime() * 10));
  498. labelData.set(category, 20, std::min<size_t>(time, 199));
  499. }
  500. {
  501. if (diff.getTime() < 0.0) {
  502. WARN_MSG("Wrong position in a phrase : position[" << idx << " / " << max << "] (probably calculation error)");
  503. }
  504. size_t time(static_cast<size_t>(diff.getTime() * 10));
  505. labelData.set(category, 21, std::min<size_t>(time, 199));
  506. }
  507. {
  508. if (idx.getPoint() < 0) {
  509. throw std::range_error("setPositionInPhrase() point is out of range");
  510. }
  511. size_t point(static_cast<size_t>(idx.getPoint()));
  512. labelData.set(category, 22, std::min<size_t>(point, 499));
  513. }
  514. {
  515. if (diff.getPoint() < 0) {
  516. throw std::range_error("setPositionInPhrase() point is out of range");
  517. }
  518. size_t point(static_cast<size_t>(diff.getPoint()));
  519. labelData.set(category, 23, std::min<size_t>(point, 499));
  520. }
  521. size_t persent(static_cast<size_t>(idx.getTime() * 100 / max.getTime()));
  522. labelData.set(category, 24, persent);
  523. labelData.set(category, 25, 100 - persent);
  524. }
  525. /*!
  526. set length to next accent
  527. */
  528. void NoteLabel::setLengthToNextAccent(const LabelPosition& value)
  529. {
  530. {
  531. if (value.getCount() < 0) {
  532. throw std::range_error("setLengthToNextAccent() count is out of range");
  533. }
  534. size_t count(static_cast<size_t>(value.getCount()));
  535. labelData.set(category, 29, std::min<size_t>(count, 9));
  536. }
  537. {
  538. if (value.getTime() < 0.0) {
  539. throw std::range_error("setLengthToNextAccent() time is out of range");
  540. }
  541. size_t time(static_cast<size_t>(value.getTime() * 10));
  542. labelData.set(category, 31, std::min<size_t>(time, 99));
  543. }
  544. {
  545. if (value.getPoint() < 0) {
  546. throw std::range_error("setLengthToNextAccent() point is out of range");
  547. }
  548. size_t point(static_cast<size_t>(value.getPoint()));
  549. labelData.set(category, 33, std::min<size_t>(point, 99));
  550. }
  551. }
  552. /*!
  553. set length from previous accent
  554. */
  555. void NoteLabel::setLengthFromPrevAccent(const LabelPosition& value)
  556. {
  557. {
  558. if (value.getCount() < 0) {
  559. throw std::range_error("setLengthFromPrevAccent() count is out of range");
  560. }
  561. size_t count(static_cast<size_t>(value.getCount()));
  562. labelData.set(category, 30, std::min<size_t>(count, 9));
  563. }
  564. {
  565. if (value.getTime() < 0.0) {
  566. throw std::range_error("setLengthFromPrevAccent() time is out of range");
  567. }
  568. size_t time(static_cast<size_t>(value.getTime() * 10));
  569. labelData.set(category, 32, std::min<size_t>(time, 99));
  570. }
  571. {
  572. if (value.getPoint() < 0) {
  573. throw std::range_error("setLengthFromPrevAccent() point is out of range");
  574. }
  575. size_t point(static_cast<size_t>(value.getPoint()));
  576. labelData.set(category, 34, std::min<size_t>(point, 99));
  577. }
  578. }
  579. /*!
  580. set length to next staccato
  581. */
  582. void NoteLabel::setLengthToNextStaccato(const LabelPosition& value)
  583. {
  584. {
  585. if (value.getCount() < 0) {
  586. throw std::range_error("setLengthToNextStaccato() count is out of range");
  587. }
  588. size_t count(static_cast<size_t>(value.getCount()));
  589. labelData.set(category, 35, std::min<size_t>(count, 9));
  590. }
  591. {
  592. if (value.getTime() < 0.0) {
  593. throw std::range_error("setLengthToNextStaccato() time is out of range");
  594. }
  595. size_t time(static_cast<size_t>(value.getTime() * 10));
  596. labelData.set(category, 37, std::min<size_t>(time, 99));
  597. }
  598. {
  599. if (value.getPoint() < 0) {
  600. throw std::range_error("setLengthToNextStaccato() point is out of range");
  601. }
  602. size_t point(static_cast<size_t>(value.getPoint()));
  603. labelData.set(category, 39, std::min<size_t>(point, 99));
  604. }
  605. }
  606. /*!
  607. set length from previous staccato
  608. */
  609. void NoteLabel::setLengthFromPrevStaccato(const LabelPosition& value)
  610. {
  611. {
  612. if (value.getCount() < 0) {
  613. throw std::range_error("setLengthFromPrevStaccato() count is out of range");
  614. }
  615. size_t count(static_cast<size_t>(value.getCount()));
  616. labelData.set(category, 36, std::min<size_t>(count, 9));
  617. }
  618. {
  619. if (value.getTime() < 0.0) {
  620. throw std::range_error("setLengthFromPrevStaccato() time is out of range");
  621. }
  622. size_t time(static_cast<size_t>(value.getTime() * 10));
  623. labelData.set(category, 38, std::min<size_t>(time, 99));
  624. }
  625. {
  626. if (value.getPoint() < 0) {
  627. throw std::range_error("setLengthFromPrevStaccato() point is out of range");
  628. }
  629. size_t point(static_cast<size_t>(value.getPoint()));
  630. labelData.set(category, 40, std::min<size_t>(point, 99));
  631. }
  632. }
  633. /*!
  634. set position in crescendo
  635. */
  636. void NoteLabel::setPositionInCrescendo(const LabelPosition& idx, const LabelPosition& max)
  637. {
  638. LabelPosition diff(max - idx);
  639. {
  640. if (idx.getCount() < 0) {
  641. throw std::range_error("setPositionInCrescendo() count is out of range");
  642. }
  643. size_t count(static_cast<size_t>(idx.getCount()) + 1);
  644. labelData.set(category, 41, std::min<size_t>(count, 49));
  645. }
  646. {
  647. if (diff.getCount() < 0) {
  648. throw std::range_error("setPositionInCrescendo() count is out of range");
  649. }
  650. size_t count(static_cast<size_t>(diff.getCount()));
  651. labelData.set(category, 42, std::min<size_t>(count, 49));
  652. }
  653. {
  654. if (idx.getTime() < 0.0) {
  655. throw std::range_error("setPositionInCrescendo() time is out of range");
  656. }
  657. size_t time(static_cast<size_t>(idx.getTime() * 10));
  658. labelData.set(category, 43, std::min<size_t>(time, 99));
  659. }
  660. {
  661. if (diff.getTime() < 0.0) {
  662. WARN_MSG("Wrong position in a crescendo : position[" << idx << " / " << max << "] (probably calculation error)");
  663. }
  664. size_t time(static_cast<size_t>(diff.getTime() * 10));
  665. labelData.set(category, 44, std::min<size_t>(time, 99));
  666. }
  667. {
  668. if (idx.getPoint() < 0) {
  669. throw std::range_error("setPositionInCrescendo() point is out of range");
  670. }
  671. size_t point(static_cast<size_t>(idx.getPoint()));
  672. labelData.set(category, 45, std::min<size_t>(point, 499));
  673. }
  674. {
  675. if (diff.getPoint() < 0) {
  676. throw std::range_error("setPositionInCrescendo() point is out of range");
  677. }
  678. size_t point(static_cast<size_t>(diff.getPoint()));
  679. labelData.set(category, 46, std::min<size_t>(point, 499));
  680. }
  681. size_t persent(static_cast<size_t>(idx.getTime() * 100 / max.getTime()));
  682. labelData.set(category, 47, persent);
  683. labelData.set(category, 48, 100 - persent);
  684. }
  685. /*!
  686. set position in diminundo
  687. */
  688. void NoteLabel::setPositionInDiminuendo(const LabelPosition& idx, const LabelPosition& max)
  689. {
  690. LabelPosition diff(max - idx);
  691. {
  692. if (idx.getCount() < 0) {
  693. throw std::range_error("setPositionInDiminuendo() count is out of range");
  694. }
  695. size_t count(static_cast<size_t>(idx.getCount()) + 1);
  696. labelData.set(category, 49, std::min<size_t>(count, 49));
  697. }
  698. {
  699. if (diff.getCount() < 0) {
  700. throw std::range_error("setPositionInDiminuendo() count is out of range");
  701. }
  702. size_t count(static_cast<size_t>(diff.getCount()));
  703. labelData.set(category, 50, std::min<size_t>(count, 49));
  704. }
  705. {
  706. if (idx.getTime() < 0.0) {
  707. throw std::range_error("setPositionInDiminuendo() time is out of range");
  708. }
  709. size_t time(static_cast<size_t>(idx.getTime() * 10));
  710. labelData.set(category, 51, std::min<size_t>(time, 99));
  711. }
  712. {
  713. if (diff.getTime() < 0.0) {
  714. WARN_MSG("Wrong position in a diminuendo : position[" << idx << " / " << max << "] (probably calculation error)");
  715. }
  716. size_t time(static_cast<size_t>(diff.getTime() * 10));
  717. labelData.set(category, 52, std::min<size_t>(time, 99));
  718. }
  719. {
  720. if (idx.getPoint() < 0) {
  721. throw std::range_error("setPositionInDiminuendo() point is out of range");
  722. }
  723. size_t point(static_cast<size_t>(idx.getPoint()));
  724. labelData.set(category, 53, std::min<size_t>(point, 499));
  725. }
  726. {
  727. if (diff.getPoint() < 0) {
  728. throw std::range_error("setPositionInDiminuendo() point is out of range");
  729. }
  730. size_t point(static_cast<size_t>(diff.getPoint()));
  731. labelData.set(category, 54, std::min<size_t>(point, 499));
  732. }
  733. size_t persent(static_cast<size_t>(idx.getTime() * 100 / max.getTime()));
  734. labelData.set(category, 55, persent);
  735. labelData.set(category, 56, 100 - persent);
  736. }
  737. /*!
  738. set pitch difference from previous note
  739. */
  740. void NoteLabel::setPitchDifferenceFromPrev(int value)
  741. {
  742. std::ostringstream oss;
  743. if (value < 0) {
  744. oss << "m";
  745. value *= -1;
  746. } else {
  747. oss << "p";
  748. }
  749. oss << value;
  750. labelData.set(category, 57, oss.str());
  751. }
  752. /*!
  753. set pitch difference to next
  754. */
  755. void NoteLabel::setPitchDifferenceToNext(int value)
  756. {
  757. std::ostringstream oss;
  758. if (value < 0) {
  759. oss << "m";
  760. value *= -1;
  761. } else {
  762. oss << "p";
  763. }
  764. oss << value;
  765. labelData.set(category, 58, oss.str());
  766. }
  767. class NextNoteLabel : public _NoteLabel
  768. {
  769. public:
  770. //! constructor
  771. NextNoteLabel(LabelData& ld) : _NoteLabel(ld, 'f') {}
  772. //! destructor
  773. virtual ~NextNoteLabel() {}
  774. };
  775. }; // namespace
  776. /*!
  777. constructor
  778. */
  779. LabelMaker::LabelMaker(Converter& c, bool sepRests) :
  780. converter(c), encoding(DEFAULT_ENCODING), separateWholeNoteRests(sepRests),
  781. isFixed(false), tempo(DEFAULT_TEMPO), syllableNum(0),
  782. inTie(false), inCrescendo(false), inDiminuendo(false), residualMeasureDuration(0)
  783. {
  784. }
  785. /*!
  786. destructor
  787. */
  788. LabelMaker::~LabelMaker()
  789. {
  790. std::for_each(noteList.begin(), noteList.end(), Deleter<NoteLabeler>());
  791. std::for_each(measureList.begin(), measureList.end(), Deleter<LabelMeasure>());
  792. std::for_each(phraseList.begin(), phraseList.end(), Deleter<NoteGroup>());
  793. std::for_each(crescendoList.begin(), crescendoList.end(), Deleter<NoteGroup>());
  794. std::for_each(diminuendoList.begin(), diminuendoList.end(), Deleter<NoteGroup>());
  795. }
  796. /*!
  797. set encoding
  798. */
  799. void LabelMaker::setEncoding(const std::string& e)
  800. {
  801. if (isFixed) {
  802. throw std::runtime_error("LabelMaker::setEncoding() already fixed");
  803. }
  804. this->encoding = e;
  805. }
  806. /*!
  807. change tempo
  808. */
  809. void LabelMaker::changeTempo(double t)
  810. {
  811. if (isFixed) {
  812. throw std::runtime_error("LabelMaker::changeTempo() already fixed");
  813. }
  814. this->tempo = t;
  815. }
  816. /*!
  817. change beat
  818. */
  819. void LabelMaker::changeBeat(const Beat& b)
  820. {
  821. if (isFixed) {
  822. throw std::runtime_error("LabelMaker::changeBeat() already fixed");
  823. }
  824. this->beat = b;
  825. }
  826. /*!
  827. change dynamics
  828. */
  829. void LabelMaker::changeDynamics(const Dynamics& d)
  830. {
  831. if (isFixed) {
  832. throw std::runtime_error("LabelMaker::changeDynamics() already fixed");
  833. }
  834. this->dynamics = d;
  835. }
  836. /*!
  837. change key
  838. */
  839. void LabelMaker::changeKey(const Key& k)
  840. {
  841. if (isFixed) {
  842. throw std::runtime_error("LabelMaker::changeKey() already fixed");
  843. }
  844. this->key = k;
  845. }
  846. /*!
  847. start crescendo
  848. */
  849. void LabelMaker::startCrescendo()
  850. {
  851. if (isFixed) {
  852. throw std::runtime_error("LabelMaker::startCrescendo() already fixed");
  853. }
  854. if (inTie) {
  855. tempScore.startCrescendo();
  856. return;
  857. }
  858. if (inCrescendo) {
  859. WARN_MSG("Cannot start a crescendo : already in a crescendo");
  860. return;
  861. }
  862. crescendoList.push_back(new NoteGroup());
  863. inCrescendo = true;
  864. }
  865. /*!
  866. start diminuendo
  867. */
  868. void LabelMaker::startDiminuendo()
  869. {
  870. if (isFixed) {
  871. throw std::runtime_error("LabelMaker::startDiminuendo() already fixed");
  872. }
  873. if (inTie) {
  874. tempScore.startDiminuendo();
  875. return;
  876. }
  877. if (inDiminuendo) {
  878. WARN_MSG("Cannot start a diminuendo : already in a diminuendo");
  879. return;
  880. }
  881. diminuendoList.push_back(new NoteGroup());
  882. inDiminuendo = true;
  883. }
  884. /*!
  885. stop crescendo
  886. */
  887. void LabelMaker::stopCrescendo()
  888. {
  889. if (isFixed) {
  890. throw std::runtime_error("LabelMaker::stopCrescendo() already fixed");
  891. }
  892. if (inTie) {
  893. tempScore.stopCrescendo();
  894. return;
  895. }
  896. inCrescendo = false;
  897. }
  898. /*!
  899. stop diminuendo
  900. */
  901. void LabelMaker::stopDiminuendo()
  902. {
  903. if (isFixed) {
  904. throw std::runtime_error("LabelMaker::stopDiminuendo() already fixed");
  905. }
  906. if (inTie) {
  907. tempScore.stopDiminuendo();
  908. return;
  909. }
  910. inDiminuendo = false;
  911. }
  912. /*!
  913. add note
  914. */
  915. void LabelMaker::addNote(const Note& note)
  916. {
  917. if (isFixed) {
  918. throw std::runtime_error("LabelMaker::addNote() already fixed");
  919. }
  920. // if the first note is not rest, add a rest at first
  921. if (!note.isRest() && measureList.empty()) {
  922. WARN_MSG("The first note is not rest");
  923. Note restNote;
  924. restNote.setRest(true);
  925. restNote.setDuration(getMeasureDuration(beat));
  926. addNote(restNote);
  927. }
  928. if (inTie && ((noteList.back()->isRest() != note.isRest())
  929. || (!noteList.back()->isRest() && (noteList.back()->getPitch() != note.getPitch())))) {
  930. inTie = false;
  931. if (inCrescendo) {
  932. noteList.back()->setCrescendo(crescendoList.back());
  933. }
  934. if (inDiminuendo) {
  935. noteList.back()->setDiminuendo(diminuendoList.back());
  936. }
  937. applyStocks();
  938. // for log
  939. if (note.isRest()) {
  940. WARN_MSG("Rest cannot be tied");
  941. } else if (!noteList.back()->isRest() && (noteList.back()->getPitch() != note.getPitch())) {
  942. WARN_MSG("Notes that have different pitches cannot be tied");
  943. }
  944. }
  945. {
  946. size_t duration(note.getDuration());
  947. if (static_cast<size_t>(std::numeric_limits<int>::max()) < duration) {
  948. throw std::runtime_error("LabelMaker::addNote() duration is larger than max of int");
  949. }
  950. while (residualMeasureDuration < static_cast<int>(duration)) {
  951. if (0 < residualMeasureDuration) {
  952. measurePosition.add(residualMeasureDuration, tempo);
  953. getLastMeasure()->setMaxPosition(measurePosition);
  954. if (static_cast<int>(duration) < residualMeasureDuration) {
  955. throw std::runtime_error("LabelMaker::addNote() duration is smaller than residual measure duration");
  956. }
  957. duration -= residualMeasureDuration;
  958. if (static_cast<size_t>(std::numeric_limits<int>::max()) < duration) {
  959. throw std::runtime_error("LabelMaker::addNote() duration is larger than max of int");
  960. }
  961. }
  962. size_t measureIndex(measureList.size() + stockMeasures.size());
  963. stockMeasures.push_back(new LabelMeasure(this->beat));
  964. stockMeasures.back()->setIndex(measureIndex);
  965. if ((0 == residualMeasureDuration && !inTie)) {
  966. applyStocks();
  967. }
  968. residualMeasureDuration = getMeasureDuration(beat);
  969. measurePosition = LabelPosition(0, tempo);
  970. }
  971. measurePosition.add(duration, tempo);
  972. getLastMeasure()->setMaxPosition(measurePosition);
  973. residualMeasureDuration -= duration;
  974. }
  975. if (!inTie) {
  976. NoteLabeler* noteLabeler(new NoteLabeler(beat, dynamics, key));
  977. noteLabeler->setMeasure(measureList.back());
  978. noteList.push_back(noteLabeler);
  979. }
  980. if (note.isRest()) {
  981. inTie = true;
  982. } else {
  983. if (note.isTieStop()) {
  984. inTie = false;
  985. }
  986. if (note.isTieStart()) {
  987. inTie = true;
  988. }
  989. }
  990. noteList.back()->addNote(note, tempo);
  991. if (!inTie) {
  992. applyStocks();
  993. if (inCrescendo) {
  994. noteList.back()->setCrescendo(crescendoList.back());
  995. }
  996. if (inDiminuendo) {
  997. noteList.back()->setDiminuendo(diminuendoList.back());
  998. }
  999. }
  1000. }
  1001. /*!
  1002. fix
  1003. */
  1004. void LabelMaker::fix()
  1005. {
  1006. if (isFixed) {
  1007. throw std::runtime_error("LabelMaker::fix() already fixed");
  1008. }
  1009. // add last rest
  1010. {
  1011. // add rest to fix measure
  1012. if (0 != residualMeasureDuration) {
  1013. WARN_MSG("Length of notes in the last measure is not just");
  1014. int dur(residualMeasureDuration);
  1015. while (dur < 0) {
  1016. dur += getMeasureDuration(beat);
  1017. }
  1018. Note restNote;
  1019. restNote.setRest(true);
  1020. restNote.setDuration(static_cast<size_t>(dur));
  1021. addNote(restNote);
  1022. // if the last note is not rest, add a rest at last
  1023. } else if (!noteList.empty() && !noteList.back()->isRest()) {
  1024. WARN_MSG("The last note is not rest");
  1025. Note restNote;
  1026. restNote.setRest(true);
  1027. restNote.setDuration(getMeasureDuration(beat));
  1028. addNote(restNote);
  1029. }
  1030. inTie = false;
  1031. applyStocks();
  1032. }
  1033. {
  1034. bool inSlur(false);
  1035. NoteLabeler* lastPitch(NULL);
  1036. syllableNum = 0;
  1037. const NoteList::iterator itrBegin(noteList.begin());
  1038. const NoteList::iterator itrEnd(noteList.end());
  1039. for (NoteList::iterator itr(itrBegin); itrEnd != itr; ++itr) {
  1040. // phrase
  1041. {
  1042. if (!(*itr)->isRest()) {
  1043. if ((itr == itrBegin) || (*(itr - 1))->isRest() || (*(itr - 1))->hasBreathToNext()) {
  1044. phraseList.push_back(new NoteGroup());
  1045. }
  1046. (*itr)->setPhrase(phraseList.back());
  1047. }
  1048. }
  1049. // next and prev notes
  1050. {
  1051. if (itrBegin != itr) {
  1052. (*itr)->setPrevNote(*(itr - 1));
  1053. (*(itr - 1))->setNextNote(*itr);
  1054. }
  1055. }
  1056. // slur
  1057. {
  1058. (*itr)->setInSlurFromPrev(inSlur);
  1059. if ((*itr)->isSlurStop()) {
  1060. inSlur = false;
  1061. }
  1062. if ((*itr)->isSlurStart()) {
  1063. inSlur = true;
  1064. }
  1065. (*itr)->setInSlurToNext(inSlur);
  1066. }
  1067. // pitch difference
  1068. {
  1069. if (!(*itr)->isRest()) {
  1070. if (lastPitch) {
  1071. (*itr)->setPrevPitch(lastPitch->getPitch());
  1072. lastPitch->setNextPitch((*itr)->getPitch());
  1073. }
  1074. lastPitch = *itr;
  1075. }
  1076. }
  1077. }
  1078. }
  1079. // accent & staccato (next)
  1080. {
  1081. bool hasAccent(false);
  1082. bool hasStaccato(false);
  1083. LabelPosition accentPos;
  1084. LabelPosition staccatoPos;
  1085. const NoteList::reverse_iterator itrEnd(noteList.rend());
  1086. for (NoteList::reverse_iterator itr(noteList.rbegin()); itrEnd != itr; ++itr) {
  1087. if ((*itr)->isRest()) {
  1088. accentPos = LabelPosition();
  1089. staccatoPos = LabelPosition();
  1090. hasAccent = false;
  1091. hasStaccato = false;
  1092. } else {
  1093. LabelPosition length((*itr)->getLength());
  1094. if (hasAccent) {
  1095. accentPos += length;
  1096. (*itr)->setNextAccentPosition(accentPos);
  1097. }
  1098. if ((*itr)->hasAccent()) {
  1099. accentPos = LabelPosition();
  1100. hasAccent = true;
  1101. }
  1102. if (hasStaccato) {
  1103. staccatoPos += length;
  1104. (*itr)->setNextStaccatoPosition(staccatoPos);
  1105. }
  1106. if ((*itr)->hasStaccato()) {
  1107. staccatoPos = LabelPosition();
  1108. hasStaccato = true;
  1109. }
  1110. }
  1111. }
  1112. }
  1113. // accent & staccato (prev)
  1114. {
  1115. bool hasAccent(false);
  1116. bool hasStaccato(false);
  1117. LabelPosition accentPos;
  1118. LabelPosition staccatoPos;
  1119. const NoteList::iterator itrEnd(noteList.end());
  1120. for (NoteList::iterator itr(noteList.begin()); itrEnd != itr; ++itr) {
  1121. if ((*itr)->isRest()) {
  1122. accentPos = LabelPosition();
  1123. staccatoPos = LabelPosition();
  1124. hasAccent = false;
  1125. hasStaccato = false;
  1126. } else {
  1127. LabelPosition length((*itr)->getLength());
  1128. if (hasAccent) {
  1129. (*itr)->setPrevAccentPosition(accentPos);
  1130. accentPos += length;
  1131. }
  1132. if ((*itr)->hasAccent()) {
  1133. accentPos = length;
  1134. hasAccent = true;
  1135. }
  1136. if (hasStaccato) {
  1137. (*itr)->setPrevStaccatoPosition(staccatoPos);
  1138. staccatoPos += length;
  1139. }
  1140. if ((*itr)->hasStaccato()) {
  1141. staccatoPos = length;
  1142. hasStaccato = true;
  1143. }
  1144. }
  1145. }
  1146. }
  1147. // set prev phrase
  1148. {
  1149. const NoteGroup* prevPhrase(NULL);
  1150. const NoteList::iterator itrBegin(noteList.begin());
  1151. const NoteList::iterator itrEnd(noteList.end());
  1152. for (NoteList::iterator itr(itrBegin); itrEnd != itr; ++itr) {
  1153. const NoteGroup* p((*itr)->getPhrase());
  1154. const NoteGroup* pOld((itrBegin == itr) ? NULL : (*(itr - 1))->getPhrase());
  1155. if (NULL != pOld) {
  1156. if (pOld != p) {
  1157. prevPhrase = pOld;
  1158. }
  1159. }
  1160. (*itr)->setPrevPhrase(prevPhrase);
  1161. }
  1162. }
  1163. // set next phrase
  1164. {
  1165. const NoteGroup* nextPhrase(NULL);
  1166. const NoteList::reverse_iterator itrBegin(noteList.rbegin());
  1167. const NoteList::reverse_iterator itrEnd(noteList.rend());
  1168. for (NoteList::reverse_iterator itr(itrBegin); itrEnd != itr; ++itr) {
  1169. const NoteGroup* p((*itr)->getPhrase());
  1170. const NoteGroup* pOld((itrBegin == itr) ? NULL : (*(itr - 1))->getPhrase());
  1171. if (NULL != pOld) {
  1172. if (pOld != p) {
  1173. nextPhrase = pOld;
  1174. }
  1175. }
  1176. (*itr)->setNextPhrase(nextPhrase);
  1177. }
  1178. }
  1179. // convert
  1180. {
  1181. IConf::ConvertableList cList;
  1182. cList.reserve(noteList.size());
  1183. std::for_each(noteList.begin(), noteList.end(), Copier(cList));
  1184. converter.convert(encoding, cList.begin(), cList.end());
  1185. }
  1186. // breath
  1187. {
  1188. const NoteList::iterator itrBegin(noteList.begin());
  1189. const NoteList::iterator itrEnd(noteList.end());
  1190. for (NoteList::iterator itr(itrBegin); itrEnd != itr; ++itr) {
  1191. if (!(*itr)->isRest() && (*itr)->hasBreathToNext()) { // note has breath symbol
  1192. if ((itrEnd != itr + 1) && !(*(itr + 1))->isRest()) { // next note is not rest
  1193. (*itr)->setBreathPhoneme();
  1194. }
  1195. }
  1196. }
  1197. }
  1198. // set positions
  1199. {
  1200. const NoteList::iterator itrBegin(noteList.begin());
  1201. const NoteList::iterator itrEnd(noteList.end());
  1202. for (NoteList::iterator itr(itrBegin); itrEnd != itr; ++itr) {
  1203. (*itr)->setPositions();
  1204. }
  1205. }
  1206. // count syllables
  1207. {
  1208. syllableNum = 0;
  1209. const NoteList::iterator itrEnd(noteList.end());
  1210. for (NoteList::iterator itr(noteList.begin()); itrEnd != itr; ++itr) {
  1211. syllableNum += (*itr)->getSyllableNum();
  1212. }
  1213. }
  1214. isFixed = true;
  1215. }
  1216. /*!
  1217. output label
  1218. */
  1219. void LabelMaker::outputLabel(ILabelOutput& output, bool monophoneFlag, int overwriteEnableFlag, int timeFlag) const
  1220. {
  1221. if ((overwriteEnableFlag < 0) || (2 < overwriteEnableFlag)) {
  1222. throw std::out_of_range("LabelMaker::outputLabel() overwriteEnableFlag is out of range [0...2]");
  1223. }
  1224. if ((timeFlag < 0) || (2 < timeFlag)) {
  1225. throw std::out_of_range("LabelMaker::outputLabel() timeFlag is out of range [0...2]");
  1226. }
  1227. double time(0.0);
  1228. // Note
  1229. const NoteList::const_iterator nItrBegin(noteList.begin());
  1230. const NoteList::const_iterator nItrEnd(noteList.end());
  1231. for (NoteList::const_iterator nItr(nItrBegin) ; nItrEnd != nItr; ++nItr) {
  1232. double beginTime(0.0);
  1233. // Syllable
  1234. const NoteLabeler::List::const_iterator sItrBegin((*nItr)->childBegin());
  1235. const NoteLabeler::List::const_iterator sItrEnd((*nItr)->childEnd());
  1236. for (NoteLabeler::List::const_iterator sItr(sItrBegin) ; sItrEnd != sItr; ++sItr) {
  1237. // Phoneme
  1238. const SyllableLabeler::List::const_iterator pItrBegin((*sItr)->childBegin());
  1239. const SyllableLabeler::List::const_iterator pItrEnd((*sItr)->childEnd());
  1240. for (SyllableLabeler::List::const_iterator pItr(pItrBegin); pItrEnd != pItr; ++pItr) {
  1241. LabelData labelData;
  1242. labelData.setMonophoneFlag(monophoneFlag);
  1243. if (0 != timeFlag) {
  1244. labelData.setOutputTimeFlag(true);
  1245. // begin time
  1246. if ((sItrBegin == sItr) && (pItrBegin == pItr)) {
  1247. labelData.setBeginTime(time);
  1248. beginTime = time;
  1249. time += (*nItr)->getLength().getTime();
  1250. } else if (1 == timeFlag) {
  1251. labelData.setBeginTime(beginTime);
  1252. }
  1253. // end time
  1254. if ((sItrEnd == (sItr + 1)) && (pItrEnd == (pItr + 1))) {
  1255. labelData.setEndTime(time);
  1256. } else if (1 == timeFlag) {
  1257. labelData.setEndTime(time);
  1258. }
  1259. } else {
  1260. labelData.setOutputTimeFlag(false);
  1261. }
  1262. setLabelData(labelData, nItr, sItr, pItr, overwriteEnableFlag, timeFlag);
  1263. std::ostringstream oss;
  1264. oss << labelData;
  1265. output.output(oss.str());
  1266. }
  1267. }
  1268. }
  1269. }
  1270. /*!
  1271. get last measure
  1272. */
  1273. LabelMeasure* LabelMaker::getLastMeasure()
  1274. {
  1275. if (!stockMeasures.empty()) {
  1276. return stockMeasures.back();
  1277. }
  1278. if (!measureList.empty()) {
  1279. return measureList.back();
  1280. }
  1281. return NULL;
  1282. }
  1283. /*!
  1284. @internal
  1285. move to previous note
  1286. */
  1287. bool LabelMaker::moveToPrevNote(ConstNoteItr& nItr, bool skipRests) const
  1288. {
  1289. for ( ; ; ) {
  1290. if (noteList.begin() == nItr) {
  1291. return false;
  1292. }
  1293. --nItr;
  1294. if (!skipRests || !(*nItr)->isRest()) {
  1295. break;
  1296. }
  1297. }
  1298. return true;
  1299. }
  1300. /*!
  1301. @internal
  1302. move to next note
  1303. */
  1304. bool LabelMaker::moveToNextNote(ConstNoteItr& nItr, bool skipRests) const
  1305. {
  1306. for ( ; ; ) {
  1307. if (noteList.end() == nItr + 1) {
  1308. return false;
  1309. }
  1310. ++nItr;
  1311. if (!skipRests || !(*nItr)->isRest()) {
  1312. break;
  1313. }
  1314. }
  1315. return true;
  1316. }
  1317. /*!
  1318. @internal
  1319. move to previous syllable
  1320. */
  1321. bool LabelMaker::moveToPrevSyllable(ConstNoteItr& nItr, ConstSyllableItr& sItr, bool skipRests) const
  1322. {
  1323. if ((*nItr)->childBegin() == sItr) {
  1324. if (false == moveToPrevNote(nItr, skipRests)) {
  1325. return false;
  1326. }
  1327. sItr = (*nItr)->childEnd() - 1;
  1328. } else {
  1329. --sItr;
  1330. }
  1331. return true;
  1332. }
  1333. /*!
  1334. @internal
  1335. move to next syllable
  1336. */
  1337. bool LabelMaker::moveToNextSyllable(ConstNoteItr& nItr, ConstSyllableItr& sItr, bool skipRests) const
  1338. {
  1339. if ((*nItr)->childEnd() - 1 == sItr) {
  1340. if (false == moveToNextNote(nItr, skipRests)) {
  1341. return false;
  1342. }
  1343. sItr = (*nItr)->childBegin();
  1344. } else {
  1345. ++sItr;
  1346. }
  1347. return true;
  1348. }
  1349. /*!
  1350. @internal
  1351. move to previous phoneme
  1352. */
  1353. bool LabelMaker::moveToPrevPhoneme(ConstNoteItr& nItr, ConstSyllableItr& sItr, ConstPhonemeItr& pItr, bool skipRests) const
  1354. {
  1355. if ((*sItr)->childBegin() == pItr) {
  1356. if (false == moveToPrevSyllable(nItr, sItr, skipRests)) {
  1357. return false;
  1358. }
  1359. pItr = (*sItr)->childEnd() - 1;
  1360. } else {
  1361. --pItr;
  1362. }
  1363. return true;
  1364. }
  1365. /*!
  1366. @internal
  1367. move to next phoneme
  1368. */
  1369. bool LabelMaker::moveToNextPhoneme(ConstNoteItr& nItr, ConstSyllableItr& sItr, ConstPhonemeItr& pItr, bool skipRests) const
  1370. {
  1371. if ((*sItr)->childEnd() - 1 == pItr) {
  1372. if (false == moveToNextSyllable(nItr, sItr, skipRests)) {
  1373. return false;
  1374. }
  1375. pItr = (*sItr)->childBegin();
  1376. } else {
  1377. ++pItr;
  1378. }
  1379. return true;
  1380. }
  1381. /*!
  1382. @internal
  1383. set label data
  1384. */
  1385. void LabelMaker::setLabelData(LabelData& label, const ConstNoteItr& noteItr, const ConstSyllableItr& syllableItr, const ConstPhonemeItr& phonemeItr, int overwriteEnableFlag, int timeFlag) const
  1386. {
  1387. {
  1388. size_t j1(syllableNum / measureList.size());
  1389. label.set('j', 1, std::min<size_t>(j1, 99));
  1390. }
  1391. {
  1392. size_t j2(noteList.size() / measureList.size());
  1393. label.set('j', 2, std::min<size_t>(j2, 99));
  1394. }
  1395. label.set('j', 3, phraseList.size());
  1396. // Note
  1397. NoteLabeler* note(*noteItr);
  1398. NoteLabeler* pNote(NULL);
  1399. NoteLabeler* nNote(NULL);
  1400. {
  1401. ConstNoteItr nItr(noteItr);
  1402. if (moveToPrevNote(nItr, true)) {
  1403. pNote = *nItr;
  1404. }
  1405. }
  1406. {
  1407. ConstNoteItr nItr(noteItr);
  1408. if (moveToNextNote(nItr, true)) {
  1409. nNote = *nItr;
  1410. }
  1411. }
  1412. // Syllable
  1413. SyllableLabeler* syllable(*syllableItr);
  1414. SyllableLabeler* pSyllable(NULL);
  1415. SyllableLabeler* nSyllable(NULL);
  1416. {
  1417. ConstNoteItr nItr(noteItr);
  1418. ConstSyllableItr sItr(syllableItr);
  1419. if (moveToPrevSyllable(nItr, sItr, true)) {
  1420. pSyllable = *sItr;
  1421. }
  1422. }
  1423. {
  1424. ConstNoteItr nItr(noteItr);
  1425. ConstSyllableItr sItr(syllableItr);
  1426. if (moveToNextSyllable(nItr, sItr, true)) {
  1427. nSyllable = *sItr;
  1428. }
  1429. }
  1430. // Phoneme
  1431. PhonemeLabeler* phoneme(*phonemeItr);
  1432. PhonemeLabeler* pPhoneme(NULL);
  1433. PhonemeLabeler* nPhoneme(NULL);
  1434. PhonemeLabeler* ppPhoneme(NULL);
  1435. PhonemeLabeler* nnPhoneme(NULL);
  1436. {
  1437. ConstNoteItr nItr(noteItr);
  1438. ConstSyllableItr sItr(syllableItr);
  1439. ConstPhonemeItr pItr(phonemeItr);
  1440. if (moveToPrevPhoneme(nItr, sItr, pItr, false)) {
  1441. pPhoneme = *pItr;
  1442. if (moveToPrevPhoneme(nItr, sItr, pItr, false)) {
  1443. ppPhoneme = *pItr;
  1444. }
  1445. }
  1446. }
  1447. {
  1448. ConstNoteItr nItr(noteItr);
  1449. ConstSyllableItr sItr(syllableItr);
  1450. ConstPhonemeItr pItr(phonemeItr);
  1451. if (moveToNextPhoneme(nItr, sItr, pItr, false)) {
  1452. nPhoneme = *pItr;
  1453. if (moveToNextPhoneme(nItr, sItr, pItr, false)) {
  1454. nnPhoneme = *pItr;
  1455. }
  1456. }
  1457. }
  1458. // Note
  1459. {
  1460. NoteLabel l(label);
  1461. note->setLabel(l);
  1462. }
  1463. if (pNote) {
  1464. PrevNoteLabel l(label);
  1465. pNote->setLabel(l);
  1466. }
  1467. if (nNote) {
  1468. NextNoteLabel l(label);
  1469. nNote->setLabel(l);
  1470. }
  1471. // Syllable
  1472. {
  1473. CurrentSyllableLabel l(label);
  1474. syllable->setLabel(l);
  1475. }
  1476. if (pSyllable) {
  1477. PrevSyllableLabel l(label);
  1478. pSyllable->setLabel(l);
  1479. }
  1480. if (nSyllable) {
  1481. NextSyllableLabel l(label);
  1482. nSyllable->setLabel(l);
  1483. }
  1484. // Phoneme
  1485. {
  1486. CurrentPhonemeLabel l(label);
  1487. phoneme->setLabel(l, overwriteEnableFlag);
  1488. }
  1489. if (ppPhoneme) {
  1490. PrevPrevPhonemeLabel l(label);
  1491. ppPhoneme->setLabel(l, overwriteEnableFlag);
  1492. }
  1493. if (pPhoneme) {
  1494. PrevPhonemeLabel l(label);
  1495. pPhoneme->setLabel(l, overwriteEnableFlag);
  1496. }
  1497. if (nPhoneme) {
  1498. NextPhonemeLabel l(label);
  1499. nPhoneme->setLabel(l, overwriteEnableFlag);
  1500. }
  1501. if (nnPhoneme) {
  1502. NextNextPhonemeLabel l(label);
  1503. nnPhoneme->setLabel(l, overwriteEnableFlag);
  1504. }
  1505. }
  1506. /*!
  1507. @internal
  1508. apply stocks of score data
  1509. */
  1510. void LabelMaker::applyStocks()
  1511. {
  1512. // add measures from stocks to measure list
  1513. while (!stockMeasures.empty()) {
  1514. if (!measureList.empty()) {
  1515. if (separateWholeNoteRests && !noteList.empty() && noteList.back()->isRest()
  1516. && (0 < measureList.back()->getPosition().getCount()) && (1 <= stockMeasures.size())) { // divide rest
  1517. // separate whole note rests
  1518. NoteLabeler* lastNote(noteList.back());
  1519. INT64 dur(lastNote->getMeasureIdx().getDuration()); // start point of the last note
  1520. INT64 maxDur(measureList.back()->getDuration()); // total duration of this measure
  1521. INT64 d(maxDur - dur); // residual duration of this measure
  1522. if ((d < 0) || (std::numeric_limits<size_t>::max() < d)) {
  1523. throw std::runtime_error("LabelMaker::applyStocks() duration has invalud value");
  1524. }
  1525. size_t newDur = 0;
  1526. LabelMeasure* targetMeasure = NULL;
  1527. INT64 nextMeasureDur = stockMeasures.front()->getDuration();
  1528. if (maxDur == d) { // start from head of this measure
  1529. if (nextMeasureDur + d <= lastNote->getDuration()) { // tail of this note is equal to or over tail of next measure
  1530. // divide note at tail of this measure
  1531. newDur = d;
  1532. targetMeasure = stockMeasures.front();
  1533. }
  1534. } else { // start from middle of this measure
  1535. if (nextMeasureDur + d < lastNote->getDuration()) { // tail of this note is over tail of next measure
  1536. INT64 nextNextMeasureDur = stockMeasures[1]->getDuration();
  1537. if (nextMeasureDur + nextNextMeasureDur + d <= lastNote->getDuration()) { // tail of this note is equal to or over tail of next next measure
  1538. // divide note at tail of next measure
  1539. newDur = d + nextMeasureDur;
  1540. targetMeasure = stockMeasures[1]; // second measure
  1541. }
  1542. }
  1543. }
  1544. if (0 < newDur) {
  1545. NoteLabeler* newNote(new NoteLabeler(lastNote->getBeat(), lastNote->getDynamics(), lastNote->getKey()));
  1546. newNote->setMeasure(targetMeasure);
  1547. lastNote->moveTo(*newNote, static_cast<size_t>(newDur));
  1548. noteList.push_back(newNote);
  1549. if (inCrescendo) {
  1550. newNote->setCrescendo(crescendoList.back());
  1551. }
  1552. if (inDiminuendo) {
  1553. newNote->setDiminuendo(diminuendoList.back());
  1554. }
  1555. } else {
  1556. LabelPosition pos(measureList.back()->getPosition());
  1557. LabelPosition maxPos(measureList.back()->getMaxPosition());
  1558. if (maxPos.getTime() < pos.getTime()) {
  1559. LabelPosition diff(pos - maxPos);
  1560. diff.setCount(0);
  1561. stockMeasures.front()->addPosition(diff);
  1562. }
  1563. }
  1564. } else {
  1565. LabelPosition pos(measureList.back()->getPosition());
  1566. LabelPosition maxPos(measureList.back()->getMaxPosition());
  1567. if (maxPos.getTime() < pos.getTime()) {
  1568. LabelPosition diff(pos - maxPos);
  1569. diff.setCount(0);
  1570. stockMeasures.front()->addPosition(diff);
  1571. }
  1572. }
  1573. }
  1574. measureList.push_back(stockMeasures.front());
  1575. stockMeasures.pop_front();
  1576. }
  1577. *this << tempScore;
  1578. tempScore.clear();
  1579. }
  1580. }; // namespace sinsy