#flutter #flutter-layout #gesturedetector #animatedcontainer
#flutter #flutter-layout #gesturedetector #animatedcontainer
Вопрос:
Я пытаюсь выделить цвет GestureDetector при его нажатии, я хочу, чтобы был изменен только цвет контейнера, но мой GestureDetector создается из массива, поэтому, когда я меняю его, все меняется.
Как мне достичь своей цели? тексты в массивах не являются фиксированными и будут увеличиваться или уменьшаться.
примерный пример gif с текущим кодом
import 'package:flutter/material.dart';
void main() {
runApp(MyApp());
}
class MyApp extends StatelessWidget {
@override
Widget build(BuildContext context) {
return MaterialApp(
debugShowCheckedModeBanner: false,
home: MyFloat(),
);
}
}
class MyFloat extends StatefulWidget {
@override
_MyFloatState createState() => _MyFloatState();
}
class _MyFloatState extends State<MyFloat> {
List<BoxShadow> shadow = customShadow;
Color color = Colors.green;
@override
Widget build(BuildContext context) {
return Scaffold(
backgroundColor: primaryColor,
body: SafeArea(
child: Column(
children: [
Wrap(
children: [
...(["hello", "hi", "hey"]
.map(
(val) => GestureDetector(
onTap: () {
setState(() {
this.color == Colors.green
? this.color = Colors.cyan
: this.color = Colors.green;
});
},
child: AnimatedContainer(
duration: Duration(milliseconds: 250),
height: 100,
width: 100,
decoration: BoxDecoration(
borderRadius: BorderRadius.circular(20),
color: this.color == Colors.green
? Colors.cyan
: Colors.green,
),
child: Center(
child: Text(val),
),
),
),
)
.toList())
],
)
],
),
),
);
}
}
Ответ №1:
Вот конечный результат :
Map<String,Color> stringColorMap = { /// Map which maps the text string to its corresponding color
"hello" : Colors.green,
"hi" : Colors.green,
"hey" : Colors.green,
};
class MyFloat extends StatefulWidget {
@override
_MyFloatState createState() => _MyFloatState();
}
class _MyFloatState extends State<MyFloat> {
Color color = Colors.green;
@override
Widget build(BuildContext context) {
return Scaffold(
backgroundColor: Colors.white,
body: SafeArea(
child: Column(
children: [
Wrap(
children: [
...(["hello", "hi", "hey"]
.map(
(val){print("Val : $val"); return GestureDetector(
onTap: () {
setState(() {
/* this.color == Colors.green
? this.color = Colors.cyan
: this.color = Colors.green; */
if(stringColorMap[val] == Colors.green)
stringColorMap[val] = Colors.cyan;
else
stringColorMap[val] = Colors.green;
});
},
child: AnimatedContainer(
duration: Duration(milliseconds: 250),
height: 100,
width: 100,
decoration: BoxDecoration(
borderRadius: BorderRadius.circular(20),
color: stringColorMap[val],
),
child: Center(
child: Text(val),
),
),
);}
)
.toList())
],
)
],
),
),
);
}
}
Изменения сделаны:
- Что я сделал, так это добавил карту, которая сопоставляет текстовую строку с соответствующим цветом. (stringColorMap)
- Затем переходим к функции onTap виджета, как вы можете видеть, когда пользователь нажимает на кнопку, он проверяет текущий цвет текста и соответствующим образом меняет цвет.
- Затем я использовал цвет соответствующего текста в качестве цвета нашего виджета.
Комментарии:
1. да, это хороший подход, извиняюсь за то, что не прояснил мою проблему, тексты в массивах не фиксированы и будут увеличиваться или уменьшаться. в таком случае есть какие-либо предложения?
2. Вы можете соответствующим образом изменить значения в вашей карте. Тогда вместо использования жестко запрограммированного списка строк ([«привет», «привет»,»привет»]) в дочернем параметре Wrap, вы можете использовать значения, присутствующие в самой карте. Тогда список в вашем пользовательском интерфейсе изменится в соответствии с изменениями, внесенными в карту. Создайте функцию, в которой вы будете обновлять stringColorMap и вызывать setState .