/* * $Id: main.c,v 2.5.4.1 2006/08/23 07:34:46 markus Exp $ * **************************************************************************** * * MODULE: d.save * AUTHOR(S): David Satnik - Central Washington University * PURPOSE: Output all commands that have been used to create the * current display graphics with the help of the internal Pad * contents. * COPYRIGHT: (C) 2000 by the GRASS Development Team * * This program is free software under the GNU General Public * License (>=v2). Read the file COPYING that comes with GRASS * for details. * *****************************************************************************/ #include #include #include #include #include #include #include "locals.h" /* globals !!! */ int Sheight, Swidth; char Scurwin[100]; int Wtop, Wbot, Wleft, Wright; char Wcell[100]="", Wdig[100], Wsite[100], Wcolor[25]=""; int Mtype; int proj; struct Cell_head *Mwind; char Nstr[20], Sstr[20], Estr[20], Wstr[20], EWRESstr[20], NSRESstr[20]; struct list_struct *List = NULL, *List_last = NULL; int in_frame_list(struct Option *, char *); int init_globals(void); int which_item(char *); int set_item(char *, char **); int process_list(char *, char **, int); int process_items(char **, int); int process_pad(char ***, int *); int main (int argc, char **argv) { char **pads; char **items; char **list; int npads; int nitems; int p; int stat; int i, j; int redraw; int total_rno, *rno; int total_mno, **mno; int nlists, *live; int from, to, tmp; struct list_struct *temp_list; struct Flag *all_flag; struct Flag *cur_frame; struct Flag *only_object; struct Option *opt1; struct Option *opt2; struct Option *opt3; struct GModule *module; char buff[1024]; char current_frame[64]; G_gisinit(argv[0]); module = G_define_module(); module->keywords = _("display"); module->description = _("Create a list of commands for recreating screen graphics."); opt1 = G_define_option(); opt1->key = "frame"; opt1->description = _("Name of frame(s) to save"); opt1->type = TYPE_STRING; opt1->required = NO; opt1->multiple = YES; /* Conditionalize so "help" and "--interface-description" work */ R__open_quiet(); /* don't let library code make us die */ if (R_open_driver() == 0) { Sheight = R_screen_bot() - R_screen_top() + 1; Swidth = R_screen_rite() - R_screen_left() + 1; Mwind = (struct Cell_head *) G_malloc(sizeof(struct Cell_head)); R_pad_list (&pads, &npads); /* process the screen pad */ p = -1; stat = R_pad_select (""); if (stat) { R_pad_perror ("echo ERROR", stat); fprintf (stdout,"exit -1\n\n"); } else process_pad(&items, &nitems); opt1->answer = Scurwin; buff[0] = '\0'; for (p=npads-1; p>=0; p--) { strcat(buff, pads[p]); if (p != 0) strcat(buff, ","); } opt1->options = buff; } else stat = -1; /* used to exit, if driver open failed */ opt2 = G_define_option(); opt2->key = "remove"; opt2->description = _("List of object numbers to remove which are displayed after \"#\". " "-1 for the last object."); opt2->type = TYPE_INTEGER; opt2->required = NO; opt2->multiple = YES; opt3 = G_define_option(); opt3->key = "move"; opt3->description = _("List of object numbers to move " "(\"from\" to \"to\"). remove= option will be done first, if any."); opt3->type = TYPE_INTEGER; opt3->required = NO; opt3->key_desc = "from,to"; opt3->multiple = YES; cur_frame = G_define_flag(); cur_frame->key = 'c'; cur_frame->description = _("Save current frame"); cur_frame->answer = 0; all_flag = G_define_flag(); all_flag->key = 'a'; all_flag->description = _("Save all the frames"); all_flag->answer = 0; only_object = G_define_flag(); only_object->key = 'o'; only_object->description = _("Only map objects without extra header and tailer"); only_object->answer = 0; if (G_parser(argc, argv)) exit(EXIT_FAILURE); if (stat) /* Check we have monitor */ G_fatal_error(_("No monitor selected")); total_rno = 0; if (opt2->answers) { for (total_rno=0; opt2->answers[total_rno]; total_rno++); if (total_rno) { rno = (int *) G_malloc(total_rno*sizeof(int)); for (i=0; ianswers[i]); } } total_mno = 0; if (opt3->answers) { for (total_mno=0; opt3->answers[total_mno]; total_mno++); total_mno /= 2; if (total_mno) { mno = (int **) G_malloc(total_mno*sizeof(int *)); for (i=0,j=0; ianswers[j]); mno[i][1] = atoi(opt3->answers[j+1]); } } } if (cur_frame->answer) { D_get_cur_wind(current_frame) ; opt1->answer = current_frame ; } if(!only_object->answer) fprintf (stdout,":\n# Shell Script created by d.save %s\n\n", G_date()); G_get_window ( Mwind ); redraw = 0; /* now start at the end (the earliest made window) and process them */ for (p = npads-1; p >= 0; p--) { if (all_flag->answer || in_frame_list(opt1, pads[p])) { init_globals(); if(!cur_frame->answer && !only_object->answer) fprintf (stdout,"\n# Here are the commands to create window: %s\n", pads[p]); stat = R_pad_select (pads[p]); if (stat) { R_pad_perror ("echo ERROR", stat); fprintf (stdout,"exit -1\n\n"); continue; } if (total_rno || total_mno) { stat = R_pad_get_item("list", &list, &nlists); if (stat || !nlists) { R_pad_perror ("echo ERROR", stat); fprintf (stdout,"exit -1\n\n"); continue; } R_pad_delete_item("list"); live = (int *) G_malloc(nlists*sizeof(int)); for (i=0; inlists) continue; redraw = 1; rno[i] = (rno[i]==-1 ? nlists:(rno[i]==0 ? 1:rno[i])); live[nlists-rno[i]] = -1; } G_free(rno); } if (total_mno) { for (i=0; inlists || to<1 || to>nlists || from==to || live[nlists-from]<0) { G_free(mno[i]); continue; } redraw = 1; tmp = live[nlists-to]; live[nlists-to] = live[nlists-from]; if (from=nlists-to+2; j--) live[j] = live[j-1]; live[nlists-to+1] = tmp; } else { for (j=nlists-from; j<=nlists-to-2; j++) live[j] = live[j+1]; live[nlists-to-1] = tmp; } G_free(mno[i]); } G_free(mno); } for (i=0;i=0) D_add_to_list(list[live[i]]); } G_free(live); R_pad_freelist (list, nlists); } if (process_pad(&items, &nitems) != 0) continue; Wtop = (100.0 * Wtop)/Sheight + 0.5; Wbot = (100.0 * Wbot)/Sheight + 0.5; Wleft = (100.0 * Wleft)/Swidth + 0.5; Wright = (100.0 * Wright)/Swidth + 0.5; if (Wtop<0) Wtop=0; if (Wbot<0) Wbot=0; if (Wleft<0) Wleft=0; if (Wright<0) Wright=0; if(!cur_frame->answer && !only_object->answer) { if (all_flag->answer && p==npads-1) fprintf (stdout,"d.frame -ec frame=%s at=%d,%d,%d,%d\n", pads[p], 100-Wbot, 100-Wtop, Wleft, Wright); else fprintf (stdout,"d.frame -c frame=%s at=%d,%d,%d,%d\n", pads[p], 100-Wbot, 100-Wtop, Wleft, Wright); } if(!only_object->answer) { if (Wcolor[0] == '\0') fprintf (stdout,"d.erase\n"); else fprintf (stdout,"d.erase color=%s\n", Wcolor); if (Mtype != -1) { fprintf (stdout,"g.region n=%s s=%s e=%s w=%s nsres=%s ewres=%s\n", Nstr, Sstr, Estr, Wstr, NSRESstr, EWRESstr); } fprintf (stdout,"\n"); } /* List already has commands to draw these maps. if (Wcell[0]!='\0') fprintf (stdout,"d.rast map=%s\n", Wcell); if (Wdig[0]!='\0') fprintf (stdout,"d.vect map=%s\n", Wdig); if (Wsite[0]!='\0') fprintf (stdout,"d.sites sitefile=%s\n", Wsite); */ /* print out the list */ i=0; temp_list = List; while (temp_list!=NULL) { i++; temp_list = temp_list->ptr; } while (List!=NULL) { fprintf (stdout,"%-70s # %d\n", List->string, i--); temp_list = List; List = List->ptr; G_free (temp_list->string); G_free (temp_list); } List_last = NULL; } if (! all_flag->answer && ! strcmp(opt1->answer, pads[p])) break; } if (!only_object->answer && (all_flag->answer || in_frame_list(opt1, Scurwin))) fprintf (stdout,"\nd.frame -s frame=%s\n", Scurwin); R_close_driver(); if (redraw) G_system("d.redraw"); exit(EXIT_SUCCESS); } /* return 1 if the padname is in the opt->answers list of frame names */ int in_frame_list (struct Option *opt, char *padname) { int n; if (opt->answers) for (n=0; opt->answers[n] != NULL; n++) if (! strcmp(opt->answers[n], padname)) return(1); return(0); } int init_globals (void) { Wtop = Wbot = Wleft = Wright = 0; Wcell[0] = '\0'; Wdig[0] = '\0'; Wsite[0] = '\0'; Wcolor[0] = '\0'; Mtype = Mwind->zone = -1; Mwind->ew_res = Mwind->ns_res = Mwind->north = Mwind->south = Mwind->east = Mwind->west = 0.0; return 0; } /* this array of strings defines the possible item types */ #define ITEM_TYPES 12 #define ITEM_SIZE 10 char Known_items[ITEM_TYPES][ITEM_SIZE] = { "cur_w", "d_win", "m_win", "time", "list", "erase", "cell", "dig", "site", "cell_list", "dig_list", "site_list" }; /* this function returns the position in the Known_items array that the given item string matches or -1 if no match. */ int which_item (char *itemstr) { int i; for(i=0; izone), Estr, Wstr, Nstr, Sstr, &(Mwind->rows), &(Mwind->cols)); proj = G_projection(); G_scan_easting(Estr, &(Mwind->east), proj); G_scan_easting(Wstr, &(Mwind->west), proj); G_scan_northing(Nstr, &(Mwind->north), proj); G_scan_northing(Sstr, &(Mwind->south), proj); if ( (err = G_adjust_Cell_head (Mwind, 1, 1)) ) { G_fatal_error ( err ); } G_format_resolution (Mwind->ew_res, EWRESstr, proj); G_format_resolution (Mwind->ns_res, NSRESstr, proj); break; case 3: /* time */ break; case 5: /* d.erase color */ sscanf(list[0]," %s ", Wcolor); break; case 6: /* cell */ sscanf(list[0]," %s ", Wcell); break; case 7: /* dig */ sscanf(list[0]," %s ", Wdig); break; case 8: /* site */ sscanf(list[0]," %s ", Wsite); break; case 9: case 10: case 11: break; default: G_warning(_("Unknown item type in pad: %s"), item); break; } } return 0; } /* this function processes items which have multiple lines */ int process_list (char *item, char **list, int count) { int n; struct list_struct *new_list; switch (which_item(item)) { case 4: /* list */ for (n = 0; n < count; n++) { new_list = (struct list_struct *) G_malloc(sizeof(struct list_struct)); new_list->ptr = NULL; new_list->string = (char *) G_malloc(strlen(list[n])+1); strcpy(new_list->string, list[n]); if (List == NULL) /* nothing on the list yet */ List = new_list; else List_last->ptr = new_list; List_last = new_list; } break; case 9: case 10: case 11: break; default: /* otherwise */ G_warning(_("Unkown item type in pad: %s"), item); break; } return 0; } /* this function processes the items in a pad */ int process_items (char **items, int nitems) { int count; char **list; int i; int stat ; for (i = nitems-1; i >= 0; i--) { stat = R_pad_get_item (items[i], &list, &count); if (stat) { R_pad_perror ("# ERROR", stat); fprintf (stdout,"exit -1\n\n"); continue; } if (count==1) set_item(items[i],list); else process_list(items[i],list, count); R_pad_freelist (list,count); } return 0; } /* this function processes a pad */ int process_pad (char ***items, int *nitems) { int stat; stat = R_pad_list_items (items, nitems); if (stat) { R_pad_perror ("echo ERROR", stat); fprintf (stdout,"exit -1\n\n"); return(-1); } process_items(*items, *nitems); return(0); }