【平头哥RVB2601创意应用开发】7 随机字母落下的效果
[复制链接]
上一期实现了字母落下,摩尔斯电码输入消除字母后分数显示。
这一期要实现随机字母下落。怎么办呢?
简单粗暴的方法,是对数组进行排序。
重温一下,结构体数组:
int size = 36;
struct Obj{
char name[20];
char code[20];
lv_obj_t *label;
int x;
int y;
}objs[36]={
{"A",".-"},
{"B","-..."},
{"C","-.-."},
{"D","-.."},
{"E","."},
{"F","..-."},
{"G","--."},
{"H","...."},
{"I",".."},
{"J",".---"},
{"K","-.-"},
{"L",".-.."},
{"M","--"},
{"N","-."},
{"O","---"},
{"P",".--."},
{"Q","--.-"},
{"R",".-."},
{"S","..."},
{"T","-"},
{"U","..-"},
{"V","...-"},
{"W",".--"},
{"X","-..-"},
{"Y","-.--"},
{"Z","--.."},
{"0","-----"},
{"1",".----"},
{"2","..---"},
{"3","...--"},
{"4","....-"},
{"5","....."},
{"6","-...."},
{"7","--..."},
{"8","---.."},
{"9","----."},
};
之后,对其循环,把lvgl的label标签对象加上去,注意下面我注释的内容:
for(int i=0;i<size;i++){
objs[i].label=lv_label_create(lv_scr_act(), NULL);
objs[i].x=10 + rand() % (128-30);
objs[i].y=-1*(rand() % size)-30; //这里重点是这个随机数,不是为了y轴坐标,而是用来排序的!
lv_obj_set_pos(objs[i].label, objs[i].x, objs[i].y);
lv_obj_set_size(objs[i].label, 20, 20);
lv_label_set_text(objs[i].label, objs[i].name);
}
之后,再用循环,完成排序:
for (int i = 0; i < size; ++i){
for (int j = i + 1; j < size; ++j){
if (objs[i].y < objs[j].y){
struct Obj temp = objs[i];
objs[i] = objs[j];
objs[j] = temp;
}
}
}
再循环一次,重新排完序的结构体数组重新设置y轴。
for(int i=0;i<size;i++){
objs[i].y=-1*30*i;
}
至于下落,还是老样子,在while中循环,每隔一定时间,让结构体的y轴+1:
for(int i=0;i<size;i++){
objs[i].y+=1;
lv_obj_set_pos(objs[i].label, objs[i].x, objs[i].y);
}
另外,本期还优化了上期一段代码,用于分数的显示:
优化前:用strcat拼接字符串实现分数的显示
sprintf(value, "%d", score);
strcat(text_score,value);
lv_label_set_text(score_label,text_score);
优化后,用lv_label_set_text_fmt方法,可以自己设置模板文本:
lv_label_set_text_fmt(score_label, "score: %d", score);
最后:
gui_game_task全部代码:
static void gui_game_task(void *arg)
{
lv_init();
oled_init();
time_t t;
srand((unsigned) time(&t));
int looptime = 0;
int score=0;//分数初始为0
int status=0;//初始状态为 0 游戏中 1 胜利 2 失败 3
lv_obj_t *text_gameover = lv_label_create(lv_scr_act(), NULL);
lv_obj_set_pos(text_gameover, 28, 30);
lv_obj_set_size(text_gameover, 128, 60);
lv_label_set_text(text_gameover, "");
//输入的标签
lv_obj_t *text_input = lv_label_create(lv_scr_act(), NULL);
lv_obj_set_pos(text_input, 100, 50);
lv_obj_set_size(text_input, 80, 20);
lv_label_set_text(text_input, "");
lv_obj_t *score_label = lv_label_create(lv_scr_act(), NULL);
lv_obj_set_pos(score_label, 0, 0);
lv_obj_set_size(score_label, 128, 30);
lv_label_set_text_fmt(score_label, "score: %d", score);
int size = 36;
struct Obj{
char name[20];
char code[20];
lv_obj_t *label;
int x;
int y;
}objs[36]={
{"A",".-"},
{"B","-..."},
{"C","-.-."},
{"D","-.."},
{"E","."},
{"F","..-."},
{"G","--."},
{"H","...."},
{"I",".."},
{"J",".---"},
{"K","-.-"},
{"L",".-.."},
{"M","--"},
{"N","-."},
{"O","---"},
{"P",".--."},
{"Q","--.-"},
{"R",".-."},
{"S","..."},
{"T","-"},
{"U","..-"},
{"V","...-"},
{"W",".--"},
{"X","-..-"},
{"Y","-.--"},
{"Z","--.."},
{"0","-----"},
{"1",".----"},
{"2","..---"},
{"3","...--"},
{"4","....-"},
{"5","....."},
{"6","-...."},
{"7","--..."},
{"8","---.."},
{"9","----."},
};
for(int i=0;i<size;i++){
objs[i].label=lv_label_create(lv_scr_act(), NULL);
objs[i].x=10 + rand() % (128-30);
objs[i].y=-1*(rand() % size)-30;
lv_obj_set_pos(objs[i].label, objs[i].x, objs[i].y);
lv_obj_set_size(objs[i].label, 20, 20);
lv_label_set_text(objs[i].label, objs[i].name);
}
for (int i = 0; i < size; ++i){
for (int j = i + 1; j < size; ++j){
if (objs[i].y < objs[j].y){
struct Obj temp = objs[i];
objs[i] = objs[j];
objs[j] = temp;
}
}
}
for(int i=0;i<size;i++){
objs[i].y=-1*30*i;
}
status=1;
while (1) {
/* Periodically call the lv_task handler.
* It could be done in a timer interrupt or an OS task too.*/
lv_task_handler();
if(status==1){
looptime+=1;
if(looptime % 15 ==0){
for(int i=0;i<size;i++){
objs[i].y+=1;
lv_obj_set_pos(objs[i].label, objs[i].x, objs[i].y);
}
if(objs[size-1].y>64){
lv_label_set_text(text_gameover, "GameOver");
status = 3; //game over
}
}
}
if(GPIO_PIN_LOW == csi_gpio_pin_read(&key1)) {
//当低电平(按下时)
if(button1_pressed==0){
// 如果button1的状态没有被按下,则设为按下
button1_pressed = 1;
}
if(button1_pressed==1){
//如果button1的状态是按下,则计时
time_for_pressed++;
}
}
if(GPIO_PIN_HIGH == csi_gpio_pin_read(&key1)) {
if(button1_pressed==0){
nopress_time++;
if(nopress_time>30){
//check_input();
for(int i=0;i<size;i++){
if(objs[i].y>0 && objs[i].y<64){
//在可视区间
if(strcmp(input,objs[i].code)==0){
lv_label_set_text(objs[i].label, "");
char value[10];
char text_score[20]="score:";
score++;
lv_label_set_text_fmt(score_label, "score: %d", score);
}
}
}
strcpy(input,"");
lv_label_set_text(text_input,"");//输入效果清空
//check win
//if status == playing
if(score==size){
//status == "win"
}
}
}
if(button1_pressed==1){
nopress_time=0;
printf("%d",time_for_pressed);
//通过判断time_for_pressed的大小,得出是长按还是短按
if(time_for_pressed>20){
//长按
printf("-");
strcat(input,"-");
}else{
//短按
printf(".");
strcat(input,".");
}
lv_label_set_text(text_input,input);//输入效果
time_for_pressed=0;//恢复计数
button1_pressed = 0;
}
}
if(GPIO_PIN_LOW == csi_gpio_pin_read(&key2)) {
if(button2_pressed==0){
button2_pressed=1;
}
}
if(GPIO_PIN_HIGH == csi_gpio_pin_read(&key2)) {
if(button2_pressed==1){
printf("\n");
button2_pressed=0;
strcpy(input,"");
lv_label_set_text(text_input,"");//输入效果清空
}
}
aos_msleep(5);
lv_tick_inc(1);
}
}
效果:
|