From: Jordan Date: Fri, 17 Feb 2017 00:47:01 +0000 (-0800) Subject: more binaryout changes X-Git-Url: https://www.kengrimes.com/gitweb/?p=henge%2Fapc.git;a=commitdiff_plain;h=d1f689cb043076cea58da995cbfbaf9ebca6e398 more binaryout changes --- diff --git a/src/binaryout.c b/src/binaryout.c index ee82c6f..ffb4021 100644 --- a/src/binaryout.c +++ b/src/binaryout.c @@ -19,7 +19,9 @@ #define XXH_PRIVATE_API #include "../xxHash/xxhash.h" #define STB_IMAGE_IMPLEMENTATION -#include "stb_image.h" +#include "../stb/stb_image.h" +#define STB_IMAGE_WRITE_IMPLEMENTATION +#include "../stb/stb_image_write.h" /* Public */ void ir_binout_init(struct ir_class_t*); @@ -80,22 +82,18 @@ struct bin_plink_t { struct bin_pixel_t { int x, y, z; uint32_t ref; + int attach_idx; }; struct bin_pixel_node_t { struct bin_pixel_node_t* next; struct bin_pixel_t data; }; -struct bin_op_t { - int x; - int y; - int attach_idx; -}; struct bin_attachment_header_t { int num_attachment_lists; int num_attachments; }; struct bin_attachment_t { - int idx; + int x, y, z, idx; ir_set set; }; /* Read out of the als, after first ir pass, resolves the @@ -114,6 +112,41 @@ FILE* binaryout; #define NAMEHASH(name, domain) (XXH32(name, u8_strlen(name), 0XCEED ) & domain) +static inline +int bin_set_varcount +( ir_set set ) +{ int count; + framebox set_fb; + framebox iter; + set_fb = ir_set_framebox(set); + count = 0; + for (iter = set_fb; iter != NULL; iter = ir_setdata_nextsib(iter)) + count++; + return count; +} + +static inline +int bin_class_sibcount +( ir_class class ) +{ int count; + ir_class iter; + count = 0; + for (iter = class; iter != NULL; iter = ir_class_nextsib(iter)) + count++; + return count; +} + +static inline +int bin_set_sibcount +( ir_set set ) +{ int count; + ir_set iter; + count = 0; + for (iter = set; iter != NULL; iter = ir_set_nextsib(iter)) + count++; + return count; +} + /* Given a position and a size, checks if the bytes are null and returns the file position to where it started. 1 if not null, 0 if null*/ /* TODO: Determine why fseeking file past end sets bytes to -1, and not 0 */ @@ -230,10 +263,10 @@ bin_traverse_class uint8_t* class_name; class_start = ftell(binaryout); - class_name = get_class_name(class); + class_name = ir_class_name(class); - num_csibs = get_class_sibcount(class); - num_ssibs = get_set_sibcount(get_class_root_set(class)); + num_csibs = bin_class_sibcount(class); + num_ssibs = bin_set_sibcount(ir_class_rootset(class)); /* alloc space (before hash tables) for class header */ class_header.namelen = u8_strlen(class_name); @@ -253,19 +286,23 @@ bin_traverse_class fwrite(class_name, class_header.namelen, 1, binaryout); /* Start populating root_set hash table */ - for ( siter = get_class_root_set(class); siter != NULL; siter = get_set_nextsib(siter)) + for ( siter = ir_class_rootset(class); siter != NULL; siter = ir_set_nextsib(siter)) { fseek(binaryout, 0, SEEK_END); - ht_entry.key = NAMEHASH(get_set_name(siter), num_ssibs << 1); + ht_entry.key = NAMEHASH(ir_set_name(siter), num_ssibs << 1); ht_entry.value = bin_traverse_set(siter); bin_insert_ht_entry(rootsetht_start, rootsetht_size, &ht_entry, 0); } /* Start populating class child hash table */ - for ( citer = get_class_nextchild(class); citer != NULL; citer = get_class_nextsib(citer)) - { fseek(binaryout, 0, SEEK_END); - ht_entry.key = NAMEHASH(get_class_name(citer), num_csibs << 1); + for ( citer = ir_class_nextchild(class); citer != NULL; citer = ir_class_nextsib(citer)) + { if(chdir((char*) class_name)) + eprintf("CHDIR %U from %s\n",(char*) class_name,getcwd(NULL,255)); + fseek(binaryout, 0, SEEK_END); + ht_entry.key = NAMEHASH(ir_class_name(citer), num_csibs << 1); ht_entry.value = bin_traverse_class(citer); bin_insert_ht_entry(classht_start, classht_size, &ht_entry, 0); + if (chdir("..")) + eprintf("CHDIR ..\n"); } return class_start; @@ -294,7 +331,7 @@ bin_traverse_set uint8_t* set_name; set_start = ftell(binaryout); - set_name = get_set_name(set); + set_name = ir_set_name(set); /* alloc space for set header */ setname_len = u8_strlen(set_name); @@ -304,7 +341,7 @@ bin_traverse_set header.sdat_start = bin_process_sdat(set); /* Setup child hash table for current sets children */ - num_child = get_set_sibcount(get_set_nextchild(set)); + num_child = bin_set_sibcount(ir_set_nextchild(set)); HT_INIT(childht_start, childht_size, num_child); /* populate header, write to file */ @@ -314,15 +351,15 @@ bin_traverse_set fwrite(&header, sizeof(struct bin_set_header_t), 1, binaryout); fwrite(set_name, setname_len, 1, binaryout); - for(iter = get_set_nextchild(set); iter != NULL; iter = get_set_nextsib(iter)) + for(iter = ir_set_nextchild(set); iter != NULL; iter = ir_set_nextsib(iter)) { fseek(binaryout, 0, SEEK_END); - ht_entry.key = NAMEHASH(get_set_name(iter), num_child << 1); + ht_entry.key = NAMEHASH(ir_set_name(iter), num_child << 1); ht_entry.value = bin_traverse_set(iter); bin_insert_ht_entry(childht_start, childht_size, &ht_entry, 0); } - set_set_filepos(set, set_start); + ir_set_assign_fpos(set, set_start); return set_start; } @@ -362,7 +399,7 @@ bin_process_sdat fseek(binaryout, sizeof(struct bin_setdata_header_t), SEEK_CUR); num_links = bin_process_links(set, olink_head); - num_entries = get_set_variants(set) + num_links; + num_entries = bin_set_varcount(set) + num_links; HT_INIT(varht_start, varht_size, num_entries); @@ -406,7 +443,7 @@ bin_process_vlink num_links = 0; /* TODO: Macroize? or not worth? */ - link_name = get_link_name(vlink); + link_name = ir_setdata_name(vlink); if (link_name) { plp = struct_alloc(bin_plink_t); @@ -417,10 +454,10 @@ bin_process_vlink num_links++; } else // linking a variant hash table - for (fiter = get_set_frameboxes(trg_set); fiter != NULL; fiter = get_framebox_nextsib(fiter)) + for (fiter = ir_set_framebox(trg_set); fiter != NULL; fiter = ir_setdata_nextsib(fiter)) { plp = struct_alloc(bin_plink_t); plp->src_pos = 0; // TBD @ process_setdata - plp->name = get_framebox_name(fiter); + plp->name = ir_setdata_name(fiter); plp->trg_set = trg_set; plp->type = VLINK; num_links++; @@ -438,7 +475,7 @@ bin_process_mlink ) { struct bin_plink_t* plp; uint8_t* mlink_name; - mlink_name = get_link_name(mlink); + mlink_name = ir_setdata_name(mlink); plp = struct_alloc(bin_plink_t); plp->src_pos = 0; //TBD after resolving the childlist | TODO: attach_pos? if(mlink_name) plp->name = mlink_name; @@ -472,14 +509,14 @@ bin_process_links ir_setdata olink_head ) { int num_links; - ir_setdata liter; //link iter + linkdata liter; //link iter ir_set trg_set; num_links = 0; - for(liter = get_set_links(src_set); liter != NULL; liter = get_link_nextsib(liter)) - { trg_set = get_set_from_ref(get_link_ref(liter)); - switch (get_link_type(liter)) { + for(liter = ir_set_link(src_set); liter != NULL; liter = ir_setdata_nextsib((ir_setdata) liter)) + { trg_set = ir_set_from_ref(ir_linkdata_ref(liter)); + switch (ir_linkdata_type(liter)) { case OLINK: if (olink_cycle(liter, olink_head)) //TODO: stack of olinks to iterate and check for cycles? return num_links; @@ -587,9 +624,9 @@ bin_process_frameboxes ir_setdata fiter; /* Insert variants into hash table to overwrite olink insertions*/ - for ( fiter = get_set_frameboxes(set); fiter != NULL; fiter = get_framebox_nextsib(fiter)) + for ( fiter = ir_set_framebox(set); fiter != NULL; fiter = ir_setdata_nextsib(fiter)) { fseek(binaryout, 0, SEEK_END); - ht_entry.key = NAMEHASH(get_framebox_name(fiter), ht->entries << 1); + ht_entry.key = NAMEHASH(ir_setdata_name(fiter), ht->entries << 1); ht_entry.value = bin_process_framebox(set, fiter, default_pixel_list); bin_insert_ht_entry(ht->start, ht->entries * sizeof(ht_entry), &ht_entry, 1); } @@ -599,103 +636,196 @@ bin_process_frameboxes static inline void bin_set_img_info ( struct bin_img_info_t* img_info, - ir_setdata framedata + ir_setdata frame_data ) -{ img_info->fwidth = get_framedata_width(framedata); - img_info->fheight = get_framedata_height(framedata); +{ ir_frameinfo frameinfo; + frameinfo = ir_framedata_frameinfo(frame_data); + img_info->fwidth = frameinfo->w; + img_info->fheight = frameinfo->h; img_info->unaligned_height = img_info->height % img_info->fheight; img_info->unaligned_width = img_info->width % img_info->fwidth; } +/* |-----------------------------| + | frame header | + |-----------------------------| + | pixel data for frame1 - n | + |-----------------------------| + | op data for frame1 - n | + |-----------------------------| */ -/* TODO: Implement this */ -long -bin_process_frame - () -{} - - - -/* Combine the framesheet and mapsheet to create - the output sheet */ -/* |-------------------------| - | outputsheet header | - |-------------------------| - | pixel data for frame1 | - |-------------------------| - | op data for frame1 | - |-------------------------| - | etc. | */ -//TODO: processing direction sounds dumb, but cant call it process_framesheet because -// its actually the mapsheet and the framesheet. rename to output sheet? -/* THIS FUNCTION IS NOT DONE */ long +#define GENERATE_FILENAME(_N) ((char*) u8_strcat(_N, png_suffix)) bin_process_facing ( ir_setdata framebox, apc_facing facing, struct bin_pixel_node_t* default_pixel_list ) { struct bin_img_info_t mapsheet_info, framesheet_info; - int num_mapchannels, num_framechannels; + int num_mapchannels, num_framechannels, x; + struct bin_frame_header_t header; long facing_start; unsigned char* mapdata, * framedata; + uint8_t* png_suffix = ".png"; + struct bin_pixel_node_t* map_pixel_list; facing_start = ftell(binaryout); /* Set up data pointers to mapsheet and framesheet, as well as their image infos */ - mapdata = stbi_load(get_framedata_name(get_framebox_facing_mapdata(framebox,SFACE)), &mapsheet_info.width, &mapsheet_info.width, &num_framechannels , 0); - framedata = stbi_load(get_framedata_name(get_framebox_facing_framedata(framebox,SFACE)), &framesheet_info.width, &framesheet_info.height, &num_mapchannels, 0); - bin_set_img_info(&framesheet_info, get_framebox_facing_framedata(framebox, SFACE)); - bin_set_img_info(&mapsheet_info, get_framebox_facing_mapdata(framebox, SFACE)); - - /* TODO: output framesheet/direction header */ + mapdata = stbi_load(GENERATE_FILENAME(ir_setdata_name((ir_setdata) ir_framebox_mapsheet(framebox,SFACE))), &mapsheet_info.width, &mapsheet_info.width, &num_framechannels , 0); + framedata = stbi_load(GENERATE_FILENAME(ir_setdata_name((ir_setdata) ir_framebox_framesheet(framebox,SFACE))), &framesheet_info.width, &framesheet_info.height, &num_mapchannels, 0); + bin_set_img_info(&framesheet_info, ir_framebox_framesheet(framebox, SFACE)); + bin_set_img_info(&mapsheet_info, ir_framebox_mapsheet(framebox, SFACE)); + /* Allocate space for header */ + fseek(binaryout, sizeof(header), SEEK_CUR); + + + /* Output framesheet */ + if(!stbi_write_png(binaryout, framesheet_info.width, framesheet_info.height, 4, mapdata, framesheet_info.fwidth)) + eprintf("error writing out framesheet\n"); - /* For each frame and map i in framesheet + mapsheet */ - /* output frame data */ - /* output op space for frames */ - /* determine ops in map */ - /* check if ops are acceptable */ - /* output ops */ + /* Output framesheet header */ + header.width = framesheet_info.fwidth; + header.height = framesheet_info.fheight; + header.frames = framesheet_info.width / framesheet_info.fwidth; //TODO: division is bad + header.op_start = ftell(binaryout); + fseek(binaryout, facing_start, SEEK_SET); + fwrite(&header, sizeof(header), 1, binaryout); + fseek(binaryout, 0, SEEK_END); + + + /* Assuming that fheight = image height */ + /* For each mapframe in mapsheet */ + for ( x = 0; x < header.frames; x++) + { map_pixel_list = bin_map_to_pixel_list(mapsheet_info, 0, x * mapsheet_info.fwidth, data); + if(!bin_process_map_pixel_list(default_pixel_list, map_pixel_list)) + eprintf("error processing map pixel list\n"); + bin_output_pixel_list(map_pixel_list); + data += mapsheet_info.fwidth; + + } + /* Determine pixel_list */ + + /* Output pixel_list */ return facing_start; } +/* TODO: Please rename all the functions jhc*/ +static inline +void bin_number_pixel_list +( struct bin_pixel_node_t* pixel_list ) +{ int num = 0; + struct bin_pixel_node_t* iter; + while (iter) + { iter.data.attach_idx = num++; + iter = iter->next; + } +} + +/* Assuming at this point that map_pixel_list is valid */ +static inline +int bin_set_map_pixel_list_attach_idxs +( struct bin_pixel_node_t* default_pixel_list, + struct bin_pixel_node_t* map_pixel_list +) +{ struct bin_pixel_node_t* mapiter, defaultiter; + mapiter = map_pixel_list; + defaultiter = default_pixel_list; + while (mapiter && defaultiter) + { /* if mapiter.data.ref == defaultiter.data.ref, assign mapiter index_idx to defaultiter */ + if (mapiter.data.ref == defauliter.data.ref) + { defaultiter.data.attach_idx = mapiter.data.attach_idx; + mapiter = mapiter->next; + defaultiter = defaultiter->next; + } + else + defaultiter = defaultiter->next; + } +} +/* map_pixel_list cannot have more pixels. for all of its pixels, + the refs must be represented in default pixel list. 0 if invalid, 1 if valid */ +static inline +int bin_valid_map_pixel_list +( struct bin_pixel_node_t* default_pixel_list, + struct bin_pixel_node_t* map_pixel_list +) +{ struct bin_pixel_node_t* mapiter, defaultiter; + defaultiter = default_pixel_list; + /* check length of each to make sure default < max */ + /* for each pixel node in default and map */ + while(defaultiter) + { for( mapiter = map_pixel_list; mapiter != NULL; mapiter = mapiter->next) + { + } + } + if(!mapiter && defaultiter) //defaultiter is longer so error! + return 0; + + + + + +} +static inline +int bin_process_map_pixel_list +( struct bin_pixel_node_t* default_pixel_list, + struct bin_pixel_node_t* map_pixel_list +) +{ /* Determine if pixel_list is valid */ + + /* Determine attach_idx of each pixel, as compared to default pixel list */ + +} -/* Insert pixel(s) into the list, z sorted */ void +bin_assign_pixel_idxs +( struct bin_pixel_node_t* pixel_list ) +{ +} + +/* Insert pixel(s) into the list, z sorted */ +/* number the pixels as you insert them */ +struct bin_pixel_node_t* bin_insert_node_into_list ( struct bin_pixel_node_t* pixel_list_root, struct bin_pixel_node_t* pixel_node ) -{ struct bin_pixel_node_t* head_node, *prev_node; - int node_z; +{ struct bin_pixel_node_t* head_node, * prev_node; - head_node = pixel_list_root->next; - node_z = pixel_node->data.z; - if(head_node == NULL) - { head_node = pixel_node; + if(pixel_list_root == NULL) + { pixel_list_root = pixel_node; } - prev_node = pixel_list_root; + + prev_node = head_node = pixel_list_root; while(head_node != NULL) - { if(node_z > head_node->data.z) - { prev_node = head_node; - head_node = head_node->next; + { if(pixel_node->data.z > head_node->data.z) + { if(head_node->next) + { prev_node = head_node; + head_node = head_node->next; + } + else + { head_node->next = pixel_node; + break; + } } - else if (node_z < head_node->data.z || node_z == head_node->data.z) + else if (pixel_node->data.z < head_node->data.z || pixel_node->data.z == head_node->data.z) { prev_node->next = pixel_node; pixel_node->next = head_node; break; } } + return pixel_list_root; + } @@ -716,7 +846,8 @@ bin_process_pixel if(data) { /* get ref from 4 bytes of data */ pixel_node->data.ref = (int) data; - /* bitshift by ? to get Z ordering */ + /* bitshift by ? to get Z */ + pixel_node->data.z = ((int) data << 24); /* set x and y */ pixel_node->data.x = x + init_width ; @@ -734,35 +865,49 @@ bin_process_pixel } -/* Returns the non null pixels of a single frame */ +/* Returns the non null pixels of a single map */ /* TODO: Finish this */ struct bin_pixel_node_t* -bin_map_to_pixel_list +bin_mapframe_to_pixel_list ( struct bin_img_info_t* img_info, int init_height, int init_width, unsigned char* data ) -{ int x, y; +{ int x, y, fheight, fwidth; struct bin_pixel_node_t* pixel_list, * pixel_node; pixel_list = NULL; - /* Check if frame clips */ + /* if frame clips, process unclippign frames */ if( img_info->unaligned_width ) - ; + { if(img_info->height < img_info->fheight) + fheight = img_info->height; + else + fheight = img_info->fheight; + } + else + fheight = img_info->fheight; if (img_info->unaligned_height ) - ; + { if(img_info->width < img_info->fwidth) + fwidth = img_info->width; + else + fwidth = img_info->fwidth; + } + else + fwidth = img_info->fwidth; + /* Process the map*/ - for (y = 0; y < img_info->fheight; y++) - { for ( x = 0; x < img_info->fwidth; x++ ) + for (y = 0; y < fheight; y++) + { for ( x = 0; x < fwidth; x++ ) { pixel_node = bin_process_pixel(data, x, y, init_height, init_width); - bin_insert_node_into_list(pixel_list, pixel_node); + pixel_list = bin_insert_node_into_list(pixel_list, pixel_node); + data += img_info->width - img_info->fwidth; //stride } } - return pixel_node; + return pixel_list; } static inline @@ -784,7 +929,7 @@ bin_cmp_default_pixel_lists ( struct bin_pixel_node_t* pl1, struct bin_pixel_node_t* pl2 ) -{ struct bin_pixel_node_t* pl1p, * pl2p; +{ struct bin_pixel_node_t* pl1p, * pl2p; int i, pl1_len, pl2_len; pl1p = pl1; @@ -818,12 +963,12 @@ bin_find_default_pixel_list int num_channels; struct bin_img_info_t img_info; - for (fiter = get_set_frameboxes(set); fiter != NULL; fiter = get_framebox_nextsib(fiter)) + for (fiter = ir_set_framebox(set); fiter != NULL; fiter = ir_setdata_nextsib(fiter)) { /* TODO: Stringify the frame name with .png? */ /* TODO: Add directory changing */ - data = stbi_load(get_framedata_name(get_framebox_facing_mapdata(fiter, SFACE)), &img_info.width, &img_info.width, &num_channels, 0); - bin_set_img_info(&img_info, get_framebox_facing_mapdata(fiter, SFACE)); - curr_pixel_list = bin_map_to_pixel_list(&img_info, 0, 0, data); + data = stbi_load(ir_setdata_name((ir_setdata) ir_framebox_mapsheet(fiter,SFACE) ), &img_info.width, &img_info.width, &num_channels, 0); + bin_set_img_info(&img_info, ir_framebox_mapsheet(fiter, SFACE)); + curr_pixel_list = bin_mapframe_to_pixel_list(&img_info, 0, 0, data); default_pixel_list = bin_cmp_default_pixel_lists(curr_pixel_list, default_pixel_list); free(data);