Merge pull request #298 from alexvandesande/UI

UI changes to Mist
This commit is contained in:
Jeffrey Wilcke 2015-02-10 17:21:29 +01:00
commit 5fe2916ee1
21 changed files with 1526 additions and 920 deletions

Binary file not shown.

After

Width:  |  Height:  |  Size: 663 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.5 KiB

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

@ -9,14 +9,19 @@ import Ethereum 1.0
import "../ext/filter.js" as Eth import "../ext/filter.js" as Eth
import "../ext/http.js" as Http import "../ext/http.js" as Http
ApplicationWindow { ApplicationWindow {
id: root id: root
//flags: Qt.FramelessWindowHint
// Use this to make the window frameless. But then you'll need to do move and resize by hand
property var ethx : Eth.ethx property var ethx : Eth.ethx
width: 1200 width: 1200
height: 820 height: 820
minimumWidth: 300 minimumHeight: 600
minimumWidth: 800
title: "Mist" title: "Mist"
@ -33,9 +38,11 @@ ApplicationWindow {
// Takes care of loading all default plugins // Takes care of loading all default plugins
Component.onCompleted: { Component.onCompleted: {
var wallet = addPlugin("./views/wallet.qml", {noAdd: true, close: false, section: "ethereum", active: true});
addPlugin("./views/miner.qml", {noAdd: true, close: false, section: "ethereum", active: true});
addPlugin("./views/catalog.qml", {noAdd: true, close: false, section: "begin"});
var wallet = addPlugin("./views/wallet.qml", {noAdd: true, close: false, section: "ethereum", active: true});
addPlugin("./views/miner.qml", {noAdd: true, close: false, section: "ethereum", active: true});
addPlugin("./views/transaction.qml", {noAdd: true, close: false, section: "legacy"}); addPlugin("./views/transaction.qml", {noAdd: true, close: false, section: "legacy"});
addPlugin("./views/whisper.qml", {noAdd: true, close: false, section: "legacy"}); addPlugin("./views/whisper.qml", {noAdd: true, close: false, section: "legacy"});
addPlugin("./views/chain.qml", {noAdd: true, close: false, section: "legacy"}); addPlugin("./views/chain.qml", {noAdd: true, close: false, section: "legacy"});
@ -44,7 +51,7 @@ ApplicationWindow {
mainSplit.setView(wallet.view, wallet.menuItem); mainSplit.setView(wallet.view, wallet.menuItem);
newBrowserTab(eth.assetPath("html/home.html")); newBrowserTab("http://ethereum-dapp-whisper-client.meteor.com/chat/amsteam");
// Command setup // Command setup
gui.sendCommand(0) gui.sendCommand(0)
@ -113,6 +120,8 @@ ApplicationWindow {
activeView(window.view, window.menuItem); activeView(window.view, window.menuItem);
} }
menuBar: MenuBar { menuBar: MenuBar {
Menu { Menu {
title: "File" title: "File"
@ -137,7 +146,7 @@ ApplicationWindow {
text: "New tab" text: "New tab"
shortcut: "Ctrl+t" shortcut: "Ctrl+t"
onTriggered: { onTriggered: {
newBrowserTab("about:blank"); newBrowserTab("http://etherian.io");
} }
} }
@ -245,6 +254,8 @@ ApplicationWindow {
statusBar: StatusBar { statusBar: StatusBar {
//height: 32 //height: 32
visible: false
id: statusBar id: statusBar
Label { Label {
//y: 6 //y: 6
@ -264,11 +275,10 @@ ApplicationWindow {
} }
Label { Label {
//y: 6
id: lastBlockLabel id: lastBlockLabel
objectName: "lastBlockLabel" objectName: "lastBlockLabel"
visible: true visible: true
text: "" text: "---"
font.pixelSize: 10 font.pixelSize: 10
anchors.right: peerGroup.left anchors.right: peerGroup.left
anchors.rightMargin: 5 anchors.rightMargin: 5
@ -323,6 +333,11 @@ ApplicationWindow {
id: mainSplit id: mainSplit
anchors.fill: parent anchors.fill: parent
resizing: false resizing: false
handleDelegate: Item {
Rectangle {
anchors.fill: parent
}
}
function setView(view, menu) { function setView(view, menu) {
for(var i = 0; i < views.length; i++) { for(var i = 0; i < views.length; i++) {
@ -359,10 +374,71 @@ ApplicationWindow {
********************/ ********************/
Rectangle { Rectangle {
id: menu id: menu
Layout.minimumWidth: 210 Layout.minimumWidth: 192
Layout.maximumWidth: 210 Layout.maximumWidth: 192
FontLoader {
id: sourceSansPro
source: "fonts/SourceSansPro-Regular.ttf"
}
FontLoader {
source: "fonts/SourceSansPro-Semibold.ttf"
}
FontLoader {
source: "fonts/SourceSansPro-Bold.ttf"
}
FontLoader {
source: "fonts/SourceSansPro-Black.ttf"
}
FontLoader {
source: "fonts/SourceSansPro-Light.ttf"
}
FontLoader {
source: "fonts/SourceSansPro-ExtraLight.ttf"
}
FontLoader {
id: simpleLineIcons
source: "fonts/Simple-Line-Icons.ttf"
}
Rectangle {
color: "steelblue"
anchors.fill: parent
MouseArea {
anchors.fill: parent
property real lastMouseX: 0
property real lastMouseY: 0
onPressed: {
lastMouseX = mouseX
lastMouseY = mouseY
}
onPositionChanged: {
root.x += (mouseX - lastMouseX)
root.y += (mouseY - lastMouseY)
}
/*onDoubleClicked: {
//!maximized ? view.set_max() : view.set_normal()}
visibility = "Minimized"
}*/
}
}
anchors.top: parent.top anchors.top: parent.top
color: "#ececec" Rectangle {
width: parent.height
height: parent.width
anchors.centerIn: parent
rotation: 90
gradient: Gradient {
GradientStop { position: 0.0; color: "#E2DEDE" }
GradientStop { position: 0.1; color: "#EBE8E8" }
GradientStop { position: 1.0; color: "#EBE8E8" }
}
}
Component { Component {
id: menuItemTemplate id: menuItemTemplate
@ -377,10 +453,20 @@ ApplicationWindow {
property alias secondaryTitle: secondary.text property alias secondaryTitle: secondary.text
function setSelection(on) { function setSelection(on) {
sel.visible = on sel.visible = on
if (this.closable == true) {
closeIcon.visible = on
}
} }
width: 206 function setAsBigButton(on) {
height: 28 newAppButton.visible = on
label.visible = !on
buttonLabel.visible = on
}
width: 192
height: 55
color: "#00000000" color: "#00000000"
anchors { anchors {
@ -388,6 +474,19 @@ ApplicationWindow {
leftMargin: 4 leftMargin: 4
} }
Rectangle {
// New App Button
id: newAppButton
visible: false
anchors.fill: parent
anchors.rightMargin: 8
border.width: 0
radius: 5
height: 55
width: 180
color: "#F3F1F3"
}
Rectangle { Rectangle {
id: sel id: sel
visible: false visible: false
@ -396,8 +495,7 @@ ApplicationWindow {
Rectangle { Rectangle {
id: r id: r
anchors.fill: parent anchors.fill: parent
border.color: "#CCCCCC" border.width: 0
border.width: 1
radius: 5 radius: 5
color: "#FFFFFFFF" color: "#FFFFFFFF"
} }
@ -409,75 +507,129 @@ ApplicationWindow {
} }
width: 10 width: 10
color: "#FFFFFFFF" color: "#FFFFFFFF"
border.width:0
Rectangle { Rectangle {
// Small line on top of selection. What's this for?
anchors { anchors {
left: parent.left left: parent.left
right: parent.right right: parent.right
top: parent.top top: parent.top
} }
height: 1 height: 1
color: "#CCCCCC" color: "#FFFFFF"
} }
Rectangle { Rectangle {
// Small line on bottom of selection. What's this for again?
anchors { anchors {
left: parent.left left: parent.left
right: parent.right right: parent.right
bottom: parent.bottom bottom: parent.bottom
} }
height: 1 height: 1
color: "#CCCCCC" color: "#FFFFFF"
} }
} }
} }
MouseArea { MouseArea {
anchors.fill: parent anchors.fill: parent
hoverEnabled: true
onClicked: { onClicked: {
activeView(view, menuItem); activeView(view, menuItem);
} }
onEntered: {
if (parent.closable == true) {
closeIcon.visible = sel.visible
}
}
onExited: {
closeIcon.visible = false
}
} }
Image { Image {
id: icon id: icon
height: 20 height: 24
width: 20 width: 24
anchors { anchors {
left: parent.left left: parent.left
verticalCenter: parent.verticalCenter verticalCenter: parent.verticalCenter
leftMargin: 3 leftMargin: 6
} }
}
Text {
id: buttonLabel
visible: false
text: "GO TO NEW APP"
font.family: sourceSansPro.name
font.weight: Font.DemiBold
anchors.horizontalCenter: parent.horizontalCenter
anchors.verticalCenter: parent.verticalCenter
color: "#AAA0A0"
}
Text {
id: label
font.family: sourceSansPro.name
font.weight: Font.DemiBold
anchors {
left: icon.right
verticalCenter: parent.verticalCenter
leftMargin: 6
// verticalCenterOffset: -10
}
x:250
color: "#665F5F"
font.pixelSize: 14
}
Text {
id: secondary
font.family: sourceSansPro.name
font.weight: Font.Light
anchors {
left: icon.right
leftMargin: 6
top: label.bottom
}
color: "#6691C2"
font.pixelSize: 12
}
Rectangle {
id: closeIcon
visible: false
width: 10
height: 10
color: "#FFFFFF"
anchors {
fill: icon
}
MouseArea { MouseArea {
anchors.fill: parent anchors.fill: parent
onClicked: { onClicked: {
menuItem.closeApp() menuItem.closeApp()
} }
} }
}
Text { Text {
id: label
font.family: simpleLineIcons.name
anchors { anchors {
left: icon.right centerIn: parent
verticalCenter: parent.verticalCenter }
leftMargin: 3 color: "#665F5F"
font.pixelSize: 18
text: "\ue082"
}
} }
color: "#0D0A01"
font.pixelSize: 12
}
Text {
id: secondary
anchors {
right: parent.right
rightMargin: 8
verticalCenter: parent.verticalCenter
}
color: "#AEADBE"
font.pixelSize: 12
}
function closeApp() { function closeApp() {
@ -509,6 +661,9 @@ ApplicationWindow {
var section; var section;
switch(options.section) { switch(options.section) {
case "begin":
section = menuBegin
break;
case "ethereum": case "ethereum":
section = menuDefault; section = menuDefault;
break; break;
@ -529,6 +684,10 @@ ApplicationWindow {
} }
comp.closable = options.close; comp.closable = options.close;
if (options.section === "begin") {
comp.setAsBigButton(true)
}
return comp return comp
} }
@ -540,16 +699,34 @@ ApplicationWindow {
anchors.right: parent.right anchors.right: parent.right
spacing: 3 spacing: 3
Text {
text: "ETHEREUM"
font.bold: true ColumnLayout {
id: menuBegin
spacing: 3
anchors { anchors {
left: parent.left left: parent.left
leftMargin: 5 right: parent.right
} }
color: "#888888"
} }
Rectangle {
height: 55
color: "transparent"
Text {
text: "ETHEREUM"
font.family: sourceSansPro.name
font.weight: Font.DemiBold
anchors {
left: parent.left
top: parent.verticalCenter
leftMargin: 16
}
color: "#AAA0A0"
}
}
ColumnLayout { ColumnLayout {
id: menuDefault id: menuDefault
spacing: 3 spacing: 3
@ -559,15 +736,20 @@ ApplicationWindow {
} }
} }
Rectangle {
height: 55
color: "transparent"
Text { Text {
text: "NET" text: "APPS"
font.bold: true font.family: sourceSansPro.name
font.weight: Font.DemiBold
anchors { anchors {
left: parent.left left: parent.left
leftMargin: 5 top: parent.verticalCenter
leftMargin: 16
}
color: "#AAA0A0"
} }
color: "#888888"
} }
ColumnLayout { ColumnLayout {
@ -579,15 +761,22 @@ ApplicationWindow {
} }
} }
Rectangle {
height: 55
color: "transparent"
Text { Text {
text: "DEBUG" text: "DEBUG"
font.bold: true font.family: sourceSansPro.name
font.weight: Font.DemiBold
anchors { anchors {
left: parent.left left: parent.left
leftMargin: 5 top: parent.verticalCenter
leftMargin: 16
} }
color: "#888888" color: "#AAA0A0"
} }
}
ColumnLayout { ColumnLayout {
id: menuLegacy id: menuLegacy

@ -56,12 +56,34 @@ Rectangle {
//uriNav.text = uri.text.replace(/(^https?\:\/\/(?:www\.)?)([a-zA-Z0-9_\-]*\.\w{2,3})(.*)/, "$1$2<span style='color:#CCC'>$3</span>"); //uriNav.text = uri.text.replace(/(^https?\:\/\/(?:www\.)?)([a-zA-Z0-9_\-]*\.\w{2,3})(.*)/, "$1$2<span style='color:#CCC'>$3</span>");
uriNav.text = uri; uriNav.text = uri;
} else { } else {
// Prevent inf loop. // Prevent inf loop.
window.cleanPath = false; window.cleanPath = false;
} }
} }
function showFullUrlBar(on){
if (on) {
//appTitle.visible = false
//appDomain.visible = false
//uriNav.visible = true
clickAnywhereOnApp.visible = true
navBar.state = "fullUrlVisible"
} else {
//appTitle.visible = true
//appDomain.visible = true
//uriNav.visible = false
clickAnywhereOnApp.visible = false
navBar.state = "titleVisible"
}
}
Component.onCompleted: { Component.onCompleted: {
} }
@ -71,75 +93,234 @@ Rectangle {
anchors.fill: parent anchors.fill: parent
state: "inspectorShown" state: "inspectorShown"
MouseArea {
id: clickAnywhereOnApp
z:15
//hoverEnabled: true
anchors.fill: parent
/*hoverEnabled: true*/
onClicked: {
showFullUrlBar(false);
}
/*Rectangle {
anchors.fill: parent
color: "#88888888"
}*/
}
RowLayout { RowLayout {
id: navBar id: navBar
height: 40 height: 74
z: 20
anchors { anchors {
left: parent.left left: parent.left
right: parent.right right: parent.right
leftMargin: 7
} }
Button { Button {
id: back id: back
onClicked: { onClicked: {
webview.goBack() webview.goBack()
} }
anchors{
left: parent.left
leftMargin: 6
}
style: ButtonStyle { style: ButtonStyle {
background: Image { background: Image {
source: "../../back.png" source: "../../backButton.png"
width: 30 width: 20
height: 30 height: 30
} }
} }
} }
TextField { Rectangle {
id: appInfoPane
height: 28
color: "#FFFFFF"
radius: 6
MouseArea {
anchors.fill: parent
z: 10
hoverEnabled: true
onEntered: {
showFullUrlBar(true);
}
}
anchors { anchors {
left: back.right left: back.right
right: toggleInspector.left right: parent.right
leftMargin: 10 leftMargin: 10
rightMargin: 10 rightMargin: 10
} }
text: webview.url;
id: uriNav
y: parent.height / 2 - this.height / 2
Keys.onReturnPressed: { Text {
webview.url = this.text; id: appTitle
} text: "LOADING"
} font.bold: true
font.capitalization: Font.AllUppercase
horizontalAlignment: Text.AlignRight
verticalAlignment: Text.AlignVCenter
Button {
id: toggleInspector
anchors { anchors {
right: parent.right left: parent.left
} right: parent.horizontalCenter
iconSource: "../../bug.png" top: parent.top
onClicked: { bottom: parent.bottom
// XXX soon rightMargin: 10
return
if(inspector.visible == true){
inspector.visible = false
}else{
inspector.visible = true
inspector.url = webview.experimental.remoteInspectorUrl
}
}
} }
color: "#928484"
} }
// Border Text {
Rectangle { id: appDomain
id: divider text: "loading domain"
font.bold: false
horizontalAlignment: Text.AlignLeft
verticalAlignment: Text.AlignVCenter
anchors {
left: parent.horizontalCenter
right: parent.right
top: parent.top
bottom: parent.bottom
leftMargin: 10
}
color: "#C0AFAF"
}
TextField {
id: uriNav
opacity: 0.0
anchors { anchors {
left: parent.left left: parent.left
right: parent.right right: parent.right
top: navBar.bottom leftMargin: 16
}
horizontalAlignment: Text.AlignHCenter
style: TextFieldStyle {
textColor: "#928484"
background: Rectangle {
border.width: 0
color: "transparent"
}
}
text: webview.url;
y: parent.height / 2 - this.height / 2
z: 20
activeFocusOnPress: true
Keys.onReturnPressed: {
webview.url = this.text;
}
/* onFocusedChanged: {
if (focused) {
//uriNav.selectAll();
}
}*/
}
z:2
}
Rectangle {
id: appInfoPaneShadow
width: 10
height: 30
color: "#BDB6B6"
radius: 6
anchors {
left: back.right
right: parent.right
leftMargin:10
rightMargin:10
top: parent.top
topMargin: 23
}
z:1
}
Rectangle {
id: navBarBackground
anchors.fill: parent
gradient: Gradient {
GradientStop { position: 0.0; color: "#F6F1F2" }
GradientStop { position: 1.0; color: "#DED5D5" }
} }
z:-1 z:-1
height: 1 }
color: "#CCCCCC"
states: [
State {
name: "fullUrlVisible"
PropertyChanges {
target: appTitle
anchors.rightMargin: -50
opacity: 0.0
}
PropertyChanges {
target: appDomain
anchors.leftMargin: -50
opacity: 0.0
}
PropertyChanges {
target: uriNav
anchors.leftMargin: 0
opacity: 1.0
}
},
State {
name: "titleVisible"
PropertyChanges {
target: appTitle
anchors.rightMargin: 10
opacity: 1.0
}
PropertyChanges {
target: appDomain
anchors.leftMargin: 10
opacity: 1.0
}
PropertyChanges {
target: uriNav
anchors.leftMargin: -50
opacity: 0.0
}
}
]
transitions: [
// This adds a transition that defaults to applying to all state changes
Transition {
// This applies a default NumberAnimation to any changes a state change makes to x or y properties
NumberAnimation {
properties: "anchors.leftMargin, anchors.rightMargin, opacity"
easing.type: Easing.InOutQuad //Easing.InOutBack
duration: 300
}
}
]
} }
WebEngineView { WebEngineView {
@ -149,16 +330,44 @@ Rectangle {
left: parent.left left: parent.left
right: parent.right right: parent.right
bottom: parent.bottom bottom: parent.bottom
top: divider.bottom top: navBar.bottom
} }
z: 10
onLoadingChanged: { onLoadingChanged: {
if (loadRequest.status == WebEngineView.LoadSucceededStatus) { if (loadRequest.status == WebEngineView.LoadSucceededStatus) {
webview.runJavaScript("document.title", function(pageTitle) { webview.runJavaScript("document.title", function(pageTitle) {
menuItem.title = pageTitle; menuItem.title = pageTitle;
}); });
//var topBarStyle
webView.runJavaScript("document.querySelector(\"meta[name='ethereum-dapp-url-bar-style']\").getAttribute(\"content\")", function(topBarStyle){
if (topBarStyle=="transparent") {
// Adjust for a transparent sidebar Dapp
navBarBackground.visible = false;
back.visible = false;
appInfoPane.anchors.leftMargin = -16;
appInfoPaneShadow.anchors.leftMargin = -16;
webview.anchors.topMargin = -74;
webview.runJavaScript("document.querySelector('body').classList.add('ethereum-dapp-url-bar-style-transparent')")
};
});
webview.runJavaScript(eth.readFile("bignumber.min.js")); webview.runJavaScript(eth.readFile("bignumber.min.js"));
webview.runJavaScript(eth.readFile("ethereum.js/dist/ethereum.js")); webview.runJavaScript(eth.readFile("ethereum.js/dist/ethereum.js"));
var cleanTitle = webview.url.toString()
var matches = cleanTitle.match(/^[a-z]*\:\/\/([^\/?#]+)(?:[\/?#]|$)/i);
var domain = matches && matches[1];
appDomain.text = domain //webview.url.replace("a", "z")
appTitle.text = webview.title
showFullUrlBar(false);
} }
} }
onJavaScriptConsoleMessage: { onJavaScriptConsoleMessage: {
@ -208,4 +417,3 @@ Rectangle {
] ]
} }
} }

@ -0,0 +1,209 @@
import QtQuick 2.0
import QtQuick.Controls 1.0;
import QtQuick.Controls.Styles 1.0
import QtQuick.Layouts 1.0;
import QtWebEngine 1.0
//import QtWebEngine.experimental 1.0
import QtQuick.Window 2.0;
Rectangle {
id: window
anchors.fill: parent
color: "#00000000"
property var title: ""
property var iconSource: ""
property var menuItem
property var hideUrl: true
property alias url: webview.url
property alias windowTitle: webview.title
property alias webView: webview
property var cleanPath: false
property var open: function(url) {
if(!window.cleanPath) {
var uri = url;
if(!/.*\:\/\/.*/.test(uri)) {
uri = "http://" + uri;
}
var reg = /(^https?\:\/\/(?:www\.)?)([a-zA-Z0-9_\-]*\.eth)(.*)/
if(reg.test(uri)) {
uri.replace(reg, function(match, pre, domain, path) {
uri = pre;
var lookup = eth.lookupDomain(domain.substring(0, domain.length - 4));
var ip = [];
for(var i = 0, l = lookup.length; i < l; i++) {
ip.push(lookup.charCodeAt(i))
}
if(ip.length != 0) {
uri += lookup;
} else {
uri += domain;
}
uri += path;
});
}
window.cleanPath = true;
webview.url = uri;
//uriNav.text = uri.text.replace(/(^https?\:\/\/(?:www\.)?)([a-zA-Z0-9_\-]*\.\w{2,3})(.*)/, "$1$2<span style='color:#CCC'>$3</span>");
uriNav.text = uri;
} else {
// Prevent inf loop.
window.cleanPath = false;
}
}
Component.onCompleted: {
}
Item {
objectName: "root"
id: root
anchors.fill: parent
state: "inspectorShown"
RowLayout {
id: navBar
height: 184
z: 20
anchors {
left: parent.left
right: parent.right
}
Rectangle {
id: appInfoPane
height: 28
color: "#efefef"
radius: 6
z:25
MouseArea {
anchors.fill: parent
z: 10
hoverEnabled: true
onEntered: {
uriNav.visible = true
appTitle.visible = false
appDomain.visible = false
}
}
anchors {
left: parent.left
right: parent.right
leftMargin: 10
rightMargin: 10
top: parent.verticalCenter
topMargin: 23
}
TextField {
id: uriNav
anchors {
left: parent.left
right: parent.right
leftMargin: 16
top: parent.verticalCenter
topMargin: -10
}
horizontalAlignment: Text.AlignHCenter
style: TextFieldStyle {
textColor: "#928484"
background: Rectangle {
border.width: 0
color: "transparent"
}
}
text: "Type the address of a new Dapp";
y: parent.height / 2 - this.height / 2
z: 30
activeFocusOnPress: true
Keys.onReturnPressed: {
newBrowserTab(this.text);
this.text = "Type the address of a new Dapp";
}
}
}
Rectangle {
id: appInfoPaneShadow
width: 10
height: 30
color: "#BDB6B6"
radius: 6
z: 15
anchors {
left: parent.left
right: parent.right
leftMargin:10
rightMargin:10
top: parent.verticalCenter
topMargin: 23
}
}
}
WebEngineView {
objectName: "webView"
id: webview
anchors.fill: parent
onLoadingChanged: {
if (loadRequest.status == WebEngineView.LoadSucceededStatus) {
webview.runJavaScript(eth.readFile("bignumber.min.js"));
webview.runJavaScript(eth.readFile("ethereum.js/dist/ethereum.js"));
}
}
onJavaScriptConsoleMessage: {
console.log(sourceID + ":" + lineNumber + ":" + JSON.stringify(message));
}
}
WebEngineView {
id: inspector
visible: false
z:10
anchors {
left: root.left
right: root.right
top: sizeGrip.bottom
bottom: root.bottom
}
}
states: [
State {
name: "inspectorShown"
PropertyChanges {
target: inspector
}
}
]
}
}