Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Submit feedback
Contribute to GitLab
Sign in
Toggle navigation
I
interface
Project
Project
Details
Activity
Releases
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Boards
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
LuckySwap
interface
Commits
d265b120
Commit
d265b120
authored
Jul 29, 2019
by
ian-jh
Browse files
Options
Browse Files
Download
Plain Diff
Merge remote-tracking branch 'upstream/beta' into beta
parents
870b3f7e
30887ef1
Changes
21
Expand all
Hide whitespace changes
Inline
Side-by-side
Showing
21 changed files
with
1121 additions
and
688 deletions
+1121
-688
LICENSE
LICENSE
+0
-0
en.json
public/locales/en.json
+2
-1
question-mark.svg
src/assets/images/question-mark.svg
+4
-0
question.svg
src/assets/images/question.svg
+4
-0
index.js
src/components/AddressInputPanel/index.js
+1
-1
index.js
src/components/ContextualInfoNew/index.js
+5
-6
index.js
src/components/CurrencyInputPanel/index.js
+3
-3
index.js
src/components/Modal/index.js
+2
-1
index.js
src/components/NavigationTabs/index.js
+3
-3
index.js
src/components/TransactionDetails/index.js
+571
-0
index.js
src/components/Web3Status/index.js
+1
-9
Application.js
src/contexts/Application.js
+1
-25
LocalStorage.js
src/contexts/LocalStorage.js
+90
-0
Tokens.js
src/contexts/Tokens.js
+14
-0
index.js
src/index.js
+13
-9
AddLiquidity.js
src/pages/Pool/AddLiquidity.js
+4
-1
ModeSelector.js
src/pages/Pool/ModeSelector.js
+1
-1
index.js
src/pages/Send/index.js
+3
-3
index.js
src/pages/Swap/index.js
+51
-132
index.js
src/theme/index.js
+4
-0
yarn.lock
yarn.lock
+344
-493
No files found.
LICENSE
.md
→
LICENSE
View file @
d265b120
File moved
public/locales/en.json
View file @
d265b120
...
...
@@ -80,5 +80,6 @@
"symbol"
:
"Symbol"
,
"decimals"
:
"Decimals"
,
"enterTokenCont"
:
"Enter a token address to continue"
,
"priceChange"
:
"This trade will cause the price to change by"
"priceChange"
:
"Expected price slippage"
,
"forAtLeast"
:
"for at least "
}
src/assets/images/question-mark.svg
0 → 100644
View file @
d265b120
<svg
width=
"18"
height=
"18"
viewBox=
"0 0 18 18"
fill=
"none"
xmlns=
"http://www.w3.org/2000/svg"
>
<circle
cx=
"9"
cy=
"9"
r=
"9"
fill=
"#E1E1E1"
/>
<path
d=
"M8.06493 10.8317H9.15706V10.7592C9.17233 9.88089 9.42436 9.48757 10.0735 9.08662C10.7571 8.67421 11.1771 8.09378 11.1771 7.23459C11.1771 5.99354 10.2377 5.15344 8.83629 5.15344C7.54942 5.15344 6.51839 5.90571 6.46875 7.28041H7.62961C7.67543 6.47086 8.25204 6.11573 8.83629 6.11573C9.48546 6.11573 10.0124 6.54724 10.0124 7.22313C10.0124 7.79211 9.65729 8.19306 9.20288 8.47564C8.49262 8.91096 8.07257 9.34246 8.06493 10.7592V10.8317ZM8.64154 13.1534C9.05777 13.1534 9.40527 12.8136 9.40527 12.3897C9.40527 11.9735 9.05777 11.6298 8.64154 11.6298C8.22149 11.6298 7.87782 11.9735 7.87782 12.3897C7.87782 12.8136 8.22149 13.1534 8.64154 13.1534Z"
fill=
"#737373"
/>
</svg>
src/assets/images/question.svg
0 → 100644
View file @
d265b120
<svg
width=
"16"
height=
"16"
viewBox=
"0 0 16 16"
fill=
"none"
xmlns=
"http://www.w3.org/2000/svg"
>
<circle
cx=
"8"
cy=
"8"
r=
"8"
fill=
"#E1E1E1"
/>
<path
d=
"M7.09618 9.67828H8.18831V9.60573C8.20358 8.72745 8.45561 8.33413 9.10477 7.93317C9.78831 7.52076 10.2084 6.94033 10.2084 6.08115C10.2084 4.8401 9.26897 4 7.86754 4C6.58067 4 5.54964 4.75227 5.5 6.12697H6.66086C6.70668 5.31742 7.28329 4.96229 7.86754 4.96229C8.51671 4.96229 9.04368 5.39379 9.04368 6.06969C9.04368 6.63866 8.68854 7.03962 8.23413 7.3222C7.52387 7.75752 7.10382 8.18902 7.09618 9.60573V9.67828ZM7.67279 12C8.08902 12 8.43652 11.6601 8.43652 11.2363C8.43652 10.82 8.08902 10.4764 7.67279 10.4764C7.25274 10.4764 6.90907 10.82 6.90907 11.2363C6.90907 11.6601 7.25274 12 7.67279 12Z"
fill=
"#737373"
/>
</svg>
src/components/AddressInputPanel/index.js
View file @
d265b120
...
...
@@ -21,7 +21,7 @@ const ContainerRow = styled.div`
justify-content: center;
align-items: center;
border-radius: 1.25rem;
box-shadow: 0 0 0
0.5
px
${({
error
,
theme
})
=>
(
error
?
theme
.
salmonRed
:
theme
.
mercuryGray
)}
;
box-shadow: 0 0 0
1
px
${({
error
,
theme
})
=>
(
error
?
theme
.
salmonRed
:
theme
.
mercuryGray
)}
;
background-color:
${({
theme
})
=>
theme
.
white
}
;
transition: box-shadow 200ms ease-in-out;
`
...
...
src/components/ContextualInfoNew/index.js
View file @
d265b120
...
...
@@ -32,10 +32,10 @@ const SummaryWrapperContainer = styled.div`
const
Details
=
styled
.
div
`
background-color:
${({
theme
})
=>
theme
.
concreteGray
}
;
padding: 1.5rem;
/* padding: 1.25rem 1.25rem 1rem 1.25rem; */
border-radius: 1rem;
font-size: 0.75rem;
margin
-top: 1
rem;
margin
: 1rem 0.5rem 0 0.5
rem;
`
const
ErrorSpan
=
styled
.
span
`
...
...
@@ -89,13 +89,12 @@ export default function ContextualInfo({
closeDetailsText
=
'
Hide Details
'
,
contextualInfo
=
''
,
allowExpand
=
false
,
renderTransactionDetails
=
()
=>
{},
isError
=
false
,
slippageWarning
,
highSlippageWarning
highSlippageWarning
,
dropDownContent
})
{
const
[
showDetails
,
setShowDetails
]
=
useState
(
false
)
return
!
allowExpand
?
(
<
SummaryWrapper
>
{
contextualInfo
}
<
/SummaryWrapper
>
)
:
(
...
...
@@ -117,7 +116,7 @@ export default function ContextualInfo({
)}
<
/
>
<
/SummaryWrapperContainer
>
{
showDetails
&&
<
Details
>
{
renderTransactionDetails
()}
<
/Details>
}
{
showDetails
&&
<
Details
>
{
dropDownContent
()}
<
/Details>
}
<
/
>
)
}
src/components/CurrencyInputPanel/index.js
View file @
d265b120
...
...
@@ -70,7 +70,7 @@ const CurrencySelect = styled.button`
}
:focus {
box-shadow: 0 0
0.5px 0.5
px
${({
theme
})
=>
theme
.
malibuBlue
}
;
box-shadow: 0 0
1px 1
px
${({
theme
})
=>
theme
.
malibuBlue
}
;
}
:active {
...
...
@@ -104,12 +104,12 @@ const InputPanel = styled.div`
const
Container
=
styled
.
div
`
border-radius: 1.25rem;
box-shadow: 0 0 0
0.5
px
${({
error
,
theme
})
=>
(
error
?
theme
.
salmonRed
:
theme
.
mercuryGray
)}
;
box-shadow: 0 0 0
1
px
${({
error
,
theme
})
=>
(
error
?
theme
.
salmonRed
:
theme
.
mercuryGray
)}
;
background-color:
${({
theme
})
=>
theme
.
white
}
;
transition: box-shadow 200ms ease-in-out;
:focus-within {
box-shadow: 0 0
0.5px 0.5
px
${({
theme
})
=>
theme
.
malibuBlue
}
;
box-shadow: 0 0
1px 1
px
${({
theme
})
=>
theme
.
malibuBlue
}
;
}
`
...
...
src/components/Modal/index.js
View file @
d265b120
...
...
@@ -5,7 +5,8 @@ import { DialogOverlay, DialogContent } from '@reach/dialog'
import
'
@reach/dialog/styles.css
'
const
AnimatedDialogOverlay
=
animated
(
DialogOverlay
)
const
StyledDialogOverlay
=
styled
(
AnimatedDialogOverlay
).
attrs
({
const
WrappedDialogOverlay
=
({
suppressClassNameWarning
,
...
rest
})
=>
<
AnimatedDialogOverlay
{...
rest
}
/
>
const
StyledDialogOverlay
=
styled
(
WrappedDialogOverlay
).
attrs
({
suppressClassNameWarning
:
true
})
`
&[data-reach-dialog-overlay] {
...
...
src/components/NavigationTabs/index.js
View file @
d265b120
...
...
@@ -5,7 +5,7 @@ import styled from 'styled-components'
import
{
transparentize
,
darken
}
from
'
polished
'
import
{
useBodyKeyDown
}
from
'
../../hooks
'
import
{
useBetaMessageManager
}
from
'
../../contexts/
Application
'
import
{
useBetaMessageManager
}
from
'
../../contexts/
LocalStorage
'
const
tabOrder
=
[
{
...
...
@@ -84,11 +84,11 @@ const StyledNavLink = styled(NavLink).attrs({
&.
${
activeClassName
}
{
background-color:
${({
theme
})
=>
theme
.
white
}
;
border-radius: 3rem;
box-shadow: 0 0
0.5
px 1px
${({
theme
})
=>
theme
.
mercuryGray
}
;
box-shadow: 0 0
1
px 1px
${({
theme
})
=>
theme
.
mercuryGray
}
;
font-weight: 500;
color:
${({
theme
})
=>
theme
.
royalBlue
}
;
:hover {
box-shadow: 0 0
0.5
px 1px
${({
theme
})
=>
darken
(
0.1
,
theme
.
mercuryGray
)}
;
box-shadow: 0 0
1
px 1px
${({
theme
})
=>
darken
(
0.1
,
theme
.
mercuryGray
)}
;
}
}
...
...
src/components/TransactionDetails/index.js
0 → 100644
View file @
d265b120
This diff is collapsed.
Click to expand it.
src/components/Web3Status/index.js
View file @
d265b120
...
...
@@ -5,7 +5,7 @@ import { useWeb3Context, Connectors } from 'web3-react'
import
{
darken
,
transparentize
}
from
'
polished
'
import
Jazzicon
from
'
jazzicon
'
import
{
ethers
}
from
'
ethers
'
import
{
Activity
,
ArrowRight
}
from
'
react-feather
'
import
{
Activity
}
from
'
react-feather
'
import
{
shortenAddress
}
from
'
../../utils
'
import
{
useENSName
}
from
'
../../hooks
'
...
...
@@ -91,13 +91,6 @@ const NetworkIcon = styled(Activity)`
height: 16px;
`
const
ArrowIcon
=
styled
(
ArrowRight
)
`
margin-left: 0.25rem;
margin-right: 0.5rem;
width: 16px;
height: 16px;
`
const
SpinnerWrapper
=
styled
(
Spinner
)
`
margin: 0 0.25rem 0 0.25rem;
`
...
...
@@ -251,7 +244,6 @@ export default function Web3Status() {
return
(
<
Web3StatusConnect
onClick
=
{
onClick
}
>
<
Text
>
{
t
(
'
Connect
'
)}
<
/Text
>
<
ArrowIcon
/>
<
/Web3StatusConnect
>
)
}
else
{
...
...
src/contexts/Application.js
View file @
d265b120
...
...
@@ -2,10 +2,8 @@ import React, { createContext, useContext, useReducer, useMemo, useCallback, use
import
{
useWeb3Context
}
from
'
web3-react
'
import
{
safeAccess
}
from
'
../utils
'
const
SHOW_BETA_MESSAGE
=
'
SHOW_BETA_MESSAGE
'
const
BLOCK_NUMBERS
=
'
BLOCK_NUMBERS
'
const
DISMISS_BETA_MESSAGE
=
'
DISMISS_BETA_MESSAGE
'
const
UPDATE_BLOCK_NUMBER
=
'
UPDATE_BLOCK_NUMBER
'
const
ApplicationContext
=
createContext
()
...
...
@@ -16,12 +14,6 @@ function useApplicationContext() {
function
reducer
(
state
,
{
type
,
payload
})
{
switch
(
type
)
{
case
DISMISS_BETA_MESSAGE
:
{
return
{
...
state
,
[
SHOW_BETA_MESSAGE
]:
false
}
}
case
UPDATE_BLOCK_NUMBER
:
{
const
{
networkId
,
blockNumber
}
=
payload
return
{
...
...
@@ -40,25 +32,15 @@ function reducer(state, { type, payload }) {
export
default
function
Provider
({
children
})
{
const
[
state
,
dispatch
]
=
useReducer
(
reducer
,
{
[
SHOW_BETA_MESSAGE
]:
true
,
[
BLOCK_NUMBERS
]:
{}
})
const
dismissBetaMessage
=
useCallback
(()
=>
{
dispatch
({
type
:
DISMISS_BETA_MESSAGE
})
},
[])
const
updateBlockNumber
=
useCallback
((
networkId
,
blockNumber
)
=>
{
dispatch
({
type
:
UPDATE_BLOCK_NUMBER
,
payload
:
{
networkId
,
blockNumber
}
})
},
[])
return
(
<
ApplicationContext
.
Provider
value
=
{
useMemo
(()
=>
[
state
,
{
dismissBetaMessage
,
updateBlockNumber
}],
[
state
,
dismissBetaMessage
,
updateBlockNumber
])}
>
<
ApplicationContext
.
Provider
value
=
{
useMemo
(()
=>
[
state
,
{
updateBlockNumber
}],
[
state
,
updateBlockNumber
])}
>
{
children
}
<
/ApplicationContext.Provider
>
)
...
...
@@ -101,12 +83,6 @@ export function Updater() {
return
null
}
export
function
useBetaMessageManager
()
{
const
[
state
,
{
dismissBetaMessage
}]
=
useApplicationContext
()
return
[
safeAccess
(
state
,
[
SHOW_BETA_MESSAGE
]),
dismissBetaMessage
]
}
export
function
useBlockNumber
()
{
const
{
networkId
}
=
useWeb3Context
()
...
...
src/contexts/LocalStorage.js
0 → 100644
View file @
d265b120
import
React
,
{
createContext
,
useContext
,
useReducer
,
useMemo
,
useCallback
,
useEffect
}
from
'
react
'
const
UNISWAP
=
'
UNISWAP
'
const
VERSION
=
'
VERSION
'
const
CURRENT_VERSION
=
0
const
LAST_SAVED
=
'
LAST_SAVED
'
const
BETA_MESSAGE_DISMISSED
=
'
BETA_MESSAGE_DISMISSED
'
const
UPDATABLE_KEYS
=
[
BETA_MESSAGE_DISMISSED
]
const
UPDATE_KEY
=
'
UPDATE_KEY
'
const
LocalStorageContext
=
createContext
()
function
useLocalStorageContext
()
{
return
useContext
(
LocalStorageContext
)
}
function
reducer
(
state
,
{
type
,
payload
})
{
switch
(
type
)
{
case
UPDATE_KEY
:
{
const
{
key
,
value
}
=
payload
if
(
!
UPDATABLE_KEYS
.
some
(
k
=>
k
===
key
))
{
throw
Error
(
`Unexpected key in LocalStorageContext reducer: '
${
key
}
'.`
)
}
else
{
return
{
...
state
,
[
key
]:
value
}
}
}
default
:
{
throw
Error
(
`Unexpected action type in LocalStorageContext reducer: '
${
type
}
'.`
)
}
}
}
function
init
()
{
const
defaultLocalStorage
=
{
[
VERSION
]:
CURRENT_VERSION
,
[
BETA_MESSAGE_DISMISSED
]:
false
}
try
{
const
parsed
=
JSON
.
parse
(
window
.
localStorage
.
getItem
(
UNISWAP
))
if
(
parsed
[
VERSION
]
!==
CURRENT_VERSION
)
{
// this is where we could run migration logic
return
defaultLocalStorage
}
else
{
return
parsed
}
}
catch
{
return
defaultLocalStorage
}
}
export
default
function
Provider
({
children
})
{
const
[
state
,
dispatch
]
=
useReducer
(
reducer
,
undefined
,
init
)
const
updateKey
=
useCallback
((
key
,
value
)
=>
{
dispatch
({
type
:
UPDATE_KEY
,
payload
:
{
key
,
value
}
})
},
[])
return
(
<
LocalStorageContext
.
Provider
value
=
{
useMemo
(()
=>
[
state
,
{
updateKey
}],
[
state
,
updateKey
])}
>
{
children
}
<
/LocalStorageContext.Provider
>
)
}
export
function
Updater
()
{
const
[
state
]
=
useLocalStorageContext
()
useEffect
(()
=>
{
window
.
localStorage
.
setItem
(
UNISWAP
,
JSON
.
stringify
({
...
state
,
[
LAST_SAVED
]:
Math
.
floor
(
Date
.
now
()
/
1000
)
}))
})
return
null
}
export
function
useBetaMessageManager
()
{
const
[
state
,
{
updateKey
}]
=
useLocalStorageContext
()
const
dismissBetaMessage
=
useCallback
(()
=>
{
updateKey
(
BETA_MESSAGE_DISMISSED
,
true
)
},
[
updateKey
])
return
[
!
state
[
BETA_MESSAGE_DISMISSED
],
dismissBetaMessage
]
}
src/contexts/Tokens.js
View file @
d265b120
...
...
@@ -89,6 +89,14 @@ const INITIAL_TOKENS_CONTEXT = {
[
DECIMALS
]:
9
,
[
EXCHANGE_ADDRESS
]:
'
0xb92dE8B30584392Af27726D5ce04Ef3c4e5c9924
'
},
'
0xc719d010B63E5bbF2C0551872CD5316ED26AcD83
'
:
{
[
NAME
]:
'
Decentralized Insurance Protocol
'
,
[
SYMBOL
]:
'
DIP
'
,
[
DECIMALS
]:
18
,
[
EXCHANGE_ADDRESS
]:
'
0x61792F290e5100FBBcBb2309F03A1Bab869fb850
'
},
'
0x4946Fcea7C692606e8908002e55A582af44AC121
'
:
{
[
NAME
]:
'
FOAM Token
'
,
[
SYMBOL
]:
'
FOAM
'
,
...
...
@@ -191,6 +199,12 @@ const INITIAL_TOKENS_CONTEXT = {
[
DECIMALS
]:
18
,
[
EXCHANGE_ADDRESS
]:
'
0x2C4Bd064b998838076fa341A83d007FC2FA50957
'
},
'
0xec67005c4E498Ec7f55E092bd1d35cbC47C91892
'
:
{
[
NAME
]:
'
Melon Token
'
,
[
SYMBOL
]:
'
MLN
'
,
[
DECIMALS
]:
18
,
[
EXCHANGE_ADDRESS
]:
'
0xA931F4eB165AC307fD7431b5EC6eADde53E14b0C
'
},
'
0x957c30aB0426e0C93CD8241E2c60392d08c6aC8e
'
:
{
[
NAME
]:
'
Modum Token
'
,
[
SYMBOL
]:
'
MOD
'
,
...
...
src/index.js
View file @
d265b120
...
...
@@ -4,6 +4,7 @@ import ReactGA from 'react-ga'
import
Web3Provider
,
{
Connectors
}
from
'
web3-react
'
import
ThemeProvider
,
{
GlobalStyle
}
from
'
./theme
'
import
LocalStorageContextProvider
,
{
Updater
as
LocalStorageContextUpdater
}
from
'
./contexts/LocalStorage
'
import
ApplicationContextProvider
,
{
Updater
as
ApplicationContextUpdater
}
from
'
./contexts/Application
'
import
TransactionContextProvider
,
{
Updater
as
TransactionContextUpdater
}
from
'
./contexts/Transactions
'
import
TokensContextProvider
from
'
./contexts/Tokens
'
...
...
@@ -29,21 +30,24 @@ const connectors = { Injected, Network }
function
ContextProviders
({
children
})
{
return
(
<
ApplicationContextProvider
>
<
TransactionContextProvider
>
<
TokensContextProvider
>
<
BalancesContextProvider
>
<
AllowancesContextProvider
>
{
children
}
<
/AllowancesContextProvider
>
<
/BalancesContextProvider
>
<
/TokensContextProvider
>
<
/TransactionContextProvider
>
<
/ApplicationContextProvider
>
<
LocalStorageContextProvider
>
<
ApplicationContextProvider
>
<
TransactionContextProvider
>
<
TokensContextProvider
>
<
BalancesContextProvider
>
<
AllowancesContextProvider
>
{
children
}
<
/AllowancesContextProvider
>
<
/BalancesContextProvider
>
<
/TokensContextProvider
>
<
/TransactionContextProvider
>
<
/ApplicationContextProvider
>
<
/LocalStorageContextProvider
>
)
}
function
Updaters
()
{
return
(
<>
<
LocalStorageContextUpdater
/>
<
ApplicationContextUpdater
/>
<
TransactionContextUpdater
/>
<
/
>
...
...
src/pages/Pool/AddLiquidity.js
View file @
d265b120
...
...
@@ -362,6 +362,7 @@ export default function AddLiquidity() {
})
const
deadline
=
Math
.
ceil
(
Date
.
now
()
/
1000
)
+
DEADLINE_FROM_NOW
const
estimatedGasLimit
=
await
exchangeContract
.
estimate
.
addLiquidity
(
isNewExchange
?
ethers
.
constants
.
Zero
:
liquidityTokensMin
,
isNewExchange
?
outputValueParsed
:
outputValueMax
,
...
...
@@ -371,6 +372,8 @@ export default function AddLiquidity() {
}
)
const
gasLimit
=
calculateGasMargin
(
estimatedGasLimit
,
GAS_MARGIN
)
exchangeContract
.
addLiquidity
(
isNewExchange
?
ethers
.
constants
.
Zero
:
liquidityTokensMin
,
...
...
@@ -378,7 +381,7 @@ export default function AddLiquidity() {
deadline
,
{
value
:
inputValueParsed
,
gasLimit
:
calculateGasMargin
(
estimatedGasLimit
,
GAS_MARGIN
)
gasLimit
}
)
.
then
(
response
=>
{
...
...
src/pages/Pool/ModeSelector.js
View file @
d265b120
...
...
@@ -64,7 +64,7 @@ const StyledNavLink = styled(NavLink).attrs({
&.
${
activeClassName
}
{
background-color:
${({
theme
})
=>
theme
.
white
}
;
border-radius: 3rem;
box-shadow: 0 0
0.5px 0.5
px
${({
theme
})
=>
theme
.
mercuryGray
}
;
box-shadow: 0 0
1px 1
px
${({
theme
})
=>
theme
.
mercuryGray
}
;
font-weight: 500;
color:
${({
theme
})
=>
theme
.
royalBlue
}
;
}
...
...
src/pages/Send/index.js
View file @
d265b120
...
...
@@ -612,7 +612,7 @@ export default function Swap({ initialCurrency }) {
isError
=
{
isError
}
slippageWarning
=
{
slippageWarning
&&
slippageWarningText
}
highSlippageWarning
=
{
highSlippageWarning
&&
slippageWarningText
}
renderTransactionDetails
=
{
renderTransactionDetails
}
dropDownContent
=
{
renderTransactionDetails
}
/
>
)
}
...
...
@@ -760,13 +760,13 @@ export default function Swap({ initialCurrency }) {
{
inverted
?
(
<
span
>
{
exchangeRate
?
`1
${
outputSymbol
}
=
${
amountFormatter
(
exchangeRateInverted
,
18
,
4
,
false
)}
${
in
putSymbol
}
`
?
`1
${
inputSymbol
}
=
${
amountFormatter
(
exchangeRate
,
18
,
4
,
false
)}
${
out
putSymbol
}
`
:
'
-
'
}
<
/span
>
)
:
(
<
span
>
{
exchangeRate
?
`1
${
inputSymbol
}
=
${
amountFormatter
(
exchangeRate
,
18
,
4
,
false
)}
${
out
putSymbol
}
`
?
`1
${
outputSymbol
}
=
${
amountFormatter
(
exchangeRateInverted
,
18
,
4
,
false
)}
${
in
putSymbol
}
`
:
'
-
'
}
<
/span
>
)}
...
...
src/pages/Swap/index.js
View file @
d265b120
...
...
@@ -7,8 +7,8 @@ import styled from 'styled-components'
import
{
Button
}
from
'
../../theme
'
import
CurrencyInputPanel
from
'
../../components/CurrencyInputPanel
'
import
NewContextualInfo
from
'
../../components/ContextualInfoNew
'
import
OversizedPanel
from
'
../../components/OversizedPanel
'
import
TransactionDetails
from
'
../../components/TransactionDetails
'
import
ArrowDownBlue
from
'
../../assets/images/arrow-down-blue.svg
'
import
ArrowDownGrey
from
'
../../assets/images/arrow-down-grey.svg
'
import
{
amountFormatter
,
calculateGasMargin
}
from
'
../../utils
'
...
...
@@ -26,8 +26,8 @@ const TOKEN_TO_ETH = 1
const
TOKEN_TO_TOKEN
=
2
// denominated in bips
const
ALLOWED_SLIPPAGE
=
ethers
.
utils
.
bigNumberify
(
200
)
const
TOKEN_ALLOWED_SLIPPAGE
=
ethers
.
utils
.
bigNumberify
(
400
)
const
ALLOWED_SLIPPAGE
_DEFAULT
=
100
const
TOKEN_ALLOWED_SLIPPAGE
_DEFAULT
=
100
// denominated in seconds
const
DEADLINE_FROM_NOW
=
60
*
15
...
...
@@ -35,14 +35,6 @@ const DEADLINE_FROM_NOW = 60 * 15
// denominated in bips
const
GAS_MARGIN
=
ethers
.
utils
.
bigNumberify
(
1000
)
const
BlueSpan
=
styled
.
span
`
color:
${({
theme
})
=>
theme
.
royalBlue
}
;
`
const
LastSummaryText
=
styled
.
div
`
margin-top: 1rem;
`
const
DownArrowBackground
=
styled
.
div
`
${({
theme
})
=>
theme
.
flexRowNoWrap
}
justify-content: center;
...
...
@@ -81,9 +73,9 @@ const Flex = styled.div`
}
`
function
calculateSlippageBounds
(
value
,
token
=
false
)
{
function
calculateSlippageBounds
(
value
,
token
=
false
,
tokenAllowedSlippage
,
allowedSlippage
)
{
if
(
value
)
{
const
offset
=
value
.
mul
(
token
?
TOKEN_ALLOWED_SLIPPAGE
:
ALLOWED_SLIPPAGE
).
div
(
ethers
.
utils
.
bigNumberify
(
10000
))
const
offset
=
value
.
mul
(
token
?
tokenAllowedSlippage
:
allowedSlippage
).
div
(
ethers
.
utils
.
bigNumberify
(
10000
))
const
minimum
=
value
.
sub
(
offset
)
const
maximum
=
value
.
add
(
offset
)
return
{
...
...
@@ -244,12 +236,18 @@ export default function Swap({ initialCurrency }) {
const
addTransaction
=
useTransactionAdder
()
const
[
rawSlippage
,
setRawSlippage
]
=
useState
(
ALLOWED_SLIPPAGE_DEFAULT
)
const
[
rawTokenSlippage
,
setRawTokenSlippage
]
=
useState
(
TOKEN_ALLOWED_SLIPPAGE_DEFAULT
)
let
allowedSlippageBig
=
ethers
.
utils
.
bigNumberify
(
rawSlippage
)
let
tokenAllowedSlippageBig
=
ethers
.
utils
.
bigNumberify
(
rawTokenSlippage
)
// analytics
useEffect
(()
=>
{
ReactGA
.
pageview
(
window
.
location
.
pathname
+
window
.
location
.
search
)
},
[])
// core swap state
// core swap state
-
const
[
swapState
,
dispatchSwapState
]
=
useReducer
(
swapStateReducer
,
initialCurrency
,
getInitialSwapState
)
const
{
independentValue
,
dependentValue
,
independentField
,
inputCurrency
,
outputCurrency
}
=
swapState
...
...
@@ -326,7 +324,9 @@ export default function Swap({ initialCurrency }) {
// calculate slippage from target rate
const
{
minimum
:
dependentValueMinumum
,
maximum
:
dependentValueMaximum
}
=
calculateSlippageBounds
(
dependentValue
,
swapType
===
TOKEN_TO_TOKEN
swapType
===
TOKEN_TO_TOKEN
,
tokenAllowedSlippageBig
,
allowedSlippageBig
)
// validate input allowance + balance
...
...
@@ -496,118 +496,6 @@ export default function Swap({ initialCurrency }) {
return
`Balance:
${
value
}
`
}
function
renderTransactionDetails
()
{
ReactGA
.
event
({
category
:
'
TransactionDetail
'
,
action
:
'
Open
'
})
const
b
=
text
=>
<
BlueSpan
>
{
text
}
<
/BlueSpan
>
if
(
independentField
===
INPUT
)
{
return
(
<
div
>
<
div
>
{
t
(
'
youAreSelling
'
)}{
'
'
}
{
b
(
`
${
amountFormatter
(
independentValueParsed
,
independentDecimals
,
Math
.
min
(
4
,
independentDecimals
)
)}
${
inputSymbol
}
`
)}
.
<
/div
>
<
LastSummaryText
>
{
t
(
'
youWillReceive
'
)}{
'
'
}
{
b
(
`
${
amountFormatter
(
dependentValueMinumum
,
dependentDecimals
,
Math
.
min
(
4
,
dependentDecimals
)
)}
${
outputSymbol
}
`
)}{
'
'
}
{
t
(
'
orTransFail
'
)}
<
/LastSummaryText
>
<
LastSummaryText
>
{(
slippageWarning
||
highSlippageWarning
)
&&
(
<
span
role
=
"
img
"
aria
-
label
=
"
warning
"
>
⚠️
<
/span
>
)}
{
t
(
'
priceChange
'
)}
{
b
(
`
${
percentSlippageFormatted
}
%`
)}.
<
/LastSummaryText
>
<
/div
>
)
}
else
{
return
(
<
div
>
<
div
>
{
t
(
'
youAreBuying
'
)}{
'
'
}
{
b
(
`
${
amountFormatter
(
independentValueParsed
,
independentDecimals
,
Math
.
min
(
4
,
independentDecimals
)
)}
${
outputSymbol
}
`
)}
.
<
/div
>
<
LastSummaryText
>
{
t
(
'
itWillCost
'
)}{
'
'
}
{
b
(
`
${
amountFormatter
(
dependentValueMaximum
,
dependentDecimals
,
Math
.
min
(
4
,
dependentDecimals
)
)}
${
inputSymbol
}
`
)}{
'
'
}
{
t
(
'
orTransFail
'
)}
<
/LastSummaryText
>
<
LastSummaryText
>
{
t
(
'
priceChange
'
)}
{
b
(
`
${
percentSlippageFormatted
}
%`
)}.
<
/LastSummaryText
>
<
/div
>
)
}
}
function
renderSummary
()
{
let
contextualInfo
=
''
let
isError
=
false
if
(
inputError
||
independentError
)
{
contextualInfo
=
inputError
||
independentError
isError
=
true
}
else
if
(
!
inputCurrency
||
!
outputCurrency
)
{
contextualInfo
=
t
(
'
selectTokenCont
'
)
}
else
if
(
!
independentValue
)
{
contextualInfo
=
t
(
'
enterValueCont
'
)
}
else
if
(
!
account
)
{
contextualInfo
=
t
(
'
noWallet
'
)
isError
=
true
}
const
slippageWarningText
=
highSlippageWarning
?
t
(
'
highSlippageWarning
'
)
:
slippageWarning
?
t
(
'
slippageWarning
'
)
:
''
return
(
<
NewContextualInfo
openDetailsText
=
{
t
(
'
transactionDetails
'
)}
closeDetailsText
=
{
t
(
'
hideDetails
'
)}
contextualInfo
=
{
contextualInfo
?
contextualInfo
:
slippageWarningText
}
allowExpand
=
{
!!
(
inputCurrency
&&
outputCurrency
&&
inputValueParsed
&&
outputValueParsed
)}
isError
=
{
isError
}
slippageWarning
=
{
slippageWarning
&&
!
contextualInfo
}
highSlippageWarning
=
{
highSlippageWarning
&&
!
contextualInfo
}
renderTransactionDetails
=
{
renderTransactionDetails
}
/
>
)
}
async
function
onSwap
()
{
const
deadline
=
Math
.
ceil
(
Date
.
now
()
/
1000
)
+
DEADLINE_FROM_NOW
...
...
@@ -664,6 +552,8 @@ export default function Swap({ initialCurrency }) {
})
}
const
[
customSlippageError
,
setcustomSlippageError
]
=
useState
(
''
)
return
(
<>
<
CurrencyInputPanel
...
...
@@ -731,22 +621,51 @@ export default function Swap({ initialCurrency }) {
{
inverted
?
(
<
span
>
{
exchangeRate
?
`1
${
outputSymbol
}
=
${
amountFormatter
(
exchangeRateInverted
,
18
,
4
,
false
)}
${
in
putSymbol
}
`
?
`1
${
inputSymbol
}
=
${
amountFormatter
(
exchangeRate
,
18
,
4
,
false
)}
${
out
putSymbol
}
`
:
'
-
'
}
<
/span
>
)
:
(
<
span
>
{
exchangeRate
?
`1
${
inputSymbol
}
=
${
amountFormatter
(
exchangeRate
,
18
,
4
,
false
)}
${
out
putSymbol
}
`
?
`1
${
outputSymbol
}
=
${
amountFormatter
(
exchangeRateInverted
,
18
,
4
,
false
)}
${
in
putSymbol
}
`
:
'
-
'
}
<
/span
>
)}
<
/ExchangeRateWrapper
>
<
/OversizedPanel
>
{
renderSummary
()}
<
TransactionDetails
account
=
{
account
}
setRawSlippage
=
{
setRawSlippage
}
setRawTokenSlippage
=
{
setRawTokenSlippage
}
rawSlippage
=
{
rawSlippage
}
slippageWarning
=
{
slippageWarning
}
highSlippageWarning
=
{
highSlippageWarning
}
inputError
=
{
inputError
}
independentError
=
{
independentError
}
inputCurrency
=
{
inputCurrency
}
outputCurrency
=
{
outputCurrency
}
independentValue
=
{
independentValue
}
independentValueParsed
=
{
independentValueParsed
}
independentField
=
{
independentField
}
INPUT
=
{
INPUT
}
inputValueParsed
=
{
inputValueParsed
}
outputValueParsed
=
{
outputValueParsed
}
inputSymbol
=
{
inputSymbol
}
outputSymbol
=
{
outputSymbol
}
dependentValueMinumum
=
{
dependentValueMinumum
}
dependentValueMaximum
=
{
dependentValueMaximum
}
dependentDecimals
=
{
dependentDecimals
}
independentDecimals
=
{
independentDecimals
}
percentSlippageFormatted
=
{
percentSlippageFormatted
}
setcustomSlippageError
=
{
setcustomSlippageError
}
/
>
<
Flex
>
<
Button
disabled
=
{
!
isValid
}
onClick
=
{
onSwap
}
warning
=
{
highSlippageWarning
}
>
{
highSlippageWarning
?
t
(
'
swapAnyway
'
)
:
t
(
'
swap
'
)}
<
Button
disabled
=
{
!
isValid
||
customSlippageError
===
'
invalid
'
}
onClick
=
{
onSwap
}
warning
=
{
highSlippageWarning
||
customSlippageError
===
'
warning
'
}
>
{
highSlippageWarning
||
customSlippageError
===
'
warning
'
?
t
(
'
swapAnyway
'
)
:
t
(
'
swap
'
)}
<
/Button
>
<
/Flex
>
<
/
>
...
...
src/theme/index.js
View file @
d265b120
...
...
@@ -38,6 +38,9 @@ const theme = {
chaliceGray
:
'
#AEAEAE
'
,
doveGray
:
'
#737373
'
,
mineshaftGray
:
'
#2B2B2B
'
,
buttonOutlineGrey
:
'
#f2f2f2
'
,
//blacks
charcoalBlack
:
'
#404040
'
,
// blues
zumthorBlue
:
'
#EBF4FF
'
,
malibuBlue
:
'
#5CA2FF
'
,
...
...
@@ -53,6 +56,7 @@ const theme = {
// pink
uniswapPink
:
'
#DC6BE5
'
,
connectedGreen
:
'
#27AE60
'
,
// media queries
mediaWidth
:
mediaWidthTemplates
,
// css snippets
...
...
yarn.lock
View file @
d265b120
This diff is collapsed.
Click to expand it.
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment