@kahitsan/ksui 0.38.3 → 0.39.1

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.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@kahitsan/ksui",
3
- "version": "0.38.3",
3
+ "version": "0.39.1",
4
4
  "description": "ksui is a standalone set of SolidJS UI components for KahitSan/Hilinga and any SolidJS app. Published to the public npm registry and consumed as a normal dependency. Ships source under a `solid` export condition so the consumer's vite-plugin-solid compiles it with only solid-js externalized; it depends on nothing but solid-js + lucide-solid and injects its own CSS.",
5
5
  "type": "module",
6
6
  "main": "./src/index.ts",
@@ -43,6 +43,7 @@ import ExistingAttachmentTile, {
43
43
  import FormField from "../base/FormField";
44
44
  import DatePicker from "../base/DatePicker";
45
45
  import Button from "../base/Button";
46
+ import { injectCSS } from "../../utils/inject-css";
46
47
  import {
47
48
  type PendingFile,
48
49
  createPendingFile,
@@ -294,9 +295,15 @@ export interface TransactionFormProps {
294
295
  * For a caller that locks `category` to one value and never needs
295
296
  * EWT/sharing (e.g. a "record my own expense" surface). */
296
297
  simpleMode?: boolean;
298
+ layout?: "default" | "compact";
297
299
  }
298
300
 
299
301
  export default function TransactionForm(props: TransactionFormProps) {
302
+ injectCSS("ksui-transaction-form-compact", `.ks-transaction-compact{min-height:0;font-family:var(--ks-font-body,"Inter", system-ui, sans-serif)}.ks-transaction-compact-body{display:flex;flex-direction:column;min-height:0;overflow:auto;padding:1rem 1.25rem 1.5rem;gap:1rem}.ks-transaction-compact-body>div{width:100%;flex:0 0 auto}.ks-transaction-compact-body input[data-testid="transactions-form-amount"]{min-height:3.5rem;text-align:center;font-size:2rem}.ks-transaction-compact-body input[data-testid="transactions-form-description"]{background:transparent;border-color:var(--ks-border)}.ks-transaction-compact-body>div:has(input[data-testid="transactions-form-amount"])>label,.ks-transaction-compact-body>div:has(input[data-testid="transactions-form-description"])>label{display:none}.ks-transaction-compact-body>div:has(button[aria-label="Today"])>label{font-size:0;text-transform:uppercase;letter-spacing:.12em}.ks-transaction-compact-body>div:has(button[aria-label="Today"])>label:after{content:"TRANSACTION DATE";font-size:10px}.ks-transaction-compact-body [role="radiogroup"]{display:flex;flex-wrap:nowrap;overflow-x:auto;scrollbar-width:none}.ks-transaction-compact-body [role="radiogroup"]::-webkit-scrollbar{display:none}.ks-transaction-compact-body [role="radio"]{min-width:8rem}.ks-transaction-compact-footer{flex:0 0 auto}.ks-transaction-compact:not(.ks-transaction-compact-details) .ks-transaction-compact-body>div:has(button[data-testid="form-payee-picker"]),.ks-transaction-compact:not(.ks-transaction-compact-details) .ks-transaction-compact-body>div:has([data-testid="subcategory-select"]),.ks-transaction-compact:not(.ks-transaction-compact-details) .ks-transaction-compact-body>div:has(textarea),.ks-transaction-compact:not(.ks-transaction-compact-details) .ks-transaction-compact-body>div:has(button[aria-label="Add attachment"]){display:none}
303
+ .ks-transaction-compact:not(.ks-transaction-compact-details) .ks-transaction-compact-secondary{display:none;}
304
+ .ks-transaction-compact .ks-transaction-compact-body{display:flex;flex-direction:column;min-height:0;overflow:auto;}
305
+ `);
306
+ const compact = () => props.layout === "compact";
300
307
  const catConfig = () =>
301
308
  CATEGORY_FORM[props.category] || CATEGORY_FORM.expense;
302
309
  const [dragging, setDragging] = createSignal(false);
@@ -422,6 +429,7 @@ export default function TransactionForm(props: TransactionFormProps) {
422
429
  return (
423
430
  <div
424
431
  class="relative flex flex-col flex-1 min-h-0"
432
+ classList={{ "ks-transaction-compact": compact(), "ks-transaction-compact-details": compact() && viewMode() === "advanced" }}
425
433
  onDragEnter={handleDragEnter}
426
434
  onDragLeave={handleDragLeave}
427
435
  onDragOver={handleDragOver}
@@ -455,7 +463,8 @@ export default function TransactionForm(props: TransactionFormProps) {
455
463
  }}
456
464
  class="flex flex-col flex-1 min-h-0"
457
465
  >
458
- <div class="flex-1 overflow-x-hidden overflow-y-auto px-5 sm:px-6 py-5 space-y-4">
466
+ <div class="flex-1 overflow-x-hidden overflow-y-auto px-5 sm:px-6 py-5 space-y-4"
467
+ classList={{ "ks-transaction-compact-body": compact() }}>
459
468
  <Show when={props.error}>
460
469
  <div
461
470
  class="rounded-lg border border-[color-mix(in_srgb,var(--ks-danger,#ef4444)_30%,transparent)] bg-[color-mix(in_srgb,var(--ks-danger,#ef4444)_10%,transparent)] px-3 py-2 text-sm text-[var(--ks-danger-fg,#f87171)]"
@@ -531,7 +540,7 @@ export default function TransactionForm(props: TransactionFormProps) {
531
540
  <Show
532
541
  when={!(props.category === "sale" && props.saleItems.length > 0)}
533
542
  >
534
- <FormField label="Amount *">
543
+ <FormField label={compact() ? "" : "Amount *"}>
535
544
  <div class="flex items-stretch gap-2 px-4 py-3 border bg-[color-mix(in_srgb,var(--ks-overlay-surface,#18181b)_60%,transparent)] border-[color-mix(in_srgb,var(--ks-border,rgba(39,39,42,0.5))_60%,transparent)] ks-hud-clip-button focus-within:border-[color-mix(in_srgb,var(--ks-focus-ring,#c9a961)_50%,transparent)] transition-colors">
536
545
  <span class="self-center text-3xl font-bold text-[var(--ks-fg-subtle,#71717a)] tabular-nums">
537
546
 
@@ -598,7 +607,7 @@ export default function TransactionForm(props: TransactionFormProps) {
598
607
  </Show>
599
608
  </Show>
600
609
 
601
- <FormField label="Date *">
610
+ <FormField label={compact() ? "TRANSACTION DATE" : "Date *"}>
602
611
  <DatePicker
603
612
  value={props.date}
604
613
  onChange={(d: string | null) => d && props.setDate(d)}
@@ -629,7 +638,7 @@ export default function TransactionForm(props: TransactionFormProps) {
629
638
  </div>
630
639
  </Show>
631
640
 
632
- <FormField label="Description *">
641
+ <FormField label={compact() ? "" : "Description *"}>
633
642
  <input
634
643
  type="text"
635
644
  data-testid="transactions-form-description"
@@ -642,7 +651,7 @@ export default function TransactionForm(props: TransactionFormProps) {
642
651
  </FormField>
643
652
 
644
653
  <Show when={catConfig().showPayee}>
645
- <div class="grid grid-cols-2 gap-4">
654
+ <div class="grid grid-cols-2 gap-4" classList={{ "ks-transaction-compact-secondary": compact() }}>
646
655
  <FormField label={catConfig().payeeLabel!}>
647
656
  <ComboBox<PayeeOption>
648
657
  testIdPrefix="form-payee-picker"
@@ -690,7 +699,8 @@ export default function TransactionForm(props: TransactionFormProps) {
690
699
  </div>
691
700
  </Show>
692
701
  <Show when={!catConfig().showPayee}>
693
- <FormField label="Reference #">
702
+ <div classList={{ "ks-transaction-compact-secondary": compact() }}>
703
+ <FormField label="Reference #">
694
704
  <input
695
705
  type="text"
696
706
  value={props.refNumber}
@@ -698,11 +708,13 @@ export default function TransactionForm(props: TransactionFormProps) {
698
708
  class="w-full bg-[color-mix(in_srgb,var(--ks-overlay-surface,#18181b)_60%,transparent)] border border-[color-mix(in_srgb,var(--ks-border,rgba(39,39,42,0.5))_60%,transparent)] px-3 py-3 text-sm text-[var(--ks-fg,#ffffff)] ks-hud-clip-button focus:outline-none focus:border-[color-mix(in_srgb,var(--ks-focus-ring,#c9a961)_50%,transparent)]"
699
709
  placeholder="Reference number (optional)"
700
710
  />
701
- </FormField>
711
+ </FormField>
712
+ </div>
702
713
  </Show>
703
714
 
704
715
  <Show when={subcategoryAppliesTo() !== null}>
705
- <FormField label="Category">
716
+ <div classList={{ "ks-transaction-compact-secondary": compact() }}>
717
+ <FormField label="Category">
706
718
  <Show
707
719
  when={subcategoryOptionsReady()}
708
720
  fallback={
@@ -748,11 +760,13 @@ export default function TransactionForm(props: TransactionFormProps) {
748
760
  <p class="text-[10px] text-[var(--ks-fg-subtle,#71717a)] mt-0.5">
749
761
  Optional. Used for tax-prep classification.
750
762
  </p>
751
- </FormField>
763
+ </FormField>
764
+ </div>
752
765
  </Show>
753
766
 
754
767
  <Show when={props.category === "payable"}>
755
- <TransactionPayableFields
768
+ <div classList={{ "ks-transaction-compact-secondary": compact() }}>
769
+ <TransactionPayableFields
756
770
  payableKind={props.payableKind}
757
771
  setPayableKind={props.setPayableKind}
758
772
  dueDate={props.dueDate}
@@ -761,7 +775,8 @@ export default function TransactionForm(props: TransactionFormProps) {
761
775
  setChequeNumber={props.setChequeNumber}
762
776
  pdcStatus={props.pdcStatus}
763
777
  setPdcStatus={props.setPdcStatus}
764
- />
778
+ />
779
+ </div>
765
780
  </Show>
766
781
 
767
782
  <TransactionAccountFields
@@ -781,6 +796,7 @@ export default function TransactionForm(props: TransactionFormProps) {
781
796
  allowTransferFee={props.allowTransferFee}
782
797
  />
783
798
 
799
+ <div classList={{ "ks-transaction-compact-secondary": compact() }}>
784
800
  <FormField label="Notes">
785
801
  <MentionTextarea
786
802
  value={props.notes}
@@ -791,6 +807,7 @@ export default function TransactionForm(props: TransactionFormProps) {
791
807
  ariaLabel="Notes"
792
808
  />
793
809
  </FormField>
810
+ </div>
794
811
 
795
812
  <div>
796
813
  <div class="flex items-center gap-1 mb-2 text-xs text-[var(--ks-fg-subtle,#71717a)]">
@@ -899,9 +916,7 @@ export default function TransactionForm(props: TransactionFormProps) {
899
916
  }
900
917
  class="text-xs text-[var(--ks-fg-subtle,#71717a)] hover:text-[var(--ks-accent,#fbbf24)] px-3 py-1.5 transition-colors cursor-pointer"
901
918
  >
902
- {viewMode() === "default"
903
- ? "Show advanced fields"
904
- : "Hide advanced fields"}
919
+ {compact() ? (viewMode() === "default" ? "More details" : "Less details") : (viewMode() === "default" ? "Show advanced fields" : "Hide advanced fields")}
905
920
  </button>
906
921
  </div>
907
922
 
@@ -929,7 +944,8 @@ export default function TransactionForm(props: TransactionFormProps) {
929
944
  </Show>
930
945
  </div>
931
946
 
932
- <div class="px-5 sm:px-6 py-4 border-t border-[color-mix(in_srgb,var(--ks-border,rgba(39,39,42,0.5))_60%,transparent)] bg-[var(--ks-bg,#0a0a0a)] flex flex-col-reverse sm:flex-row sm:items-center sm:justify-between gap-3 shrink-0">
947
+ <div class="px-5 sm:px-6 py-4 border-t border-[color-mix(in_srgb,var(--ks-border,rgba(39,39,42,0.5))_60%,transparent)] bg-[var(--ks-bg,#0a0a0a)] flex flex-col-reverse sm:flex-row sm:items-center sm:justify-between gap-3 shrink-0"
948
+ classList={{ "ks-transaction-compact-footer": compact() }}>
933
949
  <div class="text-xs text-[var(--ks-fg-subtle,#71717a)]">
934
950
  <span class="text-[var(--ks-fg-subtle,#71717a)]">Will record as </span>
935
951
  <span