svg_embedded_graph() and ps_embedded_graph() do not do a full redraw prior to graph rasterizing, draw only the current graph area. This avoid `overstrike` problems with superimposed text objects

This commit is contained in:
stefan schippers 2025-02-21 11:12:27 +01:00
parent 90bb42e7fa
commit 34fd430c13
5 changed files with 38 additions and 27 deletions

View File

@ -4770,8 +4770,11 @@ static void draw_images_all(void)
#endif
}
void svg_embedded_graph(FILE *fd, xRect *r, double rx1, double ry1, double rx2, double ry2)
void svg_embedded_graph(FILE *fd, int i, double rx1, double ry1, double rx2, double ry2)
{
#ifndef __unix__
xRect *r = &xctx->rect[GRIDLAYER][i];
#endif
#if HAS_CAIRO==1
Zoom_info zi;
char *ptr = NULL;
@ -4821,7 +4824,9 @@ void svg_embedded_graph(FILE *fd, xRect *r, double rx1, double ry1, double rx2,
xctx->draw_pixmap=1;
save = xctx->do_copy_area;
xctx->do_copy_area=0;
draw();
setup_graph_data(i, 0, &xctx->graph_struct);
draw_graph(i, 8 + (xctx->graph_flags & (4 | 2 | 128 | 256)), &xctx->graph_struct, NULL);
#ifdef __unix__
png_sfc = cairo_xlib_surface_create(display, xctx->save_pixmap, visual,
xctx->xrect[0].width, xctx->xrect[0].height);
@ -4834,12 +4839,9 @@ void svg_embedded_graph(FILE *fd, xRect *r, double rx1, double ry1, double rx2,
cairo_set_source_surface(ct, xctx->cairo_save_sfc, 0, 0);
cairo_set_operator(ct, CAIRO_OPERATOR_SOURCE);
cairo_paint(ct);
for(int i = 0; i < xctx->rects[GRIDLAYER]; ++i) {
xRect *r = &xctx->rect[GRIDLAYER][i];
if(r->flags & 1) {
setup_graph_data(i, 0, &xctx->graph_struct);
draw_graph(i, 8 + (xctx->graph_flags & (4 | 2 | 128 | 256)), &xctx->graph_struct, (void *)ct);
}
if(r->flags & 1) {
setup_graph_data(i, 0, &xctx->graph_struct);
draw_graph(i, 8 + (xctx->graph_flags & (4 | 2 | 128 | 256)), &xctx->graph_struct, (void *)ct);
}
#endif
closure.buffer = NULL;

View File

@ -250,8 +250,9 @@ static int ps_embedded_image(xRect* r, double x1, double y1, double x2, double y
return 1;
}
static int ps_embedded_graph(xRect* r, double rx1, double ry1, double rx2, double ry2)
static int ps_embedded_graph(int i, double rx1, double ry1, double rx2, double ry2)
{
xRect *r = &xctx->rect[GRIDLAYER][i];
#if defined(HAS_LIBJPEG) && HAS_CAIRO==1
Zoom_info zi;
double rw, rh, scale;
@ -269,7 +270,7 @@ static int ps_embedded_graph(xRect* r, double rx1, double ry1, double rx2, doubl
int quality=40;
const char *quality_attr;
size_t oLength;
int i;
int j;
double sx1, sy1, sx2, sy2;
/* screen position */
@ -323,7 +324,9 @@ static int ps_embedded_graph(xRect* r, double rx1, double ry1, double rx2, doubl
d_c = tclgetboolvar("dark_colorscheme");
tclsetboolvar("dark_colorscheme", 0);
build_colors(0, 0);
draw();
setup_graph_data(i, 0, &xctx->graph_struct);
draw_graph(i, 8 + (xctx->graph_flags & (4 | 2 | 128 | 256)), &xctx->graph_struct, NULL);
dbg(1, "width=%d, rwi=%d height=%d rhi=%d\n", xctx->xrect[0].width, rwi, xctx->xrect[0].height, rhi);
#ifdef __unix__
png_sfc = cairo_xlib_surface_create(display, xctx->save_pixmap, visual,
@ -337,13 +340,8 @@ static int ps_embedded_graph(xRect* r, double rx1, double ry1, double rx2, doubl
cairo_set_source_surface(ct, xctx->cairo_save_sfc, 0, 0);
cairo_set_operator(ct, CAIRO_OPERATOR_SOURCE);
cairo_paint(ct);
for (i = 0; i < xctx->rects[GRIDLAYER]; ++i) {
xRect* r2 = &xctx->rect[GRIDLAYER][i];
if (r2->flags & 1) {
setup_graph_data(i, 0, &xctx->graph_struct);
draw_graph(i, 8 + (xctx->graph_flags & (4 | 2 | 128 | 256)), &xctx->graph_struct, (void *)ct);
}
}
setup_graph_data(i, 0, &xctx->graph_struct);
draw_graph(i, 8 + (xctx->graph_flags & (4 | 2 | 128 | 256)), &xctx->graph_struct, (void *)ct);
#endif
cairo_image_surface_write_to_jpeg_mem(png_sfc, &jpgData, &fileSize, quality);
@ -382,10 +380,10 @@ static int ps_embedded_graph(xRect* r, double rx1, double ry1, double rx2, doubl
fprintf(fd, "} exec\n");
#if 1 /* break lines */
for (i = 0; i < oLength; ++i)
for (j = 0; j < oLength; ++j)
{
fputc(ascii85EncodedJpeg[i],fd);
if(i > 0 && (i % 64) == 0)
fputc(ascii85EncodedJpeg[j],fd);
if(j > 0 && (j % 64) == 0)
{
fputc('\n',fd);
/* if (ascii85Encode[i+1]=='%') idx=63; imageMagic does this for some reason?!
@ -1449,8 +1447,8 @@ void create_ps(char **psfile, int what, int fullzoom, int eps)
continue;
}
if (c == GRIDLAYER && (xctx->rect[c][i].flags & 1)) { /* graph */
xRect* r = &xctx->rect[c][i];
ps_embedded_graph(r, r->x1, r->y1, r->x2, r->y2);
xRect *r = &xctx->rect[c][i];
ps_embedded_graph(i, r->x1, r->y1, r->x2, r->y2);
}
if(c != GRIDLAYER || !(xctx->rect[c][i].flags & 1) ) {
ps_filledrect(c, xctx->rect[c][i].x1, xctx->rect[c][i].y1,

View File

@ -1035,7 +1035,7 @@ void svg_draw(void)
{
if(xctx->rect[c][i].flags & 1) { /* graph */
xRect *r = &xctx->rect[c][i];
svg_embedded_graph(fd, r, r->x1, r->y1, r->x2, r->y2);
svg_embedded_graph(fd, i, r->x1, r->y1, r->x2, r->y2);
}
}
}

View File

@ -1329,7 +1329,7 @@ extern int process_options(int argc, char **argv);
extern void calc_drawing_bbox(xRect *boundbox, int selected);
extern int ps_draw(int what, int fullzoom, int eps);
extern void svg_draw(void);
extern void svg_embedded_graph(FILE *fd, xRect *r, double rx1, double ry1, double rx2, double ry2);
extern void svg_embedded_graph(FILE *fd, int i, double rx1, double ry1, double rx2, double ry2);
extern void set_viewport_size(int w, int h, double lw);
extern void print_image();
extern const char *get_trailing_path(const char *str, int no_of_dir, int skip_ext);

View File

@ -8412,9 +8412,20 @@ proc build_widgets { {topwin {} } } {
-variable intuitive_interface -selectcolor $selectcolor \
-command {xschem set intuitive_interface $intuitive_interface}
$topwin.menubar.option add checkbutton -label "Draw crosshair" \
-variable draw_crosshair -selectcolor $selectcolor -accelerator {Alt-X}
$topwin.menubar.option add cascade -label "Crosshair" \
-menu $topwin.menubar.option.crosshair
menu $topwin.menubar.option.crosshair -tearoff 0
$topwin.menubar.option.crosshair add checkbutton -label "Draw snap cursor" \
-variable snap_cursor -selectcolor $selectcolor
$topwin.menubar.option.crosshair add checkbutton -label "Draw crosshair" \
-variable draw_crosshair -selectcolor $selectcolor -accelerator {Alt-X}
$topwin.menubar.option.crosshair add command -label "Crosshair size" \
-command {
input_line "Enter crosshair size (int, 0 = full screen width):" \
"set crosshair_size" $crosshair_size
}
$topwin.menubar.option add command -label "Replace \[ and \] for buses in SPICE netlist" \
-command {
input_line "Enter two characters to replace default bus \[\] delimiters:" "set bus_replacement_char"