2015-07-07 3 views
0

Я использую библиотеку libstreaming и пытаюсь передать RtspClient и API MedicaCodec. Я тестирую галактику s3 с помощью android 4.4. Проблема в том, что независимо от того, использую ли я буфер для буфера или поверхности для буфера, я получаю эту ошибку: java.lang.IllegalStateException: The decoder input buffer is not big enough (nal=181322, capacity=65536). и java.lang.RuntimeException: The decoder did not decode anything. MediaRecorder api работает отлично, но качество настолько низкое. Я не могу сказать, есть ли у меня кошка или собака впереди меня.android libstreaming with MedicaCodec Размер буфера APi не достаточно большой

Вот мой код:

import android.support.v4.app.Fragment; 
import android.os.Bundle; 
import android.view.LayoutInflater; 
import android.view.View; 
import android.view.ViewGroup; 
import android.view.SurfaceHolder; 
import net.majorkernelpanic.streaming.Session; 
import net.majorkernelpanic.streaming.SessionBuilder; 
import net.majorkernelpanic.streaming.audio.AudioQuality; 
import net.majorkernelpanic.streaming.gl.SurfaceView; 
import net.majorkernelpanic.streaming.rtsp.RtspClient; 
import net.majorkernelpanic.streaming.video.VideoQuality; 
import net.majorkernelpanic.streaming.MediaStream; 
import java.util.regex.Matcher; 
import java.util.regex.Pattern; 

/** 
* A placeholder fragment containing a simple view. 
*/ 
public class MainActivityFragment extends Fragment implements RtspClient.Callback, 
     Session.Callback, SurfaceHolder.Callback { 

    // surfaceview 
    private static SurfaceView mSurfaceView; 

    // Rtsp session 
    private Session mSession; 
    private static RtspClient mClient; 

    public MainActivityFragment() { 
    } 

    @Override 
    public View onCreateView(LayoutInflater inflater, ViewGroup container, 
          Bundle savedInstanceState) { 

     View view = inflater.inflate(R.layout.fragment_main, container, false); 

     mSurfaceView = (SurfaceView) view.findViewById(R.id.surface); 

     // Configures the SessionBuilder 
     mSession = SessionBuilder.getInstance() 
       .setContext(getActivity().getApplicationContext()) 
       .setAudioEncoder(SessionBuilder.AUDIO_AAC) 
       .setAudioQuality(new AudioQuality(8000, 16000)) 
       .setVideoEncoder(SessionBuilder.VIDEO_H264) 
       .setVideoQuality(new VideoQuality(960, 720, 20, 500000)) 
       .setSurfaceView(mSurfaceView) 
       .setPreviewOrientation(0) 
       .setCallback(this) 
       .build(); 

     // Configures the RTSP client 
     mClient = new RtspClient(); 
     String ip, port, path; 

     // We parse the URI written in the Editext 
     Pattern uri = Pattern.compile("rtsp://(.+):(\\d+)/(.+)"); 
     Matcher m = uri.matcher(AppConfig.STREAM_URL); 
     m.find(); 
     ip = m.group(1); 
     port = m.group(2); 
     path = m.group(3); 

     mClient.setCredentials(AppConfig.PUBLISHER_USERNAME, 
       AppConfig.PUBLISHER_PASSWORD); 
     mClient.setServerAddress(ip, Integer.parseInt(port)); 
     mClient.setStreamPath("/" + path); 
     mClient.setSession(mSession); 
     mClient.setCallback(this); 

     // Use this to force streaming with the MediaRecorder API 
     mSession.getVideoTrack().setStreamingMethod(MediaStream.MODE_MEDIACODEC_API_2); 

     mSurfaceView.getHolder().addCallback(this); 

     return view; 
    } 

    @Override 
    public void onDestroy() { 
     super.onDestroy(); 
     mClient.release(); 
     mSession.release(); 
     mSurfaceView.getHolder().removeCallback(this); 
    } 

    @Override 
    public void onRtspUpdate(int message, Exception exception) { 
     switch (message) { 
      case RtspClient.ERROR_CONNECTION_FAILED: 
      case RtspClient.ERROR_WRONG_CREDENTIALS: 
       System.out.println(exception.getMessage()); 
       exception.printStackTrace(); 
       break; 
     } 
    } 

    @Override 
    public void onSessionError(int reason, int streamType, Exception e) { 
     switch (reason) { 
      case Session.ERROR_CAMERA_ALREADY_IN_USE: 
       break; 
      case Session.ERROR_CAMERA_HAS_NO_FLASH: 
       break; 
      case Session.ERROR_INVALID_SURFACE: 
       break; 
      case Session.ERROR_STORAGE_NOT_READY: 
       break; 
      case Session.ERROR_CONFIGURATION_NOT_SUPPORTED: 
       VideoQuality quality = mSession.getVideoTrack().getVideoQuality(); 
       System.out.println("APPERROR: The following settings are not supported on this phone: " + 
         quality.toString()+" "+ 
         "("+e.getMessage()+")"); 
       e.printStackTrace(); 
       break; 
      case Session.ERROR_OTHER: 
       break; 
     } 

     if (e != null) { 
      System.out.println(e.getMessage()); 
      e.printStackTrace(); 
     } 
    } 

    @Override 
    public void onPreviewStarted() { 
     mClient.startStream(); 
    } 

    @Override 
    public void onSessionConfigured() { 
    } 

    @Override 
    public void onSessionStopped() { 
    } 

    @Override 
    public void surfaceChanged(SurfaceHolder arg0, int arg1, int arg2, int arg3) { 
    } 

    @Override 
    public void surfaceCreated(SurfaceHolder holder) { 
     mSession.startPreview(); 
    } 

    @Override 
    public void surfaceDestroyed(SurfaceHolder holder) { 
     mClient.stopStream(); 
    } 

    @Override 
    public void onBitrateUpdate(long bitrate) { 
    } 

    @Override 
    public void onSessionStarted() { 
    } 
} 

Пожалуйста, помогите! Я в отчаянии!

+0

Можете ли вы включить полное исключение? Было бы полезно узнать, откуда он брошен. – fadden

ответ

1

Запрос на получение дополнительных данных пришел поздно, но я нашел решение. Как и многие сообщения, мне пришлось изменить библиотеку libstreaming. Я изменил:

public MediaStream() { 
     // code change 
     mRequestedMode = MODE_MEDIACODEC_API_2; 
     mMode = MODE_MEDIACODEC_API_2; 
    } 
public synchronized void start() throws IllegalStateException, IOException { 

     if (mDestination==null) 
      throw new IllegalStateException("No destination ip address set for the stream !"); 

     if (mRtpPort<=0 || mRtcpPort<=0) 
      throw new IllegalStateException("No destination ports set for the stream !"); 

     mPacketizer.setTimeToLive(mTTL); 

     // code change 
     encodeWithMediaCodec(); 
} 

И пришлось вызвать на поверхность методом mSession.getVideoTrack().setStreamingMethod(MediaStream.MODE_MEDIACODEC_API_2); И пришлось ограничить мой конфиг для этих значений: http://developer.android.com/guide/appendix/media-formats.html#recommendations или врежется или зеленый экран или любой другой.