простой зум

This commit is contained in:
2026-02-26 22:08:01 +03:00
parent 2ab6bcd408
commit 78d586ce3d

View File

@@ -186,30 +186,31 @@ fn handleCanvasZoom(canvas: *Canvas, scroll: anytype) void {
switch (action) { switch (action) {
.wheel_y => |y| { .wheel_y => |y| {
const viewport_pt = scroll.data().contentRectScale().pointFromPhysical(mouse.p); const viewport_pt = scroll.data().contentRectScale().pointFromPhysical(mouse.p);
const content_pt = dvui.Point{ var content_pt = dvui.Point{
.x = viewport_pt.x + canvas.scroll.viewport.x, .x = viewport_pt.x + canvas.scroll.viewport.x,
.y = viewport_pt.y + canvas.scroll.viewport.y, .y = viewport_pt.y + canvas.scroll.viewport.y,
}; };
const doc_pt = canvas.contentPointToDocument(content_pt, natural_scale); const doc_pt = canvas.contentPointToDocument(content_pt, natural_scale);
canvas.addZoom(y / 1000); // canvas.addZoom(y / 1000);
// canvas.multZoom(1 + y / 3000); canvas.multZoom(1 + y / 2000);
canvas.requestRedraw(); canvas.requestRedraw();
// Сдвигаем viewport так, чтобы точка под курсором (даже вне холста) не уезжала const doc_pt_after = canvas.contentPointToDocument(content_pt, natural_scale);
const new_zoom = canvas.getZoom();
const img = canvas.getZoomedImageSize(); const zoom = canvas.getZoom();
const new_content_x = (@as(f32, @floatFromInt(img.x)) + doc_pt.x * new_zoom) / natural_scale; const dx = (doc_pt_after.x - doc_pt.x) * zoom;
const new_content_y = (@as(f32, @floatFromInt(img.y)) + doc_pt.y * new_zoom) / natural_scale; const dy = (doc_pt_after.y - doc_pt.y) * zoom;
canvas.scroll.viewport.x = new_content_x - viewport_pt.x;
canvas.scroll.viewport.y = new_content_y - viewport_pt.y; canvas.scroll.viewport.x -= dx;
const viewport_rect = scroll.data().contentRect(); canvas.scroll.viewport.y -= dy;
const content_w = @as(f32, @floatFromInt(img.x + img.w)) / natural_scale; content_pt = dvui.Point{
const content_h = @as(f32, @floatFromInt(img.y + img.h)) / natural_scale; .x = viewport_pt.x + canvas.scroll.viewport.x,
const max_x = @max(0, content_w - viewport_rect.w + canvas.pos.x); .y = viewport_pt.y + canvas.scroll.viewport.y,
const max_y = @max(0, content_h - viewport_rect.h + canvas.pos.y); };
canvas.scroll.viewport.x = std.math.clamp(canvas.scroll.viewport.x, 0, max_x); const fixed = canvas.contentPointToDocument(content_pt, natural_scale);
canvas.scroll.viewport.y = std.math.clamp(canvas.scroll.viewport.y, 0, max_y);
std.debug.print("prev: {any}, after: {any}, fixed: {}\n", .{ doc_pt, doc_pt_after, fixed });
}, },
else => {}, else => {},
} }