aboutsummaryrefslogtreecommitdiff
path: root/vendor/libghostty-vt/pkg/macos/foundation/attributed_string.zig
diff options
context:
space:
mode:
authorCan Celik <ogulcancelik@gmail.com>2026-04-04 19:22:04 +0300
committerCan Celik <ogulcancelik@gmail.com>2026-04-05 01:23:06 +0300
commit41dd733ca7123c9ac4bfc6c781697a660e95b052 (patch)
tree3fc91815ca139ef2e0b281bba0abda4ef15175f4 /vendor/libghostty-vt/pkg/macos/foundation/attributed_string.zig
parent55c138263e190a1e79d4b997bfb9397306c0ec1f (diff)
feat: finish ghostty pane backend integration
Diffstat (limited to 'vendor/libghostty-vt/pkg/macos/foundation/attributed_string.zig')
-rw-r--r--vendor/libghostty-vt/pkg/macos/foundation/attributed_string.zig103
1 files changed, 103 insertions, 0 deletions
diff --git a/vendor/libghostty-vt/pkg/macos/foundation/attributed_string.zig b/vendor/libghostty-vt/pkg/macos/foundation/attributed_string.zig
new file mode 100644
index 00000000..c7f27d7d
--- /dev/null
+++ b/vendor/libghostty-vt/pkg/macos/foundation/attributed_string.zig
@@ -0,0 +1,103 @@
+const std = @import("std");
+const assert = std.debug.assert;
+const Allocator = std.mem.Allocator;
+const foundation = @import("../foundation.zig");
+const text = @import("../text.zig");
+const c = @import("c.zig").c;
+
+pub const AttributedString = opaque {
+ pub fn create(
+ str: *foundation.String,
+ attributes: *foundation.Dictionary,
+ ) Allocator.Error!*AttributedString {
+ return @ptrCast(@constCast(c.CFAttributedStringCreate(
+ null,
+ @ptrCast(str),
+ @ptrCast(attributes),
+ ) orelse return Allocator.Error.OutOfMemory));
+ }
+
+ pub fn release(self: *AttributedString) void {
+ foundation.CFRelease(self);
+ }
+
+ pub fn getLength(self: *AttributedString) usize {
+ return @intCast(c.CFAttributedStringGetLength(@ptrCast(self)));
+ }
+
+ pub fn getString(self: *AttributedString) *foundation.String {
+ return @ptrFromInt(@intFromPtr(
+ c.CFAttributedStringGetString(@ptrCast(self)),
+ ));
+ }
+};
+
+pub const MutableAttributedString = opaque {
+ pub fn create(cap: usize) Allocator.Error!*MutableAttributedString {
+ return @as(
+ ?*MutableAttributedString,
+ @ptrFromInt(@intFromPtr(c.CFAttributedStringCreateMutable(
+ null,
+ @intCast(cap),
+ ))),
+ ) orelse Allocator.Error.OutOfMemory;
+ }
+
+ pub fn release(self: *MutableAttributedString) void {
+ foundation.CFRelease(self);
+ }
+
+ pub fn replaceString(
+ self: *MutableAttributedString,
+ range: foundation.Range,
+ replacement: *foundation.String,
+ ) void {
+ c.CFAttributedStringReplaceString(
+ @ptrCast(self),
+ @bitCast(range),
+ @ptrCast(replacement),
+ );
+ }
+
+ pub fn setAttribute(
+ self: *MutableAttributedString,
+ range: foundation.Range,
+ key: anytype,
+ value: ?*anyopaque,
+ ) void {
+ const T = @TypeOf(key);
+ const info = @typeInfo(T);
+ const Key = if (info != .pointer) T else info.pointer.child;
+ const key_arg = if (@hasDecl(Key, "key"))
+ key.key()
+ else
+ key;
+
+ c.CFAttributedStringSetAttribute(
+ @ptrCast(self),
+ @bitCast(range),
+ @ptrCast(key_arg),
+ value,
+ );
+ }
+
+ pub fn getLength(self: *MutableAttributedString) usize {
+ return @intCast(c.CFAttributedStringGetLength(@ptrCast(self)));
+ }
+};
+
+test "mutable attributed string" {
+ //const testing = std.testing;
+
+ const str = try MutableAttributedString.create(0);
+ defer str.release();
+
+ {
+ const rep = try foundation.String.createWithBytes("hello", .utf8, false);
+ defer rep.release();
+ str.replaceString(foundation.Range.init(0, 0), rep);
+ }
+
+ str.setAttribute(foundation.Range.init(0, 0), text.FontAttribute.url, null);
+ str.setAttribute(foundation.Range.init(0, 0), text.FontAttribute.name.key(), null);
+}