LinkedIn YouTube Facebook
Szukaj

Wstecz
Artykuły

ZL31ARM: sterowanie kulki i obroty bryły w 3D za pomocą czujnika MEMS LIS35

Również parametry czasowe, jak ograniczenie w czasie i opóźnienie są podawane (wartości te są przykładowe i mogą zostać swobodnie zmieniane w zależności od potrzeb):

LIS35_WriteRegister(LIS35_CLICK_TIME_LIMIT,0x0F);	// 7.5 msec
LIS35_WriteRegister(LIS35_CLICK_LATENCY,0x07);	// 7 msec

Na koniec zostaje jeszcze włączenie generacji sygnału przerwania po wykryciu kliknięcia:

//Poziom niski (log. 0) - przerwanie aktywne
//Linia podciagnieta do (+) w STM32
//Przerwanie na linii INT1 po wystapieniu klikniecia
LIS35_WriteRegister(LIS35_CR3,0x87);

Po skonfigurowaniu czujnika wg powyższego wzoru (konfigurację przerwań z kontrolerem NVIC przedstawiono przy konfiguracji projektu) można skorzystać z funkcji EXTI0_IRQHandler i odpowiednio reagować za zdarzenia w postaci kliknięć:

void EXTI0_IRQHandler(void){
  LIS35_ReadRegister(LIS35_CLICK_SRC, &rx_data);

  if(rx_data | 0x10){
    color = color << 4;	//Kolejny kolor
    if(color > 0xF00) color = 0x00F;
    setBallColor(color);	//Zmien kolor kulki

    //Zmien stan wyswietlania diody na przeciwny
    GPIO_WriteBit(GPIOB, GPIO_Pin_1, (BitAction)((1 - GPIO_ReadOutputDataBit(GPIOB,
                  GPIO_Pin_1))));
  }

  // Czyszczenie flagi przerwania
  EXTI_ClearITPendingBit(EXTI_Line0);
}

Obracanie figury

Wykorzystując wiedzę nabytą w poprzednim punkcie można zrealizować obracanie figurą 3D za pomocą odchylenia akcelerometru od pozycji neutralnej (osie X i Y są równoległe do powierzchni Ziemi). Im dłużej jest on odchylony tym coraz szybciej figura się obraca, a im większy jest kąt pochylenia tym większe przyśpieszenie kątowe otrzymuje obracający się obiekt. Również uwzględnia się tarcie, które powoduje, że prędkość kątowa w dowolnej osi maleje do zera w pozycji neutralnej akcelerometru. Funkcja realizująca powyższe zamierzenie jest podobna do tej opisanej z kulką na stole wirtualnym z niewielką różnicą; wielkości liniowe zostały zamienione na kątowe:

#define Ts		1	//Okres probkowania
#define Tstrat	1	//Wspolczynnik strat na skutek tarcia
void rotatingFigure(){
  signed short x_orient=0, y_orient=0;	//Zmienne orientacji
  signed short x_angle=0, y_angle=0;	//Zmienne katowe
  signed short Wx=0, Wy=0;			//Zmienne predkosci katowej
  signed short delta_x=0, delta_y=0;	//Zmienne przemieszczenia katowego

  while(1){
    drawCube(0, 0, x_angle, y_angle, 0, 0x000);	//Usun stara figure

    LIS35_GetPosition(&x, &y, &z);			//Odczyt wartosci przyspieszen

    //Korekta wskazan akcelerometru
    x+=_xKor;
    y+=_yKor;
    z+=_zKor;

    //Wyznaczanie aktualnej predkosci katowej
    Wx += (x/5)*Ts;
    Wy += (y/5)*Ts;

    //Uwzglednienie strat na skutek tarcia
    if(Wx > 0) Wx -= Tstrat;
    else if(Wx < 0) Wx += Tstrat;
    else Wx = 0;
    if(Wy > 0) Wy -= Tstrat;
    else if(Wy < 0) Wy += Tstrat;
    else Wy = 0;

    //Wyznaczanie aktualnego przemieszczenia katowego
    delta_x = Wx*Ts;
    delta_y = Wy*Ts;

    //Wyznaczanie aktualnej orientacji
    x_orient += delta_x;
    y_orient += delta_y;
		
    //Pobranie katow w zakresie -+360 stopni
    x_angle = x_orient % 360;
    y_angle = y_orient % 360;

    drawCube(0, 0, x_angle, y_angle, 0, 0xFFF);	//Rysuj nowa obrocona figure
    Delay(0xFFFF);	//Ustawienie okresu aktualizacji pomiaru/obrazu
  }
}
Autor: Jan Szemiet