ソースを参照

cmXScore.h/c : Added colors to color map. Allow for double whole (breve) as rvalue. Changed note.rvalue from unsigned to double. Recognize 'heel' mark.

master
kevin 8年前
コミット
d7a7b3a895
2個のファイルの変更89行の追加49行の削除
  1. 83
    45
      app/cmXScore.c
  2. 6
    4
      app/cmXScore.h

+ 83
- 45
app/cmXScore.c ファイルの表示

@@ -28,10 +28,11 @@ enum
28 28
   kDynXsFl       = 0x0040,
29 29
   kEvenXsFl      = 0x0080,
30 30
   kTempoXsFl     = 0x0100,
31
-  kPedalDnXsFl   = 0x0200,
32
-  kPedalUpXsFl   = 0x0400,
33
-  kPedalUpDnXsFl = 0x0800,
34
-  kMetronomeXsFl = 0x1000  // duration holds BPM 
31
+  kHeelXsFl      = 0x0200,
32
+  kPedalDnXsFl   = 0x0400,
33
+  kPedalUpXsFl   = 0x0800,
34
+  kPedalUpDnXsFl = 0x1000,
35
+  kMetronomeXsFl = 0x2000  // duration holds BPM 
35 36
 };
36 37
 
37 38
 
@@ -41,7 +42,7 @@ typedef struct cmXsNote_str
41 42
   unsigned             pitch;    // midi pitch
42 43
   unsigned             tick;     // 
43 44
   unsigned             duration; // duration in ticks
44
-  unsigned             rvalue;   // 1/type = rythmic value (1/4=quarter note, 1/8=eighth note, ...)
45
+  double               rvalue;   // 1/rvalue = rythmic value (1/0.5 double whole 1/1 whole 1/2 half 1/4=quarter note, 1/8=eighth note, ...)
45 46
   const cmChar_t*      tvalue;   // text value
46 47
   struct cmXsNote_str* mlink;    // measure note list 
47 48
   struct cmXsNote_str* slink;    // time sorted event list
@@ -233,46 +234,57 @@ cmXsRC_t  _cmXScoreParsePitch( cmXScore_t* p, const cmXmlNode_t* nnp, unsigned*
233 234
   return rc;  
234 235
 }
235 236
 
236
-unsigned _cmXScoreParseNoteRValue( cmXScore_t* p, const cmXmlNode_t* nnp, const cmChar_t* label )
237
+cmXsRC_t  _cmXScoreParseNoteRValue( cmXScore_t* p, const cmXmlNode_t* nnp, const cmChar_t* label, double* rvalueRef )
237 238
 {
238 239
   typedef struct map_str
239 240
   {
240
-    unsigned        rvalue;
241
+    double         rvalue;
241 242
     const cmChar_t* label;
242 243
   } map_t;
243 244
 
244 245
   map_t mapV[] =
245 246
   {
246
-    {  -1, "measure" },  // whole measure rest
247
-    {   1, "whole"   },
248
-    {   2, "half"    },
249
-    {   4, "quarter" },
250
-    {   8, "eighth"  },
251
-    {  16, "16th"    },
252
-    {  32, "32nd"    },
253
-    {  64, "64th"    },
254
-    { 128, "128th"   },
255
-    {   0, ""        }
247
+    {-1.0, "measure" },  // whole measure rest
248
+    { 0.5, "breve"   },  // double whole
249
+    { 1.0, "whole"   },
250
+    { 2.0, "half"    },
251
+    { 4.0, "quarter" },
252
+    { 8.0, "eighth"  },
253
+    {16.0, "16th"    },
254
+    {32.0, "32nd"    },
255
+   { 64.0, "64th"    },
256
+   {128.0, "128th"   },
257
+   {  0.0, ""        }
256 258
   };
257 259
 
258 260
   const cmChar_t* str;
261
+  // get the XML rvalue label
259 262
   if((str = cmXmlNodeValue(nnp,label,NULL)) == NULL)
260 263
   {
261 264
     if((nnp = cmXmlSearch(nnp,"rest",NULL,0)) != NULL )
262 265
     {
263 266
       const cmXmlAttr_t* a;
264 267
       if((a = cmXmlFindAttrib(nnp,"measure")) != NULL && cmTextCmp(a->value,"yes")==0)
265
-        return -1;
268
+      {
269
+        *rvalueRef = -1;
270
+        return kOkXsRC;
271
+      }
266 272
     }
267
-    return 0;
273
+
274
+    return cmErrMsg(&p->err,kSyntaxErrorXsRC,"The 'beat-unit' metronome value is missing on line %i.",nnp->line);
268 275
   }
269 276
   
270 277
   unsigned i;
278
+  // lookup the rvalue numeric value from the mapV[] table
271 279
   for(i=0; mapV[i].rvalue!=0; ++i)
272 280
     if( cmTextCmp(mapV[i].label,str) == 0 )
273
-      return mapV[i].rvalue;
281
+    {
282
+      *rvalueRef = mapV[i].rvalue;
283
+      return kOkXsRC;
284
+    }
274 285
   
275
-  return 0;
286
+  // the rvalue label was not found
287
+  return cmErrMsg(&p->err,kSyntaxErrorXsRC,"Unknown rvalue type='%s'.",str);
276 288
 }
277 289
 
278 290
 cmXsRC_t  _cmXScoreParseColor( cmXScore_t* p, const cmXmlNode_t* nnp, cmXsNote_t* note )
@@ -288,28 +300,51 @@ cmXsRC_t  _cmXScoreParseColor( cmXScore_t* p, const cmXmlNode_t* nnp, cmXsNote_t
288 300
 
289 301
   map_t mapV[] =
290 302
   {
291
-    { kEvenXsFl,                         "#0000FF" },
292
-    { kTempoXsFl,                        "#00FF00" },
293
-    { kDynXsFl,                          "#FF0000" },
294
-    { kTempoXsFl | kEvenXsFl,            "#00FFFF" },
295
-    { kDynXsFl   | kEvenXsFl,            "#FF00FF" },    
296
-    { kDynXsFl   | kTempoXsFl,           "#FF7F00" },
297
-    { kTempoXsFl | kEvenXsFl | kDynXsFl, "#996633" },
298
-    { 0, "" }
303
+    { kEvenXsFl,                         "#0000FF" },  // blue (even)
304
+    { kTempoXsFl,                        "#00FF00" },  // green (tempo)
305
+    { kDynXsFl,                          "#FF0000" },  // red   (dynamics)
306
+    { kTempoXsFl | kEvenXsFl,            "#00FFFF" },  // green + blue (turquoise)
307
+    { kDynXsFl   | kEvenXsFl,            "#FF00FF" },  // red   + blue  
308
+    { kDynXsFl   | kEvenXsFl,            "#FF0CF7" },  // magenta (even+dyn)
309
+    { kDynXsFl   | kTempoXsFl,           "#FF7F00" },  // red   + green (brown)
310
+    { kTempoXsFl | kEvenXsFl | kDynXsFl, "#996633" },  // (purple)
311
+    { kDynXsFl,                          "#FF6A03" },  //   176 orange  (dynamics)
312
+    { kEvenXsFl,                         "#2F00E8" },  //  1001 blue (even)    
313
+    { kTempoXsFl,                        "#01CD1F" },  //  1196 green   (tempo)
314
+    { kEvenXsFl,                         "#3600E8" },  //  1627 blue (even)
315
+    { kDynXsFl | kTempoXsFl,             "#9E8F15" },  //  8827 brown (dyn + tempo)
316
+    { kEvenXsFl,                         "#2E00E6" },  //  5393 blue (even)
317
+    { kEvenXsFl,                         "#2C00DD" },  //  5895 blue (even)
318
+    { kDynXsFl,                          "#FF5B03" },  //  6498 orange (dyn)
319
+    { kDynXsFl,                          "#FF6104" },  //  6896 orange
320
+    { kEvenXsFl,                         "#2A00E6" },  //  7781 blue
321
+    { kEvenXsFl,                         "#2300DD" },  //  8300 blue (even)    
322
+    { kTempoXsFl,                        "#03CD22" },  // 10820 green (tempo)
323
+    { kEvenXsFl,                         "#3400DB" },  // 11627 blue (dyn)
324
+    { -1, "" }
299 325
   };
326
+
327
+  /*
328
+    orange  #FF6A03
329
+    magenta #FF0CF7
330
+    blue    #2F00E8
331
+    green   #01CD1F
332
+    gold    #9E8F15
333
+    green   #03CD22
334
+   */
300 335
   
301 336
   if((a = cmXmlFindAttrib(nnp, "color" )) != NULL )
302 337
   {
303 338
     unsigned i;
304
-    for(i=0; mapV[i].value != 0; ++i)
339
+    for(i=0; mapV[i].value != -1; ++i)
305 340
       if( cmTextCmp(a->value,mapV[i].label) == 0 )
306 341
       {
307 342
         note->flags += mapV[i].value;
308 343
         break;
309 344
       }
310 345
 
311
-    if( mapV[i].value == 0 )
312
-      rc = cmErrMsg(&p->err,kSyntaxErrorXsRC,"The note color '%s' was not found.",a->value);
346
+    if( mapV[i].value == -1 )
347
+      cmErrMsg(&p->err,kSyntaxErrorXsRC,"The note color '%s' was not found on line %i.",a->value,nnp->line);
313 348
   }
314 349
 
315 350
   return rc;
@@ -349,13 +384,17 @@ cmXsRC_t _cmXScoreParseNote(cmXScore_t* p, cmXsMeas_t* meas, const cmXmlNode_t*
349 384
   if( cmXmlNodeHasChild(nnp,"chord",NULL) )
350 385
     note->flags |= kChordXsFl;
351 386
 
387
+  // has 'heel' mark
388
+  if( cmXmlNodeHasChild(nnp,"notations","technical","heel",NULL) )
389
+    note->flags |= kHeelXsFl;
390
+  
352 391
   // set color coded flags
353 392
   if((rc = _cmXScoreParseColor(p, nnp, note )) != kOkXsRC )
354 393
     return rc;
355 394
   
356 395
   // get the note's rythmic value
357
-  if((note->rvalue =  _cmXScoreParseNoteRValue(p,nnp,"type")) == 0 )
358
-    return _cmXScoreMissingNode(p,nnp,"type");
396
+  if((rc =  _cmXScoreParseNoteRValue(p,nnp,"type",&note->rvalue)) != kOkXsRC )
397
+    return rc;
359 398
 
360 399
   note->tick = *tickRef;
361 400
 
@@ -365,7 +404,7 @@ cmXsRC_t _cmXScoreParseNote(cmXScore_t* p, cmXsMeas_t* meas, const cmXmlNode_t*
365 404
   return _cmXScorePushNote(p, meas, voiceId, note );
366 405
 }
367 406
 
368
-cmXsRC_t _cmXScorePushNonNote( cmXScore_t* p, cmXsMeas_t* meas, unsigned tick, unsigned duration, unsigned rvalue, const cmChar_t* tvalue, unsigned flags )
407
+cmXsRC_t _cmXScorePushNonNote( cmXScore_t* p, cmXsMeas_t* meas, unsigned tick, unsigned duration, double rvalue, const cmChar_t* tvalue, unsigned flags )
369 408
 {
370 409
   cmXsNote_t* note    = cmLhAllocZ(p->lhH,cmXsNote_t,1);
371 410
   unsigned    voiceId = 0;    // non-note's are always assigned to voiceId=0;
@@ -381,18 +420,17 @@ cmXsRC_t _cmXScorePushNonNote( cmXScore_t* p, cmXsMeas_t* meas, unsigned tick, u
381 420
 
382 421
 cmXsRC_t  _cmXScoreParseDirection(cmXScore_t* p, cmXsMeas_t* meas, const cmXmlNode_t* dnp, unsigned tick)
383 422
 {
384
-  const cmXmlNode_t* np = NULL;
385
-  const cmXmlAttr_t* a = NULL;
423
+  cmXsRC_t           rc       = kOkXsRC;
424
+  const cmXmlNode_t* np       = NULL;
425
+  const cmXmlAttr_t* a        = NULL;
386 426
   unsigned           flags    = 0;
387 427
   int                offset   = 0;
388
-  unsigned           rvalue   = 0;
428
+  double             rvalue   = 0;
389 429
   const cmChar_t*    tvalue   = NULL;
390 430
   unsigned           duration = 0;
391 431
 
392
-  
393 432
   cmXmlNodeInt(dnp, &offset, "offset", NULL );
394 433
    
395
- 
396 434
   // if this is a metronome direction
397 435
   if((np = cmXmlSearch( dnp, "metronome", NULL, 0)) != NULL )
398 436
   {
@@ -400,9 +438,9 @@ cmXsRC_t  _cmXScoreParseDirection(cmXScore_t* p, cmXsMeas_t* meas, const cmXmlNo
400 438
     if( cmXmlNodeUInt(np,&duration,"per-minute",NULL) != kOkXmlRC )
401 439
       return cmErrMsg(&p->err,kSyntaxErrorXsRC,"The 'per-minute' metronome value is missing on line %i.",np->line);
402 440
 
403
-    if((rvalue = _cmXScoreParseNoteRValue(p,np,"beat-unit")) == 0 )
404
-      return cmErrMsg(&p->err,kSyntaxErrorXsRC,"The 'beat-unit' metronome value is missing on line %i.",np->line);
405
-
441
+    if((rc = _cmXScoreParseNoteRValue(p,np,"beat-unit",&rvalue)) != kOkXsRC )
442
+      return rc;
443
+    
406 444
     flags = kMetronomeXsFl;
407 445
   }
408 446
   else
@@ -668,7 +706,7 @@ void _cmXScoreReportNote( cmRpt_t* rpt, const cmXsNote_t* note )
668 706
   P = cmIsFlag(note->flags,kPedalUpXsFl)   ? "^" : P;
669 707
   P = cmIsFlag(note->flags,kPedalUpDnXsFl) ? "X" : P;
670 708
   const cmChar_t* N = note->pitch==0 ? " " : cmMidiToSciPitch( note->pitch, NULL, 0 );
671
-  cmRptPrintf(rpt,"      %5i %5i %2i %3s %s%s%s%s%s%s%s%s%s",note->tick,note->duration,note->rvalue,N,B,R,G,D,C,e,d,t,P);
709
+  cmRptPrintf(rpt,"      %5i %5i %4.1f %3s %s%s%s%s%s%s%s%s%s",note->tick,note->duration,note->rvalue,N,B,R,G,D,C,e,d,t,P);
672 710
 
673 711
   if( cmIsFlag(note->flags,kSectionXsFl) )
674 712
     cmRptPrintf(rpt," %i",cmStringNullGuard(note->tvalue));
@@ -1033,7 +1071,7 @@ cmXsRC_t cmXScoreTest( cmCtx_t* ctx, const cmChar_t* fn )
1033 1071
   if((rc = cmXScoreInitialize( ctx, &h, fn)) != kOkXsRC )
1034 1072
     return cmErrMsg(&ctx->err,rc,"XScore alloc failed.");
1035 1073
 
1036
-  cmXScoreWriteCsv(h,"/home/kevin/temp/a0.csv");
1074
+  cmXScoreWriteCsv(h,"/Users/kevin/temp/a0.csv");
1037 1075
   cmXScoreReport(h,&ctx->rpt,true);
1038 1076
   
1039 1077
   return cmXScoreFinalize(&h);

+ 6
- 4
app/cmXScore.h ファイルの表示

@@ -27,13 +27,15 @@ extern "C" {
27 27
   //
28 28
   // 2) Replace "DoletSibelius Unknown Symbol Index" with "DoletSibelius unknownSymIdx"
29 29
   //
30
-  // 3) How to assigned dynamic markings.
31
-  // 4) Tempo syntax is inconsistent.
32
-  // 5) Heel is not being recognized
33
-  // 6) Sostenuto pedal events are not being parsed.
30
+  // 3) How to assigned dynamic markings (they are not attached to notes). (from MIDI file?)
31
+  // 4) Tempo syntax is inconsistent (only a problem in full part2 score)     
32
+  // 5) Heel is being parsed but not used. 
33
+  // 6) Sostenuto pedal events are not being parsed because they are not pedal events.
34 34
   // 7) What is a 'pedal-change' event vs. a 'pedal-stop' event.
35 35
   // 8) Verify the colors.
36 36
   // 9) Remove blank bars at end.
37
+  //10) Need to assign section targets (always default to next section)
38
+  //11) Mark tied notes for skip.
37 39
  
38 40
   cmXsRC_t cmXScoreInitialize( cmCtx_t* ctx, cmXsH_t* hp, const cmChar_t* xmlFn );
39 41
   cmXsRC_t cmXScoreFinalize( cmXsH_t* hp );

読み込み中…
キャンセル
保存