340 lines
12 KiB
Vue
340 lines
12 KiB
Vue
<template>
|
|
<q-page padding>
|
|
|
|
<AddressHeader :address="info.address" :header="info.name" :subheader="info.address" />
|
|
|
|
|
|
<div class="row justify-between" style="max-width: 768px">
|
|
|
|
<div class="infoBox">
|
|
<div class="infoBoxContent">
|
|
<div class="text"><span>Balance</span></div>
|
|
<div class="value"><span><FormatRyo :amount="info.balance" /></span></div>
|
|
</div>
|
|
</div>
|
|
|
|
<div class="infoBox">
|
|
<div class="infoBoxContent">
|
|
<div class="text"><span>Unlocked balance</span></div>
|
|
<div class="value"><span><FormatRyo :amount="info.unlocked_balance" /></span></div>
|
|
</div>
|
|
</div>
|
|
|
|
<div class="infoBox q-pt-md">
|
|
|
|
<q-btn icon-right="more_vert" label="Wallet actions" size="md" flat>
|
|
<q-popover anchor="bottom right" self="top right">
|
|
<q-list separator link>
|
|
<q-item :disabled="!is_ready"
|
|
v-close-overlay @click.native="getPrivateKeys()">
|
|
<q-item-main>
|
|
<q-item-tile label>Show Private Keys</q-item-tile>
|
|
</q-item-main>
|
|
</q-item>
|
|
<q-item :disabled="!is_ready"
|
|
v-close-overlay @click.native="showModal('rescan_modal_show')">
|
|
<q-item-main>
|
|
<q-item-tile label>Rescan Wallet</q-item-tile>
|
|
</q-item-main>
|
|
</q-item>
|
|
<q-item :disabled="!is_ready"
|
|
v-close-overlay @click.native="showModal('key_image_modal_show')">
|
|
<q-item-main>
|
|
<q-item-tile label>Manage Key Images</q-item-tile>
|
|
</q-item-main>
|
|
</q-item>
|
|
</q-list>
|
|
</q-popover>
|
|
|
|
</q-btn>
|
|
|
|
</div>
|
|
</div>
|
|
|
|
|
|
<h6 class="q-my-none">Recent transactions:</h6>
|
|
|
|
<div style="margin: 0 -16px;">
|
|
|
|
<TxList :limit="5" />
|
|
|
|
</div>
|
|
|
|
<q-inner-loading :visible="spinner">
|
|
<q-spinner color="primary" :size="30" />
|
|
</q-inner-loading>
|
|
|
|
<q-modal minimized v-model="private_keys_modal_show" @hide="closePrivateKeys()">
|
|
<div class="q-ma-md">
|
|
|
|
<template v-if="secret.mnemonic">
|
|
<h6 class="q-mb-xs q-mt-lg">Seed words</h6>
|
|
<p>{{ secret.mnemonic }}</p>
|
|
</template>
|
|
|
|
<template v-if="secret.view_key != secret.spend_key">
|
|
<h6 class="q-mb-xs">View key</h6>
|
|
<p>{{ secret.view_key }}</p>
|
|
</template>
|
|
|
|
<template v-if="secret.spend_key != '0000000000000000000000000000000000000000000000000000000000000000'">
|
|
<h6 class="q-mb-xs">Spend key</h6>
|
|
<p>{{ secret.spend_key }}</p>
|
|
</template>
|
|
|
|
<q-btn
|
|
color="primary"
|
|
@click="private_keys_modal_show = false"
|
|
label="Close"
|
|
/>
|
|
</div>
|
|
</q-modal>
|
|
|
|
|
|
<q-modal minimized v-model="rescan_modal_show">
|
|
<div class="q-ma-md">
|
|
|
|
<h4 class="q-mt-lg q-mb-md">Rescan wallet</h4>
|
|
<p>Select full rescan or rescan of spent outputs only.</p>
|
|
|
|
<div class="q-mt-lg">
|
|
<q-radio v-model="rescan_type" val="full" label="Rescan full blockchain" />
|
|
</div>
|
|
<div class="q-mt-sm">
|
|
<q-radio v-model="rescan_type" val="spent" label="Rescan spent outputs" />
|
|
</div>
|
|
|
|
<div class="q-mt-xl text-right">
|
|
<q-btn
|
|
flat class="q-mr-sm"
|
|
@click="rescan_modal_show = false"
|
|
label="Close"
|
|
/>
|
|
<q-btn
|
|
color="primary"
|
|
@click="rescanWallet()"
|
|
label="Rescan"
|
|
/>
|
|
</div>
|
|
</div>
|
|
</q-modal>
|
|
|
|
<q-modal minimized v-model="key_image_modal_show">
|
|
<div class="q-ma-md">
|
|
|
|
<h4 class="q-mt-lg q-mb-md">{{key_image_import_export}} key images</h4>
|
|
|
|
<div class="row q-mb-md">
|
|
<div class="q-mr-xl"><q-radio v-model="key_image_import_export" val="Export" label="Export" /></div>
|
|
<div><q-radio v-model="key_image_import_export" val="Import" label="Import" /></div>
|
|
</div>
|
|
|
|
<template v-if="key_image_import_export == 'Export'">
|
|
<q-field style="width:450px">
|
|
<div class="row gutter-sm">
|
|
<div class="col-9">
|
|
<q-input v-model="key_image_export_path" stack-label="Key image export directory" disable />
|
|
<input type="file" webkitdirectory directory id="keyImageExportPath" v-on:change="setKeyImageExportPath" ref="keyImageExportSelect" hidden />
|
|
</div>
|
|
<div class="col-3">
|
|
<q-btn class="float-right" v-on:click="selectKeyImageExportPath">Browse</q-btn>
|
|
</div>
|
|
</div>
|
|
</q-field>
|
|
</template>
|
|
<template v-if="key_image_import_export == 'Import'">
|
|
<q-field style="width:450px">
|
|
<div class="row gutter-sm">
|
|
<div class="col-9">
|
|
<q-input v-model="key_image_import_path" stack-label="Key image import file" disable />
|
|
<input type="file" id="keyImageImportPath" v-on:change="setKeyImageImportPath" ref="keyImageImportSelect" hidden />
|
|
</div>
|
|
<div class="col-3">
|
|
<q-btn class="float-right" v-on:click="selectKeyImageImportPath">Browse</q-btn>
|
|
</div>
|
|
</div>
|
|
</q-field>
|
|
</template>
|
|
|
|
<div class="q-mt-xl text-right">
|
|
<q-btn
|
|
flat class="q-mr-sm"
|
|
@click="key_image_modal_show = false"
|
|
label="Close"
|
|
/>
|
|
<q-btn
|
|
color="primary"
|
|
@click="doKeyImages()"
|
|
:label="this.key_image_import_export"
|
|
/>
|
|
</div>
|
|
</div>
|
|
</q-modal>
|
|
|
|
</q-page>
|
|
</template>
|
|
|
|
<script>
|
|
import { mapState } from "vuex"
|
|
import AddressHeader from "components/address_header"
|
|
import FormatRyo from "components/format_ryo"
|
|
import TxList from "components/tx_list"
|
|
export default {
|
|
computed: mapState({
|
|
theme: state => state.gateway.app.config.appearance.theme,
|
|
info: state => state.gateway.wallet.info,
|
|
secret: state => state.gateway.wallet.secret,
|
|
data_dir: state => state.gateway.app.config.app.data_dir,
|
|
is_ready (state) {
|
|
return this.$store.getters["gateway/isReady"]
|
|
}
|
|
}),
|
|
data () {
|
|
return {
|
|
spinner: false,
|
|
private_keys_modal_show: false,
|
|
rescan_modal_show: false,
|
|
rescan_type: "full",
|
|
key_image_modal_show: false,
|
|
key_image_import_export: "Export",
|
|
key_image_export_path: '',
|
|
key_image_import_path: '',
|
|
}
|
|
},
|
|
mounted() {
|
|
const path = require("path")
|
|
this.key_image_export_path = path.join(this.data_dir, "gui")
|
|
this.key_image_import_path = path.join(this.data_dir, "gui", "key_image_export.json")
|
|
},
|
|
watch: {
|
|
secret: {
|
|
handler(val, old) {
|
|
if(val.view_key == old.view_key) return
|
|
this.spinner = false
|
|
switch(this.secret.view_key) {
|
|
case "":
|
|
break
|
|
case -1:
|
|
this.$q.notify({
|
|
type: "negative",
|
|
timeout: 1000,
|
|
message: this.secret.mnemonic
|
|
})
|
|
this.$store.commit("gateway/set_wallet_data", {
|
|
secret: {
|
|
mnemonic: "",
|
|
spend_key: "",
|
|
view_key: ""
|
|
}
|
|
})
|
|
break
|
|
default:
|
|
this.private_keys_modal_show = true
|
|
break
|
|
}
|
|
},
|
|
deep: true
|
|
}
|
|
},
|
|
methods: {
|
|
showModal (which) {
|
|
if(!this.is_ready) return
|
|
this[which] = true;
|
|
},
|
|
getPrivateKeys () {
|
|
if(!this.is_ready) return
|
|
this.$q.dialog({
|
|
title: "Show seed words",
|
|
message: "Enter wallet password to continue.",
|
|
prompt: {
|
|
model: "",
|
|
type: "password"
|
|
},
|
|
ok: {
|
|
label: "SHOW"
|
|
},
|
|
cancel: {
|
|
flat: true,
|
|
label: "CANCEL",
|
|
color: this.theme=="dark"?"white":"dark"
|
|
}
|
|
}).then(password => {
|
|
//this.spinner = true
|
|
this.$gateway.send("wallet", "get_private_keys", {password})
|
|
}).catch(() => {
|
|
})
|
|
},
|
|
closePrivateKeys () {
|
|
this.private_keys_modal_show = false
|
|
setTimeout(() => {
|
|
this.$store.commit("gateway/set_wallet_data", {
|
|
secret: {
|
|
mnemonic: "",
|
|
spend_key: "",
|
|
view_key: ""
|
|
}
|
|
})
|
|
}, 500)
|
|
},
|
|
rescanWallet () {
|
|
this.rescan_modal_show = false
|
|
if(this.rescan_type == "full") {
|
|
this.$gateway.send("wallet", "rescan_blockchain")
|
|
} else {
|
|
this.$gateway.send("wallet", "rescan_spent")
|
|
}
|
|
},
|
|
selectKeyImageExportPath () {
|
|
this.$refs.keyImageExportSelect.click()
|
|
},
|
|
setKeyImageExportPath (file) {
|
|
this.key_image_export_path = file.target.files[0].path
|
|
},
|
|
selectKeyImageImportPath () {
|
|
this.$refs.keyImageImportSelect.click()
|
|
},
|
|
setKeyImageImportPath (file) {
|
|
this.key_image_import_path = file.target.files[0].path
|
|
},
|
|
doKeyImages () {
|
|
this.key_image_modal_show = false
|
|
|
|
this.$q.dialog({
|
|
title: this.key_image_import_export + " key images",
|
|
message: "Enter wallet password to continue.",
|
|
prompt: {
|
|
model: "",
|
|
type: "password"
|
|
},
|
|
ok: {
|
|
label: this.key_image_import_export
|
|
},
|
|
cancel: {
|
|
flat: true,
|
|
label: "CANCEL",
|
|
color: this.theme=="dark"?"white":"dark"
|
|
}
|
|
}).then(password => {
|
|
if(this.key_image_import_export == "Export")
|
|
this.$gateway.send("wallet", "export_key_images", {password: password, path: this.key_image_export_path})
|
|
else if(this.key_image_import_export == "Import")
|
|
this.$gateway.send("wallet", "import_key_images", {password: password, path: this.key_image_import_path})
|
|
}).catch(() => {
|
|
})
|
|
|
|
}
|
|
},
|
|
components: {
|
|
FormatRyo,
|
|
AddressHeader,
|
|
TxList
|
|
},
|
|
}
|
|
</script>
|
|
|
|
<style lang="scss">
|
|
.layout-padding {
|
|
padding: 15px 16px !important;
|
|
}
|
|
</style>
|