Files
device_rockchip/rk3308/aispeech/dds_client/demo/music.c
Eddie Cai 6ea5e91a98 initial commit
Signed-off-by: Eddie Cai <eddie.cai.linux@gmail.com>
2018-06-23 10:08:13 +08:00

361 lines
10 KiB
C
Executable File
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

/*================================================================
* Copyright (C) 2018 FREEDOM Ltd. All rights reserved.
*
* 文件名称music.c
* 创 建 者chenjie.gu
* 创建日期2018年05月24日
* 描 述:
*
================================================================*/
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include "audio_player.h"
#include <time.h>
#include "cJSON.h"
#include <unistd.h>
#include <pthread.h>
#include <stdbool.h>
audio_player_t *aplayer = NULL;
float vol_multiplier = 0.4;
int player_is_end = 0;
pthread_mutex_t music_mutex;
int play_judge_f(int index, int count, int mode);
void play_manager_f(const char *cmd, const char *data);
static int g_player_ev = AUDIO_PLAYER_EV_END;
bool music_is_playing(void) {
if (g_player_ev == AUDIO_PLAYER_EV_END ||
g_player_ev == AUDIO_PLAYER_EV_ERROR ||
g_player_ev == AUDIO_PLAYER_EV_STOPPED)
return false;
else
return true;
}
static int play_callback(void *userdata, int ev) {
printf("++++++%s: ev %d\n", __func__, ev);
if (ev == AUDIO_PLAYER_EV_END) {
player_is_end = 1;
}
g_player_ev = ev;
return 0;
}
void *player_routine(void *user) {
while (1) {
if (player_is_end) {
player_is_end = 0;
play_manager_f("player.end", NULL);
}
usleep(100 * 1000);
}
return (void *)0;
}
int music_player_init(char *dev) {
aplayer = audio_player_new(dev, play_callback, NULL);
audio_player_set_channel_volume(aplayer, vol_multiplier);
pthread_mutex_init(&music_mutex, NULL);
return 0;
}
int music_player_play(char *path) {
audio_player_play(aplayer, path);
}
int music_player_start() {
int ret;
pthread_t tid;
pthread_create(&tid, NULL, player_routine, NULL);
return 0;
}
void play_manager_f(const char *cmd, const char *data) {
/*
* 1. volume.set
* 2. play.list.update
* 3. play.list.clear
* 4. play.list.get
* 5. status.set
* 6. change.set
* 7. mode.set
* 8. play.choose.update
* 9. play.collect.choose
* 10. play.uncollect.choose
* 11. player.end
*/
enum PLAY_MODE {
sequence, random, single, loop
};
enum PLAY_STATUS {
idle, pause, playing
};
static enum PLAY_MODE mode = sequence;
static enum PLAY_STATUS status = idle;
static int count = 0;
static int index = 0;
static int old_index = 0;
static cJSON *root = NULL;
printf("play_manager_f cmd: %s\tdata: %s\n", cmd, data);
pthread_mutex_lock(&music_mutex);
if (!strcmp(cmd, "volume.set")) {
// 设置音量
if (!strcmp(data, "+")) {
vol_multiplier += 0.05;
if (vol_multiplier > 1.0) vol_multiplier = 0.99;
audio_player_set_channel_volume(aplayer, vol_multiplier);
printf("set vol_multiplier to %f\n", vol_multiplier);
printf("set vol to %d\n", (int)(vol_multiplier * 100.0));
}
else if (!strcmp(data, "-")) {
vol_multiplier -= 0.05;
if (vol_multiplier < 0.01) vol_multiplier = 0.01;
audio_player_set_channel_volume(aplayer, vol_multiplier);
printf("set vol_multiplier to %f\n", vol_multiplier);
printf("set vol to %d\n", (int)(vol_multiplier * 100.0));
}
else {
int vol = atoi(data);
vol_multiplier = vol / 100.0;
audio_player_set_channel_volume(aplayer, vol_multiplier);
printf("set vol_multiplier to %f\n", vol_multiplier);
printf("set vol to %d\n", (int)(vol_multiplier * 100.0));
}
}
else if (!strcmp(cmd, "play.list.clear")) {
// 清空播放列表
printf("clear the play list info\n");
audio_player_stop(aplayer);
cJSON_Delete(root);
root = NULL;
index = 0;
old_index = 0;
count = 0;
status = idle;
}
else if (!strcmp(cmd, "play.list.get")) {
}
else if (!strcmp(cmd, "play.list.check")) {
// 开始真正播放
cJSON *temp, *music;
if (root) {
if (status == idle) {
temp = cJSON_GetObjectItem(root, "count");
count = temp->valueint;
if (count > 0) {
status = playing;
music = cJSON_GetObjectItem(root, "content");
temp = cJSON_GetArrayItem(music, index);
temp = cJSON_GetObjectItem(temp, "linkUrl");
printf("ready to play url is %s\n", temp->valuestring);
audio_player_play(aplayer, temp->valuestring);
}
}
else if (status == pause) {
status = playing;
audio_player_resume(aplayer);
}
}
}
else if (!strcmp(cmd, "play.list.update")) {
// 更新播放列表
// TODO: update
printf("update the play list info\n");
audio_player_stop(aplayer);
if (root) cJSON_Delete(root);
root = NULL;
index = 0;
old_index = 0;
count = 0;
status = idle;
root = cJSON_Parse(data);
}
else if (!strcmp(cmd, "status.set")) {
// 设置播放状态
printf("status.set data is %s status is %d\n", data, status);
if (!strcmp(data, "pause") && status == playing) {
status = pause;
audio_player_pause(aplayer);
}
else if (!strcmp(data, "resume") && status == pause) {
status = playing;
audio_player_resume(aplayer);
}
else if (!strcmp(data, "replay") && status == pause) {
status = playing;
cJSON *temp, *music;
music = cJSON_GetObjectItem(root, "content");
temp = cJSON_GetArrayItem(music, index);
temp = cJSON_GetObjectItem(temp, "linkUrl");
printf("ready to play url is %s\n", temp->valuestring);
audio_player_stop(aplayer);
audio_player_play(aplayer, temp->valuestring);
}
else if (!strcmp(data, "step")) {
if (status == playing) {
status = pause;
audio_player_pause(aplayer);
}
else if (status == pause) {
status = playing;
audio_player_resume(aplayer);
}
}
}
else if (!strcmp(cmd, "mode.set")) {
// 播放模式
if (!strcmp(data, "sequence")) mode = sequence;
else if (!strcmp(data, "random")) mode = random;
else if (!strcmp(data, "single")) mode = single;
else if (!strcmp(data, "loop")) mode = loop;
}
else if (!strcmp(cmd, "change.set")) {
// 歌曲切换
// TODO: update
if (!strcmp(data, "prev")) {
// 上一首
index = old_index;
}
else if (!strcmp(data, "next")) {
// 下一首
old_index = index;
index = play_judge_f(index, count, mode);
}
else if (!strcmp(data, "change")) {
// 换一首
old_index = index;
index = play_judge_f(index, count, mode);
}
if (index == -1) {
// 播放结束
cJSON_Delete(root);
audio_player_stop(aplayer);
root = NULL;
index = 0;
old_index = 0;
count = 0;
status = idle;
}
else {
// 待播放指定的音频
status = idle;
}
}
else if (!strcmp(cmd, "play.choose.update")) {
// 播放特定歌曲
// TODO: update
int find = 0;
int i = 0;
cJSON *temp = cJSON_Parse(data);
temp = cJSON_GetObjectItem(temp, "linkUrl");
cJSON *music = cJSON_GetObjectItem(root, "content");
cJSON *xx;
for (i = 0; i < count; i++) {
xx = cJSON_GetArrayItem(music, i);
xx = cJSON_GetObjectItem(xx, "linkUrl");
if (!strcmp(xx->valuestring, temp->valuestring)) {
find = 1;
break;
}
}
if (find) {
old_index = index;
index = i;
printf("ready to play url is %s\n", temp->valuestring);
audio_player_stop(aplayer);
audio_player_play(aplayer, temp->valuestring);
}
else {
// 播放歌曲不在播放列表里面
printf("wwwwwwwwwwwwwwwwwwwwwwwwwww\n");
}
}
else if (!strcmp(cmd, "play.collect.choose")) {
// 收藏歌曲
}
else if (!strcmp(cmd, "play.uncollect.choose")) {
// 取消收藏
}
else if (!strcmp(cmd, "player.end") && root) {
// 播放器播放结束
// TODO: update
old_index = index;
index = play_judge_f(index, count, mode);
printf("play_judge_f index is %d\n", index);
if (index == -1) {
// 播放结束
audio_player_stop(aplayer);
cJSON_Delete(root);
root = NULL;
index = 0;
old_index = 0;
count = 0;
status = idle;
}
else {
// 播放指定的音频
cJSON *temp, *music;
music = cJSON_GetObjectItem(root, "content");
temp = cJSON_GetArrayItem(music, index);
temp = cJSON_GetObjectItem(temp, "linkUrl");
printf("ready to play url is %s\n", temp->valuestring);
audio_player_stop(aplayer);
audio_player_play(aplayer, temp->valuestring);
}
}
pthread_mutex_unlock(&music_mutex);
}
int play_judge_f(int index, int count, int mode) {
// sequence, random, single, loop
if (mode == 0) {
// 顺序播放
if (index + 1 == count) return -1;
else return index + 1;
}
else if (mode == 1) {
// 随机播放
srand(time(0));
return rand() % count;
}
else if (mode == 2) {
// 单曲循环
return index;
}
else if (mode == 3) {
// 循环播放
return (index + 1) % count;
}
else return -1;
}