Merge pull request #1463 from pietervdvn/clsx

Introduce tailwind merge package
This commit is contained in:
Pieter Vander Vennet 2023-06-15 10:33:05 +02:00 committed by GitHub
commit 19ab941287
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
19 changed files with 70 additions and 46 deletions

View file

@ -6,15 +6,15 @@
import SubtleButton from "./SubtleButton.svelte" import SubtleButton from "./SubtleButton.svelte"
import { ChevronLeftIcon } from "@rgossiaux/svelte-heroicons/solid" import { ChevronLeftIcon } from "@rgossiaux/svelte-heroicons/solid"
import { createEventDispatcher } from "svelte" import { createEventDispatcher } from "svelte"
import { twMerge } from "tailwind-merge"
const dispatch = createEventDispatcher<{ click }>() const dispatch = createEventDispatcher<{ click }>()
export let clss = "" export let clss: string | undefined = undefined
</script> </script>
<SubtleButton <SubtleButton
on:click={() => dispatch("click")} on:click={() => dispatch("click")}
options={{ extraClasses: clss + " flex items-center" }} options={{ extraClasses: twMerge("flex items-center", clss) }}>
>
<ChevronLeftIcon class="h-12 w-12" slot="image" /> <ChevronLeftIcon class="h-12 w-12" slot="image" />
<slot slot="message" /> <slot slot="message" />
</SubtleButton> </SubtleButton>

View file

@ -11,7 +11,7 @@
} }
} }
export let clss = "" export let clss: string | undefined = undefined
</script> </script>
{#if src !== undefined} {#if src !== undefined}

View file

@ -6,7 +6,7 @@
import Svg from "../../Svg" import Svg from "../../Svg"
export let osmConnection: OsmConnection export let osmConnection: OsmConnection
export let clss = "" export let clss: string | undefined = undefined
</script> </script>
<button class={clss} on:click={() => osmConnection.AttemptLogin()}> <button class={clss} on:click={() => osmConnection.AttemptLogin()}>

View file

@ -1,5 +1,6 @@
<script lang="ts"> <script lang="ts">
import { createEventDispatcher } from "svelte" import { createEventDispatcher } from "svelte"
import { twJoin } from "tailwind-merge"
/** /**
* A round button with an icon and possible a small text, which hovers above the map * A round button with an icon and possible a small text, which hovers above the map
@ -10,7 +11,6 @@
<button <button
on:click={(e) => dispatch("click", e)} on:click={(e) => dispatch("click", e)}
class={"pointer-events-auto m-0.5 h-fit w-fit rounded-full p-0.5 sm:p-1 md:m-1 " + cls} class={twJoin("pointer-events-auto m-0.5 h-fit w-fit rounded-full p-0.5 sm:p-1 md:m-1", cls)}>
>
<slot /> <slot />
</button> </button>

View file

@ -6,16 +6,16 @@
import SubtleButton from "./SubtleButton.svelte" import SubtleButton from "./SubtleButton.svelte"
import { ChevronRightIcon } from "@rgossiaux/svelte-heroicons/solid" import { ChevronRightIcon } from "@rgossiaux/svelte-heroicons/solid"
import { createEventDispatcher } from "svelte" import { createEventDispatcher } from "svelte"
import { twMerge } from "tailwind-merge"
const dispatch = createEventDispatcher<{ click }>() const dispatch = createEventDispatcher<{ click }>()
export let clss: string = "" export let clss: string | undefined = undefined
</script> </script>
<SubtleButton <SubtleButton
on:click={() => dispatch("click")} on:click={() => dispatch("click")}
options={{ extraClasses: clss + " flex items-center" }} options={{ extraClasses: twMerge("flex items-center", clss) }}>
>
<slot name="image" slot="image" /> <slot name="image" slot="image" />
<div class="flex w-full items-center justify-between" slot="message"> <div class="flex w-full items-center justify-between" slot="message">
<slot /> <slot />

View file

@ -2,23 +2,22 @@
import { createEventDispatcher } from "svelte" import { createEventDispatcher } from "svelte"
import BaseUIElement from "../BaseUIElement" import BaseUIElement from "../BaseUIElement"
import Img from "./Img" import Img from "./Img"
import { twJoin, twMerge } from "tailwind-merge"
export let imageUrl: string | BaseUIElement = undefined export let imageUrl: string | BaseUIElement = undefined
export let message: string | BaseUIElement = undefined export const message: string | BaseUIElement = undefined
export let options: { export let options: {
imgSize?: string imgSize?: string
extraClasses?: string extraClasses?: string
} = {} } = {}
let imgClasses = "block justify-center shrink-0 mr-4 " + (options?.imgSize ?? "h-11 w-11") let imgClasses = twJoin("block justify-center shrink-0 mr-4", options?.imgSize ?? "h-11 w-11")
const dispatch = createEventDispatcher<{ click }>() const dispatch = createEventDispatcher<{ click }>()
</script> </script>
<button <button
class={(options.extraClasses ?? "") + " secondary no-image-background"} class={twMerge(options.extraClasses, "secondary no-image-background")}
target={options?.newTab ? "_blank" : ""} on:click={(e) => dispatch("click", e)}>
on:click={(e) => dispatch("click", e)}
>
<slot name="image"> <slot name="image">
{#if imageUrl !== undefined} {#if imageUrl !== undefined}
{#if typeof imageUrl === "string"} {#if typeof imageUrl === "string"}

View file

@ -1,5 +1,6 @@
<script lang="ts"> <script lang="ts">
import { onMount } from "svelte" import { onMount } from "svelte"
import { twJoin, twMerge } from "tailwind-merge"
import BaseUIElement from "../BaseUIElement" import BaseUIElement from "../BaseUIElement"
import Img from "./Img" import Img from "./Img"
@ -8,11 +9,11 @@
export let newTab = false export let newTab = false
export let options: { export let options: {
imgSize?: string imgSize?: string
// extraClasses?: string extraClasses?: string
} = {} } = {}
let imgElem: HTMLElement let imgElem: HTMLElement
let imgClasses = "block justify-center shrink-0 mr-4 " + (options?.imgSize ?? "h-11 w-11") let imgClasses = twJoin("block justify-center shrink-0 mr-4", options?.imgSize ?? "h-11 w-11")
onMount(() => { onMount(() => {
// Image // Image
@ -30,7 +31,7 @@
</script> </script>
<a <a
class={(options.extraClasses ?? "") + " button text-ellipsis"} class={twMerge(options.extraClasses, "button text-ellipsis")}
{href} {href}
target={newTab ? "_blank" : undefined} target={newTab ? "_blank" : undefined}
> >

View file

@ -5,6 +5,7 @@
import { Tab, TabGroup, TabList, TabPanel, TabPanels } from "@rgossiaux/svelte-headlessui" import { Tab, TabGroup, TabList, TabPanel, TabPanels } from "@rgossiaux/svelte-headlessui"
import { UIEventSource } from "../../Logic/UIEventSource" import { UIEventSource } from "../../Logic/UIEventSource"
import { twJoin } from "tailwind-merge"
export let tab: UIEventSource<number> export let tab: UIEventSource<number>
let tabElements: HTMLElement[] = [] let tabElements: HTMLElement[] = []
@ -29,35 +30,35 @@
<div class="interactive sticky top-0 flex items-center justify-between"> <div class="interactive sticky top-0 flex items-center justify-between">
<TabList class="flex flex-wrap"> <TabList class="flex flex-wrap">
{#if $$slots.title1} {#if $$slots.title1}
<Tab class={({ selected }) => "tab " + (selected ? "primary" : "")}> <Tab class={({ selected }) => twJoin("tab", selected && "primary")}>
<div bind:this={tabElements[0]} class="flex"> <div bind:this={tabElements[0]} class="flex">
<slot name="title0">Tab 0</slot> <slot name="title0">Tab 0</slot>
</div> </div>
</Tab> </Tab>
{/if} {/if}
{#if $$slots.title1} {#if $$slots.title1}
<Tab class={({ selected }) => "tab " + (selected ? "primary" : "")}> <Tab class={({ selected }) => twJoin("tab", selected && "primary")}>
<div bind:this={tabElements[1]} class="flex"> <div bind:this={tabElements[1]} class="flex">
<slot name="title1" /> <slot name="title1" />
</div> </div>
</Tab> </Tab>
{/if} {/if}
{#if $$slots.title2} {#if $$slots.title2}
<Tab class={({ selected }) => "tab " + (selected ? "primary" : "")}> <Tab class={({ selected }) => twJoin("tab", selected && "primary")}>
<div bind:this={tabElements[2]} class="flex"> <div bind:this={tabElements[2]} class="flex">
<slot name="title2" /> <slot name="title2" />
</div> </div>
</Tab> </Tab>
{/if} {/if}
{#if $$slots.title3} {#if $$slots.title3}
<Tab class={({ selected }) => "tab " + (selected ? "primary" : "")}> <Tab class={({ selected }) => twJoin("tab", selected && "primary")}>
<div bind:this={tabElements[3]} class="flex"> <div bind:this={tabElements[3]} class="flex">
<slot name="title3" /> <slot name="title3" />
</div> </div>
</Tab> </Tab>
{/if} {/if}
{#if $$slots.title4} {#if $$slots.title4}
<Tab class={({ selected }) => "tab " + (selected ? "primary" : "")}> <Tab class={({ selected }) => twJoin("tab", selected && "primary")}>
<div bind:this={tabElements[4]} class="flex"> <div bind:this={tabElements[4]} class="flex">
<slot name="title4" /> <slot name="title4" />
</div> </div>

View file

@ -11,7 +11,7 @@
export let theme: LayoutInformation export let theme: LayoutInformation
export let isCustom: boolean = false export let isCustom: boolean = false
export let userDetails: UIEventSource<UserDetails> export let userDetails: UIEventSource<UserDetails>
export let state: { layoutToUse: { id: string }; osmConnection: OsmConnection } export let state: { layoutToUse?: { id: string }; osmConnection: OsmConnection }
$: title = new Translation( $: title = new Translation(
theme.title, theme.title,

View file

@ -10,6 +10,7 @@
import If from "../Base/If.svelte" import If from "../Base/If.svelte"
import { UIEventSource } from "../../Logic/UIEventSource" import { UIEventSource } from "../../Logic/UIEventSource"
import { SearchIcon } from "@rgossiaux/svelte-heroicons/solid" import { SearchIcon } from "@rgossiaux/svelte-heroicons/solid"
import { twJoin } from "tailwind-merge"
/** /**
* The theme introduction panel * The theme introduction panel
@ -78,9 +79,8 @@ loginStatus.SetClass("block mt-6 pt-2 md:border-t-2 border-dotted border-gray-40
/> />
</div> </div>
<button <button
class={"flex items-center justify-between gap-x-2 " + (searchEnabled ? "" : "disabled")} class={twJoin("flex items-center justify-between gap-x-2", !searchEnabled && "disabled")}
on:click={() => triggerSearch.ping()} on:click={() => triggerSearch.ping()}>
>
<Tr t={Translations.t.general.search.searchShort} /> <Tr t={Translations.t.general.search.searchShort} />
<SearchIcon class="h-6 w-6" /> <SearchIcon class="h-6 w-6" />
</button> </button>

View file

@ -1,4 +1,5 @@
<script lang="ts"> <script lang="ts">
import { twJoin } from "tailwind-merge"
import { Store, Stores, UIEventSource } from "../../../Logic/UIEventSource" import { Store, Stores, UIEventSource } from "../../../Logic/UIEventSource"
/** /**
@ -106,8 +107,10 @@
{#each $floors as floor, i} {#each $floors as floor, i}
<button <button
style={`height: ${HEIGHT}px; width: ${HEIGHT}px`} style={`height: ${HEIGHT}px; width: ${HEIGHT}px`}
class={"content-box m-0 flex items-center justify-center border-2 border-gray-300 " + class={twJoin(
(i === (forceIndex ?? $index) ? "selected" : "")} "content-box m-0 flex items-center justify-center border-2 border-gray-300",
i === (forceIndex ?? $index) && "selected"
)}
on:click={() => { on:click={() => {
forceIndex = i forceIndex = i
}} }}
@ -124,8 +127,7 @@
draggable="false" draggable="false"
on:mousedown={click} on:mousedown={click}
src="./assets/svg/elevator.svg" src="./assets/svg/elevator.svg"
style={" top: " + top + "px;"} style={`top: ${top}px;`} />
/>
</div> </div>
</div> </div>

View file

@ -32,6 +32,7 @@
import ToSvelte from "../../Base/ToSvelte.svelte" import ToSvelte from "../../Base/ToSvelte.svelte"
import Svg from "../../../Svg" import Svg from "../../../Svg"
import OpenBackgroundSelectorButton from "../../BigComponents/OpenBackgroundSelectorButton.svelte"; import OpenBackgroundSelectorButton from "../../BigComponents/OpenBackgroundSelectorButton.svelte";
import { twJoin } from "tailwind-merge"
export let coordinate: { lon: number; lat: number } export let coordinate: { lon: number; lat: number }
export let state: SpecialVisualizationState export let state: SpecialVisualizationState
@ -319,8 +320,8 @@
/> />
</div> </div>
<div class={(preciseInputIsTapped ? "" : "hidden") + " absolute top-4 flex justify-center w-full"}> <div class={twJoin(!preciseInputIsTapped && "hidden", "absolute top-4 flex justify-center w-full")}>
<NextButton on:click={confirm} clss="primary w-fit "> <NextButton on:click={confirm} clss="primary w-fit">
<div class="flex w-full justify-end gap-x-2"> <div class="flex w-full justify-end gap-x-2">
<Tr t={Translations.t.general.add.confirmLocation}/> <Tr t={Translations.t.general.add.confirmLocation}/>
</div> </div>

View file

@ -18,6 +18,7 @@
import ChangeTagAction from "../../../Logic/Osm/Actions/ChangeTagAction" import ChangeTagAction from "../../../Logic/Osm/Actions/ChangeTagAction"
import Loading from "../../Base/Loading.svelte" import Loading from "../../Base/Loading.svelte"
import { DeleteFlowState } from "./DeleteFlowState" import { DeleteFlowState } from "./DeleteFlowState"
import { twJoin } from "tailwind-merge"
export let state: SpecialVisualizationState export let state: SpecialVisualizationState
export let deleteConfig: DeleteConfig export let deleteConfig: DeleteConfig
@ -111,11 +112,10 @@
<button <button
slot="save-button" slot="save-button"
on:click={onDelete} on:click={onDelete}
class={(selectedTags === undefined ? "disabled" : "") + " primary flex bg-red-600"} class={twJoin((selectedTags === undefined && "disabled"), "primary flex bg-red-600")}
> >
<TrashIcon <TrashIcon
class={"ml-1 mr-2 h-6 w-6 rounded-full p-1 " + class={twJoin("ml-1 mr-2 h-6 w-6 rounded-full p-1", selectedTags !== undefined && "bg-red-600")}
(selectedTags !== undefined ? "bg-red-600" : "")}
/> />
<Tr t={t.delete} /> <Tr t={t.delete} />
</button> </button>

View file

@ -8,6 +8,7 @@
import { UIEventSource } from "../../../Logic/UIEventSource" import { UIEventSource } from "../../../Logic/UIEventSource"
import { onDestroy } from "svelte" import { onDestroy } from "svelte"
import LayerConfig from "../../../Models/ThemeConfig/LayerConfig" import LayerConfig from "../../../Models/ThemeConfig/LayerConfig"
import { twMerge } from "tailwind-merge"
export let tags: UIEventSource<Record<string, string> | undefined> export let tags: UIEventSource<Record<string, string> | undefined>
let _tags: Record<string, string> let _tags: Record<string, string>
@ -17,7 +18,7 @@
export let selectedElement: Feature export let selectedElement: Feature
export let layer: LayerConfig export let layer: LayerConfig
export let config: TagRenderingConfig export let config: TagRenderingConfig
export let extraClasses: string = "" export let extraClasses: string | undefined = undefined
if (config === undefined) { if (config === undefined) {
throw "Config is undefined in tagRenderingAnswer" throw "Config is undefined in tagRenderingAnswer"
@ -28,12 +29,10 @@
trs = Utils.NoNull(config?.GetRenderValues(_tags)) trs = Utils.NoNull(config?.GetRenderValues(_tags))
}) })
) )
let classes = ""
$: classes = config?.classes?.join(" ") ?? ""
</script> </script>
{#if config !== undefined && (config?.condition === undefined || config.condition.matchesProperties(_tags))} {#if config !== undefined && (config?.condition === undefined || config.condition.matchesProperties(_tags))}
<div class={"link-underline inline-block w-full " + classes + " " + extraClasses}> <div class={twMerge("link-underline inline-block w-full", config?.classes, extraClasses)}>
{#if trs.length === 1} {#if trs.length === 1}
<TagRenderingMapping mapping={trs[0]} {tags} {state} {selectedElement} {layer} /> <TagRenderingMapping mapping={trs[0]} {tags} {state} {selectedElement} {layer} />
{/if} {/if}

View file

@ -5,6 +5,7 @@
import type { Feature } from "geojson" import type { Feature } from "geojson"
import { UIEventSource } from "../../../Logic/UIEventSource" import { UIEventSource } from "../../../Logic/UIEventSource"
import LayerConfig from "../../../Models/ThemeConfig/LayerConfig" import LayerConfig from "../../../Models/ThemeConfig/LayerConfig"
import { twJoin } from "tailwind-merge"
export let selectedElement: Feature export let selectedElement: Feature
export let tags: UIEventSource<Record<string, string>> export let tags: UIEventSource<Record<string, string>>
@ -23,12 +24,15 @@
| "medium-height" | "medium-height"
| "large-height" | "large-height"
} }
let iconclass = "mapping-icon-" + mapping.iconClass
</script> </script>
{#if mapping.icon !== undefined} {#if mapping.icon !== undefined}
<div class="inline-flex"> <div class="inline-flex">
<img class={iconclass + " mr-1"} src={mapping.icon} /> <img
class={twJoin(`mapping-icon-${mapping.iconClass}`, "mr-1")}
src={mapping.icon}
aria-hidden="true"
alt="" />
<SpecialTranslation t={mapping.then} {tags} {state} {layer} feature={selectedElement} /> <SpecialTranslation t={mapping.then} {tags} {state} {layer} feature={selectedElement} />
</div> </div>
{:else if mapping.then !== undefined} {:else if mapping.then !== undefined}

View file

@ -14,6 +14,7 @@
import { TagsFilter } from "../../../Logic/Tags/TagsFilter" import { TagsFilter } from "../../../Logic/Tags/TagsFilter"
import { onDestroy } from "svelte" import { onDestroy } from "svelte"
import TagRenderingMapping from "./TagRenderingMapping.svelte" import TagRenderingMapping from "./TagRenderingMapping.svelte"
import { twJoin } from "tailwind-merge"
export let selectedElement: Feature export let selectedElement: Feature
export let tags: UIEventSource<Record<string, string>> export let tags: UIEventSource<Record<string, string>>
@ -82,7 +83,7 @@
</script> </script>
{#if $matchesTerm && !$mappingIsHidden} {#if $matchesTerm && !$mappingIsHidden}
<label class={"flex " + (mappingIsSelected ? "checked" : "")}> <label class={twJoin("flex", mappingIsSelected && "checked")}>
<slot /> <slot />
<TagRenderingMapping {mapping} {tags} {state} {selectedElement} {layer} /> <TagRenderingMapping {mapping} {tags} {state} {selectedElement} {layer} />
</label> </label>

View file

@ -21,6 +21,7 @@
import Constants from "../../../Models/Constants" import Constants from "../../../Models/Constants"
import { Unit } from "../../../Models/Unit" import { Unit } from "../../../Models/Unit"
import UserRelatedState from "../../../Logic/State/UserRelatedState" import UserRelatedState from "../../../Logic/State/UserRelatedState"
import { twJoin } from "tailwind-merge"
export let config: TagRenderingConfig export let config: TagRenderingConfig
export let tags: UIEventSource<Record<string, string>> export let tags: UIEventSource<Record<string, string>>
@ -276,8 +277,7 @@
<slot name="save-button" {selectedTags}> <slot name="save-button" {selectedTags}>
<button <button
on:click={onSave} on:click={onSave}
class={(selectedTags === undefined ? "disabled" : "button-shadow") + " primary"} class={twJoin(selectedTags === undefined ? "disabled" : "button-shadow", "primary")}>
>
<Tr t={Translations.t.general.save} /> <Tr t={Translations.t.general.save} />
</button> </button>
</slot> </slot>

15
package-lock.json generated
View file

@ -47,6 +47,7 @@
"prompt-sync": "^4.2.0", "prompt-sync": "^4.2.0",
"showdown": "^2.1.0", "showdown": "^2.1.0",
"svg-path-parser": "^1.1.0", "svg-path-parser": "^1.1.0",
"tailwind-merge": "^1.13.1",
"tailwindcss": "^3.1.8", "tailwindcss": "^3.1.8",
"vite-node": "^0.28.3", "vite-node": "^0.28.3",
"vitest": "^0.28.3", "vitest": "^0.28.3",
@ -10008,6 +10009,15 @@
"resolved": "https://registry.npmjs.org/symbol-tree/-/symbol-tree-3.2.4.tgz", "resolved": "https://registry.npmjs.org/symbol-tree/-/symbol-tree-3.2.4.tgz",
"integrity": "sha512-9QNk5KwDF+Bvz+PyObkmSYjI5ksVUYtjW7AU22r2NKcfLJcXp96hkDWU3+XndOsUb+AQ9QhfzfCT2O+CNWT5Tw==" "integrity": "sha512-9QNk5KwDF+Bvz+PyObkmSYjI5ksVUYtjW7AU22r2NKcfLJcXp96hkDWU3+XndOsUb+AQ9QhfzfCT2O+CNWT5Tw=="
}, },
"node_modules/tailwind-merge": {
"version": "1.13.1",
"resolved": "https://registry.npmjs.org/tailwind-merge/-/tailwind-merge-1.13.1.tgz",
"integrity": "sha512-tRtRN22TDokGi2TuYSvuHQuuW6BJ/zlUEG+iYpAQ9i66msc/0eU/+HPccbPnNNH0mCPp0Ob8thaC8Uy9CxHitQ==",
"funding": {
"type": "github",
"url": "https://github.com/sponsors/dcastil"
}
},
"node_modules/tailwindcss": { "node_modules/tailwindcss": {
"version": "3.2.4", "version": "3.2.4",
"resolved": "https://registry.npmjs.org/tailwindcss/-/tailwindcss-3.2.4.tgz", "resolved": "https://registry.npmjs.org/tailwindcss/-/tailwindcss-3.2.4.tgz",
@ -19611,6 +19621,11 @@
"resolved": "https://registry.npmjs.org/symbol-tree/-/symbol-tree-3.2.4.tgz", "resolved": "https://registry.npmjs.org/symbol-tree/-/symbol-tree-3.2.4.tgz",
"integrity": "sha512-9QNk5KwDF+Bvz+PyObkmSYjI5ksVUYtjW7AU22r2NKcfLJcXp96hkDWU3+XndOsUb+AQ9QhfzfCT2O+CNWT5Tw==" "integrity": "sha512-9QNk5KwDF+Bvz+PyObkmSYjI5ksVUYtjW7AU22r2NKcfLJcXp96hkDWU3+XndOsUb+AQ9QhfzfCT2O+CNWT5Tw=="
}, },
"tailwind-merge": {
"version": "1.13.1",
"resolved": "https://registry.npmjs.org/tailwind-merge/-/tailwind-merge-1.13.1.tgz",
"integrity": "sha512-tRtRN22TDokGi2TuYSvuHQuuW6BJ/zlUEG+iYpAQ9i66msc/0eU/+HPccbPnNNH0mCPp0Ob8thaC8Uy9CxHitQ=="
},
"tailwindcss": { "tailwindcss": {
"version": "3.2.4", "version": "3.2.4",
"resolved": "https://registry.npmjs.org/tailwindcss/-/tailwindcss-3.2.4.tgz", "resolved": "https://registry.npmjs.org/tailwindcss/-/tailwindcss-3.2.4.tgz",

View file

@ -99,6 +99,7 @@
"prompt-sync": "^4.2.0", "prompt-sync": "^4.2.0",
"showdown": "^2.1.0", "showdown": "^2.1.0",
"svg-path-parser": "^1.1.0", "svg-path-parser": "^1.1.0",
"tailwind-merge": "^1.13.1",
"tailwindcss": "^3.1.8", "tailwindcss": "^3.1.8",
"vite-node": "^0.28.3", "vite-node": "^0.28.3",
"vitest": "^0.28.3", "vitest": "^0.28.3",