smaller fixes, started boundary box scanner. Rotation, scaling and flipping is not handled correctly yet
This commit is contained in:
parent
221d5a5db5
commit
542737622f
@ -36,6 +36,8 @@
|
|||||||
|
|
||||||
#define GDS_ERROR(fmt, ...) printf("[PARSE_ERROR] " fmt "\n", ##__VA_ARGS__)
|
#define GDS_ERROR(fmt, ...) printf("[PARSE_ERROR] " fmt "\n", ##__VA_ARGS__)
|
||||||
#define GDS_WARN(fmt, ...) printf("[PARSE_WARNING] " fmt "\n", ##__VA_ARGS__)
|
#define GDS_WARN(fmt, ...) printf("[PARSE_WARNING] " fmt "\n", ##__VA_ARGS__)
|
||||||
|
#define MIN(a,b) (((a) < (b)) ? (a) : (b))
|
||||||
|
#define MAX(a,b) (((a) > (b)) ? (a) : (b))
|
||||||
|
|
||||||
enum record {
|
enum record {
|
||||||
INVALID = 0x0000,
|
INVALID = 0x0000,
|
||||||
@ -223,6 +225,7 @@ static GList *append_cell(GList *curr_list, struct gds_cell **cell_ptr)
|
|||||||
cell->child_cells = NULL;
|
cell->child_cells = NULL;
|
||||||
cell->graphic_objs = NULL;
|
cell->graphic_objs = NULL;
|
||||||
cell->name[0] = 0;
|
cell->name[0] = 0;
|
||||||
|
cell->bounding_box.scanned = FALSE;
|
||||||
} else
|
} else
|
||||||
return NULL;
|
return NULL;
|
||||||
/* return cell */
|
/* return cell */
|
||||||
@ -347,6 +350,97 @@ void scan_library_references(gpointer library_list_item, gpointer user)
|
|||||||
g_list_foreach(lib->cells, scan_cell_reference_dependencies, lib);
|
g_list_foreach(lib->cells, scan_cell_reference_dependencies, lib);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void cell_create_bounding_box(struct gds_cell *cell)
|
||||||
|
{
|
||||||
|
GList *ref;
|
||||||
|
GList *gfx_list;
|
||||||
|
GList *vertex_list;
|
||||||
|
|
||||||
|
struct gds_cell_instance *cell_inst;
|
||||||
|
struct gds_graphics *gfx;
|
||||||
|
struct gds_point *vertex;
|
||||||
|
|
||||||
|
int xlow=0, xhigh=0, ylow=0, yhigh=0;
|
||||||
|
gboolean first = TRUE;
|
||||||
|
|
||||||
|
if (cell->bounding_box.scanned == TRUE)
|
||||||
|
return;
|
||||||
|
|
||||||
|
/* Generate bounding boxes of child cells and update current box*/
|
||||||
|
for (ref = cell->child_cells; ref != NULL; ref = ref->next) {
|
||||||
|
cell_inst = (struct gds_cell_instance *)ref->data;
|
||||||
|
if (cell_inst->cell_ref) {
|
||||||
|
if (cell_inst->cell_ref->bounding_box.scanned == FALSE)
|
||||||
|
cell_create_bounding_box(cell_inst->cell_ref);
|
||||||
|
/* TODO: calculate rotation and inversion to process size correctly */
|
||||||
|
if (cell_inst->cell_ref->bounding_box.scanned == TRUE) {
|
||||||
|
if (first == TRUE) {
|
||||||
|
xlow = cell_inst->cell_ref->bounding_box.coords[0].x +
|
||||||
|
cell_inst->origin.x;
|
||||||
|
ylow = cell_inst->cell_ref->bounding_box.coords[0].y +
|
||||||
|
cell_inst->origin.y;
|
||||||
|
xhigh = cell_inst->cell_ref->bounding_box.coords[1].x +
|
||||||
|
cell_inst->origin.x;
|
||||||
|
yhigh = cell_inst->cell_ref->bounding_box.coords[1].y +
|
||||||
|
cell_inst->origin.y;
|
||||||
|
first = FALSE;
|
||||||
|
} else {
|
||||||
|
xlow = MIN(cell_inst->cell_ref->bounding_box.coords[0].x +
|
||||||
|
cell_inst->origin.x, xlow);
|
||||||
|
ylow = MIN(cell_inst->cell_ref->bounding_box.coords[0].y +
|
||||||
|
cell_inst->origin.y, ylow);
|
||||||
|
xhigh = MAX(cell_inst->cell_ref->bounding_box.coords[1].x +
|
||||||
|
cell_inst->origin.x, xhigh);
|
||||||
|
yhigh = MAX(cell_inst->cell_ref->bounding_box.coords[1].y +
|
||||||
|
cell_inst->origin.y, yhigh);
|
||||||
|
}
|
||||||
|
} else
|
||||||
|
GDS_WARN("Unscanned cells present. This should not happen");
|
||||||
|
} else
|
||||||
|
GDS_WARN("Cell referenced that does not exist: %s. Bounding box might be incorrect.",
|
||||||
|
cell_inst->ref_name);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Generate update box using graphic objects*/
|
||||||
|
for (gfx_list = cell->graphic_objs; gfx_list != NULL; gfx_list = gfx_list->next) {
|
||||||
|
gfx = (struct gds_graphics *)gfx_list->data;
|
||||||
|
|
||||||
|
for (vertex_list = gfx->vertices; vertex_list != NULL; vertex_list = vertex_list->next) {
|
||||||
|
vertex = (struct gds_point *)vertex_list->data;
|
||||||
|
if (first == TRUE) {
|
||||||
|
xlow = vertex->x - (gfx->gfx_type == GRAPHIC_PATH ? gfx->width_absolute / 2: 0);
|
||||||
|
ylow = vertex->y - (gfx->gfx_type == GRAPHIC_PATH ? gfx->width_absolute / 2 : 0);
|
||||||
|
xhigh = vertex->x + (gfx->gfx_type == GRAPHIC_PATH ? gfx->width_absolute / 2: 0);
|
||||||
|
yhigh = vertex->y + (gfx->gfx_type == GRAPHIC_PATH ? gfx->width_absolute / 2 : 0);
|
||||||
|
first = FALSE;
|
||||||
|
} else {
|
||||||
|
xlow = MIN(xlow, vertex->x - (gfx->gfx_type == GRAPHIC_PATH ? gfx->width_absolute / 2 : 0));
|
||||||
|
ylow = MIN(ylow, vertex->y - (gfx->gfx_type == GRAPHIC_PATH ? gfx->width_absolute / 2 : 0));
|
||||||
|
xhigh = MAX(xhigh, vertex->x + (gfx->gfx_type == GRAPHIC_PATH ? gfx->width_absolute / 2 : 0));
|
||||||
|
yhigh = MAX(yhigh, vertex->y + (gfx->gfx_type == GRAPHIC_PATH ? gfx->width_absolute / 2 : 0));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
printf("Cell '%s' has size: %d / %d\n", cell->name, xhigh - xlow, yhigh - ylow);
|
||||||
|
cell->bounding_box.coords[0].x = xlow;
|
||||||
|
cell->bounding_box.coords[0].y = ylow;
|
||||||
|
cell->bounding_box.coords[1].x = xhigh;
|
||||||
|
cell->bounding_box.coords[1].y = yhigh;
|
||||||
|
cell->bounding_box.scanned = TRUE;
|
||||||
|
}
|
||||||
|
|
||||||
|
static void library_create_bounding_boxes(gpointer library_list_item, gpointer user)
|
||||||
|
{
|
||||||
|
GList *cell_list;
|
||||||
|
struct gds_library *lib = (struct gds_library *)library_list_item;
|
||||||
|
if (!lib)
|
||||||
|
return;
|
||||||
|
for (cell_list = lib->cells; cell_list != NULL; cell_list = cell_list->next) {
|
||||||
|
cell_create_bounding_box((struct gds_cell *)cell_list->data);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
void gds_parse_date(const char *buffer, int length, struct gds_time_field *mod_date, struct gds_time_field *access_date)
|
void gds_parse_date(const char *buffer, int length, struct gds_time_field *mod_date, struct gds_time_field *access_date)
|
||||||
{
|
{
|
||||||
|
|
||||||
@ -727,8 +821,13 @@ int parse_gds_from_file(const char *filename, GList **library_list)
|
|||||||
if (!run) {
|
if (!run) {
|
||||||
/* Iterate and find references to cells */
|
/* Iterate and find references to cells */
|
||||||
g_list_foreach(lib_list, scan_library_references, NULL);
|
g_list_foreach(lib_list, scan_library_references, NULL);
|
||||||
|
/* Create bounding boxes */
|
||||||
|
g_list_foreach(lib_list, library_create_bounding_boxes, NULL);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
*library_list = lib_list;
|
*library_list = lib_list;
|
||||||
|
|
||||||
free(workbuff);
|
free(workbuff);
|
||||||
|
@ -9,6 +9,16 @@
|
|||||||
enum graphics_type {GRAPHIC_PATH = 0, GRAPHIC_POLYGON = 1};
|
enum graphics_type {GRAPHIC_PATH = 0, GRAPHIC_POLYGON = 1};
|
||||||
enum path_type {PATH_FLUSH = 0, PATH_ROUNDED = 1, PATH_SQUARED = 2};
|
enum path_type {PATH_FLUSH = 0, PATH_ROUNDED = 1, PATH_SQUARED = 2};
|
||||||
|
|
||||||
|
struct gds_point {
|
||||||
|
int x;
|
||||||
|
int y;
|
||||||
|
};
|
||||||
|
|
||||||
|
struct gds_bounding_box {
|
||||||
|
gboolean scanned;
|
||||||
|
struct gds_point coords[2];
|
||||||
|
};
|
||||||
|
|
||||||
struct gds_time_field {
|
struct gds_time_field {
|
||||||
uint16_t year;
|
uint16_t year;
|
||||||
uint16_t month;
|
uint16_t month;
|
||||||
@ -18,11 +28,6 @@ struct gds_time_field {
|
|||||||
uint16_t second;
|
uint16_t second;
|
||||||
};
|
};
|
||||||
|
|
||||||
struct gds_point {
|
|
||||||
int x;
|
|
||||||
int y;
|
|
||||||
};
|
|
||||||
|
|
||||||
struct gds_graphics {
|
struct gds_graphics {
|
||||||
enum graphics_type gfx_type;
|
enum graphics_type gfx_type;
|
||||||
GList *vertices;
|
GList *vertices;
|
||||||
@ -47,6 +52,7 @@ struct gds_cell {
|
|||||||
struct gds_time_field access_time;
|
struct gds_time_field access_time;
|
||||||
GList *child_cells;
|
GList *child_cells;
|
||||||
GList *graphic_objs;
|
GList *graphic_objs;
|
||||||
|
struct gds_bounding_box bounding_box;
|
||||||
};
|
};
|
||||||
|
|
||||||
struct gds_library {
|
struct gds_library {
|
||||||
|
@ -157,6 +157,11 @@ static void render_cell(struct gds_cell *cell, GList *layer_infos, FILE *tex_fil
|
|||||||
/* Draw polygons of childs */
|
/* Draw polygons of childs */
|
||||||
for (list_child = cell->child_cells; list_child != NULL; list_child = list_child->next) {
|
for (list_child = cell->child_cells; list_child != NULL; list_child = list_child->next) {
|
||||||
inst = (struct gds_cell_instance *)list_child->data;
|
inst = (struct gds_cell_instance *)list_child->data;
|
||||||
|
|
||||||
|
/* Abort if cell has no reference */
|
||||||
|
if (!inst->cell_ref)
|
||||||
|
continue;
|
||||||
|
|
||||||
/* generate translation scope */
|
/* generate translation scope */
|
||||||
g_string_printf(buffer, "\\begin{scope}[shift={(%lf pt,%lf pt)}]\n",
|
g_string_printf(buffer, "\\begin{scope}[shift={(%lf pt,%lf pt)}]\n",
|
||||||
((double)inst->origin.x)/1000.0,((double)inst->origin.y)/1000.0);
|
((double)inst->origin.x)/1000.0,((double)inst->origin.y)/1000.0);
|
||||||
@ -168,7 +173,6 @@ static void render_cell(struct gds_cell *cell, GList *layer_infos, FILE *tex_fil
|
|||||||
g_string_printf(buffer, "\\begin{scope}[yscale=%s]\n", (inst->flipped ? "-1" : "1"));
|
g_string_printf(buffer, "\\begin{scope}[yscale=%s]\n", (inst->flipped ? "-1" : "1"));
|
||||||
WRITEOUT_BUFFER(buffer);
|
WRITEOUT_BUFFER(buffer);
|
||||||
|
|
||||||
if (inst->cell_ref)
|
|
||||||
render_cell(inst->cell_ref, layer_infos, tex_file, buffer);
|
render_cell(inst->cell_ref, layer_infos, tex_file, buffer);
|
||||||
|
|
||||||
g_string_printf(buffer, "\\end{scope}\n");
|
g_string_printf(buffer, "\\end{scope}\n");
|
||||||
|
Loading…
Reference in New Issue
Block a user