Текущее время: 22 май 2018, 09:06

Город ХОББИ

Занятие любимым хобби - это путь к счастливой жизни!

Игра "Змейка" на Ардуино

Тут собраны различные проекты на Ардуино
Аватар пользователя
 
Сообщений: 661
Зарегистрирован: 27 мар 2013, 23:12

Игра "Змейка" на Ардуино

Сообщение -=dp=- » 20 мар 2018, 23:45

Игра "Змейка" на Ардуино
Для создания игры "Змейка" на Ардуино нам понадобятся:
1 - плата контроллера Ардуино УНО
2 - плата расширения LCD KeyPad шилд
3 - кабель microUSB > USB

Купить Ардуино в Калининграде можно тут: http://newmar.ru
Изображение
Изображение
Подключение сводится в соединении шилда с платой контроллера Ардуино УНО.

Далее, загружаем архивы с библиотеками LiquidCrystal.zip, LCDKeypad.zip, Adafruit_Circuit_Playground.zip, Adafruit_Sensor.zip
LiquidCrystal.zip
Игра "Змейка" на Ардуино
(18.58 KiB) Скачиваний: 22

Adafruit_Circuit_Playground.zip
Игра "Змейка" на Ардуино
(125.12 KiB) Скачиваний: 23

Adafruit_Sensor.zip
Игра "Змейка" на Ардуино
(6.59 KiB) Скачиваний: 23

Библиотека LCDKeypad.zip выложена в следующем посте, так как на форуме установлено ограничение не более 3-х вложений в одном посте
Распаковываем все библиотеки и копируем папки в папку libraries программы Arduino IDE.
Затем запускаем среду разработки Arduino IDE и копируем туда вот этот скетч:

Код: выделить все
#include <LiquidCrystal.h>
#include <LCDKeypad.h>
 
byte mySnake[8][8] =
{
{ B00000,
  B00000,
  B00011,
  B00110,
  B01100,
  B11000,
  B00000,
},
{ B00000,
  B11000,
  B11110,
  B00011,
  B00001,
  B00000,
  B00000,
},
{ B00000,
  B00000,
  B00000,
  B00000,
  B00000,
  B11111,
  B01110,
},
{ B00000,
  B00000,
  B00011,
  B01111,
  B11000,
  B00000,
  B00000,
},
{ B00000,
  B11100,
  B11111,
  B00001,
  B00000,
  B00000,
  B00000,
},
{ B00000,
  B00000,
  B00000,
  B11000,
  B01101,
  B00111,
  B00000,
},
{ B00000,
  B00000,
  B01110,
  B11011,
  B11111,
  B01110,
  B00000,
},
{ B00000,
  B00000,
  B00000,
  B01000,
  B10000,
  B01000,
  B00000,
}
};
 
boolean levelz[5][2][16] = {
{{false,false,false,false,false,false,false,false,false,false,false,false,false,false,false,false},
{false,false,false,false,false,false,false,false,false,false,false,false,false,false,false,false}},
{{true,false,false,false,false,false,false,false,false,false,false,false,false,false,false,true},
{true,false,false,false,false,false,false,false,false,false,false,false,false,false,false,true}},
{{true,false,false,false,true,false,false,false,false,false,false,true,false,false,false,true},
{true,false,false,false,false,false,false,false,true,false,false,false,false,false,false,true}},
{{true,false,true,false,false,false,false,false,false,true,false,false,false,true,false,false},
{false,false,false,false,true,false,false,true,false,false,false,true,false,false,false,true}}
};
LiquidCrystal lcd(8, 9, 4, 5, 6, 7);
unsigned long time, timeNow;
int gameSpeed;
boolean skip, gameOver, gameStarted;
int olddir;
int selectedLevel,levels;
int adc_key_val[5] ={50, 200, 400, 600, 800 };
int NUM_KEYS = 5;
int adc_key_in;
int key=-1;
int oldkey=-1;
boolean x[16][80];
byte myChar[8];
byte nullChar[8] = { 0x0,0x0,0x0,0x0,0x0,0x0,0x0,0x0 };
boolean special;
struct partdef
{
  int row,column,dir;
  struct partdef *next;
};
typedef partdef part;
 
part *head, *tail;
int i,j,collected;
long pc,pr;
 
void drawMatrix()
{
  int cc=0;
  if (!gameOver)
  {
  x[pr][pc] = true;
  //for (i=0;i<8;i++) lcd.createChar(i, nullChar);
  for(int r=0;r<2;r++)
  {
    for(int c=0;c<16;c++)
    {
      special = false;
      for(int i=0;i<8;i++)
      {
        byte b=B00000;
        if (x[r*8+i][c*5+0]) {b+=B10000; special = true;}
        if (x[r*8+i][c*5+1]) {b+=B01000; special = true;}
        if (x[r*8+i][c*5+2]) {b+=B00100; special = true;}
        if (x[r*8+i][c*5+3]) {b+=B00010; special = true;}
        if (x[r*8+i][c*5+4]) {b+=B00001; special = true;}
        myChar[i] = b;
      }
      if (special)
      {
        lcd.createChar(cc, myChar);
        lcd.setCursor(c,r);
        lcd.write(byte(cc));
        cc++;
      }
      else
      {
        lcd.setCursor(c,r);
        if (levelz[selectedLevel][r][c]) lcd.write(255);
        else lcd.write(254);
 }}}}}
 
void freeList()
{
  part *p,*q;
  p = tail;
  while (p!=NULL)
  {
    q = p;
    p = p->next;
    free(q);
  }
  head = tail = NULL;
}
 
void gameOverFunction()
{
  delay(1000);
  lcd.clear();
  freeList();
  lcd.setCursor(3,0);
  lcd.print("Game Over!");
  lcd.setCursor(4,1);
  lcd.print("Score: ");
  lcd.print(collected);
  delay(1000);
}
 
void growSnake()
{part *p;
  p = (part*)malloc(sizeof(part));
  p->row = tail->row;
  p->column = tail->column;
  p->dir = tail->dir;
  p->next = tail;
  tail = p;
}
 
void newPoint()
{part *p;
  p = tail;
  boolean newp = true;
  while (newp)
  {
    pr = random(16);
    pc = random(80);
    newp = false;
    if (levelz[selectedLevel][pr / 8][pc / 5]) newp=true;
    while (p->next != NULL && !newp)
    {
      if (p->row == pr && p->column == pc) newp = true;
      p = p->next;
    }
  }
  if (collected < 13 && gameStarted) growSnake();
}
 
void moveHead()
{
  switch(head->dir)
  {
    case 0: head->row--; break;
    case 1: head->row++; break;
    case 2: head->column++; break;
    case 3: head->column--; break;
    default : break;
  }
  if (head->column >= 80) head->column = 0;
  if (head->column < 0) head->column = 79;
  if (head->row >= 16) head->row = 0;
  if (head->row < 0) head->row = 15;
  if (levelz[selectedLevel][head->row / 8][head->column / 5]) gameOver = true;
  part *p;
  p = tail;
  while (p != head && !gameOver)
  {
    if (p->row == head->row && p->column == head->column) gameOver = true;
    p = p->next;
  }
  if (gameOver)
    gameOverFunction();
  else
  {
  x[head->row][head->column] = true;
  if (head->row == pr && head->column == pc)
  {
    collected++;
    if (gameSpeed < 25) gameSpeed+=3;
    newPoint();
 }}}
 
void moveAll()
{
  part *p;
  p = tail;
  x[p->row][p->column] = false;
  while (p->next != NULL)
  {
    p->row = p->next->row;
    p->column = p->next->column;
    p->dir = p->next->dir;
    p = p->next;
  }
  moveHead();
}
 
void createSnake(int n)
{
  for (i=0;i<16;i++)
    for (j=0;j<80;j++)
      x[i][j] = false;
         
  part *p, *q;
  tail = (part*)malloc(sizeof(part));
  tail->row = 7;
  tail->column = 39 + n/2;
  tail->dir = 3;
  q = tail;
  x[tail->row][tail->column] = true;
  for (i = 0; i < n-1; i++)
  {
    p = (part*)malloc(sizeof(part));
    p->row = q->row;
    p->column = q->column - 1;
    x[p->row][p->column] = true;
    p->dir = q->dir;
    q->next = p;
    q = p;
  }
  if (n>1)
  {
    p->next = NULL;
    head  = p;
  }
  else
  {
    tail->next = NULL;
    head = tail;
  }
}
 
void startF()
{
  gameOver = false;
  gameStarted = false;
  selectedLevel = 1;
  lcd.clear();
  lcd.setCursor(0,0);
  lcd.print("Select level: 1");
  for(i=0;i<8;i++)
  {
    lcd.createChar(i,mySnake[i]);
    lcd.setCursor(i+4,1);
    lcd.write(byte(i));
  }
  collected = 0;
  gameSpeed = 8;
  createSnake(3);
  time = 0;
}
void setup()
{levels = 5;
  lcd.begin(16, 2);
  startF();
}
 
void loop()
{ if (!gameOver && !gameStarted)
  { adc_key_in = analogRead(0);   
   key = get_key(adc_key_in);
   if (key != oldkey)   
   {delay(50); 
     adc_key_in = analogRead(0);
     key = get_key(adc_key_in);
     if (key != oldkey)   
     { oldkey = key;
       if (key >=0)
       { olddir = head->dir;
         if (key==1 && selectedLevel<levels) selectedLevel++;
         if (key==2 && selectedLevel>1) selectedLevel--;
         if (key==4)
         { lcd.clear();
           selectedLevel--;
           newPoint();
           gameStarted = true;
         }
         else
         { lcd.setCursor(14,0);
           lcd.print(selectedLevel);
  }}}}}
  if (!gameOver && gameStarted)
  {skip = false;
   adc_key_in = analogRead(0);
   key = get_key(adc_key_in);
   if (key != oldkey)
   {delay(50);
     adc_key_in = analogRead(0);
     key = get_key(adc_key_in);
     if (key != oldkey)   
     { oldkey = key;
       if (key >=0)
       { olddir = head->dir;
         if (key==0 && head->dir!=3) head->dir = 2;
         if (key==1 && head->dir!=1) head->dir = 0;
         if (key==2 && head->dir!=0) head->dir = 1;
         if (key==3 && head->dir!=2) head->dir = 3;
         if (olddir != head->dir)
         { skip = true;
           delay(1000/gameSpeed);
           moveAll();
           drawMatrix();
         }}}}
   if (!skip)
 {timeNow = millis();
     if (timeNow - time > 1000 / gameSpeed)
     {moveAll();
       drawMatrix();
       time = millis();
     } } }
  if(gameOver)
  {adc_key_in = analogRead(0);
   key = get_key(adc_key_in);
   if (key != oldkey)
   { delay(50);
     adc_key_in = analogRead(0);
     key = get_key(adc_key_in);
     if (key != oldkey)   
     {   oldkey = key;
       if (key >=0)
       {startF();
 }}}}}
int get_key(unsigned int input)
{ int k;
    for (k = 0; k < NUM_KEYS; k++)
    { if (input < adc_key_val[k])
      { return k;} } 
    if (k >= NUM_KEYS)k = -1;
    return k;}
 



Аватар пользователя
 
Сообщений: 661
Зарегистрирован: 27 мар 2013, 23:12

Re: Игра "Змейка" на Ардуино

Сообщение -=dp=- » 20 мар 2018, 23:48

Библиотека LCDKeypad.zip

LCDKeypad.zip
Библиотека LCDKeypad.zip
(12.67 KiB) Скачиваний: 25


После загрузки скетча , перезагружаем плату контроллера Ардуино , выбираем уровень кнопками вверх - вниз и наслаждаемся классической игрой в Змейку :D



Аватар пользователя
 
Сообщений: 661
Зарегистрирован: 27 мар 2013, 23:12

Re: Игра "Змейка" на Ардуино

Сообщение -=dp=- » 20 мар 2018, 23:53

Вот так это будет выглядеть

Arduino snake 1.jpg
Игра "Змейка" на Ардуино
Arduino snake 1.jpg (9.39 KiB) Просмотров: 194


Arduino snake 2.jpg
Игра "Змейка" на Ардуино
Arduino snake 2.jpg (11.02 KiB) Просмотров: 194


Arduino snake 3.jpg
Игра "Змейка" на Ардуино
Arduino snake 3.jpg (12.75 KiB) Просмотров: 194



Аватар пользователя
 
Сообщений: 661
Зарегистрирован: 27 мар 2013, 23:12

Re: Игра "Змейка" на Ардуино

Сообщение -=dp=- » 24 мар 2018, 12:43

:!: Отснял и выложил видео на ютюб :arrow: https://youtu.be/5vEn1yUhSY8




Вернуться в Проекты на Ардуино

Кто сейчас на форуме

Сейчас этот форум просматривают: нет зарегистрированных пользователей и гости: 0