-
Notifications
You must be signed in to change notification settings - Fork 29.7k
Description
Is there an existing issue for this?
- I have searched the existing issues
- I have read the guide to filing a bug
Steps to reproduce
I embed a SurfaceView in a Flutter page, and I get some unexpected results. When using AndroidView, SurfaceView is added to VirtualDisplay, and when performing hot reload or rotate the screen , SurfaceView will not display any frame. When using AndroidSurfaceView, hot reload is normal, But when the page exits, there will be one frame left.
Steps to reproduce:
1.Run the example, click the play_video button, it will jump to the playback page, and then execute hot reload or rotate the screen.
2.Change the child to AndroidSurfaceView , re-run the example, when you exit the page, you will see a frame remains.
Expected results
It is expected that when embedding SurfaceView, it can behave normally regardless of whetherVDmode orHC mode is used.
Actual results
When using VD mode
Do a hot reload or rotate the screen
AndroidView.mp4
When using HD mode
AndroidSurfaceViews.mp4
Code sample
import 'package:flutter/foundation.dart';
import 'package:flutter/gestures.dart';
import 'package:flutter/material.dart';
import 'package:flutter/rendering.dart';
import 'package:flutter/services.dart';
class VideoPlayPage extends StatefulWidget {
const VideoPlayPage({Key? key}) : super(key: key);
@override
State<VideoPlayPage> createState() => _VideoPlayPageState();
}
class _VideoPlayPageState extends State<VideoPlayPage> {
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: const Text('play'),
),
body: LayoutBuilder(
builder: (BuildContext context, BoxConstraints boxConstraints) {
return Container(
color: Colors.black,
width: boxConstraints.maxWidth,
height: boxConstraints.maxWidth * 9 / 16,
child: _surface(),
);
},
),
);
}
Widget _surface() {
return PlatformViewLink(
surfaceFactory: (context, controller) {
return AndroidViewSurface(
controller: controller as AndroidViewController,
gestureRecognizers: const <Factory<OneSequenceGestureRecognizer>>{},
hitTestBehavior: PlatformViewHitTestBehavior.opaque,
);
},
onCreatePlatformView: (params) {
return PlatformViewsService.initSurfaceAndroidView(
id: params.id,
viewType: 'video_player',
layoutDirection: TextDirection.ltr,
creationParams: {},
creationParamsCodec: const StandardMessageCodec(),
onFocus: () {
params.onFocusChanged(true);
},
)
..addOnPlatformViewCreatedListener(params.onPlatformViewCreated)
..create();
},
viewType: 'video_player');
}
Widget _vd() {
return const AndroidView(viewType: 'video_player');
}
}PlatformView is defined in java, providing a MediaPlayer for playing MP4 files in the asset.
// create SurfaceViewPlatformView
class SurfaceViewPlatformView implements PlatformView {
private final SurfaceView surfaceView;
private MediaPlayer mediaPlayer;
SurfaceViewPlatformView(SurfaceView surfaceView) {
this.surfaceView = surfaceView;
//simple delay play the video
surfaceView.postDelayed(new Runnable() {
@Override
public void run() {
// 创建MediaPlayer并设置数据源
mediaPlayer = new MediaPlayer();
mediaPlayer.setDisplay(surfaceView.getHolder());
AssetFileDescriptor assetFileDescriptor = null;
try {
// 获取MP4文件的AssetFileDescriptor
assetFileDescriptor = surfaceView.getContext().getAssets().openFd("big_buck_bunny.mp4");
// 设置MediaPlayer的数据源为AssetFileDescriptor
mediaPlayer.setDataSource(assetFileDescriptor.getFileDescriptor(),
assetFileDescriptor.getStartOffset(), assetFileDescriptor.getLength());
// 准备MediaPlayer
mediaPlayer.prepare();
// 开始播放
mediaPlayer.start();
} catch (IOException e) {
e.printStackTrace();
} finally {
// 释放AssetFileDescriptor资源
if (assetFileDescriptor != null) {
try {
assetFileDescriptor.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
}, 1000);
}
@Override
public View getView() {
return surfaceView;
}
@Override
public void dispose() {
// 清理资源
mediaPlayer.release();
}
}The demo example is a plugin,
The complete code can be found in project video_player_surface
Screenshots or Video
No response
Logs
Logs
[Paste your logs here]Flutter Doctor output
Doctor output
Doctor summary (to see all details, run flutter doctor -v):
[√] Flutter (Channel stable, 3.10.4, on Microsoft Windows [版本 10.0.19044.2965], locale zh-CN)
[X] Windows Version (Installed version of Windows is version 10 or higher)
[!] Android toolchain - develop for Android devices (Android SDK version 33.0.2)
X cmdline-tools component is missing
Run `path/to/sdkmanager --install "cmdline-tools;latest"`
See https://developer.android.com/studio/command-line for more details.
X Android license status unknown.
Run `flutter doctor --android-licenses` to accept the SDK licenses.
See https://flutter.dev/docs/get-started/install/windows#android-setup for more details.
[√] Chrome - develop for the web
[X] Visual Studio - develop for Windows
X Visual Studio not installed; this is necessary for Windows development.
Download at https://visualstudio.microsoft.com/downloads/.
Please install the "Desktop development with C++" workload, including all of its default components
[√] Android Studio (version 2021.3)
[!] Android Studio (version 2022.1)
X Unable to find bundled Java version.
[√] VS Code (version 1.77.1)
[√] Connected device (4 available)