/* * gui/glabel.c - Global label pop-up * * Written 2016 by Werner Almesberger * Copyright 2016 by 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 #include #include #include #include "misc/util.h" #include "kicad/dwg.h" #include "gui/style.h" #include "gui/aoi.h" #include "gui/over.h" #include "gui/common.h" /* small offset to hide rounding errors */ #define CHEAT 1 struct glabel_aoi_ctx { const struct gui_sheet *sheet; const struct sch_obj *obj; struct dwg_bbox bbox; struct overlay *over; }; /* ----- Tools ------------------------------------------------------------- */ static void eeschema_coord(const struct gui_ctx *ctx, int x, int y, int *rx, int *ry) { GtkAllocation alloc; gtk_widget_get_allocation(ctx->da, &alloc); *rx = ((x - ctx->x) >> ctx->zoom) + alloc.width / 2; *ry = ((y - ctx->y) >> ctx->zoom) + alloc.height / 2; } /* ----- AoIs -------------------------------------------------------------- */ static void glabel_dest_click(void *user) { struct gui_sheet *sheet = user; go_to_sheet(sheet->ctx, sheet); } void dehover_glabel(struct gui_ctx *ctx) { overlay_remove_all(&ctx->pop_overlays); redraw(ctx); } static bool hover_glabel(void *user, bool on) { struct glabel_aoi_ctx *aoi_ctx = user; struct gui_ctx *ctx = aoi_ctx->sheet->ctx; const struct gui_sheet *curr_sheet = ctx->curr_sheet; const struct dwg_bbox *bbox = &aoi_ctx->bbox; if (!on) { dehover_glabel(ctx); return 1; } GtkAllocation alloc; struct overlay_style style = { .font = BOLD_FONT, .wmin = 100, .wmax = 100, .radius = 0, .pad = 4, .skip = -4, .fg = { 0.0, 0.0, 0.0, 1.0 }, .bg = { 1.0, 0.8, 0.4, 0.8 }, .frame = { 1.0, 1.0, 1.0, 1.0 }, /* debugging */ .width = 0, }; int sx, sy, ex, ey, mx, my; unsigned n = 0; struct gui_sheet *sheet; const struct sch_obj *obj; struct overlay *over; aoi_dehover(); overlay_remove_all(&ctx->pop_overlays); for (sheet = ctx->new_hist->sheets; sheet; sheet = sheet->next) { n++; if (sheet == curr_sheet) continue; for (obj = sheet->sch->objs; obj; obj = obj->next) { if (obj->type != sch_obj_glabel) continue; if (strcmp(obj->u.text.s, aoi_ctx->obj->u.text.s)) continue; over = overlay_add(&ctx->pop_overlays, &ctx->aois, NULL, glabel_dest_click, sheet); overlay_text(over, "%d %s", n, sheet->sch->title); overlay_style(over, &style); break; } } eeschema_coord(ctx, bbox->x - curr_sheet->xmin, bbox->y - curr_sheet->ymin, &sx, &sy); eeschema_coord(ctx, bbox->x + bbox->w - curr_sheet->xmin, bbox->y + bbox->h - curr_sheet->ymin, &ex, &ey); gtk_widget_get_allocation(ctx->da, &alloc); mx = (sx + ex) / 2; my = (sy + ey) / 2; ctx->pop_x = mx < alloc.width / 2 ? sx - CHEAT : -(alloc.width - ex) + CHEAT; ctx->pop_y = my < alloc.height / 2 ? sy - CHEAT : -(alloc.height - ey) + CHEAT; redraw(ctx); return 0; } void add_glabel_aoi(struct gui_sheet *sheet, const struct sch_obj *obj) { const struct dwg_bbox *bbox = &obj->u.text.bbox; struct glabel_aoi_ctx *aoi_ctx = alloc_type(struct glabel_aoi_ctx); struct aoi cfg = { .x = bbox->x, .y = bbox->y, .w = bbox->w, .h = bbox->h, .hover = hover_glabel, .user = aoi_ctx, }; aoi_ctx->sheet = sheet; aoi_ctx->obj = obj; aoi_ctx->bbox = *bbox; aoi_add(&sheet->aois, &cfg); }