I would know if is possible to use two surface in same layout and view each at same time. In future I would a grid-view of video-view, but each video-view using vlc.
I modify this sample (android-vlc-sample) using fragment.
The result is that I see only one video...How can I solve ?
From log-cat I not see important error, but I think that there are rendering problems for android UIThread
Java Coding
public class MultipleVideoPlayFragmentActivity extends FragmentActivity { public final static String LOCATION = "com.compdigitec.libvlcandroidsample.MultipleVideoPlayFragmentActivity.location"; private static final String TAG = "MediaPlayer"; public String mFilePatha; @Override public void onCreate(Bundle icicle) { super.onCreate(icicle); setContentView(R.layout.activity_multiple_video_play_fragment); Intent intent = getIntent(); mFilePatha = intent.getExtras().getString(LOCATION); } public static class VideoFragment extends Fragment implements SurfaceHolder.Callback, IVideoPlayer { public final static String TAG = "LibVLCAndroidSample/VideoActivity"; public final static String LOCATION = "com.compdigitec.libvlcandroidsample.VideoFragment.location"; private String mFilePath; // display surface private SurfaceView mSurface; private SurfaceHolder holder; // media player private LibVLC libvlc; private int mVideoWidth; private int mVideoHeight; private final static int VideoSizeChanged = -1; /************* * Activity *************/ @Override public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) { return inflater.inflate(R.layout.sample, container, false); } @Override public void onActivityCreated(Bundle savedInstanceState) { super.onActivityCreated(savedInstanceState); // Receive path to play from intent Log.d(TAG, "Playing back " + mFilePath); mFilePath = ((MultipleVideoPlayFragmentActivity) getActivity()).mFilePatha; // mFilePath="rtsp://192.168.4.125:554/0"; // mFilePath="android.resource://it.nexera.visiamobile/raw/sample_mpeg4"; mSurface = (SurfaceView) getView().findViewById(R.id.surface); holder = mSurface.getHolder(); holder.addCallback(this); } @Override public void onConfigurationChanged(Configuration newConfig) { super.onConfigurationChanged(newConfig); setSize(mVideoWidth, mVideoHeight); } @Override public void onResume() { super.onResume(); createPlayer(mFilePath); } @Override public void onPause() { super.onPause(); releasePlayer(); } @Override public void onDestroy() { super.onDestroy(); releasePlayer(); } /************* * Surface *************/ public void surfaceCreated(SurfaceHolder holder) { } public void surfaceChanged(SurfaceHolder surfaceholder, int format, int width, int height) { if (libvlc != null) libvlc.attachSurface(holder.getSurface(), this); } public void surfaceDestroyed(SurfaceHolder surfaceholder) { } private void setSize(int width, int height) { mVideoWidth = width; mVideoHeight = height; if (mVideoWidth * mVideoHeight <= 1) return; // get screen size int w = getActivity().getWindow().getDecorView().getWidth(); int h = getActivity().getWindow().getDecorView().getHeight(); // getWindow().getDecorView() doesn't always take orientation into // account, we have to correct the values boolean isPortrait = getResources().getConfiguration().orientation == Configuration.ORIENTATION_PORTRAIT; if (w > h && isPortrait || w < h && !isPortrait) { int i = w; w = h; h = i; } float videoAR = (float) mVideoWidth / (float) mVideoHeight; float screenAR = (float) w / (float) h; if (screenAR < videoAR) h = (int) (w / videoAR); else w = (int) (h * videoAR); // force surface buffer size holder.setFixedSize(mVideoWidth, mVideoHeight); // set display size LayoutParams lp = mSurface.getLayoutParams(); lp.width = w; lp.height = h; mSurface.setLayoutParams(lp); mSurface.invalidate(); } @Override public void setSurfaceSize(int width, int height, int visible_width, int visible_height, int sar_num, int sar_den) { Message msg = Message.obtain(mHandler, VideoSizeChanged, width, height); msg.sendToTarget(); } /************* * Player *************/ private void createPlayer(String media) { releasePlayer(); try { if (media.length() > 0) { Toast toast = Toast.makeText(this.getActivity(), media, Toast.LENGTH_LONG); toast.setGravity( Gravity.BOTTOM | Gravity.CENTER_HORIZONTAL, 0, 0); toast.show(); } // Create a new media player libvlc = LibVLC.getInstance(); libvlc.setHardwareAcceleration(LibVLC.HW_ACCELERATION_DISABLED); libvlc.setSubtitlesEncoding(""); libvlc.setAout(LibVLC.AOUT_OPENSLES); libvlc.setTimeStretching(true); libvlc.setChroma("RV32"); libvlc.setVerboseMode(true); // LibVLC.restart(this.getActivity()); EventHandler.getInstance().addHandler(mHandler); holder.setFormat(PixelFormat.RGBX_8888); holder.setKeepScreenOn(true); MediaList list = libvlc.getMediaList(); list.clear(); list.add(new Media(libvlc, LibVLC.PathToURI(media)), false); libvlc.playIndex(0); } catch (Exception e) { Toast.makeText(this.getActivity(), "Error creating player!", Toast.LENGTH_LONG).show(); } } private void releasePlayer() { if (libvlc == null) return; EventHandler.getInstance().removeHandler(mHandler); libvlc.stop(); libvlc.detachSurface(); holder = null; libvlc.closeAout(); libvlc.destroy(); libvlc = null; mVideoWidth = 0; mVideoHeight = 0; } /************* * Events *************/ private Handler mHandler = new MyHandler(this); private static class MyHandler extends Handler { private WeakReference<VideoFragment> mOwner; public MyHandler(VideoFragment owner) { mOwner = new WeakReference<VideoFragment>(owner); } @Override public void handleMessage(Message msg) { VideoFragment player = mOwner.get(); // SamplePlayer events if (msg.what == VideoSizeChanged) { player.setSize(msg.arg1, msg.arg2); return; } // Libvlc events Bundle b = msg.getData(); switch (b.getInt("event")) { case EventHandler.MediaPlayerEndReached: player.releasePlayer(); break; case EventHandler.MediaPlayerPlaying: case EventHandler.MediaPlayerPaused: case EventHandler.MediaPlayerStopped: default: break; } } } } }
XML Coding
<?xml version="1.0" encoding="utf-8"?>
<fragment android:id="@+id/video_1_fragment" android:layout_width="100dp" android:layout_height="0dp" android:layout_weight="1" class="com.compdigitec.libvlcandroidsample.MultipleVideoPlayFragmentActivity$VideoFragment" /> <fragment android:id="@+id/video_2_fragment" android:layout_width="100dp" android:layout_height="0dp" android:layout_weight="1" class="com.compdigitec.libvlcandroidsample.MultipleVideoPlayFragmentActivity$VideoFragment" />
Single Fragment Layout
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent" android:layout_height="match_parent" android:baselineAligned="false" android:orientation="vertical" tools:context=".SampleActivity" > <FrameLayout android:layout_width="match_parent" android:layout_height="match_parent" > <SurfaceView android:id="@+id/surface" android:layout_width="fill_parent" android:layout_height="fill_parent" android:layout_gravity="center" /> </FrameLayout>