Flutter浮动动作按钮错误! 试图创建一排具有响应触摸效果的按钮。

问题描述 投票:1回答:1

我的代码:

bool _isClicked = false;

@override
  Widget build(BuildContext context) {
    return Scaffold(
    body: Padding(
      padding: EdgeInsets.symmetric(horizontal: 3.0),
      child: Container(
        decoration: BoxDecoration(
          color: _isClicked ? Colors.orange[300] : Colors.white,
          borderRadius: BorderRadius.circular(30.0),
        ),
        child: FlatButton(
          splashColor: Colors.orange[300],
          shape: RoundedRectangleBorder(
            borderRadius: BorderRadius.circular(30.0),
          ),
          onPressed: () {
            setState(() {
              _isClicked = !_isClicked;
            });
          },
          child: Padding(
            padding: EdgeInsets.symmetric(
              horizontal: 20.0,
            ),
            child: Text(
              foodItem,
              style: TextStyle(
                fontSize: 20.0,
                color: _isClicked ? Colors.white : Colors.grey[700],
              ),
            ),
          ),
        ),
      ),
     ),
   );

现实:

one1two2

期待:

  1. 当我点击一个按钮时,只有那个按钮变成了橙色,其余的都是白色的。
  2. 当我再次点击它时,它又和其他按钮一样变成了灰色。
flutter flutter-layout flutter-animation flutter-web flutter-test
1个回答
1
投票

我相信你是想实现按钮的某种切换行为。虽然 ToggleBar 小组件是很好的,但它对子小组件的期望不灵活。所以一个 ButtonBar 小部件如果能有一些关于被点击的按钮的内部状态会很有帮助。这里有一个可行的解决方案,可能会帮助你。同样的代码可以作为一个代码本使用 此处.

办法

  1. 将您的按钮代码提取到一个叫做 TButton 参数如下
    • isClicked - 表示按钮是否被点击的布尔标志。
    • foodItem - 按钮上显示的文本。
    • onPressed - 当按钮被按下时要调用的回调函数。
  2. 在父部件中 MyButtons 囊括 bool 表示每个按钮的点击状态。
  3. MyButtons 接受一个 foodItems. 迭代这个列表,并生成一个由 TButton 小部件,并将其传递给 ButtonBar 作为儿童。
import 'package:flutter/material.dart';

void main() => runApp(MyApp());

final Color darkBlue = Color.fromARGB(255, 18, 32, 47);

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      title: 'Flutter Demo',
      debugShowCheckedModeBanner: false,
      theme: ThemeData(
          primarySwatch: Colors.blue, scaffoldBackgroundColor: darkBlue),
      home: Scaffold(
        body: MyButtons(foodItems: ['Pizza', 'Burger', 'Kebab']),
      ),
    );
  }
}

class MyButtons extends StatefulWidget {
  MyButtons({Key key, this.foodItems}) : super(key: key);

  final List<String> foodItems;

  @override
  _MyButtonsState createState() => _MyButtonsState();
}

class _MyButtonsState extends State<MyButtons> {
  List<bool> isSelected;

  @override
  initState() {
    super.initState();
    // initialize the selected buttons
    isSelected = List<bool>.generate(widget.foodItems.length, (index) => false);
  }

  @override
  Widget build(BuildContext context) {
    return Padding(
      // just for aesthetics
      padding: const EdgeInsets.only(top: 80.0),
      child: ButtonBar(        
        // use the alignment to positon the buttons in the screen horizontally
        alignment: MainAxisAlignment.center,
        // iterate over the foodItems and generate the buttons.
        children: widget.foodItems.asMap().entries.map((entry) {
          return TButton(
              isClicked: isSelected[entry.key],
              foodItem: entry.value,
              onPressed: () {
                setState(() {
                  isSelected[entry.key] = !isSelected[entry.key];
                });
              });
        }).toList(),
      ),
    );
  }
}

class TButton extends StatelessWidget {
  final bool isClicked;
  final String foodItem;
  /// OnPressed is passed from the parent. This can be changed to handle it using any state management.
  final Function onPressed;

  TButton(
      {@required this.isClicked,
      @required this.foodItem,
      @required this.onPressed});

  @override
  Widget build(BuildContext context) {
    return Container(
      decoration: BoxDecoration(
        color: isClicked ? Colors.orange[300] : Colors.white,
        borderRadius: BorderRadius.circular(30.0),
      ),
      child: FlatButton(
        splashColor: Colors.orange[300],
        shape: RoundedRectangleBorder(
          borderRadius: BorderRadius.circular(30.0),
        ),
        onPressed: onPressed,
        child: Padding(
          padding: EdgeInsets.symmetric(
            horizontal: 20.0,
          ),
          child: Text(
            foodItem,
            style: TextStyle(
              fontSize: 20.0,
              color: isClicked ? Colors.white : Colors.grey[700],
            ),
          ),
        ),
      ),
    );
  }
}

© www.soinside.com 2019 - 2024. All rights reserved.