Android Mediaplayer: problème de setDataSource pour le fichier multimédia téléchargé

j'ai une application qui va enregistrer et lire des fichiers audio. Certains fichiers audio sont téléchargés à l'aide de téléchargements http standard simples en utilisant httpclient. Ça a fonctionné comme un charme pendant longtemps. Maintenant, tout d'un coup, je ne peut pas lire les fichiers téléchargés. Il échoue avec cette pile. Je stocke les fichiers sur la carte SDCard et je fais l'expérience du problème à la fois sur un combiné et un périphérique USB connecté.

j'ai vérifié que le fichier téléchargé est cool sur le serveur, et je peux jouer sans aucun problème.

ce sont les extraits de code que j'utilise ( je sais que recordingFile est un chemin valide pour le fichier).

    // inside the activity class
    private void playRecording() throws IOException{
        File recordingFile = new File(recordingFileName);
        FileInputStream recordingInputStream = new FileInputStream(recordingFile); 
        audioMediaPlayer.playAudio(recordingInputStream);
    }

voici le code du lecteur multimédia:

    // inside my media player class which handles the recordings
    public void playAudio(FileInputStream audioInputStream) throws IOException {
        mediaPlayer.reset();
        mediaPlayer.setDataSource(audioInputStream.getFD());
        mediaPlayer.prepare();
        mediaPlayer.start();
}

Voici l'exception:

E/MediaPlayerService(  555): offset error
E/MediaPlayer(  786): Unable to to create media player
W/System.err(  786): java.io.IOException: setDataSourceFD failed.: status=0x80000000
W/System.err(  786):    at android.media.MediaPlayer.setDataSource(Native Method)
W/System.err(  786):    at android.media.MediaPlayer.setDataSource(MediaPlayer.java:632)
W/System.err(  786):    at net.xxx.xxx.AudioMediaPlayer.playAudio(AudioMediaPlayer.java:69)
W/System.err(  786):    at net.xxx.xxx.Downloads.playRecording(Downloads.java:299)
W/System.err(  786):    at net.xxx.xxx.Downloads.access(Downloads.java:294)
W/System.err(  786):    at net.xxx.xxx.Downloads.onClick(Downloads.java:135)

j'ai essayé de trouver une réponse à l'erreur de décalage, mais pas vraiment claire ce que cette question pourrait être.

PS j'ai télécharger le fichier avec ce code:

    public FileOutputStream executeHttpGet(FileOutputStream fileOutputStream) throws ClientProtocolException, IOException{
        try {     
            // Execute HTTP Post Request  
            httpResponse = httpClient.execute(httpPost, localContext);
            int status = httpResponse.getStatusLine().getStatusCode();

            // we assume that the response body contains the error message
            if (status != HttpStatus.SC_OK) {
                ByteArrayOutputStream ostream = new ByteArrayOutputStream();
                httpResponse.getEntity().writeTo(ostream);
                fileOutputStream = null;
            } else {
                InputStream content = httpResponse.getEntity().getContent();

                byte[] buffer = new byte[1024];
                int len = 0;
                while ( (len = content.read(buffer)) > 0 ) {
                    fileOutputStream.write(buffer,0, len);
                }
                fileOutputStream.close();
                content.close(); // this will also close the connection
            }

        } catch (ClientProtocolException e1) {  
            // TODO Auto-generated catch block 
            e1.printStackTrace();
            fileOutputStream = null;
        } catch (IOException e2) {  
            // TODO Auto-generated catch block  
            e2.printStackTrace();
            fileOutputStream = null;
        }
        return fileOutputStream;
    }
13
demandé sur Erik 2010-05-09 19:59:29

2 réponses

j'ai résolu mon problème propres. Comme je l'ai dit mon commentaire au-dessus de la solution était ceci:

quand j'ai refactorisé une partie du code, j'ai fait une typographie sur un code de hachage que j'utilise pour autoriser les téléchargements et non. Malheureusement, je n'ai pas eu la bonne prise quand j'ai téléchargé le fichier forçant le fichier à être vide. Fondamentalement, j'envoie un mauvais en-tête de requête si vous essayez de récupérer un fichier sans un code d'activation approprié.

le coupable était ici:

        if (status != HttpStatus.SC_OK) {
            ByteArrayOutputStream ostream = new ByteArrayOutputStream();
            httpResponse.getEntity().writeTo(ostream);
            fileOutputStream = null;
        } else {
            InputStream content = httpResponse.getEntity().getContent();

            byte[] buffer = new byte[1024];
            int len = 0;
            while ( (len = content.read(buffer)) > 0 ) {
                fileOutputStream.write(buffer,0, len);
            }
            fileOutputStream.close();
           content.close(); // this will also close the connection
    }

Pour les cas où le statut le code est revenu comme mauvais (c'est-à-dire mauvais en-tête de requête pour les accès bloqués). Ce que j'ai manqué était de capturer le cas d'un pointeur null là et qui a causé une entrée SQLite à être mis à jour en prétendant à l'application que le téléchargement a été réussi mais il n'était pas.

leçon apprise: Toujours mettre les vérifications nulles pour ces cas, même pour les prototypes. : -)

3
répondu Erik 2010-05-09 18:58:09

tout d'Abord, assurez-vous que votre appareil n'est pas monté. Android ou le PC hôte peuvent accéder à la carte SD, mais pas les deux simultanément.

deuxièmement, il n'est pas clair pourquoi vous utilisez un FileInputStream et getFD(). Il suffit de passer le chemin vers le fichier sur la carte SD vers le MediaPlayer(e.g.,new File(Environment.getExternalStorageDirectory(), "yourfile.mp3")) et laissez le joueur ouvrir le fichier.

1
répondu CommonsWare 2010-05-09 17:18:41