开发者

How to get duration of a video file?

开发者 https://www.devze.com 2023-01-20 04:42 出处:网络
I\'m a beginner in Android programming. I\'m writing an application to list all video file in a folder and display information of all videos in the folder. But when i try to get the video duration it

I'm a beginner in Android programming.

I'm writing an application to list all video file in a folder and display information of all videos in the folder. But when i try to get the video duration it return null and i can't find the way to get it.

Any one can help me?

Below is my code:

Uri uri = Uri开发者_StackOverflow中文版.parse("content://media/external/video/media/9");
Cursor cursor = MediaStore.Video.query(res, data.getData(), new String[]{MediaStore.Video.VideoColumns.DURATION});
if(cursor.moveToFirst()) {
    String duration = cursor.getString(0);
    System.out.println("Duration: " + duration);
}


Use MediaMetadataRetriever to retrieve media specific data:

MediaMetadataRetriever retriever = new MediaMetadataRetriever();
//use one of overloaded setDataSource() functions to set your data source
retriever.setDataSource(context, Uri.fromFile(videoFile));
String time = retriever.extractMetadata(MediaMetadataRetriever.METADATA_KEY_DURATION);
long timeInMillisec = Long.parseLong(time );

retriever.release()


I think the easiest way is:

MediaPlayer mp = MediaPlayer.create(this, Uri.parse(uriOfFile));
int duration = mp.getDuration();
mp.release();
/*convert millis to appropriate time*/
return String.format("%d min, %d sec", 
        TimeUnit.MILLISECONDS.toMinutes(duration),
        TimeUnit.MILLISECONDS.toSeconds(duration) - 
        TimeUnit.MINUTES.toSeconds(TimeUnit.MILLISECONDS.toMinutes(duration))
    );


Kotlin Extension Solution

Here is the way to fetch media file duration in Kotlin

fun File.getMediaDuration(context: Context): Long {
    if (!exists()) return 0
    val retriever = MediaMetadataRetriever()
    retriever.setDataSource(context, Uri.parse(absolutePath))
    val duration = retriever.extractMetadata(METADATA_KEY_DURATION)
    retriever.release()

    return duration.toLongOrNull() ?: 0
}

If you want to make it safer (Uri.parse could throw exception), use this combination. The others are generally just useful as well :)

fun String?.asUri(): Uri? {
    try {
        return Uri.parse(this)
    } catch (e: Exception) {
    }
    return null
}

val File.uri get() = this.absolutePath.asUri()

fun File.getMediaDuration(context: Context): Long {
    if (!exists()) return 0
    val retriever = MediaMetadataRetriever()
    retriever.setDataSource(context, uri)
    val duration = retriever.extractMetadata(METADATA_KEY_DURATION)
    retriever.release()

    return duration.toLongOrNull() ?: 0
}

Not necessary here, but generally helpful additional Uri extensions

val Uri?.exists get() = if (this == null) false else asFile().exists()

fun Uri.asFile(): File = File(toString())


I don't think you post your URI into the mediastore video query

Uri uri = Uri.parse("content://media/external/video/media/9");

Cursor cursor = MediaStore.Video.query(res, data.getData(), new String[]{MediaStore.Video.VideoColumns.DURATION});


MediaMetadataRetriever retriever = new MediaMetadataRetriever();
retriever.setDataSource(uriOfFile);
long duration = Long.parseLong(retriever.extractMetadata(MediaMetadataRetriever.METADATA_KEY_DURATION))
int width = Integer.valueOf(retriever.extractMetadata(MediaMetadataRetriever.METADATA_KEY_VIDEO_WIDTH));
int height = Integer.valueOf(retriever.extractMetadata(MediaMetadataRetriever.METADATA_KEY_VIDEO_HEIGHT));
retriever.release();


public static long getDurationOfSound(Context context, Object soundFile)
  {
    int millis = 0;
    MediaPlayer mp = new MediaPlayer();
    try
    {
      Class<? extends Object> currentArgClass = soundFile.getClass();
      if(currentArgClass == Integer.class)
      {
        AssetFileDescriptor afd = context.getResources().openRawResourceFd((Integer)soundFile);
            mp.setDataSource(afd.getFileDescriptor(), afd.getStartOffset(), afd.getLength());
        afd.close();
      }
      else if(currentArgClass == String.class)
      {
        mp.setDataSource((String)soundFile);
      }
      else if(currentArgClass == File.class)
      {
        mp.setDataSource(((File)soundFile).getAbsolutePath());
      }
      mp.prepare();
      millis = mp.getDuration();
    }
    catch(Exception e)
    {
    //  Logger.e(e.toString());
    }
    finally
    {
      mp.release();
      mp = null;
    }
    return millis;
  }


MediaPlayer mpl = MediaPlayer.create(this,R.raw.videoFile);   
int si = mpl.getDuration();

This will give the duration of the video file


object MediaHelper {

    const val PICK_IMAGE_FROM_DEVICE = 100
    const val PICK_MEDIA_FROM_DEVICE = 101

    fun openPhoneGalleryForImage(fragment: Fragment){
        Intent(Intent.ACTION_GET_CONTENT).run {
            this.type = "image/*"
            fragment.startActivityForResult(this, PICK_IMAGE_FROM_DEVICE)
        }
    }

    fun openPhoneGalleryForMedia(fragment: Fragment){
        Intent(Intent.ACTION_GET_CONTENT).run {
            this.type = "*/*"
            fragment.startActivityForResult(this, PICK_MEDIA_FROM_DEVICE)
        }
    }

    fun getMediaType(context: Context, source: Uri): MediaType? {
        val mediaTypeRaw = context.contentResolver.getType(source)
        if (mediaTypeRaw?.startsWith("image") == true)
            return MediaType.Image
        if (mediaTypeRaw?.startsWith("video") == true)
            return MediaType.Video
        return null
    }

    fun getVideoDuration(context: Context, source: Uri): Long? {
        if (getMediaType(context, source) != MediaType.Video) 
            return null
        val retriever = MediaMetadataRetriever()
        retriever.setDataSource(context, source)
        val duration = retriever.extractMetadata(METADATA_KEY_DURATION)
        retriever.release()
        return duration?.toLongOrNull()
    }
}

enum class MediaType {
    Image {
        override val mimeType: String = "image/jpeg"
        override val fileExtension: String = ".jpg"
    },
    Video {
        override val mimeType: String = "video/mp4"
        override val fileExtension: String = ".mp4"
    };

    abstract val mimeType: String
    abstract val fileExtension: String
}


fun File.getVideoDuration(context: Context): Long {
    context.contentResolver.query(toUri(), arrayOf(MediaStore.Video.Media.DURATION), null, null, null)?.use {
        val durationColumn = it.getColumnIndexOrThrow(MediaStore.Video.Media.DURATION)
        it.moveToFirst()
        return it.getLong(durationColumn)
    }
    return 0
0

精彩评论

暂无评论...
验证码 换一张
取 消