悬停按钮上随机 Image.asset 变化?
Flutter random Image.asset changes on hovering Button?
我想在用户每次进入页面时随机显示一张图片。我在这个页面上还有一个按钮(带有悬停的红色容器),当用户悬停它时,会显示一张新的随机图片,但自页面加载后它不应该改变。我认为这与 setState() 有关,但我不知道该怎么做。代码:
import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart';
import 'package:flutter/rendering.dart';
import 'dart:core';
import 'dart:math';
class Home2 extends StatefulWidget {
const Home2({Key? key}) : super(key: key);
@override
_Home2State createState() => _Home2State();
}
class _Home2State extends State<Home2> {
dynamic listCinematicImages = [
"assets/cinematic/1.jpg",
"assets/cinematic/2.jpg",
"assets/cinematic/3.jpg",
"assets/cinematic/4.jpg",
"assets/cinematic/5.jpg",
"assets/cinematic/6.jpg",
"assets/cinematic/7.jpg",
];
late Random rnd;
@override
bool isHoveringButton = false;
@override
Widget build(BuildContext context) {
Size size = MediaQuery.of(context).size;
return Scaffold(
backgroundColor: Colors.black,
body: Row(
mainAxisAlignment: MainAxisAlignment.center,
children: [
Container(
height: double.infinity,
width: size.width * 0.5,
alignment: Alignment.center,
child: InkWell(
onTap: () {
},
onHover: (hovering) {
setState(() => isHoveringButton = hovering);
},
child: Container(
height: 50,
width: 50,
color: Colors.red,
),
),
),
Container(
height: double.infinity,
width: size.width * 0.5,
child: img(),
),
],
),
);
}
Image img() {
int min = 0;
int max = listCinematicImages.length-1;
rnd = new Random();
int r = min + rnd.nextInt(max - min);
String image_name = listCinematicImages[r].toString();
return Image.asset(image_name, fit: BoxFit.cover,);
}
}
我不知道这是否有帮助,但这是给出的一些错误:
Error: Expected a value of type 'Map<String, dynamic>', but got one of type 'Null'
at Object.throw_ [as throw] (http://localhost:60569/dart_sdk.js:5054:11)
at Object.castError (http://localhost:60569/dart_sdk.js:5013:15)
at Object.cast [as as] (http://localhost:60569/dart_sdk.js:5336:17)
at Function.as_C [as as] (http://localhost:60569/dart_sdk.js:4959:19)
好的,这里发生了很多事情。让我们一步一步地考虑这个问题。您正试图在某些事件中展示新形象。所以我们需要创建一个变量来跟踪当前图像:
class Home2 extends StatefulWidget {
const Home2({Key? key}) : super(key: key);
@override
_Home2State createState() => _Home2State();
}
class _Home2State extends State<Home2> {
static const listCinematicImages = [
"assets/cinematic/1.jpg",
"assets/cinematic/2.jpg",
"assets/cinematic/3.jpg",
"assets/cinematic/4.jpg",
"assets/cinematic/5.jpg",
"assets/cinematic/6.jpg",
"assets/cinematic/7.jpg",
];
late String currentImage;
}
在我们开始担心事件之前,让我们弄清楚如何从您的列表中 select 随机图像。您提供的功能具有正确的元素,但发生了一些奇怪的事情。我举的一个简单例子是:
String _getRandomImage() {
final randomIndex = Random().nextInt(listCinematicImages.length-1);
return listCinematicImages[randomIndex];
}
现在我们拥有所有元素,我们只需要在正确的时间更新小部件。首先你想在每次加载这个小部件时设置一个新图像。我们可以使用 initState 方法来做到这一点:
@override
void initState() {
super.initState();
final newImage = _getRandomImage();
setState(() => currentImage = newImage);
}
并且您想在用户将鼠标悬停在图像上时再次更改图像。您确实可以使用 InkWell
执行此操作,但请记住,根据 documentation,每次鼠标进入和离开该区域时,onHover
都会提供回调,因此我们必须确保仅在我们进入区域时更新图像:
InkWell(
onHover: (bool hasEntered) {
if(!hasEntered) return;
final newImage = _getRandomImage();
setState(() => currentImage = newImage);
}
);
就是这样!将它们与您的示例放在一起:
import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart';
import 'package:flutter/rendering.dart';
import 'dart:core';
import 'dart:math';
class Home2 extends StatefulWidget {
const Home2({Key? key}) : super(key: key);
@override
_Home2State createState() => _Home2State();
}
class _Home2State extends State<Home2> {
static const listCinematicImages = [
"assets/cinematic/1.jpg",
"assets/cinematic/2.jpg",
"assets/cinematic/3.jpg",
"assets/cinematic/4.jpg",
"assets/cinematic/5.jpg",
"assets/cinematic/6.jpg",
"assets/cinematic/7.jpg",
];
late String currentImage;
@override
void initState() {
super.initState();
final newImage = _getRandomImage();
setState(() => currentImage = newImage);
}
@override
Widget build(BuildContext context) {
Size size = MediaQuery.of(context).size;
return Scaffold(
backgroundColor: Colors.black,
body: Row(
mainAxisAlignment: MainAxisAlignment.center,
children: [
Container(
height: double.infinity,
width: size.width * 0.5,
alignment: Alignment.center,
child: InkWell(
onHover: (bool hasEntered) {
if(!hasEntered) return;
final newImage = _getRandomImage();
setState(() => currentImage = newImage);
},
child: Container(
height: 50,
width: 50,
color: Colors.red,
),
),
),
Container(
height: double.infinity,
width: size.width * 0.5,
child: Image.asset(currentImage, fit: BoxFit.cover,);,
),
],
),
);
}
String _getRandomImage() {
final randomIndex = Random().nextInt(listCinematicImages.length-1);
return listCinematicImages[randomIndex];
}
}
我想在用户每次进入页面时随机显示一张图片。我在这个页面上还有一个按钮(带有悬停的红色容器),当用户悬停它时,会显示一张新的随机图片,但自页面加载后它不应该改变。我认为这与 setState() 有关,但我不知道该怎么做。代码:
import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart';
import 'package:flutter/rendering.dart';
import 'dart:core';
import 'dart:math';
class Home2 extends StatefulWidget {
const Home2({Key? key}) : super(key: key);
@override
_Home2State createState() => _Home2State();
}
class _Home2State extends State<Home2> {
dynamic listCinematicImages = [
"assets/cinematic/1.jpg",
"assets/cinematic/2.jpg",
"assets/cinematic/3.jpg",
"assets/cinematic/4.jpg",
"assets/cinematic/5.jpg",
"assets/cinematic/6.jpg",
"assets/cinematic/7.jpg",
];
late Random rnd;
@override
bool isHoveringButton = false;
@override
Widget build(BuildContext context) {
Size size = MediaQuery.of(context).size;
return Scaffold(
backgroundColor: Colors.black,
body: Row(
mainAxisAlignment: MainAxisAlignment.center,
children: [
Container(
height: double.infinity,
width: size.width * 0.5,
alignment: Alignment.center,
child: InkWell(
onTap: () {
},
onHover: (hovering) {
setState(() => isHoveringButton = hovering);
},
child: Container(
height: 50,
width: 50,
color: Colors.red,
),
),
),
Container(
height: double.infinity,
width: size.width * 0.5,
child: img(),
),
],
),
);
}
Image img() {
int min = 0;
int max = listCinematicImages.length-1;
rnd = new Random();
int r = min + rnd.nextInt(max - min);
String image_name = listCinematicImages[r].toString();
return Image.asset(image_name, fit: BoxFit.cover,);
}
}
我不知道这是否有帮助,但这是给出的一些错误:
Error: Expected a value of type 'Map<String, dynamic>', but got one of type 'Null'
at Object.throw_ [as throw] (http://localhost:60569/dart_sdk.js:5054:11)
at Object.castError (http://localhost:60569/dart_sdk.js:5013:15)
at Object.cast [as as] (http://localhost:60569/dart_sdk.js:5336:17)
at Function.as_C [as as] (http://localhost:60569/dart_sdk.js:4959:19)
好的,这里发生了很多事情。让我们一步一步地考虑这个问题。您正试图在某些事件中展示新形象。所以我们需要创建一个变量来跟踪当前图像:
class Home2 extends StatefulWidget {
const Home2({Key? key}) : super(key: key);
@override
_Home2State createState() => _Home2State();
}
class _Home2State extends State<Home2> {
static const listCinematicImages = [
"assets/cinematic/1.jpg",
"assets/cinematic/2.jpg",
"assets/cinematic/3.jpg",
"assets/cinematic/4.jpg",
"assets/cinematic/5.jpg",
"assets/cinematic/6.jpg",
"assets/cinematic/7.jpg",
];
late String currentImage;
}
在我们开始担心事件之前,让我们弄清楚如何从您的列表中 select 随机图像。您提供的功能具有正确的元素,但发生了一些奇怪的事情。我举的一个简单例子是:
String _getRandomImage() {
final randomIndex = Random().nextInt(listCinematicImages.length-1);
return listCinematicImages[randomIndex];
}
现在我们拥有所有元素,我们只需要在正确的时间更新小部件。首先你想在每次加载这个小部件时设置一个新图像。我们可以使用 initState 方法来做到这一点:
@override
void initState() {
super.initState();
final newImage = _getRandomImage();
setState(() => currentImage = newImage);
}
并且您想在用户将鼠标悬停在图像上时再次更改图像。您确实可以使用 InkWell
执行此操作,但请记住,根据 documentation,每次鼠标进入和离开该区域时,onHover
都会提供回调,因此我们必须确保仅在我们进入区域时更新图像:
InkWell(
onHover: (bool hasEntered) {
if(!hasEntered) return;
final newImage = _getRandomImage();
setState(() => currentImage = newImage);
}
);
就是这样!将它们与您的示例放在一起:
import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart';
import 'package:flutter/rendering.dart';
import 'dart:core';
import 'dart:math';
class Home2 extends StatefulWidget {
const Home2({Key? key}) : super(key: key);
@override
_Home2State createState() => _Home2State();
}
class _Home2State extends State<Home2> {
static const listCinematicImages = [
"assets/cinematic/1.jpg",
"assets/cinematic/2.jpg",
"assets/cinematic/3.jpg",
"assets/cinematic/4.jpg",
"assets/cinematic/5.jpg",
"assets/cinematic/6.jpg",
"assets/cinematic/7.jpg",
];
late String currentImage;
@override
void initState() {
super.initState();
final newImage = _getRandomImage();
setState(() => currentImage = newImage);
}
@override
Widget build(BuildContext context) {
Size size = MediaQuery.of(context).size;
return Scaffold(
backgroundColor: Colors.black,
body: Row(
mainAxisAlignment: MainAxisAlignment.center,
children: [
Container(
height: double.infinity,
width: size.width * 0.5,
alignment: Alignment.center,
child: InkWell(
onHover: (bool hasEntered) {
if(!hasEntered) return;
final newImage = _getRandomImage();
setState(() => currentImage = newImage);
},
child: Container(
height: 50,
width: 50,
color: Colors.red,
),
),
),
Container(
height: double.infinity,
width: size.width * 0.5,
child: Image.asset(currentImage, fit: BoxFit.cover,);,
),
],
),
);
}
String _getRandomImage() {
final randomIndex = Random().nextInt(listCinematicImages.length-1);
return listCinematicImages[randomIndex];
}
}