1 <style lang="scss" scoped>
9 justify-content: space-between;
11 .topbar .topbar-left {
14 text-overflow: ellipsis;
19 .topbar-left .btn-menu {
23 .topbar-left .btn-menu i {
33 .topbar .topbar-right {
43 .content .token-amount {
48 .token-amount:first-letter {
49 color: rgba(255, 255, 255, 0.56);
54 justify-content: space-evenly;
64 a:hover .icon, a:focus .icon, a:active .icon{
65 background: rgba(255, 255, 255, 0.2);
74 .transaction-title h3 {
76 padding: 12px 0 16px 0px;
87 text-transform: capitalize;
113 background: rgba(255, 255, 255, 0.04);
115 display: inline-flex;
117 justify-content: center;
125 background: linear-gradient(228.34deg, rgba(255, 255, 255, 0) 0%, rgba(255, 255, 255, 0.1) 100%), #1A1A1A;
130 background: linear-gradient(228.34deg, rgba(255, 255, 255, 0) 0%, rgba(255, 255, 255, 0.16) 100%), #0A42D0;
134 color: rgba(255, 255, 255, 0.72);
139 /* The switch - the box around the slider */
142 display: inline-block;
147 /* Hide default HTML checkbox */
162 background-color: #F5F5F5;
163 -webkit-transition: .4s;
174 background-color: white;
175 box-shadow: 0px 4px 8px rgba(0, 0, 0, 0.04);
176 -webkit-transition: .4s;
180 /*input:checked + .slider {*/
181 /*background-color: #2196F3;*/
184 /*input:focus + .slider {*/
185 /*box-shadow: 0 0 1px #2196F3;*/
188 input:checked + .slider:before {
189 -webkit-transform: translateX(67px);
190 -ms-transform: translateX(67px);
191 transform: translateX(67px);
194 /* Rounded sliders */
199 .slider.round:before {
205 justify-content: space-around;
210 color: rgba(0, 0, 0, 0.24);
213 .slider-label>div.active{
214 color: rgba(0, 0, 0, 0.64);
226 flex-direction: column;
229 @media screen and (min-width: 768px) {
247 .token-amount:first-letter {
253 margin-right: inherit;
263 border-radius: 16px 0px 0px 16px;
265 color: rgba(0, 0, 0, 0.88);
273 vertical-align: middle;
278 <div class="warp-menu">
281 <div v-if="address!=undefined" >
282 <span class="alias color-black">{{currentAccount.alias}}</span>
284 <div class="topbar-right">
285 <label class="switch">
286 <input type="checkbox" v-model="isVapor" @change="netTypeToggle">
287 <span class="slider round"></span>
288 <div class="d-flex slider-label">
289 <div :class="{ active: !isVapor }" >{{ $t('main.bytom') }}</div>
290 <div :class="{ active: isVapor }">{{ $t('main.vapor') }}</div>
295 <div :class="['content balance-bg',{ 'vapor-bg': isVapor }]">
296 <div class="amount color-white">
297 <div class="total-asset">{{ $t('main.totalAsset') }}</div>
298 <div class="token-amount">
302 <div class="btn-send-transfer">
304 <a @click="transferOpen">
305 <i class="icon iconfont icon_send"></i>
306 <div>{{ $t('main.send') }}</div>
308 <a @click="showQrcode">
309 <i class="icon iconfont icon_recvice"></i>
310 <div>{{ $t('main.receive') }}</div>
312 <a class="color-white" href="https://ofmf.bymov.io/cross-chain" target="_blank">
313 <i class="icon iconfont icon_cross"></i>
314 <div>{{ $t('main.crossChain') }}</div>
320 <section v-if="address!=undefined" class="transaction-title">
321 <h3 class="color-black">{{ $t('main.asset') }}</h3>
322 <a class="delay-btn" @click="delayOpen"><i class="iconfont icon_SBell"></i>{{ $t('delayTx.title') }}</a>
324 <section class="assets">
325 <div v-if=" balances && balances.length > 0">
327 <li class="list-item" v-for="(balance, index) in balances" :key="index" @click="assetOpen(balance)">
328 <div class="symbol" v-if="balance.asset.symbol!== 'Asset'">
329 <img :src="img(balance.asset.symbol)" alt="" class="c-icon" v-on:error="onImgError">
330 <div class="uppercase">
331 {{balance.asset.symbol}}
339 <div class="addr color-grey uppercase">{{ shortAddress(balance.asset.assetId) }}</div>
342 <div class="text-align-right">
343 <div class="value">{{ itemBalance(balance) }}</div>
344 <div class="addr color-grey">{{ formatCurrency(currentBalanceAmount(balance)) }}</div>
352 <li class="list-item" v-for="(asset, index) in defaultBalances" :key="index" @click="assetOpen(asset)">
355 <img :src="img(asset.asset.symbol)" alt="" class="c-icon" v-on:error="onImgError">
357 <div class="uppercase">
358 {{asset.asset.symbol}}
363 <div class=" text-align-right">
364 <div class="value">{{ itemBalance(asset) }}</div>
365 <div class="addr color-grey">{{ formatCurrency(asset[ currency ]) }}</div>
374 <div class="mask" v-show="maskShow"></div>
375 <transition :enter-active-class="enterActive" :leave-active-class="leaveActive">
376 <router-view></router-view>
383 import address from "@/utils/address";
384 import account from "@/models/account";
385 import { camelize } from "@/utils/utils";
386 import { BTM } from "@/utils/constants";
387 import { mapActions, mapGetters, mapState } from 'vuex'
388 import * as Actions from '@/store/constants';
389 import _ from 'lodash';
390 import { Number as Num } from "@/utils/Number"
391 import BigNumber from "bignumber.js"
392 import getLang from "@/assets/language/sdk";
395 const EnterActive = 'animated faster fadeInLeft';
396 const LeaveActive = 'animated faster fadeOutLeft';
403 enterActive: EnterActive,
404 leaveActive: LeaveActive,
424 if (to.name.startsWith('menu')) {
426 } else if (from.name.startsWith('menu')) {
427 this.maskShow = false
430 // remove transition for some page
431 this.enterActive = EnterActive
432 this.leaveActive = LeaveActive
433 if (to.name == 'transfer-confirm' || from.name == 'transfer-confirm') {
434 this.enterActive = ''
435 this.leaveActive = ''
437 if (from.name == 'transfer-confirm') {
441 currentAccount(newVal, oldVal) {
442 if (newVal.guid == undefined){
447 if(this.netType === 'vapor'){
448 addr = newVal.vpAddress
450 addr = newVal.address
452 this.refreshBalance(addr)
456 accountBalance: function () {
458 const balances = this.balances
460 if(balances && balances.length >0 ){
461 const currency = camelize(this.currency)
462 const arr = balances.map(o => o[currency])
463 balance = BigNumber.sum.apply(null, arr)
465 return Num.formatCurrency( (balance != null && balance != 0)? balance : '0.00', this.currency)
468 if(this.netType === 'vapor'){
469 const vpAddress = this.currentAccount.vpAddress
471 const bytom = this.bytom.clone();
472 return account.copy(this.currentAccount.guid).then(accounts => {
473 //update currentAccount
474 bytom.currentAccount.vpAddress = accounts.address
476 bytom.keychain.pairs[this.net][bytom.currentAccount.alias].vpAddress = accounts.address
478 this[Actions.UPDATE_STORED_BYTOM](bytom).then(() => {
479 this.setupRefreshTimer()
482 return accounts.address
484 }else return vpAddress
487 return this.currentAccount.address
490 balances: function(){
491 if(this.netType === 'vapor'){
492 return this.currentAccount.vpBalances
494 return this.currentAccount.balances
509 img:function (symbol) {
510 const _symbol = symbol.toLowerCase();
511 if(this.netType === 'vapor'){
512 return `https://cdn.blockmeta.com/resources/logo/vapor/${_symbol}.png`
514 return `https://cdn.blockmeta.com/resources/logo/bytom/${_symbol}.png`
517 onImgError: function(event) {
518 event.target.src = require(`@/assets/img/asset/${this.netType}.png`)
520 currentBalanceAmount: function (balance) {
521 return balance[ camelize(this.currency) ]
523 shortAddress: function (add) {
524 return address.short(add)
526 formatCurrency: function (num) {
527 return Num.formatCurrency(num, this.currency)
529 itemBalance: function(assetObj){
530 const asset = assetObj.asset
531 if(asset.assetId === BTM){
532 return Num.formatNue(assetObj.balance,8)
534 return assetObj.balance
537 setupRefreshTimer() {
539 clearInterval(this.t)
541 this.t = setInterval(() => {
542 this.refreshBalance(this.address)
545 netTypeToggle: function () {
546 const bytom = this.bytom.clone();
547 const newNetType = this.isVapor? 'vapor':'bytom'
549 bytom.settings.netType = newNetType;
551 account.setupNet(`${this.net}${newNetType}`)
552 if(this.isVapor && !this.currentAccount.vpAddress){
553 account.copy(this.currentAccount.guid).then(accounts => {
554 //update currentAccount
555 bytom.currentAccount.vpAddress = accounts.address
557 bytom.keychain.pairs[this.net][bytom.currentAccount.alias].vpAddress = accounts.address
559 this[Actions.UPDATE_STORED_BYTOM](bytom).then(()=>{
560 this.setupRefreshTimer()
565 e = this.$t(`error.${error.code}`)
566 }else if(error.message){
567 e = getLang(error.message, this.language)
569 this.$toast.error(e);
572 this[Actions.UPDATE_STORED_BYTOM](bytom).then(()=>{
573 this.setupRefreshTimer()
577 showQrcode: function () {
578 this.$router.push('received')
580 openMenu: function () {
581 this.$router.push('menu')
583 transferOpen: function () {
584 this.$router.push('transfer')
586 delayOpen: function () {
587 this.$router.push('delayTx')
589 crossChainOpen: function () {
590 this.$router.push('crossChain')
592 listVoteOpen: function () {
593 this.$router.push('listVote')
595 assetOpen: function (asset) {
596 this[Actions.SET_CURRENT_ASSET](asset)
597 this.$router.push('asset')
599 refreshBalance: function (address) {
601 account.balance(address, this)
608 Actions.UPDATE_STORED_BYTOM,
609 Actions.SET_CURRENT_ASSET,
613 this.setupRefreshTimer();
614 this.refreshBalance(this.address)
616 this.isVapor = this.netType =='vapor'
621 clearInterval(this.t)