基本上,我想制作一个音频可视化工具。我知道这是可能的,因为我的手机附带了一些动态壁纸。问题是,我似乎无法弄清楚如何使用Android API。
我的应用会选择当前播放的媒体流,然后根据当时正在播放的音量,它会在屏幕上显示更多或更少的小节。
我该怎么做?看起来我可以使用麦克风做这样的事情,但我希望能够用于音乐,播客等。
答案 0 :(得分:7)
看起来2.3中的内容已经改变,现在有权限
<uses-permission android:name="android.permission.RECORD_AUDIO"/>
<uses-permission android:name="android.permission.MODIFY_AUDIO_SETTINGS"/>
在aosp中有一个AudioCapture助手类来帮助动态壁纸正确地完成它。 https://android.googlesource.com/platform/packages/wallpapers/MusicVisualization/+/gingerbread-release/src/com/android/musicvis/AudioCapture.java
修改强>
AOSP中的一个导入与公共API不匹配
import android.media.audiofx.Visualizer;
是
import android.media.Visualizer;
如果头疼,请务必切换。这都是2.3 api,它显然返回了一个低分辨率的音频流,但不足以录音。
答案 1 :(得分:5)
MusicVisualization wallpaper source位于AOSP。它基本上似乎涉及调用MediaPlayer.snoop()
,这是Eclair中添加的一个未记录的方法。
答案 2 :(得分:3)
除了从
修改一个小的返回值之外,roskit基本上说的是什么return 0;
到
return Integer.parseInt( (m.invoke(c, outData, kind)).toString() );
换句话说:
public static int snoop(short [] outData, int kind){
try {
Class c = MediaPlayer.class;
Method m = c.getMethod("snoop", outData.getClass(), Integer.TYPE);
m.setAccessible(true);
return Integer.parseInt( (m.invoke(c, outData, kind)).toString() );
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
return 1;
}
}
答案 3 :(得分:2)
这就是我从我的申请中做到的:
protected short [] mAudioData = new short[1024];
然后在循环中:
int res = snoop(mAudioData, 0);
这是函数本身:
public static int snoop(short [] outData, int kind){
try {
Class c = MediaPlayer.class;
Method m = c.getMethod("snoop", outData.getClass(), Integer.TYPE);
m.setAccessible(true);
m.invoke(c, outData, kind);
return 0;
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
return 1;
}
}
答案 4 :(得分:2)
稍微快一点snoop()
就可以拨打Class.getMethod()
一次,然后使用自定义parseInt()
代替Integer.parseInt()
...
private static Method mSnoop;
//..(http://nadeausoftware.com/node/97)..
private static int customParseInt( final String s )
{
// Check for a sign.
int num = 0;
int sign = -1;
final int len = s.length( );
final char ch = s.charAt( 0 );
if ( ch == '-' )
sign = 1;
else
num = '0' - ch;
// Build the number.
int i = 1;
while ( i < len )
num = num*10 + '0' - s.charAt( i++ );
return sign * num;
}
private static int snoop(short [] outData, int kind)
{
if ( mSnoop != null )
{
try
{
return customParseInt( (mSnoop.invoke( MediaPlayer.class , outData, kind)).toString() );
}
catch ( Exception e )
{
Log.e( TAG, "Failed to MediaPlayer.snoop()!", e );
return 1;
}
}
else
{
try {
Class c = MediaPlayer.class;
Method m = c.getMethod("snoop", outData.getClass(), Integer.TYPE);
m.setAccessible(true);
mSnoop = m;
return customParseInt( (m.invoke(c, outData, kind)).toString() );
}
catch (Exception e)
{
Log.e( TAG, "Failed to MediaPlayer.snoop()!", e );
return 1;
}
}
}
答案 5 :(得分:0)