Files
James Ritchie 0632e82a4b Squashed commit of the following:
commit 09bed34946
Author: James Ritchie <james@jamesritchie.co.uk>
Date:   Fri Apr 8 14:03:50 2022 +0100

    Fixed the layout of a search list item

commit 90126d43ad
Author: Eric Allam <eallam@icloud.com>
Date:   Fri Apr 1 17:25:13 2022 +0100

    Insanely complicated path search results highlighitng and truncating

commit a4bbd5521e
Author: James Ritchie <james@jamesritchie.co.uk>
Date:   Fri Apr 1 14:05:01 2022 +0100

    Improved the title editing in the header

commit 5814053968
Author: James Ritchie <james@jamesritchie.co.uk>
Date:   Fri Apr 1 13:38:33 2022 +0100

    Improved text highlight colour

commit 110de37242
Author: James Ritchie <james@jamesritchie.co.uk>
Date:   Fri Apr 1 13:36:57 2022 +0100

    Icon hover state now uses isHighlighted

commit fb6da943d9
Author: James Ritchie <james@jamesritchie.co.uk>
Date:   Fri Apr 1 13:31:11 2022 +0100

    Light mode styling

commit 2c378d5158
Author: James Ritchie <james@jamesritchie.co.uk>
Date:   Fri Apr 1 12:24:43 2022 +0100

    Spacing between search items no longer a hack

commit 85d90bb0ae
Author: Eric Allam <eallam@icloud.com>
Date:   Fri Apr 1 12:19:10 2022 +0100

    Added ellipsis to search matches if they are windowed

commit 91f3e70676
Author: Eric Allam <eallam@icloud.com>
Date:   Fri Apr 1 12:08:00 2022 +0100

    Fixed search item icons

commit e384c87c6f
Author: James Ritchie <james@jamesritchie.co.uk>
Date:   Fri Apr 1 11:52:58 2022 +0100

    Improved hover state

commit f4681edc07
Author: James Ritchie <james@jamesritchie.co.uk>
Date:   Fri Apr 1 11:47:33 2022 +0100

    Removed focus state on button

commit faa2d0663c
Author: Eric Allam <eallam@icloud.com>
Date:   Fri Apr 1 11:26:42 2022 +0100

    made the search palette a little bigger

commit df8bd521fe
Author: Eric Allam <eallam@icloud.com>
Date:   Fri Apr 1 11:26:14 2022 +0100

    Remove onOverlayClick prop

commit ecd046b3b2
Author: Eric Allam <eallam@icloud.com>
Date:   Fri Apr 1 11:18:46 2022 +0100

    Close search when the overlay is clicked

commit fba330b5d9
Author: Eric Allam <eallam@icloud.com>
Date:   Fri Apr 1 11:10:35 2022 +0100

    hitting esc when search input is focused and empty should close the search

commit fc2fe8ae6f
Author: Eric Allam <eallam@icloud.com>
Date:   Fri Apr 1 11:00:08 2022 +0100

    Highlight the window of the best search match in the search results

commit 45193ec92c
Author: James Ritchie <james@jamesritchie.co.uk>
Date:   Fri Apr 1 10:45:01 2022 +0100

    Now you can arrow down to the last item in the list

commit 0de5fef7e9
Author: James Ritchie <james@jamesritchie.co.uk>
Date:   Fri Apr 1 10:37:20 2022 +0100

    Added a hacky margin between items and remove the transition to make it feel snappier

commit 167b548343
Author: Eric Allam <eallam@icloud.com>
Date:   Fri Apr 1 09:30:33 2022 +0100

    WIP implementing search

commit 5655631f12
Author: James Ritchie <james@jamesritchie.co.uk>
Date:   Fri Mar 25 15:28:19 2022 +0000

    Build and styled search modal

commit e368db81c8
Author: Eric Allam <eallam@icloud.com>
Date:   Fri Mar 25 14:42:03 2022 +0000

    Implement JSON search through fuse.js + web worker + react hook

commit 8caa11ba1c
Author: Eric Allam <eallam@icloud.com>
Date:   Wed Mar 23 10:21:33 2022 +0000

    Start of the Command Palette using radix-ui Dialog

commit 904b64d781
Author: Eric Allam <eallam@icloud.com>
Date:   Wed Mar 23 09:58:52 2022 +0000

    Uncommented out the search bar field
2022-04-08 14:07:39 +01:00

157 lines
3.4 KiB
TypeScript

import { Temporal } from "@js-temporal/polyfill";
import { inferTemporal } from "./inferredTemporal";
import {
JSONDateTimeFormat,
JSONStringFormat,
JSONValueType,
} from "@jsonhero/json-infer-types";
export function formatRawValue(type: JSONValueType): string {
switch (type.name) {
case "string":
return type.value;
case "int":
return type.value.toString();
case "float":
return type.value.toString();
case "bool":
return type.value ? "true" : "false";
case "null":
return "null";
case "array":
return "[]";
case "object":
return "{}";
}
}
export type FormatValueOptions = {
leafNodesOnly?: boolean;
};
export function formatValue(
type: JSONValueType,
options?: FormatValueOptions
): string | undefined {
switch (type.name) {
case "array": {
if (options?.leafNodesOnly) {
return;
}
if (type.value.length == 0) {
return formatRawValue(type);
} else if (type.value.length === 1) {
return `1 item`;
} else {
return `${type.value.length} items`;
}
}
case "object": {
if (options?.leafNodesOnly) {
return;
}
if (Object.keys(type.value).length == 0) {
return formatRawValue(type);
} else if (Object.keys(type.value).length === 1) {
return `1 field`;
} else {
return `${Object.keys(type.value).length} fields`;
}
}
case "bool": {
return type.value ? "true" : "false";
}
case "float":
case "int":
return formatNumber(type.value);
case "null": {
return "null";
}
case "string":
return formatString(type.value, type.format);
default:
const _exhaustiveCheck: never = type;
return _exhaustiveCheck;
}
}
const numberFormatter = new Intl.NumberFormat(undefined, {
maximumFractionDigits: 6,
});
export function formatNumber(value: number): string {
return numberFormatter.format(value);
}
function formatString(value: string, format?: JSONStringFormat): string {
if (!format) {
return value;
}
switch (format.name) {
case "email":
return value;
case "uri":
return value;
case "datetime":
return formatDateTime(value, format);
default:
return value;
}
}
export function formatDateTime(
value: string,
format?: JSONDateTimeFormat
): string {
if (!format) {
return value;
}
const temporal = inferTemporal(value, format);
if (!temporal) {
return value;
}
switch (format.parts) {
case "datetime":
return temporal.toLocaleString("en-US", {
year: "numeric",
month: "short",
day: "numeric",
hour: "numeric",
minute: "numeric",
second: "numeric",
timeZoneName: "short",
});
case "date":
return temporal.toLocaleString("en-US", {
year: "numeric",
month: "short",
day: "numeric",
});
case "time":
return temporal.toLocaleString("en-US", {
hour: "numeric",
minute: "numeric",
second: "numeric",
});
}
}
export function formatBytes(bytes: number, decimals = 2): string {
if (bytes === 0) return "0 Bytes";
const k = 1024;
const dm = decimals < 0 ? 0 : decimals;
const sizes = ["Bytes", "KB", "MB", "GB", "TB", "PB", "EB", "ZB", "YB"];
const i = Math.floor(Math.log(bytes) / Math.log(k));
return parseFloat((bytes / Math.pow(k, i)).toFixed(dm)) + " " + sizes[i];
}