feat: collect portable project media with transactional cleanup and qualify composition workflows
This commit is contained in:
parent
d676d74a11
commit
b0cfa79131
15 changed files with 225 additions and 10 deletions
|
|
@ -1396,6 +1396,8 @@ int main(int argc, char **argv)
|
|||
CHECK(window.import_audio(sample)==XTC_OK);CHECK(s->normalize_audio(.25f)==XTC_OK);
|
||||
xtc_clip_info normalized{};xtc_project_find_clip(s->project(),s->selected_clip(),&normalized);CHECK(normalized.gain>0 && normalized.gain<=4);
|
||||
CHECK(window.undo()==XTC_OK);
|
||||
std::string folder="/tmp/xtc-gui-collect-"+std::to_string(getpid());CHECK(window.collect_project(folder.c_str())==XTC_OK);
|
||||
CHECK(access((folder+"/project.xtc").c_str(),F_OK)==0);unlink((folder+"/project.xtc").c_str());unlink((folder+"/media-000.wav").c_str());rmdir(folder.c_str());
|
||||
window.do_callback();
|
||||
}
|
||||
if (failures != 0) return 1;
|
||||
|
|
|
|||
|
|
@ -1,3 +1,4 @@
|
|||
#define _XOPEN_SOURCE 700
|
||||
/* GNU ld allocation interposition: fail preparation at every allocation and
|
||||
* reject host allocation/reclamation inside processing. No production hooks. */
|
||||
#include "xtc/xtc_realtime.h"
|
||||
|
|
@ -5,6 +6,7 @@
|
|||
#include "xtc/xtc_control.h"
|
||||
#include "xtc/xtc_plugin.h"
|
||||
#include "xtc/xtc_editing.h"
|
||||
#include "xtc/xtc_audio.h"
|
||||
#include <assert.h>
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
|
|
@ -221,8 +223,54 @@ static void modern_edit_failures(void)
|
|||
}
|
||||
xtc_clipboard_destroy(board);xtc_mix_snapshot_destroy(mix);xtc_project_destroy(p);
|
||||
}
|
||||
static void composition_failures(void)
|
||||
{
|
||||
xtc_project *p=NULL;uint64_t t,ids[2],note,audio;char sample[4096],root[]="/tmp/xtc-compose-fail-XXXXXX";
|
||||
int operation,failure;xtc_midi_transform human={0};int intervals[2]={4,7};
|
||||
assert(mkdtemp(root));assert(getcwd(sample,sizeof(sample)));assert(strlen(sample)+40<sizeof(sample));strcat(sample,"/examples/projects/original-pluck.wav");
|
||||
assert(xtc_project_create(&p)==XTC_OK && xtc_project_add_track(p,"Track",&t)==XTC_OK);
|
||||
assert(xtc_project_add_midi_clip(p,t,0,1920,&ids[0])==XTC_OK && xtc_project_add_midi_clip(p,t,3840,1920,&ids[1])==XTC_OK);
|
||||
assert(xtc_project_add_note(p,ids[0],480,240,60,100,0,¬e)==XTC_OK && xtc_project_add_note(p,ids[1],480,240,64,100,0,¬e)==XTC_OK);
|
||||
assert(xtc_project_import_audio(p,t,sample,7680,&audio)==XTC_OK);
|
||||
fail_after=0;assert(xtc_project_set_marker(p,3840,"Section")==XTC_OK);fail_after=-1;
|
||||
human.type=XTC_MIDI_TRANSFORM_HUMANIZE;human.seed=42;human.timing_variation=12;human.velocity_variation=8;
|
||||
for(operation=0;operation<9;++operation) {
|
||||
int succeeded=0;
|
||||
for(failure=0;failure<128;++failure) {
|
||||
xtc_project *copy=NULL;xtc_clip_info c;uint64_t output=999;xtc_result r;size_t tracks,clips,notes;
|
||||
char dest[512],file[512];snprintf(dest,sizeof(dest),"%s/copy-%d-%d",root,operation,failure);
|
||||
assert(xtc_project_clone(p,©)==XTC_OK);fail_after=failure;
|
||||
switch(operation) {
|
||||
case 0:r=xtc_project_ripple_time(copy,1920,960,0);break;
|
||||
case 1:r=xtc_project_duplicate_track(copy,t,"Copy",&output);break;
|
||||
case 2:r=xtc_project_split_midi(copy,ids[0],960,&output);break;
|
||||
case 3:r=xtc_project_merge_midi(copy,ids,2,&output);break;
|
||||
case 4:r=xtc_project_transform_midi(copy,ids,2,&human);break;
|
||||
case 5:r=xtc_project_chordify(copy,ids,2,intervals,2);break;
|
||||
case 6:r=xtc_project_arpeggiate(copy,ids,2,120,50,0);break;
|
||||
case 7:r=xtc_project_normalize_audio(copy,&audio,1,.25f);break;
|
||||
default:r=xtc_project_collect(copy,dest);break;
|
||||
}
|
||||
fail_after=-1;
|
||||
if(r==XTC_OK)succeeded=1;
|
||||
else {
|
||||
assert((r==XTC_ERR_OUT_OF_MEMORY || (operation==8 && r==XTC_ERR_IO)) && output==999);
|
||||
assert(xtc_project_get_counts(copy,&tracks,&clips)==XTC_OK && tracks==1 && clips==3);
|
||||
assert(xtc_project_note_count(copy,¬es)==XTC_OK && notes==2);
|
||||
assert(xtc_project_find_clip(copy,ids[1],&c)==XTC_OK && c.start_tick==3840);
|
||||
assert(access(dest,F_OK)!=0);
|
||||
{uint64_t probe;assert(xtc_project_duplicate_clip(copy,ids[0],t,9600,&probe)==XTC_OK && probe==3);}
|
||||
}
|
||||
if(operation==8 && succeeded){snprintf(file,sizeof(file),"%s/copy-%d-%d/project.xtc",root,operation,failure);assert(unlink(file)==0);snprintf(file,sizeof(file),"%s/copy-%d-%d/media-000.wav",root,operation,failure);assert(unlink(file)==0 && rmdir(dest)==0);}
|
||||
xtc_project_destroy(copy);if(succeeded)break;
|
||||
}
|
||||
assert(succeeded);
|
||||
}
|
||||
xtc_project_destroy(p);assert(rmdir(root)==0);
|
||||
}
|
||||
int main(void)
|
||||
{
|
||||
composition_failures();
|
||||
modern_edit_failures();
|
||||
builtin_failures();
|
||||
graph_limits();
|
||||
|
|
|
|||
|
|
@ -8,6 +8,7 @@
|
|||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <unistd.h>
|
||||
#include <sys/stat.h>
|
||||
#include <math.h>
|
||||
|
||||
static void put32(unsigned char *p,uint32_t value){p[0]=(unsigned char)value;p[1]=(unsigned char)(value>>8);p[2]=(unsigned char)(value>>16);p[3]=(unsigned char)(value>>24);}
|
||||
|
|
@ -191,4 +192,35 @@ static void normalize(void)
|
|||
assert(xtc_project_normalize_audio(p,ids,1,NAN)==XTC_ERR_INVALID_ARGUMENT);
|
||||
xtc_project_destroy(p);assert(unlink(path)==0 && rmdir(dir)==0);
|
||||
}
|
||||
int main(void){markers();sections();ripple();duplicate_track();split_midi();merge_midi();humanize();chords();arpeggio();normalize();puts("Next DAW workflow tests passed.");return 0;}
|
||||
static void collect(void)
|
||||
{
|
||||
xtc_project *p=NULL,*q=NULL;xtc_audio_plan *audio=NULL;xtc_midi_plan *midi=NULL;xtc_plugin_spec spec;
|
||||
uint64_t t,c,n;xtc_clip_info original,loaded;char root[]="/tmp/xtc-collect-XXXXXX",source[512],dest[512],moved[512],project[512],media[512],failed[512];
|
||||
assert(mkdtemp(root));snprintf(source,sizeof(source),"%s/source.wav",root);test_wave(source,.5f);
|
||||
snprintf(dest,sizeof(dest),"%s/collected",root);snprintf(moved,sizeof(moved),"%s/moved",root);snprintf(failed,sizeof(failed),"%s/failed",root);
|
||||
assert(xtc_project_create(&p)==XTC_OK && xtc_project_create(&q)==XTC_OK && xtc_project_add_track(p,"Track",&t)==XTC_OK);
|
||||
assert(xtc_project_import_audio(p,t,source,0,&c)==XTC_OK && xtc_project_find_clip(p,c,&original)==XTC_OK);
|
||||
assert(xtc_project_add_midi_clip(p,t,960,960,&n)==XTC_OK);
|
||||
assert(xtc_plugin_probe_format(XTC_PLUGIN_BUILTIN,XTC_BUILTIN_PATH,4,48000,&spec)==XTC_OK);strcpy(spec.sample_path,source);
|
||||
assert(xtc_project_set_instrument(p,t,&spec)==XTC_OK);
|
||||
{char large[512];uint64_t extra;FILE *f;
|
||||
snprintf(large,sizeof(large),"%s/large.wav",root);f=fopen(large,"wb");assert(f && ftruncate(fileno(f),268435457)==0 && fclose(f)==0);
|
||||
assert(xtc_project_add_clip(p,t,"Oversized",1920,960,&extra)==XTC_OK && xtc_project_set_clip_asset(p,extra,large)==XTC_OK);
|
||||
assert(xtc_project_collect(p,failed)==XTC_ERR_CAPACITY && access(failed,F_OK)!=0);
|
||||
assert(unlink(large)==0 && mkfifo(large,0600)==0);
|
||||
assert(xtc_project_collect(p,failed)==XTC_ERR_IO && access(failed,F_OK)!=0);
|
||||
assert(xtc_project_remove_clip(p,extra)==XTC_OK && unlink(large)==0);}
|
||||
assert(xtc_project_collect(p,dest)==XTC_OK && xtc_project_collect(p,dest)==XTC_ERR_IO);
|
||||
assert(xtc_project_find_clip(p,c,&loaded)==XTC_OK && !strcmp(loaded.asset_path,original.asset_path));
|
||||
assert(rename(dest,moved)==0 && unlink(source)==0);
|
||||
snprintf(project,sizeof(project),"%s/moved/project.xtc",root);snprintf(media,sizeof(media),"%s/moved/media-000.wav",root);
|
||||
assert(xtc_project_load(q,project)==XTC_OK && xtc_project_find_clip(q,c,&loaded)==XTC_OK && !strcmp(loaded.asset_path,media));
|
||||
assert(xtc_project_get_instrument(q,t,&spec)==XTC_OK && !strcmp(spec.sample_path,media));
|
||||
assert(xtc_audio_plan_create(q,48000,&audio)==XTC_OK && xtc_audio_plan_issues(audio,NULL)==0);
|
||||
{float sample=0;assert(xtc_audio_plan_render(audio,0,&sample,1)==XTC_OK && fabsf(sample-.5f)<.00001f);}
|
||||
assert(xtc_midi_plan_create(q,48000,&midi)==XTC_OK && xtc_midi_plan_asset_issues(midi)==0);
|
||||
assert(xtc_project_collect(p,failed)==XTC_ERR_IO && access(failed,F_OK)!=0);
|
||||
xtc_audio_plan_destroy(audio);xtc_midi_plan_destroy(midi);xtc_project_destroy(p);xtc_project_destroy(q);
|
||||
assert(unlink(project)==0 && unlink(media)==0 && rmdir(moved)==0 && rmdir(root)==0);
|
||||
}
|
||||
int main(void){markers();sections();ripple();duplicate_track();split_midi();merge_midi();humanize();chords();arpeggio();normalize();collect();puts("Next DAW workflow tests passed.");return 0;}
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue