mirror of
https://github.com/ghostty-org/ghostty.git
synced 2025-07-17 09:16:11 +03:00
apprt/embedded: API to read text can get top left/bottom right coords
This commit is contained in:
@ -366,8 +366,15 @@ typedef enum {
|
|||||||
GHOSTTY_POINT_SURFACE,
|
GHOSTTY_POINT_SURFACE,
|
||||||
} ghostty_point_tag_e;
|
} ghostty_point_tag_e;
|
||||||
|
|
||||||
|
typedef enum {
|
||||||
|
GHOSTTY_POINT_COORD_EXACT,
|
||||||
|
GHOSTTY_POINT_COORD_TOP_LEFT,
|
||||||
|
GHOSTTY_POINT_COORD_BOTTOM_RIGHT,
|
||||||
|
} ghostty_point_coord_e;
|
||||||
|
|
||||||
typedef struct {
|
typedef struct {
|
||||||
ghostty_point_tag_e tag;
|
ghostty_point_tag_e tag;
|
||||||
|
ghostty_point_coord_e coord;
|
||||||
uint32_t x;
|
uint32_t x;
|
||||||
uint32_t y;
|
uint32_t y;
|
||||||
} ghostty_point_s;
|
} ghostty_point_s;
|
||||||
|
@ -1166,6 +1166,7 @@ pub const CAPI = struct {
|
|||||||
// ghostty_point_s
|
// ghostty_point_s
|
||||||
const Point = extern struct {
|
const Point = extern struct {
|
||||||
tag: Tag,
|
tag: Tag,
|
||||||
|
coord_tag: CoordTag,
|
||||||
x: u32,
|
x: u32,
|
||||||
y: u32,
|
y: u32,
|
||||||
|
|
||||||
@ -1176,27 +1177,51 @@ pub const CAPI = struct {
|
|||||||
history = 3,
|
history = 3,
|
||||||
};
|
};
|
||||||
|
|
||||||
fn core(self: Point) terminal.Point {
|
const CoordTag = enum(c_int) {
|
||||||
// This comes from the C API so we can't trust the input.
|
exact = 0,
|
||||||
const pt_x = std.math.cast(
|
top_left = 1,
|
||||||
terminal.size.CellCountInt,
|
bottom_right = 2,
|
||||||
self.x,
|
};
|
||||||
) orelse std.math.maxInt(terminal.size.CellCountInt);
|
|
||||||
|
|
||||||
return switch (self.tag) {
|
fn pin(
|
||||||
inline else => |tag| @unionInit(
|
self: Point,
|
||||||
terminal.Point,
|
screen: *const terminal.Screen,
|
||||||
|
) ?terminal.Pin {
|
||||||
|
// The core point tag.
|
||||||
|
const tag: terminal.point.Tag = switch (self.tag) {
|
||||||
|
inline else => |tag| @field(
|
||||||
|
terminal.point.Tag,
|
||||||
@tagName(tag),
|
@tagName(tag),
|
||||||
.{ .x = pt_x, .y = self.y },
|
|
||||||
),
|
),
|
||||||
};
|
};
|
||||||
}
|
|
||||||
|
|
||||||
fn clamp(self: Point, screen: *const terminal.Screen) Point {
|
|
||||||
// Clamp our point to the screen bounds.
|
// Clamp our point to the screen bounds.
|
||||||
const clamped_x = @min(self.x, screen.pages.cols -| 1);
|
const clamped_x = @min(self.x, screen.pages.cols -| 1);
|
||||||
const clamped_y = @min(self.y, screen.pages.rows -| 1);
|
const clamped_y = @min(self.y, screen.pages.rows -| 1);
|
||||||
return .{ .tag = self.tag, .x = clamped_x, .y = clamped_y };
|
|
||||||
|
return switch (self.coord_tag) {
|
||||||
|
// Exact coordinates require a specific pin.
|
||||||
|
.exact => exact: {
|
||||||
|
const pt_x = std.math.cast(
|
||||||
|
terminal.size.CellCountInt,
|
||||||
|
clamped_x,
|
||||||
|
) orelse std.math.maxInt(terminal.size.CellCountInt);
|
||||||
|
|
||||||
|
const pt: terminal.Point = switch (tag) {
|
||||||
|
inline else => |v| @unionInit(
|
||||||
|
terminal.Point,
|
||||||
|
@tagName(v),
|
||||||
|
.{ .x = pt_x, .y = clamped_y },
|
||||||
|
),
|
||||||
|
};
|
||||||
|
|
||||||
|
break :exact screen.pages.pin(pt) orelse null;
|
||||||
|
},
|
||||||
|
|
||||||
|
.top_left => screen.pages.getTopLeft(tag),
|
||||||
|
|
||||||
|
.bottom_right => screen.pages.getBottomRight(tag),
|
||||||
|
};
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -1212,12 +1237,8 @@ pub const CAPI = struct {
|
|||||||
) ?terminal.Selection {
|
) ?terminal.Selection {
|
||||||
return .{
|
return .{
|
||||||
.bounds = .{ .untracked = .{
|
.bounds = .{ .untracked = .{
|
||||||
.start = screen.pages.pin(
|
.start = self.tl.pin(screen) orelse return null,
|
||||||
self.tl.clamp(screen).core(),
|
.end = self.br.pin(screen) orelse return null,
|
||||||
) orelse return null,
|
|
||||||
.end = screen.pages.pin(
|
|
||||||
self.br.clamp(screen).core(),
|
|
||||||
) orelse return null,
|
|
||||||
} },
|
} },
|
||||||
.rectangle = self.rectangle,
|
.rectangle = self.rectangle,
|
||||||
};
|
};
|
||||||
|
Reference in New Issue
Block a user