Implementing 'standard' X -geometry argument



One feature I miss in GTK+ is the standard "-geometry" argument
that X apps like xterm understand. I'm sure I saw this on
someones TODO list for GTK+ 2.0, but I can't see it in there yet.
In the meantime I've implemented my own version, which is shown
below in minimal form. It looks plain nasty though, so I'm
wondering of someone has a cleaner way of implementing it (sscanf
perhaps?).

/* ------------------------------------------------------------ */

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <ctype.h>

typedef struct {
    int x, y, w, h;
} Geometry;

static int parse_args(int, char **, Geometry *);

int main(int argc, char *argv[]) {
    Geometry geom = { 0, 0, 0, 0 };

    if(parse_args(argc, argv, &geom))
        return 1;

    printf("Geometry %d x %d + %d + %d\n", geom.x, geom.y, geom.w, geom.h);

    return 0;
}

int parse_args(int argc, char *argv[], Geometry *geom) {
    char *sptr, *eptr;

    if(argc == 1)
        return 1;

    if(argc != 3 || strcmp(argv[1], "-geometry")) {
        fprintf(stderr, "Usage : progname [-geometry <geometry>]\n");
        return 1;
    }

    /* extract width */
    sptr = eptr = argv[2];
    while(*eptr && isdigit(*eptr))
        eptr++;
    if(!*eptr || eptr == sptr || *eptr != 'x')
        goto USAGE;
    *eptr = '\0';
    geom->w = strtod(sptr, NULL);

    /* extract height */
    sptr = ++eptr;
    if(!*eptr)
        goto USAGE;
    while(*eptr && isdigit(*eptr))
        eptr++;
    if(eptr == sptr || (*eptr && (*eptr != '+' && *eptr != '-')))
        goto USAGE;
    geom->h = strtod(sptr, NULL);

    /* extract x */
    if(!*eptr)
        return 0;
    sptr = eptr++;
    while(*eptr && isdigit(*eptr))
        eptr++;
    if(eptr == (sptr + 1) || (*eptr != '+' && *eptr != '-'))
        goto USAGE;
    geom->x = strtod(sptr, NULL);

    /* extract y */
    if(!*eptr)
        goto USAGE;
    sptr = eptr++;
    while(*eptr && isdigit(*eptr))
        eptr++;
    if(eptr == (sptr + 1) || (*eptr))
        goto USAGE;
    geom->y = strtod(sptr, NULL);

    return 0;

USAGE:
    fprintf(stderr, "Invalid geometry argument\n");
    return 1;
}

--
chris wareham iosystems co uk (work)
cwareham btinternet com (home)




[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]