TornadoFx实现侧边栏菜单效果

博客 动态
0 188
羽尘
羽尘 2022-05-29 16:59:51
悬赏:0 积分 收藏

TornadoFx实现侧边栏菜单效果

原文地址:TornadoFx实现侧边栏菜单效果 - Stars-One的杂货小窝

之前年前研究的东西,给蓝奏批量下载器重构了页面,实现了侧边栏菜单的效果,稍微总结下把

效果

实现

首先,要说明的是,总体布局为一个Hbox,侧边栏在左边,是一个vbox,右侧则是各菜单对应的布局,使用StackPane布局

原理是,点击左侧vbox中的菜单项,更改右侧的布局(显示对应菜单项的布局)

侧边栏切换效果

//定义个侧边菜单的数据类data class LeftMenuItem(val title: String)class TestView : View("Hello TornadoFX") {    val model by inject<MainViewModel>()    override val root = vbox() {        prefWidth = 400.0        prefHeight = 200.0                hbox {            vbox {                val list = listOf(LeftMenuItem("首页"), LeftMenuItem("下载列表"), LeftMenuItem("资源搜索"))                list.forEachIndexed { index, leftMenuItem ->                    button(leftMenuItem.title) {                        action {                            //点击按钮更改选中的下标数值                            model.selectIndex.set(index)                        }                    }                }            }            stackpane {                //显示当前选中拿到下标数值                label(model.selectIndex.asString()){                    prefWidth(120.0)                }            }        }    }}class MainViewModel : ViewModel() {    //当前选中的菜单项下标    val selectIndex = SimpleIntegerProperty(0)}

效果如下图所示:

当然,这里右侧布局只是个简单的text,我们在修改下,让右侧布局根据当前所选的下标值更改显示即可

val list = listOf(LeftMenuItem("首页"), LeftMenuItem("下载列表"), LeftMenuItem("资源搜索"))hbox {    vbox {        list.forEachIndexed { index, leftMenuItem ->            button(leftMenuItem.title) {                action {                    model.selectIndex.set(index)                }            }        }    }    stackpane {        list.forEachIndexed { index, leftMenuItem ->            //这里以label演示,可以更改为布局或者是View类型            label(model.selectIndex.asString()) {                prefWidth(120.0)                visibleWhen {                    model.selectIndex.eq(index)                }            }        }    }}

效果如下所示:

关于使用View

这里的View,指的是TornadoFx中的View

我们不同页面都是写在View中,所以按照上面的代码,还需要调整下

首先,LeftMenuItem类中新增个对象,用来存储对应的View

data class LeftMenuItem(val title: String,val view:View)

右侧布局要这样写:

//右侧布局stackpane {    //text(homeModel.selectIndex.asString())    list.forEachIndexed { index, leftMenuItem ->        val leftView = leftMenuItem.view        leftView.root.visibleWhen {            homeModel.selectIndex.eq(index)        }        this += leftMenuItem.view    }}

上面省略了构造LeftMenuItem的初始化list的相关代码,相信各位知道该如何新建LeftMenuItem对象(View对象可以直接调用无参构造方法)

侧边栏美化

接下来就是侧边栏的美化工作,这样直接贴出样式的代码吧,关于css的使用,可以看下上一篇TornadoFx中的css美化

package site.starsone.xtool.appimport javafx.scene.layout.BorderStrokeStyleimport javafx.scene.paint.CycleMethodimport javafx.scene.paint.LinearGradientimport javafx.scene.paint.Stopimport javafx.scene.text.FontWeightimport tornadofx.*class Styles : Stylesheet() {    companion object {        val leftMenu by cssclass()        val leftMenuSelect by cssclass()    }    init {        leftMenu {            prefWidth = 200.px            startMargin = 10.px            fontSize = 14.px            padding = box(15.px)            backgroundColor += c("white")            and(hover) {                textFill = c("#1890ff")            }        }        leftMenuSelect{            prefWidth = 200.px            startMargin = 10.px            fontSize = 14.px            padding = box(15.px)            backgroundColor +=c("#e6f7ff")            textFill = c("#1890ff")            borderColor += box(null,c("#1890ff"),null,null)            borderWidth += box(0.px,2.px,0.px,0.px)            borderStyle += BorderStrokeStyle.SOLID        }    }}

View中使用样式:

class TestView : View("Hello TornadoFX") {    val model by inject<MainViewModel>()    override val root = vbox() {        prefWidth = 400.0        prefHeight = 200.0        //单独运行View的话,记得导入样式的操作        importStylesheet(Styles::class)        val list = listOf(LeftMenuItem("首页"), LeftMenuItem("下载列表"), LeftMenuItem("资源搜索"))        hbox {            vbox {                list.forEachIndexed { index, leftMenuItem ->                    button(leftMenuItem.title) {                        //给button添加样式                        addClass(Styles.leftMenu)                        //根据当前是否已选(下标是否一致)来切换button样式                        toggleClass(Styles.leftMenuSelect, model.selectIndex.eq(index))                                                                        action {                            model.selectIndex.set(index)                        }                    }                }            }            stackpane {                list.forEachIndexed { index, leftMenuItem ->                    //这里以label演示,可以更改为布局或者是View类型                    label("这是"+leftMenuItem.title) {                        prefWidth(120.0)                        visibleWhen {                           model.selectIndex.eq(index)                        }                    }                }            }        }    }}

效果如下图所示:

参考

  • Type Safe CSS · TornadoFX Guide
  • TornadoFx中的css美化 - Stars-One的杂货小窝
posted @ 2022-05-29 16:49 Stars-one 阅读(0) 评论(0) 编辑 收藏 举报
回帖
    羽尘

    羽尘 (王者 段位)

    2335 积分 (2)粉丝 (11)源码

     

    温馨提示

    亦奇源码

    最新会员