@gtkx/react 1.0.0-rc.3 → 1.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (203) hide show
  1. package/README.md +8 -9
  2. package/dist/adw/config.d.ts +1 -0
  3. package/dist/adw/config.d.ts.map +1 -1
  4. package/dist/adw/config.js +1 -0
  5. package/dist/adw/config.js.map +1 -1
  6. package/dist/adw/dialog.d.ts +4 -4
  7. package/dist/adw/dialog.d.ts.map +1 -1
  8. package/dist/adw/dialog.js +16 -21
  9. package/dist/adw/dialog.js.map +1 -1
  10. package/dist/adw/element-behaviors.js +104 -57
  11. package/dist/adw/element-behaviors.js.map +1 -1
  12. package/dist/adw/element-config.d.ts +0 -5
  13. package/dist/adw/element-config.d.ts.map +1 -1
  14. package/dist/adw/element-config.js +25 -26
  15. package/dist/adw/element-config.js.map +1 -1
  16. package/dist/adw/index.d.ts +1 -0
  17. package/dist/adw/index.d.ts.map +1 -1
  18. package/dist/adw/index.js +1 -0
  19. package/dist/adw/index.js.map +1 -1
  20. package/dist/adw/prop-types.d.ts +35 -4
  21. package/dist/adw/prop-types.d.ts.map +1 -1
  22. package/dist/adw/prop-types.js.map +1 -1
  23. package/dist/bootstrap.js +1 -1
  24. package/dist/bootstrap.js.map +1 -1
  25. package/dist/components/application-window.d.ts +5 -0
  26. package/dist/components/application-window.d.ts.map +1 -0
  27. package/dist/components/application-window.js +7 -0
  28. package/dist/components/application-window.js.map +1 -0
  29. package/dist/components/application.d.ts +3 -8
  30. package/dist/components/application.d.ts.map +1 -1
  31. package/dist/components/application.js +22 -6
  32. package/dist/components/application.js.map +1 -1
  33. package/dist/components/element.d.ts +13 -2
  34. package/dist/components/element.d.ts.map +1 -1
  35. package/dist/components/element.js +39 -15
  36. package/dist/components/element.js.map +1 -1
  37. package/dist/components/portaled.d.ts +5 -0
  38. package/dist/components/portaled.d.ts.map +1 -0
  39. package/dist/components/portaled.js +8 -0
  40. package/dist/components/portaled.js.map +1 -0
  41. package/dist/components/window.d.ts +6 -5
  42. package/dist/components/window.d.ts.map +1 -1
  43. package/dist/components/window.js +17 -16
  44. package/dist/components/window.js.map +1 -1
  45. package/dist/config.d.ts +7 -2
  46. package/dist/config.d.ts.map +1 -1
  47. package/dist/config.js +5 -1
  48. package/dist/config.js.map +1 -1
  49. package/dist/element-behaviors.js +11 -2
  50. package/dist/element-behaviors.js.map +1 -1
  51. package/dist/element-config.d.ts +4 -3
  52. package/dist/element-config.d.ts.map +1 -1
  53. package/dist/element-config.js +19 -15
  54. package/dist/element-config.js.map +1 -1
  55. package/dist/hooks/use-bind-setting.d.ts +8 -7
  56. package/dist/hooks/use-bind-setting.d.ts.map +1 -1
  57. package/dist/hooks/use-bind-setting.js +2 -7
  58. package/dist/hooks/use-bind-setting.js.map +1 -1
  59. package/dist/hooks/use-merged-refs.d.ts +1 -4
  60. package/dist/hooks/use-merged-refs.d.ts.map +1 -1
  61. package/dist/hooks/use-merged-refs.js +1 -1
  62. package/dist/hooks/use-merged-refs.js.map +1 -1
  63. package/dist/hooks/use-parent-window.d.ts +3 -1
  64. package/dist/hooks/use-parent-window.d.ts.map +1 -1
  65. package/dist/hooks/use-parent-window.js +3 -1
  66. package/dist/hooks/use-parent-window.js.map +1 -1
  67. package/dist/hooks/use-presented-instance.d.ts +12 -0
  68. package/dist/hooks/use-presented-instance.d.ts.map +1 -0
  69. package/dist/hooks/use-presented-instance.js +27 -0
  70. package/dist/hooks/use-presented-instance.js.map +1 -0
  71. package/dist/hooks/use-property.d.ts +4 -3
  72. package/dist/hooks/use-property.d.ts.map +1 -1
  73. package/dist/hooks/use-property.js +1 -2
  74. package/dist/hooks/use-property.js.map +1 -1
  75. package/dist/hooks/use-setting.d.ts +2 -3
  76. package/dist/hooks/use-setting.d.ts.map +1 -1
  77. package/dist/hooks/use-setting.js +2 -3
  78. package/dist/hooks/use-setting.js.map +1 -1
  79. package/dist/hooks/use-signal.d.ts +15 -8
  80. package/dist/hooks/use-signal.d.ts.map +1 -1
  81. package/dist/hooks/use-signal.js +6 -8
  82. package/dist/hooks/use-signal.js.map +1 -1
  83. package/dist/index.d.ts +10 -2
  84. package/dist/index.d.ts.map +1 -1
  85. package/dist/index.js +8 -0
  86. package/dist/index.js.map +1 -1
  87. package/dist/internal.d.ts +8 -5
  88. package/dist/internal.d.ts.map +1 -1
  89. package/dist/internal.js +7 -5
  90. package/dist/internal.js.map +1 -1
  91. package/dist/prop-types.d.ts +88 -4
  92. package/dist/prop-types.d.ts.map +1 -1
  93. package/dist/prop-types.js.map +1 -1
  94. package/dist/reconciler/apply-props.d.ts +4 -4
  95. package/dist/reconciler/apply-props.d.ts.map +1 -1
  96. package/dist/reconciler/apply-props.js +62 -20
  97. package/dist/reconciler/apply-props.js.map +1 -1
  98. package/dist/reconciler/behaviors.d.ts +9 -20
  99. package/dist/reconciler/behaviors.d.ts.map +1 -1
  100. package/dist/reconciler/behaviors.js +44 -41
  101. package/dist/reconciler/behaviors.js.map +1 -1
  102. package/dist/reconciler/devtools.d.ts +6 -0
  103. package/dist/reconciler/devtools.d.ts.map +1 -0
  104. package/dist/reconciler/devtools.js +11 -0
  105. package/dist/reconciler/devtools.js.map +1 -0
  106. package/dist/reconciler/host-config.d.ts +1 -1
  107. package/dist/reconciler/host-config.d.ts.map +1 -1
  108. package/dist/reconciler/host-config.js +17 -26
  109. package/dist/reconciler/host-config.js.map +1 -1
  110. package/dist/reconciler/instance.d.ts.map +1 -1
  111. package/dist/reconciler/instance.js +6 -4
  112. package/dist/reconciler/instance.js.map +1 -1
  113. package/dist/reconciler/metadata.d.ts +2 -2
  114. package/dist/reconciler/metadata.d.ts.map +1 -1
  115. package/dist/reconciler/metadata.js +9 -11
  116. package/dist/reconciler/metadata.js.map +1 -1
  117. package/dist/reconciler/node.d.ts +4 -3
  118. package/dist/reconciler/node.d.ts.map +1 -1
  119. package/dist/reconciler/node.js +8 -7
  120. package/dist/reconciler/node.js.map +1 -1
  121. package/dist/reconciler/placement.js +20 -20
  122. package/dist/reconciler/placement.js.map +1 -1
  123. package/dist/reconciler/registry.d.ts +46 -32
  124. package/dist/reconciler/registry.d.ts.map +1 -1
  125. package/dist/reconciler/registry.js +10 -19
  126. package/dist/reconciler/registry.js.map +1 -1
  127. package/dist/reconciler/root-element.d.ts +1 -1
  128. package/dist/reconciler/root-element.d.ts.map +1 -1
  129. package/dist/reconciler/root-element.js +0 -1
  130. package/dist/reconciler/root-element.js.map +1 -1
  131. package/dist/reconciler/root.d.ts +9 -20
  132. package/dist/reconciler/root.d.ts.map +1 -1
  133. package/dist/reconciler/root.js +6 -19
  134. package/dist/reconciler/root.js.map +1 -1
  135. package/dist/reconciler/signals.d.ts +1 -2
  136. package/dist/reconciler/signals.d.ts.map +1 -1
  137. package/dist/reconciler/signals.js +3 -3
  138. package/dist/reconciler/signals.js.map +1 -1
  139. package/dist/reconciler/text.js +5 -5
  140. package/dist/reconciler/text.js.map +1 -1
  141. package/dist/utils/accessible-props.d.ts +57 -9
  142. package/dist/utils/accessible-props.d.ts.map +1 -1
  143. package/dist/utils/accessible-props.js +11 -13
  144. package/dist/utils/accessible-props.js.map +1 -1
  145. package/dist/utils/ref-prop.d.ts +0 -6
  146. package/dist/utils/ref-prop.d.ts.map +1 -1
  147. package/dist/utils/ref-prop.js +0 -6
  148. package/dist/utils/ref-prop.js.map +1 -1
  149. package/dist/utils/settings.d.ts +7 -0
  150. package/dist/utils/settings.d.ts.map +1 -1
  151. package/dist/utils/settings.js.map +1 -1
  152. package/dist/utils/variant.d.ts +33 -1
  153. package/dist/utils/variant.d.ts.map +1 -1
  154. package/dist/utils/variant.js.map +1 -1
  155. package/env.d.ts +11 -4
  156. package/package.json +5 -5
  157. package/src/adw/config.ts +1 -0
  158. package/src/adw/dialog.tsx +23 -25
  159. package/src/adw/element-behaviors.ts +131 -60
  160. package/src/adw/element-config.ts +25 -26
  161. package/src/adw/index.ts +1 -0
  162. package/src/adw/prop-types.ts +36 -3
  163. package/src/bootstrap.ts +1 -1
  164. package/src/components/application-window.tsx +10 -0
  165. package/src/components/application.tsx +32 -5
  166. package/src/components/element.tsx +52 -17
  167. package/src/components/portaled.tsx +14 -0
  168. package/src/components/window.tsx +25 -23
  169. package/src/config.ts +13 -8
  170. package/src/element-behaviors.ts +20 -1
  171. package/src/element-config.ts +19 -15
  172. package/src/hooks/use-bind-setting.ts +8 -7
  173. package/src/hooks/use-merged-refs.ts +1 -1
  174. package/src/hooks/use-parent-window.ts +3 -1
  175. package/src/hooks/use-presented-instance.tsx +50 -0
  176. package/src/hooks/use-property.ts +4 -3
  177. package/src/hooks/use-setting.ts +2 -3
  178. package/src/hooks/use-signal.ts +18 -11
  179. package/src/index.ts +10 -2
  180. package/src/internal.ts +8 -5
  181. package/src/prop-types.ts +119 -11
  182. package/src/reconciler/apply-props.ts +77 -24
  183. package/src/reconciler/behaviors.ts +77 -50
  184. package/src/reconciler/devtools.ts +18 -0
  185. package/src/reconciler/host-config.ts +20 -32
  186. package/src/reconciler/instance.ts +7 -4
  187. package/src/reconciler/metadata.ts +11 -14
  188. package/src/reconciler/node.ts +12 -9
  189. package/src/reconciler/placement.ts +25 -25
  190. package/src/reconciler/registry.ts +56 -39
  191. package/src/reconciler/root-element.ts +4 -2
  192. package/src/reconciler/root.ts +12 -20
  193. package/src/reconciler/signals.ts +2 -3
  194. package/src/reconciler/text.ts +6 -6
  195. package/src/utils/accessible-props.ts +70 -25
  196. package/src/utils/ref-prop.ts +0 -6
  197. package/src/utils/settings.ts +7 -0
  198. package/src/utils/variant.ts +33 -1
  199. package/dist/utils/accessible-metadata.d.ts +0 -12
  200. package/dist/utils/accessible-metadata.d.ts.map +0 -1
  201. package/dist/utils/accessible-metadata.js +0 -25
  202. package/dist/utils/accessible-metadata.js.map +0 -1
  203. package/src/utils/accessible-metadata.ts +0 -31
@@ -4,7 +4,6 @@ const SINGLE_CHILD_TYPES: string[] = [
4
4
  "GtkAspectFrame",
5
5
  "GtkButton",
6
6
  "GtkCheckButton",
7
- "GtkComboBox",
8
7
  "GtkDragIcon",
9
8
  "GtkExpander",
10
9
  "GtkFlowBoxChild",
@@ -25,14 +24,15 @@ const SINGLE_CHILD_TYPES: string[] = [
25
24
  ];
26
25
 
27
26
  /**
28
- * The static, runtime-free half of the built-in element configuration: which base props interface each
29
- * generated element extends, which component wraps it, and whether its GObject is created lazily by its
30
- * parent. Codegen imports this module, so it must never reach the GObject bindings.
27
+ * The framework's own element configuration for the GTK types it customizes: the base props interface each
28
+ * generated element extends, the component that wraps it, the GObject properties left out of its generated
29
+ * props, and whether its GObject is created by its parent. Carries no behaviors, so importing it never
30
+ * reaches the GObject bindings.
31
31
  */
32
32
  const BUILTIN_ELEMENTS: Record<string, ElementConfig> = {
33
33
  ...forTypes(SINGLE_CHILD_TYPES, {
34
34
  props: internal("ChildrenProps"),
35
- omitProps: ["child"],
35
+ omittedProps: ["child"],
36
36
  }),
37
37
  ...forTypes(["GtkHeaderBar", "GtkActionBar"], {
38
38
  props: internal("GtkHeaderBarProps"),
@@ -40,7 +40,10 @@ const BUILTIN_ELEMENTS: Record<string, ElementConfig> = {
40
40
  GtkWindow: {
41
41
  props: internal("ChildrenProps"),
42
42
  component: internal("createWindowComponent"),
43
- omitProps: ["child"],
43
+ omittedProps: ["child"],
44
+ },
45
+ GtkApplicationWindow: {
46
+ component: internal("createApplicationWindowComponent"),
44
47
  },
45
48
  GtkLabel: {
46
49
  props: internal("ChildrenProps"),
@@ -55,22 +58,22 @@ const BUILTIN_ELEMENTS: Record<string, ElementConfig> = {
55
58
  props: internal("GtkTextChildAnchorProps"),
56
59
  },
57
60
  GtkGridLayoutChild: {
58
- lazy: true,
61
+ isLazy: true,
59
62
  },
60
63
  GtkFixedLayoutChild: {
61
- lazy: true,
64
+ isLazy: true,
62
65
  },
63
66
  GtkOverlayLayoutChild: {
64
- lazy: true,
67
+ isLazy: true,
65
68
  },
66
69
  GtkStackPage: {
67
- lazy: true,
70
+ isLazy: true,
68
71
  },
69
72
  GtkNotebookPage: {
70
- lazy: true,
73
+ isLazy: true,
71
74
  },
72
75
  GActionGroup: {
73
- props: internal("GActionGroupProps"),
76
+ props: internal("ActionGroupProps"),
74
77
  },
75
78
  GtkWidget: {
76
79
  props: internal("GtkWidgetProps"),
@@ -86,7 +89,7 @@ const BUILTIN_ELEMENTS: Record<string, ElementConfig> = {
86
89
  },
87
90
  GtkOverlay: {
88
91
  props: internal("GtkOverlayProps"),
89
- omitProps: ["child"],
92
+ omittedProps: ["child"],
90
93
  },
91
94
  GtkShortcutController: {
92
95
  props: internal("GtkShortcutControllerProps"),
@@ -95,10 +98,10 @@ const BUILTIN_ELEMENTS: Record<string, ElementConfig> = {
95
98
  props: internal("ChildrenProps"),
96
99
  },
97
100
  GActionMap: {
98
- props: internal("GActionMapProps"),
101
+ props: internal("ActionMapProps"),
99
102
  },
100
103
  GMenu: {
101
- props: internal("GMenuProps"),
104
+ props: internal("MenuProps"),
102
105
  },
103
106
  GtkColumnView: {
104
107
  props: internal("ChildrenProps"),
@@ -111,6 +114,7 @@ const BUILTIN_ELEMENTS: Record<string, ElementConfig> = {
111
114
  },
112
115
  GtkSizeGroup: {
113
116
  props: internal("GtkSizeGroupProps"),
117
+ component: internal("createPortaledComponent"),
114
118
  },
115
119
  GtkConstraintLayout: {
116
120
  props: internal("GtkConstraintLayoutProps"),
@@ -6,22 +6,23 @@ import type { SettingsSchema, SettingsSchemaKeys } from "../utils/settings.js";
6
6
  import { type RefProp, resolveRefProp } from "../utils/ref-prop.js";
7
7
  import { useSettings } from "./use-setting.js";
8
8
 
9
+ /** Options for {@link useBindSetting}. */
9
10
  type UseBindSettingOptions<K extends SettingsSchemaKeys> = {
11
+ /** Schema the settings object is opened from. */
10
12
  schema: SettingsSchema<K>;
13
+ /** Key of that schema to bind. */
11
14
  key: keyof K & string;
15
+ /** Object holding the property, given directly or as a ref; nothing is bound while it is absent. */
12
16
  object: RefProp<GObject.Object>;
17
+ /** camelCase name of the property to keep in sync with the key. */
13
18
  property: string;
19
+ /** Direction and conversion behavior of the bind; defaults to `Gio.SettingsBindFlags.DEFAULT`. */
14
20
  flags?: Gio.SettingsBindFlags;
15
21
  };
16
22
 
17
23
  /**
18
- * Binds a GSettings key to a property of a GObject, keeping the two in sync for the object's lifetime.
19
- *
20
- * @param options.schema The schema reference identifying the settings backend.
21
- * @param options.key The key within the schema to bind.
22
- * @param options.object The GObject whose property is bound to the setting.
23
- * @param options.property The name of the object property to bind.
24
- * @param options.flags Flags controlling the binding's direction and behaviour.
24
+ * Binds a GSettings key to a property of a GObject, keeping the two in sync until the component unmounts.
25
+ * `property` is given in camelCase, and `flags` defaults to `Gio.SettingsBindFlags.DEFAULT`, a two-way bind.
25
26
  */
26
27
  function useBindSetting<K extends SettingsSchemaKeys>({
27
28
  schema,
@@ -61,4 +61,4 @@ function useMergedRef<T>(first: PossibleRef<T>, second: PossibleRef<T>): RefCall
61
61
  return useMemo(() => mergeRefs(first, second), [first, second]);
62
62
  }
63
63
 
64
- export { assignRef, mergeRefs, useMergedRef };
64
+ export { useMergedRef };
@@ -4,7 +4,9 @@ import { type Context, createContext, use } from "react";
4
4
  const ParentWindowContext: Context<Gtk.Window | null> = createContext<Gtk.Window | null>(null);
5
5
 
6
6
  /**
7
- * Returns the `Gtk.Window` provided by the nearest window ancestor, or `null` when there is none.
7
+ * Returns the `Gtk.Window` of the nearest window ancestor. This is `null` on the first render even inside a
8
+ * window, because a window provides itself only once its GObject exists, and stays `null` outside one. The
9
+ * component re-renders when it resolves, so derive from the value rather than reading it once.
8
10
  */
9
11
  const useParentWindow = (): Gtk.Window | null => use(ParentWindowContext);
10
12
 
@@ -0,0 +1,50 @@
1
+ import { type ElementType, type ReactNode, type Ref, type RefCallback, useLayoutEffect, useState } from "react";
2
+ import { useMergedRef } from "./use-merged-refs.js";
3
+
4
+ type PresentedProps<T> = {
5
+ ref?: Ref<T | null> | undefined;
6
+ };
7
+
8
+ type PresentedOptions<T> = {
9
+ usePresent: () => (instance: T) => void;
10
+ dismiss: (instance: T) => void;
11
+ wrap?: (element: ReactNode, instance: T | null) => ReactNode;
12
+ };
13
+
14
+ const usePresentedInstance = <T,>(
15
+ ref: Ref<T | null> | undefined,
16
+ present: (instance: T) => void,
17
+ dismiss: (instance: T) => void,
18
+ ): [T | null, RefCallback<T>] => {
19
+ const [instance, setInstance] = useState<T | null>(null);
20
+ const mergedRef = useMergedRef(ref, setInstance);
21
+
22
+ useLayoutEffect(() => {
23
+ if (!instance) {
24
+ return;
25
+ }
26
+
27
+ present(instance);
28
+
29
+ return () => {
30
+ dismiss(instance);
31
+ };
32
+ }, [instance, present, dismiss]);
33
+
34
+ return [instance, mergedRef];
35
+ };
36
+
37
+ const createPresentedComponent = <T,>(
38
+ Component: ElementType,
39
+ options: PresentedOptions<T>,
40
+ ): ((props: PresentedProps<T>) => ReactNode) => {
41
+ return ({ ref, ...rest }: PresentedProps<T>): ReactNode => {
42
+ const present = options.usePresent();
43
+ const [instance, mergedRef] = usePresentedInstance(ref, present, options.dismiss);
44
+ const element = <Component ref={mergedRef} {...rest} />;
45
+
46
+ return options.wrap ? options.wrap(element, instance) : element;
47
+ };
48
+ };
49
+
50
+ export { createPresentedComponent, type PresentedProps };
@@ -3,15 +3,16 @@ import { kebabCase } from "@gtkx/utils";
3
3
  import type { RefProp } from "../utils/ref-prop.js";
4
4
  import { useObjectValue } from "./use-object-value.js";
5
5
 
6
+ /** The property map `T` declares, from camelCase property name to value type. */
6
7
  type Properties<T extends GObject.Object> = NonNullable<T["__properties__"]>;
8
+ /** Every property `T` declares that is also readable off the instance, in camelCase. */
7
9
  type PropertyName<T extends GObject.Object> = keyof Properties<T> & keyof T;
8
10
 
9
11
  /**
10
12
  * Subscribes to a GObject property and returns its current value, re-rendering when the property changes.
11
13
  *
12
- * @param object The GObject (or ref to one) whose property to observe.
13
14
  * @param propertyName The camelCase name of a readable property on the object.
14
- * @returns The current property value, or `undefined` when the object is not resolved.
15
+ * @returns The current value, or `undefined` while the object is null or an unresolved ref.
15
16
  */
16
17
  function useProperty<T extends GObject.Object, P extends PropertyName<T>>(
17
18
  object: RefProp<T>,
@@ -20,4 +21,4 @@ function useProperty<T extends GObject.Object, P extends PropertyName<T>>(
20
21
  return useObjectValue(object, `notify::${kebabCase(propertyName)}`, (obj) => obj?.[propertyName]);
21
22
  }
22
23
 
23
- export { useProperty, type PropertyName };
24
+ export { useProperty };
@@ -16,9 +16,8 @@ const useSettings = <K extends SettingsSchemaKeys>({ id, path }: UseSettingsProp
16
16
  /**
17
17
  * Reads and writes a single key of a GSettings schema, re-rendering when the stored value changes.
18
18
  *
19
- * @param schema The schema reference identifying the settings backend.
20
- * @param key The key within the schema to read and write.
21
- * @returns A tuple of the current value and a setter that persists a new value.
19
+ * @returns The current value, and a setter that writes a new one back to GSettings.
20
+ * @throws When the key is not declared in the schema.
22
21
  */
23
22
  function useSetting<K extends SettingsSchemaKeys, P extends keyof K>(
24
23
  schema: SettingsSchema<K>,
@@ -3,9 +3,15 @@ import type { SignalHandler } from "@gtkx/runtime";
3
3
  import { useEffectEvent, useLayoutEffect } from "react";
4
4
  import { type RefProp, resolveRefProp } from "../utils/ref-prop.js";
5
5
 
6
+ /** The signal map `T` declares, from signal name to handler signature. */
6
7
  type Signals<T extends GObject.Object> = NonNullable<T["__signals__"]>;
8
+ /** Every signal name `T` declares, on its own or narrowed by a `::detail` suffix. */
7
9
  type SignalName<T extends GObject.Object> = keyof Signals<T> | `${keyof Signals<T> & string}::${string}`;
8
10
 
11
+ /**
12
+ * The handler signature `T` declares for signal `S`, looked up through any `::detail` suffix and
13
+ * falling back to an untyped `SignalHandler` when the object declares no such signal.
14
+ */
9
15
  type TypedSignalHandler<T extends GObject.Object, S extends string> = S extends keyof Signals<T>
10
16
  ? Signals<T>[S]
11
17
  : S extends `${infer TBase}::${string}`
@@ -14,9 +20,12 @@ type TypedSignalHandler<T extends GObject.Object, S extends string> = S extends
14
20
  : SignalHandler
15
21
  : SignalHandler;
16
22
 
23
+ /** Options for {@link useSignal}. */
17
24
  type UseSignalOptions = {
18
- after?: boolean;
19
- immediate?: boolean;
25
+ /** Runs the handler after the object's own default handler rather than before it. */
26
+ isAfter?: boolean;
27
+ /** Invokes the handler once, with no arguments, as soon as the signal is connected. */
28
+ isImmediate?: boolean;
20
29
  };
21
30
 
22
31
  /**
@@ -29,16 +38,14 @@ type UseSignalOptions = {
29
38
  * runs the handler captured on the first render. Keep the calling component unwrapped, or read the values the
30
39
  * handler needs off the GObject itself. React fixes this on the 19.3 line.
31
40
  *
32
- * @param object The GObject (or ref to one) to connect to.
33
- * @param signal The signal name, optionally with a detail suffix.
34
- * @param handler The callback invoked when the signal is emitted.
35
- * @param options Connection options such as running after the default handler or invoking immediately.
41
+ * @param signal The signal name, optionally with a `::detail` suffix.
42
+ * @param options `isAfter` runs the handler after the default handler; `isImmediate` also invokes it on connect.
36
43
  */
37
44
  function useSignal<T extends GObject.Object, S extends SignalName<T> & string>(
38
45
  object: RefProp<T>,
39
46
  signal: S,
40
47
  handler: TypedSignalHandler<T, S>,
41
- { after = false, immediate = false }: UseSignalOptions = {},
48
+ { isAfter = false, isImmediate = false }: UseSignalOptions = {},
42
49
  ): void {
43
50
  const emit = useEffectEvent(handler as SignalHandler);
44
51
 
@@ -49,16 +56,16 @@ function useSignal<T extends GObject.Object, S extends SignalName<T> & string>(
49
56
  return;
50
57
  }
51
58
 
52
- resolved.on(signal, emit, after);
59
+ resolved.on(signal, emit, isAfter);
53
60
 
54
- if (immediate) {
61
+ if (isImmediate) {
55
62
  emit();
56
63
  }
57
64
 
58
65
  return () => {
59
66
  resolved.off(signal, emit);
60
67
  };
61
- }, [object, signal, after, immediate]);
68
+ }, [object, signal, isAfter, isImmediate]);
62
69
  }
63
70
 
64
- export { useSignal, type SignalName, type TypedSignalHandler };
71
+ export { useSignal };
package/src/index.ts CHANGED
@@ -1,14 +1,22 @@
1
1
  import "./bootstrap.js";
2
2
 
3
+ /** @public */
3
4
  export { useApplication } from "./hooks/use-application.js";
5
+ /** @public */
4
6
  export { useBindSetting } from "./hooks/use-bind-setting.js";
7
+ /** @public */
5
8
  export { useParentWindow } from "./hooks/use-parent-window.js";
9
+ /** @public */
6
10
  export { useProperty } from "./hooks/use-property.js";
11
+ /** @public */
7
12
  export { useSetting } from "./hooks/use-setting.js";
13
+ /** @public */
8
14
  export { useSignal } from "./hooks/use-signal.js";
9
- export type { MenuItem, VflConstraints } from "./prop-types.js";
15
+ /** @public */
10
16
  export { type RootElement, rootElement } from "./reconciler/root-element.js";
17
+ /** @public */
11
18
  export { createPortal, createRoot, quit, type Root } from "./reconciler/root.js";
19
+ /** @public */
12
20
  export type { AccessibleProps } from "./utils/accessible-props.js";
21
+ /** @public */
13
22
  export type { RefProp } from "./utils/ref-prop.js";
14
- export type { SettingsSchema, SettingsSchemaKeys, SettingValue } from "./utils/settings.js";
package/src/internal.ts CHANGED
@@ -1,14 +1,17 @@
1
1
  import "./bootstrap.js";
2
2
 
3
+ /** @internal */
4
+ export { createApplicationWindowComponent } from "./components/application-window.js";
5
+ /** @internal */
3
6
  export { createApplicationComponent } from "./components/application.js";
4
7
  export { createElementComponent } from "./components/element.js";
8
+ /** @internal */
9
+ export { createPortaledComponent } from "./components/portaled.js";
10
+ /** @internal */
5
11
  export { createWindowComponent } from "./components/window.js";
6
- export { ApplicationContext } from "./hooks/use-application.js";
7
12
  export { useMergedRef } from "./hooks/use-merged-refs.js";
8
- export { useObjectValue } from "./hooks/use-object-value.js";
9
13
  export type * from "./prop-types.js";
14
+ export { settleAccessible } from "./reconciler/apply-props.js";
10
15
  export { isRootElement } from "./reconciler/root-element.js";
11
16
  export { createReconcilerRoot, type ReconcilerRoot, setReconcilerErrorHandler } from "./reconciler/root.js";
12
- export { applyWrite } from "./reconciler/signals.js";
13
- export { getAccessibleMetadata } from "./utils/accessible-metadata.js";
14
- export { type RefProp, resolveRefProp } from "./utils/ref-prop.js";
17
+ export type { SettingsSchema, SettingsSchemaKeys, SettingValue } from "./utils/settings.js";
package/src/prop-types.ts CHANGED
@@ -1,114 +1,221 @@
1
+ /* eslint-disable gtkx/no-library-prefix */
1
2
  import type * as Gdk from "@gtkx/gi/gdk";
3
+ import type * as GLib from "@gtkx/gi/glib";
2
4
  import type * as GObject from "@gtkx/gi/gobject";
3
5
  import type * as Gtk from "@gtkx/gi/gtk";
4
6
  import type { ReactNode } from "react";
5
7
 
6
8
  /** One entry of a `GMenu`'s `items` prop; `submenu` and `section` nest further menus. */
7
9
  type MenuItem = {
10
+ /** Text shown for the entry, or the heading of the submenu or section it introduces. */
8
11
  label?: string | null;
12
+ /** Detailed action name the entry activates, ignored when `submenu` or `section` is given. */
9
13
  action?: string | null;
14
+ /** Entries of a separate menu the labelled entry opens. */
10
15
  submenu?: MenuItem[];
16
+ /** Entries appended below the label as an inline section, used only when `submenu` is absent. */
11
17
  section?: MenuItem[];
12
18
  };
13
19
 
14
20
  /** One Visual Format Language block applied to a `Gtk.ConstraintLayout`. */
15
21
  type VflConstraints = {
22
+ /** Format lines, each describing every constraint on one row or column. */
16
23
  lines: string[];
24
+ /** Default horizontal spacing the `-` operator stands for; defaults to 0. */
17
25
  hspacing?: number;
26
+ /** Default vertical spacing the `-` operator stands for; defaults to 0. */
18
27
  vspacing?: number;
28
+ /** Targets the view names in `lines` refer to; defaults to none. */
19
29
  views?: Map<string, Gtk.ConstraintTarget>;
20
30
  };
21
31
 
22
32
  /** One mark on a `Gtk.Scale`. */
23
- type ScaleMark = { value?: number; position: Gtk.PositionType; markup?: string | null };
33
+ type ScaleMark = {
34
+ /** Point on the scale the mark is drawn at; defaults to 0. */
35
+ value?: number;
36
+ /** Side of the scale the mark and its label sit on. */
37
+ position: Gtk.PositionType;
38
+ /** Pango markup drawn beside the mark, or `null` for an unlabelled one. */
39
+ markup?: string | null;
40
+ };
41
+
24
42
  /** One labelled offset on a `Gtk.LevelBar`. */
25
- type LevelBarOffset = { name: string; value?: number };
43
+ type LevelBarOffset = {
44
+ /** Style class applied to the bar's blocks while the value falls in this offset's interval. */
45
+ name: string;
46
+ /** Upper bound of that interval; defaults to 0. */
47
+ value?: number;
48
+ };
49
+
26
50
  /** One credit section on a `Gtk.AboutDialog`. */
27
- type CreditSection = { sectionName: string; people: string[] };
51
+ type CreditSection = {
52
+ /** Heading the names are listed under. */
53
+ sectionName: string;
54
+ /** Names listed in the section. */
55
+ people: string[];
56
+ };
57
+
58
+ /** One command-line option a `Gtk.Application` accepts. */
59
+ type MainOption = {
60
+ /** Name the option is spelled with after two dashes, such as `verbose` for `--verbose`. */
61
+ longName: string;
62
+ /** Single character the option is spelled with after one dash, such as `v` for `-v`; defaults to none. */
63
+ shortName?: string | null;
64
+ /** How the option itself is parsed and listed; defaults to `GLib.OptionFlags.NONE`. */
65
+ flags?: GLib.OptionFlags;
66
+ /** Type of argument the option takes; defaults to `GLib.OptionArg.NONE`, meaning it takes none. */
67
+ arg?: GLib.OptionArg;
68
+ /** Text describing the option in `--help`. */
69
+ description: string;
70
+ /** Placeholder standing for the option's argument in `--help`; defaults to none. */
71
+ argDescription?: string | null;
72
+ };
73
+
28
74
  /** One accelerator binding on a `Gtk.Application`. */
29
- type ActionAccel = { detailedActionName: string; accels: string[] };
75
+ type ActionAccel = {
76
+ /** Action the accelerators activate, such as `app.quit` or `win.open('file')`. */
77
+ detailedActionName: string;
78
+ /** Accelerators in `Gtk.acceleratorParse` syntax, cleared when the entry goes away. */
79
+ accels: string[];
80
+ };
81
+
30
82
  /** The drag icon of a `Gtk.DragSource`, with its hotspot. */
31
- type DragSourceIcon = { paintable?: Gdk.Paintable | null; hotX?: number; hotY?: number };
83
+ type DragSourceIcon = {
84
+ /** Image shown under the pointer during the drag; defaults to none. */
85
+ paintable?: Gdk.Paintable | null;
86
+ /** Horizontal offset of the pointer within the image; defaults to 0. */
87
+ hotX?: number;
88
+ /** Vertical offset of the pointer within the image; defaults to 0. */
89
+ hotY?: number;
90
+ };
32
91
 
33
92
  /** Props of an element that accepts children. */
34
93
  type ChildrenProps = {
94
+ /** Elements attached to the element's default child slot, or its text for elements that hold text. */
35
95
  children?: ReactNode;
36
96
  };
37
97
 
98
+ /** Objects a widget takes through a method call rather than a property. */
38
99
  type GtkWidgetProps = {
100
+ /** `Gtk.EventController` elements added to the widget. */
39
101
  controllers?: ReactNode | null | undefined;
102
+ /** `Gio.ActionGroup` elements inserted into the widget, each under its own `prefix`. */
40
103
  actionGroups?: ReactNode | null | undefined;
41
104
  } & ChildrenProps;
42
105
 
43
- type GActionGroupProps = {
106
+ /** Props of an action group placed in a widget's `actionGroups` slot. */
107
+ type ActionGroupProps = {
108
+ /** Prefix the group's actions are addressed by, such as `win`; defaults to the empty string. */
44
109
  prefix?: string | null | undefined;
45
110
  };
46
111
 
47
- type GActionMapProps = {
112
+ /** Props of an element implementing `Gio.ActionMap`. */
113
+ type ActionMapProps = {
114
+ /** `Gio.Action` elements added to the map, removed again by their `name`. */
48
115
  actions?: ReactNode | null | undefined;
49
116
  };
50
117
 
51
- type GMenuProps = {
118
+ /** Props of a `Gio.Menu` element. */
119
+ type MenuProps = {
120
+ /** Entries the menu is rebuilt from whenever they change. */
52
121
  items?: MenuItem[] | null | undefined;
53
122
  };
54
123
 
124
+ /** Props of a `Gtk.ShortcutController` element. */
55
125
  type GtkShortcutControllerProps = {
126
+ /** `Gtk.Shortcut` elements the controller watches for. */
56
127
  shortcuts?: ReactNode | null | undefined;
57
128
  };
58
129
 
130
+ /** Props of a `Gtk.Overlay` element, whose `children` is the widget the overlays sit above. */
59
131
  type GtkOverlayProps = {
132
+ /** Widgets stacked over the main child. */
60
133
  overlays?: ReactNode | null | undefined;
61
134
  } & ChildrenProps;
62
135
 
136
+ /** Props of a `Gtk.ConstraintLayout` element. */
63
137
  type GtkConstraintLayoutProps = {
138
+ /** `Gtk.Constraint` elements added to the layout. */
64
139
  constraints?: ReactNode | null | undefined;
140
+ /** `Gtk.ConstraintGuide` elements added to the layout as invisible spacers. */
65
141
  guides?: ReactNode | null | undefined;
142
+ /** Visual Format Language blocks whose constraints are added alongside `constraints`. */
66
143
  vfl?: VflConstraints[] | null | undefined;
67
144
  };
68
145
 
69
146
  /** Props of `GtkTextChildAnchor`, which embeds either a child widget or a paintable in a text buffer. */
70
147
  type GtkTextChildAnchorProps = {
148
+ /** Image inserted into the buffer instead of an anchored widget; giving both is an error. */
71
149
  paintable?: Gdk.Paintable | null | undefined;
72
150
  } & ChildrenProps;
73
151
 
152
+ /** Props of a `Gtk.HeaderBar` or `Gtk.ActionBar` element. */
74
153
  type GtkHeaderBarProps = {
154
+ /** Widgets packed at the start of the bar. */
75
155
  start?: ReactNode | null | undefined;
156
+ /** Widgets packed at the end of the bar. */
76
157
  end?: ReactNode | null | undefined;
77
158
  };
78
159
 
160
+ /** Props of a `Gtk.Scale` element. */
79
161
  type GtkScaleProps = {
162
+ /** Marks drawn along the scale, cleared and re-added whenever the list changes. */
80
163
  marks?: ScaleMark[] | null | undefined;
81
164
  };
82
165
 
166
+ /** Props of a `Gtk.Calendar` element. */
83
167
  type GtkCalendarProps = {
168
+ /** Days of the shown month drawn as marked, cleared and re-marked whenever the list changes. */
84
169
  markedDays?: number[] | null | undefined;
85
170
  };
86
171
 
172
+ /** Props of a `Gtk.LevelBar` element. */
87
173
  type GtkLevelBarProps = {
174
+ /** Offsets that split the bar's range into differently styled intervals. */
88
175
  offsets?: LevelBarOffset[] | null | undefined;
89
176
  };
90
177
 
178
+ /** Props of a `Gtk.SizeGroup` element. */
91
179
  type GtkSizeGroupProps = {
180
+ /** Widgets the group keeps at a common size. */
92
181
  widgets?: Gtk.Widget[] | null | undefined;
93
182
  };
94
183
 
184
+ /** Props of a `Gtk.AboutDialog` element. */
95
185
  type GtkAboutDialogProps = {
186
+ /**
187
+ * Extra sections appended to the dialog's credits. GTK offers no way to remove one, so the list
188
+ * cannot change once it has been applied.
189
+ */
96
190
  creditSections?: CreditSection[] | null | undefined;
97
191
  };
98
192
 
193
+ /** Props of a `Gtk.Application` element, whose `children` are the windows it owns. */
99
194
  type GtkApplicationProps = {
195
+ /** Accelerators bound to the application's actions. */
100
196
  actionAccels?: ActionAccel[] | null | undefined;
197
+ /**
198
+ * Command-line options the application parses, registered before it starts. GLib offers no way to
199
+ * unregister one, so the list cannot change once it has been applied.
200
+ */
201
+ mainOptions?: MainOption[] | null | undefined;
101
202
  } & ChildrenProps;
102
203
 
204
+ /** Props of a `Gtk.DropTarget` element. */
103
205
  type GtkDropTargetProps = {
206
+ /** GTypes the target accepts a drop of. */
104
207
  types?: GObject.Type[] | null | undefined;
105
208
  };
106
209
 
210
+ /** Props of a `Gtk.DrawingArea` element. */
107
211
  type GtkDrawingAreaProps = {
212
+ /** Callback that draws the area's contents; setting it queues a redraw. */
108
213
  drawFunc?: Gtk.DrawingAreaDrawFunc | null | undefined;
109
214
  };
110
215
 
216
+ /** Props of a `Gtk.DragSource` element. */
111
217
  type GtkDragSourceProps = {
218
+ /** Icon shown under the pointer while a drag started from this source is in flight. */
112
219
  icon?: DragSourceIcon | null | undefined;
113
220
  };
114
221
 
@@ -118,13 +225,14 @@ export {
118
225
  type ScaleMark,
119
226
  type LevelBarOffset,
120
227
  type CreditSection,
228
+ type MainOption,
121
229
  type ActionAccel,
122
230
  type DragSourceIcon,
123
231
  type ChildrenProps,
124
232
  type GtkWidgetProps,
125
- type GActionGroupProps,
126
- type GActionMapProps,
127
- type GMenuProps,
233
+ type ActionGroupProps,
234
+ type ActionMapProps,
235
+ type MenuProps,
128
236
  type GtkShortcutControllerProps,
129
237
  type GtkOverlayProps,
130
238
  type GtkTextChildAnchorProps,