Mục lục:

Arduino - Piano Tiles: 16 bước (có hình ảnh)
Arduino - Piano Tiles: 16 bước (có hình ảnh)

Video: Arduino - Piano Tiles: 16 bước (có hình ảnh)

Video: Arduino - Piano Tiles: 16 bước (có hình ảnh)
Video: Biến hình khi văn phòng Schannel có khách đến 2024, Tháng bảy
Anonim
Arduino - Gạch Piano
Arduino - Gạch Piano

Xin chào những người sử dụng internet, Đây sẽ là bài viết về cách tạo ra thứ DEFINITELY không phải là trò chơi di động trên arduino una r3.

vì vậy để bắt đầu, bạn sẽ cần tất cả các bộ phận như sau! 1x Arduino Uno r3 ($ 42)

2x Tấm chắn bàn phím LCD ($ 19 mỗi chiếc)

Nút 5x

Điện trở 5x 220Ω

28x dây

Được rồi, khi bạn đã có tất cả các phần, đã đến lúc bắt đầu!

Bước 1: Đấu dây

Đấu dây
Đấu dây
Đấu dây
Đấu dây
Đấu dây
Đấu dây

Bắt đầu bằng cách kết nối arduino của bạn và bạn bè như trong sơ đồ, Đảm bảo rằng các nút được liên kết với nhau theo đúng cách xung quanh, với các khe A0-4 ở mặt đất của đường ray nút, nếu không arduino sẽ nghĩ rằng các nút đang được nhấn liên tục thay vì chỉ khi nhấn.

Bước 2: Tuyên bố Tuyên bố

Tất cả mã ở đây nên đi trước thiết lập void và vòng lặp void của bạn, điều này là do tất cả các biến và đối tượng này được sử dụng trong một số hàm mà chúng tôi sẽ thiết lập.

Bắt đầu bằng cách đặt:

#bao gồm

ở đầu mã của bạn, điều này nói với arduino sử dụng thư viện "LiquidCrystal.h" và các chức năng là một phần của nó.

Bước tiếp theo là xác định các chân mà chúng tôi đang sử dụng cho các nút của mình bằng cách đặt mã này vào bên dưới #include:

#define btnEnter A0 # define btn1 15 #define btn2 16 #define btn3 17 #define btn4 18

Chúng tôi xác định các thuật ngữ btnEnter và btn1 thành btn 4 để giúp chúng tôi đọc mã dễ dàng hơn hoặc thay đổi nếu cần thiết. Có nghĩa là khi chúng ta gõ btn1, arduino sẽ biết chúng ta thực sự có nghĩa là nút 15. Mặc dù chúng ta đang gọi các cổng là cổng 15, 16, 17 và 18, chúng được gắn nhãn trên arduino là A1 A2 A3 và A4, điều này là do chúng là các cổng được sử dụng đặc biệt cho đầu vào tương tự, mặc dù chúng tôi chỉ sử dụng chúng cho đầu vào kỹ thuật số.

Tiếp theo, chúng ta sẽ tạo các đối tượng sẽ điều khiển Màn hình tinh thể lỏng. Để làm điều này, hãy đặt mã này bên dưới định nghĩa của chúng tôi

LiquidCrystal lcdLeft (8, 9, 12, 10, 11, 13); LiquidCrystal lcdRight (2, 3, 4, 5, 6, 7);

Điều này nói với arduino rằng khi chúng ta gọi lcdLeft hoặc lcdRight, chúng ta đang tham chiếu đến một đối tượng LiquidCrystal. Các số trong dấu ngoặc đính kèm cho arduino biết đối tượng nên sử dụng cổng nào để gửi thông báo đến màn hình LCD khi chúng ta sử dụng các chức năng của chúng.

Bây giờ chúng ta cần khai báo các biến bằng cách đặt bit mã tiếp theo bên dưới khai báo đối tượng:

// các biến này là các tùy chọn mà bạn có thể thay đổi - số cao hơn = tốc độ trò chơi nhanh hơn.int intGameSpeedEasy = 10; int intGameSpeedMedium = 25; int intGameSpeedHard = 80;

// thiết lập các biến cho gameboolean bolPlay; // theo dõi nếu người chơi int intScore; // theo dõi điểm của người chơi int intDiff; // chỉ là một trò chơi để cho biết độ khó của trò chơi là gì // thiết lập các biến cho đầu vào int intEnter; // theo dõi nếu người dùng nhấn nút nhập int intInput; // theo dõi những nút nào người dùng nhấn boolean bolTilePressed; // đảm bảo người chơi không vô tình nhấn nút 5x và mất // thiết lập các biến cho turn int intTick; // đếm lên mili (mỗi vòng lặp) cho đến khi intDelay int intDelay; // thời gian chương trình đợi đến lượt tiếp theo tính bằng millis int intGameSpeed; // abit các tùy chọn gỡ lỗi boolean bolSerialBoard; // khi true sẽ in bảng trong màn hình nối tiếp

Chúng tôi khai báo một biến bằng cách nêu kiểu dữ liệu và sau đó là tên của biến, ví dụ: int thisIsAnInteger

Các biến Boolean, chẳng hạn như bolSerialBoard và bolPlay chỉ có thể có một trong hai giá trị, đúng hoặc sai.

Biến số nguyên (int) như intScore và intInput có thể nhận các số nguyên làm giá trị, chẳng hạn như 1, 5 hoặc 100.

Một số kiểu dữ liệu đáng chú ý khác mà chúng tôi không sử dụng ở đây là chuỗi, là một đoạn văn bản và float, là số thập phân.

Mỗi biến ở đây được chương trình sử dụng ở một số nơi khác nhau, đây là tóm tắt về những gì mỗi biến làm

bolPlay cho chương trình biết menu sẽ được hiển thị hoặc trò chơi thực sự có đang chạy hay không.

intScore theo dõi điểm số của người chơi khi họ xếp gạch, intDiff được sử dụng trên menu chính để cho chương trình biết bit văn bản nào cần in trên màn hình LCD, intEnter được sử dụng để cho chương trình biết nếu nút enter (ngoài cùng bên trái) được nhấn, intInput được sử dụng để cho chương trình biết nút nào trong số 4 nút còn lại được nhấn.

bolTilePressed được sử dụng để đảm bảo chương trình chỉ đọc khi nút được nhấn chứ không phải khi nó được giữ.

intGameSpeed, intGameSpeedEasy, intGameSpeedMedium và intGameSpeedHard được sử dụng để kiểm soát tốc độ của trò chơi dựa trên độ khó được chọn.

intTick và intDelay được sử dụng để ngăn chương trình di chuyển bảng mỗi khi nó lặp lại.

bolSerialBoard được sử dụng để cho phép bạn thực hiện chương trình gửi bo mạch đến màn hình nối tiếp của arduino dưới dạng một chuỗi số cho mục đích thử nghiệm.

Cuối cùng, đã đến lúc khai báo bảng của chúng ta dưới dạng một mảng bằng cách sử dụng mã này:

// thiết lập trò chơi arrayint arrGame [16] [4] = {{0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}};

Mảng là một ma trận mà bất kỳ điểm nào trên đó có thể được gọi cho phép toán hoặc được thay đổi.

Mã của bạn bây giờ sẽ trông giống như thế này;

// bao gồm các thư viện # bao gồm

// các biến này là các tùy chọn mà bạn có thể thay đổi - số cao hơn = tốc độ trò chơi nhanh hơn

int intGameSpeedEasy = 10; int intGameSpeedMedium = 25; int intGameSpeedHard = 80;

// Xác định chân

#define btnEnter A0 #define btn1 15 #define btn2 16 #define btn3 17 #define btn4 18

// tạo các đối tượng LCD (n, ~, n, ~, ~, n)

LiquidCrystal lcdLeft (8, 9, 12, 10, 11, 13); LiquidCrystal lcdRight (2, 3, 4, 5, 6, 7);

// thiết lập mảng trò chơi

int arrGame [16] [4] = {{0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}};

// thiết lập các biến cho trò chơi

boolean bolPlay; // theo dõi nếu người chơi int intScore; // theo dõi điểm của người chơi int intDiff; // chỉ là một thứ giả tưởng để cho biết độ khó của trò chơi

// thiết lập các biến cho đầu vào

int intEnter; // theo dõi nếu người dùng nhấn nút nhập int intInput; // theo dõi những nút nào người dùng nhấn boolean bolTilePressed; // đảm bảo người chơi không vô tình nhấn nút 5x và thua cuộc

// thiết lập các biến cho lượt

int intTick; // đếm lên mili (mỗi vòng lặp) cho đến khi intDelay int intDelay; // thời gian chương trình chờ đến lượt tiếp theo tính bằng millis int intGameSpeed;

// bỏ qua các tùy chọn gỡ lỗi

boolean bolSerialBoard; // khi true sẽ in bảng trong màn hình nối tiếp

Bước 3: Chức năng thiết lập

Vòng lặp thiết lập là một hàm được arduino đọc một lần khi nó khởi động lần đầu.

Trong vòng lặp thiết lập, chúng tôi chỉ đặt giá trị của một vài biến của chúng tôi bởi vì thay vì đặt chúng một giá trị khi khai báo chúng, chúng tôi đang thực hiện ở đây.

Bắt đầu bằng cách đặt mã này vào Thiết lập Void của bạn.

bolPlay = false; intScore = 0; intTick = 0; intDelay = 1000; intDiff = 1; intGameSpeed = intGameSpeedMedium;

Mỗi dòng chỉ là thiết lập một biến thành một giá trị.

bolPlay được đặt thành false để trò chơi không bắt đầu chơi.

intScore được đặt thành 0, vì đương nhiên điểm của bạn bắt đầu từ 0.

intTick bắt đầu từ 0 vì chương trình hiện không đếm bất kỳ thứ gì.

intDelay được đặt thành 1000 vì đó là tỷ lệ các ô bắt đầu.

intDiff chỉ là một thứ khổ hạnh để chương trình biết phải viết gì cho độ khó của trò chơi.

intGameSpeed được đặt thành bất kỳ intGameSpeedMedium, có nghĩa là nó được đặt ở độ khó trung bình.

Tiếp theo đặt mã này vào Thiết lập Void bên dưới mã bạn vừa đặt.

lcdLeft.begin (16, 2); lcdRight.begin (16, 2);

Serial.begin (9600);

Điều này yêu cầu arduino bắt đầu giao tiếp với máy tính thông qua màn hình nối tiếp (có thể nhìn thấy bằng cách nhấp vào nút ở trên cùng bên phải của arduino IDE).

Thiết lập Void của bạn bây giờ sẽ trông giống như thế này!

void setup () {Serial.begin (9600); // khởi động màn hình nối tiếp // thiết lập các biến bolPlay = false; intScore = 0; intTick = 0; intDelay = 1000; intDiff = 1; intGameSpeed = intGameSpeedMedium; // begin lcd's lcdLeft.begin (16, 2); lcdRight.begin (16, 2); }

Bước 4: Chức năng vòng lặp

Hàm loop được chạy bởi arduino mỗi lần lặp lại arduino.

Sao chép mã sau vào Void Loop của bạn.

void loop () {input (); // kiểm tra đầu vào đang chơi if (bolPlay == true) {if (intTick> = intDelay) {// kiểm tra xem trò chơi có nên chơi một lượt hay tiếp tục chờ Serial.println ("~~~~~~~ ~~ "); // in ra để biểu thị bảng di chuyển trên // writeSerial (); // nếu tùy chọn được kích hoạt, hãy ghi bảng vào serial buttonGame (); // kiểm tra đầu vào của trình phát playBoard (); // di chuyển bảng và thêm một ô mới clearLcd (); // làm sạch màn hình LCD trước khi vẽ drawBoard (); // vẽ bảng lên bottomCheck () của màn hình LCD; intTick = 0; // đặt lại intTick} else {buttonGame (); // kiểm tra đầu vào trình phát clearLcd (); // làm sạch màn hình LCD trước khi vẽ drawBoard (); // vẽ bảng lên màn hình LCD intTick = intTick + intGameSpeed; // thêm vào dấu tích}} else {clearLcd (); // làm sạch màn hình LCD trước khi vẽ title (); // hiển thị tiêu đề và điểm thông tin các nútMenu (); // đọc đầu vào trình phát clearBoard (); // đảm bảo cả bảng = 0} delay (10); // trì hoãn arduino trong giây lát}

khi bolPlay bằng true có nghĩa là trò chơi đang chơi và tất cả mã khi trò chơi đang chơi sẽ được chạy, nhưng chúng tôi chỉ muốn bảng thêm một ô mới và di chuyển xuống khi intTick lớn hơn intDelay của chúng tôi, nếu không, chúng tôi vẫn muốn cho phép người dùng nhấn một nút để nhấn một ô và để intTick tăng tốc độ.

Hầu hết mã này sử dụng các chức năng mà chúng tôi chưa thực hiện và chúng tôi sẽ thực hiện chúng trong các bước tiếp theo. Mục đích của các chức năng này như sau.

Đầu vào đọc các nút mà người dùng đã nhấn.

Các nút Trò chơi kiểm soát chức năng của các nút khi ở trong trò chơi chứ không phải trong menu

playBoard thêm một ô mới vào bảng, sau đó di chuyển mọi thứ trong bảng xuống một khoảng trống

clearLCD làm sạch màn hình LCD để đảm bảo không để lại bóng mờ phía sau các ô

drawBoard đi qua arrGame và in nó lên màn hình LCD

clearBoard xóa toàn bộ arrGame khi trò chơi không được chơi

bottomCheck kiểm tra phần dưới cùng của arrGame để tìm tình trạng lỗi

tiêu đề hiển thị tiêu đề của trò chơi và thông tin điểm số khi ở trên menu

menu nút điều khiển những gì người dùng nhập vào khi ở trong menu.

gameOver là một chức năng khác, mặc dù không được gọi ở đây vì nó được gọi trong chức năng bottomCheck và buttonGame.

Bước 5: Chức năng ClearLCD

để tạo một hàm, chúng tôi bắt đầu bằng cách thêm nó vào mã

void functionName () {

}

"functionName" có thể là bất kỳ thứ gì, miễn là nó chưa tồn tại.

Sao chép mã này vào chương trình của bạn:

void clearLcd () {for (int i = 0; i <= 15; i ++) {for (int ii = 0; ii <= 1; ii ++) {lcdLeft.setCursor (i, ii); lcdLeft.write (""); lcdRight.setCursor (i, ii); lcdRight.write (""); }}}

điều này chạy qua toàn bộ mảng bằng cách sử dụng 2 vòng lặp được đếm để đi qua mỗi điểm trên màn hình LCD và ghi một khoảng trắng.

Nếu không được đặt lại thành không có gì, màn hình LCD sẽ duy trì những gì đã được viết trước đó

Bước 6: Chức năng DrawBoard

sao chép mã này vào chương trình của bạn

void drawBoard () {for (int i = 1; i <= 15; i ++) {// vẽ collums 1 và 2 trên màn hình LCD bên trái // nếu gạch = 0 không viết gì, = 1 viết "#", = 2 ghi "@" lcdLeft.setCursor (i, 1); // đặt thành cột đầu tiên (xa nhất bên trái) if (arrGame [0] == 1) {lcdLeft.write ("#");} if (arrGame [0] == 2) {lcdLeft.write ("@");} lcdLeft.setCursor (i, 0); // đặt thành cột ghép thứ hai (giữa bên trái) if (arrGame [1] == 1) {lcdLeft.write ("#");} if (arrGame [1] == 2) {lcdLeft.write ("@");} lcdRight.setCursor (i, 1); // đặt thành cột thứ ba (giữa bên phải) if (arrGame [2] == 1) {lcdRight.write ("#");} if (arrGame [2] == 2) {lcdRight.write ("@");} lcdRight.setCursor (i, 0); // đặt thành cột thứ tư (ngoài cùng bên phải) if (arrGame [3] == 1) {lcdRight.write ("#");} if (arrGame [3] == 2) {lcdRight.viết("@");} } }

điều này sử dụng một vòng lặp để đi qua từng hàng của bảng, sau đó nó sẽ kiểm tra xem có cột nào trong hàng bằng 1 hoặc 2 hay không, dựa trên đó nó sẽ in trên màn hình LCD hoặc một thẻ bắt đầu bằng #, cho một ô chưa được hit, hoặc @ cho một ô hit.

Bước 7: Chức năng PlayBoard

sao chép mã này vào chương trình của bạn.

void playBoard () {for (int i = 0; i <= 3; i ++) {arrGame [0] = 0;} // xóa hàng trên cùng arrGame [0] [random (0, 4)] = 1; // thiết lập một điểm ngẫu nhiên ở hàng trên cùng làm ô lát for (int i = 15; i> = 1; i -) {// làm việc từ cuối bảng lên đầu for (int ii = 0; ii <= 3; ii ++) {// với mỗi collum arrGame [ii] = arrGame [i - 1] [ii]; }}}

mã này bắt đầu bằng cách xóa toàn bộ hàng trên cùng thành 0 hoặc không có ô, sau đó đặt một ô ngẫu nhiên thành ô 1 và bỏ ô.

Sau đó, nó đi qua một vòng đếm ngược lại, từ 15 đến 1, đặt hàng bằng bất kỳ hàng nào bên trên nó bằng, làm cho bảng di chuyển xuống màn hình LCD

Bước 8: Chức năng ClearBoard

sao chép mã này vào chương trình của bạn.

void clearBoard () {// đặt lại giá trị đánh dấu và trì hoãn intTick = 0; intDelay = 1000; // đi qua bảng và đặt mọi thứ thành 0 for (int i = 0; i <= 15; i ++) {for (int ii = 0; ii <= 3; ii ++) {arrGame [ii] = 0; }}}

Mã này được chạy khi trò chơi không chơi để đảm bảo toàn bộ trò chơi được đặt thành 0 hoặc không có ô, bằng cách sử dụng các vòng đếm để đi qua mảng.

Mã cũng đặt lại các giá trị của intDelay và intTick.

Bước 9: Chức năng Tiêu đề

sao chép mã sau vào chương trình của bạn

void title () {// ghi tiêu đề lên LCD và khoảng trắng cho điểm lcdRight.setCursor (0, 0); lcdRight.write ("Gạch Piano"); lcdRight.setCursor (0, 1); lcdRight.write ("Điểm:"); // chuyển điểm thành chuỗi char strScore [3]; sprintf (strScore, "% d", intScore); // hiển thị điểm lên LCD lcdRight.write (strScore); // thêm diffictuly lcdRight.setCursor (10, 1); if (intDiff == 0) {lcdRight.write ("Dễ dàng"); } if (intDiff == 1) {lcdRight.write ("Phương tiện"); } if (intDiff == 2) {lcdRight.write ("Khó"); } // Nhấn một chút lệnh lcdLeft.setCursor (0, 0); lcdLeft.write ("Nhấn Enter"); lcdLeft.setCursor (0, 1); lcdLeft.write ("để bắt đầu!"); }

Mã này ghi tiêu đề của trò chơi và điểm số lên màn hình LCD, nó thực hiện điều này bằng cách cho màn hình LCD biết nơi bắt đầu nhập bằng LCD.setCursor và sau đó viết chuỗi vào LCD.write.

Một biến mới cũng được tạo ở đây, strScore, nó được sử dụng để chuyển intScore thành kiểu dữ liệu chuỗi hoặc char bằng cách sử dụng hàm sprintf.

intDiff cũng được sử dụng ở đây, dựa trên các giá trị của nó, nó in ra các tùy chọn độ khó khác nhau.

Bước 10: Chức năng ButtonsMenu

chèn mã sau vào chương trình của bạn

void buttonMenu () {// khi nhấn enter, bắt đầu trò chơi và đặt lại giá trị điểm if (intEnter == 1) {bolPlay = true; intScore = 0; Bạn chơi(); drawBoard (); } // khi nhấn nút 3, bật tùy chọn gỡ lỗi in bảng nối tiếp if (intInput == 3) {if (bolSerialBoard == false) {Serial.println ("Serial Board Active"); bolSerialBoard = true; } else {Serial.println ("Bảng mạch nối tiếp bị vô hiệu hóa"); bolSerialBoard = false; }} // đặt tốc độ trò chơi thành độ khó dễ if (intInput == 0) {Serial.print ("Trò chơi đặt thành dễ ("); Serial.print (intGameSpeedEasy); Serial.println ("ms tăng tốc)"); intDiff = 0; intGameSpeed = intGameSpeedEasy; } // thiết lập tốc độ trò chơi ở độ khó trung bình if (intInput == 1) {Serial.print ("Game đặt thành mức trung bình ("); Serial.print (intGameSpeedMedium); Serial.println ("ms tăng tốc)"); intDiff = 1; intGameSpeed = intGameSpeedMedium; } // đặt tốc độ trò chơi thành độ khó if (intInput == 2) {Serial.print ("Game đặt thành khó ("); Serial.print (intGameSpeedHard); Serial.println ("ms tăng tốc)"); intDiff = 2; intGameSpeed = intGameSpeedHard; }}

mã này chỉ được chạy khi bolPlay bằng false trong void Loop

nếu intEnter được đặt thành 1 có nghĩa là nút enter đã được nhấn, nếu nó đang được nhấn, chương trình sẽ đặt bolPlay thành true và trò chơi bắt đầu.

Sau đó, chương trình đọc intInput bằng với giá trị nào. nếu nó bằng 0, nút đầu tiên từ bên trái đang được nhấn, đi lên bên phải lên đến 3. Nếu intInput bằng 4 thì không có nút nào được nhấn.

nếu các nút 0-2 được nhấn, trò chơi sẽ thay đổi độ khó, đồng thời điều chỉnh giá trị tốc độ trò chơi, nghĩa là nó sẽ tăng tốc nhanh hơn.

nếu nút 3 được nhấn, trò chơi sẽ kích hoạt hoặc hủy kích hoạt chế độ gỡ lỗi trong đó toàn bộ bảng được in trong màn hình nối tiếp để hỗ trợ tìm kiếm sự cố trong chương trình.

Bước 11: Chức năng ButtonsGame

sao chép mã sau vào chương trình của bạn

void buttonGame () {if (intInput! = 4) {// nếu một nút được nhấn if (bolTilePressed == false) {// chỉ khi bolTilePressed là hành động kích hoạt sai để kiểm tra một nút nhấn bolTilePressed = true; // sau đó đặt bolTilePressed thành true để đảm bảo rằng nó không được kích hoạt ngẫu nhiên lần nữa int intLowestTile = 0; // được đặt thành ô có ô thấp nhất int intCheckedTile = 15; // để theo dõi ô nào đã được kiểm tra trong khi (intLowestTile == 0) {// miễn là nó không được đặt thành bất kỳ thứ gì kiểm tra ô cho (int i = 0; i 100) {// miễn là int độ trễ không thấp hơn 100 intDelay = intDelay - 20; // lấy một giá trị từ nó}} else {Serial.println ("Nhấn nhầm nút"); gameOver (); // nếu không thì trò chơi kết thúc}}}}}

Mã chỉ được chạy khi bolPlay bằng true trong void Loop.

Like buttonMenu dựa trên giá trị của intInput, nó sẽ kiểm tra xem người chơi có trúng ô hay bỏ sót một ô nào không.

Nó thực hiện điều này bằng cách đi qua arrGame từ dưới lên trên bằng vòng lặp while để tìm xem hàng nào thấp nhất với một ô xếp không có. Sau đó, nó sẽ kiểm tra xem vị trí trong hàng tương ứng với nút được nhấn có phải là ô trống hay không. chức năng mà chúng tôi chưa tạo.

Hàm này cũng sử dụng biến bolTilePressed bằng cách đặt nó thành true khi nhấn nút và false khi không nhấn nút nào. Điều này nhằm đảm bảo người dùng không vô tình rời khỏi trò chơi vì chương trình cho rằng họ đã nhấn nút nhiều lần khi nhấn giữ nó.

Bước 12: Chức năng GameOver

Sao chép mã sau vào chương trình của bạn

void gameOver () {Serial.println ("Trận đấu kết thúc!"); Serial.print ("Điểm của bạn là:"); Serial.println (intScore); Serial.print ("Tốc độ của bạn là:"); Serial.println (intDelay); bolPlay = false; }

Điều này được kích hoạt bởi các chức năng checkBottom hoặc buttonGame và kích hoạt kết thúc trò chơi bằng cách đặt bolPlay thành false.

Nó cũng in một thông báo vào màn hình nối tiếp để biết điểm số của người dùng và các ô tốc độ được thêm vào tính bằng mili giây.

Bước 13: Chức năng nhập liệu

Sao chép mã sau vào chương trình của bạn.

void input () {intEnter = digitalRead (btnEnter); // đọc enter // đọc đầu vào nào khác hoặc nếu không có đầu vào nào được đặt thành 4 if (digitalRead (btn1) == HIGH) {intInput = 0;} else {if (digitalRead (btn2) == HIGH) {intInput = 1;} else {if (digitalRead (btn3) == HIGH) {intInput = 2;} else {if (digitalRead (btn4) == HIGH) {intInput = 3;} else {intInput = 4; }}}} // in nối tiếp các đầu vào if (intEnter == 1) {Serial.println ("Enter Pressed!");} if (intInput! = 4) {Serial.print ("Nút Bấm:"); Serial.println (intInput); } else {// nếu không có nút nào được nhấn đặt lại bolTilePressed bolTilePressed = false; }}

Mã này được sử dụng với các chức năng buttonGame và buttonMenu. Dựa trên các nút mà người dùng đã nhấn, nó sẽ đặt giá trị của intInput, hoặc nếu không có nút nào được nhấn, nó sẽ đặt intInput bằng 4.

Nếu không có nút nào được nhấn, đây là nơi bolTilePressed được đặt lại cho chức năng buttonGame.

Nó cũng in một thông báo đến màn hình nối tiếp mà trên đó nút được nhấn.

Bước 14: Chức năng BottomCheck

sao chép mã sau vào chương trình của bạn.

void bottomCheck () {for (int i = 0; i <= 3; i ++) {// cho 4 cột if (arrGame [15] == 1) {// nếu một ô nằm ở cuối Serial.println ("Ngói ở dưới cùng"); arrGame [15] = 2; drawBoard (); chậm trễ (400); arrGame [15] = 1; drawBoard (); chậm trễ (400); arrGame [15] = 2; drawBoard (); chậm trễ (400); arrGame [15] = 1; drawBoard (); chậm trễ (400); gameOver (); }}}

bằng cách sử dụng một vòng lặp, mã này sẽ kiểm tra hàng dưới cùng của arrGame xem có bất kỳ ô nào không (ô bằng 1) hay không, nếu có ô chưa được xếp ở cuối màn hình, nó sẽ nhấp nháy ô và sau đó kích hoạt chức năng kết thúc trò chơi.

Bước 15: Hàm WriteSerial

sao chép mã sau vào chương trình của bạn

void writeSerial () {if (bolSerialBoard == true) {for (int i = 0; i <= 15; i ++) {for (int ii = 0; ii <= 3; ii ++) {Serial.print (arrGame [ii]); Serial.print (","); } Serial.println (""); }}}

Đây là chức năng tiếp theo là tùy chọn gỡ lỗi có thể được bật trong chức năng buttonMenu. Nếu bolSerialBoard được đặt thành true trong hàm đó, nó sẽ đi qua arrGame và in toàn bộ bảng vào màn hình nối tiếp cho mục đích thử nghiệm bằng cách sử dụng một mảng.

Bước 16: Hoàn thành

Hoàn thành!
Hoàn thành!

Tất cả mã của bạn không được hoàn chỉnh và trông giống như thế này!

/ * * Tên - Gạch Piano; Arduino * Bởi - Domenic Marulli * Ngày - 11 / *

/ bao gồm các thư viện

#bao gồm

// các biến này là các tùy chọn mà bạn có thể thay đổi - số cao hơn = tốc độ trò chơi nhanh hơn

int intGameSpeedEasy = 10; int intGameSpeedMedium = 25; int intGameSpeedHard = 80;

// Xác định chân

#define btnEnter A0 #define btn1 15 #define btn2 16 #define btn3 17 #define btn4 18

// tạo các đối tượng LCD (n, ~, n, ~, ~, n)

LiquidCrystal lcdLeft (8, 9, 12, 10, 11, 13); LiquidCrystal lcdRight (2, 3, 4, 5, 6, 7);

// thiết lập mảng trò chơi

int arrGame [16] [4] = {{0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}, {0, 0, 0, 0}};

// thiết lập các biến cho trò chơi

boolean bolPlay; // theo dõi nếu người chơi int intScore; // theo dõi điểm của người chơi int intDiff; // chỉ là một thứ giả tưởng để cho biết độ khó của trò chơi

// thiết lập các biến cho đầu vào

int intEnter; // theo dõi nếu người dùng nhấn nút nhập int intInput; // theo dõi những nút nào người dùng nhấn boolean bolTilePressed; // đảm bảo người chơi không vô tình nhấn nút 5x và thua cuộc

// thiết lập các biến cho lượt

int intTick; // đếm lên mili (mỗi vòng lặp) cho đến khi intDelay int intDelay; // thời gian chương trình chờ đến lượt tiếp theo tính bằng millis int intGameSpeed;

// bỏ qua các tùy chọn gỡ lỗi

boolean bolSerialBoard; // khi true sẽ in bảng trong màn hình nối tiếp

// thiết lập sẽ được chạy một lần

void setup () {Serial.begin (9600); // khởi động màn hình nối tiếp // thiết lập các biến bolPlay = false; intScore = 0; intTick = 0; intDelay = 1000; intDiff = 1; intGameSpeed = intGameSpeedMedium; // begin lcd's lcdLeft.begin (16, 2); lcdRight.begin (16, 2); }

// vòng lặp sẽ được chạy sau mỗi 10 mili-lít

void loop () {input (); // kiểm tra đầu vào đang chơi if (bolPlay == true) {if (intTick> = intDelay) {// kiểm tra xem trò chơi có nên chơi một lượt hay tiếp tục chờ Serial.println ("~~~~~~~ ~~ "); // in ra để biểu thị bảng di chuyển trên // writeSerial (); // nếu tùy chọn được kích hoạt, hãy ghi bảng vào serial buttonGame (); // kiểm tra đầu vào của trình phát playBoard (); // di chuyển bảng và thêm một ô mới clearLcd (); // làm sạch màn hình LCD trước khi vẽ drawBoard (); // vẽ bảng lên bottomCheck () của màn hình LCD; intTick = 0; // đặt lại intTick} else {buttonGame (); // kiểm tra đầu vào trình phát clearLcd (); // làm sạch màn hình LCD trước khi vẽ drawBoard (); // vẽ bảng lên màn hình LCD intTick = intTick + intGameSpeed; // thêm vào dấu tích}} else {clearLcd (); // làm sạch màn hình LCD trước khi vẽ title (); // hiển thị tiêu đề và điểm thông tin các nútMenu (); // đọc đầu vào trình phát clearBoard (); // đảm bảo cả bảng = 0} delay (10); // trì hoãn arduino trong giây lát}

// làm sạch màn hình LCD, vì vậy bất kỳ ô nào chưa được giải mã sẽ không còn ở đó

void clearLcd () {for (int i = 0; i <= 15; i ++) {for (int ii = 0; ii <= 1; ii ++) {lcdLeft.setCursor (i, ii); lcdLeft.write (""); lcdRight.setCursor (i, ii); lcdRight.write (""); }}}

// vẽ bảng lên màn hình LCD

void drawBoard () {for (int i = 1; i <= 15; i ++) {// vẽ collums 1 và 2 trên màn hình LCD bên trái // nếu gạch = 0 không viết gì, = 1 viết "#", = 2 ghi "@" lcdLeft.setCursor (i, 1); // đặt thành cột đầu tiên (xa nhất bên trái) if (arrGame [0] == 1) {lcdLeft.write ("#");} if (arrGame [0] == 2) {lcdLeft.write ("@");} lcdLeft.setCursor (i, 0); // đặt thành cột ghép thứ hai (giữa bên trái) if (arrGame [1] == 1) {lcdLeft.write ("#");} if (arrGame [1] == 2) {lcdLeft.write ("@");} lcdRight.setCursor (i, 1); // đặt thành cột thứ ba (giữa bên phải) if (arrGame [2] == 1) {lcdRight.write ("#");} if (arrGame [2] == 2) {lcdRight.write ("@");} lcdRight.setCursor (i, 0); // đặt thành cột thứ tư (ngoài cùng bên phải) if (arrGame [3] == 1) {lcdRight.write ("#");} if (arrGame [3] == 2) {lcdRight.viết("@");} } }

// di chuyển bảng xuống và đặt một giá trị ngẫu nhiên để làm ô

void playBoard () {for (int i = 0; i <= 3; i ++) {arrGame [0] = 0;} // xóa hàng trên cùng arrGame [0] [random (0, 4)] = 1; // thiết lập một điểm ngẫu nhiên ở hàng trên cùng làm ô lát for (int i = 15; i> = 1; i -) {// làm việc từ cuối bảng lên đầu for (int ii = 0; ii <= 3; ii ++) {// với mỗi collum arrGame [ii] = arrGame [i - 1] [ii]; }}}

// đặt toàn bộ bảng thành 0 và đặt lại các biến thành pregame

void clearBoard () {// đặt lại giá trị đánh dấu và trì hoãn intTick = 0; intDelay = 1000; // đi qua bảng và đặt mọi thứ thành 0 for (int i = 0; i <= 15; i ++) {for (int ii = 0; ii <= 3; ii ++) {arrGame [ii] = 0; }}}

// hiển thị Menu chính trên màn hình LCD

void title () {// ghi tiêu đề lên LCD và khoảng trắng cho điểm lcdRight.setCursor (0, 0); lcdRight.write ("Gạch Piano"); lcdRight.setCursor (0, 1); lcdRight.write ("Điểm:"); // chuyển điểm thành chuỗi char strScore [3]; sprintf (strScore, "% d", intScore); // hiển thị điểm lên LCD lcdRight.write (strScore); // thêm diffictuly lcdRight.setCursor (10, 1); if (intDiff == 0) {lcdRight.write ("Dễ dàng"); } if (intDiff == 1) {lcdRight.write ("Phương tiện"); } if (intDiff == 2) {lcdRight.write ("Khó"); } // Nhấn một chút lệnh lcdLeft.setCursor (0, 0); lcdLeft.write ("Nhấn Enter"); lcdLeft.setCursor (0, 1); lcdLeft.write ("để bắt đầu!"); }

// kiểm tra các nút và phải làm gì với chúng khi ở ngoài trò chơi

void buttonMenu () {// khi nhấn enter, bắt đầu trò chơi và đặt lại giá trị điểm if (intEnter == 1) {bolPlay = true; intScore = 0; Bạn chơi(); drawBoard (); } // khi nhấn nút 3, bật tùy chọn gỡ lỗi in bảng nối tiếp if (intInput == 3) {if (bolSerialBoard == false) {Serial.println ("Serial Board Active"); bolSerialBoard = true; } else {Serial.println ("Bảng mạch nối tiếp bị vô hiệu hóa"); bolSerialBoard = false; }} // đặt tốc độ trò chơi thành độ khó dễ if (intInput == 0) {Serial.print ("Trò chơi đặt thành dễ ("); Serial.print (intGameSpeedEasy); Serial.println ("ms tăng tốc)"); intDiff = 0; intGameSpeed = intGameSpeedEasy; } // thiết lập tốc độ trò chơi ở độ khó trung bình if (intInput == 1) {Serial.print ("Game đặt thành mức trung bình ("); Serial.print (intGameSpeedMedium); Serial.println ("ms tăng tốc)"); intDiff = 1; intGameSpeed = intGameSpeedMedium; } // đặt tốc độ trò chơi thành độ khó if (intInput == 2) {Serial.print ("Game đặt thành khó ("); Serial.print (intGameSpeedHard); Serial.println ("ms tăng tốc)"); intDiff = 2; intGameSpeed = intGameSpeedHard; }}

// kiểm tra các nút và phải làm gì với chúng khi ở trong trò chơi

void buttonGame () {if (intInput! = 4) {// nếu một nút được nhấn if (bolTilePressed == false) {// chỉ khi bolTilePressed là hành động kích hoạt sai để kiểm tra một nút nhấn bolTilePressed = true; // sau đó đặt bolTilePressed thành true để đảm bảo rằng nó không được kích hoạt ngẫu nhiên lần nữa int intLowestTile = 0; // được đặt thành ô có ô thấp nhất int intCheckedTile = 15; // để theo dõi ô nào đã được kiểm tra trong khi (intLowestTile == 0) {// miễn là nó không được đặt thành bất kỳ thứ gì kiểm tra ô cho (int i = 0; i 100) {// miễn là int độ trễ không thấp hơn 100 intDelay = intDelay - 20; // lấy một giá trị từ nó}} else {Serial.println ("Nhấn nhầm nút"); gameOver (); // nếu không thì trò chơi kết thúc}}}}}

void gameOver () {

Serial.println ("Trận đấu kết thúc!"); Serial.print ("Điểm của bạn là:"); Serial.println (intScore); Serial.print ("Tốc độ của bạn là:"); Serial.println (intDelay); bolPlay = false; }

// kiểm tra đầu vào của trình phát

void input () {intEnter = digitalRead (btnEnter); // đọc enter // đọc đầu vào nào khác hoặc nếu không có đầu vào nào được đặt thành 4 if (digitalRead (btn1) == HIGH) {intInput = 0;} else {if (digitalRead (btn2) == HIGH) {intInput = 1;} else {if (digitalRead (btn3) == HIGH) {intInput = 2;} else {if (digitalRead (btn4) == HIGH) {intInput = 3;} else {intInput = 4; }}}} // in nối tiếp các đầu vào if (intEnter == 1) {Serial.println ("Enter Pressed!");} if (intInput! = 4) {Serial.print ("Nút Bấm:"); Serial.println (intInput); } else {// nếu không có nút nào được nhấn đặt lại bolTilePressed bolTilePressed = false; }}

// kiểm tra phần dưới cùng của bảng xem có bị lỗi không

void bottomCheck () {for (int i = 0; i <= 3; i ++) {// cho 4 cột if (arrGame [15] == 1) {// nếu một ô nằm ở cuối Serial.println ("Ngói ở dưới cùng"); arrGame [15] = 2; drawBoard (); chậm trễ (400); arrGame [15] = 1; drawBoard (); chậm trễ (400); arrGame [15] = 2; drawBoard (); chậm trễ (400); arrGame [15] = 1; drawBoard (); chậm trễ (400); gameOver (); }}}

// in bảng vào màn hình nối tiếp nếu bolSerialBoard là true

void writeSerial () {if (bolSerialBoard == true) {for (int i = 0; i <= 15; i ++) {for (int ii = 0; ii <= 3; ii ++) {Serial.print (arrGame [ii]); Serial.print (","); } Serial.println (""); }}}

Khi tất cả mã được nhập, hãy tải lên arduino của bạn và tận hưởng!

Đề xuất: