Android: Spielen Sie ein Asset-Sound Mit WebView
Ich versuche zu spielen einen sound aus dem Ordner "assets", wenn ein Benutzer klickt auf einen tag auf meine Anwendung WebView. Ich fand, dass ich nutzen kann, eine neue Klasse, die sich WebViewClient zu erkennen, die Verlängerung von einem link und wenn es eine mp3-Datei die Sie spielen können, es über die Standard-Audio-Player. Aber ich will es spielen innerhalb der Aktivität ohne starten einer neuen Aktivität.
Ich habe folgende links als Referenz:
Sound in Webview
und Fehler beim erstellen MediaPlayer mit Uri oder eine Datei in assets
Aber es hat nicht funktioniert.
Ich habe versucht, mithilfe des folgenden codes tun:
package com.rangga.test.webview.sound;
import android.content.Intent;
import android.content.res.AssetFileDescriptor;
import android.media.MediaPlayer;
import android.net.Uri;
import android.webkit.WebView;
import android.webkit.WebViewClient;
public class MyWebViewClient extends WebViewClient{
public MediaPlayer mp;
@Override
public boolean shouldOverrideUrlLoading(WebView view, String url){
if(url.endsWith(".mp3")){
mp = new MediaPlayer();
AssetFileDescriptor afd = getAssets().openFd(url);
mp.setDataSource(afd.getFileDescriptor());
mp.start();
return true;
}else{
return true;
}
}
}
Bekomme ich eine Undefinierte Methode, Fehler auf der getAssets(), habe ich versucht Googleing, und es sagt etwas über die übergabe eines Kontext. Ich bin sehr neu in Android und der objektorientierten Programmierung, so Frage ich mich, ob das der richtige Weg, es zu tun, und wenn es eine einfache Erklärung, was ein Kontext ist. Danke.
Unten sind meine kompletten codes:
MainActivity.class
package com.rangga.test.webview.sound;
import android.app.Activity;
import android.os.Bundle;
import android.webkit.WebView;
public class MainActivity extends Activity {
WebView webMain;
/** Called when the activity is first created. */
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
webMain = (WebView) findViewById(R.id.webMain);
webMain.loadUrl("file:///android_asset/webpages/test.html");
webMain.setWebViewClient(new MyWebViewClient());
}
}
BEARBEITEN
Also den codes funktioniert Dank https://stackoverflow.com/users/488241/squonk aber jetzt tritt ein weiteres problem auf, ich aktualisiert die MyWebViewClient in die folgenden:
package com.rangga.test.webview.sound;
import java.io.IOException;
import android.content.Context;
import android.content.res.AssetFileDescriptor;
import android.media.MediaPlayer;
import android.webkit.WebView;
import android.webkit.WebViewClient;
public class MyWebViewClient extends WebViewClient{
public MediaPlayer mp;
private Context context = null;
public MyWebViewClient(Context c){
this.context = c;
}
@Override
public boolean shouldOverrideUrlLoading(WebView view, String url){
if(url.endsWith(".mp3")){
mp = new MediaPlayer();
try {
AssetFileDescriptor afd = context.getAssets().openFd(url);
mp.setDataSource(afd.getFileDescriptor(), afd.getStartOffset(), afd.getLength());
afd.close();
mp.prepare();
mp.start();
} catch (IllegalArgumentException e) {
//TODO Auto-generated catch block
e.printStackTrace();
} catch (IllegalStateException e) {
//TODO Auto-generated catch block
e.printStackTrace();
} catch (IOException e) {
//TODO Auto-generated catch block
e.printStackTrace();
}
return true;
}else{
return true;
}
}
}
Aber ich bekomme eine java.io.FileNotFoundException, der Weg scheint Recht obwohl. Ich habe 2 mp3-Dateien in assets/Webseiten/sounds/1.mp3-und Vermögenswerte/webpages/1.mp3 und verwendet das folgende html-codes, um es zu testen:
<html>
<head>
<title>Test Audio</title>
</head>
<body>
<a href="file:///android_asset/webpages/sounds/1.mp3">File Asset</a><br/>
<a href="1.mp3">Same Folder</a>
</body>
</html>
Aber ich bekomme die folgende Fehlermeldung auf LogCat:
06-11 06:20:37.955: W/System.err(377): java.io.FileNotFoundException: file:///android_asset/webpages/1.mp3
06-11 06:20:37.966: W/System.err(377): at android.content.res.AssetManager.openAssetFd(Native Method)
06-11 06:20:37.974: W/System.err(377): at android.content.res.AssetManager.openFd(AssetManager.java:314)
06-11 06:20:37.974: W/System.err(377): at com.rangga.test.webview.sound.MyWebViewClient.shouldOverrideUrlLoading(MyWebViewClient.java:30)
06-11 06:20:37.985: W/System.err(377): at android.webkit.CallbackProxy.uiOverrideUrlLoading(CallbackProxy.java:193)
06-11 06:20:38.000: W/System.err(377): at android.webkit.CallbackProxy.handleMessage(CallbackProxy.java:304)
06-11 06:20:38.005: W/System.err(377): at android.os.Handler.dispatchMessage(Handler.java:99)
06-11 06:20:38.005: W/System.err(377): at android.os.Looper.loop(Looper.java:123)
06-11 06:20:38.014: W/System.err(377): at android.app.ActivityThread.main(ActivityThread.java:4363)
06-11 06:20:38.014: W/System.err(377): at java.lang.reflect.Method.invokeNative(Native Method)
06-11 06:20:38.024: W/System.err(377): at java.lang.reflect.Method.invoke(Method.java:521)
06-11 06:20:38.024: W/System.err(377): at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:860)
06-11 06:20:38.024: W/System.err(377): at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:618)
06-11 06:20:38.054: W/System.err(377): at dalvik.system.NativeStart.main(Native Method)
Gibt es etwas falsch mit der Art und Weise, rief ich die Datei? Danke schon mal.
GELÖST
Thx an squonk die Anregungen, ich habe versucht, die folgenden codes zu machen, damit es funktioniert und es funktionierte gut, danke, squonk!
package com.rangga.test.webview.sound;
import java.io.IOException;
import android.content.Context;
import android.content.res.AssetFileDescriptor;
import android.media.MediaPlayer;
import android.util.Log;
import android.webkit.WebView;
import android.webkit.WebViewClient;
public class MyWebViewClient extends WebViewClient{
public MediaPlayer mp;
private Context context = null;
public MyWebViewClient(Context c){
this.context = c;
mp = new MediaPlayer();
}
@Override
public boolean shouldOverrideUrlLoading(WebView view, String url){
if(url.endsWith(".mp3")){
url = url.replace("file:///android_asset/webpages/", "");
Log.i("MyWebViewClient", url);
try {
AssetFileDescriptor afd = context.getAssets().openFd(url);
mp = new MediaPlayer();
mp.setDataSource(afd.getFileDescriptor(), afd.getStartOffset(), afd.getLength());
afd.close();
mp.prepare();
mp.start();
} catch (IllegalArgumentException e) {
//TODO Auto-generated catch block
e.printStackTrace();
} catch (IllegalStateException e) {
//TODO Auto-generated catch block
e.printStackTrace();
} catch (IOException e) {
//TODO Auto-generated catch block
e.printStackTrace();
}
return true;
}else{
return true;
}
}
}
Und das html, um es zu testen:
<html>
<head>
<title>Test Audio</title>
</head>
<body>
<a href="webpages/1.mp3">File Asset</a><br/>
</body>
</html>
Aber ich habe eine Fehlermeldung erhalten, wenn ich immer wieder darauf klicken, aber das ist eine andere Frage 😀
Wie macht man schließen eine Frage? >.<
Du musst angemeldet sein, um einen Kommentar abzugeben.
Wo Sie erklären Ihre
MediaPLayer
imMyWebViewClient
fügen Sie die folgenden...Dann fügen Sie einen Konstruktor hinzu
MyWebViewClient
wie folgt...Dann in
shouldOverrideUrlLoading(...)
erhalten Sie Ihre Vermögenswerte wie folgt...In Ihrem
MainActivity
legen Sie dieWebViewClient
durch die übergabethis
(das ist die AktivitätContext
) wie folgt...Auch sollten Sie Sie wieder
false
ausshouldOverrideUrlLoading(...)
wenn die url endet mit".mp3' - dies zeigt IhreWebView
ist, Dinge zu behandeln und die "host" - Anwendung nicht starten sollte, eine Instanz der Aktie web-browser.EDIT: Für das Abspielen von audio-Dateien aus dem assets Verzeichnis, müssen Sie die Datenquelle anders - siehe die akzeptierte Antwort auf play-audio-Datei-aus-der-assets-Verzeichnis.
Außerdem sollten Sie nennen
mp.prepare()
vor dem Aufrufmp.start()
.1.mp3
direkt in der Wurzel des/res/assets
Verzeichnis wird dann die zweite URL (<a href="1.mp3">Same Folder</a>
) funktionieren sollte. Vielleicht starten Sie eine neue Frage verknüpfen die Frage, die ich verlinkte in meinem EDIT. Es ist nicht etwas, was ich getan habe, von einerWebView
vor, sorry.url
parameter übergeben wird inshouldOverrideUrlLoading
nur um zu überprüfen, dass es aussieht, wie Sie es erwarten. Auch beim erstellenafd
in dieser Methode nur versuchen...openFd("1.mp3");
als test. Andere als die, eine neue Frage mit neuen Augen zu betrachten, es könnte helfen. Viel Glück.