diff --git a/main.go b/main.go index 5e930901..fac29b44 100644 --- a/main.go +++ b/main.go @@ -1,13 +1,14 @@ package main import ( + "os" + + _ "github.com/fibercrypto/FiberCryptoWallet/src/coin/skycoin" _ "github.com/fibercrypto/FiberCryptoWallet/src/models" "github.com/therecipe/qt/core" "github.com/therecipe/qt/gui" "github.com/therecipe/qt/qml" - "os" - _ "github.com/fibercrypto/FiberCryptoWallet/src/models" ) diff --git a/src/coin/skycoin/main.go b/src/coin/skycoin/main.go index 88855014..df00d957 100644 --- a/src/coin/skycoin/main.go +++ b/src/coin/skycoin/main.go @@ -1,7 +1,9 @@ package skycoin import ( + skycoin "github.com/fibercrypto/FiberCryptoWallet/src/coin/skycoin/models" "github.com/fibercrypto/FiberCryptoWallet/src/core" + util "github.com/fibercrypto/FiberCryptoWallet/src/util" ) @@ -47,8 +49,24 @@ func (p *SkyFiberPlugin) GetDescription() string { } func (p *SkyFiberPlugin) LoadWalletEnvs() []core.WalletEnv { - // TODO: Load wallets at $HOME/.skycoin/wallets - return nil + + config := core.GetConfigManager() + wltSources := config.GetSources() + + wltEnvs := make([]core.WalletEnv, 0) + for _, wltS := range wltSources { + tp := wltS.GetType() + source := wltS.GetSource() + var wltEnv core.WalletEnv + if tp == core.LocalWallet { + wltEnv = &skycoin.WalletDirectory{WalletDir: source} + } else if tp == core.RemoteWallet { + wltEnv = &skycoin.WalletNode{NodeAddress: source} + } + wltEnvs = append(wltEnvs, wltEnv) + } + + return wltEnvs } func NewSkyFiberPlugin(params SkyFiberParams) core.AltcoinPlugin { diff --git a/src/coin/skycoin/models/account.go b/src/coin/skycoin/models/account.go index 99342382..14030919 100644 --- a/src/coin/skycoin/models/account.go +++ b/src/coin/skycoin/models/account.go @@ -1,4 +1,4 @@ -package models +package skycoin import ( "fmt" diff --git a/src/coin/skycoin/models/blockchain.go b/src/coin/skycoin/models/blockchain.go index 849a1d5c..c9ec50d3 100644 --- a/src/coin/skycoin/models/blockchain.go +++ b/src/coin/skycoin/models/blockchain.go @@ -1,4 +1,4 @@ -package models +package skycoin import ( "errors" diff --git a/src/coin/skycoin/models/cipher.go b/src/coin/skycoin/models/cipher.go index 5b8ad624..9dde9a61 100644 --- a/src/coin/skycoin/models/cipher.go +++ b/src/coin/skycoin/models/cipher.go @@ -1,4 +1,4 @@ -package models +package skycoin import ( "github.com/fibercrypto/FiberCryptoWallet/src/core" diff --git a/src/coin/skycoin/models/wallet.go b/src/coin/skycoin/models/wallet.go index aadf4ab4..959ac772 100644 --- a/src/coin/skycoin/models/wallet.go +++ b/src/coin/skycoin/models/wallet.go @@ -1,4 +1,4 @@ -package models +package skycoin import ( "encoding/hex" @@ -9,7 +9,6 @@ import ( "strings" "time" - "github.com/fibercrypto/FiberCryptoWallet/src/coin/skycoin" "github.com/fibercrypto/FiberCryptoWallet/src/core" "github.com/fibercrypto/FiberCryptoWallet/src/util" "github.com/skycoin/skycoin/src/api" @@ -20,8 +19,8 @@ import ( ) const ( - Sky = skycoin.SkycoinTicker - CoinHour = skycoin.CoinHoursTicker + Sky = "SKY" + CoinHour = "SKYCH" WalletTypeDeterministic = "deterministic" WalletTypeCollection = "collection" diff --git a/src/core/config.go b/src/core/config.go new file mode 100644 index 00000000..c517f9d6 --- /dev/null +++ b/src/core/config.go @@ -0,0 +1,167 @@ +package core + +import ( + "encoding/json" + "io/ioutil" + "os" + "path/filepath" + "sync" +) + +const ( + pathToConfigFromHome = ".fiber/config.json" + pathToDefaultWalletsFromHome = ".skycoin/wallets" + LocalWallet = iota + RemoteWallet +) + +var ( + confManager *ConfigManager + once sync.Once +) + +type ConfigManager struct { + sourceList []*WalletSource + node string +} + +type WalletSource struct { + sourceType int + source string +} + +func (ws *WalletSource) GetType() int { + return ws.sourceType +} +func (ws *WalletSource) GetSource() string { + return ws.source +} +func (ws *WalletSource) getWalletSourceJson() *walletSourceJson { + return &walletSourceJson{ + SourceType: ws.GetType(), + Source: ws.GetSource(), + } +} + +func (cm *ConfigManager) GetSources() []*WalletSource { + return cm.sourceList +} + +func (cm *ConfigManager) getConfigManagerJson() *configManagerJson { + wltSources := make([]*walletSourceJson, 0) + for _, wltS := range cm.sourceList { + wltSources = append(wltSources, wltS.getWalletSourceJson()) + } + return &configManagerJson{ + SourceList: wltSources, + Node: cm.node, + } +} + +type configManagerJson struct { + SourceList []*walletSourceJson `json:"SourceList"` + Node string `json:"Node"` +} + +func (cmJ *configManagerJson) getConfigManager() *ConfigManager { + wltsSource := make([]*WalletSource, 0) + for _, wltS := range cmJ.SourceList { + wltsSource = append(wltsSource, wltS.getWalletSource()) + } + + return &ConfigManager{ + node: cmJ.Node, + sourceList: wltsSource, + } +} + +type walletSourceJson struct { + SourceType int `json:"Type"` + Source string `json:"Source"` +} + +func (wsJ *walletSourceJson) getWalletSource() *WalletSource { + return &WalletSource{ + source: wsJ.Source, + sourceType: wsJ.SourceType, + } +} + +func GetConfigManager() *ConfigManager { + once.Do(func() { + var cm *ConfigManager + + if configFileExist() { + + cm = loadConfigFromFile() + } else { + + cm = getDefaultConfigManager() + + } + confManager = cm + }) + + return confManager +} + +func configFileExist() bool { + fileDir := getConfigFileDir() + if _, err := os.Stat(fileDir); err != nil { + if os.IsNotExist(err) { + return false + } + } + return true +} + +func loadConfigFromFile() *ConfigManager { + cm := new(configManagerJson) + fileDir := getConfigFileDir() + dat, err := ioutil.ReadFile(fileDir) + + if err != nil { + + return getDefaultConfigManager() + } + err = json.Unmarshal(dat, cm) + if err != nil { + + return getDefaultConfigManager() + } + + return cm.getConfigManager() + +} + +func getDefaultConfigManager() *ConfigManager { + + cm := new(ConfigManager) + + cm.node = "http://stagin.node.skycoin.net" + cm.sourceList = []*WalletSource{getDefaultWalletSource()} + + jsonFormat, _ := json.Marshal(cm.getConfigManagerJson()) + + os.MkdirAll(filepath.Dir(getConfigFileDir()), 0755) + + ioutil.WriteFile(getConfigFileDir(), jsonFormat, 0644) + + return cm + +} + +func getConfigFileDir() string { + homeDir := os.Getenv("HOME") + fileDir := filepath.Join(homeDir, pathToConfigFromHome) + return fileDir +} + +func getDefaultWalletSource() *WalletSource { + ws := new(WalletSource) + ws.sourceType = LocalWallet + walletsDir := filepath.Join(os.Getenv("HOME"), pathToDefaultWalletsFromHome) + ws.source = walletsDir + return ws + +} diff --git a/src/models/configurationManager.go b/src/models/configurationManager.go new file mode 100644 index 00000000..0b719ab9 --- /dev/null +++ b/src/models/configurationManager.go @@ -0,0 +1,41 @@ +package models + +import ( + "github.com/fibercrypto/FiberCryptoWallet/src/core" + + "github.com/therecipe/qt/qml" + + qtcore "github.com/therecipe/qt/core" +) + +type WalletSource struct { + qtcore.QObject + _ int `property:"sourceType"` + _ string `property:"source"` +} + +type ConfigManager struct { + qtcore.QObject + configManager *core.ConfigManager + _ func() `constructor:"init"` + _ func() []*WalletSource `slot:"getSources"` +} + +func (cm *ConfigManager) init() { + qml.QQmlEngine_SetObjectOwnership(cm, qml.QQmlEngine__CppOwnership) + cm.configManager = core.GetConfigManager() + cm.ConnectGetSources(cm.getSources) + +} + +func (cm *ConfigManager) getSources() []*WalletSource { + wltsSource := make([]*WalletSource, 0) + for _, wltS := range cm.configManager.GetSources() { + newWltSource := NewWalletSource(nil) + qml.QQmlEngine_SetObjectOwnership(newWltSource, qml.QQmlEngine__CppOwnership) + newWltSource.SetSourceType(wltS.GetType()) + newWltSource.SetSource(wltS.GetSource()) + wltsSource = append(wltsSource, newWltSource) + } + return wltsSource +} diff --git a/src/models/wallets.go b/src/models/wallets.go index d1b0ac63..00e898cd 100644 --- a/src/models/wallets.go +++ b/src/models/wallets.go @@ -6,4 +6,6 @@ func init() { AddressesModel_QmlRegisterType2("WalletsManager", 1, 0, "AddressModel") QAddress_QmlRegisterType2("WalletsManager", 1, 0, "QAddress") WalletManager_QmlRegisterType2("WalletsManager", 1, 0, "WalletManager") + ConfigManager_QmlRegisterType2("Config", 1, 0, "ConfigManager") + WalletSource_QmlRegisterType2("Config", 1, 0, "WalletSource") } diff --git a/src/models/walletsManager.go b/src/models/walletsManager.go index 882ce594..4c90617e 100644 --- a/src/models/walletsManager.go +++ b/src/models/walletsManager.go @@ -1,7 +1,7 @@ package models import ( - "github.com/fibercrypto/FiberCryptoWallet/src/coin/skycoin/models" + skycoin "github.com/fibercrypto/FiberCryptoWallet/src/coin/skycoin/models" "github.com/fibercrypto/FiberCryptoWallet/src/core" qtcore "github.com/therecipe/qt/core" ) @@ -33,10 +33,15 @@ func (walletM *WalletManager) init() { walletM.ConnectDecryptWallet(walletM.decryptWallet) walletM.ConnectGetWallets(walletM.getWallets) walletM.ConnectGetAddresses(walletM.getAddresses) + altManager := core.LoadAltcoinManager() + walletsEnvs := make([]core.WalletEnv, 0) + for _, plug := range altManager.ListRegisteredPlugins() { + walletsEnvs = append(walletsEnvs, plug.LoadWalletEnvs()...) + } - walletM.WalletEnv = &models.WalletDirectory{WalletDir: "/home/kid/.skycoin/wallets"} //just example + walletM.WalletEnv = walletsEnvs[0] - walletM.SeedGenerator = new(models.SeedService) + walletM.SeedGenerator = new(skycoin.SeedService) } diff --git a/src/ui/CustomMenuBar.qml b/src/ui/CustomMenuBar.qml index fc9b344f..a30582ff 100755 --- a/src/ui/CustomMenuBar.qml +++ b/src/ui/CustomMenuBar.qml @@ -15,11 +15,13 @@ RowLayout { property alias enablePendingTransactions: menuItemPendingTransactions.enabled property alias enableBlockchain: menuItemBlockchain.enabled property alias enableNetworking: menuItemNetworking.enabled + property alias enableSettings: menuItemSettings.enabled // Signals signal outputsRequested() signal pendingTransactionsRequested() signal networkingRequested() + signal settingsRequested() signal blockchainRequested() signal aboutRequested() signal aboutQtRequested() @@ -67,6 +69,7 @@ RowLayout { enablePendingTransactions = true enableBlockchain = true enableNetworking = true + enableSettings = true } } @@ -122,6 +125,13 @@ RowLayout { onClicked: networkingRequested() } + CustomMenuItem { + id: menuItemSettings + text: qsTr("&Settings") + iconSource: "qrc:/images/resources/images/icons/warning.svg" + + onClicked: settingsRequested() + } } // menuTools Menu { id: menuHelp diff --git a/src/ui/Delegates/PanelItem.qml b/src/ui/Delegates/PanelItem.qml new file mode 100644 index 00000000..d8072e5e --- /dev/null +++ b/src/ui/Delegates/PanelItem.qml @@ -0,0 +1,55 @@ +import QtQuick 2.7 +import QtQuick.Layouts 1.2 +import QtQuick.Controls.Material 2.12 + +Column { + id: root + property string title: "Accordion" + default property alias item: ld.sourceComponent + property alias itemWidth: info.width + Rectangle { + width: columnSettings.width + height: 40 + color: Material.color(Material.Blue) + MouseArea { + anchors.fill: parent + onClicked: info.show = !info.show + } + Text { + anchors.fill: parent + anchors.margins: 10 + horizontalAlignment: Text.AlignHCenter + verticalAlignment: Text.AlignVCenter + text: root.title + } + Text { + anchors{ + right: parent.right + top: parent.top + bottom: parent.bottom + margins: 10 + } + horizontalAlignment: Text.AlignRight + verticalAlignment: Text.AlignVCenter + text: "^" + rotation: info.show ? 0 : "180" + } + + } + Rectangle { + id: info + width: show ? ld.width : 0 + height: show ? ld.height : 0 + property bool show : false +// color: generalStackView.color // TODO Set proper color + clip: true + Loader { + id: ld + y: info.height - height + anchors.horizontalCenter: info.horizontalCenter + } + Behavior on height { + NumberAnimation { duration: 50; easing.type: Easing.InOutQuad } + } + } +} \ No newline at end of file diff --git a/src/ui/Delegates/SettingNetworkDelegate.qml b/src/ui/Delegates/SettingNetworkDelegate.qml new file mode 100644 index 00000000..4f7622d5 --- /dev/null +++ b/src/ui/Delegates/SettingNetworkDelegate.qml @@ -0,0 +1,84 @@ +import QtQuick 2.12 +import QtQuick.Controls 2.12 +import QtQuick.Controls.Material 2.12 +import QtQuick.Layouts 1.12 + +Item { + id: settingsListDelegate + + implicitHeight: Math.max(textOutputID.height, (toolButtonCopy.height - toolButtonCopy.topPadding*2), labelAddressSky.height, labelAddressCoins.height) + + RowLayout { + id: rowLayoutRoot + anchors.fill: parent + anchors.leftMargin: listOutputsLeftMargin * 2 + anchors.rightMargin: listOutputsRightMargin + spacing: listOutputsSpacing + + RowLayout { + id: rowLayoutOutputID + Layout.fillWidth: true + + TextInput { + id: textOutputID + Layout.fillWidth: true + text: outputID // a role of the model + readOnly: true + font.family: "Code New Roman" + wrapMode: TextInput.WrapAnywhere + } + ToolButton { + id: toolButtonCopy + icon.source: "qrc:/images/resources/images/icons/copy.svg" + Layout.alignment: Qt.AlignLeft + ToolTip.text: qsTr("Copy to clipboard") + ToolTip.visible: hovered // TODO: pressed when mobile? + ToolTip.delay: Qt.styleHints.mousePressAndHoldInterval + + Image { + id: imageCopied + anchors.centerIn: parent + source: "qrc:/images/resources/images/icons/check-simple.svg" + fillMode: Image.PreserveAspectFit + sourceSize: Qt.size(toolButtonCopy.icon.width*1.5, toolButtonCopy.icon.height*1.5) + z: 1 + + opacity: 0.0 + } + + onClicked: { + textOutputID.selectAll() + textOutputID.copy() + textOutputID.deselect() + if (copyAnimation.running) { + copyAnimation.restart() + } else { + copyAnimation.start() + } + } + + SequentialAnimation { + id: copyAnimation + NumberAnimation { target: imageCopied; property: "opacity"; to: 1.0; easing.type: Easing.OutCubic } + PauseAnimation { duration: 1000 } + NumberAnimation { target: imageCopied; property: "opacity"; to: 0.0; easing.type: Easing.OutCubic } + } + } // ToolButton + } // RowLayout (output ID) + + Label { + id: labelAddressSky + text: addressSky // a role of the model + color: Material.accent + horizontalAlignment: Text.AlignRight + Layout.preferredWidth: internalLabelsWidth/2 + } + + Label { + id: labelAddressCoins + text: addressCoinHours // a role of the model + horizontalAlignment: Text.AlignRight + Layout.preferredWidth: internalLabelsWidth + } + } // RowLayout (addresses) +} diff --git a/src/ui/Delegates/SettingsDelegate.qml b/src/ui/Delegates/SettingsDelegate.qml new file mode 100644 index 00000000..6ea5e67b --- /dev/null +++ b/src/ui/Delegates/SettingsDelegate.qml @@ -0,0 +1,59 @@ +import QtQuick 2.12 +import QtQuick.Controls 2.12 +import QtQuick.Controls.Material 2.12 +import QtQuick.Layouts 1.12 + +import "../" + +ItemDelegate { + id: root + + property string modelNodeDirection: "http://localhost:6420" + property var scrollSettingsWidth: 0 + property bool modelIsWalletEnvLocal: true + property string modelWalletPath: qsTr("$HOME/.skycoin/wallets") + Layout.fillWidth: true + Layout.fillHeight: true + + + width: parent.width + height: walletPanel.height + panelNetwork.height + + ColumnLayout { + id: columnSettings + anchors.fill: parent +// anchors.leftMargin: 20 +// anchors.rightMargin: 20 +// anchors.topMargin: 10 +// anchors.bottomMargin: 12 + spacing: 20 +// anchors.fill: parent +// spacing: 5 + PanelItem { + id: walletPanel + Layout.fillWidth: true + title: "Wallets" + item: WalletSettings { + id: walletSettings + width: root.width + isSetWalletEnvLocal: modelIsWalletEnvLocal + walletPath: modelWalletPath + } + } // PanelItem + PanelItem { + id: panelNetwork + Layout.fillWidth: true + title: "Networks" + item: NetworkSettings { + width: root.width + id: networkSettings + nodeDirection: modelNodeDirection + } + } // PanelItem + Component.onCompleted: { + root.width = scrollSettingsWidth + console.log("root -> " + root.width) + console.log("networkSettings -> " + panelNetwork.width) + } + } // ColumnLayout +} // ItemDelegate diff --git a/src/ui/Delegates/SettingsWalletDelegate.qml b/src/ui/Delegates/SettingsWalletDelegate.qml new file mode 100644 index 00000000..a18daac9 --- /dev/null +++ b/src/ui/Delegates/SettingsWalletDelegate.qml @@ -0,0 +1,75 @@ +import QtQuick 2.12 +import QtQuick.Controls 2.12 +import QtQuick.Controls.Material 2.12 +import QtQuick.Layouts 1.12 + +Item { + id: settingsDelegate + + property bool expanded: false + property bool animateDisplacement: false + + implicitHeight: itemDelegateSettingsName.height + (expanded ? listViewSettings.height : 0) + Behavior on implicitHeight { NumberAnimation { duration: animateDisplacement ? 250 : 0; easing.type: Easing.OutQuint; onRunningChanged: animateDisplacement = false } } + + clip: true + + ItemDelegate { + id: itemDelegateSettingsName + + property color textColor: expanded ? parent.Material.accent : parent.Material.foreground + Behavior on textColor { ColorAnimation {} } + + anchors.top: parent.top + anchors.left: parent.left + anchors.right: parent.right + + Material.foreground: textColor + text: name // a role of the model + font.bold: true + + onClicked: { + animateDisplacement = true + expanded = !expanded + } + } // ItemDelegate + + ListView { + id: listViewSettings + anchors.top: itemDelegateSettingsName.bottom + anchors.left: parent.left + anchors.right: parent.right + height: contentItem.height + + opacity: expanded ? 1.0 : 0.0 + Behavior on opacity { NumberAnimation { duration: expanded ? 250 : 1000; easing.type: Easing.OutQuint } } + + clip: true + interactive: false + model: modelOptions + + delegate: OutputsListAddressDelegate { + width: listViewSettings.width + } + } // ListView + + // Roles: address + // Use listModel.append( { "address": value } ) + // Or implement the model in the backend (a more recommendable approach) + ListModel { + id: modelOptions + // The first element must exist but will not be used + ListElement { + // + operationName: "Wallet Source" + walletsSource: "$HOME/.skycoin/wallets" + nodeDirection: "" + } + ListElement { + // + operationName: "Node Direction" + nodeDirection: "" + walletsSource: "" + } + } +} diff --git a/src/ui/GeneralStackView.qml b/src/ui/GeneralStackView.qml index dfecb4cc..89f45f57 100644 --- a/src/ui/GeneralStackView.qml +++ b/src/ui/GeneralStackView.qml @@ -47,6 +47,14 @@ Item { } } + function openSettingsPage() { + if (stackView.depth > 1) { + stackView.replace(componentSettings) + } else { + stackView.push(componentSettings) + } + } + function pop() { stackView.pop() } @@ -120,5 +128,13 @@ Item { } } + Component { + id: componentSettings + + Settings { + id: settings + } + } + } diff --git a/src/ui/NetworkSettings.qml b/src/ui/NetworkSettings.qml new file mode 100644 index 00000000..d4ec1525 --- /dev/null +++ b/src/ui/NetworkSettings.qml @@ -0,0 +1,22 @@ +import QtQuick 2.12 +import QtQuick.Controls 2.12 +import QtQuick.Controls.Material 2.12 +import QtQuick.Layouts 1.12 + +RowLayout { + property alias nodeDirection: nodeDirectionField.text + width: parent.width + height: 40 + Label { + font.pointSize: Qt.application.font.pointSize * 0.9 + font.bold: true + Layout.alignment: Qt.AlignCenter + text: "Node Direction:" + } + TextField { + id: nodeDirectionField + Layout.fillWidth: true + Layout.alignment: Qt.AlignCenter + placeholderText: qsTr("http://127.0.0.1:6420") + } +} \ No newline at end of file diff --git a/src/ui/Settings.qml b/src/ui/Settings.qml new file mode 100644 index 00000000..da4c3d6e --- /dev/null +++ b/src/ui/Settings.qml @@ -0,0 +1,60 @@ +import QtQuick 2.12 +import QtQuick.Controls 2.12 +import QtQuick.Controls.Material 2.12 +import QtQuick.Layouts 1.12 + +// Resource imports +// import "qrc:/ui/src/ui/Delegates" +import "Delegates/" // For quick UI development, switch back to resources when making a release +import QtQuick 2.12 +import QtQuick.Controls 2.12 +import QtQuick.Controls.Material 2.12 +import QtQuick.Layouts 1.12 + +// Resource imports +// import "qrc:/ui/src/ui/Delegates" +import "Delegates/" // For quick UI development, switch back to resources when making a release + +Page { + id: root + + + Frame { + anchors.fill: parent + anchors.margins: 20 + clip: true + + + ScrollView { + anchors.fill: parent + id: scrollSettings + ScrollBar.horizontal.policy: ScrollBar.AlwaysOff + ColumnLayout{ + id: columnSettings + anchors.fill: parent + Button { + text: "Button" + anchors.margins: 20 + } + SettingsDelegate { + id: settingsDelegate + width: scrollSettings.width + modelNodeDirection: "node" + modelIsWalletEnvLocal: true + modelWalletPath: "path" + } + Connections { + target: scrollSettings + onWidthChanged: { + columnSettings.width = scrollSettings.width + console.log("settingsDelegate.width changed => " + settingsDelegate.width) + } + } + Component.onCompleted: { + columnSettings.width = scrollSettings.width + + } + } // ColumnLayout + } // ScrollView + } // Frame +} // Page \ No newline at end of file diff --git a/src/ui/WalletSettings.qml b/src/ui/WalletSettings.qml new file mode 100644 index 00000000..b75eb5e3 --- /dev/null +++ b/src/ui/WalletSettings.qml @@ -0,0 +1,43 @@ +import QtQuick 2.12 +import QtQuick.Controls 2.12 +import QtQuick.Controls.Material 2.12 +import QtQuick.Layouts 1.12 + +ColumnLayout { + id: walletSettings + width: parent.width + property alias isSetWalletEnvLocal: walletEnvSwitch.checked + property alias walletPath: walletPathTextEdit.text + + RowLayout { + width: parent.width + height: 40 + Label { + font.pointSize: Qt.application.font.pointSize * 0.9 + font.bold: true + Layout.alignment: Qt.AlignCenter + text: "Wallet Path:" + } + TextField { + id: walletPathTextEdit + Layout.fillWidth: true + Layout.alignment: Qt.AlignCenter + placeholderText: "$HOME/.skycoin/wallets" + } + } + + RowLayout { + width: parent.width + height: 40 + Label { + font.pointSize: Qt.application.font.pointSize * 0.9 + font.bold: true + Layout.alignment: Qt.AlignCenter + text: "Wallet Enviroment (Local/Remote):" + } + Switch { + id: walletEnvSwitch + checked: false + } + } +} \ No newline at end of file diff --git a/src/ui/main.qml b/src/ui/main.qml index dafc62d3..52782005 100644 --- a/src/ui/main.qml +++ b/src/ui/main.qml @@ -27,6 +27,7 @@ ApplicationWindow { enablePendingTransactions = true enableBlockchain = true enableNetworking = true + enableSettings = true } onPendingTransactionsRequested: { @@ -38,6 +39,7 @@ ApplicationWindow { enablePendingTransactions = false enableBlockchain = true enableNetworking = true + enableSettings = true } @@ -50,6 +52,7 @@ ApplicationWindow { enablePendingTransactions = true enableBlockchain = false enableNetworking = true + enableSettings = true } onNetworkingRequested: { @@ -61,6 +64,19 @@ ApplicationWindow { enablePendingTransactions = true enableBlockchain = true enableNetworking = false + enableSettings = true + } + + onSettingsRequested: { + generalStackView.openSettingsPage() + menuBarColor = Material.color(Material.Blue) + customHeader.text = qsTr("Settings") + + enableOutputs = true + enablePendingTransactions = true + enableBlockchain = true + enableNetworking = true + enableSettings = false } onAboutRequested: {