1 #include "musicbox.h"
2 #include <stdio.h>
3 #include <stdlib.h>
4 #include <vfsdev/pwm_dev.h>
5
6 MENU_COVER_TYP musicbox_cover = {MENU_COVER_FUNC, NULL, NULL,
7 musicbox_cover_draw, 0};
8 MENU_TASK_TYP musicbox_tasks = {musicbox_init, musicbox_uninit};
9 MENU_TYP musicbox = {"musicbox", &musicbox_cover, &musicbox_tasks,
10 musicbox_key_handel, NULL};
11
12 static aos_task_t musicbox_task_handle;
13
14 #define NOTE_SPACE_RATIO 1.3
15
16 music_t *music_list[] = {
17 &Imperial_March,
18 &liang_zhi_lao_hu,
19 };
20
21 player_t musicbox_player = {music_list, 2, 0, 0, 0, 0};
22
musicbox_cover_draw(int * draw_index)23 void musicbox_cover_draw(int *draw_index)
24 {
25 int floating_y[] = {-5, -4, -3, -2, -1, 0, 1, 2, 3, 4,
26 5, 4, 3, 2, 1, 0, -1, -2, -3, -4};
27 OLED_Clear();
28
29 OLED_Icon_Draw(48, 16 + floating_y[*draw_index], &icon_note_32_32, 0);
30
31 OLED_Icon_Draw(2, 24, &icon_skip_left, 0);
32 OLED_Icon_Draw(122, 24, &icon_skip_right, 0);
33
34 (*draw_index)++;
35 if ((*draw_index) >= 20) {
36 (*draw_index) = 0;
37 }
38
39 OLED_Refresh_GRAM();
40 aos_msleep(100);
41 return 0;
42 }
43
musicbox_init(void)44 int musicbox_init(void)
45 {
46 OLED_Clear();
47 OLED_Refresh_GRAM();
48
49 musicbox_player.isPlaying = 0;
50 musicbox_player.cur_music_note = 0;
51 set_music_time();
52
53 aos_task_new_ext(&musicbox_task_handle, "musicbox_task", musicbox_task, NULL, 1024 * 4, AOS_DEFAULT_APP_PRI);
54 LOGI(EDU_TAG, "aos_task_new musicbox_task\n");
55 return 0;
56 }
57
musicbox_uninit(void)58 int musicbox_uninit(void)
59 {
60 noTone(0);
61 aos_task_delete(&musicbox_task_handle);
62 LOGI(EDU_TAG, "aos_task_delete musicbox_task\n");
63 return 0;
64 }
65
set_music_time()66 void set_music_time()
67 {
68 for (int i = 0; i < musicbox_player.music_list_len; i++) {
69 for (int n = 0; n < musicbox_player.music_list[i]->noteLength; n++) {
70 int noteDuration =
71 1000 / musicbox_player.music_list[i]->noteDurations[n];
72 noteDuration =
73 (noteDuration < 0) ? (-noteDuration * 1.5) : noteDuration;
74 musicbox_player.music_list[i]->musicTime +=
75 (noteDuration + (int)(noteDuration * NOTE_SPACE_RATIO));
76 }
77 }
78 }
79
next_song()80 void next_song()
81 {
82 musicbox_player.cur_music_index =
83 ((musicbox_player.cur_music_index ==
84 musicbox_player.music_list_len - 1) ?
85 (0) :
86 (musicbox_player.cur_music_index + 1));
87 LOGI(EDU_TAG, "cur_music_index %d\n", musicbox_player.cur_music_index);
88 musicbox_player.cur_music_note = 0;
89 musicbox_player.cur_music_time = 0;
90 musicbox_player.isPlaying = 1;
91 }
92
previous_song()93 void previous_song()
94 {
95 musicbox_player.cur_music_index =
96 ((musicbox_player.cur_music_index == 0) ?
97 (musicbox_player.music_list_len - 1) :
98 (musicbox_player.cur_music_index - 1));
99 LOGI(EDU_TAG, "cur_music_index %d\n", musicbox_player.cur_music_index);
100 musicbox_player.cur_music_note = 0;
101 musicbox_player.cur_music_time = 0;
102 musicbox_player.isPlaying = 1;
103 }
104
pause_resume()105 void pause_resume() { musicbox_player.isPlaying = !musicbox_player.isPlaying; }
106
musicbox_key_handel(key_code_t key_code)107 void musicbox_key_handel(key_code_t key_code)
108 {
109 switch (key_code) {
110 case 0b0001:
111 // pre
112 previous_song();
113 aos_msleep(1000);
114 break;
115 case 0b0100:
116 // next
117 next_song();
118 aos_msleep(1000);
119 break;
120 case 0b1000:
121 // pause/resume
122 pause_resume();
123 break;
124 default:
125 break;
126 }
127 }
128
tone(uint16_t port,uint16_t frequency,uint16_t duration)129 void tone(uint16_t port, uint16_t frequency, uint16_t duration)
130 {
131 int ret = -1;
132 int fd = 0;
133 char name[16] = {0};
134 float duty_cycle = 0.8;
135
136 snprintf(name, sizeof(name), "/dev/pwm%d", port);
137 fd = open(name, 0);
138 if (fd >= 0) {
139 if (frequency > 0) {
140 ret = ioctl(fd, IOC_PWM_FREQ, (unsigned long)frequency);
141 ret = ioctl(fd, IOC_PWM_DUTY_CYCLE, (unsigned long)&duty_cycle);
142 ret = ioctl(fd, IOC_PWM_ON, (unsigned long)0);
143 }
144 if (duration != 0) {
145 aos_msleep(duration);
146 }
147 if (frequency > 0 && duration > 0) {
148 ret = ioctl(fd, IOC_PWM_OFF, (unsigned long)0);
149 close(fd);
150 }
151 }
152 }
153
noTone(uint16_t port)154 void noTone(uint16_t port)
155 {
156 int ret = -1;
157 int fd = 0;
158 char name[16] = {0};
159 float duty_cycle = 0.8;
160 int freq = 1;
161 unsigned int period_s;
162
163 snprintf(name, sizeof(name), "/dev/pwm%d", port);
164 fd = open(name, 0);
165 if (fd >= 0) {
166 ret = ioctl(fd, IOC_PWM_FREQ, (unsigned long)freq);
167 ret = ioctl(fd, IOC_PWM_DUTY_CYCLE, (unsigned long)&duty_cycle);
168 ret = ioctl(fd, IOC_PWM_ON, (unsigned long)0);
169 ret = ioctl(fd, IOC_PWM_OFF, (unsigned long)0);
170 close(fd);
171 }
172 }
173
musicbox_task()174 void musicbox_task()
175 {
176 while (1) {
177 OLED_Clear();
178 music_t *cur_music =
179 musicbox_player.music_list[musicbox_player.cur_music_index];
180
181 char show_song_name[14] = {0};
182 sprintf(show_song_name, "%-13.13s", cur_music->name);
183 OLED_Show_String(14, 4, show_song_name, 16, 1);
184
185 if (musicbox_player.isPlaying) {
186 if (musicbox_player.cur_music_note < cur_music->noteLength) {
187 int noteDuration =
188 1000 /
189 cur_music->noteDurations[musicbox_player.cur_music_note];
190 noteDuration =
191 (noteDuration < 0) ? (-noteDuration * 1.5) : noteDuration;
192 LOGI(EDU_TAG, "note[%d] = %d\t delay %d ms\n",
193 musicbox_player.cur_music_note,
194 cur_music->noteDurations[musicbox_player.cur_music_note],
195 noteDuration);
196 int note = cur_music->notes[musicbox_player.cur_music_note];
197 tone(0, note, noteDuration);
198 aos_msleep((int)(noteDuration * NOTE_SPACE_RATIO));
199 musicbox_player.cur_music_time +=
200 (noteDuration + (int)(noteDuration * NOTE_SPACE_RATIO));
201 musicbox_player.cur_music_note++;
202 } else {
203 noTone(0);
204 aos_msleep(1000);
205 next_song();
206 }
207 OLED_Icon_Draw(54, 36, &icon_pause_24_24, 1);
208 } else {
209 OLED_Icon_Draw(54, 36, &icon_resume_24_24, 1);
210 aos_msleep(500);
211 }
212
213 OLED_DrawLine(14, 26, 14, 29, 1);
214 OLED_DrawLine(117, 26, 117, 29, 1);
215 OLED_DrawLine(16, 27,
216 (int)(16 + 99.0 * (musicbox_player.cur_music_time * 1.0 /
217 cur_music->musicTime)),
218 27, 1);
219 OLED_DrawLine(16, 28,
220 16 + 99.0 * (musicbox_player.cur_music_time * 1.0 /
221 cur_music->musicTime),
222 28, 1);
223 OLED_Icon_Draw(94, 36, &icon_next_song_24_24, 1);
224 OLED_Icon_Draw(14, 36, &icon_previous_song_24_24, 1);
225 OLED_Refresh_GRAM();
226 }
227 }
228