Issue
I am making a flutter game where I have made a virtual keyboard using item builder and the keyboard contains some characters and these characters can be duplicate, when i select any character it is showed in containers above keyboard.
The problem is when I select any particular character, its duplicates are also selected but I want to treat duplicates as different. Refer image below
I think this is happening due to list.contains I used in my code, check the code below
import 'package:flutter/material.dart';
class PuzzlePage extends StatefulWidget {
int? id;
String? image1;
String? image2;
String? puzzleAnswer;
PuzzlePage(this.id, this.image1, this.image2, this.puzzleAnswer);
State<StatefulWidget> createState()
{
return _PuzzlePageState(this.id,this.image1,this.image2,this.puzzleAnswer);
}
//State<StatefulWidget> createState() {
// return _PuzzlePageState(this.id,this.image1,this.image2,this.puzzleAnswer);
}
class _PuzzlePageState extends State<PuzzlePage> {
int? id;
String? image1;
String? image2;
String? puzzleAnswer;
String? randomCharactersString="";
List selection=[];
_PuzzlePageState(this.id,this.image1,this.image2,this.puzzleAnswer);
void initState(){
super.initState();
}
@override
Widget build(BuildContext context) {
// deciding keyboard size
int? remainingLetters=26-(puzzleAnswer!.length);
int extraSize=(remainingLetters/2).ceil();
// print(extraSize);
// print(puzzleAnswer!.length);
int keyboardSize=puzzleAnswer!.length+extraSize;
if(randomCharactersString==""){
randomCharactersString = RandomString(extraSize, puzzleAnswer!);
}
String keyboardWords=randomCharactersString!+puzzleAnswer!;
// print(randomCharactersString);
print(selection);
// const answer= "cde";
//final id = ModalRoute.of(context)!.settings.arguments as Id ;
return MaterialApp(
home: Scaffold(
appBar: AppBar(
title:Text("Guess the answer"),
centerTitle: true,
automaticallyImplyLeading: true,
leading: IconButton(icon:Icon(Icons.arrow_back),
onPressed: () {
Navigator.pop(context);
},
),
),
body: Container(
color: Colors.white54,
child: Column(
children: [
SizedBox(
height: 60,
),
Row(
mainAxisAlignment: MainAxisAlignment.center,
crossAxisAlignment: CrossAxisAlignment.center,
children: [
Container(
height: 125,
width: 125,
child: Image(image: AssetImage("assets/images/$image1"))),
SizedBox(
width: 20,
),
Text("$randomCharactersString"),
Container(
height: 125,
width: 125,
child: Image(image: AssetImage("assets/images/$image2"))),
], ),
Column(
children: [
Container(
height: 250,
padding: EdgeInsets.all(10),
alignment: Alignment.center,
child: GridView.builder(gridDelegate: SliverGridDelegateWithFixedCrossAxisCount(
// childAspectRatio: 1,
crossAxisCount: 7,
crossAxisSpacing: 4,
mainAxisSpacing: 4,
),
itemCount: puzzleAnswer!.length,
shrinkWrap: true,
itemBuilder: (context , index){
print(index);
if(selection.length>index){
return InkWell(
onTap: () {
setState(() {
if (!selection.contains(keyboardWords[index])){
null;
}
else{
selection.remove(keyboardWords[index]);
}
});
},
child: Container(
padding: EdgeInsets.all(10),
alignment: Alignment.center,
decoration: BoxDecoration(
color:Colors.blue,
borderRadius: BorderRadius.circular(7)
),
child: Text(selection[index],
style: TextStyle(color: Colors.black)
),
),
);
}
else{
return Container(
padding: EdgeInsets.all(10),
alignment: Alignment.center,
decoration: BoxDecoration(
color: Colors.blue,
borderRadius: BorderRadius.circular(7)
),
child: Text("",
style: TextStyle(color: Colors.black)
),
);
}
}
)
),
],
),
Expanded(child:
Container(
// height: 300,
padding: EdgeInsets.all(10),
alignment: Alignment.center,
child: GridView.builder(gridDelegate: SliverGridDelegateWithFixedCrossAxisCount(
childAspectRatio: 1,
crossAxisCount: 7,
crossAxisSpacing: 4,
mainAxisSpacing: 4,
),
itemCount: keyboardSize,
// shrinkWrap: true,
itemBuilder: (context , index)
{
return InkWell(
onTap:(){
setState(() {
if (!selection.contains(keyboardWords[index])){
selection.add(keyboardWords[index]);
}
else{
selection.remove(keyboardWords[index]);
}
}
);
},
child: Container(
padding:EdgeInsets.all(10),
alignment:Alignment.center,
decoration:BoxDecoration(
color:selection.contains(keyboardWords[index])?Colors.blueAccent:Colors.grey,
borderRadius:BorderRadius.circular(7)
),
child:Text(keyboardWords[index],
style:TextStyle(color:Colors.black)
),
),
);
// return ElevatedButton(
// style: ElevatedButton.styleFrom(
// primary: Colors.purple,
// // padding: EdgeInsets.symmetric(horizontal: 50, vertical: 20),
// textStyle: TextStyle(
// fontSize: 20,
// fontWeight: FontWeight.bold
// ),
// ),
// onPressed: null,
// child: Text("d"),
// );
}
)
),
),
],
),
),
),
);
}
}
RandomString(int strlen,String puzzleAnswer){
Random rnd = new Random();
String result = "";
const chars = "abcdefghijklmnopqrstuvwxyz";
for (var i = 0; i < strlen; i++) {
// if (!puzzleAnswer.contains(chars[i])) {
result += chars[rnd.nextInt(chars.length)];
// }
}
return result;
}
Solution
Here is the modified file, here it does not highlight the duplicates:
import 'dart:math';
import 'package:flutter/material.dart';
class PuzzlePage extends StatefulWidget {
int? id;
String? image1;
String? image2;
String? puzzleAnswer;
PuzzlePage(this.id, this.image1, this.image2, this.puzzleAnswer);
State<StatefulWidget> createState()
{
return _PuzzlePageState(this.id,this.image1,this.image2,this.puzzleAnswer);
}
//State<StatefulWidget> createState() {
// return _PuzzlePageState(this.id,this.image1,this.image2,this.puzzleAnswer);
}
class _PuzzlePageState extends State<PuzzlePage> {
int? id;
String? image1;
String? image2;
String? puzzleAnswer;
String? randomCharactersString="";
List<int> selection=[];
_PuzzlePageState(this.id,this.image1,this.image2,this.puzzleAnswer);
void initState(){
super.initState();
}
@override
Widget build(BuildContext context) {
// deciding keyboard size
int? remainingLetters=26-(puzzleAnswer!.length);
int extraSize=(remainingLetters/2).ceil();
// print(extraSize);
// print(puzzleAnswer!.length);
int keyboardSize=puzzleAnswer!.length+extraSize;
if(randomCharactersString==""){
randomCharactersString = RandomString(extraSize, puzzleAnswer!);
}
String keyboardWords=randomCharactersString!+puzzleAnswer!;
// print(randomCharactersString);
print(selection);
// const answer= "cde";
//final id = ModalRoute.of(context)!.settings.arguments as Id ;
return MaterialApp(
home: Scaffold(
appBar: AppBar(
title:Text("Guess the answer"),
centerTitle: true,
automaticallyImplyLeading: true,
leading: IconButton(icon:Icon(Icons.arrow_back),
onPressed: () {
Navigator.pop(context);
},
),
),
body: Container(
color: Colors.white54,
child: Column(
children: [
SizedBox(
height: 60,
),
Row(
mainAxisAlignment: MainAxisAlignment.center,
crossAxisAlignment: CrossAxisAlignment.center,
children: [
Container(
height: 125,
width: 125,
child: Image(image: AssetImage("assets/images/$image1"))),
SizedBox(
width: 20,
),
Text("$randomCharactersString"),
Container(
height: 125,
width: 125,
child: Image(image: AssetImage("assets/images/$image2"))),
], ),
Column(
children: [
Container(
height: 250,
padding: EdgeInsets.all(10),
alignment: Alignment.center,
child: GridView.builder(gridDelegate: SliverGridDelegateWithFixedCrossAxisCount(
// childAspectRatio: 1,
crossAxisCount: 7,
crossAxisSpacing: 4,
mainAxisSpacing: 4,
),
itemCount: puzzleAnswer!.length,
shrinkWrap: true,
itemBuilder: (context , index){
print(index);
if(selection.length>index){
return InkWell(
onTap: () {
setState(() {
if (!selection.contains(index)){
null;
}
else{
selection.remove(index);
}
});
},
child: Container(
padding: EdgeInsets.all(10),
alignment: Alignment.center,
decoration: BoxDecoration(
color:Colors.blue,
borderRadius: BorderRadius.circular(7)
),
child: Text("${selection[index]}",
style: TextStyle(color: Colors.black)
),
),
);
}
else{
return Container(
padding: EdgeInsets.all(10),
alignment: Alignment.center,
decoration: BoxDecoration(
color: Colors.blue,
borderRadius: BorderRadius.circular(7)
),
child: Text("",
style: TextStyle(color: Colors.black)
),
);
}
}
)
),
],
),
Expanded(child:
Container(
// height: 300,
padding: EdgeInsets.all(10),
alignment: Alignment.center,
child: GridView.builder(gridDelegate: SliverGridDelegateWithFixedCrossAxisCount(
childAspectRatio: 1,
crossAxisCount: 7,
crossAxisSpacing: 4,
mainAxisSpacing: 4,
),
itemCount: keyboardSize,
// shrinkWrap: true,
itemBuilder: (context , index)
{
return InkWell(
onTap:(){
setState(() {
if (!selection.contains(index)){
selection.add(index);
}
else{
selection.remove(index);
}
}
);
},
child: Container(
padding:EdgeInsets.all(10),
alignment:Alignment.center,
decoration:BoxDecoration(
color:selection.contains(index)?Colors.blueAccent:Colors.grey,
borderRadius:BorderRadius.circular(7)
),
child: Text("${keyboardWords[selection[index]]}",
style:TextStyle(color:Colors.black)
),
),
);
// return ElevatedButton(
// style: ElevatedButton.styleFrom(
// primary: Colors.purple,
// // padding: EdgeInsets.symmetric(horizontal: 50, vertical: 20),
// textStyle: TextStyle(
// fontSize: 20,
// fontWeight: FontWeight.bold
// ),
// ),
// onPressed: null,
// child: Text("d"),
// );
}
)
),
),
],
),
),
),
);
}
}
RandomString(int strlen,String puzzleAnswer){
Random rnd = new Random();
String result = "";
const chars = "abcdefghijklmnopqrstuvwxyz";
for (var i = 0; i < strlen; i++) {
// if (!puzzleAnswer.contains(chars[i])) {
result += chars[rnd.nextInt(chars.length)];
// }
}
return result;
}
Answered By – stacktrace2234
This Answer collected from stackoverflow, is licensed under cc by-sa 2.5 , cc by-sa 3.0 and cc by-sa 4.0