on master help sign in
Merge pull request #225 from urbit/fix/mobile-styling
eb9c739Matt Condon
package.json+1−1
@@ -78,7 +78,7 @@
78 "checksum": "cd build && find . -exec shasum -a256 {} ';' > ../checksums.txt && cd ..",
78 "checksum": "cd build && find . -exec shasum -a256 {} ';' > ../checksums.txt && cd ..",
79 "zip": "zip -ur bridge-$npm_package_version.zip README.md bridge-https.py checksums.txt && cd build && zip -ur ../bridge-$npm_package_version.zip ./* && cd ..",
79 "zip": "zip -ur bridge-$npm_package_version.zip README.md bridge-https.py checksums.txt && cd build && zip -ur ../bridge-$npm_package_version.zip ./* && cd ..",
80 "release": "npm install && npm run build && npm run checksum && npm run zip",
80 "release": "npm install && npm run build && npm run checksum && npm run zip",
81− "pilot:ganache": "ganache-cli --blockTime 1 --networkId 1 -m 'benefit crew supreme gesture quantum web media hazard theory mercy wing kitten' > /dev/null &",
81+ "pilot:ganache": "ganache-cli --blockTime 1 --networkId 1 --host '0.0.0.0' -m 'benefit crew supreme gesture quantum web media hazard theory mercy wing kitten' > /dev/null &",
82 "pilot:deploy": "cd node_modules/azimuth-solidity && truffle deploy",
82 "pilot:deploy": "cd node_modules/azimuth-solidity && truffle deploy",
83 "pilot:setup": "npm run pilot:ganache && npm run pilot:deploy",
83 "pilot:setup": "npm run pilot:ganache && npm run pilot:deploy",
84 "pilot": "HTTPS=true npm-run-all pilot:setup start pilot:cleanup --continue-on-error",
84 "pilot": "HTTPS=true npm-run-all pilot:setup start pilot:cleanup --continue-on-error",
src/components/Accordion.js+17−3
@@ -1,4 +1,5 @@
1import React from 'react';
1import React from 'react';
2+import cn from 'classnames';
2import { Grid, AccessoryIcon } from 'indigo-react';
3import { Grid, AccessoryIcon } from 'indigo-react';
3
4
4export default function Accordion({
5export default function Accordion({
@@ -22,9 +23,19 @@ export default function Accordion({
22 <React.Fragment key={option.value}>
23 <React.Fragment key={option.value}>
23 <Grid.Item
24 <Grid.Item
24 full
25 full
25− className="f5 pv3 rel clickable"
26+ className={cn('f5 pv3 rel', {
27+ clickable: !option.disabled,
28+ gray3: option.disabled,
29+ })}
30+ onClick={
31+ option.disabled
32+ ? null
26− onClick={() => onTabChange(isActive ? undefined : option.value)}>
33+ : () => onTabChange(isActive ? undefined : option.value)
34+ }>
27 {option.text}
35 {option.text}
36+ {option.disabled && (
37+ <sup className="f6 lowercase">{option.disabled}</sup>
38+ )}
28 <div
39 <div
29 className="abs"
40 className="abs"
30 style={{
41 style={{
@@ -34,7 +45,10 @@ export default function Accordion({
34 width: '44px',
45 width: '44px',
35 overflow: 'hidden',
46 overflow: 'hidden',
36 }}>
47 }}>
37− <AccessoryIcon className="black">
48+ <AccessoryIcon
49+ className={cn({
50+ black: !option.disabled,
51+ })}>
38 {isActive ? '▲' : '▼'}
52 {isActive ? '▲' : '▼'}
39 </AccessoryIcon>
53 </AccessoryIcon>
40 </div>
54 </div>
src/components/Passport.js+1−1
@@ -78,7 +78,7 @@ function Passport({ point, className, ticket = null, address = Nothing() }) {
78 <MaybeSigil patp={name} size={64} />
78 <MaybeSigil patp={name} size={64} />
79 </Grid.Item>
79 </Grid.Item>
80 <Grid.Item as={Flex} cols={[4, 13]} col justify="between">
80 <Grid.Item as={Flex} cols={[4, 13]} col justify="between">
81− <Flex.Item className="mono white f5">{visualName}</Flex.Item>
81+ <Flex.Item className="mono white f5 pb2">{visualName}</Flex.Item>
82 <Flex.Item as={Flex} col>
82 <Flex.Item as={Flex} col>
83 <Flex.Item as={Text} className="mono f6 f5-ns gray4 uppercase">
83 <Flex.Item as={Text} className="mono f6 f5-ns gray4 uppercase">
84 Birth Time
84 Birth Time
src/components/Sigil.js+2−1
@@ -4,8 +4,9 @@ export default function Sigil({ patp, size, colors, ...rest }) {
4 return sigil({
4 return sigil({
5 patp,
5 patp,
6 renderer: reactRenderer,
6 renderer: reactRenderer,
7− style: { width: '100%', height: '100%' }, //NOTE scale to container
7+ style: { width: '100%', height: '100%' }, // NOTE: scale to container
8 size,
8 size,
9+ margin: size / 8,
9 colors,
10 colors,
10 ...rest,
11 ...rest,
11 });
12 });
src/components/Tabs.js+27−26
@@ -14,33 +14,34 @@ export default function Tabs({
14
14
15 return (
15 return (
16 <Grid className={className}>
16 <Grid className={className}>
17− <Grid.Item full as={Flex} wrap className="b-gray3 bb1">
17+ <Grid.Item full as={Flex} className="b-gray3 bb1 scroll-x hidden-y">
18+ <Flex.Item as={Flex}>
18− {options.map((option, i) => {
19+ {options.map((option, i) => {
19− const isActive = option.value === currentTab;
20+ const isActive = option.value === currentTab;
20− const isFirst = i === 0;
21+ const isFirst = i === 0;
21
22
22− return (
23+ return (
23− <Flex.Item
24+ <Flex.Item
24− key={option.value}
25+ key={option.value}
25− onClick={() => onTabChange(option.value)}
26+ onClick={() => onTabChange(option.value)}
26− className={cn(
27+ className={cn(
27− 'f5 pv3 clickable',
28+ 'f5 pv3 clickable nowrap',
28− {
29+ {
29− 'black b-black bb1': isActive,
30+ 'black b-black bb1': isActive,
30− gray3: !isActive,
31+ gray3: !isActive,
31− },
32+ },
32− {
33+ {
33− // all items have right margin/padding
34+ // all items have right margin/padding
34− 'mr2 pr2': true,
35+ 'mr2 pr2': true,
35− // the first one is flush to the left
36+ // the first one is flush to the left
36− 'ml2 pl2': !isFirst,
37+ 'ml2 pl2': !isFirst,
37− }
38+ }
38− )}
39+ )}>
39− style={{ marginBottom: '-1px' }}>
40− {option.text}
40+ {option.text}
41− </Flex.Item>
41+ </Flex.Item>
42− );
42+ );
43− })}
43+ })}
44+ </Flex.Item>
44 </Grid.Item>
45 </Grid.Item>
45 <Grid.Item full as={Tab} {...rest} />
46 <Grid.Item full as={Tab} {...rest} />
46 </Grid>
47 </Grid>
src/components/View.js+1−1
@@ -62,7 +62,7 @@ function View({
62 <Flex.Item as={Footer.Target} />
62 <Flex.Item as={Footer.Target} />
63 </Flex.Item>
63 </Flex.Item>
64
64
65− <Flex.Item style={{ width: '48px' }} className={cn(insetPadding)} />
65+ <Flex.Item style={{ width: '48px' }} />
66 </Flex>
66 </Flex>
67 );
67 );
68}
68}
src/indigo-react/components/Input.js+3−3
@@ -78,8 +78,8 @@ export default function Input({
78 flex
78 flex
79 as={BaseComponent}
79 as={BaseComponent}
80 {...rest}
80 {...rest}
81− // NOTE: 24px = 12px * 2 (from p3 styling)
81+ // NOTE: 1.15 from input line-height, 24px = 12px * 2 (from p3 styling)
82− style={type === 'textarea' ? { minHeight: 'calc(1rem + 24px)' } : {}}
82+ style={type === 'textarea' ? { minHeight: 'calc(1.5rem * 3)' } : {}}
83 className={cn(
83 className={cn(
84 'b b1 p3 outline-none bs-none',
84 'b b1 p3 outline-none bs-none',
85 { mono },
85 { mono },
@@ -110,7 +110,7 @@ export default function Input({
110 top: 0,
110 top: 0,
111 right: 0,
111 right: 0,
112 height: '100%',
112 height: '100%',
113− width: '44px',
113+ width: 'calc(1.5em + 24px)',
114 overflow: 'hidden',
114 overflow: 'hidden',
115 }}>
115 }}>
116 {accessory}
116 {accessory}
src/store/network.js+1−1
@@ -41,7 +41,7 @@ function _useNetwork(initialNetworkType = null) {
41 switch (networkType) {
41 switch (networkType) {
42 case NETWORK_TYPES.LOCAL: {
42 case NETWORK_TYPES.LOCAL: {
43 const protocol = isDevelopment ? 'ws' : 'wss';
43 const protocol = isDevelopment ? 'ws' : 'wss';
44− const endpoint = `${protocol}://localhost:8545`;
44+ const endpoint = `${protocol}://${document.location.hostname}:8545`;
45
45
46 return initWeb3(
46 return initWeb3(
47 new Web3.providers.WebsocketProvider(endpoint),
47 new Web3.providers.WebsocketProvider(endpoint),
src/style/bridge.scss+4−18
@@ -1,18 +1,4 @@
1−@keyframes autofill {
1+$handle-extent: 24px; // $lh-regular
2− to {
3− color: #000;
4− background: transparent;
5− }
6−}
7−
8−/* avoid yellow autofill highlight on browsers that respect this attribute */
9−input:-webkit-autofill {
10− animation-name: autofill;
11− animation-fill-mode: both;
12−
13− -webkit-animation-name: autofill;
14− -webkit-animation-fill-mode: both;
15−}
16
2
17// min-height the top elements so footer behavior works correctly
3// min-height the top elements so footer behavior works correctly
18html {
4html {
@@ -36,7 +22,7 @@ input[type='range'] {
36
22
37 /* Chrome */
23 /* Chrome */
38 &::-webkit-slider-runnable-track {
24 &::-webkit-slider-runnable-track {
39− height: 24px;
25+ height: $handle-extent;
40 -webkit-appearance: none;
26 -webkit-appearance: none;
41 background-color: #e6e6e6;
27 background-color: #e6e6e6;
42 margin-top: -1px;
28 margin-top: -1px;
@@ -44,7 +30,7 @@ input[type='range'] {
44
30
45 &::-webkit-slider-thumb {
31 &::-webkit-slider-thumb {
46 -webkit-appearance: none;
32 -webkit-appearance: none;
47− width: 24px;
33+ width: $handle-extent;
48 height: 100%;
34 height: 100%;
49 background-color: #000;
35 background-color: #000;
50 border: none;
36 border: none;
@@ -63,7 +49,7 @@ input[type='range'] {
63 }
49 }
64
50
65 &::-moz-range-thumb {
51 &::-moz-range-thumb {
66− width: 24px;
52+ width: $handle-extent;
67 height: 100%;
53 height: 100%;
68 background-color: #000;
54 background-color: #000;
69 border: none;
55 border: none;
src/style/form-reset.scssnew file+47
@@ -0,0 +1,47 @@
1+$form-padding: 24px; // indigo pv3
2+$form-line-height: 1.5rem; // $lh-regular
3+
4+@keyframes autofill {
5+ to {
6+ color: #000;
7+ background: transparent;
8+ }
9+}
10+
11+input,
12+button,
13+textarea,
14+select {
15+ padding: 0;
16+ margin: 0;
17+ border-radius: 0;
18+ -webkit-appearance: none;
19+
20+ &:focus,
21+ &:hover,
22+ &:active {
23+ outline: 0;
24+ }
25+
26+ &::-moz-focus-inner {
27+ border: 0;
28+ }
29+}
30+
31+input {
32+ // enforce border-box
33+ box-sizing: border-box;
34+
35+ // enforce height & line-height for accessories
36+ height: calc(#{$form-line-height} + #{$form-padding});
37+ line-height: $form-line-height;
38+
39+ // avoid yellow autofill highlight on browsers that respect this attribute
40+ &:-webkit-autofill {
41+ animation-name: autofill;
42+ animation-fill-mode: both;
43+
44+ -webkit-animation-name: autofill;
45+ -webkit-animation-fill-mode: both;
46+ }
47+}
src/style/index.scss+3
@@ -1,3 +1,6 @@
1+/* Form Reset */
2+@import './form-reset.scss';
3+
1/* Indigo */
4/* Indigo */
2@import '../indigo-react/indigo.css';
5@import '../indigo-react/indigo.css';
3@import './indigo-proposals.scss';
6@import './indigo-proposals.scss';
src/style/indigo-proposals.scss+8
@@ -52,3 +52,11 @@
52.arial {
52.arial {
53 font-family: Arial, monospace;
53 font-family: Arial, monospace;
54}
54}
55+
56+.scroll-x {
57+ overflow-x: auto;
58+}
59+
60+.hidden-y {
61+ overflow-y: hidden;
62+}
src/views/AcceptTransfer.js+1−1
@@ -73,7 +73,7 @@ export default function AcceptTransfer() {
73 <Grid.Item
73 <Grid.Item
74 full
74 full
75 as={Text}
75 as={Text}
76− className={cn('f5', {
76+ className={cn('f5 wrap', {
77 green3: completed,
77 green3: completed,
78 })}>
78 })}>
79 {completed
79 {completed
src/views/Admin/AdminCancelTransfer.js+1−1
@@ -65,7 +65,7 @@ export default function AdminCancelTransfer() {
65 <Grid.Item
65 <Grid.Item
66 full
66 full
67 as={Text}
67 as={Text}
68− className={cn('f5', {
68+ className={cn('f5 wrap', {
69 green3: completed,
69 green3: completed,
70 })}>
70 })}>
71 {completed
71 {completed
src/views/Admin/AdminTransfer.js+1−1
@@ -78,7 +78,7 @@ export default function AdminTransfer() {
78 <Grid.Item
78 <Grid.Item
79 full
79 full
80 as={Text}
80 as={Text}
81− className={cn('f5', {
81+ className={cn('f5 wrap', {
82 green3: completed,
82 green3: completed,
83 })}>
83 })}>
84 {completed
84 {completed
src/views/CreateGalaxy.js+1−1
@@ -123,7 +123,7 @@ export default function CreateGalaxy() {
123 <Grid.Item
123 <Grid.Item
124 full
124 full
125 as={Text}
125 as={Text}
126− className={cn('f5', {
126+ className={cn('f5 wrap', {
127 green3: completed,
127 green3: completed,
128 })}>
128 })}>
129 {values.galaxyName} has been created and can be claimed by{' '}
129 {values.galaxyName} has been created and can be claimed by{' '}
src/views/IssueChild.js+1−1
@@ -149,7 +149,7 @@ export default function IssueChild() {
149 <Grid.Item
149 <Grid.Item
150 full
150 full
151 as={Text}
151 as={Text}
152− className={cn('f5', {
152+ className={cn('f5 wrap', {
153 green3: completed,
153 green3: completed,
154 })}>
154 })}>
155 {values.point} has been spawned and can be claimed by{' '}
155 {values.point} has been spawned and can be claimed by{' '}
src/views/Login/Hardware.js+17−2
@@ -1,4 +1,6 @@
1−import React, { useState } from 'react';
1+import React, { useMemo, useState } from 'react';
2+
3+import useBreakpoints from 'lib/useBreakpoints';
2
4
3import Accordion from 'components/Accordion';
5import Accordion from 'components/Accordion';
4
6
@@ -23,11 +25,24 @@ const OPTIONS = [
23export default function Hardware({ className, ...rest }) {
25export default function Hardware({ className, ...rest }) {
24 const [currentTab, setCurrentTab] = useState(undefined);
26 const [currentTab, setCurrentTab] = useState(undefined);
25
27
28+ // using breakpoint to decide if we're on mobile or not
29+ // see ActivateCode for more details on this approach
30+ const hardwareAllowed = useBreakpoints([false, true, true]);
31+
32+ const options = useMemo(
33+ () =>
34+ OPTIONS.map(option => ({
35+ ...option,
36+ disabled: !hardwareAllowed && ' not availble on mobile',
37+ })),
38+ [hardwareAllowed]
39+ );
40+
26 return (
41 return (
27 <Accordion
42 <Accordion
28 className={className}
43 className={className}
29 views={VIEWS}
44 views={VIEWS}
30− options={OPTIONS}
45+ options={options}
31 currentTab={currentTab}
46 currentTab={currentTab}
32 onTabChange={setCurrentTab}
47 onTabChange={setCurrentTab}
33 //
48 //
src/views/Party/PartySetPoolSize.js+1−1
@@ -116,7 +116,7 @@ export default function PartySetPoolSize() {
116 <Grid.Item
116 <Grid.Item
117 full
117 full
118 as={Text}
118 as={Text}
119− className={cn('f5', {
119+ className={cn('f5 wrap', {
120 green3: completed,
120 green3: completed,
121 })}>
121 })}>
122 {completed
122 {completed
src/views/Points.js+3−1
@@ -40,7 +40,9 @@ const PointList = function({ points, className, actions, ...rest }) {
40 return (
40 return (
41 <Grid gap={3} className={className}>
41 <Grid gap={3} className={className}>
42 {points.map((point, i) => (
42 {points.map((point, i) => (
43− <Grid.Item half={(i % 2) + 1} key={point}>
43+ <Grid.Item
44+ key={point}
45+ className={`full half-${(i % 2) + 1}-md half-${(i % 2) + 1}-lg`}>
44 <Flex col>
46 <Flex col>
45 <Passport.Mini
47 <Passport.Mini
46 point={point}
48 point={point}