/* ptn2wif by Max Hailperin converts .ptn file produced by Brad Keister's WinWeave and Weave programs into WIF format */ #define PROGRAM_VERSION "0.2" #include #include #define WARP_SIZE 1024 #define WEFT_SIZE 1024 #define MAX_TREADLES 16 #define TITLE_SIZE 61 #define PALETTE_SIZE 16 #define RGB_MIN 0 #define RGB_MAX 255 #define DEFAULT_CLR_FILE "winweave.clr" static void format_error(const char *description); static void read_trouble(FILE *, const char *filename); static long get16(FILE *); static void print_bit_positions(FILE *, long bits, int num_bits); int main(int argc, char *argv[]){ FILE *ptn_file, *clr_file, *wif_file; const char *clr_filename; long shafts, treadles, rising_shed, warp_threads, weft_threads, warp_mask[WARP_SIZE], tieup_mask[MAX_TREADLES], treadling_mask[WEFT_SIZE]; int red[PALETTE_SIZE] = {0x00,0x00,0x00,0x00,0xAA,0xAA,0xAA,0xAA, 0x55,0x55,0x55,0x55,0xFF,0xFF,0xFF,0xFF}; int green[PALETTE_SIZE] = {0x00,0x00,0xAA,0xAA,0x00,0x00,0x55,0xAA, 0x55,0x55,0xFF,0xFF,0x55,0x55,0xFF,0xFF}; int blue[PALETTE_SIZE] = {0x00,0xAA,0x00,0xAA,0x00,0xAA,0x00,0xAA, 0x55,0xFF,0x55,0xFF,0x55,0xFF,0x55,0xFF}; int active_warp_color, active_weft_color, warp_color[WARP_SIZE], weft_color[WEFT_SIZE]; int title[TITLE_SIZE]; if(argc < 2 || argc > 3){ fprintf(stderr, "Usage: %s ptn-file [clr-file]\n", argv[0]); exit(1); } if((ptn_file = fopen(argv[1], "rb")) == NULL){ fprintf(stderr, "Couldn't open %s for reading.\n", argv[1]); exit(1); } if(argc == 3){ if((clr_file = fopen(clr_filename = argv[2], "rb")) == NULL){ fprintf(stderr, "Couldn't open %s for reading.\n", argv[2]); exit(1); } } else{ clr_file = fopen(clr_filename = DEFAULT_CLR_FILE, "rb"); /* don't check for success, rather use clr_file == NULL later to mean use built in defaults (initialized values above of red/green/blue) */ } wif_file = stdout; switch(getc(ptn_file)){ case 0: rising_shed = 1; break; case 1: rising_shed = 0; break; case EOF: read_trouble(ptn_file, argv[1]); break; default: format_error("bad shed type"); break; } if(getc(ptn_file) == EOF) /* multiple treadling */ read_trouble(ptn_file, argv[1]); if((shafts = get16(ptn_file)) == EOF) read_trouble(ptn_file, argv[1]); if((treadles = get16(ptn_file)) == EOF) read_trouble(ptn_file, argv[1]); if((weft_threads = get16(ptn_file)) == EOF) read_trouble(ptn_file, argv[1]); if((warp_threads = get16(ptn_file)) == EOF) read_trouble(ptn_file, argv[1]); { int i; for(i = 0; i < WARP_SIZE; i++){ if((warp_mask[i] = get16(ptn_file)) == EOF) read_trouble(ptn_file, argv[1]); } } { int i; for(i = 0; i < WEFT_SIZE; i++){ if(get16(ptn_file) == EOF) /* weft mask (approx. = lift plan) */ read_trouble(ptn_file, argv[1]); } } { int i; for(i = 0; i < WARP_SIZE; i++){ if((warp_color[i] = getc(ptn_file)) == EOF) read_trouble(ptn_file, argv[1]); } } { int i; for(i = 0; i < WEFT_SIZE; i++){ if((weft_color[i] = getc(ptn_file)) == EOF) read_trouble(ptn_file, argv[1]); } } { int i; for(i = 0; i < MAX_TREADLES; i++){ if((tieup_mask[i] = get16(ptn_file)) == EOF) read_trouble(ptn_file, argv[1]); } } { int i; for(i = 0; i < WEFT_SIZE; i++){ if((treadling_mask[i] = get16(ptn_file)) == EOF) read_trouble(ptn_file, argv[1]); } } if((active_warp_color = getc(ptn_file)) == EOF) read_trouble(ptn_file, argv[1]); if((active_weft_color = getc(ptn_file)) == EOF) read_trouble(ptn_file, argv[1]); { int i; for(i = 0; i < TITLE_SIZE; i++){ if((title[i] = getc(ptn_file)) == EOF) read_trouble(ptn_file, argv[1]); } } if(getc(ptn_file) != EOF) /* double check on length */ format_error("excess stuff at end of ptn file"); if(clr_file != NULL){ { int i; for(i = 0; i < PALETTE_SIZE; i++){ if(getc(clr_file) == EOF) /* shade */ read_trouble(clr_file, clr_filename); } } { int i; for(i = 0; i < PALETTE_SIZE; i++){ if((red[i] = getc(clr_file)) == EOF) read_trouble(clr_file, clr_filename); if((green[i] = getc(clr_file)) == EOF) read_trouble(clr_file, clr_filename); if((blue[i] = getc(clr_file)) == EOF) read_trouble(clr_file, clr_filename); } } if(getc(clr_file) != EOF) /* double check on length */ format_error("excess stuff at end of clr file"); } fprintf(wif_file, "[WIF]\n" "Version=1.1\n" "Date=April 20, 1997\n" "Developers=wif@mhsoft.com\n" "Source Program=ptn2wif by Max Hailperin \n" "Source Version=" PROGRAM_VERSION "\n" "\n"); fprintf(wif_file, "[CONTENTS]\n" "COLOR PALETTE=yes\n" "TEXT=yes\n" "WEAVING=yes\n" "WARP=yes\n" "WEFT=yes\n" "TIEUP=yes\n" "COLOR TABLE=yes\n" "THREADING=yes\n" "WARP COLORS=yes\n" "TREADLING=yes\n" "WEFT COLORS=yes\n" "\n"); fprintf(wif_file, "[COLOR PALETTE]\n" "Entries=%d\n" "Range=%d,%d\n" "\n", PALETTE_SIZE, RGB_MIN, RGB_MAX); fprintf(wif_file, "[TEXT]\n" "Title="); { int i; for(i = 1; i <= title[0]; i++){ if(title[i] == '\n'){ fprintf(wif_file, "//"); } else{ fprintf(wif_file, "%c", title[i]); } } } fprintf(wif_file, "\n"); fprintf(wif_file, "\n"); fprintf(wif_file, "[WEAVING]\n" "Shafts=%ld\n" "Treadles=%ld\n" "Rising Shed=%ld\n" "\n", shafts, treadles, rising_shed); fprintf(wif_file, "[WARP]\n" "Threads=%ld\n" "Color=%d\n" "\n", warp_threads, active_warp_color+1); fprintf(wif_file, "[WEFT]\n" "Threads=%ld\n" "Color=%d\n" "\n", weft_threads, active_weft_color+1); fprintf(wif_file, "[TIEUP]\n"); { int i; for(i = 0; i < treadles; i++){ long mask = tieup_mask[i]; if(rising_shed) mask = ~mask; fprintf(wif_file, "%d=", i+1); print_bit_positions(wif_file, mask, shafts); fprintf(wif_file, "\n"); } } fprintf(wif_file, "\n"); fprintf(wif_file, "[COLOR TABLE]\n"); { int i; for(i = 0; i < PALETTE_SIZE; i++){ fprintf(wif_file, "%d=%d,%d,%d\n", i+1, red[i], green[i], blue[i]); } } fprintf(wif_file, "\n"); fprintf(wif_file, "[THREADING]\n"); { int i; for(i = 1; i <= warp_threads; i++){ fprintf(wif_file, "%d=", i); print_bit_positions(wif_file, warp_mask[i], shafts); fprintf(wif_file, "\n"); } } fprintf(wif_file, "\n"); fprintf(wif_file, "[WARP COLORS]\n"); { int i; for(i = 1; i <= warp_threads; i++){ if(warp_color[i] != active_warp_color){ fprintf(wif_file, "%d=%d\n", i, warp_color[i]+1); } } } fprintf(wif_file, "\n"); fprintf(wif_file, "[TREADLING]\n"); { int i; for(i = 1; i <= weft_threads; i++){ fprintf(wif_file, "%d=", i); print_bit_positions(wif_file, treadling_mask[i], treadles); fprintf(wif_file, "\n"); } } fprintf(wif_file, "\n"); fprintf(wif_file, "[WEFT COLORS]\n"); { int i; for(i = 1; i <= weft_threads; i++){ if(weft_color[i] != active_weft_color){ fprintf(wif_file, "%d=%d\n", i, weft_color[i]+1); } } } return 0; } static void format_error(const char *description){ fprintf(stderr, "Input file format error: %s\n", description); exit(1); } static void read_trouble(FILE *file, const char *filename){ if(feof(file)){ char msg[100]; sprintf(msg, "file %s too short", filename); format_error(msg); } else { /* presumably ferror */ fprintf(stderr, "Read error on file %s.\n", filename); exit(1); } } static long get16(FILE *f){ int c1, c2; if((c1 = getc(f)) == EOF) return EOF; if((c2 = getc(f)) == EOF) return EOF; return ((long)c2 << 8) | c1; } static void print_bit_positions(FILE *file, long bits, int num_bits){ int pos; const char *sep = ""; for(pos = 0; pos < num_bits; pos++, bits >>=1){ if(bits & 1){ fprintf(file, "%s%d", sep, pos+1); sep = ","; } } }