/*! \file lib/gis/parser_help.c \brief GIS Library - Argument parsing functions (help) (C) 2001-2009, 2011 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. \author Original author CERL \author Soeren Gebbert added Dec. 2009 WPS process_description document */ #include #include #include #include #include #include "parser_local_proto.h" static void usage(FILE *fp, int markers); static void show_options(FILE *fp, int maxlen, const char *str); static int show(FILE *fp, const char *item, int len); /*! \brief Command line help/usage message. Calls to G_usage() allow the programmer to print the usage message at any time. This will explain the allowed and required command line input to the user. This description is given according to the programmer's definitions for options and flags. This function becomes useful when the user enters options and/or flags on the command line that are syntactically valid to the parser, but functionally invalid for the command (e.g. an invalid file name.) For example, the parser logic doesn't directly support grouping options. If two options be specified together or not at all, the parser must be told that these options are not required and the programmer must check that if one is specified the other must be as well. If this additional check fails, then G_parser() will succeed, but the programmer can then call G_usage() to print the standard usage message and print additional information about how the two options work together. */ void G_usage(void) { usage(stderr, 0); } void G__usage_text(void) { usage(stdout, 1); } static void usage(FILE *fp, int markers) { struct Option *opt; struct Flag *flag; char item[256]; const char *key_desc; int maxlen; int len, n; int new_prompt = 0; new_prompt = G__uses_new_gisprompt(); if (!st->pgm_name) /* v.dave && r.michael */ st->pgm_name = G_program_name(); if (!st->pgm_name) st->pgm_name = "??"; if (st->module_info.label || st->module_info.description) { fprintf(fp, "\n"); if (markers) fprintf(fp, "{{{DESCRIPTION}}}\n"); fprintf(fp, "%s\n", _("Description:")); if (st->module_info.label) fprintf(fp, " %s\n", st->module_info.label); if (st->module_info.description) fprintf(fp, " %s\n", st->module_info.description); } if (st->module_info.keywords) { fprintf(fp, "\n"); if (markers) fprintf(fp, "{{{KEYWORDS}}}\n"); fprintf(fp, "%s\n ", _("Keywords:")); G__print_keywords(fp, NULL); fprintf(fp, "\n"); } fprintf(fp, "\n"); if (markers) fprintf(fp, "{{{USAGE}}}\n"); fprintf(fp, "%s\n ", _("Usage:")); len = show(fp, st->pgm_name, 1); /* Print flags */ if (st->n_flags) { item[0] = ' '; item[1] = '['; item[2] = '-'; flag = &st->first_flag; for (n = 3; flag != NULL; n++, flag = flag->next_flag) item[n] = flag->key; item[n++] = ']'; item[n] = 0; len = show(fp, item, len); } maxlen = 0; if (st->n_opts) { opt = &st->first_option; while (opt != NULL) { if (opt->key_desc != NULL) key_desc = opt->key_desc; else if (opt->type == TYPE_STRING) key_desc = "string"; else key_desc = "value"; if (!opt->key) { fprintf(stderr, "\n%s\n", _("ERROR: Option key not defined")); exit(EXIT_FAILURE); } n = strlen(opt->key); if (n > maxlen) maxlen = n; strcpy(item, " "); if (!opt->required) strcat(item, "["); strcat(item, opt->key); strcat(item, "="); strcat(item, key_desc); if (opt->multiple) { strcat(item, "[,"); strcat(item, key_desc); strcat(item, ",...]"); } if (!opt->required) strcat(item, "]"); len = show(fp, item, len); opt = opt->next_opt; } } if (new_prompt) { strcpy(item, " [--overwrite]"); len = show(fp, item, len); } strcpy(item, " [--verbose]"); len = show(fp, item, len); strcpy(item, " [--quiet]"); len = show(fp, item, len); fprintf(fp, "\n"); /* Print help info for flags */ fprintf(fp, "\n"); if (markers) fprintf(fp, "{{{FLAGS}}}\n"); fprintf(fp, "%s\n", _("Flags:")); if (st->n_flags) { flag = &st->first_flag; while (flag != NULL) { fprintf(fp, " -%c ", flag->key); if (flag->label) { fprintf(fp, "%s\n", flag->label); if (flag->description) fprintf(fp, " %s\n", flag->description); } else if (flag->description) { fprintf(fp, "%s\n", flag->description); } flag = flag->next_flag; } } if (new_prompt) fprintf(fp, " --o %s\n", _("Allow output files to overwrite existing files")); fprintf(fp, " --v %s\n", _("Verbose module output")); fprintf(fp, " --q %s\n", _("Quiet module output")); /* Print help info for options */ if (st->n_opts) { fprintf(fp, "\n"); if (markers) fprintf(fp, "{{{PARAMETERS}}}\n"); fprintf(fp, "%s\n", _("Parameters:")); opt = &st->first_option; while (opt != NULL) { fprintf(fp, " %*s ", maxlen, opt->key); if (opt->label) { fprintf(fp, "%s\n", opt->label); if (opt->description) { fprintf(fp, " %*s %s\n", maxlen, " ", opt->description); } } else if (opt->description) { fprintf(fp, "%s\n", opt->description); } if (opt->options) show_options(fp, maxlen, opt->options); /* fprintf (fp, " %*s options: %s\n", maxlen, " ", _(opt->options)) ; */ if (opt->def) fprintf(fp, _(" %*s default: %s\n"), maxlen, " ", opt->def); if (opt->descs) { int i = 0; while (opt->opts[i]) { if (opt->descs[i]) fprintf(fp, " %*s %s: %s\n", maxlen, " ", opt->opts[i], opt->descs[i]); i++; } } opt = opt->next_opt; } } } static void show_options(FILE *fp, int maxlen, const char *str) { char *buff = G_store(str); char *p1, *p2; int totlen, len; fprintf(fp, _(" %*s options: "), maxlen, " "); totlen = maxlen + 13; p1 = buff; while ((p2 = strchr(p1, ','))) { *p2 = '\0'; len = strlen(p1) + 1; if ((len + totlen) > 76) { totlen = maxlen + 13; fprintf(fp, "\n %*s", maxlen + 13, " "); } fprintf(fp, "%s,", p1); totlen += len; p1 = p2 + 1; } len = strlen(p1); if ((len + totlen) > 76) fprintf(fp, "\n %*s", maxlen + 13, " "); fprintf(fp, "%s\n", p1); G_free(buff); } static int show(FILE *fp, const char *item, int len) { int n; n = strlen(item) + (len > 0); if (n + len > 76) { if (len) fprintf(fp, "\n "); len = 0; } fprintf(fp, "%s", item); return n + len; }