Dark mode GUI

This commit is contained in:
Ben Carman 2020-04-07 16:06:55 -05:00
parent d25e8eb8fb
commit 70d29050f8
5 changed files with 102 additions and 8 deletions

View file

@ -0,0 +1,34 @@
.root {
-fx-accent: #1e74c6;
-fx-focus-color: -fx-accent;
-fx-base: #373e43;
-fx-control-inner-background: derive(-fx-base, 35%);
-fx-control-inner-background-alt: -fx-control-inner-background ;
}
.label{
-fx-text-fill: lightgray;
}
.text-field {
-fx-prompt-text-fill: gray;
}
.titulo{
-fx-font-weight: bold;
-fx-font-size: 18px;
}
.button{
-fx-focus-traversable: false;
}
.button:hover{
-fx-text-fill: white;
}
.separator *.line {
-fx-background-color: #3C3C3C;
-fx-border-style: solid;
-fx-border-width: 1px;
}

View file

@ -6,4 +6,8 @@ object GlobalData {
val currentBalance: DoubleProperty = DoubleProperty(0) val currentBalance: DoubleProperty = DoubleProperty(0)
val log: StringProperty = StringProperty("") val log: StringProperty = StringProperty("")
val statusText: StringProperty = StringProperty("")
val defaultDarkTheme: Boolean = true
} }

View file

@ -11,7 +11,7 @@ import scalafx.scene.control.{Alert, Label}
* *
* Copied from [[https://github.com/scalafx/ScalaFX-Tutorials/blob/master/slick-table/src/main/scala/org/scalafx/slick_table/TaskRunner.scala]] * Copied from [[https://github.com/scalafx/ScalaFX-Tutorials/blob/master/slick-table/src/main/scala/org/scalafx/slick_table/TaskRunner.scala]]
*/ */
class TaskRunner(mainView: Node, glassPane: Node, statusLabel: Label) { class TaskRunner(mainView: Node, glassPane: Node) {
/** /**
* Run an operation on a separate thread. Return and wait for its completion, * Run an operation on a separate thread. Return and wait for its completion,
@ -35,7 +35,7 @@ class TaskRunner(mainView: Node, glassPane: Node, statusLabel: Label) {
// Indicate task in progress // Indicate task in progress
Platform.runLater { Platform.runLater {
showProgress(true) showProgress(true)
statusLabel.text = caption GlobalData.statusText.value = caption
} }
val task = new javafx.concurrent.Task[R] { val task = new javafx.concurrent.Task[R] {
@ -44,13 +44,13 @@ class TaskRunner(mainView: Node, glassPane: Node, statusLabel: Label) {
} }
override def succeeded(): Unit = { override def succeeded(): Unit = {
showProgress(false) showProgress(false)
statusLabel.text = caption + " - Done." GlobalData.statusText.value = caption + " - Done."
// Do callback, if defined // Do callback, if defined
} }
override def failed(): Unit = { override def failed(): Unit = {
showProgress(false) showProgress(false)
statusLabel.text = caption + " - Failed." GlobalData.statusText.value = caption + " - Failed."
val t = Option(getException) val t = Option(getException)
t.foreach(_.printStackTrace()) t.foreach(_.printStackTrace())
// Show error message // Show error message
@ -65,7 +65,7 @@ class TaskRunner(mainView: Node, glassPane: Node, statusLabel: Label) {
} }
override def cancelled(): Unit = { override def cancelled(): Unit = {
showProgress(false) showProgress(false)
statusLabel.text = caption + " - Cancelled." GlobalData.statusText.value = caption + " - Cancelled."
} }
} }

View file

@ -1,11 +1,13 @@
package org.bitcoins.gui package org.bitcoins.gui
import javafx.event.{ActionEvent, EventHandler} import javafx.event.{ActionEvent, EventHandler}
import org.bitcoins.gui.settings.SettingsPane
import scalafx.application.{JFXApp, Platform} import scalafx.application.{JFXApp, Platform}
import scalafx.beans.property.StringProperty import scalafx.beans.property.StringProperty
import scalafx.geometry.{Insets, Pos} import scalafx.geometry.{Insets, Pos}
import scalafx.scene.Scene import scalafx.scene.Scene
import scalafx.scene.control.Alert.AlertType import scalafx.scene.control.Alert.AlertType
import scalafx.scene.control.TabPane.TabClosingPolicy
import scalafx.scene.control._ import scalafx.scene.control._
import scalafx.scene.layout.{BorderPane, HBox, StackPane, VBox} import scalafx.scene.layout.{BorderPane, HBox, StackPane, VBox}
@ -51,7 +53,7 @@ object WalletGUI extends JFXApp {
private val model = new WalletGUIModel() private val model = new WalletGUIModel()
private val getNewAddressButton = new Button { private val getNewAddressButton = new Button {
text = "Get New Addreses" text = "Get New Address"
onAction = new EventHandler[ActionEvent] { onAction = new EventHandler[ActionEvent] {
override def handle(event: ActionEvent): Unit = model.onGetNewAddress() override def handle(event: ActionEvent): Unit = model.onGetNewAddress()
} }
@ -76,9 +78,28 @@ object WalletGUI extends JFXApp {
bottom = statusLabel bottom = statusLabel
} }
private val settingsPane = new SettingsPane
private val tabPane: TabPane = new TabPane {
val walletTab: Tab = new Tab {
text = "Wallet"
content = borderPane
}
val settingsTab: Tab = new Tab {
text = "Settings"
content = settingsPane.view
}
tabs = Seq(walletTab, settingsTab)
tabClosingPolicy = TabClosingPolicy.Unavailable
}
private val rootView = new StackPane { private val rootView = new StackPane {
children = Seq( children = Seq(
borderPane, tabPane,
glassPane glassPane
) )
} }
@ -88,7 +109,11 @@ object WalletGUI extends JFXApp {
scene = new Scene(rootView) scene = new Scene(rootView)
} }
private val taskRunner = new TaskRunner(resultArea, glassPane, statusLabel) if (GlobalData.defaultDarkTheme) {
stage.scene.value.getStylesheets.add("/themes/dark-theme.css")
}
private val taskRunner = new TaskRunner(resultArea, glassPane)
model.taskRunner = taskRunner model.taskRunner = taskRunner
Platform.runLater(sendButton.requestFocus()) Platform.runLater(sendButton.requestFocus())

View file

@ -0,0 +1,31 @@
package org.bitcoins.gui.settings
import javafx.event.{ActionEvent, EventHandler}
import org.bitcoins.gui.GlobalData
import org.bitcoins.gui.WalletGUI.stage
import scalafx.scene.control.CheckBox
import scalafx.scene.layout.StackPane
class SettingsPane {
private val themeCheckBox = new CheckBox {
text = "Dark Theme"
selected = GlobalData.defaultDarkTheme
onAction = new EventHandler[ActionEvent] {
override def handle(event: ActionEvent): Unit = {
if (!selected.value) {
stage.scene.value.getStylesheets.removeAll("/themes/dark-theme.css")
} else {
stage.scene.value.getStylesheets.add("/themes/dark-theme.css")
}
()
}
}
}
val view: StackPane = new StackPane {
children = Seq(
themeCheckBox
)
}
}