#android
#Android
Вопрос:
Мне нужно получить время выполнения видео, которое воспроизводится в «Видеообзоре» (то есть время, показанное в левой части индикатора выполнения).
Любая помощь будет действительно оценена. Спасибо.
Ответ №1:
Вы можете получить продолжительность видео mVideoView.getDuration()
, сначала установить индикатор выполнения на 0, а затем получить текущий прогресс видео mVideoView.getCurrentPosition();
и увеличить статус индикатора выполнения на основе текущего прогресса видео в процентах (%) (current * 100 / duration)
. Я попробовал это, используя AsyncTask
проверку этого полного примера.
main.xml
<?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/my_Video_View"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:text="@string/hello"
/>
<ProgressBar android:layout_alignParentBottom="true"
style="@android:style/Widget.ProgressBar.Horizontal"
android:layout_width="fill_parent"
android:layout_height="10dp"
android:id="@ id/Progressbar"/>
</RelativeLayout>
VideoPlayActivity.java
public class VideoPlayActivity extends Activity {
ProgressBar mProgressBar;
VideoView mVideoView;
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
String path = Environment.getExternalStorageDirectory().toString();
String filename = "/hr.3gp";
mProgressBar = (ProgressBar) findViewById(R.id.Progressbar);
mProgressBar.setProgress(0);
mProgressBar.setMax(100);
mVideoView = (VideoView) findViewById(R.id.my_Video_View);
mVideoView.setVideoURI(Uri.parse(path filename));
new MyAsync().execute();
}
private class MyAsync extends AsyncTask<Void, Integer, Void>
{
int duration = 0;
int current = 0;
@Override
protected Void doInBackground(Void... params) {
mVideoView.start();
mVideoView.setOnPreparedListener(new OnPreparedListener() {
public void onPrepared(MediaPlayer mp) {
duration = mVideoView.getDuration();
}
});
do {
current = mVideoView.getCurrentPosition();
System.out.println("duration - " duration " current- "
current);
try {
publishProgress((int) (current * 100 / duration));
if(mProgressBar.getProgress() >= 100){
break;
}
} catch (Exception e) {
}
} while (mProgressBar.getProgress() <= 100);
return null;
}
@Override
protected void onProgressUpdate(Integer... values) {
super.onProgressUpdate(values);
System.out.println(values[0]);
mProgressBar.setProgress(values[0]);
}
}
}
Комментарии:
1. вы действительно можете позвонить
mVideoView.start();
doInBackground
? нет исключения wrongUiThread?2. привет, Лалит. Что произойдет, если пользователь выйдет из VideoView или закроет его? Как можно предотвратить бесконечное выполнение этой асинхронной задачи?
3. @android-user вы можете явно вызвать
cancel()
метод в своей AsyncTask4. метод
setOnPreparedListener
должен вызываться из потока пользовательского интерфейса.5. Весь ваш код фоновой задачи должен вызываться из потока пользовательского интерфейса
Ответ №2:
Для этой цели вы можете использовать поток, как показано ниже:
videoView.start();
videoView.setOnPreparedListener(new OnPreparedListener() {
public void onPrepared(MediaPlayer mp) {
running = true;
final int duration = videoView.getDuration();
new Thread(new Runnable() {
public void run() {
do{
textView.post(new Runnable() {
public void run() {
int time = (duration - videoView.getCurrentPosition())/1000;
textView.setText(time "");
}
});
try {
Thread.sleep(500);
} catch (InterruptedException e) {
e.printStackTrace();
}
if(!running) break;
}
while(videoView.getCurrentPosition()<duration);
}
}).start();
}
});
Комментарии:
1. это приводит к утечке в textview
2. @isudansh не беспокойтесь об утечках памяти, просто забудьте
Ответ №3:
Вы можете использовать getCurrentPosition()
и getDuration()
для вычисления прогресса.
Комментарии:
1. но, когда вызывать эти методы?, так как мне нужно отслеживать это каждую секунду.
2. @mr-narendra, вы можете обратиться к ответам от Nolesh и Алексея Тимощенко выше, установив таймер или режим ожидания потока на 1000 мс.
3. Я добился этого с помощью
handler
.
Ответ №4:
Я добился этого таким образом
private void playVideo() {
setViewNotVisibility();
final String videoSource = "android.resource://" getPackageName() File.separator R.raw.moviiegood;
videoView.setKeepScreenOn(true);
videoView.setVideoURI(Uri.parse(videoSource));
videoView.setMediaController(null);
videoView.setOnCompletionListener(myVideoViewCompletionListener);
videoView.setOnPreparedListener(new MediaPlayer.OnPreparedListener() {
@Override
public void onPrepared(MediaPlayer mp) {
startVideo();
setDuration();
timerCounter();
}
}
);
}
private Timer timer;
private void timerCounter(){
timer = new Timer();
TimerTask task = new TimerTask() {
@Override
public void run() {
runOnUiThread(new Runnable() {
@Override
public void run() {
updateUI();
}
});
}
};
timer.schedule(task, 0, 1000);
}
private int duration = 0;
private void setDuration(){
duration = videoView.getDuration();
}
private void updateUI(){
if (pbVideoView.getProgress() >= 100) {
timer.cancel();
}
int current = videoView.getCurrentPosition();
int progress = current * 100 / duration;
pbVideoView.setProgress(progress);
}
Если у вас есть вопросы, не стесняйтесь задавать