cancel
Showing results for 
Search instead for 
Did you mean: 

Trying to do an encoder with an FSM

OMart.6
Associate

Hello, right now im trying to do an encoder as a project for my digital electronics class. I've done it in two different ways, by functions and by switch cases, and neither seem to work. I have to make it so every time a switch of states ocurr within the two sensors (i.e. 00 to 10 to 11 to 01 to 00 again) the counter in two 7seg displays adds a 1, all the way up to 99, but for some reason giving it the required entrances doesnt make it change states and stays in 00. Can you help me? I'll write my code below (in the function based program)

#include "main.h"

#include <math.h>

#include <stdio.h>

void SystemClock_Config(void);

static void MX_GPIO_Init(void);

uint8_t number[10]={

0x3F,0x06,0x5B,0x4F,0x66,0x6D,0x7D,0x07,0x7F,0x67

};

uint8_t swipe[2]={

0x01,0x02

};

uint16_t inp[4]={

0x0000, 0x0002, 0x0003, 0x0001

};

enum states{

STATE_A = 0,

STATE_B = 1,

STATE_C = 2,

STATE_D = 3

};

typedef enum states State_Type;

void state_a_function(void);

void state_b_function(void);

void state_c_function(void);

void state_d_function(void);

void state_machine_init(void);

void display(int j,int i);

static void (*state_table[])(void) = {

state_a_function,

state_b_function,

state_c_function,

state_d_function

};

static State_Type current_state;

static int j,i,encoder;

int main(void)

{

 HAL_Init();

 SystemClock_Config();

 MX_GPIO_Init();

 while (1)

 {

 encoder = GPIOA -> IDR;

 state_table[current_state]();

 HAL_Delay(6);

 }

}

void state_machine_init(void){

current_state = STATE_A;

}

void state_a_function(void){

display (j,i);

if(encoder == inp[1]){

if(i<99){i++;}

else if (i>=99){i=0;};

current_state = STATE_B;

}

else if(encoder == inp[3]){

if(i>0){i--;}

else if (i<=0){i=99;};

current_state = STATE_D;

};

}

void state_b_function(void){

display(j,i);

if(encoder == inp[2]){

if(i<99){i++;}

else if (i>=99){i=0;};

current_state = STATE_C;

}

else if(encoder == inp[0]){

if(i>0){i--;}

else if (i<=0){i=99;};

current_state = STATE_A;

};

}

void state_c_function(void){

display(j,i);

if(encoder == inp[3]){

if(i<99){i++;}

else if (i>=99){i=0;};

current_state = STATE_D;

}

else if(encoder == inp[1]){

if(i>0){i--;}

else if (i<=0){i=99;};

current_state = STATE_B;

};

}

void state_d_function(void){

display(j,i);

if(encoder == inp[0]){

if(i<99){i++;}

else if (i>=99){i=0;};

current_state = STATE_A;

}

else if(encoder == inp[2]){

if(i>0){i--;}

else if (i<=0){i=99;};

current_state = STATE_C;

};

}

void display(int j, int i){

for(j=0;j<2;j++){

  GPIOC -> ODR=swipe[j];

  HAL_Delay(3);

  if (j==0){

  GPIOB -> ODR= number[(int)floor(i/10)];

  HAL_Delay(3);

  }

  else if(j==1){

  GPIOB -> ODR= number[(int)(i%10)];

  HAL_Delay(3);

  }

 }

}

2 REPLIES 2
GLaure
Senior

One error:

state_machine_init() is never called, therefore current_state is something random and not STATE_A.

true! thanks for the observation :') sadly, the problem still persists. I've seen that the problem is in the "if" statements, where i compare the int encoder (the input) to my list of values wanted inp[]. Somehow, even though im giving it the input, the values somehow dont match or dont work. Maybe its got something to do with the format, but i dont really know.