🚀 Flutter 富文本与按钮点击事件实践教程

在日常的 Flutter UI 开发中,我们经常会遇到需要展示多样式文本的场景,比如"部分文字高亮"、"点击某段文字触发操作"等。这篇文章将通过一个完整的示例,带你一步步了解如何在 Flutter 中使用 RichText 展示富文本,并结合各种按钮组件实现交互功能。demo地址


一、富文本 RichText 基础用法

Flutter 提供了 RichText 和 TextSpan 来支持多样式文本渲染。与普通 Text 不同,RichText 可以让你为一段文字中的不同部分设置不同的样式,甚至加入点击事件。

dart 复制代码
RichText(
  text: TextSpan(
    text: 'Hello ',
    style: TextStyle(color: Colors.black, fontSize: 20),
    children: <TextSpan>[
      TextSpan(
        text: 'Flutter ',
        style: TextStyle(
            color: Colors.blue,
            fontWeight: FontWeight.bold,
            fontSize: 22),
        recognizer: _tapRecognizer, // 添加点击事件
      ),
      TextSpan(
        text: 'World!',
        style: TextStyle(
            color: Colors.red, fontStyle: FontStyle.italic),
      ),
    ],
  ),
),

二、为富文本添加点击事件

我们可以使用 TapGestureRecognizer 来为 TextSpan 添加点击事件:

dart 复制代码
late TapGestureRecognizer _tapRecognizer;

@override
void initState() {
  super.initState();
  _tapRecognizer = TapGestureRecognizer()
    ..onTap = () {
      showDialog(
        context: context,
        builder: (context) => AlertDialog(
          title: Text("提示"),
          content: Text("你点击了 Flutter"),
          actions: [
            TextButton(
              onPressed: () => Navigator.pop(context),
              child: Text("确定"),
            ),
          ],
        ),
      );
    };
}

@override
void dispose() {
  _tapRecognizer.dispose(); // 释放资源,防止内存泄漏
  super.dispose();
}

三、按钮组件演示

Flutter 提供了多种按钮控件,这里我们展示了常见的四种,并实现了点击后更新文字:

  • ElevatedButton
  • TextButton
  • OutlinedButton
  • IconButton
dart 复制代码
ElevatedButton(
  onPressed: () => _handleButtonClick("ElevatedButton"),
  child: Text("ElevatedButton"),
),

TextButton(
  onPressed: () => _handleButtonClick("TextButton"),
  child: Text("TextButton"),
),

OutlinedButton(
  onPressed: () => _handleButtonClick("OutlinedButton"),
  child: Text("OutlinedButton"),
),

IconButton(
  onPressed: () => _handleButtonClick("IconButton"),
  icon: Icon(Icons.favorite, color: Colors.pink),
)

四、完整示例代码(可直接运行)

dart 复制代码
import 'package:flutter/material.dart';
import 'package:flutter/gestures.dart';

class ComponentDemoPage extends StatefulWidget {
  @override
  State<StatefulWidget> createState() => _ComponentDemoPageState();
}

class _ComponentDemoPageState extends State<ComponentDemoPage> {
  String _message = "你还没有点击按钮";
  late TapGestureRecognizer _tapRecognizer;

  TextStyle blackStyle = TextStyle(fontWeight: FontWeight.normal, fontSize: 20, color: Colors.black);
  TextStyle redStyle = TextStyle(fontWeight: FontWeight.bold, fontSize: 20, color: Colors.red);

  @override
  void initState() {
    super.initState();
    _tapRecognizer = TapGestureRecognizer()
      ..onTap = () {
        showDialog(
          context: context,
          builder: (context) => AlertDialog(
            title: Text("提示"),
            content: Text("你点击了 Flutter"),
            actions: [
              TextButton(
                onPressed: () => Navigator.pop(context),
                child: Text("确定"),
              ),
            ],
          ),
        );
      };
  }

  @override
  void dispose() {
    _tapRecognizer.dispose();
    super.dispose();
  }

  void _handleButtonClick(String label) {
    setState(() {
      _message = "你点击了:$label";
    });
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(title: Text("富文本 & 按钮示例")),
      body: Padding(
        padding: const EdgeInsets.all(16.0),
        child: Column(
          crossAxisAlignment: CrossAxisAlignment.start,
          children: [
            RichText(
              text: TextSpan(
                text: 'Hello ',
                style: TextStyle(color: Colors.black, fontSize: 20),
                children: <TextSpan>[
                  TextSpan(
                    text: 'Flutter ',
                    style: TextStyle(
                        color: Colors.blue,
                        fontWeight: FontWeight.bold,
                        fontSize: 22),
                    recognizer: _tapRecognizer,
                  ),
                  TextSpan(
                    text: 'World!',
                    style: TextStyle(
                        color: Colors.red, fontStyle: FontStyle.italic),
                  ),
                ],
              ),
            ),
            SizedBox(height: 20),

            Text.rich(
              TextSpan(
                children: [
                  TextSpan(text:'文本是视图系统中常见的控件,它用来显示一段特定样式的字符串,类似', style: redStyle),
                  TextSpan(text:'iOS', style: blackStyle),
                  TextSpan(text:'中的', style: redStyle),
                  TextSpan(text:'UILabel', style: blackStyle),
                ],
              ),
              textAlign: TextAlign.center,
            ),

            SizedBox(height: 30),

            ElevatedButton(
              onPressed: () => _handleButtonClick("ElevatedButton"),
              child: Text("ElevatedButton"),
            ),
            TextButton(
              onPressed: () => _handleButtonClick("TextButton"),
              child: Text("TextButton"),
            ),
            OutlinedButton(
              onPressed: () => _handleButtonClick("OutlinedButton"),
              child: Text("OutlinedButton"),
            ),
            IconButton(
              onPressed: () => _handleButtonClick("IconButton"),
              icon: Icon(Icons.favorite, color: Colors.pink),
            ),
            SizedBox(height: 20),

            Text(
              _message,
              style: TextStyle(fontSize: 16, color: Colors.green),
            ),
          ],
        ),
      ),
    );
  }
}

五、总结

这篇教程向您展示了:

  • 如何在 Flutter 中使用 RichText 和 TextSpan 渲染富文本;
  • 如何使用 TapGestureRecognizer 给文字添加点击事件;
  • 常见按钮组件的使用方法;
  • 如何通过 setState 更新状态和 UI。
相关推荐
JosieBook43 分钟前
【web应用】如何进行前后端调试Debug? + 前端JavaScript调试Debug?
前端·chrome·debug
LBJ辉44 分钟前
2. Webpack 高级配置
前端·javascript·webpack
灵感__idea7 小时前
JavaScript高级程序设计(第5版):好的编程就是掌控感
前端·javascript·程序员
烛阴8 小时前
Mix
前端·webgl
代码续发9 小时前
前端组件梳理
前端
试图让你心动9 小时前
原生input添加删除图标类似vue里面移入显示删除[jquery]
前端·vue.js·jquery
陈不知代码10 小时前
uniapp创建vue3+ts+pinia+sass项目
前端·uni-app·sass
小王码农记10 小时前
sass中@mixin与 @include
前端·sass
陈琦鹏10 小时前
轻松管理 WebSocket 连接!easy-websocket-client
前端·vue.js·websocket
hui函数10 小时前
掌握JavaScript函数封装与作用域
前端·javascript