2011-12-15 24 views
12

पर एएसी के लिए एनकोड वैव आप एएसी को सीधे स्ट्रीम रिकॉर्ड करने के लिए MediaRecorder का उपयोग कर सकते हैं, लेकिन मौजूदा पीसीएम/डब्ल्यूएवी फ़ाइल को एएसी में एन्कोड करने का कोई तरीका नहीं लगता है। एएसी को एन्कोड करने की क्षमता एंड्रॉइड में मूल रूप से मौजूद है और मैं इसका उपयोग करना चाहूंगा। क्या पूर्व-मौजूदा ऑडियो फ़ाइल के साथ ऐसा करने का कोई तरीका नहीं है?एंड्रॉइड

उत्तर

1

आप मूल कोड के साथ अपने हाथ गंदे प्राप्त कर सकते हैं और ढांचे में डीकोडर्स के लिए आईओएमएक्स सी ++ इंटरफ़ेस का उपयोग कर सकते हैं। लेकिन यह संवेदनशील है और अन्य फोन और एंड्रॉइड स्वादों पर काम नहीं करेगा।

एक और विकल्प पोर्टफार्म की तरह एक ओपनसोर्स एएसी एन्कोडर पोर्ट करता है और जेनी पर इसके ऊपर एक ऐप लिखता है। उसी वास्तुकला वाले फोन के साथ कम से कम काम करेगा (आर्म-9, कॉर्टेक्स ए 8 ..)।

जेबी में आपकी इच्छाओं को पूरा करने के लिए मीडियाकोडक है। लेकिन जेबी के साथ उपकरणों के लिए समस्या आधार कुछ और समय के लिए दुबला होगा।

http://developer.android.com/about/versions/android-4.1.html#Multimedia

+0

क्या MediaCodec का उपयोग करने का कोई कामकाजी उदाहरण है? – Taras

3

इस खूबसूरत (और पूरी तरह से काम कर रहे) उदाहरण देखें: Mp4ParserSample

वर्ग (पंक्तियों 335-442) के अंतिम भाग में देखो, convert Runnable वस्तु बस नौकरी करता है! आपको उस कोड को अपनी आवश्यकताओं के अनुसार आकार देना होगा, इनपुट और आउटपुट फ़ाइल पथ और रूपांतरण पैरामीटर समायोजित करना होगा (नमूना दर, बिट दर, आदि)।

public static final String AUDIO_RECORDING_FILE_NAME = "audio_Capturing-190814-034638.422.wav"; // Input PCM file 
public static final String COMPRESSED_AUDIO_FILE_NAME = "convertedmp4.m4a"; // Output MP4/M4A file 
public static final String COMPRESSED_AUDIO_FILE_MIME_TYPE = "audio/mp4a-latm"; 
public static final int COMPRESSED_AUDIO_FILE_BIT_RATE = 64000; // 64kbps 
public static final int SAMPLING_RATE = 48000; 
public static final int BUFFER_SIZE = 48000; 
public static final int CODEC_TIMEOUT_IN_MS = 5000; 
String LOGTAG = "CONVERT AUDIO"; 
Runnable convert = new Runnable() { 
    @TargetApi(Build.VERSION_CODES.JELLY_BEAN_MR2) 
    @Override 
    public void run() { 
     android.os.Process.setThreadPriority(android.os.Process.THREAD_PRIORITY_BACKGROUND); 
     try { 
      String filePath = Environment.getExternalStorageDirectory().getPath() + "/" + AUDIO_RECORDING_FILE_NAME; 
      File inputFile = new File(filePath); 
      FileInputStream fis = new FileInputStream(inputFile); 

      File outputFile = new File(Environment.getExternalStorageDirectory().getAbsolutePath() + "/" + COMPRESSED_AUDIO_FILE_NAME); 
      if (outputFile.exists()) outputFile.delete(); 

      MediaMuxer mux = new MediaMuxer(outputFile.getAbsolutePath(), MediaMuxer.OutputFormat.MUXER_OUTPUT_MPEG_4); 

      MediaFormat outputFormat = MediaFormat.createAudioFormat(COMPRESSED_AUDIO_FILE_MIME_TYPE,SAMPLING_RATE, 1); 
      outputFormat.setInteger(MediaFormat.KEY_AAC_PROFILE, MediaCodecInfo.CodecProfileLevel.AACObjectLC); 
      outputFormat.setInteger(MediaFormat.KEY_BIT_RATE, COMPRESSED_AUDIO_FILE_BIT_RATE); 
      outputFormat.setInteger(MediaFormat.KEY_MAX_INPUT_SIZE, 16384); 

      MediaCodec codec = MediaCodec.createEncoderByType(COMPRESSED_AUDIO_FILE_MIME_TYPE); 
      codec.configure(outputFormat, null, null, MediaCodec.CONFIGURE_FLAG_ENCODE); 
      codec.start(); 

      ByteBuffer[] codecInputBuffers = codec.getInputBuffers(); // Note: Array of buffers 
      ByteBuffer[] codecOutputBuffers = codec.getOutputBuffers(); 

      MediaCodec.BufferInfo outBuffInfo = new MediaCodec.BufferInfo(); 
      byte[] tempBuffer = new byte[BUFFER_SIZE]; 
      boolean hasMoreData = true; 
      double presentationTimeUs = 0; 
      int audioTrackIdx = 0; 
      int totalBytesRead = 0; 
      int percentComplete = 0; 
      do { 
       int inputBufIndex = 0; 
       while (inputBufIndex != -1 && hasMoreData) { 
        inputBufIndex = codec.dequeueInputBuffer(CODEC_TIMEOUT_IN_MS); 

        if (inputBufIndex >= 0) { 
         ByteBuffer dstBuf = codecInputBuffers[inputBufIndex]; 
         dstBuf.clear(); 

         int bytesRead = fis.read(tempBuffer, 0, dstBuf.limit()); 
         Log.e("bytesRead","Readed "+bytesRead); 
         if (bytesRead == -1) { // -1 implies EOS 
          hasMoreData = false; 
          codec.queueInputBuffer(inputBufIndex, 0, 0, (long) presentationTimeUs, MediaCodec.BUFFER_FLAG_END_OF_STREAM); 
         } else { 
          totalBytesRead += bytesRead; 
          dstBuf.put(tempBuffer, 0, bytesRead); 
          codec.queueInputBuffer(inputBufIndex, 0, bytesRead, (long) presentationTimeUs, 0); 
          presentationTimeUs = 1000000l * (totalBytesRead/2)/SAMPLING_RATE; 
         } 
        } 
       } 
       // Drain audio 
       int outputBufIndex = 0; 
       while (outputBufIndex != MediaCodec.INFO_TRY_AGAIN_LATER) { 
        outputBufIndex = codec.dequeueOutputBuffer(outBuffInfo, CODEC_TIMEOUT_IN_MS); 
        if (outputBufIndex >= 0) { 
         ByteBuffer encodedData = codecOutputBuffers[outputBufIndex]; 
         encodedData.position(outBuffInfo.offset); 
         encodedData.limit(outBuffInfo.offset + outBuffInfo.size); 
         if ((outBuffInfo.flags & MediaCodec.BUFFER_FLAG_CODEC_CONFIG) != 0 && outBuffInfo.size != 0) { 
          codec.releaseOutputBuffer(outputBufIndex, false); 
         }else{ 
          mux.writeSampleData(audioTrackIdx, codecOutputBuffers[outputBufIndex], outBuffInfo); 
          codec.releaseOutputBuffer(outputBufIndex, false); 
         } 
        } else if (outputBufIndex == MediaCodec.INFO_OUTPUT_FORMAT_CHANGED) { 
         outputFormat = codec.getOutputFormat(); 
         Log.v(LOGTAG, "Output format changed - " + outputFormat); 
         audioTrackIdx = mux.addTrack(outputFormat); 
         mux.start(); 
        } else if (outputBufIndex == MediaCodec.INFO_OUTPUT_BUFFERS_CHANGED) { 
         Log.e(LOGTAG, "Output buffers changed during encode!"); 
        } else if (outputBufIndex == MediaCodec.INFO_TRY_AGAIN_LATER) { 
         // NO OP 
        } else { 
         Log.e(LOGTAG, "Unknown return code from dequeueOutputBuffer - " + outputBufIndex); 
        } 
       } 
       percentComplete = (int) Math.round(((float) totalBytesRead/(float) inputFile.length()) * 100.0); 
       Log.v(LOGTAG, "Conversion % - " + percentComplete); 
      } while (outBuffInfo.flags != MediaCodec.BUFFER_FLAG_END_OF_STREAM); 
      fis.close(); 
      mux.stop(); 
      mux.release(); 
      Log.v(LOGTAG, "Compression done ..."); 
     } catch (FileNotFoundException e) { 
      Log.e(LOGTAG, "File not found!", e); 
     } catch (IOException e) { 
      Log.e(LOGTAG, "IO exception!", e); 
     } 

     //mStop = false; 
     // Notify UI thread... 
    } 
};