void grid_draw(DDisplay *ddisp, Rectangle *update) { Grid *grid = &ddisp->grid; DiaRenderer *renderer = ddisp->renderer; if (grid->visible) { /* distance between visible grid lines */ real width_x = ddisp->diagram->grid.width_x; real width_y = ddisp->diagram->grid.width_y; real width_w = ddisp->diagram->grid.width_w; if (ddisp->diagram->grid.dynamic) { calculate_dynamic_grid(ddisp, &width_x, &width_y); } else { width_x = ddisp->diagram->grid.width_x * ddisp->diagram->grid.visible_x; width_y = ddisp->diagram->grid.width_y * ddisp->diagram->grid.visible_y; } DIA_RENDERER_GET_CLASS(renderer)->set_linewidth(renderer, 0.0); if (ddisp->diagram->grid.hex) { grid_draw_hex(ddisp, update, width_w); } else { if (ddisplay_transform_length(ddisp, width_y) >= 2.0 && ddisplay_transform_length(ddisp, width_x) >= 2.0) { /* Vertical lines: */ grid_draw_vertical_lines(ddisp, update, width_x); /* Horizontal lines: */ grid_draw_horizontal_lines(ddisp, update, width_y); } } } }
void object_draw_connectionpoints(DiaObject *obj, DDisplay *ddisp) { int i; static Color midpoint_color = { 1.0, 0.0, 0.0, 1.0 }; DiaRenderer *renderer = ddisp->renderer; DiaRendererClass *renderer_ops = DIA_RENDERER_GET_CLASS (ddisp->renderer); DiaInteractiveRendererInterface *irenderer = DIA_GET_INTERACTIVE_RENDERER_INTERFACE (ddisp->renderer); /* this does not change for any of the points */ renderer_ops->set_linewidth (renderer, 0.0); renderer_ops->set_linestyle (renderer, LINESTYLE_SOLID); /* optimization to only draw the connection points at all if the size * of the object (bounding box) is bigger than the summed size of the * connection points - or some variation thereof ;) */ if (dia_object_get_num_connections(obj) > 1) { const Rectangle *bbox = dia_object_get_bounding_box (obj); real w = ddisplay_transform_length (ddisp, bbox->right - bbox->left); real h = ddisplay_transform_length (ddisp, bbox->bottom - bbox->top); int n = dia_object_get_num_connections(obj); /* just comparing the sizes is still drawing more CPs than useful - try 50% */ if (w * h < n * CONNECTIONPOINT_SIZE * CONNECTIONPOINT_SIZE * 2) { if (ddisp->mainpoint_magnetism) return; /* just draw the main point */ for (i = 0; i < n; ++i) { if (obj->connections[i]->flags & CP_FLAG_ANYPLACE) connectionpoint_draw(obj->connections[i], ddisp, renderer, irenderer, &midpoint_color); } return; } } for (i=0;i<dia_object_get_num_connections(obj);i++) { if ((obj->connections[i]->flags & CP_FLAG_ANYPLACE) == 0) connectionpoint_draw(obj->connections[i], ddisp, renderer, irenderer, &connectionpoint_color); else if (!ddisp->mainpoint_magnetism) /* draw the "whole object"/center connpoints, but only when we don't * have snap-to-grid */ connectionpoint_draw(obj->connections[i], ddisp, renderer, irenderer, &midpoint_color); } }
/* Call this after diagram_find_closest_handle() */ int handle_is_clicked(DDisplay *ddisp, Handle *handle, Point *pos) { real dx, dy; int idx, idy; if (handle==NULL) return FALSE; dx = ABS(handle->pos.x - pos->x); dy = ABS(handle->pos.y - pos->y); idx = ddisplay_transform_length(ddisp, dx); idy = ddisplay_transform_length(ddisp, dy); return (idx<(HANDLE_SIZE+1)/2) && (idy<(HANDLE_SIZE+1)/2); }
static gboolean modify_move_already(ModifyTool *tool, DDisplay *ddisp, Point *to) { static gboolean settings_taken = FALSE; static int double_click_time = 250; real dist; if (!settings_taken) { /* One could argue that if the settings were updated while running, we should re-read them. But I don't see any way to get notified, and I don't want to do this whole thing for each bit of the move --Lars */ GtkSettings *settings = gtk_settings_get_default(); if (settings == NULL) { g_message(_("Couldn't get GTK+ settings")); } else { g_object_get(G_OBJECT(settings), "gtk-double-click-time", &double_click_time, NULL); } settings_taken = TRUE; } if (tool->start_time < time_micro()-double_click_time*1000) { return TRUE; } dist = distance_point_point_manhattan(&tool->start_at, to); if (ddisp->grid.snap) { real grid_x = ddisp->diagram->grid.width_x; real grid_y = ddisp->diagram->grid.width_y; if (dist > grid_x || dist > grid_y) { return TRUE; } } if (ddisplay_transform_length(ddisp, dist) > MIN_PIXELS) { return (ddisplay_transform_length(ddisp, dist) > MIN_PIXELS); } else { return FALSE; } }
/** Calculate the width (in cm) of the gap between grid lines in dynamic * grid mode. */ static void calculate_dynamic_grid(DDisplay *ddisp, real *width_x, real *width_y) { real zoom = ddisplay_untransform_length(ddisp, 1.0); real ret, tmp; /* Twiddle zoom to make change-over appropriate */ zoom *= 5; ret = pow(10, ceil(log10(zoom))); /* dont' make it too small or huge (this is in pixels) */ tmp = ddisplay_transform_length(ddisp, ret); if (tmp < 10.0) ret *= 2.0; else if (tmp > 35.0) ret /= 2.0; *width_x = ret; *width_y = ret; }
/** Find a connectionpoint sufficiently close to the given point. * * @param ddisp The display to search * @param pos A position in the display, typically mouse position * @param notthis If not null, an object to ignore (typically the object * connecting) * @param snap_to_objects Whether snapping to objects should be in effect * in this call (anded to the display-wide setting). */ ConnectionPoint * object_find_connectpoint_display(DDisplay *ddisp, Point *pos, DiaObject *notthis, gboolean snap_to_objects) { real distance; ConnectionPoint *connectionpoint; GList *avoid = NULL; DiaObject *obj_here; distance = diagram_find_closest_connectionpoint(ddisp->diagram, &connectionpoint, pos, notthis); distance = ddisplay_transform_length(ddisp, distance); if (distance < OBJECT_CONNECT_DISTANCE) { return connectionpoint; } if (ddisp->mainpoint_magnetism && snap_to_objects) { DiaObject *parent; /* Try to find an all-object CP. */ /* Don't pick a parent, though */ avoid = g_list_prepend(avoid, notthis); for (parent = notthis->parent; parent != NULL; parent = parent->parent) { avoid = g_list_prepend(avoid, parent); } obj_here = diagram_find_clicked_object_except(ddisp->diagram, pos, 0.00001, avoid); if (obj_here != NULL) { int i; for (i = 0; i < dia_object_get_num_connections(obj_here); ++i) { if (obj_here->connections[i]->flags & CP_FLAG_ANYPLACE) { g_list_free(avoid); return obj_here->connections[i]; } } } } return NULL; }