Introduce state controllers, avoid double submit on group create. Fixes #326

This commit is contained in:
Jon Staab 2024-05-20 15:20:17 -07:00
parent c0e870907d
commit b6027a608f
4 changed files with 69 additions and 30 deletions

View File

@ -29,6 +29,7 @@
- [x] Only tag parent event in reactions
- [x] Fix url hashes, render code blocks
- [x] Use bitcoin connect instead of webln
- [x] Fix double submit on group create dialog
# 0.4.4

View File

@ -1,6 +1,7 @@
<script lang="ts">
import {debounce} from "throttle-debounce"
import {isSearchFeed, makeSearchFeed, makeScopeFeed, Scope, getFeedArgs} from "@welshman/feeds"
import {boolCtrl} from 'src/partials/utils'
import Modal from "src/partials/Modal.svelte"
import Input from "src/partials/Input.svelte"
import Popover2 from "src/partials/Popover2.svelte"
@ -17,25 +18,19 @@
feed.definition = normalizeFeedDefinition(feed.definition)
const form = boolCtrl()
const listMenu = boolCtrl()
const followsFeed = makeFeed({definition: normalizeFeedDefinition(makeScopeFeed(Scope.Follows))})
const networkFeed = makeFeed({definition: normalizeFeedDefinition(makeScopeFeed(Scope.Network))})
const openListMenu = () => {
listMenuIsOpen = true
}
const closeListMenu = () => {
listMenuIsOpen = false
}
const openForm = () => {
savePoint = {...feed}
formIsOpen = true
$form.enable()
}
const closeForm = () => {
feed = savePoint
formIsOpen = false
$form.disable()
}
const getSearch = definition => (getFeedArgs(definition)?.find(isSearchFeed)?.[1] as string) || ""
@ -43,8 +38,8 @@
const setFeedDefinition = definition => {
feed.definition = definition
search = getSearch(definition)
formIsOpen = false
closeListMenu()
$form.disable()
$listMenu.disable()
updateFeed(feed)
}
@ -88,8 +83,6 @@
})
let savePoint
let formIsOpen = false
let listMenuIsOpen = false
let search = getSearch(feed.definition)
$: subFeeds = getFeedArgs(feed.definition as any)
@ -111,11 +104,11 @@
<div class="relative lg:hidden">
<div
class="flex h-7 w-6 cursor-pointer items-center justify-center rounded bg-neutral-700 text-center text-neutral-50 transition-colors hover:bg-neutral-600"
on:click={openListMenu}>
on:click={$listMenu.enable}>
<i class="fa fa-sm fa-ellipsis-v" />
</div>
{#if listMenuIsOpen}
<Popover2 absolute hideOnClick onClose={closeListMenu} class="right-0 top-8 w-60">
{#if $listMenu.enabled}
<Popover2 absolute hideOnClick onClose={$listMenu.disable} class="right-0 top-8 w-60">
<Menu>
<MenuItem inert class="staatliches bg-neutral-800 text-lg shadow">Your Feeds</MenuItem>
<div class="max-h-96 overflow-auto">
@ -146,7 +139,7 @@
</div>
</div>
{#if formIsOpen}
{#if $form.enabled}
<Modal onEscape={closeForm}>
<FeedForm {feed} exit={exitForm} apply={() => setFeedDefinition(feed.definition)} />
</Modal>

View File

@ -20,6 +20,7 @@
import {ucFirst} from "hurdak"
import {Address} from "@welshman/util"
import {fly} from "src/util/transition"
import {formCtrl} from "src/partials/utils"
import {showInfo, showWarning} from "src/partials/Toast.svelte"
import Field from "src/partials/Field.svelte"
import FieldInline from "src/partials/FieldInline.svelte"
@ -62,23 +63,23 @@
values.feeds = values.feeds.toSpliced(i, 1)
}
const submit = async () => {
if (values.relays.length < 1) {
showWarning("At least one relay is required.")
const ctrl = formCtrl({
submit: async () => {
if (values.relays.length < 1) {
showWarning("At least one relay is required.")
} else {
await onSubmit(values)
return
}
await onSubmit(values)
showInfo("Your group has been saved!")
}
showInfo("Your group has been saved!")
}
},
})
let feedsInput
let showAdvanced = false
</script>
<form on:submit|preventDefault={submit} in:fly={{y: 20}}>
<form on:submit|preventDefault={$ctrl.submit} in:fly={{y: 20}}>
<FlexColumn>
<div class="mb-4 flex flex-col items-center justify-center">
<Heading>{ucFirst(mode)} Group</Heading>
@ -180,7 +181,7 @@
<span>Show Advanced Settings</span>
</Anchor>
{/if}
<Anchor button tag="button" type="submit">{buttonText}</Anchor>
<Anchor button loading={$ctrl.loading} tag="button" type="submit">{buttonText}</Anchor>
</div>
</FlexColumn>
</form>

44
src/partials/utils.ts Normal file
View File

@ -0,0 +1,44 @@
import {writable, assoc} from '@welshman/lib'
export const formCtrl = ({submit}) => {
const store = writable({
loading: false,
submit: async () => {
if (store.get().loading) {
return
}
store.update(assoc("loading", true))
try {
await submit()
} catch (e) {
// pass
}
store.update(assoc("loading", false))
},
})
return store
}
export const boolCtrl = ({defaultValue = false} = {}) => {
const store = writable({
enabled: defaultValue,
disable: () => store.update(assoc('enabled', false)),
enable: () => store.update(assoc('enabled', true)),
})
return store
}
export const valueCtrl = ({defaultValue = null} = {}) => {
const store = writable({
enabled: defaultValue,
clear: () => store.update(assoc('enabled', null)),
set: value => store.update(assoc('enabled', value)),
})
return store
}