lutra 0.0.12 → 0.0.15

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 (117) hide show
  1. package/dist/data/Stat.svelte +1 -1
  2. package/dist/display/Avatar.svelte +1 -1
  3. package/dist/display/Badge.svelte +1 -1
  4. package/dist/display/Callout.svelte +3 -3
  5. package/dist/display/Code.svelte +1 -1
  6. package/dist/display/ContextTip.svelte +12 -8
  7. package/dist/display/Details.svelte +1 -1
  8. package/dist/display/Hero.svelte +1 -1
  9. package/dist/display/Icon.svelte +13 -6
  10. package/dist/display/IconButton.svelte +9 -9
  11. package/dist/display/IconButton.svelte.d.ts +0 -2
  12. package/dist/display/Image.svelte +41 -0
  13. package/dist/display/Image.svelte.d.ts +24 -0
  14. package/dist/display/Indicator.svelte +1 -1
  15. package/dist/display/Inset.svelte +18 -0
  16. package/dist/display/Inset.svelte.d.ts +17 -0
  17. package/dist/display/Popup.svelte +1 -1
  18. package/dist/display/Popup.svelte.d.ts +1 -3
  19. package/dist/display/Table.svelte +21 -0
  20. package/dist/display/Table.svelte.d.ts +23 -0
  21. package/dist/display/Tag.svelte +2 -2
  22. package/dist/display/Tooltip.svelte +8 -5
  23. package/dist/display/index.d.ts +1 -0
  24. package/dist/display/index.js +1 -0
  25. package/dist/form/Button.svelte +1 -1
  26. package/dist/form/FieldActions.svelte +27 -6
  27. package/dist/form/FieldActions.svelte.d.ts +1 -0
  28. package/dist/form/FieldContainer.svelte +4 -3
  29. package/dist/form/FieldContent.svelte +54 -16
  30. package/dist/form/FieldError.svelte +1 -1
  31. package/dist/form/FieldSection.svelte +21 -46
  32. package/dist/form/Fieldset.svelte +10 -5
  33. package/dist/form/Fieldset.svelte.d.ts +2 -0
  34. package/dist/form/Form.svelte +30 -25
  35. package/dist/form/Form.svelte.d.ts +1 -1
  36. package/dist/form/Input.svelte +23 -42
  37. package/dist/form/Input.svelte.d.ts +5 -1
  38. package/dist/form/InputLength.svelte +1 -1
  39. package/dist/form/Label.svelte +2 -1
  40. package/dist/form/Select.svelte +7 -26
  41. package/dist/form/Select.svelte.d.ts +2 -26
  42. package/dist/form/client.svelte.js +13 -9
  43. package/dist/form/form.d.ts +1 -1
  44. package/dist/form/form.js +4 -0
  45. package/dist/grid/Column.svelte +1 -1
  46. package/dist/grid/Grid.svelte +1 -1
  47. package/dist/grid/Row.svelte +1 -1
  48. package/dist/icons/Alert.svelte +2 -2
  49. package/dist/icons/Copy.svelte +2 -2
  50. package/dist/icons/Done.svelte +2 -2
  51. package/dist/icons/Error.svelte +2 -2
  52. package/dist/icons/Help.svelte +2 -2
  53. package/dist/icons/Hide.svelte +2 -2
  54. package/dist/icons/Info.svelte +2 -2
  55. package/dist/icons/Link.svelte +2 -2
  56. package/dist/icons/MenuBurger.svelte +3 -0
  57. package/dist/icons/MenuBurger.svelte.d.ts +23 -0
  58. package/dist/icons/MenuDots.svelte +3 -0
  59. package/dist/icons/MenuDots.svelte.d.ts +23 -0
  60. package/dist/icons/Show.svelte +2 -2
  61. package/dist/icons/Success.svelte +2 -2
  62. package/dist/icons/Warning.svelte +2 -2
  63. package/dist/layout/Layout.svelte +1 -1
  64. package/dist/layout/LayoutFooter.svelte +1 -1
  65. package/dist/layout/LayoutGrid.svelte +1 -1
  66. package/dist/layout/LayoutHeader.svelte +1 -1
  67. package/dist/layout/PageContent.svelte +1 -1
  68. package/dist/layout/Theme.svelte +7 -7
  69. package/dist/layout/UIContent.svelte +1 -1
  70. package/dist/nav/Breadcrumb.svelte +1 -1
  71. package/dist/nav/Menu.svelte +177 -161
  72. package/dist/nav/Menu.svelte.d.ts +11 -3
  73. package/dist/nav/MenuItem.svelte +122 -0
  74. package/dist/nav/MenuItem.svelte.d.ts +17 -0
  75. package/dist/nav/MenuTypes.d.ts +24 -3
  76. package/dist/nav/NavMenu.svelte +183 -0
  77. package/dist/nav/NavMenu.svelte.d.ts +18 -0
  78. package/dist/nav/TabbedContent.svelte +1 -1
  79. package/dist/nav/Tabs.svelte +8 -8
  80. package/dist/nav/index.d.ts +2 -0
  81. package/dist/nav/index.js +1 -0
  82. package/dist/style.css +36 -24
  83. package/dist/typo/Clamp.svelte +1 -1
  84. package/dist/typo/H.svelte +3 -2
  85. package/dist/typo/H.svelte.d.ts +2 -0
  86. package/dist/typo/H1.svelte +3 -3
  87. package/dist/typo/H1.svelte.d.ts +2 -0
  88. package/dist/typo/H2.svelte +3 -2
  89. package/dist/typo/H2.svelte.d.ts +2 -0
  90. package/dist/typo/H3.svelte +3 -2
  91. package/dist/typo/H3.svelte.d.ts +2 -0
  92. package/dist/typo/H4.svelte +3 -2
  93. package/dist/typo/H4.svelte.d.ts +2 -0
  94. package/dist/typo/H5.svelte +3 -2
  95. package/dist/typo/H5.svelte.d.ts +2 -0
  96. package/dist/typo/H6.svelte +3 -2
  97. package/dist/typo/H6.svelte.d.ts +2 -0
  98. package/dist/typo/P.svelte +3 -1
  99. package/dist/typo/P.svelte.d.ts +2 -0
  100. package/dist/utils/StringOrComponentOrSnippet.svelte +13 -0
  101. package/dist/utils/StringOrComponentOrSnippet.svelte.d.ts +17 -0
  102. package/dist/utils/index.d.ts +8 -0
  103. package/dist/utils/index.js +5 -0
  104. package/dist/utils/keyboard.svelte.d.ts +3 -0
  105. package/dist/utils/keyboard.svelte.js +142 -0
  106. package/dist/utils/transitions.js +14 -7
  107. package/package.json +9 -13
  108. package/dist/datatable/DataTable.svelte +0 -30
  109. package/dist/datatable/DataTable.svelte.d.ts +0 -20
  110. package/dist/datatable/DataTableColumn.svelte +0 -20
  111. package/dist/datatable/DataTableColumn.svelte.d.ts +0 -18
  112. package/dist/datatable/DataTableRow.svelte +0 -60
  113. package/dist/datatable/DataTableRow.svelte.d.ts +0 -21
  114. package/dist/datatable/index.d.ts +0 -3
  115. package/dist/datatable/index.js +0 -3
  116. package/dist/form/server.d.ts +0 -21
  117. package/dist/form/server.js +0 -48
@@ -1,4 +1,4 @@
1
- <script>import { getStatusColorVar, isStatusColor } from "../utils/color.js";
1
+ <script lang="ts">import { getStatusColorVar, isStatusColor } from "../utils/color.js";
2
2
  import { isSnippet } from "../utils/isSnippet.js";
3
3
  let {
4
4
  title,
@@ -1,4 +1,4 @@
1
- <script>import { hexRelativeLuminance, stringToColor } from "../utils/color.js";
1
+ <script lang="ts">import { hexRelativeLuminance, stringToColor } from "../utils/color.js";
2
2
  const {
3
3
  src,
4
4
  name = "N/A",
@@ -1,4 +1,4 @@
1
- <script>import { isStatusColor } from "../utils/color.js";
1
+ <script lang="ts">import { isStatusColor } from "../utils/color.js";
2
2
  let {
3
3
  count,
4
4
  max = 99,
@@ -1,4 +1,4 @@
1
- <script>import Icon from "./Icon.svelte";
1
+ <script lang="ts">import Icon from "./Icon.svelte";
2
2
  import Alert from "../icons/Alert.svelte";
3
3
  import Info from "../icons/Info.svelte";
4
4
  import Success from "../icons/Success.svelte";
@@ -39,7 +39,7 @@ if (!icon) {
39
39
 
40
40
  <div class="Callout {type}" class:hasIcon={!!icon} class:contained class:rounded class:dismissable>
41
41
  {#if icon}
42
- <Icon {icon} width="1.5rem" />
42
+ <Icon {icon} --icon-width="1.5rem" --icon-height="1.5rem" />
43
43
  {/if}
44
44
  <div class="CalloutText">
45
45
  <PageContent>
@@ -49,7 +49,7 @@ if (!icon) {
49
49
  {#if dismissable}
50
50
  <div class="Dismiss">
51
51
  <Tooltip tip="Dismiss">
52
- <button class="CalloutDismiss" aria-label="Dismiss callout">
52
+ <button type="button" class="CalloutDismiss" aria-label="Dismiss callout">
53
53
  <svg width="16" height="16" viewBox="0 0 16 16" fill="none" xmlns="http://www.w3.org/2000/svg">
54
54
  <path d="M1 1L15 15" stroke="white" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"/>
55
55
  <path d="M1 15L15 1" stroke="white" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"/>
@@ -1,4 +1,4 @@
1
- <script>import Copy from "../icons/Copy.svelte";
1
+ <script lang="ts">import Copy from "../icons/Copy.svelte";
2
2
  import Done from "../icons/Done.svelte";
3
3
  import IconButton from "./IconButton.svelte";
4
4
  import Tooltip from "./Tooltip.svelte";
@@ -1,4 +1,4 @@
1
- <script>import Tooltip from "./Tooltip.svelte";
1
+ <script lang="ts">import Tooltip from "./Tooltip.svelte";
2
2
  import Help from "../icons/Help.svelte";
3
3
  import Icon from "./Icon.svelte";
4
4
  let {
@@ -7,17 +7,21 @@ let {
7
7
  </script>
8
8
 
9
9
  <Tooltip {tip}>
10
- <button onclick={(e) => e.preventDefault()}>
11
- <Icon icon={Help} />
12
- </button>
10
+ <a href="#foo" onclick={(e) => { e.preventDefault(); e.stopPropagation(); }}>
11
+ <Icon icon={Help} --icon-width="16px" --icon-height="16px" --cursor="help" />
12
+ </a>
13
13
  </Tooltip>
14
14
 
15
15
  <style>
16
- button {
16
+ a {
17
17
  border-radius: 50%;
18
+ color: var(--text);
19
+ height: 16px;
20
+ width: 16px;
21
+ display: inline-block;
18
22
  }
19
- button:focus,
20
- button:active {
21
- outline-offset: -3px;
23
+ a:focus,
24
+ a:active {
25
+ outline-offset: -2px;
22
26
  }
23
27
  </style>
@@ -1,4 +1,4 @@
1
- <script>let {
1
+ <script lang="ts">let {
2
2
  summary,
3
3
  contained,
4
4
  rounded,
@@ -1,4 +1,4 @@
1
- <script>import { setContext } from "svelte";
1
+ <script lang="ts">import { setContext } from "svelte";
2
2
  let {
3
3
  children,
4
4
  pad = true,
@@ -1,4 +1,4 @@
1
- <script>import { isComponent, isSnippet } from "../utils/isSnippet.js";
1
+ <script lang="ts">import { isComponent, isSnippet } from "../utils/isSnippet.js";
2
2
  let {
3
3
  icon,
4
4
  alt
@@ -17,19 +17,26 @@ let {
17
17
 
18
18
  <style>
19
19
  .Icon {
20
- display: inline-flex;
20
+ display: flex;
21
21
  align-items: center;
22
22
  justify-content: center;
23
23
  font-size: 1em;
24
- width: var(--icon-width, var(--font-size, 1em));
25
- height: var(--icon-height, var(--font-size, 1em));
24
+ width: max(
25
+ var(--icon-width,
26
+ var(--icon-height, 1rem)
27
+ ), 16px);
28
+ height: max(
29
+ var(--icon-height,
30
+ var(--icon-width, 1rem)
31
+ ), 16px);
26
32
  overflow: clip;
27
- vertical-align: var(--vertical-align, baseline);
33
+ vertical-align: var(--vertical-align, text-bottom);
28
34
  cursor: var(--cursor, default);
29
35
  }
36
+ img,
30
37
  .Icon :global(svg) {
31
38
  width: 100%;
32
39
  height: 100%;
33
- display: inline-block;
40
+ display: block;
34
41
  }
35
42
  </style>
@@ -1,10 +1,9 @@
1
- <script>import Icon from "./Icon.svelte";
1
+ <script lang="ts">import Icon from "./Icon.svelte";
2
2
  import { fade, fly, slide } from "svelte/transition";
3
3
  import { popBezier, popBezierInverse } from "../utils/transitions.js";
4
4
  import { cubicIn, cubicOut } from "svelte/easing";
5
5
  let {
6
6
  icon,
7
- hang,
8
7
  disabled,
9
8
  children,
10
9
  onclick
@@ -15,7 +14,7 @@ let {
15
14
  <span class="IconMask">
16
15
  {#key icon}
17
16
  <span class="IconContent" in:fly={{ duration: 250, y: -32, easing: popBezier }} out:fly={{ duration: 250, y: 32, easing: popBezierInverse }}>
18
- <Icon {icon} />
17
+ <Icon {icon} --cursor="pointer" />
19
18
  {#if children}
20
19
  {@render children()}
21
20
  {/if}
@@ -25,11 +24,11 @@ let {
25
24
  {/snippet}
26
25
 
27
26
  {#if onclick}
28
- <button {disabled} class="IconButton" class:hang {onclick}>
27
+ <button type="button" {disabled} class="IconButton" {onclick}>
29
28
  {@render inside()}
30
29
  </button>
31
30
  {:else}
32
- <span class="IconButton" class:hang>
31
+ <span class="IconButton">
33
32
  {@render inside()}
34
33
  </span>
35
34
  {/if}
@@ -41,14 +40,15 @@ let {
41
40
  color: inherit;
42
41
  opacity: 1;
43
42
  background-color: var(--field-bg);
44
- transition: background-color 0.1s;
43
+ transition: background-color 0.04s;
44
+ border-radius: var(--field-radius);
45
+ }
46
+ .IconButton:hover {
47
+ background-color: var(--menu-bg-hover);
45
48
  }
46
49
  .IconButton:active {
47
50
  scale: 1;
48
51
  }
49
- .IconButton.hang {
50
- margin-inline-start: calc(-1 * var(--padding, 0.75rem));
51
- }
52
52
  button.IconButton {
53
53
  border: none;
54
54
  background: none;
@@ -4,8 +4,6 @@ declare const __propDef: {
4
4
  props: {
5
5
  /** The icon to display. */
6
6
  icon: string | ComponentType;
7
- /** Whether the button should hang to the inline start to line up with other elements. The amount of hanging is the same as the padding. */
8
- hang?: boolean | undefined;
9
7
  /** The children to display. */
10
8
  children?: ((this: void) => typeof import("svelte").SnippetReturn & {
11
9
  _: "functions passed to {@render ...} tags must use the `Snippet` type imported from \"svelte\"";
@@ -0,0 +1,41 @@
1
+ <script lang="ts">let {
2
+ aspectRatio,
3
+ fit,
4
+ src,
5
+ srcset,
6
+ alt,
7
+ width,
8
+ height,
9
+ style,
10
+ class: className
11
+ } = $props();
12
+ if (!src && srcset) {
13
+ const [src1, src2] = srcset.split(", ");
14
+ src = src1.split(" ")[0];
15
+ }
16
+ if (!style) {
17
+ style = `aspect-ratio: ${aspectRatio};`;
18
+ } else {
19
+ style += ` aspect-ratio: ${aspectRatio};`;
20
+ }
21
+ </script>
22
+
23
+ <img
24
+ src={src}
25
+ srcset={srcset}
26
+ alt={alt}
27
+ width={width}
28
+ height={height}
29
+ style={style}
30
+ class="{className} {fit}"
31
+ />
32
+
33
+ <style>
34
+ img {
35
+ display: inline-block;
36
+ vertical-align: middle;
37
+ }
38
+ img.cover { object-fit: cover; }
39
+ img.contain { object-fit: contain; }
40
+ img.scale-down { object-fit: scale-down; }
41
+ </style>
@@ -0,0 +1,24 @@
1
+ import { SvelteComponent } from "svelte";
2
+ declare const __propDef: {
3
+ props: {
4
+ aspectRatio?: string | undefined;
5
+ fit?: "cover" | "contain" | "scale-down" | undefined;
6
+ src?: string | undefined;
7
+ srcset?: string | undefined;
8
+ alt?: string | undefined;
9
+ width?: string | undefined;
10
+ height?: string | undefined;
11
+ style?: string | undefined;
12
+ class?: string | undefined;
13
+ };
14
+ events: {
15
+ [evt: string]: CustomEvent<any>;
16
+ };
17
+ slots: {};
18
+ };
19
+ export type ImageProps = typeof __propDef.props;
20
+ export type ImageEvents = typeof __propDef.events;
21
+ export type ImageSlots = typeof __propDef.slots;
22
+ export default class Image extends SvelteComponent<ImageProps, ImageEvents, ImageSlots> {
23
+ }
24
+ export {};
@@ -1,4 +1,4 @@
1
- <script>import { isStatusColor, StatusColors } from "../utils/color.js";
1
+ <script lang="ts">import { isStatusColor, StatusColors } from "../utils/color.js";
2
2
  let {
3
3
  color = "default",
4
4
  motion,
@@ -0,0 +1,18 @@
1
+ <script lang="ts">let {
2
+ children
3
+ } = $props();
4
+ </script>
5
+
6
+ <div class="Inset">
7
+ {@render children()}
8
+ </div>
9
+
10
+ <style>
11
+ .Inset {
12
+ margin-block: calc(var(--inset-block, 0) * -1);
13
+ margin-inline: calc(var(--inset-inline, 0) * -1);
14
+ }
15
+ .Inset > * {
16
+ display: block;
17
+ }
18
+ </style>
@@ -0,0 +1,17 @@
1
+ import { SvelteComponent } from "svelte";
2
+ import type { Snippet } from "svelte";
3
+ declare const __propDef: {
4
+ props: {
5
+ children: Snippet;
6
+ };
7
+ events: {
8
+ [evt: string]: CustomEvent<any>;
9
+ };
10
+ slots: {};
11
+ };
12
+ export type InsetProps = typeof __propDef.props;
13
+ export type InsetEvents = typeof __propDef.events;
14
+ export type InsetSlots = typeof __propDef.slots;
15
+ export default class Inset extends SvelteComponent<InsetProps, InsetEvents, InsetSlots> {
16
+ }
17
+ export {};
@@ -1,4 +1,4 @@
1
- <script>import UiContent from "../layout/UIContent.svelte";
1
+ <script lang="ts">import UiContent from "../layout/UIContent.svelte";
2
2
  import { slidefade } from "../utils/transitions.js";
3
3
  import { attr } from "../utils/attr.js";
4
4
  let {
@@ -5,9 +5,7 @@ declare const __propDef: {
5
5
  /** The content of the popup */
6
6
  content: Snippet<[close: () => void]>;
7
7
  /** Snippet containing the trigger element */
8
- trigger: (this: void, attrs: (node: Element) => void) => typeof import("svelte").SnippetReturn & {
9
- _: "functions passed to {@render ...} tags must use the `Snippet` type imported from \"svelte\"";
10
- };
8
+ trigger: Snippet<[attrs: (node: Element) => void]>;
11
9
  /** Triggers the popup on hover (and keyboard focus) instead of click */
12
10
  hover?: boolean | undefined;
13
11
  /** The shape of the popup */
@@ -0,0 +1,21 @@
1
+ <script lang="ts">let {
2
+ colored,
3
+ contained,
4
+ rounded,
5
+ hoverable,
6
+ hang,
7
+ fullWidth,
8
+ children
9
+ } = $props();
10
+ </script>
11
+
12
+ <table
13
+ class:colored
14
+ class:contained
15
+ class:rounded
16
+ class:hang
17
+ class:fullWidth
18
+ class:hoverable
19
+ >
20
+ {@render children()}
21
+ </table>
@@ -0,0 +1,23 @@
1
+ import { SvelteComponent } from "svelte";
2
+ import type { Snippet } from "svelte";
3
+ declare const __propDef: {
4
+ props: {
5
+ colored?: boolean | undefined;
6
+ contained?: boolean | undefined;
7
+ rounded?: boolean | undefined;
8
+ hang?: boolean | undefined;
9
+ hoverable?: boolean | undefined;
10
+ fullWidth?: boolean | undefined;
11
+ children: Snippet;
12
+ };
13
+ events: {
14
+ [evt: string]: CustomEvent<any>;
15
+ };
16
+ slots: {};
17
+ };
18
+ export type TableProps = typeof __propDef.props;
19
+ export type TableEvents = typeof __propDef.events;
20
+ export type TableSlots = typeof __propDef.slots;
21
+ export default class Table extends SvelteComponent<TableProps, TableEvents, TableSlots> {
22
+ }
23
+ export {};
@@ -1,4 +1,4 @@
1
- <script>import { isStatusColor } from "../utils/color.js";
1
+ <script lang="ts">import { isStatusColor } from "../utils/color.js";
2
2
  let {
3
3
  code,
4
4
  color = "default",
@@ -22,7 +22,7 @@ let isSet = $derived(color ? isStatusColor(color) : true);
22
22
  {@render content()}
23
23
  </a>
24
24
  {:else if onclick}
25
- <button class:code class="Tag {shape}" style="--bgColor: {!isSet ? color : 'var(--status-'+color+')'};" onclick={onclick}>
25
+ <button type="button" class:code class="Tag {shape}" style="--bgColor: {!isSet ? color : 'var(--status-'+color+')'};" onclick={onclick}>
26
26
  {@render content()}
27
27
  </button>
28
28
  {:else}
@@ -1,4 +1,4 @@
1
- <script>import Theme from "../layout/Theme.svelte";
1
+ <script lang="ts">import Theme from "../layout/Theme.svelte";
2
2
  let {
3
3
  children,
4
4
  tip,
@@ -32,9 +32,8 @@ const id = `tt-${Math.random().toString(36).substring(2, 15) + Math.random().toS
32
32
  <style>
33
33
  .Tooltip {
34
34
  position: relative;
35
- height: 100%;
36
35
  display: inline-flex;
37
- align-items: center;
36
+ vertical-align: var(--vertical-align, text-bottom);
38
37
  }
39
38
  .TooltipContainer {
40
39
  position: absolute;
@@ -58,8 +57,8 @@ const id = `tt-${Math.random().toString(36).substring(2, 15) + Math.random().toS
58
57
  border-left: var(--border-subtle);
59
58
  border-right: var(--border-subtle);
60
59
  display: block;
61
- font-size: max(0.85rem, 12px);
62
- line-height: 1.4;
60
+ font-size: max(0.75rem, 11px);
61
+ line-height: 1.35;
63
62
  font-weight: 500;
64
63
  color: var(--text);
65
64
  max-width: clamp(5ch, 100%, 35ch);
@@ -72,6 +71,10 @@ const id = `tt-${Math.random().toString(36).substring(2, 15) + Math.random().toS
72
71
  .TooltipContent :global(b) {
73
72
  font-weight: 700;
74
73
  }
74
+ .TooltipTrigger {
75
+ display: inline-flex;
76
+ align-items: center;
77
+ }
75
78
  .Tooltip:has(.TooltipTrigger:hover):not(.open) .TooltipContainer {
76
79
  animation: fadeIn 0.2s var(--delay, 0.5s) ease-in-out forwards;
77
80
  }
@@ -10,4 +10,5 @@ export { default as IconButton } from './IconButton.svelte';
10
10
  export { default as Indicator } from './Indicator.svelte';
11
11
  export { default as Popup } from './Popup.svelte';
12
12
  export { default as Tag } from './Tag.svelte';
13
+ export { default as Table } from './Table.svelte';
13
14
  export { default as Tooltip } from './Tooltip.svelte';
@@ -10,4 +10,5 @@ export { default as IconButton } from './IconButton.svelte';
10
10
  export { default as Indicator } from './Indicator.svelte';
11
11
  export { default as Popup } from './Popup.svelte';
12
12
  export { default as Tag } from './Tag.svelte';
13
+ export { default as Table } from './Table.svelte';
13
14
  export { default as Tooltip } from './Tooltip.svelte';
@@ -1,4 +1,4 @@
1
- <script>import Icon from "../display/Icon.svelte";
1
+ <script lang="ts">import Icon from "../display/Icon.svelte";
2
2
  let {
3
3
  href,
4
4
  type = "button",
@@ -1,24 +1,45 @@
1
- <script>let {
1
+ <script lang="ts">let {
2
+ align = "end",
2
3
  children
3
4
  } = $props();
4
5
  </script>
5
6
 
6
- <div class="FieldActions">
7
- {@render children()}
7
+ <div class="FieldActions {align}">
8
+ <div class="Actions">
9
+ {@render children()}
10
+ </div>
8
11
  </div>
9
12
 
10
13
  <style>
11
14
  .FieldActions {
15
+ display: grid;
16
+ background: color-mix(in srgb, var(--bg-subtle) calc(var(--fcc) * 100%), transparent);
17
+ padding: calc(1.5em * var(--fcc)) calc(3em * var(--fcc));
18
+ grid-column: 1 / -1;
19
+ grid-template-columns: subgrid;
20
+ }
21
+ .Actions {
12
22
  display: flex;
13
23
  flex-direction: row;
14
24
  align-items: center;
15
25
  justify-content: space-between;
16
26
  gap: 1.35em;
17
- background: color-mix(in srgb, var(--bg-subtle) calc(var(--fcc) * 100%), transparent);
18
- padding: calc(1.5em * var(--fcc)) calc(1.5em * var(--fcc));
27
+ grid-column: 2 / -1;
28
+ }
29
+ .FieldActions.start .Actions {
30
+ justify-content: start;
31
+ grid-column: 1 / -1;
32
+ }
33
+ .FieldActions.middle .Actions {
34
+ justify-content: center;
35
+ grid-column: 1 / -1;
36
+ }
37
+ .FieldActions.end .Actions {
38
+ justify-content: end;
39
+ grid-column: 1 / -1;
19
40
  }
20
41
  @container (max-width: 400px) {
21
- .FieldActions {
42
+ .Actions {
22
43
  flex-direction: column;
23
44
  }
24
45
  }
@@ -2,6 +2,7 @@ import { SvelteComponent } from "svelte";
2
2
  import type { Snippet } from "svelte";
3
3
  declare const __propDef: {
4
4
  props: {
5
+ align?: "middle" | "justified" | "start" | "end" | undefined;
5
6
  children: Snippet;
6
7
  };
7
8
  events: {
@@ -1,4 +1,4 @@
1
- <script>let {
1
+ <script lang="ts">let {
2
2
  children,
3
3
  contained
4
4
  } = $props();
@@ -12,8 +12,9 @@
12
12
  .FieldContainer {
13
13
  container-type: inline-size;
14
14
  display: grid;
15
- gap: 1.5em;
16
- grid-template-columns: 1fr;
15
+ row-gap: 1.5em;
16
+ column-gap: 3em;
17
+ grid-template-columns: minmax(25ch, 35%) minmax(min-content, 1fr);
17
18
  border-radius: var(--border-radius);
18
19
  }
19
20
  .FieldContainer.contained {
@@ -1,4 +1,4 @@
1
- <script>import Label from "./Label.svelte";
1
+ <script lang="ts">import Label from "./Label.svelte";
2
2
  import FieldError from "./FieldError.svelte";
3
3
  let {
4
4
  id,
@@ -16,21 +16,55 @@ let {
16
16
  } = $props();
17
17
  </script>
18
18
 
19
+ {#snippet _prefix()}
20
+ <div class="Fix Prefix">
21
+ {#if typeof prefix === 'string'}
22
+ {prefix}
23
+ {:else}
24
+ {@render prefix()}
25
+ {/if}
26
+ </div>
27
+ {/snippet}
28
+
29
+ {#snippet _suffix()}
30
+ <div class="Fix Suffix">
31
+ {#if typeof suffix === 'string'}
32
+ {suffix}
33
+ {:else}
34
+ {@render suffix()}
35
+ {/if}
36
+ </div>
37
+ {/snippet}
19
38
 
20
39
  <div class="FieldContent {type} {direction}" class:contained>
21
40
  <Label {label} tip={labelTip} {id} />
22
41
  {#if contained}
23
- <div class="Field">
42
+ <div
43
+ class="Field"
44
+ class:hasPrefix={prefix}
45
+ class:hasSuffix={suffix}
46
+ class:invalid={field?.tainted && issue?.code}
47
+ >
24
48
  {#if prefix}
25
- <div class="Fix Prefix">{prefix}</div>
49
+ {@render _prefix()}
26
50
  {/if}
51
+
27
52
  {@render children()}
53
+
28
54
  {#if suffix}
29
- <div class="Fix Suffix">{suffix}</div>
55
+ {@render _suffix()}
30
56
  {/if}
31
57
  </div>
32
58
  {:else}
59
+ {#if prefix}
60
+ {@render _prefix()}
61
+ {/if}
62
+
33
63
  {@render children()}
64
+
65
+ {#if suffix}
66
+ {@render _suffix()}
67
+ {/if}
34
68
  {/if}
35
69
 
36
70
  {#if field?.tainted && issue?.code}
@@ -45,12 +79,21 @@ let {
45
79
  flex-direction: column;
46
80
  font-size: var(--font-size, 1em);
47
81
  }
82
+ .FieldContent.row {
83
+ flex-direction: row-reverse;
84
+ justify-content: start;
85
+ align-items: center;
86
+ flex-shrink: 0;
87
+ }
48
88
  .Field {
49
89
  background-color: var(--field-bg);
50
- border: var(--border-size) var(--border-style) var(--border-color);
90
+ border: var(--field-border-size) var(--field-border-style) var(--field-border-color);
51
91
  border-radius: var(--field-radius);
52
92
  display: flex;
53
- padding-inline: 0.15em;
93
+ }
94
+ .Field:has(input:user-invalid),
95
+ .Field.invalid {
96
+ border-color: var(--field-border-color-error);
54
97
  }
55
98
  .Field > *:not(input) {
56
99
  flex-grow: 0;
@@ -73,21 +116,16 @@ let {
73
116
  .Field:has(input:focus-visible) {
74
117
  outline: var(--focus-outline);
75
118
  }
76
- .Field.hasPrefix input {
119
+ .Field:has(input:focus-visible:user-invalid),
120
+ .Field.invalid:has(input:focus-visible) {
121
+ outline-color: var(--focus-color-error);
122
+ }
123
+ .Field.hasPrefix :global(input) {
77
124
  padding-inline-start: 0.35em;
78
125
  }
79
- /**
80
- * Buttons
81
- */
82
126
  .Field :global(button:focus-visible) {
83
127
  outline: var(--focus-outline);
84
128
  outline-offset: 3px;
85
129
  border-radius: calc(var(--field-radius) - 2px);
86
130
  }
87
- /**
88
- * Row
89
- */
90
- .FieldContent.row {
91
- flex-direction: row;
92
- }
93
131
  </style>
@@ -1,4 +1,4 @@
1
- <script>let {
1
+ <script lang="ts">let {
2
2
  code,
3
3
  message
4
4
  } = $props();