问题
I use the code below to play a video from my SD-Card using Video View of Android. I placed a video file named Video.mp4 in the external storage root directory. But when starting my App on my Smartphone and switching to my video activity with the code below for Video.java I see a notification with an OK button saying that the video can not be played. (German: "Video kann nicht wiedergegeben werden.")
Is it a missing permission in my AndroidManifest.xml?
Thanks in advance for any hints and help.
package com.noureddine_ouertani.www.wocelli50;
import android.net.Uri;
import android.os.Bundle;
import android.os.Environment;
import android.support.v7.app.AppCompatActivity;
import android.widget.MediaController;
import android.widget.VideoView;
public class Video extends AppCompatActivity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_video);
getSupportActionBar().setHomeButtonEnabled(true);
getSupportActionBar().setDisplayHomeAsUpEnabled(true);
VideoView v = (VideoView) findViewById(R.id.videoView);
v.setVideoURI(Uri.parse(Environment.getExternalStorageDirectory().getPath() + "/Video.mp4"));
//Set media controller buttons
v.setMediaController(new MediaController(this));
v.requestFocus();
v.start(); //start Playback
}
}
EDIT: @Alexandre Martin: Thanks for your answer. I have no general problem with embedding videos in my app. When I create a raw folder and put the video testvideo.mp4 in it then replace
v.setVideoURI(Uri.parse(Environment.getExternalStorageDirectory().getPath() + "/Video.mp4"));
with
v.setVideoURI(Uri.parse("android.resource://com.noureddine_ouertani.www.wocelli50/"+ R.raw.testvideo));
in my code, everything works fine and I see my video playing in my app. Remark: I had to rename Video.mp4 to testvideo.mp4 because capital letters are not allowed for videos called from the raw folder. My problem is just to get the path to the video on my SD-card.
@Lonnie Zamora: Thanks for your answer. It doesn´t seem to be a format or coding problem. testvideo.mp4 is just Video.mp4 renamed and placed in my raw folder. And it plays fine with the code below:
package com.noureddine_ouertani.www.wocelli50;
import android.net.Uri;
import android.os.Bundle;
import android.support.v7.app.AppCompatActivity;
import android.widget.MediaController;
import android.widget.VideoView;
public class Video extends AppCompatActivity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_video);
getSupportActionBar().setHomeButtonEnabled(true);
getSupportActionBar().setDisplayHomeAsUpEnabled(true);
VideoView v = (VideoView) findViewById(R.id.videoView);
v.setVideoURI(Uri.parse("android.resource://com.noureddine_ouertani.www.wocelli50/"+ R.raw.testvideo));
//Set media controller buttons
v.setMediaController(new MediaController(this));
v.requestFocus();
v.start(); //start Playback
}
}
@CommonsWare: Thanks for your answer. I tried your suggestion but it didn´t solve the problem.
Best regards,
EDIT 2: @CommonsWare It doesn´t seem to be a missing permission or a missing permission request issue. I implemented the following runtime permission logic and see "Video is playing. No permissioon request was needed." which means to me that (Manifest.permission.READ_EXTERNAL_STORAGE == PackageManager.PERMISSION_GRANTED) was true
package com.noureddine_ouertani.www.wocelli50;
import android.Manifest;
import android.content.pm.PackageManager;
import android.net.Uri;
import android.os.Bundle;
import android.os.Environment;
import android.support.v4.app.ActivityCompat;
import android.support.v4.content.ContextCompat;
import android.support.v7.app.AppCompatActivity;
import android.widget.MediaController;
import android.widget.Toast;
import android.widget.VideoView;
public class Video extends AppCompatActivity {
final int REQUEST_READ_EXTERNAL_STORAGE = 1;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_video);
if (ContextCompat.checkSelfPermission(this, Manifest.permission.READ_EXTERNAL_STORAGE) != PackageManager.PERMISSION_GRANTED) {
// Should we show an explanation?
if (ActivityCompat.shouldShowRequestPermissionRationale(this, Manifest.permission.READ_EXTERNAL_STORAGE)) {
Toast.makeText(getApplicationContext(), "Show explanation for requesting the permission to read the SD-card.", Toast.LENGTH_SHORT).show();
// Show an expanation to the user *asynchronously* -- don't block
// this thread waiting for the user's response! After the user
// sees the explanation, try again to request the permission.
} else {
// No explanation needed, we can request the permission.
Toast.makeText(getApplicationContext(), "No explanation needed, we can request the permission.", Toast.LENGTH_SHORT).show();
ActivityCompat.requestPermissions(this, new String[]{Manifest.permission.READ_EXTERNAL_STORAGE}, REQUEST_READ_EXTERNAL_STORAGE);
// MY_PERMISSIONS_REQUEST_READ_CONTACTS is an
// app-defined int constant. The callback method gets the
// result of the request.
}
} else {
playmyvideo();
Toast.makeText(getApplicationContext(), "Video is playing. No permissioon request was needed.", Toast.LENGTH_SHORT).show();
}
}
@Override
public void onRequestPermissionsResult(int requestCode, String permissions[], int[] grantResults) {
switch (requestCode) {
case REQUEST_READ_EXTERNAL_STORAGE: {
// If request is cancelled, the result arrays are empty.
if (grantResults.length > 0 && grantResults[0] == PackageManager.PERMISSION_GRANTED) {
playmyvideo();
Toast.makeText(getApplicationContext(), "Video is playing after permissioon was granted.", Toast.LENGTH_SHORT).show();
} else {
Toast.makeText(getApplicationContext(), "permission denied,Disable the functionality that depends on this permission.", Toast.LENGTH_SHORT).show();
// permission denied, boo! Disable the
// functionality that depends on this permission.
}
return;
}
// other 'case' lines to check for other
// permissions this app might request
}
}
public void playmyvideo(){
getSupportActionBar().setHomeButtonEnabled(true);
getSupportActionBar().setDisplayHomeAsUpEnabled(true);
VideoView v = (VideoView) findViewById(R.id.videoView);
v.setVideoURI(Uri.parse(Environment.getExternalStorageDirectory().getPath() + "/testvideo.mp4"));
//v.setVideoURI(Uri.parse("android.resource://com.noureddine_ouertani.www.wocelli50/"+ R.raw.testvideo));
v.setMediaController(new MediaController(this));
v.requestFocus();
v.start(); //start Playback
}
}
回答1:
Replace
Uri.parse(Environment.getExternalStorageDirectory().getPath() + "/Video.mp4")
(which is invalid, since it lacks a scheme)
with:
Uri.fromFile(new File(Environment.getExternalStorageDirectory(), "Video.mp4"))
回答2:
SOLUTION @all Solution to access the external SD-card:
v.setVideoURI(Uri.parse("/storage/sdcard1/testvideo.mp4"));
instead of
v.setVideoURI(Uri.parse(Environment.getExternalStorageDirectory().getPath() + "/testvideo.mp4"));
REASON:
Environment.getExternalStorageDirectory().getPath() == "/storage/emulated/0"
Environment.getExternalStorageDirectory().getPath() delivers the path to an internal storage chip on my smartphone (HUAWEI P8) that is mounted like an SD-card but is not the external SD-card though.
来源:https://stackoverflow.com/questions/37816382/app-can%c2%b4t-play-a-video-from-the-sd-card-despite-the-fact-that-the-code-looks-fin