2010-09-10 2 views
49

У меня есть VideoView, который занимает верхнюю половину Activity в портретной ориентации, а нижняя половина экрана показывает некоторые изображения и текст. При запуске Activity я воспроизвожу видеопоток rtsp в виде видео. Я приложил MediaController к VideoView через следующий код:Позиционирование MediaController над VideoView

MediaController controller = new MediaController(this); 
    controller.setAnchorView(this.videoView); 
    controller.setMediaPlayer(this.videoView); 
    this.videoView.setMediaController(controller); 

Когда я нажимаю на VideoView, чтобы открыть MediaController на экране я ожидал управления воспроизведением появится наложенная на нижнюю область VideoView (дно MediaController даже с нижней частью VideoView). Вместо этого MediaController появляется на экране снизу вниз, накладывая часть графики и текста, которые у меня ниже VideoView.

Есть ли еще несколько шагов, которые нужно предпринять, чтобы заставить MediaController появляться там, где я хочу, чтобы он появился на экране?

+6

Я заинтересован в этом, а также. Вы когда-нибудь это выясняли? – Ronnie

+1

Нет, я никогда этого не делал. –

+1

Посмотрите на этот вопрос http://stackoverflow.com/questions/6093756/how-to-re-position-mediacontroller – Sandeep

ответ

5

Честно говоря, я бы просто написал свой собственный контроллер. Фактически, I did once.

Это, пожалуйста, попробуйте setAnchorView() - по моему чтению исходного кода в нижней части любого вида якоря появится MediaController.

+3

Я отчаянно люблю рисовать Я опубликовал вчера вопрос о расширении MediaController: http://stackoverflow.com/questions/7881272/extending-mediacontroller-for-android. Я просмотрел ваш код github, но не смог понять его Я думаю, мне нужно переопределить метод setAnchorView, поэтому я могу начать размещать MediaController везде, где захочу. Является ли их способ заставить его «плавать» и позиционировать его таким образом? – Ronnie

+0

Я хочу добавить наклейки к видео, я опубликовал подробный вопрос http://stackoverflow.com/questions/43963522/android-stickers-on-video-using-ffmpeg, моя проблема заключается в том, чтобы вводить пользователя, как заявлял commonsware, относительно изображения наложения (положение, масштаб , вращение) и фоновое видео – 1234567

7

Я использую этот код для его решения.

mediaController.setPadding(0, 0, 0, px); 

Чтобы установить вид медиантроллера в нужное положение. Надеюсь, это поможет вам.

+3

Что такое 'px' ....? –

+1

px - это переменная типа int, которая представляет собой число пикселей в нижней части экрана. – Rongan

+1

Именно то, что я искал. – nifo

40

Установка представления привязки будет работать только в том случае, если размер видеоизображения известен - он будет не по умолчанию. Но вы можете сделать что-то вроде этого:

video.setOnPreparedListener(new OnPreparedListener() { 
     @Override 
     public void onPrepared(MediaPlayer mp) { 
      mp.setOnVideoSizeChangedListener(new OnVideoSizeChangedListener() { 
      @Override 
      public void onVideoSizeChanged(MediaPlayer mp, int width, int height) { 
       /* 
       * add media controller 
       */ 
       mc = new MediaController(YourActivity.this); 
       video.setMediaController(mc); 
       /* 
       * and set its position on screen 
       */ 
       mc.setAnchorView(video); 
      } 
     }); 
    } 
}); 
+0

имеет смысл вызвать setAnchorView() после просмотра готовности к запуску. то есть вызов из onPrepared() – CoDe

+5

setAnchorView (видео) использует родительский элемент VideoView для наложения средств управления мультимедиа. Если у вас есть видео с фиксированной высотой, убедитесь, что вы поместили его внутри рамки, чтобы средства управления мультимедиа находились поверх видео. – Prakash

+0

@Prakash Это то, что я искал .. ваш комментарий был всем, что мне нужно ... Большое спасибо. –

11

я сталкиваюсь с той же проблемой в последнее время, используя setAnchorView (VideoView) будет установлен контроллер полностью под VideoView вместо зависания в нижней части документа. Мой VideoView - один третий экран в верхней области, поэтому контроллер в конечном итоге покрывает любой вид в VideoView.

Ниже, как я в конечном итоге делаю это без написания полномасштабного пользовательского контроллера (только переопределение onSizeChanged из MediaController для перемещения якоря вверх):

Использование FrameLayout в качестве якоря для MediaContoller, завернуть вместе с VideoView как показано ниже:

<RelativeLayout 
    android:id="@+id/videoLayout" 
    android:layout_width="match_parent" 
    android:layout_height="0dp" 
    android:layout_weight="1.3" 
    android:layout_gravity="center" 
    android:background="#000000"> 

    <VideoView 
     android:id="@+id/videoView1" 
     android:layout_width="match_parent" 
     android:layout_height="match_parent" 
     android:layout_centerInParent="true" /> 

    <FrameLayout android:id="@+id/controllerAnchor" 
     android:layout_width="wrap_content" 
     android:layout_height="wrap_content" 
     android:layout_alignParentBottom="true" 
     android:layout_alignParentLeft="true" 
     android:layout_alignParentRight="true" 
     /> 

</RelativeLayout> 

Создание пользовательских MediaController, которые будут двигаться FrameLayout вверх (с MediaController, что привязывается к нему будет следовать), когда его размер изменен:

public class MyMediaController extends MediaController 
{ 
    private FrameLayout anchorView; 


    public MyMediaController(Context context, FrameLayout anchorView) 
    { 
     super(context); 
     this.anchorView = anchorView;  
    } 

    @Override 
    protected void onSizeChanged(int xNew, int yNew, int xOld, int yOld) 
    { 
     super.onSizeChanged(xNew, yNew, xOld, yOld); 

     RelativeLayout.LayoutParams lp = (RelativeLayout.LayoutParams) anchorView.getLayoutParams(); 
     lp.setMargins(0, 0, 0, yNew); 

     anchorView.setLayoutParams(lp); 
     anchorView.requestLayout(); 
    }  
} 

Используйте собственный контроллер выше вместо стандартного, а затем привязать его к FrameLayout:

protected void onCreate(Bundle savedInstanceState) 
{ 

    //... 

    videoView = (VideoView) findViewById(R.id.videoView1);  
    videoController = new MyMediaController(this, (FrameLayout) findViewById(R.id.controllerAnchor));    
    videoView.setMediaController(videoController);  

    //...  
} 

public void onPrepared(MediaPlayer mp) 
{ 
    videoView.start();    

    FrameLayout controllerAnchor = (FrameLayout) findViewById(R.id.controllerAnchor); 
    videoController.setAnchorView(controllerAnchor);     
} 
+0

Его префект благодарит. – Steve

15

Я нашел очень простое решение.

Просто оберните VideoView в FrameLayout, то вы можете добавить MediaController к этому FrameLayout из кода, как это:

MediaController mc = new MediaController(context); 
    videoView.setMediaController(mc); 

    FrameLayout.LayoutParams lp = new FrameLayout.LayoutParams(LayoutParams.MATCH_PARENT, LayoutParams.WRAP_CONTENT); 
    lp.gravity = Gravity.BOTTOM; 
    mc.setLayoutParams(lp); 

    ((ViewGroup) mc.getParent()).removeView(mc); 

    ((FrameLayout) findViewById(R.id.videoViewWrapper)).addView(mc); 

EDIT: так как я отправил этот ответ я столкнулся много проблем с получением его чтобы скрыть и контролировать его размер так, что я в конечном итоге делает это я просто создал свой собственный макет с элементами управления, которые я мог оживлять и работать с без головной боли

+0

лучшее решение, спасибо – keybee

+0

Он работает как шарм! Спасибо! –

+0

отлично поработал .Состоял мой много усилий :) – Radhey

3
//It work good with me 

<?xml version="1.0" encoding="utf-8"?> 
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" 
    android:layout_width="fill_parent" 
    android:layout_height="fill_parent" > 

    <VideoView 
     android:id="@+id/videoview" 
     android:layout_width="640dp" 
     android:layout_height="400dp" 
     android:layout_centerInParent="true" > 
    </VideoView> 

     <FrameLayout 
      android:id="@+id/videoViewWrapper" 
      android:layout_width="match_parent" 
      android:layout_height="wrap_content" 
      android:layout_alignParentBottom="true" > 
     </FrameLayout> 

    </RelativeLayout> 

package com.example.videoview; 

import android.app.Activity; 
import android.content.res.Configuration; 
import android.media.MediaPlayer; 
import android.media.MediaPlayer.OnCompletionListener; 
import android.media.MediaPlayer.OnPreparedListener; 
import android.media.MediaPlayer.OnVideoSizeChangedListener; 
import android.os.Bundle; 
import android.os.Handler; 
import android.view.MotionEvent; 
import android.view.View; 
import android.view.View.OnTouchListener; 
import android.view.ViewGroup; 
import android.widget.FrameLayout; 
import android.widget.MediaController; 
import android.widget.RelativeLayout; 
import android.widget.RelativeLayout.LayoutParams; 
import android.widget.Toast; 
import android.widget.VideoView; 

public class MainActivity extends Activity { 

    // private String path = "http://clips.vorwaerts-gmbh.de/VfE_html5.mp4"; 
    private String path = "http://2387227f13276d2e8940-fbe0b8d9df729a57ca0a851a69d15ebb.r55.cf1.rackcdn.com/hero_2012_demo.mp4"; 

    private VideoView mVideoView; 

    MediaController mc; 

    @Override 
    protected void onCreate(Bundle savedInstanceState) { 
     super.onCreate(savedInstanceState); 
     setContentView(R.layout.activity_main); 

     if (mVideoView != null) 
      return; 
     /** 
     * TODO: Set the path variable to a streaming video URL or a local media 
     * file path. 
     */ 

     mVideoView = (VideoView) findViewById(R.id.videoview); 
     mVideoView.setOnCompletionListener(new OnCompletionListener() { 

      @Override 
      public void onCompletion(MediaPlayer mp) { 
       Toast.makeText(MainActivity.this, "The End", Toast.LENGTH_LONG) 
         .show(); 
      } 
     }); 

     if (path == "") { 
      // Tell the user to provide a media file URL/path. 
      Toast.makeText(
        MainActivity.this, 
        "Please edit MainActivity, and set path" 
          + " variable to your media file URL/path", 
        Toast.LENGTH_LONG).show(); 

     } else { 
      /* 
      * Alternatively,for streaming media you can use 
      * mVideoView.setVideoURI(Uri.parse(path)); 
      */ 
      mVideoView.setVideoPath(path); 

      mVideoView 
        .setMediaController(new MediaController(MainActivity.this)); 
      mVideoView.requestFocus(); 

      mVideoView.setOnPreparedListener(new OnPreparedListener() { 

       @Override 
       public void onPrepared(MediaPlayer mp) { 
        // TODO Auto-generated method stub 
        mp.setOnVideoSizeChangedListener(new OnVideoSizeChangedListener() { 
         @Override 
         public void onVideoSizeChanged(MediaPlayer mp, 
           int width, int height) { 
          /* 
          * add media controller 
          */ 
          mc = new MediaController(MainActivity.this); 
          mVideoView.setMediaController(mc); 
          /* 
          * and set its position on screen 
          */ 
          mc.setAnchorView(mVideoView); 

          ((ViewGroup) mc.getParent()).removeView(mc); 

          ((FrameLayout) findViewById(R.id.videoViewWrapper)) 
            .addView(mc); 
          mc.setVisibility(View.INVISIBLE); 
         } 
        }); 
        mVideoView.start(); 
       } 
      }); 

      mVideoView.setOnTouchListener(new OnTouchListener() { 

       @Override 
       public boolean onTouch(View v, MotionEvent event) { 
        // TODO Auto-generated method stub 
        if (mc != null) { 
         mc.setVisibility(View.VISIBLE); 
         new Handler().postDelayed(new Runnable() { 

          @Override 
          public void run() { 
           mc.setVisibility(View.INVISIBLE); 
          } 
         }, 2000); 
        } 

        return false; 
       } 
      }); 

     } 
    } 

    private RelativeLayout.LayoutParams paramsNotFullscreen, paramsFullscreen; 

    /** 
    * handle with the configChanges attribute in your manifest 
    */ 
    @Override 
    public void onConfigurationChanged(Configuration newConfig) { 
     // TODO Auto-generated method stub 
     super.onConfigurationChanged(newConfig); 

     if (paramsFullscreen == null) { 
      paramsNotFullscreen = (RelativeLayout.LayoutParams) mVideoView 
        .getLayoutParams(); 
      paramsFullscreen = new LayoutParams(paramsNotFullscreen); 
      paramsFullscreen.setMargins(0, 0, 0, 0); 
      paramsFullscreen.height = ViewGroup.LayoutParams.MATCH_PARENT; 
      paramsFullscreen.width = ViewGroup.LayoutParams.MATCH_PARENT; 
      paramsFullscreen.addRule(RelativeLayout.CENTER_IN_PARENT); 
      paramsFullscreen.addRule(RelativeLayout.ALIGN_PARENT_LEFT); 
      paramsFullscreen.addRule(RelativeLayout.ALIGN_PARENT_RIGHT); 
      paramsFullscreen.addRule(RelativeLayout.ALIGN_PARENT_TOP); 
      paramsFullscreen.addRule(RelativeLayout.ALIGN_PARENT_BOTTOM); 
     } 
     // To fullscreen 
     if (newConfig.orientation == Configuration.ORIENTATION_LANDSCAPE) { 
      mVideoView.setLayoutParams(paramsFullscreen); 

     } else if (newConfig.orientation == Configuration.ORIENTATION_PORTRAIT) { 
      mVideoView.setLayoutParams(paramsNotFullscreen); 
     } 
    } 

    @Override 
    protected void onPause() { 
     if (mVideoView.isPlaying()) { 
      mVideoView.pause(); 
     } 
     super.onPause(); 
    } 

    @Override 
    public void onBackPressed() { 
     if (mVideoView != null) { 
      mVideoView.stopPlayback(); 
     } 
     finish(); 
    } 
} 


<?xml version="1.0" encoding="utf-8"?> 
<manifest xmlns:android="http://schemas.android.com/apk/res/android" 
    package="com.example.videoview" 
    android:versionCode="1" 
    android:versionName="1.0" > 

    <uses-sdk 
     android:minSdkVersion="8" 
     android:targetSdkVersion="17" /> 

    <uses-permission android:name="android.permission.INTERNET" /> 
    <uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" /> 

    <application 
     android:allowBackup="true" 
     android:icon="@drawable/ic_launcher" 
     android:label="@string/app_name" 
     android:theme="@style/AppTheme" > 
     <activity 
      android:name="com.example.videoview.MainActivity" 
      android:configChanges="orientation|screenSize" 
      android:label="@string/app_name" 
      android:theme="@android:style/Theme.Dialog" > 
      <intent-filter> 
       <action android:name="android.intent.action.MAIN" /> 

       <category android:name="android.intent.category.LAUNCHER" /> 
      </intent-filter> 
     </activity> 
    </application> 

</manifest> 
+1

Пожалуйста, дайте мне знать, если у вас возникли проблемы –

+0

nope no issues code работает нормально –

0

это первый раз, когда я ответить на вопрос в StackOverflow, Я только вставляю видео Просмотр внутри FrameLayout с одинаковыми показателями. MediaController будет в нижней части FrameLayout. Это работает для меня:

main_activity.XML:

  <FrameLayout  
      android:id="@+id/frame_layout_video" 
      android:layout_centerHorizontal="true" 
      android:layout_width="wrap_content" 
      android:layout_height="400dp"> 

      <VideoView 
       android:id="@+id/video_select" 
       android:layout_width="wrap_content" 
       android:layout_height="400dp" 
       android:adjustViewBounds="true" 
       android:clickable="true" 
       android:scaleType="centerCrop" 
       /> 

     </FrameLayout> 

MainActivity.java:

@Override 
public void onClick(View v) { 
    int i = v.getId(); 

    if(i == R.id.select_video){ 
     selectVideo(); 
    } 

private void selectVideo(){ 
    //this code is to get videos from gallery: 
    Intent galleryIntent = new Intent(Intent.ACTION_GET_CONTENT); 
    galleryIntent.addCategory(Intent.CATEGORY_OPENABLE); 
    galleryIntent.setAction(Intent.ACTION_GET_CONTENT); 
    galleryIntent.setType("video/*"); 
    startActivityForResult(galleryIntent, GALLERY_REQUEST); 

    MediaController mediaController = new MediaController(this); 
    mediaController.setAnchorView(mVideo); 
    //mVideo is the VideoView where I insert the video 
    mVideo.setMediaController(mediaController); 
    mVideo.pause(); 
} 


@Override 
protected void onActivityResult(int requestCode, int resultCode, Intent data) { 

    switch (requestCode) { 
     case 1: 
      if (resultCode == RESULT_OK) { 
       mVideoUri = data.getData(); 
       mVideo.setVideoURI(mVideoUri); 
       mVideo.start(); 
      } 
    } 
} 
Смежные вопросы