Files: 3451510316992d414ec76ba5b29681fe359b7428 / lib / depject / sheet / profiles.js
2892 bytesRaw
1 | const { h, map, computed, Value, lookup } = require('mutant') |
2 | const nest = require('depnest') |
3 | const catchLinks = require('../../catch-links') |
4 | const displaySheet = require('../../sheet/display') |
5 | |
6 | exports.needs = nest({ |
7 | 'contact.html.followToggle': 'first', |
8 | 'profile.obs.rank': 'first', |
9 | 'about.html.image': 'first', |
10 | 'about.obs.name': 'first', |
11 | 'app.navigate': 'first', |
12 | 'intl.sync.i18n': 'first' |
13 | }) |
14 | |
15 | exports.gives = nest('sheet.profiles') |
16 | |
17 | exports.create = function (api) { |
18 | const i18n = api.intl.sync.i18n |
19 | return nest('sheet.profiles', function (ids, title) { |
20 | displaySheet(close => { |
21 | const currentFilter = Value() |
22 | const nameLookup = lookup(ids, (id) => { |
23 | return [id, api.about.obs.name(id)] |
24 | }) |
25 | const filteredIds = computed([ids, nameLookup, currentFilter], (ids, nameLookup, filter) => { |
26 | if (filter) { |
27 | const result = [] |
28 | for (const k in nameLookup) { |
29 | if ((nameLookup[k] && nameLookup[k].toLowerCase().includes(filter.toLowerCase())) || k === filter) { |
30 | result.push(k) |
31 | } |
32 | } |
33 | return result |
34 | } else { |
35 | return ids |
36 | } |
37 | }) |
38 | const content = h('div', { |
39 | style: { padding: '20px' } |
40 | }, [ |
41 | h('h2', { |
42 | style: { 'font-weight': 'normal' } |
43 | }, [ |
44 | title, |
45 | h('input', { |
46 | type: 'search', |
47 | classList: 'search', |
48 | placeholder: i18n('filter names'), |
49 | 'ev-input': function (ev) { |
50 | currentFilter.set(ev.target.value) |
51 | }, |
52 | hooks: [FocusHook()], |
53 | style: { |
54 | float: 'right', |
55 | 'font-size': '100%' |
56 | } |
57 | }) |
58 | ]), |
59 | renderContactBlock(filteredIds) |
60 | ]) |
61 | |
62 | catchLinks(content, (href, external, anchor) => { |
63 | if (!external) { |
64 | api.app.navigate(href, anchor) |
65 | close() |
66 | } |
67 | }) |
68 | |
69 | return { |
70 | content, |
71 | footer: [ |
72 | h('button -close', { |
73 | 'ev-click': close |
74 | }, i18n('Close')) |
75 | ] |
76 | } |
77 | }) |
78 | }) |
79 | |
80 | function renderContactBlock (profiles) { |
81 | profiles = api.profile.obs.rank(profiles) |
82 | return [ |
83 | h('div', { |
84 | classList: 'ProfileList' |
85 | }, [ |
86 | map(profiles, (id) => { |
87 | return h('a.profile', { |
88 | href: id, |
89 | title: id |
90 | }, [ |
91 | h('div.avatar', [api.about.html.image(id)]), |
92 | h('div.main', [ |
93 | h('div.name', [api.about.obs.name(id)]) |
94 | ]), |
95 | h('div.buttons', [ |
96 | api.contact.html.followToggle(id, { block: false }) |
97 | ]) |
98 | ]) |
99 | }, { nextTime: true, maxTime: 10 }) |
100 | ]) |
101 | ] |
102 | } |
103 | } |
104 | |
105 | function FocusHook () { |
106 | return function (element) { |
107 | setTimeout(() => { |
108 | element.focus() |
109 | element.select() |
110 | }, 5) |
111 | } |
112 | } |
113 |
Built with git-ssb-web