@@ -0,0 +1,148 @@
1+import { Just, Nothing } from 'folktale/maybe';
2+import React from 'react';
3+import { pour } from 'sigil-js';
4+import * as ob from 'urbit-ob';
5+import * as azimuth from 'azimuth-js';
6+import * as need from '../lib/need';
8+import PointList from '../components/PointList';
9+import ReactSVGComponents from '../components/ReactSVGComponents';
10+import KeysAndMetadata from './Point/KeysAndMetadata';
11+import Actions from './Point/Actions';
12+import { Row, Col, H1, H3 } from '../components/Base';
14+import { compose } from '../lib/lib';
15+import { ROUTE_NAMES } from '../lib/routeNames';
17+import { withHistory } from '../store/history';
18+import { withNetwork } from '../store/network';
19+import { withPointCursor } from '../store/pointCursor';
20+import { withPointCache } from '../store/pointCache';
22+class PointHome extends React.Component {
33+ componentDidMount() {
35+ this.updateBirthday();
38+ //TODO can probably re-use this to implement point switching
39+ componentDidUpdate(prevProps) {
43+ // When a link in the 'issued points' component is clicked, we don't
44+ // actually leave the Point component, and componentDidMount will not fire
45+ // again. But, we can force a call to cachePoints here.
47+ const oldCursor = prevProps.pointCursor.getOrElse(true);
48+ const newCursor = this.props.pointCursor.getOrElse(true);
50+ if (oldCursor !== newCursor) {
56+ const { web3, contracts, pointCursor, addToPointCache } = this.props;
59+ contracts.chain(ctrcs =>
60+ pointCursor.chain(point => {
62+ .getPoint(ctrcs, point)
63+ .then(details => addToPointCache({ [point]: details }));
64+ azimuth.delegatedSending
65+ .getTotalUsableInvites(ctrcs, point)
66+ .then(count => this.setState({ invites: Just(count) }));
67+ this.updateSpawned(ctrcs, point);
73+ async updateBirthday(blockNumber) {
74+ const birthBlock = await azimuth.azimuth.getActivationBlock(
75+ need.contracts(this.props),
76+ need.pointCursor(this.props)
78+ if (birthBlock === 0) {
79+ this.setState({ birthday: Nothing() });
81+ const block = await need.web3(this.props).eth.getBlock(birthBlock);
82+ this.setState({ birthday: Just(new Date(block.timestamp * 1000)) });
86+ updateSpawned = contracts => {
87+ const { pointCursor } = this.props;
89+ pointCursor.matchWith({
93+ .getSpawned(contracts, point.value)
94+ .then(spawned => this.setState({ spawned }));
100+ const { web3, history, wallet, setPointCursor, pointCache } = this.props;
102+ const point = need.pointCursor(this.props);
104+ const pointDetails =
105+ point in pointCache ? Just(pointCache[point]) : Nothing();
107+ const name = ob.patp(point);
109+ const sigil = pour({
111+ renderer: ReactSVGComponents,
115+ const online = Just.hasInstance(web3);
117+ const authenticated = Just.hasInstance(wallet);
122+ <div className={'mt-12 pt-6'}>{sigil}</div>
131+ pointDetails={pointDetails}
132+ invites={this.state.invites}
136+ {online ? <KeysAndMetadata pointDetails={pointDetails} /> : <div />}
143+export default compose(