質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.35%
C

C言語は、1972年にAT&Tベル研究所の、デニス・リッチーが主体となって作成したプログラミング言語です。 B言語の後継言語として開発されたことからC言語と命名。そのため、表記法などはB言語やALGOLに近いとされています。 Cの拡張版であるC++言語とともに、現在世界中でもっとも普及されているプログラミング言語です。

マイコン

マイクロコンピュータの略で、CPUにマイクロプロセッサを用いたコンピュータのこと。家電製品、電磁機器などの制御に用いられています。単体でコンピュータとしての機能を一通り備えています。 現代のパーソナルコンピュータに近く、同時期のメインフレームやミニコンピュータと比べ、小さいことが特徴です。

Q&A

解決済

1回答

1308閲覧

c言語 マイコンでのゲーム作り うまく動かず困っています

tmk727

総合スコア2

C

C言語は、1972年にAT&Tベル研究所の、デニス・リッチーが主体となって作成したプログラミング言語です。 B言語の後継言語として開発されたことからC言語と命名。そのため、表記法などはB言語やALGOLに近いとされています。 Cの拡張版であるC++言語とともに、現在世界中でもっとも普及されているプログラミング言語です。

マイコン

マイクロコンピュータの略で、CPUにマイクロプロセッサを用いたコンピュータのこと。家電製品、電磁機器などの制御に用いられています。単体でコンピュータとしての機能を一通り備えています。 現代のパーソナルコンピュータに近く、同時期のメインフレームやミニコンピュータと比べ、小さいことが特徴です。

0グッド

0クリップ

投稿2021/11/19 14:35

編集2021/11/20 13:56

前提・実現したいこと

8X8のLEDと2個のスイッチがついたマイコンを使って簡単なゲームをつくろうとしています。ですがゲーム画面になってからうまく動かずに困っています。ゲームの動きとしては、最初の画面で一番下の段が光っており、次に光っている部分の1個上の段が光り、左右に移動しているのでそれをタイミングよくボタンを押して止めるといったものです。下の部分と上の部分の光っている部分が一つでも一致したら、成功でさらにその上の段が光り、同じことを繰り返すといったものです。イメージとしては、昔テレビ番組でやっていた東京フレンドパークという番組ののストッパーキューブリッチというゲームみたいな動きをします。

発生している問題・エラーメッセージ

エラーメッセージはないのですが、うまく機能していない部分があり、一番下が光った状態でその上ではなく2個上が光ってしまったり、謎に右端が縦にひかってしまいます。また、ボタンを押して止めた部分の光が保持されません。じぶんでも修正を試みたのですがうまくいかなくて困っております。

該当のソースコード

c言語 #include<string.h> #include<stdio.h> #include "user.h" unsigned char i; //カウンタ unsigned char s_count = 0; // つなげることに成功した回数(最大6回) unsigned char game_flag = 0; //画面遷移の変数 void user_init(void) { _sound(33, 2); } void appear_bridge(){ //橋の出現 caseのほうがいいのかな? if(s_count == 0){ led[6] = 0x1f; }else if(s_count == 1){ led[5] = 0xf1; }else if(s_count == 2){ led[4] = 0x0f; }else if(s_count == 3){ led[3] = 0x0f; }else if(s_count == 4){ led[2] = 0x07; }else if(s_count == 5){ led[1] = 0x03; }else if(s_count == 6){ led[0] = 0x01; } } void shift() //ライトを左右に動かすメソッド { static unsigned char span_cnt = 0; static unsigned char move_left = 0; char height = 6 - s_count; if (span_cnt++ > 10){ // 1s span_cnt = 0; if(led[height] & 0b10000000) move_left = 0; if(led[height] & 0b00000001) move_left = 1; if(move_left) led[height] = led[height] << 1; else led[height] = led[height] >> 1; } } void fresh(){ for (i=0; i<8; i++) led[i] = 0; } void game(void) { led[7] = 0xff; shift(); if(sw_flag){ sw_flag = 0; char height = 6 - s_count; if (led[height] = led[height+1] && led[height]){ s_count++; } else{ // 失敗 game_flag = 0; fresh(); return; } _sound(33, 1); char chata = 5;// チャタリング対策 while(chata>0) chata--; appear_bridge(); } if(s_count == 6){ // クリア _sound(33, 10); game_flag = 0; } } void title(void) { if(sw_flag){ //ボタン押されたらゲーム画面に遷移 sw_flag = 0; game_flag = 1; s_count = 0; appear_bridge(); } } void user_main(void) { switch(game_flag){ case 0: title(); //初期画面に遷移(スタートしたときや失敗したとき) break; case 1: game(); //ゲーム画面に遷移 break; } }
フレームワーク user.h #include <stdint.h> typedef unsigned char uchar; #define LED_SZ 8 enum{ BEEP_HIGH = 46, BEEP_LOW = 168, BEEP_C4 = 238, BEEP_D4 = 212, BEEP_E4 = 189, BEEP_F4 = 178, BEEP_G4 = 158, BEEP_A4 = 141, BEEP_B4 = 126, BEEP_C5 = 118, }; extern void _wait(uint8_t wait); extern uint8_t _rand(void); extern void _sound(uint8_t tone, uint8_t length); extern volatile uint8_t sw_flag; extern volatile uint8_t sw; extern volatile uint8_t led[LED_SZ]; extern void user_init(void); extern void user_main(void);

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

thkana

2021/11/19 22:35

まずは質問の文章を完成させましょう。 プログラムも未完成な感じがしますが、それはまぁ質問そのものに関わることかも知れないので。
y_waiwai

2021/11/19 23:52

上手く動かないとはどういうふうに上手く動かないのか説明しよう
jimbe

2021/11/20 07:55

本文が「~ 一番下が光った状態から、」で切れているのを直して頂きたいです。
tmk727

2021/11/20 13:57

コメントありがとうございます。自分の不手際で説明が抜けてしまっていました。申し訳ありません。修正いたしましたので。読んでいただけると幸いです。
jimbe

2021/11/20 14:42

まず、tmk727 さんの言われる "マイコン" の仕様が全く分かりませんので、コードの見た目だけからの判断です。 if (led[height] = led[height+1] && led[height]){ の && は & の間違いではないでしょうか。
thkana

2021/11/21 00:41

編集で随分プログラム変わったみたいですけれど... 「自分でできるとこまでやったモノ」として一旦は確定させてから質問してくださいね。 わからないところがあるのは仕方ないけれど、自分の考えも固まらないドロドロをぶつけられるのは勘弁して欲しいし、回答考えたりしているうちに質問のほうがコロコロ変わっていくんじゃたまらないので。 ところで、そのフレームワークってのは、user_main()を繰り返し呼び出すのですか? また、フレームワークのスイッチの検出の仕様はどのようになっていますか?
nac_tnk

2021/11/21 05:23

だいぶ良くなったね。 最初はどうなるかと思ったけど。 2,3日ほっといたら完成するかも?
tmk727

2021/11/21 08:51

あれから jimbeさんの提案や、友人の助言を受け、完成させることができました!皆さんのおかげです。本当にありがとうございます。
nac_tnk

2021/11/21 09:01

自分で解決するのが一番だよ。 残りは主に判定部分だけだったからね。最初のやつは変なとこがいっぱいあったけど。 回答で、出来たコード貼って解決済みにするといいよ。
tmk727

2021/11/21 09:01

thkana さんへ、貴重な時間を割いていただいているのにもかかわらず、自分の都合で更新してしまい申し訳ありません。今後はそのようなことがないよう気を付けたいと思います。
guest

回答1

0

自己解決

前提・実現したいこと

8X8のLEDと2個のスイッチがついたマイコンを使って簡単なゲームをつくろうとしています。ですがゲーム画面になってからうまく動かずに困っています。ゲームの動きとしては、最初の画面で一番下の段が光っており、次に光っている部分の1個上の段が光り、左右に移動しているのでそれをタイミングよくボタンを押して止めるといったものです。下の部分と上の部分の光っている部分が一つでも一致したら、成功でさらにその上の段が光り、同じことを繰り返すといったものです。イメージとしては、昔テレビ番組でやっていた東京フレンドパークという番組ののストッパーキューブリッチというゲームみたいな動きをします。

発生している問題・エラーメッセージ

エラーメッセージはないのですが、うまく機能していない部分があり、一番下が光った状態でその上ではなく2個上が光ってしまったり、謎に右端が縦にひかってしまいます。また、ボタンを押して止めた部分の光が保持されません。じぶんでも修正を試みたのですがうまくいかなくて困っております。

該当のソースコード

c言語 #include<string.h> #include<stdio.h> #include "user.h" unsigned char i; //カウンタ unsigned char s_count = 0; // つなげることに成功した回数(最大6回) unsigned char game_flag = 0; //画面遷移の変数 void user_init(void) { _sound(33, 2); } void appear_bridge(){ //橋の出現 caseのほうがいいのかな? if(s_count == 0){ led[6] = 0x1f; }else if(s_count == 1){ led[5] = 0x1f; }else if(s_count == 2){ led[4] = 0x0f; }else if(s_count == 3){ led[3] = 0x0f; }else if(s_count == 4){ led[2] = 0x07; }else if(s_count == 5){ led[1] = 0x03; }else if(s_count == 6){ led[0] = 0x01; } } void shift() //ライトを左右に動かすメソッド { static unsigned char span_cnt = 0; static unsigned char move_left = 0; char height = 6 - s_count; if (span_cnt++ > 10){ // 1s span_cnt = 0; if(led[height] & 0b10000000) move_left = 0; if(led[height] & 0b00000001) move_left = 1; if(move_left) led[height] = led[height] << 1; else led[height] = led[height] >> 1; } } void fresh(){ for (i=0; i<8; i++) led[i] = 0; } void game(void) { led[7] = 0xff; shift(); if(sw_flag){ sw &= sw_flag; if(sw >= 1){ char height = 6 - s_count; if (led[height] = led[height+1] & led[height]){ s_count++; } else{ // 失敗 game_flag = 0; fresh(); return; } sw_flag = 0; _sound(33, 1); char chata = 5000;// チャタリング対策 while(chata>0) chata--; appear_bridge(); } if(s_count == 7){ // クリア _sound(33, 10); game_flag = 0; } } } void title(void) { if(sw_flag){ //ボタン押されたらゲーム画面に遷移 sw &= sw_flag; if(sw >= 1){ game_flag = 1; s_count = 0; appear_bridge(); } sw_flag =0; } } void user_main(void) { switch(game_flag){ case 0: title(); //初期画面に遷移(スタートしたときや失敗したとき) break; case 1: game(); //ゲーム画面に遷移 break; } }
フレームワーク user.h /* user.h emb-88 フレームワーク(ヘッダ) Created: 2018/06/02 Author : Daisuke Takago, Osamu Tamura */ #ifndef _USER_HEADER_ #define _USER_HEADER_ #include <stdint.h> #define LED_SZ 8 /* ブザー用 */ enum { BEEP_HIGH = 46, BEEP_LOW = 168, BEEP_C4 = 238, BEEP_D4 = 212, BEEP_E4 = 189, BEEP_F4 = 178, BEEP_G4 = 158, BEEP_A4 = 141, BEEP_B4 = 126, BEEP_C5 = 118 }; /* システム定義 */ extern void _wait(uint8_t wait); // 時間待ち extern uint8_t _rand(void); // 擬似乱数生成 extern void _sound(uint8_t tone, uint8_t length); // ブザー extern volatile uint8_t sw_flag; // 押しボタン変化フラグ(手動クリア) extern volatile uint8_t sw; // 押しボタン状態 extern volatile uint8_t led[LED_SZ]; // マトリクスLED /* ユーザー定義 */ extern void user_init(void); // 起動時に呼ばれる extern void user_main(void); // 0.1秒ごとに呼ばれる #endif // _USER_HEADER_

投稿2021/11/21 08:59

tmk727

総合スコア2

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

nac_tnk

2021/11/21 17:33

いやいや、これまだ出来ていないでしょ。 ・重なっていたら残し、重なっていなければ消す。 ・一つでも重なっていたらクリア(次のライン) という部分が出来ていないと思うけど。 uint8_t result=0; for(uint8_t i=0; i<8; i++) {//列を検査 if((led[height]&(1<<i))&&(led[height+1]&(1<<i))) {//重なっていれば result=1; } else led[height]&=~(1<<i);//重なっていなければ消す } if(result) {//成功 s_count++; } else { // 失敗 game_flag = 0; fresh(); return; } のような感じじゃない?
jimbe

2021/11/21 18:30 編集

led[height] = led[height+1] & led[height] がまさにそれではないでしょうか。
nac_tnk

2021/11/21 19:23

あぁ。そうだね。 よく見れば、スマートに書いてある。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.35%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問