00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021 #include "fluid_ramsfont.h"
00022 #include "fluid_sys.h"
00023 #include "fluid_synth.h"
00024
00025
00026 #define SAMPLE_LOOP_MARGIN 8
00027
00028
00029 int fluid_rampreset_add_sample(fluid_rampreset_t* preset, fluid_sample_t* sample, int lokey, int hikey);
00030 int fluid_rampreset_izone_set_gen(fluid_rampreset_t* preset, fluid_sample_t* sample, int gen_type, float value);
00031 int fluid_rampreset_izone_set_loop(fluid_rampreset_t* preset, fluid_sample_t* sample, int on, float loopstart, float loopend);
00032 int fluid_rampreset_remove_izone(fluid_rampreset_t* preset, fluid_sample_t* sample);
00033 void fluid_rampreset_updatevoices(fluid_rampreset_t* preset, int gen_type, float val);
00034
00035
00036
00037
00038 fluid_sfont_t*
00039 fluid_ramsfont_create_sfont()
00040 {
00041 fluid_sfont_t* sfont;
00042 fluid_ramsfont_t* ramsfont;
00043
00044 ramsfont = new_fluid_ramsfont();
00045 if (ramsfont == NULL) {
00046 return NULL;
00047 }
00048
00049 sfont = FLUID_NEW(fluid_sfont_t);
00050 if (sfont == NULL) {
00051 FLUID_LOG(FLUID_ERR, "Out of memory");
00052 return NULL;
00053 }
00054
00055 sfont->data = ramsfont;
00056 sfont->free = fluid_ramsfont_sfont_delete;
00057 sfont->get_name = fluid_ramsfont_sfont_get_name;
00058 sfont->get_preset = fluid_ramsfont_sfont_get_preset;
00059 sfont->iteration_start = fluid_ramsfont_sfont_iteration_start;
00060 sfont->iteration_next = fluid_ramsfont_sfont_iteration_next;
00061
00062 return sfont;
00063
00064 }
00065
00066
00067
00068
00069
00070
00071 int fluid_ramsfont_sfont_delete(fluid_sfont_t* sfont)
00072 {
00073 if (delete_fluid_ramsfont(sfont->data) != 0)
00074 return -1;
00075 FLUID_FREE(sfont);
00076 return 0;
00077 }
00078
00079 char* fluid_ramsfont_sfont_get_name(fluid_sfont_t* sfont)
00080 {
00081 return fluid_ramsfont_get_name((fluid_ramsfont_t*) sfont->data);
00082 }
00083
00084 fluid_preset_t* fluid_ramsfont_sfont_get_preset(fluid_sfont_t* sfont, unsigned int bank, unsigned int prenum)
00085 {
00086 fluid_preset_t* preset;
00087 fluid_rampreset_t* rampreset;
00088
00089 rampreset = fluid_ramsfont_get_preset((fluid_ramsfont_t*) sfont->data, bank, prenum);
00090
00091 if (rampreset == NULL) {
00092 return NULL;
00093 }
00094
00095 preset = FLUID_NEW(fluid_preset_t);
00096 if (preset == NULL) {
00097 FLUID_LOG(FLUID_ERR, "Out of memory");
00098 return NULL;
00099 }
00100
00101 preset->sfont = sfont;
00102 preset->data = rampreset;
00103 preset->free = fluid_rampreset_preset_delete;
00104 preset->get_name = fluid_rampreset_preset_get_name;
00105 preset->get_banknum = fluid_rampreset_preset_get_banknum;
00106 preset->get_num = fluid_rampreset_preset_get_num;
00107 preset->noteon = fluid_rampreset_preset_noteon;
00108 preset->notify = NULL;
00109
00110 return preset;
00111 }
00112
00113 void fluid_ramsfont_sfont_iteration_start(fluid_sfont_t* sfont)
00114 {
00115 fluid_ramsfont_iteration_start((fluid_ramsfont_t*) sfont->data);
00116 }
00117
00118 int fluid_ramsfont_sfont_iteration_next(fluid_sfont_t* sfont, fluid_preset_t* preset)
00119 {
00120 preset->free = fluid_rampreset_preset_delete;
00121 preset->get_name = fluid_rampreset_preset_get_name;
00122 preset->get_banknum = fluid_rampreset_preset_get_banknum;
00123 preset->get_num = fluid_rampreset_preset_get_num;
00124 preset->noteon = fluid_rampreset_preset_noteon;
00125 preset->notify = NULL;
00126
00127 return fluid_ramsfont_iteration_next((fluid_ramsfont_t*) sfont->data, preset);
00128 }
00129
00130 int fluid_rampreset_preset_delete(fluid_preset_t* preset)
00131 {
00132 FLUID_FREE(preset);
00133
00134
00135
00136 return 0;
00137 }
00138
00139 char* fluid_rampreset_preset_get_name(fluid_preset_t* preset)
00140 {
00141 return fluid_rampreset_get_name((fluid_rampreset_t*) preset->data);
00142 }
00143
00144 int fluid_rampreset_preset_get_banknum(fluid_preset_t* preset)
00145 {
00146 return fluid_rampreset_get_banknum((fluid_rampreset_t*) preset->data);
00147 }
00148
00149 int fluid_rampreset_preset_get_num(fluid_preset_t* preset)
00150 {
00151 return fluid_rampreset_get_num((fluid_rampreset_t*) preset->data);
00152 }
00153
00154 int fluid_rampreset_preset_noteon(fluid_preset_t* preset, fluid_synth_t* synth, int chan, int key, int vel)
00155 {
00156 return fluid_rampreset_noteon((fluid_rampreset_t*) preset->data, synth, chan, key, vel);
00157 }
00158
00159
00160
00161
00162
00163
00164
00165
00166
00167
00168
00169
00170 fluid_ramsfont_t* new_fluid_ramsfont()
00171 {
00172 fluid_ramsfont_t* sfont;
00173
00174 sfont = FLUID_NEW(fluid_ramsfont_t);
00175 if (sfont == NULL) {
00176 FLUID_LOG(FLUID_ERR, "Out of memory");
00177 return NULL;
00178 }
00179
00180 sfont->name[0] = 0;
00181 sfont->sample = NULL;
00182 sfont->preset = NULL;
00183
00184 return sfont;
00185 }
00186
00187
00188
00189
00190 int delete_fluid_ramsfont(fluid_ramsfont_t* sfont)
00191 {
00192 fluid_list_t *list;
00193 fluid_rampreset_t* preset;
00194
00195
00196 for (list = sfont->sample; list; list = fluid_list_next(list)) {
00197 fluid_sample_t* sam = (fluid_sample_t*) fluid_list_get(list);
00198 if (fluid_sample_refcount(sam) != 0) {
00199 return -1;
00200 }
00201 }
00202
00203 for (list = sfont->sample; list; list = fluid_list_next(list)) {
00204
00205 fluid_sample_t* sam = (fluid_sample_t*)fluid_list_get(list);
00206 delete_fluid_ramsample(sam);
00207 }
00208
00209 if (sfont->sample) {
00210 delete_fluid_list(sfont->sample);
00211 }
00212
00213 preset = sfont->preset;
00214 while (preset != NULL) {
00215 sfont->preset = preset->next;
00216 delete_fluid_rampreset(preset);
00217 preset = sfont->preset;
00218 }
00219
00220 FLUID_FREE(sfont);
00221 return FLUID_OK;
00222 }
00223
00224
00225
00226
00227 char* fluid_ramsfont_get_name(fluid_ramsfont_t* sfont)
00228 {
00229 return sfont->name;
00230 }
00231
00232
00233
00234
00235 int
00236 fluid_ramsfont_set_name(fluid_ramsfont_t* sfont, char * name)
00237 {
00238 FLUID_MEMCPY(sfont->name, name, 20);
00239 return FLUID_OK;
00240 }
00241
00242
00243
00244
00245
00246
00247 int fluid_ramsfont_add_preset(fluid_ramsfont_t* sfont, fluid_rampreset_t* preset)
00248 {
00249 fluid_rampreset_t *cur, *prev;
00250 if (sfont->preset == NULL) {
00251 preset->next = NULL;
00252 sfont->preset = preset;
00253 } else {
00254
00255 cur = sfont->preset;
00256 prev = NULL;
00257 while (cur != NULL) {
00258 if ((preset->bank < cur->bank)
00259 || ((preset->bank == cur->bank) && (preset->num < cur->num))) {
00260 if (prev == NULL) {
00261 preset->next = cur;
00262 sfont->preset = preset;
00263 } else {
00264 preset->next = cur;
00265 prev->next = preset;
00266 }
00267 return FLUID_OK;
00268 }
00269 prev = cur;
00270 cur = cur->next;
00271 }
00272 preset->next = NULL;
00273 prev->next = preset;
00274 }
00275 return FLUID_OK;
00276 }
00277
00278
00279
00280
00281 int fluid_ramsfont_add_izone(fluid_ramsfont_t* sfont,
00282 unsigned int bank, unsigned int num, fluid_sample_t* sample,
00283 int lokey, int hikey)
00284 {
00285
00286
00287
00288
00289 int err;
00290
00291 fluid_rampreset_t* preset = fluid_ramsfont_get_preset(sfont, bank, num);
00292 if (preset == NULL) {
00293
00294 preset = new_fluid_rampreset(sfont);
00295 if (preset == NULL) {
00296 return FLUID_FAILED;
00297 }
00298
00299 preset->bank = bank;
00300 preset->num = num;
00301
00302 err = fluid_rampreset_add_sample(preset, sample, lokey, hikey);
00303 if (err != FLUID_OK) {
00304 return FLUID_FAILED;
00305 }
00306
00307
00308 fluid_ramsfont_add_preset(sfont, preset);
00309
00310 } else {
00311
00312
00313 err = fluid_rampreset_add_sample(preset, sample, lokey, hikey);
00314 if (err != FLUID_OK) {
00315 return FLUID_FAILED;
00316 }
00317 }
00318
00319 sfont->sample = fluid_list_append(sfont->sample, sample);
00320 return FLUID_OK;
00321 }
00322
00323 int fluid_ramsfont_remove_izone(fluid_ramsfont_t* sfont,
00324 unsigned int bank, unsigned int num, fluid_sample_t* sample) {
00325 int err;
00326 fluid_rampreset_t* preset = fluid_ramsfont_get_preset(sfont, bank, num);
00327 if (preset == NULL) {
00328 return FLUID_FAILED;
00329 }
00330
00331
00332
00333 err = fluid_rampreset_remove_izone(preset, sample);
00334 if (err != FLUID_OK)
00335 return err;
00336
00337
00338 sfont->sample = fluid_list_remove(sfont->sample, sample);
00339
00340 return FLUID_OK;
00341 }
00342
00343
00344
00345 int fluid_ramsfont_izone_set_gen(fluid_ramsfont_t* sfont,
00346 unsigned int bank, unsigned int num, fluid_sample_t* sample,
00347 int gen_type, float value) {
00348
00349 fluid_rampreset_t* preset = fluid_ramsfont_get_preset(sfont, bank, num);
00350 if (preset == NULL) {
00351 return FLUID_FAILED;
00352 }
00353
00354 return fluid_rampreset_izone_set_gen(preset, sample, gen_type, value);
00355 }
00356
00357
00358 int fluid_ramsfont_izone_set_loop(fluid_ramsfont_t* sfont,
00359 unsigned int bank, unsigned int num, fluid_sample_t* sample,
00360 int on, float loopstart, float loopend) {
00361 fluid_rampreset_t* preset = fluid_ramsfont_get_preset(sfont, bank, num);
00362 if (preset == NULL) {
00363 return FLUID_FAILED;
00364 }
00365
00366 return fluid_rampreset_izone_set_loop(preset, sample, on, loopstart, loopend);
00367 }
00368
00369
00370
00371
00372 fluid_rampreset_t* fluid_ramsfont_get_preset(fluid_ramsfont_t* sfont, unsigned int bank, unsigned int num)
00373 {
00374 fluid_rampreset_t* preset = sfont->preset;
00375 while (preset != NULL) {
00376 if ((preset->bank == bank) && ((preset->num == num))) {
00377 return preset;
00378 }
00379 preset = preset->next;
00380 }
00381 return NULL;
00382 }
00383
00384
00385
00386
00387 void fluid_ramsfont_iteration_start(fluid_ramsfont_t* sfont)
00388 {
00389 sfont->iter_cur = sfont->preset;
00390 }
00391
00392
00393
00394
00395 int fluid_ramsfont_iteration_next(fluid_ramsfont_t* sfont, fluid_preset_t* preset)
00396 {
00397 if (sfont->iter_cur == NULL) {
00398 return 0;
00399 }
00400
00401 preset->data = (void*) sfont->iter_cur;
00402 sfont->iter_cur = fluid_rampreset_next(sfont->iter_cur);
00403 return 1;
00404 }
00405
00406
00407
00408
00409
00410
00411 typedef struct _fluid_rampreset_voice_t fluid_rampreset_voice_t;
00412 struct _fluid_rampreset_voice_t {
00413 fluid_voice_t *voice;
00414 unsigned int voiceID;
00415 };
00416
00417
00418
00419
00420 fluid_rampreset_t*
00421 new_fluid_rampreset(fluid_ramsfont_t* sfont)
00422 {
00423 fluid_rampreset_t* preset = FLUID_NEW(fluid_rampreset_t);
00424 if (preset == NULL) {
00425 FLUID_LOG(FLUID_ERR, "Out of memory");
00426 return NULL;
00427 }
00428 preset->next = NULL;
00429 preset->sfont = sfont;
00430 preset->name[0] = 0;
00431 preset->bank = 0;
00432 preset->num = 0;
00433 preset->global_zone = NULL;
00434 preset->zone = NULL;
00435 preset->presetvoices = NULL;
00436 return preset;
00437 }
00438
00439
00440
00441
00442 int
00443 delete_fluid_rampreset(fluid_rampreset_t* preset)
00444 {
00445 int err = FLUID_OK;
00446 fluid_preset_zone_t* zone;
00447 fluid_rampreset_voice_t *data;
00448
00449 if (preset->global_zone != NULL) {
00450 if (delete_fluid_preset_zone(preset->global_zone) != FLUID_OK) {
00451 err = FLUID_FAILED;
00452 }
00453 preset->global_zone = NULL;
00454 }
00455 zone = preset->zone;
00456 while (zone != NULL) {
00457 preset->zone = zone->next;
00458 if (delete_fluid_preset_zone(zone) != FLUID_OK) {
00459 err = FLUID_FAILED;
00460 }
00461 zone = preset->zone;
00462 }
00463
00464 if (preset->presetvoices != NULL) {
00465 fluid_list_t *tmp = preset->presetvoices, *next;
00466 while (tmp) {
00467 data = (fluid_rampreset_voice_t *)(tmp->data);
00468 FLUID_FREE(data);
00469
00470 next = tmp->next;
00471 FLUID_FREE(tmp);
00472 tmp = next;
00473 }
00474 }
00475 preset->presetvoices = NULL;
00476
00477 FLUID_FREE(preset);
00478 return err;
00479 }
00480
00481 int
00482 fluid_rampreset_get_banknum(fluid_rampreset_t* preset)
00483 {
00484 return preset->bank;
00485 }
00486
00487 int
00488 fluid_rampreset_get_num(fluid_rampreset_t* preset)
00489 {
00490 return preset->num;
00491 }
00492
00493 char*
00494 fluid_rampreset_get_name(fluid_rampreset_t* preset)
00495 {
00496 return preset->name;
00497 }
00498
00499
00500
00501
00502 fluid_rampreset_t*
00503 fluid_rampreset_next(fluid_rampreset_t* preset)
00504 {
00505 return preset->next;
00506 }
00507
00508
00509
00510
00511
00512 int
00513 fluid_rampreset_add_zone(fluid_rampreset_t* preset, fluid_preset_zone_t* zone)
00514 {
00515 if (preset->zone == NULL) {
00516 zone->next = NULL;
00517 preset->zone = zone;
00518 } else {
00519 zone->next = preset->zone;
00520 preset->zone = zone;
00521 }
00522 return FLUID_OK;
00523 }
00524
00525
00526
00527
00528
00529 int fluid_rampreset_add_sample(fluid_rampreset_t* preset, fluid_sample_t* sample, int lokey, int hikey)
00530 {
00531
00532
00533
00534 if (preset->zone == NULL) {
00535 fluid_preset_zone_t* zone;
00536 zone = new_fluid_preset_zone("");
00537 if (zone == NULL) {
00538 return FLUID_FAILED;
00539 }
00540
00541
00542 zone->inst = (fluid_inst_t*) new_fluid_inst();
00543 if (zone->inst == NULL) {
00544 delete_fluid_preset_zone(zone);
00545 return FLUID_FAILED;
00546 }
00547
00548 fluid_rampreset_add_zone(preset, zone);
00549 }
00550
00551
00552 {
00553 fluid_inst_t* inst = fluid_preset_zone_get_inst(preset->zone);
00554 fluid_inst_zone_t* izone = new_fluid_inst_zone("");
00555 if (izone == NULL) {
00556 return FLUID_FAILED;
00557 }
00558
00559 if (fluid_inst_add_zone(inst, izone) != FLUID_OK) {
00560 delete_fluid_inst_zone(izone);
00561 return FLUID_FAILED;
00562 }
00563
00564 izone->sample = sample;
00565 izone->keylo = lokey;
00566 izone->keyhi = hikey;
00567
00568
00569 FLUID_MEMCPY(preset->name, sample->name, 20);
00570 }
00571
00572 return FLUID_OK;
00573 }
00574
00575 fluid_inst_zone_t* fluid_rampreset_izoneforsample(fluid_rampreset_t* preset, fluid_sample_t* sample)
00576 {
00577 fluid_inst_t* inst;
00578 fluid_inst_zone_t* izone;
00579
00580 if (preset->zone == NULL) return NULL;
00581
00582 inst = fluid_preset_zone_get_inst(preset->zone);
00583 izone = inst->zone;
00584 while (izone) {
00585 if (izone->sample == sample)
00586 return izone;
00587 izone = izone->next;
00588 }
00589 return NULL;
00590 }
00591
00592 int fluid_rampreset_izone_set_loop(fluid_rampreset_t* preset, fluid_sample_t* sample,
00593 int on, float loopstart, float loopend) {
00594 fluid_inst_zone_t* izone = fluid_rampreset_izoneforsample(preset, sample);
00595 short coarse, fine;
00596
00597 if (izone == NULL)
00598 return FLUID_FAILED;
00599
00600 if (!on) {
00601 izone->gen[GEN_SAMPLEMODE].flags = GEN_SET;
00602 izone->gen[GEN_SAMPLEMODE].val = FLUID_UNLOOPED;
00603 fluid_rampreset_updatevoices(preset, GEN_SAMPLEMODE, FLUID_UNLOOPED);
00604 return FLUID_OK;
00605 }
00606
00607
00608
00609
00610 if (loopstart > 32767. || loopstart < -32767.) {
00611 coarse = (short)(loopstart/32768.);
00612 fine = (short)(loopstart - (float)(coarse)*32768.);
00613 } else {
00614 coarse = 0;
00615 fine = (short)loopstart;
00616 }
00617 izone->gen[GEN_STARTLOOPADDROFS].flags = GEN_SET;
00618 izone->gen[GEN_STARTLOOPADDROFS].val = fine;
00619 fluid_rampreset_updatevoices(preset, GEN_STARTLOOPADDROFS, fine);
00620 if (coarse) {
00621 izone->gen[GEN_STARTLOOPADDRCOARSEOFS].flags = GEN_SET;
00622 izone->gen[GEN_STARTLOOPADDRCOARSEOFS].val = coarse;
00623 } else {
00624 izone->gen[GEN_STARTLOOPADDRCOARSEOFS].flags = GEN_UNUSED;
00625 }
00626 fluid_rampreset_updatevoices(preset, GEN_STARTLOOPADDRCOARSEOFS, coarse);
00627
00628
00629 if (loopend > 32767. || loopend < -32767.) {
00630 coarse = (short)(loopend/32768.);
00631 fine = (short)(loopend - (float)(coarse)*32768.);
00632 } else {
00633 coarse = 0;
00634 fine = (short)loopend;
00635 }
00636 izone->gen[GEN_ENDLOOPADDROFS].flags = GEN_SET;
00637 izone->gen[GEN_ENDLOOPADDROFS].val = fine;
00638 fluid_rampreset_updatevoices(preset, GEN_ENDLOOPADDROFS, fine);
00639 if (coarse) {
00640 izone->gen[GEN_ENDLOOPADDRCOARSEOFS].flags = GEN_SET;
00641 izone->gen[GEN_ENDLOOPADDRCOARSEOFS].val = coarse;
00642 } else {
00643 izone->gen[GEN_ENDLOOPADDRCOARSEOFS].flags = GEN_UNUSED;
00644 }
00645 fluid_rampreset_updatevoices(preset, GEN_ENDLOOPADDRCOARSEOFS, coarse);
00646
00647 izone->gen[GEN_SAMPLEMODE].flags = GEN_SET;
00648 izone->gen[GEN_SAMPLEMODE].val = FLUID_LOOP_DURING_RELEASE;
00649 fluid_rampreset_updatevoices(preset, GEN_SAMPLEMODE, FLUID_LOOP_DURING_RELEASE);
00650
00651
00652
00653
00654
00655
00656 return FLUID_OK;
00657 }
00658
00659 int fluid_rampreset_izone_set_gen(fluid_rampreset_t* preset, fluid_sample_t* sample,
00660 int gen_type, float value) {
00661 fluid_inst_zone_t* izone = fluid_rampreset_izoneforsample(preset, sample);
00662 if (izone == NULL)
00663 return FLUID_FAILED;
00664
00665 izone->gen[gen_type].flags = GEN_SET;
00666 izone->gen[gen_type].val = value;
00667
00668 fluid_rampreset_updatevoices(preset, gen_type, value);
00669
00670 return FLUID_OK;
00671 }
00672
00673 int fluid_rampreset_remove_izone(fluid_rampreset_t* preset, fluid_sample_t* sample) {
00674 fluid_inst_t* inst;
00675 fluid_inst_zone_t* izone, * prev;
00676 int found = 0;
00677
00678 if (preset->zone == NULL) return FLUID_FAILED;
00679 inst = fluid_preset_zone_get_inst(preset->zone);
00680 izone = inst->zone;
00681 prev = NULL;
00682 while (izone && !found) {
00683 if (izone->sample == sample) {
00684 if (prev == NULL) {
00685 inst->zone = izone->next;
00686 } else {
00687 prev->next = izone->next;
00688 }
00689 izone->next = NULL;
00690 delete_fluid_inst_zone(izone);
00691 found = 1;
00692 } else {
00693 prev = izone;
00694 izone = izone->next;
00695 }
00696 }
00697 if (!found)
00698 return FLUID_FAILED;
00699
00700
00701
00702 {
00703 fluid_list_t *tmp = preset->presetvoices;
00704 while (tmp) {
00705 fluid_rampreset_voice_t *presetvoice = (fluid_rampreset_voice_t *)(tmp->data);
00706 fluid_voice_t *voice = presetvoice->voice;
00707 if (fluid_voice_is_playing(voice) && (fluid_voice_get_id(voice) == presetvoice->voiceID)) {
00708
00709 if (voice->sample == sample) {
00710
00711
00712 fluid_voice_off(voice);
00713 }
00714 }
00715 tmp = tmp->next;
00716 }
00717 }
00718 return FLUID_OK;
00719 }
00720
00721
00722
00723
00724 int
00725 fluid_rampreset_remembervoice(fluid_rampreset_t* preset, fluid_voice_t* voice) {
00726
00727 fluid_rampreset_voice_t *presetvoice = FLUID_NEW(fluid_rampreset_voice_t);
00728 if (presetvoice == NULL) {
00729 FLUID_LOG(FLUID_ERR, "Out of memory");
00730 return FLUID_FAILED;
00731 }
00732
00733 presetvoice->voice = voice;
00734 presetvoice->voiceID = fluid_voice_get_id(voice);
00735
00736 preset->presetvoices = fluid_list_append(preset->presetvoices, (void *)presetvoice);
00737 if (preset->presetvoices == NULL) {
00738 FLUID_FREE(presetvoice);
00739 FLUID_LOG(FLUID_ERR, "Out of memory");
00740 return FLUID_FAILED;
00741 }
00742 return FLUID_OK;
00743 }
00744
00745
00746
00747
00748 void
00749 fluid_rampreset_updatevoices(fluid_rampreset_t* preset, int gen_type, float val) {
00750 fluid_list_t *tmp = preset->presetvoices, *prev = NULL, *next;
00751
00752
00753
00754
00755 while (tmp) {
00756 fluid_rampreset_voice_t *presetvoice = (fluid_rampreset_voice_t *)(tmp->data);
00757 fluid_voice_t *voice = presetvoice->voice;
00758 if (!fluid_voice_is_playing(voice) || (fluid_voice_get_id(voice) != presetvoice->voiceID)) {
00759
00760 FLUID_FREE(presetvoice);
00761
00762
00763 next = tmp->next;
00764 FLUID_FREE(tmp);
00765 if (prev) {
00766 prev->next = next;
00767 } else {
00768 preset->presetvoices = next;
00769 }
00770 tmp = next;
00771
00772 } else {
00773
00774
00775 fluid_voice_gen_set(voice, gen_type, val);
00776 fluid_voice_update_param(voice, gen_type);
00777
00778
00779 prev = tmp;
00780 tmp = tmp->next;
00781 }
00782 }
00783 }
00784
00785
00786
00787
00788
00789 int
00790 fluid_rampreset_noteon(fluid_rampreset_t* preset, fluid_synth_t* synth, int chan, int key, int vel)
00791 {
00792 fluid_preset_zone_t *preset_zone;
00793 fluid_inst_t* inst;
00794 fluid_inst_zone_t *inst_zone, *global_inst_zone, *z;
00795 fluid_sample_t* sample;
00796 fluid_voice_t* voice;
00797 fluid_mod_t * mod;
00798 fluid_mod_t * mod_list[FLUID_NUM_MOD];
00799 int mod_list_count;
00800 int i;
00801
00802
00803 preset_zone = preset->zone;
00804 while (preset_zone != NULL) {
00805
00806
00807
00808 if (fluid_preset_zone_inside_range(preset_zone, key, vel)) {
00809
00810 inst = fluid_preset_zone_get_inst(preset_zone);
00811 global_inst_zone = fluid_inst_get_global_zone(inst);
00812
00813
00814 inst_zone = fluid_inst_get_zone(inst);
00815 while (inst_zone != NULL) {
00816
00817
00818 sample = fluid_inst_zone_get_sample(inst_zone);
00819 if (fluid_sample_in_rom(sample) || (sample == NULL)) {
00820 inst_zone = fluid_inst_zone_next(inst_zone);
00821 continue;
00822 }
00823
00824
00825
00826
00827 if (fluid_inst_zone_inside_range(inst_zone, key, vel) && (sample != NULL)) {
00828
00829
00830
00831
00832 voice = fluid_synth_alloc_voice(synth, sample, chan, key, vel);
00833 if (voice == NULL) {
00834 return FLUID_FAILED;
00835 }
00836
00837 if (fluid_rampreset_remembervoice(preset, voice) != FLUID_OK) {
00838 return FLUID_FAILED;
00839 }
00840
00841 z = inst_zone;
00842
00843
00844
00845 for (i = 0; i < GEN_LAST; i++) {
00846
00847
00848
00849
00850
00851
00852
00853 if (inst_zone->gen[i].flags){
00854 fluid_voice_gen_set(voice, i, inst_zone->gen[i].val);
00855
00856 } else if (global_inst_zone != NULL && global_inst_zone->gen[i].flags){
00857 fluid_voice_gen_set(voice, i, global_inst_zone->gen[i].val);
00858
00859 } else {
00860
00861
00862
00863 };
00864
00865 };
00866
00867
00868
00869
00870 mod_list_count = 0;
00871
00872 if (global_inst_zone){
00873 mod = global_inst_zone->mod;
00874 while (mod){
00875 mod_list[mod_list_count++] = mod;
00876 mod = mod->next;
00877 };
00878 };
00879
00880
00881
00882
00883
00884 mod = inst_zone->mod;
00885
00886 while (mod){
00887
00888
00889
00890
00891
00892
00893 for (i = 0; i < mod_list_count; i++){
00894 if (fluid_mod_test_identity(mod,mod_list[i])){
00895 mod_list[i] = NULL;
00896 };
00897 };
00898
00899
00900 mod_list[mod_list_count++] = mod;
00901 mod = mod->next;
00902 };
00903
00904
00905 for (i = 0; i < mod_list_count; i++){
00906
00907 mod = mod_list[i];
00908
00909 if (mod != NULL){
00910
00911
00912
00913 fluid_voice_add_mod(voice, mod, FLUID_VOICE_OVERWRITE);
00914 };
00915 };
00916
00917
00918
00919 for (i = 0; i < GEN_LAST; i++) {
00920
00921
00922
00923 if ((i != GEN_STARTADDROFS)
00924 && (i != GEN_ENDADDROFS)
00925 && (i != GEN_STARTLOOPADDROFS)
00926 && (i != GEN_ENDLOOPADDROFS)
00927 && (i != GEN_STARTADDRCOARSEOFS)
00928 && (i != GEN_ENDADDRCOARSEOFS)
00929 && (i != GEN_STARTLOOPADDRCOARSEOFS)
00930 && (i != GEN_KEYNUM)
00931 && (i != GEN_VELOCITY)
00932 && (i != GEN_ENDLOOPADDRCOARSEOFS)
00933 && (i != GEN_SAMPLEMODE)
00934 && (i != GEN_EXCLUSIVECLASS)
00935 && (i != GEN_OVERRIDEROOTKEY)) {
00936
00937
00938
00939
00940
00941
00942 if (preset_zone->gen[i].flags){
00943 fluid_voice_gen_incr(voice, i, preset_zone->gen[i].val);
00944 } else {
00945
00946
00947
00948 };
00949 };
00950 };
00951
00952
00953
00954
00955 mod_list_count = 0;
00956
00957
00958
00959
00960
00961 mod = preset_zone->mod;
00962 while (mod){
00963 for (i = 0; i < mod_list_count; i++){
00964 if (fluid_mod_test_identity(mod,mod_list[i])){
00965 mod_list[i] = NULL;
00966 };
00967 };
00968
00969
00970 mod_list[mod_list_count++] = mod;
00971 mod = mod->next;
00972 };
00973
00974
00975 for (i = 0; i < mod_list_count; i++){
00976 mod = mod_list[i];
00977 if ((mod != NULL) && (mod->amount != 0)) {
00978
00979
00980
00981
00982 fluid_voice_add_mod(voice, mod, FLUID_VOICE_ADD);
00983 };
00984 };
00985
00986
00987 fluid_synth_start_voice(synth, voice);
00988
00989
00990
00991
00992
00993
00994
00995 }
00996
00997 inst_zone = fluid_inst_zone_next(inst_zone);
00998 }
00999 }
01000 preset_zone = fluid_preset_zone_next(preset_zone);
01001 }
01002
01003 return FLUID_OK;
01004 }
01005
01006
01007
01008
01009
01010
01011
01012
01013
01014
01015
01016
01017
01018 int
01019 fluid_sample_set_name(fluid_sample_t* sample, char * name)
01020 {
01021 FLUID_MEMCPY(sample->name, name, 20);
01022 return FLUID_OK;
01023 }
01024
01025
01026
01027
01028 int
01029 fluid_sample_set_sound_data(fluid_sample_t* sample, short *data, unsigned int nbframes, short copy_data, int rootkey)
01030 {
01031
01032
01033 unsigned int storedNbFrames;
01034
01035
01036 if (sample->data != NULL) {
01037 FLUID_FREE(sample->data);
01038 }
01039
01040 if (copy_data) {
01041
01042
01043 storedNbFrames = nbframes;
01044 if (storedNbFrames < 48) storedNbFrames = 48;
01045
01046 sample->data = FLUID_MALLOC(storedNbFrames*2 + 4*SAMPLE_LOOP_MARGIN);
01047 if (sample->data == NULL) {
01048 FLUID_LOG(FLUID_ERR, "Out of memory");
01049 return FLUID_FAILED;
01050 }
01051 FLUID_MEMSET(sample->data, 0, storedNbFrames*2 + 4*SAMPLE_LOOP_MARGIN);
01052 FLUID_MEMCPY((char*)(sample->data) + 2*SAMPLE_LOOP_MARGIN, data, nbframes*2);
01053
01054 #if 0
01055
01056 FLUID_MEMCPY((char*)(sample->data) + 2*SAMPLE_LOOP_MARGIN + storedNbFrames*2, (char*)data, 2*SAMPLE_LOOP_MARGIN);
01057 FLUID_MEMCPY((char*)(sample->data), (char*)data + nbframes*2 - 2*SAMPLE_LOOP_MARGIN, 2*SAMPLE_LOOP_MARGIN);
01058 #endif
01059
01060
01061
01062 sample->start = SAMPLE_LOOP_MARGIN;
01063 sample->end = SAMPLE_LOOP_MARGIN + storedNbFrames;
01064 } else {
01065
01066 sample->data = data;
01067 sample->start = 0;
01068 sample->end = nbframes;
01069 }
01070
01071
01072 sample->loopstart = sample->start;
01073 sample->loopend = sample->end;
01074
01075 sample->samplerate = 44100;
01076 sample->origpitch = rootkey;
01077 sample->pitchadj = 0;
01078 sample->sampletype = FLUID_SAMPLETYPE_MONO;
01079 sample->valid = 1;
01080
01081 return FLUID_OK;
01082 }
01083
01084
01085
01086
01087 fluid_sample_t*
01088 new_fluid_ramsample()
01089 {
01090
01091 fluid_sample_t* sample = NULL;
01092
01093 sample = FLUID_NEW(fluid_sample_t);
01094 if (sample == NULL) {
01095 FLUID_LOG(FLUID_ERR, "Out of memory");
01096 return NULL;
01097 }
01098
01099 memset(sample, 0, sizeof(fluid_sample_t));
01100
01101 return sample;
01102 }
01103
01104
01105
01106
01107 int
01108 delete_fluid_ramsample(fluid_sample_t* sample)
01109 {
01110
01111 if (sample->data != NULL) {
01112 FLUID_FREE(sample->data);
01113 }
01114 sample->data = NULL;
01115 FLUID_FREE(sample);
01116 return FLUID_OK;
01117 }