android中的speex支持 [英] speex support in android

查看:154
本文介绍了android中的speex支持的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

有人可以帮助我如何在android中使用speex或jspeex吗?

我进行了很多搜索,但找不到任何地方.在Android中解码speex编码的字节数组.因此,如果您对此有所了解,请向我提供有关此信息.

I have searched a lot but could not able to find anywhere.There are many issues regarding this in code.google.com/android but none have answered it. Here also this question did not got a good response as my another question regarding this is Decoding speex encoded byte array in Android. So If you know something about this then Please provide me information regarding this.

我需要使用此编解码器对音频文件的字节数组进行编码和解码.

I need to encode and decode bytearray of audio file using this codec.

我尝试了 Android-ndk并完成了编码,,但是在解码字节数组时遇到了一个问题.还有其他方法可以实现吗?

I have tried Android-ndk and got encoding done, but getting a problem in decoding the byte array. Is there any other alternative to achieve this?

编辑

我的编码本机c文件中的函数如下:

my encoding Functions in native c file are as follow:

#include <jni.h>
#include "speex/speex.h"

#define FRAME_SIZE 320

int nbBytes;
/*Holds the state of the encoder*/
void *state;
void *decod_state;


/*Holds bits so they can be read and written to by the Speex routines*/

SpeexBits decod_bits;
SpeexBits bits;
int i, tmp;

void Java_com_mycom_speex_SpeexEncodingActivity_init(JNIEnv * env, jobject jobj) {
   /*Create a new encoder state in narrowband mode*/
   state = speex_encoder_init(&speex_wb_mode);

   /*Set the quality to 8*/
   tmp=8;
   speex_encoder_ctl(state, SPEEX_SET_QUALITY, &tmp);

   /*Initialization of the structure that holds the bits*/
   speex_bits_init(&bits);
}

jbyteArray Java_com_mycom_speex_SpeexEncodingActivity_encode(JNIEnv * env, jobject jobj, jshortArray inputData) {
        jbyteArray ret;

        jshort * inputArrayElements = (*env)->GetShortArrayElements(env, inputData, 0);

        /*Flush all the bits in the struct so we can encode a new frame*/
        speex_bits_reset(&bits);

        /*Encode the frame*/
        speex_encode_int(state, inputArrayElements, &bits);
        /*Copy the bits to an array of char that can be written*/
        nbBytes = speex_bits_nbytes(&bits);

        ret = (jbyteArray) ((*env)->NewByteArray(env, nbBytes));
        jbyte * arrayElements = (*env)->GetByteArrayElements(env, ret, 0);

        speex_bits_write(&bits, arrayElements, nbBytes);

        (*env)->ReleaseShortArrayElements(env, inputData, inputArrayElements, JNI_ABORT);
        (*env)->ReleaseByteArrayElements(env, ret, arrayElements, 0);
        return ret;
}

现在要解码,我将转换后的短数组发送给解码函数,如下所示:

now for decoding i am sending the converted short array to decode function as follow:

void Java_com_mycom_speex_SpeexEncodingActivity_initDecode(JNIEnv * env,
        jobject jobj) {

    decod_state = speex_decoder_init(&speex_wb_mode);

    tmp = 1;
    speex_decoder_ctl(decod_state, SPEEX_SET_ENH, &tmp);

    /*Initialization of the structure that holds the bits*/
    speex_bits_init(&decod_bits);
}

jshortArray Java_com_mycom_speex_SpeexEncodingActivity_decode(JNIEnv * env,
        jobject jobj, jshortArray inputData) {



    jshort * inputArrayElements = (*env)->GetShortArrayElements(env, inputData,
            0);

    /*Flush all the bits in the struct so we can decode a new frame*/
    speex_bits_reset(&decod_bits);
    /*Copy the bits to an array of char that can be written*/
    nbBytes = speex_bits_nbytes(&decod_bits);
    speex_bits_read_from(&decod_bits,inputArrayElements, nbBytes); // here it requires char * in second argument
    /*Decode the frame*/
    speex_decode_int(decod_state, &decod_bits, inputArrayElements);
    (*env)->ReleaseShortArrayElements(env, encodedData, inputArrayElements,
            JNI_ABORT);
    return inputArrayElements;
}

我的编码功能运行良好,博客上提供了该示例

my Encoding functions are working fine the example is provided on the blog A JNI Wrapper for Speex on Android

通过传递char数组并返回短数组的另一种尝试解码如下:

jshortArray Java_com_mycom_speex_SpeexEncodingActivity_decode(JNIEnv * env,
        jobject jobj, jcharArray inputCharData) {

    jshortArray ret;
    jchar * inputArrayElements = (*env)->GetCharArrayElements(env,
            inputCharData, 0);
    /*Flush all the bits in the struct so we can decode a new frame*/
    speex_bits_reset(&decod_bits);
    /*Copy the bits to an array of char that can be written*/
    nbBytes = speex_bits_nbytes(&decod_bits);
    ret = (jshortArray)((*env)->NewShortArray(env, nbBytes));
    jshort * arrayElements = (*env)->GetShortArrayElements(env, ret, 0);

    speex_bits_read_from(&decod_bits,(char *) inputArrayElements, nbBytes);
    /*Decode the frame*/
    speex_decode_int(decod_state, &decod_bits, arrayElements);

    (*env)->ReleaseCharArrayElements(env, inputCharData, inputArrayElements,
            JNI_ABORT);
    (*env)->ReleaseShortArrayElements(env, ret, arrayElements, 0);
    return ret;
}

结果是

Returned empty array of short if i return ret and if i return arrayElements it 
gives an error Fatal signal 11 (SIGSEGV) at 0x00000018 (code=1)

推荐答案

speex_bits_reset在其主体中执行以下操作:

speex_bits_reset do following in its body:

bits->nbBits=0;

和speex_bits_nbytes返回((bits-> nbBits + 7)>> 3); 因此,如果您在speex_bits_reset之后立即调用speex_bits_nbytes,则始终会收到0.因此,必须在分配数组之前调用speex_bits_read_from:

and speex_bits_nbytes returns ((bits->nbBits+7)>>3); So if you call speex_bits_nbytes right after speex_bits_reset, you always receive 0. So you must call speex_bits_read_from before array allocation:

/*Flush all the bits in the struct so we can decode a new frame*/
speex_bits_reset(&decod_bits);

/*Read bits in decod_bits struct from java array*/
speex_bits_read_from(&decod_bits,(char *) inputArrayElements, nbBytes);

/*Copy the bits to an array of char that can be written*/
nbBytes = speex_bits_nbytes(&decod_bits);
ret = (jshortArray)((*env)->NewShortArray(env, nbBytes));
jshort * arrayElements = (*env)->GetShortArrayElements(env, ret, 0);

/*Decode the frame*/
speex_decode_int(decod_state, &decod_bits, arrayElements);

(*env)->ReleaseCharArrayElements(env, inputCharData, inputArrayElements,
        JNI_ABORT);
(*env)->ReleaseShortArrayElements(env, ret, arrayElements, 0);
return ret;

这篇关于android中的speex支持的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆