|
@@ -0,0 +1,116 @@
|
|
|
+// ignore_for_file: avoid_print
|
|
|
+
|
|
|
+import 'dart:async';
|
|
|
+import 'dart:typed_data';
|
|
|
+import 'dart:ui';
|
|
|
+
|
|
|
+import 'package:flutter/material.dart' hide Image;
|
|
|
+import 'package:get/get.dart';
|
|
|
+import 'package:vid_player_demo/controller/player_controller.dart';
|
|
|
+
|
|
|
+class ImageTestView extends StatefulWidget {
|
|
|
+ const ImageTestView(
|
|
|
+ this.imageNum, {
|
|
|
+ Key? key,
|
|
|
+ this.viewSize = const Size(600, 500),
|
|
|
+ }) : super(key: key);
|
|
|
+ final int imageNum;
|
|
|
+ final Size viewSize;
|
|
|
+
|
|
|
+ @override
|
|
|
+ _ImageTestViewState createState() => _ImageTestViewState();
|
|
|
+}
|
|
|
+
|
|
|
+class _ImageTestViewState extends State<ImageTestView> {
|
|
|
+ PlayerStateController? _playerStateController;
|
|
|
+ PlayerStateController get playerStateController => _playerStateController!;
|
|
|
+ Image? image;
|
|
|
+ int loadedImageCount = 0;
|
|
|
+
|
|
|
+ /// 外部状态控制器
|
|
|
+ void clickPlay() async {
|
|
|
+ print("${DateTime.now()} Click play");
|
|
|
+ for (int i = 0; i < widget.imageNum; i++) {
|
|
|
+ final image = await _loadImage(600, 800);
|
|
|
+ // final cloneImage = image.clone();
|
|
|
+ print(
|
|
|
+ "${DateTime.now()} Clone image $i ${image.width} x ${image.height}");
|
|
|
+ setState(() {
|
|
|
+ loadedImageCount++;
|
|
|
+ });
|
|
|
+ // cloneImage.dispose();
|
|
|
+ image.dispose();
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ void clickPause() {
|
|
|
+ print("${DateTime.now()} Click pause");
|
|
|
+ }
|
|
|
+
|
|
|
+ void onClickPlay(Object sender, dynamic e) {
|
|
|
+ print("${DateTime.now()} receive Load together $e");
|
|
|
+ clickPlay();
|
|
|
+ }
|
|
|
+
|
|
|
+ Future<Image> _loadImage(int width, int height) {
|
|
|
+ final Completer<Image> completer = Completer<Image>();
|
|
|
+ decodeImageFromPixels(
|
|
|
+ Uint8List.fromList(List<int>.filled(width * height * 4, 0xFF0000FF)),
|
|
|
+ width,
|
|
|
+ height,
|
|
|
+ PixelFormat.rgba8888,
|
|
|
+ // Don't worry about disposing or cloning this image - responsibility
|
|
|
+ // is transferred to the caller, and that is safe since this method
|
|
|
+ // will not touch it again.
|
|
|
+ (Image image) => completer.complete(image),
|
|
|
+ );
|
|
|
+ return completer.future;
|
|
|
+ }
|
|
|
+
|
|
|
+ @override
|
|
|
+ void initState() {
|
|
|
+ _playerStateController = Get.find<PlayerStateController>();
|
|
|
+ playerStateController.trigglePlay.addListener(onClickPlay);
|
|
|
+ super.initState();
|
|
|
+ }
|
|
|
+
|
|
|
+ @override
|
|
|
+ Widget build(BuildContext context) {
|
|
|
+ return Center(
|
|
|
+ child: Column(
|
|
|
+ mainAxisAlignment: MainAxisAlignment.spaceEvenly,
|
|
|
+ children: [
|
|
|
+ SizedBox(
|
|
|
+ width: widget.viewSize.width,
|
|
|
+ height: widget.viewSize.height,
|
|
|
+ child: RepaintBoundary(
|
|
|
+ child: Text("共需要 ${widget.imageNum} ,已加载 $loadedImageCount 张图片"),
|
|
|
+ ),
|
|
|
+ ),
|
|
|
+ const Text('Image 载入测试'),
|
|
|
+ Row(
|
|
|
+ mainAxisAlignment: MainAxisAlignment.spaceEvenly,
|
|
|
+ children: [
|
|
|
+ ElevatedButton(
|
|
|
+ onPressed: () {
|
|
|
+ clickPlay();
|
|
|
+ },
|
|
|
+ child: const Text('▶ Play')),
|
|
|
+ ElevatedButton(
|
|
|
+ onPressed: () {
|
|
|
+ clickPause();
|
|
|
+ },
|
|
|
+ child: const Text('⏸ Pause')),
|
|
|
+ ],
|
|
|
+ ),
|
|
|
+ ],
|
|
|
+ ),
|
|
|
+ );
|
|
|
+ }
|
|
|
+
|
|
|
+ @override
|
|
|
+ void dispose() {
|
|
|
+ print("ImageTestView dispose");
|
|
|
+ super.dispose();
|
|
|
+ }
|
|
|
+}
|