mirror of
https://github.com/coracle-social/coracle.git
synced 2024-09-29 08:21:20 +00:00
Add list field to feed form
This commit is contained in:
parent
44ce59c807
commit
12f134f26c
@ -12,7 +12,7 @@
|
||||
import Toggle from "src/partials/Toggle.svelte"
|
||||
import Modal from "src/partials/Modal.svelte"
|
||||
import FeedForm from "src/app/shared/FeedForm.svelte"
|
||||
import {feedLoader, displayPubkey} from "src/engine"
|
||||
import {feedLoader, displayRelayUrl, displayPubkey} from "src/engine"
|
||||
|
||||
export let value
|
||||
|
||||
@ -71,19 +71,15 @@
|
||||
{/if}
|
||||
{#if feedType === FeedType.Relay}
|
||||
<Chip class="mb-2 mr-2 inline-block">
|
||||
On {quantify(feed[1], "relay")}
|
||||
On {feed[1].length === 1 ? displayRelayUrl(feed[1][0]) : `${feed[1].length} relays`}
|
||||
</Chip>
|
||||
{:else if feedType === FeedType.List}
|
||||
<Chip class="mb-2 mr-2 inline-block">
|
||||
From {quantify(feed.slice(1), "list")}
|
||||
</Chip>
|
||||
{:else if feedType === FeedType.LOL}
|
||||
<Chip class="mb-2 mr-2 inline-block">
|
||||
From {quantify(feed.slice(1), "list")} of lists
|
||||
From {quantify(feed.slice(1).length, "list")}
|
||||
</Chip>
|
||||
{:else if feedType === FeedType.DVM}
|
||||
<Chip class="mb-2 mr-2 inline-block">
|
||||
From {quantify(feed.slice(1), "DVM")}
|
||||
From {quantify(feed.slice(1).length, "DVM")}
|
||||
</Chip>
|
||||
{:else if feedType === FeedType.Filter}
|
||||
{#if feed.length > 2}
|
||||
|
@ -14,7 +14,7 @@
|
||||
import Select from "src/partials/Select.svelte"
|
||||
import SearchSelect from "src/partials/SearchSelect.svelte"
|
||||
import FilterField from "src/app/shared/FilterField.svelte"
|
||||
import {searchRelayUrls, displayRelayUrl} from "src/engine"
|
||||
import {searchRelayUrls, searchListAddrs, displayListByAddress, displayRelayUrl} from "src/engine"
|
||||
|
||||
export let feed
|
||||
export let onChange
|
||||
@ -40,13 +40,10 @@
|
||||
|
||||
const onTypeChange = type => setAtCursor([type])
|
||||
|
||||
const onRelayChange = urls => setAtCursor(urls, [1])
|
||||
|
||||
const displayFeed = ([type, ...feed]) =>
|
||||
switcherFn(type, {
|
||||
[FeedType.Filter]: () => quantify(feed.length, "filter"),
|
||||
[FeedType.List]: () => quantify(feed.length, "list"),
|
||||
[FeedType.LOL]: () => quantify(feed.length, "list") + " of lists",
|
||||
[FeedType.DVM]: () => quantify(feed.length, "DVM"),
|
||||
[FeedType.Relay]: () =>
|
||||
quantify(feed.slice(1).length, "feed") + " on " + quantify(feed[0].length, "relays"),
|
||||
@ -68,8 +65,7 @@
|
||||
<Field label="Feed Type">
|
||||
<Select value={feedType} onChange={onTypeChange}>
|
||||
<option value={FeedType.Filter}>Standard</option>
|
||||
<option value={FeedType.List}>List</option>
|
||||
<option value={FeedType.LOL}>List of lists</option>
|
||||
<option value={FeedType.List}>From lists</option>
|
||||
<option value={FeedType.DVM}>Data vending machine</option>
|
||||
<option value={FeedType.Relay}>Relays</option>
|
||||
<option value={FeedType.Union}>Union</option>
|
||||
@ -88,11 +84,11 @@
|
||||
multiple
|
||||
value={feed[1] || []}
|
||||
search={$searchRelayUrls}
|
||||
onChange={onRelayChange}>
|
||||
onChange={urls => setAtCursor(urls, [1])}>
|
||||
<span slot="item" let:item>{displayRelayUrl(item)}</span>
|
||||
</SearchSelect>
|
||||
<p slot="info">Select which relays you'd like to limit loading feeds from.</p>
|
||||
<p></p></Field>
|
||||
</Field>
|
||||
{:else if feedType === FeedType.Filter}
|
||||
{#each current.slice(1) as filter, filterIdx ([current.length, filterIdx].join(':'))}
|
||||
{@const feedIdx = inc(filterIdx)}
|
||||
@ -111,7 +107,19 @@
|
||||
<i class="fa fa-plus" /> Add filter
|
||||
</Anchor>
|
||||
</div>
|
||||
{:else if feedType === FeedType.List}{:else if feedType === FeedType.LOL}{:else if feedType === FeedType.DVM}{/if}
|
||||
{:else if feedType === FeedType.List}
|
||||
<Field label="List Selections">
|
||||
<SearchSelect
|
||||
multiple
|
||||
value={feed.slice(1)}
|
||||
search={$searchListAddrs}
|
||||
onChange={addrs => setAtCursor([FeedType.List, ...addrs])}>
|
||||
<span slot="item" let:item>{displayListByAddress(item)}</span>
|
||||
</SearchSelect>
|
||||
<p slot="info">Select which lists you'd like to view.</p>
|
||||
</Field>
|
||||
{:else if feedType === FeedType.DVM}
|
||||
{/if}
|
||||
{#each subFeeds as subFeed, i (displayFeed(subFeed) + i)}
|
||||
<Card class="flex items-center justify-between">
|
||||
<span class="text-lg">{displayFeed(subFeed)}</span>
|
||||
@ -133,7 +141,6 @@
|
||||
<Menu>
|
||||
<MenuItem on:click={() => addFeed(FeedType.Filter)}>Standard Feed</MenuItem>
|
||||
<MenuItem on:click={() => addFeed(FeedType.List)}>List Feed</MenuItem>
|
||||
<MenuItem on:click={() => addFeed(FeedType.LOL)}>Lists of Lists</MenuItem>
|
||||
<MenuItem on:click={() => addFeed(FeedType.DVM)}>DVM Feed</MenuItem>
|
||||
</Menu>
|
||||
</div>
|
||||
|
@ -10,6 +10,7 @@ import {
|
||||
isContextAddress,
|
||||
decodeAddress,
|
||||
} from "@welshman/util"
|
||||
import {Tracker} from "@welshman/net"
|
||||
import type {Feed, Loader} from "@welshman/feeds"
|
||||
import {FeedLoader as CoreFeedLoader, FeedType} from "@welshman/feeds"
|
||||
import {LOCAL_RELAY_URL, noteKinds, reactionKinds, repostKinds} from "src/util/nostr"
|
||||
@ -68,13 +69,14 @@ export class FeedLoader {
|
||||
}
|
||||
|
||||
const promises = []
|
||||
const tracker = new Tracker()
|
||||
|
||||
// Use relays specified in feeds
|
||||
if (relays.length > 0) {
|
||||
promises.push(load({filters, relays, onEvent}))
|
||||
promises.push(load({filters, relays, tracker, onEvent}))
|
||||
} else {
|
||||
if (!this.opts.skipCache) {
|
||||
promises.push(load({filters, relays: [LOCAL_RELAY_URL], onEvent}))
|
||||
promises.push(load({filters, relays: [LOCAL_RELAY_URL], tracker, onEvent}))
|
||||
}
|
||||
|
||||
if (!this.opts.skipNetwork) {
|
||||
@ -85,7 +87,7 @@ export class FeedLoader {
|
||||
}
|
||||
|
||||
for (const {relay, filters} of selections) {
|
||||
promises.push(load({filters, relays: [relay], onEvent}))
|
||||
promises.push(load({filters, relays: [relay], tracker, onEvent}))
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -40,9 +40,7 @@
|
||||
<Note note={$root} />
|
||||
{#if showAncestors}
|
||||
{#each $ancestors as ancestor (ancestor.id)}
|
||||
<div in:fly={{y: 20}}>
|
||||
<Note topLevel showParent={false} note={ancestor} />
|
||||
</div>
|
||||
<Note topLevel showParent={false} note={ancestor} />
|
||||
{/each}
|
||||
{:else if $ancestors.length > 0}
|
||||
<Anchor
|
||||
|
@ -1,9 +1,10 @@
|
||||
import {whereEq, sortBy} from "ramda"
|
||||
import {whereEq, pluck, sortBy} from "ramda"
|
||||
import {derivedCollection} from "@welshman/lib"
|
||||
import {pubkey} from "src/engine/session/state"
|
||||
import {deletes} from "src/engine/events/state"
|
||||
import type {List} from "./model"
|
||||
import {_lists} from "./state"
|
||||
import {getListSearch} from './utils'
|
||||
|
||||
export const lists = derivedCollection<List>("address", [_lists, deletes], ([$l, $d]) =>
|
||||
$l.filter(l => !$d.has(l.address)),
|
||||
@ -23,3 +24,7 @@ export const userLists = derivedCollection<List>("address", [lists, pubkey], ([$
|
||||
|
||||
return sortBy(getName, Array.from(m.values()))
|
||||
})
|
||||
|
||||
export const searchLists = lists.derived(getListSearch)
|
||||
|
||||
export const searchListAddrs = searchLists.derived(search => term => pluck('address', search(term)))
|
||||
|
@ -1,5 +1,6 @@
|
||||
export * from "./model"
|
||||
export * from "./state"
|
||||
export * from "./utils"
|
||||
export * from "./derived"
|
||||
export * from "./projections"
|
||||
export * from "./commands"
|
||||
|
11
src/engine/lists/utils.ts
Normal file
11
src/engine/lists/utils.ts
Normal file
@ -0,0 +1,11 @@
|
||||
import {fuzzy} from "src/util/misc"
|
||||
import type {List} from "./model"
|
||||
import {_lists} from './state'
|
||||
|
||||
export const displayList = (list: List) => list?.title || ""
|
||||
|
||||
export const displayListByAddress = (address: string) => displayList(_lists.key(address).get())
|
||||
|
||||
export const getListSearch = ($lists: List[]): ((term: string) => List[]) => {
|
||||
return fuzzy($lists, {keys: ["title", "description"]})
|
||||
}
|
@ -35,6 +35,7 @@
|
||||
|
||||
export const clearValue = () => {
|
||||
value = multiple ? [] : null
|
||||
onChange?.(value)
|
||||
}
|
||||
|
||||
export const clearTerm = () => {
|
||||
@ -47,6 +48,7 @@
|
||||
|
||||
const remove = item => {
|
||||
value = multiple ? reject(equals(item), value) : null
|
||||
onChange?.(value)
|
||||
}
|
||||
|
||||
const select = item => {
|
||||
|
@ -88,11 +88,21 @@ export const createScroller = (
|
||||
loadMore: () => Promise<void>,
|
||||
{delay = 1000, threshold = 2000, reverse = false, element}: ScrollerOpts = {},
|
||||
) => {
|
||||
const getScrollElement = () => {
|
||||
let e = element
|
||||
|
||||
while (e.parentElement && e.scrollTop === 0) {
|
||||
e = e.parentElement
|
||||
}
|
||||
|
||||
return e
|
||||
}
|
||||
|
||||
let done = false
|
||||
const check = async () => {
|
||||
// While we have empty space, fill it
|
||||
const {scrollY, innerHeight} = window
|
||||
const {scrollHeight, scrollTop} = element
|
||||
const {scrollHeight, scrollTop} = getScrollElement()
|
||||
const offset = Math.abs(scrollTop || scrollY)
|
||||
const shouldLoad = offset + innerHeight + threshold > scrollHeight
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user