mirror of
git://projects.qi-hardware.com/cae-tools.git
synced 2024-12-23 09:55:32 +02:00
77 lines
1.6 KiB
C
77 lines
1.6 KiB
C
|
/*
|
||
|
* connect.c - Connect paths
|
||
|
*
|
||
|
* Written 2010-2012, 2015 by Werner Almesberger
|
||
|
* Copyright 2010-2012, 2015 Werner Almesberger
|
||
|
*
|
||
|
* This program is free software; you can redistribute it and/or modify
|
||
|
* it under the terms of the GNU General Public License as published by
|
||
|
* the Free Software Foundation; either version 2 of the License, or
|
||
|
* (at your option) any later version.
|
||
|
*/
|
||
|
|
||
|
|
||
|
#include <stdlib.h>
|
||
|
#include <math.h>
|
||
|
|
||
|
#include "util.h"
|
||
|
#include "path.h"
|
||
|
|
||
|
|
||
|
static void path_reverse_inplace(struct path *path)
|
||
|
{
|
||
|
struct point *points = NULL, *p, *next;
|
||
|
|
||
|
path->last = path->first;
|
||
|
for (p = path->first; p; p = next) {
|
||
|
next = p->next;
|
||
|
p->next = points;
|
||
|
points = p;
|
||
|
}
|
||
|
path->first = points;
|
||
|
}
|
||
|
|
||
|
|
||
|
static int attr_eq(const struct path *a, const struct path *b)
|
||
|
{
|
||
|
return a->r_tool == b->r_tool && a->outside == b->outside &&
|
||
|
a->notch == b->notch;
|
||
|
}
|
||
|
|
||
|
|
||
|
struct path *path_connect(struct path *path)
|
||
|
{
|
||
|
struct path **a, **b;
|
||
|
struct path *tmp;
|
||
|
|
||
|
again:
|
||
|
for (a = &path; *a; a = &(*a)->next)
|
||
|
for (b = &(*a)->next; *b; b = &(*b)->next) {
|
||
|
if (!attr_eq(*a, *b))
|
||
|
continue;
|
||
|
if (points_eq((*a)->last, (*b)->last))
|
||
|
path_reverse_inplace(*b);
|
||
|
if (points_eq((*a)->last, (*b)->first)) {
|
||
|
(*a)->last->next = (*b)->first->next;
|
||
|
(*a)->last = (*b)->last;
|
||
|
free((*b)->first);
|
||
|
tmp = *b;
|
||
|
*b = tmp->next;
|
||
|
free(tmp);
|
||
|
goto again;
|
||
|
}
|
||
|
if (points_eq((*a)->first, (*b)->first))
|
||
|
path_reverse_inplace(*b);
|
||
|
if (points_eq((*a)->first, (*b)->last)) {
|
||
|
(*b)->last->next = (*a)->first->next;
|
||
|
(*b)->last = (*a)->last;
|
||
|
free((*a)->first);
|
||
|
tmp = *a;
|
||
|
*a = tmp->next;
|
||
|
free(tmp);
|
||
|
goto again;
|
||
|
}
|
||
|
}
|
||
|
return path;
|
||
|
}
|