人脸识别 在线音乐,自己开发的一款不太成熟的安卓APP

【声明】 欢迎转载,但请保留文章原始出处

第一次写博客,大家见谅 先附上最后成品图,虽然有些功能不是很成熟

人脸识别

首先是人脸识别功能,人脸识别现在有很多公司做了这方面的功能供开发人员选择,我这里使用的是Face++公司的人脸识别技术,但是现在只能通过调用系统相机拍照后上传图片解析图片获取人脸信息,不能直接摄像头边预览直接获取人脸并解析。 这是Face++官网开发者中心,可以参考API文档 http://www.faceplusplus.com.cn/uc_home/ 这是对人脸的解析的代码

private Handler handler = new Handler() {
        @Override
        public void handleMessage(Message msg) {
            super.handleMessage(msg);
            switch (msg.what) {
                case PARSE_OK:

                    JSONObject rs = (JSONObject) msg.obj;
                    parseInfo(rs);
                    Log.i("MyTest", "---age-->" + age + "-----gender--" + gender + "----smiling--" + smiling);
                    emotionInfo.setVisibility(View.VISIBLE);
                    find_btn_submit.setVisibility(View.GONE);
                    emotionInfo.setText("检测结果如下:\n年龄:" + age + "\n性别:" + gender + "\n笑脸值:" + smiling);
                    noCamera.clearAnimation();
                    tips.clearAnimation();
                    tips.setText("下拉开启音乐之旅");
                    break;
                case PARSE_ERRO:
                    handler.post(new Runnable() {
                        @Override
                        public void run() {
                            Toast.makeText(FindMusicActivity.this, "请检查网络连接", Toast.LENGTH_SHORT).show();
                            tips.clearAnimation();
                            tips.setText("当前网络状况出了点问题,检查一下再来吧~\n下拉随机推荐音乐");
                            noCamera.clearAnimation();
                            noCamera.setImageResource(R.mipmap.get_face_fail);
                        }
                    });
                    break;
            }
        }


    };

    /**
     * 解析心情
     */
    private void parseInfo(JSONObject obj) {
        try {
            JSONArray faces = obj.getJSONArray("face");
            int faceCounts = faces.length();
            if (faceCounts == 0) {
                Toast.makeText(FindMusicActivity.this, "不好意思,没有检测出来,请重新检测", Toast.LENGTH_SHORT).show();
                tips.clearAnimation();
                tips.setText("不好意思,没有检测出来,请长按重新检测");
                noCamera.clearAnimation();
                noCamera.setImageResource(R.mipmap.get_face_fail);
                smiling=50;
            } else {
                JSONObject face = faces.getJSONObject(0);
                String sex = face.getJSONObject("attribute").getJSONObject("gender").getString("value");
                gender = "Male".equals(sex) ? "男" : "女";
                age = face.getJSONObject("attribute").getJSONObject("age").getInt("value");
                smiling = face.getJSONObject("attribute").getJSONObject("smiling").getDouble("value");
            }
        } catch (JSONException e) {
            e.printStackTrace();
        }
    }
在线播放音乐

播放音乐这个问题让我头疼了好久,老是找不到接口,好多网上找的接口说着能用但是并不能解析出数据,最后,还是没有找到很好的接口,只能直接从网络上获取了70个歌曲链接存放在类中,然后根据地址从网络加载并播放音乐 歌曲链接获得方式: 歌曲播放其实是我一个朋友写的,这个过程也是出现各种问题,特别是服务的问题,老是获取不到服务,要不就是服务注销不了,音乐不能停,到现在也不是很完善,这是个尚存的问题

其他功能侧滑栏

侧滑栏使用的是安卓v4包的DrawLayout,DrawLayout的用法我应该不用说了,相信大家都知道,主要就是注意一点要声明它出现的位置,不然会报错

手势

里面用到了很多手势,上滑、下滑、长按等,可以用Gesture类来实现,我这里没有用这个,用的是View.OnTouchListener这个接口,然后在OnTouch()方法里面对手指在屏幕上的触摸做出判断,根据按下和抬起时不同的坐标和时间戳,判断出做出的是什么操作,不过这样判断不太精确,不建议使用

圆形进度条

这是个自定义的圆形进度条,是在网上找的参考的代码 大家可以参考一下

package com.sdf.DefineView;

import android.content.Context;
import android.content.res.TypedArray;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.graphics.RectF;
import android.util.AttributeSet;
import android.view.View;

import com.sdf.facemusic.R;

/**
 * Created by Administrator on 15-11-5.
 */
public class RoundProgressBar extends View
{
    // 画笔对象的引用
    private Paint paint;

    // 圆环的颜色
    private int roundColor;

    // 圆环进度的颜色

    private int roundProgressColor;

    // 中间进度百分比的字符串的颜色
    // private int textColor;

    // 中间进度百分比的字符串的字体
    // private float textSize;

    // 圆环的宽度
    private float roundWidth;

    // 最大进度
    private int max;

    // 当前进度
    private int progress;

    // 是否显示中间的进度
    //private boolean textIsDisplayable;

    // 进度的风格,实心或者空心
    private int style;

    public static final int STROKE = 0;
    public static final int FILL = 1;

    public RoundProgressBar(Context context) {
        this(context, null);
    }

    public RoundProgressBar(Context context, AttributeSet attrs) {
        this(context, attrs, 0);
    }

    public RoundProgressBar(Context context, AttributeSet attrs, int defStyle) {
        super(context, attrs, defStyle);

        paint = new Paint();

        TypedArray mTypedArray = context.obtainStyledAttributes(attrs, R.styleable.RoundProgressBar);

        // 获取自定义属性和默认值
        roundColor = mTypedArray.getColor(R.styleable.RoundProgressBar_roundColor, Color.WHITE);
        roundProgressColor = mTypedArray.getColor(R.styleable.RoundProgressBar_roundProgressColor, Color.GREEN);
        roundWidth = mTypedArray.getDimension(R.styleable.RoundProgressBar_roundWidth, 5);
        max = mTypedArray.getInteger(R.styleable.RoundProgressBar_max, 100);
        style = mTypedArray.getInt(R.styleable.RoundProgressBar_style, 0);
        //回收mTypedArray
        mTypedArray.recycle();
    }

    @Override
    protected void onDraw(Canvas canvas) {
        super.onDraw(canvas);

        // 画最外层的大圆环
        int centre = getWidth() / 2; // 获取圆心的x坐标
        int radius = (int) (centre - roundWidth / 2); // 圆环的半径
        paint.setColor(roundColor); // 设置圆环的颜色
        paint.setStyle(Paint.Style.STROKE); // 设置空心
        paint.setStrokeWidth(roundWidth); // 设置圆环的宽度
        paint.setAntiAlias(true); // 消除锯齿
        canvas.drawCircle(centre, centre, radius, paint); // 画出圆环


        // 画圆弧 ,画圆环的进度
        // 设置进度是实心还是空心
        paint.setStrokeWidth(roundWidth); // 设置圆环的宽度
        paint.setColor(roundProgressColor); // 设置进度的颜色
        RectF oval = new RectF(centre - radius, centre - radius, centre + radius, centre + radius); // 用于定义的圆弧的形状和大小的界限

        switch (style) {
            case STROKE: {
                paint.setStyle(Paint.Style.STROKE);
                canvas.drawArc(oval, 0, 360 * progress / max, false, paint); // 根据进度画圆弧
                break;
            }
            case FILL: {
                paint.setStyle(Paint.Style.FILL_AND_STROKE);
                if (progress != 0)
                    canvas.drawArc(oval, 0, 360 * progress / max, true, paint); // 根据进度画圆弧
                break;
            }
        }

    }

    public synchronized int getMax() {
        return max;
    }

    /**
     * 设置进度的最大值
     *
     * @param max
     */
    public synchronized void setMax(int max) {
        if (max < 0) {
            throw new IllegalArgumentException("max not less than 0");
        }
        this.max = max;
    }

    /**
     * 获取进度.需要同步
     *
     * @return
     */
    public synchronized int getProgress() {
        return progress;
    }

    /**
     * 设置进度,此为线程安全控件,由于考虑多线的问题,需要同步 刷新界面调用postInvalidate()能在非UI线程刷新
     *
     * @param progress
     */
    public synchronized void setProgress(int progress) {
        if (progress < 0) {
            throw new IllegalArgumentException("progress not less than 0");
        }
        if (progress > max) {
            progress = max;
        }
        if (progress <= max) {
            this.progress = progress;
            postInvalidate();
        }

    }

    public int getCricleColor() {
        return roundColor;
    }

    public void setCricleColor(int cricleColor) {
        this.roundColor = cricleColor;
    }

    public int getCricleProgressColor() {
        return roundProgressColor;
    }

    public void setCricleProgressColor(int cricleProgressColor) {
        this.roundProgressColor = cricleProgressColor;
    }


    public float getRoundWidth() {
        return roundWidth;
    }

    public void setRoundWidth(float roundWidth) {
        this.roundWidth = roundWidth;
    }

}
第三方登录和分享功能

第三方用的是ShareSDK,相信作为一个开发人员都用过。我在做这个项目的时候,因为是第一次用Android studio开发,所以不知道怎么添加,后来从网上找的一位朋友的,很详细的教程,大家可以参考

至此,项目大概功能就介绍完了,第一次写博客,可能写的比较乱,见谅