我正在使用VLC-Android来在我的android应用程序中播放H264 RTSP实时流,以下代码成功地将流视频呈现到了表面视图上:
MediaPlayer mMediaPlayer = new MediaPlayer(VLCInstance.get());
SurfaceView mSurfaceView = (SurfaceView) findViewById(R.id.player);
final IVLCVout vlcVout = Constants.mMediaPlayer.getVLCVout();
vlcVout.detachViews();
vlcVout.setVideoView(mSurfaceView);
vlcVout.setWindowSize(mSurfaceDims.getWidth(), mSurfaceDims.getHeight());
vlcVout.attachViews();
mSurfaceView.setKeepScreenOn(true);
Media media = new Media(VLCInstance.get(), Uri.parse(path));
mMediaPlayer.setMedia(media);
mMediaPlayer.play();
VLCInstance.java:
package bi.anpr.vlc;
import android.content.Context;
import android.util.Log;
import org.videolan.libvlc.LibVLC;
import org.videolan.libvlc.util.VLCUtil;
public class VLCInstance {
public final static String TAG = "VLC/Util/VLCInstance";
private static LibVLC sLibVLC = null;
/** A set of utility functions for the VLC application */
public synchronized static LibVLC get() throws IllegalStateException {
if (sLibVLC == null) {
final Context context = VLCApplication.getAppContext();
if(!VLCUtil.hasCompatibleCPU(context)) {
Log.e(TAG, VLCUtil.getErrorMsg());
throw new IllegalStateException("LibVLC initialisation failed: " + VLCUtil.getErrorMsg());
}
try{
sLibVLC = new LibVLC(context);
}catch (Throwable e){
e.printStackTrace();
}
}
return sLibVLC;
}
public static synchronized void restart(Context context) throws IllegalStateException {
if (sLibVLC != null) {
sLibVLC.release();
sLibVLC = new LibVLC(context);
}
}
}
问题在于,org.videolan.libvlc.MediaPlayer
在调用play()之后在SurfaceView上呈现视频,而没有任何事件可帮助您在视图上捕获当前帧,在此我需要获取每个间隔的当前帧是时候对它执行一些图像处理了。
在播放实时流或本地视频资源时,是否可以使用vlc-android-sdk
将当前帧捕获到缓冲的图像或OpenCV Mat
中?
请注意,对于Java(桌面vlcj),可以通过 DirectMediaPlayer 类实现。
提前谢谢!
答案 0 :(得分:0)
我找到了一个非常简单,非常快速的解决方案。只需使用 TextureView 而不是 SurfaceView ,然后在播放时随时使用getBitmap()
函数检索图像,如下所示。
public class MainActivity extends AppCompatActivity implements TextureView.SurfaceTextureListener,
org.videolan.libvlc.media.MediaPlayer.OnBufferingUpdateListener,
org.videolan.libvlc.media.MediaPlayer.OnCompletionListener,
org.videolan.libvlc.media.MediaPlayer.OnPreparedListener,
org.videolan.libvlc.media.MediaPlayer.OnVideoSizeChangedListener {
private AppCompatActivity me = this;
private MediaPlayer mMediaPlayer;
private TextureView mTextureViewmTextureView;
private String mUrl = "/storage/emulated/0/videos/test.mp4";
private static final String TAG = "MainActivity";
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.content_main);
mMediaPlayer = new MediaPlayer(VLCInstance.get());
mTextureViewmTextureView = (TextureView) findViewById(R.id.player);
mTextureView.setSurfaceTextureListener(this);
}
private void attachViewSurface() {
final IVLCVout vlcVout = mMediaPlayer.getVLCVout();
mMediaPlayer.setScale(0);
vlcVout.detachViews();
vlcVout.setVideoView(mTextureView);
vlcVout.setWindowSize(mTextureView.getWidth(), mTextureView.getHeight());
vlcVout.attachViews();
mTextureView.setKeepScreenOn(true);
}
private void play(String path) {
try {
Media media;
if (new File(path).exists()) {
media = new Media(VLCInstance.get(), path);
} else {
media = new Media(VLCInstance.get(), Uri.parse(path));
}
mMediaPlayer.setMedia(media);
mMediaPlayer.play();
} catch (Exception e) {
Log.e(TAG, e.getMessage());
}
}
@Override
public void onSurfaceTextureAvailable(SurfaceTexture surface, int width, int height) {
attachViewSurface();
if (mMediaPlayer.hasMedia())
mMediaPlayer.play();
else
play(mUrl);
}
public Bitmap getImage() {
return mTextureView.getBitmap();
}
}
VLCInstance.java:
import android.content.Context;
import android.util.Log;
import org.videolan.libvlc.LibVLC;
import org.videolan.libvlc.util.VLCUtil;
public class VLCInstance {
public final static String TAG = "VLC/Util/VLCInstance";
private static LibVLC sLibVLC = null;
/** A set of utility functions for the VLC application */
public synchronized static LibVLC get() throws IllegalStateException {
if (sLibVLC == null) {
final Context context = VLCApplication.getAppContext();
if(!VLCUtil.hasCompatibleCPU(context)) {
Log.e(TAG, VLCUtil.getErrorMsg());
throw new IllegalStateException("LibVLC initialisation failed: " + VLCUtil.getErrorMsg());
}
try{
sLibVLC = new LibVLC(context);
}catch (Throwable e){
e.printStackTrace();
}
}
return sLibVLC;
}
public static synchronized void restart(Context context) throws IllegalStateException {
if (sLibVLC != null) {
sLibVLC.release();
sLibVLC = new LibVLC(context);
}
}
}