0
点赞
收藏
分享

微信扫一扫

Rust语言入门教程(五) - 流控制语句

zhoulujun 2023-11-26 阅读 57

注:此文适合于对rust有一些了解的朋友

iced是一个跨平台的GUI库,用于为rust语言程序构建UI界面。
在这里插入图片描述  
iced的基本逻辑是:
UI交互产生消息message,message传递给后台的update,在这个函数中编写逻辑,然后通过View函数更新UI。

下面我们将通过举例来说明iced如何显示一个窗口,以及如何在窗口上显示中文。

一、如何用iced构建窗口:

我们构建一个基本窗口,窗口有一个按钮,一个文本框,一个标签,在文本框输入字符,点击按钮后,标签上显示相同内容。
UI实例预览:
在这里插入图片描述
在这里插入图片描述
1 导入库

use iced::widget::{button, column, text, text_input};    
use iced::{Alignment, Element, Sandbox, Settings};

2、配置Cargo.toml

[dependencies]   
iced="0.10"

这样,使用cargo check时,会自动安装iced库。

3、构建窗口程序

主函数:

pub fn main() -> iced::Result {     

    Counter::run(Settings::default())             //此处为使用默认窗口设置
  
}

定义数据结构:

//创建结构体struct
struct Counter{
    value: String,
    value2:String,
}

定义消息:

#[derive(Debug, Clone)]           //为下方的enum添加特性trait
enum Message {
    Showtext,
    InputChanged(String),
}

实现一个实例:

//sandbox是一个trait
impl Sandbox for Counter {             //impl将sandbox添加给Counter,使Counter具有了sandbox的一些特性
    type Message = Message;     
    fn new() -> Self {                  //初始化sandbox,返回初始值
        Self { 
            value: String::new(),
            value2:String::new(),
        }
    }

    fn title(&self) -> String {         //返回sandbox的标题
        String::from("iced_UI")
    }

    fn update(&mut self, message: Message) {        //此处书写更新逻辑程序,所有UI交互会在这里处理
       
        match message {
            Message::Showtext=> { 
                let ss=&self.value;  
                self.value2=ss.to_string(); 
                    
            }
            Message::InputChanged(value) =>{
                self.value=value;
            }
                
        }
    }

    fn view(&self) -> Element<Message> {            
  
        column![
            
            text_input("enter some string",&self.value)
            .on_input(Message::InputChanged)
            .padding(10)
            .size(16),
            button("push")
            .on_press(Message::Showtext)
            .padding(2)
            .width(40),  
            text(format!("enter text:{}",&self.value2)).size(16), 
                                             
        ]
        .spacing(10)
        .padding(6)
        .align_items(Alignment::Center)
        .into()
      
    }


}

完整代码:

use iced::widget::{button, column, text, text_input}; 
use iced::{Alignment, Element, Sandbox, Settings};


pub fn main() -> iced::Result {

    Counter::run(Settings::default())             //此处为使用默认窗口设置
  
}

//创建结构体struct
struct Counter{
    value: String,
    value2:String,
}

#[derive(Debug, Clone)]           //为下方的enum添加特性trait
enum Message {
    Showtext,
    InputChanged(String),
}



//sandbox是一个trait
impl Sandbox for Counter {             //impl将sandbox添加给Counter,使Counter具有了sandbox的一些特性
    type Message = Message;
    fn new() -> Self {                  //初始化sandbox,返回初始值
        Self { 
            value: String::new(),
            value2:String::new(),
        }
    }

    fn title(&self) -> String {         //返回sandbox的标题
        String::from("iced_UI")
    }

    fn update(&mut self, message: Message) {        //此处书写更新逻辑程序,所有UI交互会在这里处理
       
        match message {
            Message::Showtext=> { 
                let ss=&self.value;  
                self.value2=ss.to_string(); 
                    
            }
            Message::InputChanged(value) =>{
                self.value=value;
            }
                
        }
    }

    fn view(&self) -> Element<Message> {            
  
        column![
            
            text_input("enter some string",&self.value)
            .on_input(Message::InputChanged)
            .padding(10)
            .size(16),
            button("push")
            .on_press(Message::Showtext)
            .padding(2)
            .width(40),  
            text(format!("enter text:{}",&self.value2)).size(16), 
                                             
        ]
        .spacing(10)
        .padding(6)
        .align_items(Alignment::Center)
        .into()
      
    }


}

cargo run以上代码,演示如下:
在这里插入图片描述
由于涉及rust和iced两个方面的应用,在此,仅就iced的相关使用作一下说明,至于对rust的代码有疑问的,可以参考rust的官方手册。

impl Sandbox for Counter{}

这里的sandbox是iced库提供的一个简单的应用特性,它是一个trait,有update、view、run等函数功能,此处,update和view是两个有点对应的功能,当你在UI操作部件时,会产生交互消息message,update就是接受message的,你可以在update函数下,编写你的逻辑:
此例中,我的逻辑是,当在文本框输入信息时,实时文本会传给之前定义好的一个数据即value。当点击按钮时,会将文本框的数据传给另一个数据value2,然后value2是和用于显示的文本框绑定的。

  fn update(&mut self, message: Message) {        //此处书写更新逻辑程序,所有UI交互会在这里处理
       
        match message {          
            Message::Showtext=> { 
                let ss=&self.value;  
                self.value2=ss.to_string(); 
                    
            }
            Message::InputChanged(value) =>{
                self.value=value;
            }
                
        }
    }

value2通过view函数显示到UI界面。
下面的代码是其中一句,这里将text部件绑定了一个值self.value2即前面定义的value2。

 text(format!("enter text:{}",&self.value2)).size(16),   

二、如何在iced窗口显示中文:

但是上面的程序,有个小小的不足,就是窗口无法显示中文字符,比如,我将按钮的名称由push改成开始

button("开始")

再运行的话:
在这里插入图片描述
可以看到上图中按钮的名字变成了乱码,这是因为在窗口的设定时,使用了默认参数:

pub fn main() -> iced::Result {
    Counter::run(Settings::default())             //此处为使用默认窗口设置 
}

就是此处的Settings,而iced的默认窗口参数中,字体使用的是:SansSerif。因此不支持中文字符,所以,如果想要在UI界面用中文来表示各个部件的名称或注释,需要更改字体。

所以,此处我们对上面的程序进行修改,以便窗口可以显示中文,其实就是修改字体的设置。

首先需要添加导入:

use iced::Font;
use iced::font::Family;

然后,修改主函数中的run函数的Settings:

pub fn main() -> iced::Result {       
    //Counter::run(Settings::default())             //此处为使用默认窗口设置 
    let ff="Microsoft YaHei";     //设置自定义字体
    Counter::run(Settings {
        default_font:Font{                      //设置自定义字体,用于显示中文字符
            family:Family::Name(ff),
            ..Font::DEFAULT},
        ..Settings::default()
    })
}

和之前的主函数对一下,可以发现,这里我先定义了一个字符串,用来表示字体的名字,此处是微软雅黑字体。
然后在Settings中,将关于字体的default_font单独设置。
设置好后,我们再来cargo run一下:
在这里插入图片描述
可以看到,中文字符能正常显示了。
对上面的主函数,我们再做一下修改,使窗口启动时的尺寸按照我们想要的来,即自定义窗口尺寸:

先添加导入

use iced::window;

然后主函数:

pub fn main() -> iced::Result {    
    //Counter::run(Settings::default())             //此处为使用默认窗口设置 
    let ff="Microsoft YaHei";     //设置自定义字体
    Counter::run(Settings {
        window:window::Settings{                //设置自定义窗口尺寸
            size:(600,400),
            ..window::Settings::default()
        },
        default_font:Font{                      //设置自定义字体,用于显示中文字符
            family:Family::Name(ff),
            ..Font::DEFAULT},
        ..Settings::default()
    })
}

这样一来,窗口启动时不会按照默认的来,而是按照自己设定来显示。

举报

相关推荐

0 条评论