|
| 1 | +import { lit as html } from '../helpers/lit.js' |
| 2 | +import { |
| 3 | + envoy, |
| 4 | + restate, |
| 5 | + // sortContactsByAlias, |
| 6 | + // filterPairedContacts, |
| 7 | + // filterUnpairedContacts, |
| 8 | + // timeago, |
| 9 | + // getAvatar, |
| 10 | +} from '../helpers/utils.js' |
| 11 | + |
| 12 | +let _handlers = [] |
| 13 | + |
| 14 | +const initialState = { |
| 15 | + id: 'Transactions', |
| 16 | + name: 'List', |
| 17 | + placement: 'transactions', |
| 18 | + rendered: null, |
| 19 | + responsive: true, |
| 20 | + showUnpaired: false, |
| 21 | + delay: 500, |
| 22 | + wallet: {}, |
| 23 | + transactions: [], |
| 24 | + restate, |
| 25 | + render( |
| 26 | + renderState = {}, |
| 27 | + position = 'beforeend', |
| 28 | + ) {}, |
| 29 | + header: state => html` |
| 30 | + <header> |
| 31 | + <h5 class="lh-2">Transactions</h5> |
| 32 | + </header> |
| 33 | + `, |
| 34 | + list: async state => { |
| 35 | + if (state.transactions?.length === 0) { |
| 36 | + return html`<span class="flex flex-fill center">No Transactions found</span>` |
| 37 | + } |
| 38 | + |
| 39 | + return ( |
| 40 | + await Promise.all( |
| 41 | + state.transactions |
| 42 | + // .filter( |
| 43 | + // state.showUnpaired |
| 44 | + // ? filterUnpairedContacts |
| 45 | + // : filterPairedContacts |
| 46 | + // ) |
| 47 | + // .sort(sortContactsByAlias) |
| 48 | + .map(async c => await state.item(c)), |
| 49 | + ) |
| 50 | + ).join('') |
| 51 | + }, |
| 52 | + content: async state => html` |
| 53 | + ${state.header(state)} |
| 54 | +
|
| 55 | + <div> |
| 56 | + ${await state.list(state)} |
| 57 | + </div> |
| 58 | + `, |
| 59 | + item: async c => { |
| 60 | + // if ('string' === typeof c) { |
| 61 | + return html` |
| 62 | + <article> |
| 63 | + <address> |
| 64 | + <h4><!-- Encrypted --> Transaction</h4> |
| 65 | + </address> |
| 66 | + </article> |
| 67 | + ` |
| 68 | + // } |
| 69 | + |
| 70 | + // let outgoing = Object.values(c?.outgoing || {}) |
| 71 | + // let paired = outgoing.length > 0 |
| 72 | + // let out = outgoing?.[0] |
| 73 | + // let created = c.createdAt |
| 74 | + // ? timeago(Date.now() - (new Date(c.createdAt)).getTime()) |
| 75 | + // : '' |
| 76 | + // let user = c.alias || c.info?.preferred_username |
| 77 | + // let finishPairing = !paired |
| 78 | + // ? 'Finish pairing with contact' |
| 79 | + // : '' |
| 80 | + // let enterContactInfo = !paired || !user |
| 81 | + // ? `Enter contact information for` |
| 82 | + // : '' |
| 83 | + // let name = c.info?.name |
| 84 | + |
| 85 | + // if ( |
| 86 | + // !name && |
| 87 | + // !user && |
| 88 | + // !out?.xkeyId && |
| 89 | + // out?.address |
| 90 | + // ) { |
| 91 | + // name = out?.address |
| 92 | + // } else if (!name) { |
| 93 | + // name = created |
| 94 | + // } |
| 95 | + |
| 96 | + // let inId = Object.keys(c?.incoming || {})?.[0]?.split('/')[1] |
| 97 | + |
| 98 | + // let atUser = user |
| 99 | + // ? `@${user}` |
| 100 | + // : '' |
| 101 | + // let itemAlias = user |
| 102 | + // ? `${atUser}${ !paired ? ' - ' : '' }${finishPairing}` |
| 103 | + // : finishPairing || enterContactInfo |
| 104 | + // let itemName = name |
| 105 | + // ? `${name}` |
| 106 | + // : '' |
| 107 | + // let itemSub = inId |
| 108 | + // ? `href="/#!/contact/${atUser || inId}" data-id="${inId}"` |
| 109 | + // : '' |
| 110 | + // let itemCtrls = paired |
| 111 | + // ? html`<aside class="inline row"> |
| 112 | + // <button class="pill rounded"> |
| 113 | + // <svg width="24" height="24" viewBox="0 0 24 24"> |
| 114 | + // <use xlink:href="#icon-arrow-circle-up"></use> |
| 115 | + // </svg> |
| 116 | + // </button> |
| 117 | + // <button class="pill rounded"> |
| 118 | + // <svg width="24" height="24" viewBox="0 0 24 24"> |
| 119 | + // <use xlink:href="#icon-arrow-circle-down"></use> |
| 120 | + // </svg> |
| 121 | + // </button> |
| 122 | + // </aside>` |
| 123 | + // : '' |
| 124 | + |
| 125 | + // itemCtrls = '' // temp override |
| 126 | + |
| 127 | + // return html` |
| 128 | + // <a ${itemSub}> |
| 129 | + // ${await getAvatar(c)} |
| 130 | + // <address> |
| 131 | + // <h4>${itemAlias}</h4> |
| 132 | + // <h5>${itemName}</h5> |
| 133 | + // </address> |
| 134 | + // ${itemCtrls} |
| 135 | + // </a> |
| 136 | + // ` |
| 137 | + }, |
| 138 | + footer: async state => html``, |
| 139 | + slugs: { |
| 140 | + }, |
| 141 | + elements: { |
| 142 | + }, |
| 143 | + events: { |
| 144 | + handleClick: state => event => { |
| 145 | + event.preventDefault() |
| 146 | + event.stopPropagation() |
| 147 | + console.log( |
| 148 | + 'handle transactions click', |
| 149 | + event, |
| 150 | + state, |
| 151 | + ) |
| 152 | + }, |
| 153 | + handleTransactionsChange: (newState, oldState) => { |
| 154 | + if (newState.transactions !== oldState.transactions) { |
| 155 | + newState.render?.({ |
| 156 | + transactions: newState.transactions |
| 157 | + }) |
| 158 | + } |
| 159 | + } |
| 160 | + }, |
| 161 | +} |
| 162 | + |
| 163 | +let state = envoy( |
| 164 | + initialState, |
| 165 | + initialState.events.handleTransactionsChange, |
| 166 | +) |
| 167 | + |
| 168 | +export async function setupTransactionsList( |
| 169 | + el, setupState = {} |
| 170 | +) { |
| 171 | + restate(state, setupState) |
| 172 | + |
| 173 | + state.slugs.section = `${state.name}_${state.id}` |
| 174 | + .toLowerCase().replace(' ', '_') |
| 175 | + |
| 176 | + const section = document.createElement('section') |
| 177 | + |
| 178 | + section.id = state.slugs.section |
| 179 | + section.classList.add(state.placement || '') |
| 180 | + section.innerHTML = await state.content(state) |
| 181 | + |
| 182 | + state.elements.section = section |
| 183 | + |
| 184 | + const list = section.querySelector('& > div') |
| 185 | + |
| 186 | + state.elements.list = list |
| 187 | + |
| 188 | + function addListener( |
| 189 | + node, |
| 190 | + event, |
| 191 | + handler, |
| 192 | + capture = false |
| 193 | + ) { |
| 194 | + _handlers.push({ node, event, handler, capture }) |
| 195 | + node.addEventListener(event, handler, capture) |
| 196 | + } |
| 197 | + |
| 198 | + function removeAllListeners( |
| 199 | + targets = [state.elements.section], |
| 200 | + ) { |
| 201 | + _handlers = _handlers |
| 202 | + .filter(({ node, event, handler, capture }) => { |
| 203 | + if (targets.includes(node)) { |
| 204 | + node.removeEventListener(event, handler, capture) |
| 205 | + return false |
| 206 | + } |
| 207 | + return true |
| 208 | + }) |
| 209 | + } |
| 210 | + |
| 211 | + function addListeners() { |
| 212 | + addListener( |
| 213 | + state.elements.section, |
| 214 | + 'click', |
| 215 | + state.events.handleClick(state), |
| 216 | + ) |
| 217 | + } |
| 218 | + |
| 219 | + state.removeAllListeners = removeAllListeners |
| 220 | + state.addListeners = addListeners |
| 221 | + |
| 222 | + async function render( |
| 223 | + renderState = {}, |
| 224 | + position = 'beforeend', |
| 225 | + ) { |
| 226 | + await restate(state, renderState) |
| 227 | + |
| 228 | + state.elements.section.id = state.slugs.section |
| 229 | + |
| 230 | + state.elements.list.innerHTML = await state.list(state) |
| 231 | + |
| 232 | + state.removeAllListeners() |
| 233 | + state.addListeners() |
| 234 | + |
| 235 | + if (!state.rendered) { |
| 236 | + el.insertAdjacentElement(position, section) |
| 237 | + state.rendered = section |
| 238 | + } |
| 239 | + } |
| 240 | + |
| 241 | + state.render = render |
| 242 | + |
| 243 | + return { |
| 244 | + element: section, |
| 245 | + render, |
| 246 | + restate: async newState => await restate(state, newState), |
| 247 | + } |
| 248 | +} |
| 249 | + |
| 250 | +export default setupTransactionsList |
0 commit comments