Android播放音乐时跳动的屏谱demo
Android实现播放音频时的跳动频谱,并实现可以调节的均衡器。
Main.java
- package com.wjq.audiofx;
- import android.app.Activity;
- import android.media.AudioManager;
- import android.media.MediaPlayer;
- import android.media.audiofx.Equalizer;
- import android.media.audiofx.Visualizer;
- import android.os.Bundle;
- import android.util.Log;
- import android.view.Gravity;
- import android.view.ViewGroup;
- import android.widget.LinearLayout;
- import android.widget.SeekBar;
- import android.widget.TextView;
- public class Main extends Activity {
- private static final String TAG = "AudioFxDemo";
- private static final float VISUALIZER_HEIGHT_DIP = 50f;
- private MediaPlayer mMediaPlayer;
- private Visualizer mVisualizer;
- private Equalizer mEqualizer;//均横器
- private LinearLayout mLinearLayout;
- VisualizerView mVisualizerView;
- private TextView mStatusTextView;
- @Override
- public void onCreate(Bundle icicle) {
- super.onCreate(icicle);
- setVolumeControlStream(AudioManager.STREAM_MUSIC);
- mStatusTextView = new TextView(this);
- mLinearLayout = new LinearLayout(this);
- mLinearLayout.setOrientation(LinearLayout.VERTICAL);
- mLinearLayout.addView(mStatusTextView);
- setContentView(mLinearLayout);
- // Create the MediaPlayer
- mMediaPlayer = MediaPlayer.create(this, R.raw.test_cbr);
- if( null == mMediaPlayer )
- return ;
- Log.d(TAG, "MediaPlayer audio session ID: " + mMediaPlayer.getAudioSessionId());
- setupVisualizerFxAndUI();
- setupEqualizerFxAndUI();
- // Make sure the visualizer is enabled only when you actually want to receive data, and
- // when it makes sense to receive data.
- mVisualizer.setEnabled(true);
- // When the stream ends, we don't need to collect any more data. We don't do this in
- // setupVisualizerFxAndUI because we likely want to have more, non-Visualizer related code
- // in this callback.
- mMediaPlayer.setOnCompletionListener(new MediaPlayer.OnCompletionListener() {
- public void onCompletion(MediaPlayer mediaPlayer) {
- mVisualizer.setEnabled(false);
- }
- });
- mMediaPlayer.start();
- mStatusTextView.setText("播放音频...");
- }
- /**
- * 通过mMediaPlayer返回的AudioSessionId创建一个优先级为0均衡器对象,并且通过频谱生成相应的UI和对应的事件
- */
- private void setupEqualizerFxAndUI() {
- mEqualizer = new Equalizer(0, mMediaPlayer.getAudioSessionId());
- // 启用均衡器
- mEqualizer.setEnabled(true);
- TextView eqTextView = new TextView(this);
- eqTextView.setText("均横器:");
- mLinearLayout.addView(eqTextView);
- // 通过均衡器得到其支持的频谱引擎
- short bands = mEqualizer.getNumberOfBands();
- // getBandLevelRange是一个数组,返回一组频谱等级数组,返回一组频谱等级数组
- // 第一个下标为最低的限度范围,第二个下标为最高的限度范围
- // 依次取出
- final short minEQLevel = mEqualizer.getBandLevelRange()[0];
- final short maxEQLevel = mEqualizer.getBandLevelRange()[1];
- for (short i = 0; i < bands; i++) {
- final short band = i;
- TextView freqTextView = new TextView(this);
- freqTextView.setLayoutParams(new ViewGroup.LayoutParams(
- ViewGroup.LayoutParams.FILL_PARENT,
- ViewGroup.LayoutParams.WRAP_CONTENT));
- freqTextView.setGravity(Gravity.CENTER_HORIZONTAL);
- freqTextView.setText((mEqualizer.getCenterFreq(band) / 1000) + " Hz");
- mLinearLayout.addView(freqTextView);
- LinearLayout row = new LinearLayout(this);
- row.setOrientation(LinearLayout.HORIZONTAL);
- TextView minDbTextView = new TextView(this);
- minDbTextView.setLayoutParams(new ViewGroup.LayoutParams(
- ViewGroup.LayoutParams.WRAP_CONTENT,
- ViewGroup.LayoutParams.WRAP_CONTENT));
- minDbTextView.setText((minEQLevel / 100) + " dB");
- TextView maxDbTextView = new TextView(this);
- maxDbTextView.setLayoutParams(new ViewGroup.LayoutParams(
- ViewGroup.LayoutParams.WRAP_CONTENT,
- ViewGroup.LayoutParams.WRAP_CONTENT));
- maxDbTextView.setText((maxEQLevel / 100) + " dB");
- LinearLayout.LayoutParams layoutParams = new LinearLayout.LayoutParams(
- ViewGroup.LayoutParams.FILL_PARENT,
- ViewGroup.LayoutParams.WRAP_CONTENT);
- layoutParams.weight = 1;
- SeekBar bar = new SeekBar(this);
- bar.setLayoutParams(layoutParams);
- bar.setMax(maxEQLevel - minEQLevel);
- bar.setProgress(mEqualizer.getBandLevel(band));
- bar.setOnSeekBarChangeListener(new SeekBar.OnSeekBarChangeListener() {
- public void onStopTrackingTouch(SeekBar seekBar) {}
- public void onStartTrackingTouch(SeekBar seekBar) {}
- public void onProgressChanged(SeekBar seekBar, int progress,
- boolean fromUser) {
- mEqualizer.setBandLevel(band, (short) (progress + minEQLevel));
- }
- });
- row.addView(minDbTextView);
- row.addView(bar);
- row.addView(maxDbTextView);
- mLinearLayout.addView(row);
- }
- }
- /**
- * 生成一个VisualizerView对象,使音频频谱的波段能够反映到 VisualizerView上
- */
- private void setupVisualizerFxAndUI() {
- mVisualizerView = new VisualizerView(this);
- mVisualizerView.setLayoutParams(new ViewGroup.LayoutParams(
- ViewGroup.LayoutParams.FILL_PARENT,
- (int)(VISUALIZER_HEIGHT_DIP * getResources().getDisplayMetrics().density)));
- mLinearLayout.addView(mVisualizerView);
- int sessId = mMediaPlayer.getAudioSessionId() ;
- mVisualizer = new Visualizer(sessId);
- // 参数必须是2的位数
- mVisualizer.setCaptureSize(Visualizer.getCaptureSizeRange()[1]);
- // 设置允许波形表示,并且捕获它
- mVisualizer.setDataCaptureListener(new Visualizer.OnDataCaptureListener() {
- public void onWaveFormDataCapture(Visualizer visualizer, byte[] bytes,
- int samplingRate) {
- mVisualizerView.updateVisualizer(bytes);
- }
- public void onFftDataCapture(Visualizer visualizer, byte[] bytes, int samplingRate) {}
- }, Visualizer.getMaxCaptureRate() / 2, true, false);
- }
- @Override
- protected void onPause() {
- super.onPause();
- if (isFinishing() && mMediaPlayer != null) {
- mVisualizer.release();
- mEqualizer.release();
- mMediaPlayer.release();
- mMediaPlayer = null;
- }
- }
- }
VisualizerView.java
- package com.wjq.audiofx;
- import android.content.Context;
- import android.graphics.Canvas;
- import android.graphics.Color;
- import android.graphics.Paint;
- import android.graphics.Rect;
- import android.view.View;
- public class VisualizerView extends View {
- private byte[] mBytes;
- private float[] mPoints;
- //矩形区域
- private Rect mRect = new Rect();
- // 画笔
- private Paint mForePaint = new Paint();
- // 初始化画笔
- private void init() {
- mBytes = null;
- mForePaint.setStrokeWidth(1f);
- mForePaint.setAntiAlias(true);
- mForePaint.setColor(Color.GREEN);
- }
- public VisualizerView(Context context) {
- super(context);
- init();
- }
- public void updateVisualizer(byte[] bytes) {
- mBytes = bytes;
- invalidate();
- }
- @Override
- protected void onDraw(Canvas canvas) {
- super.onDraw(canvas);
- if (mBytes == null) {
- return;
- }
- if (mPoints == null || mPoints.length < mBytes.length * 4) {
- mPoints = new float[mBytes.length * 4];
- }
- mRect.set(0, 0, getWidth(), getHeight());
- for (int i = 0; i < mBytes.length - 1; i++) {
- mPoints[i * 4] = mRect.width() * i / (mBytes.length - 1);
- mPoints[i * 4 + 1] = mRect.height() / 2
- + ((byte) (mBytes[i] + 128)) * (mRect.height() / 2) / 128;
- mPoints[i * 4 + 2] = mRect.width() * (i + 1) / (mBytes.length - 1);
- mPoints[i * 4 + 3] = mRect.height() / 2
- + ((byte) (mBytes[i + 1] + 128)) * (mRect.height() / 2) / 128;
- }
- canvas.drawLines(mPoints, mForePaint);
- }
- }
Android播放音乐时跳动的屏谱demo的更多相关文章
- android 播放视频时切换全屏隐藏状态栏
1. Demo: @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstance ...
- android 播放音乐-进度条
今天学渣研究了一下使用MediaPlayer播放音乐时加入进度条,进度条如今用的是android自带的seekbar,后期会跟换UI的,在之前可以播放音乐的基础上,如今加入的主要功能有两个: 1实时显 ...
- 绘制播放音乐时的音波图形的View
绘制播放音乐时的音波图形的View 这个效果类似于这个哦: 效果如下: 源码: MusicView.h 与 MusicView.m // // MusicView.h // Music // // C ...
- android 播放音乐媒体文件(一)
Audio formats and codecs Format / Codec Encoder Decoder Details Supported File Type(s) / Container F ...
- Android 播放电影时滑动屏幕调整屏幕亮度(转)
(转自:http://blog.csdn.net/piaozhiye/article/details/6544450) 发现有一些主流的播放器播放电影时可以通过滑动屏幕调整屏幕亮度,其实实现起来也很容 ...
- 关于Windows 8使用WMP播放音乐时WUDFHost跑CPU和硬盘的问题解决
Windows 8使用Windows Media Player播放音乐的时候.事实上有一个这种情况,WMP和某个什么名字看起来非常屌的进程跑CPU非常高,这个跑非常高视你插入的SD卡内的文件数或者移动 ...
- android修改系统时系统黑屏时不进入休眠状态
基于android4.4修改,在frameworks/base/services/java/com/android/server/power/PowerManagerService.java里,查看休 ...
- android关闭屏幕时不锁屏实现
所需权限: <uses-permission android:name="android.permission.DISABLE_KEYGUARD"/> 关闭系统锁屏服务 ...
- 解决Android Activity切换时出现白屏问题
有些性能低的机器,在切换activity时候出现白屏一段时候后才显示正确的视图 高性能的机器可能太快看不到,但是事实是存在的, 特别是当你新开一个进程的时候,A进程的activity跳转到B进程的Ac ...
随机推荐
- Linux学习:netstat命令
Netstat 命令用于显示各种网络相关信息,如网络连接,路由表,接口状态等.对于开发来说,很多时候用于查看端口占用情况. 执行netstat命令,其输出结果可以分成两部分: 1)一是“Active ...
- Uva 511 Updating a Dictionary
大致题意:用{ key:value, key:value, key:value }的形式表示一个字典key表示建,在一个字典内没有重复,value则可能重复 题目输入两个字典,如{a:3,b:4,c: ...
- Ubuntu12.04 cuda5.5安装
预处理步骤: 首先确认你的电脑装了一个可以运行CUDA程序的GPU. lspci | grep -i nvidia 另外要确认linux版本和gcc版本 具体参考链接:http://docs.nvid ...
- 如何使用W5300实现ADSL连接(一)
在介绍W5300连接ADSL之前,先给大家简单介绍一下WIZnet W5300这款芯片. W5300是WIZnet公司的一款单芯片器件,采用0.18μmCMOS工艺,内部集成10/100M以太网控制器 ...
- HH的军训(容斥)
1248: HH的军训 时间限制: 1 Sec 内存限制: 128 MB 提交: 95 解决: 11 [提交][状态][讨论版] 题目描述 大学里,最难忘的事情莫过于军训了,白白的HH童鞋就被无情 ...
- android 时间滚动控件 底部弹出
下载地址:http://download.csdn.net/detail/ldd119/7440895 转载请说明出处 先上个效果图 watermark/2/text/aHR0cDovL2Jsb2cu ...
- 如何安装系统认证签名过的APK
如果你的App因为权限原因需要设置 android:sharedUserId="android.uid.system" 那么IDE编译出的包通常是无法直接安装的,查看控制台会发现报 ...
- 自己动手为PHP7添加新的语法特性
好文章! nikic介绍了如何向PHP添加新的语法特性,原文写的非常精彩,具体是添加in语法功能,使最终实现: <?php $words = ['hello', 'world', 'foo', ...
- ViewPager+View实现Tab
注:源码来自慕课网. 使用ViewPager+View实现Tab底部导航: 主要思想:顶部top.xml,中间ViewPager,底部线性布局Tab导航. top.xml具体实现: <?xml ...
- 【论文阅读】Retrieving Similar Similar Styles to Parse Clothing(相关工作)
发表于2015年5月PAMI 作者: Kota Yamaguchi, M.Hadi Kiapour, Luis E. Ortiz, Tamara L. Berg 相关工作: [服装检索Clothing ...