Add followers/follows list

This commit is contained in:
Jonathan Staab 2023-02-09 10:26:09 -06:00
parent f67435395c
commit 9b276885e6
8 changed files with 82 additions and 23 deletions

View File

@ -20,6 +20,7 @@
import Spinner from 'src/partials/Spinner.svelte'
import Modal from 'src/partials/Modal.svelte'
import SignUp from "src/views/SignUp.svelte"
import PersonList from "src/views/PersonList.svelte"
import PrivKeyLogin from "src/views/PrivKeyLogin.svelte"
import PubKeyLogin from "src/views/PubKeyLogin.svelte"
import NoteDetail from "src/views/NoteDetail.svelte"
@ -348,6 +349,8 @@
<PubKeyLogin />
{:else if $modal.type === 'person/settings'}
<PersonSettings />
{:else if $modal.type === 'person/list'}
<PersonList pubkeys={$modal.pubkeys} />
{:else if $modal.type === 'message'}
<Content size="lg">
<div class="text-center">{$modal.message}</div>

View File

@ -0,0 +1,29 @@
<script lang="ts">
import {last} from 'ramda'
import {ellipsize} from 'hurdak/lib/hurdak'
import {renderContent} from "src/util/html"
import {displayPerson} from "src/util/nostr"
import {routes} from "src/app/ui"
export let person
</script>
<a
href={routes.person(person.pubkey)}
class="flex gap-4 border-l-2 border-solid border-dark hover:bg-black hover:border-accent transition-all py-3 px-6 overflow-hidden">
<div
class="overflow-hidden w-12 h-12 rounded-full bg-cover bg-center shrink-0 border border-solid border-white"
style="background-image: url({person.picture})" />
<div class="flex-grow">
<div class="flex gap-2 items-center justify-between">
<h1 class="text-2xl">{displayPerson(person)}</h1>
{#if person.verified_as}
<div class="flex gap-1 text-sm">
<i class="fa fa-user-check text-accent" />
<span class="text-light">{last(person.verified_as.split('@'))}</span>
</div>
{/if}
</div>
<p>{@html renderContent(ellipsize(person.about || '', 140))}</p>
</div>
</a>

View File

@ -6,11 +6,12 @@
import {database} from 'src/agent'
import {alerts} from 'src/app'
import Note from 'src/partials/Note.svelte'
import Spinner from 'src/partials/Spinner.svelte'
import Content from 'src/partials/Content.svelte'
import Like from 'src/partials/Like.svelte'
let limit = 0
let notes = []
let notes = null
onMount(async () => {
alerts.lastCheckedAlerts.set(now())
@ -25,6 +26,7 @@
})
</script>
{#if notes}
<Content>
{#each notes as e (e.id)}
<div in:fly={{y: 20}}>
@ -40,3 +42,6 @@
</Content>
{/each}
</Content>
{:else}
<Spinner />
{/if}

View File

@ -6,7 +6,7 @@
import {fly} from 'svelte/transition'
import {navigate} from 'svelte-routing'
import {renderContent} from 'src/util/html'
import {displayPerson} from 'src/util/nostr'
import {displayPerson, Tags} from 'src/util/nostr'
import Tabs from "src/partials/Tabs.svelte"
import Content from "src/partials/Content.svelte"
import Anchor from "src/partials/Anchor.svelte"
@ -61,6 +61,16 @@
const setActiveTab = tab => navigate(routes.person(pubkey, tab))
const showFollows = () => {
const pubkeys = Tags.wrap(person.petnames).pubkeys()
modal.set({type: 'person/list', pubkeys})
}
const showFollowers = () => {
modal.set({type: 'person/list', pubkeys: Array.from(followers)})
}
const follow = async () => {
const relay = first(relays || getRelays(pubkey))
const tag = ["p", pubkey, relay.url, person.name || ""]
@ -131,8 +141,12 @@
<p>{@html renderContent(person.about || '')}</p>
{#if person?.petnames}
<div class="flex gap-8">
<div><strong>{person.petnames.length}</strong> following</div>
<div><strong>{followersCount}</strong> followers</div>
<button on:click={showFollows}>
<strong>{person.petnames.length}</strong> following
</button>
<button on:click={showFollowers}>
<strong>{followersCount}</strong> followers
</button>
</div>
{/if}
</div>

View File

@ -1,5 +1,5 @@
<script>
import {pluck, objOf} from 'ramda'
import {pluck, objOf, fromPairs} from 'ramda'
import {noop, createMap} from 'hurdak/lib/hurdak'
import {onMount} from 'svelte'
import {get} from 'svelte/store'
@ -44,7 +44,7 @@
// Attempt to connect so we can show status
relays.forEach(relay => pool.connect(relay.url))
status = Object.fromEntries(
status = fromPairs(
pool.getConnections().map(({url, status, stats}) => {
// Be more strict here than with alerts
if (status === 'ready' && stats.timer / stats.count > 1000) {

View File

@ -26,6 +26,9 @@ export class Tags {
relays() {
return uniq(flatten(this.tags).filter(isRelay)).map(objOf('url'))
}
pubkeys() {
return this.type("p").values().all()
}
values() {
return new Tags(this.tags.map(t => t[1]))
}

View File

@ -0,0 +1,18 @@
<script type="ts">
import Content from 'src/partials/Content.svelte'
import PersonInfo from 'src/partials/PersonInfo.svelte'
import {database, getRelays} from 'src/agent'
import loaders from 'src/app/loaders'
export let pubkeys
const people = database.watch('people', people => people.all({pubkey: pubkeys}))
loaders.loadPeople(getRelays(), pubkeys)
</script>
<Content gap={2}>
{#each ($people || []) as person}
<PersonInfo {person} />
{/each}
</Content>

View File

@ -1,10 +1,7 @@
<script>
import {ellipsize} from 'hurdak/lib/hurdak'
import {fuzzy} from "src/util/misc"
import {renderContent} from "src/util/html"
import {displayPerson} from "src/util/nostr"
import PersonInfo from 'src/partials/PersonInfo.svelte'
import {user, database} from 'src/agent'
import {routes} from "src/app/ui"
export let q
@ -15,18 +12,8 @@
})
</script>
{#each (search ? search(q) : []).slice(0, 30) as p (p.pubkey)}
{#if p.pubkey !== $user.pubkey}
<a href={routes.person(p.pubkey)} class="flex gap-4">
<div
class="overflow-hidden w-12 h-12 rounded-full bg-cover bg-center shrink-0 border border-solid border-white"
style="background-image: url({p.picture})" />
<div class="flex-grow">
<div class="flex gap-2 items-center justify-between">
<h1 class="text-2xl">{displayPerson(p)}</h1>
</div>
<p>{@html renderContent(ellipsize(p.about || '', 140))}</p>
</div>
</a>
{#each (search ? search(q) : []).slice(0, 30) as person (person.pubkey)}
{#if person.pubkey !== $user.pubkey}
<PersonInfo {person} />
{/if}
{/each}