2024-09-01 05:47 AM
So i started to learn stm32cubeide recently i decided to write a driver for AS5047u magnetic sensor using SPI and i can communicate with the IC with SPI. On reading the data i get a 16 bit value from it the first two bits are don't care bits and i have now 14 bits of data. How do i convert them into angles ? should i convert the 14bit Binary vaue into something else ??? This is the datasheet of the IC
https://look.ams-osram.com/m/48d90c982e0879e8/original/AS5047U-DS000637.pdf
Any help would be appreciated. Thank you
Solved! Go to Solution.
2024-09-01 08:59 AM
Which part, the one where the document explains you're sending data out, and getting it back later?
That each 16-bit frame has a CS around it, the bus is symmetrical, so you send the read command in one burst, but get the response in the next, and send a new command or NOP.
So Read ADD[ANGLEUNC] then Read ADD[NOP], the data you get back when clocking out the NOP will be the ANGLEUNC value.
2024-09-01 06:29 AM
Perhaps 360 / 16384 = 0.02197265625
Velocity quoted as 24.141 degrees/second/bit
https://github.com/Adrien-Legrand/AS5X47
https://github.com/Adrien-Legrand/AS5X47/blob/master/src/AS5X47.cpp#L71
https://github.com/jonas-merkle/AS5047P
https://github.com/jonas-merkle/AS5047P/blob/master/src/AS5047P.cpp#L227
2024-09-01 06:52 AM - edited 2024-09-01 06:54 AM
Why should i divide it by 16384?
Also the SPI data will be in binary right? what should i divide it with?
2024-09-01 07:25 AM
Why would you think? 2**14 = 16384
0 ..16383 relates to 0 to 359.99
You're trying to scale the full range 14-bit value into 360 degrees, or 2PI radians
Binary value, multiplied by 0.02197 to scale to degrees
2024-09-01 07:32 AM
Understood if i want to know the angle i should multiply the binary value by 0.02197 like this
HAL_GPIO_WritePin(GPIOA, GPIO_PIN_4, GPIO_PIN_RESET);
HAL_SPI_TransmitReceive(&hspi1, (uint8_t*)&angle_addr, data, 16, HAL_MAX_DELAY);
HAL_GPIO_WritePin(GPIOA, GPIO_PIN_4, GPIO_PIN_SET);
uint16_t value = (data[0]<<8) | data[1];
angle = value*0.02197.;
2024-09-01 07:57 AM
>>HAL_SPI_TransmitReceive(&hspi1, (uint8_t*)&angle_addr, data, 16, HAL_MAX_DELAY);
16 bytes? Also doesn't it return the response in a subsequent interaction? It's not going to know the address whilst you're shifting it in. That's what the NOP's for, to clear out the chain of requests.
Would probably mask or check the ER bits
https://look.ams-osram.com/m/48d90c982e0879e8/original/AS5047U-DS000637.pdf
Send a READ ANGLEUNC + NOP sequence as a 4-byte pattern
uint16_t value = ((data[2]<<8) | data[3]) & 0x3FFF;
float angle = (float)value*0.02197f;
2024-09-01 08:32 AM - edited 2024-09-01 09:34 AM
sorry i couldn't understand your second statement ERbits you mean the don't care bit rights yeah i changed it afterwards to remove the first two bits
You mean like this
while (1)
{
/* USER CODE END WHILE */
/* USER CODE BEGIN 3 */
HAL_GPIO_WritePin(GPIOA, GPIO_PIN_4, GPIO_PIN_RESET);
HAL_SPI_Transmit(&hspi1, (uint8_t*)&ANGLECOM, 16, HAL_MAX_DELAY);
HAL_GPIO_WritePin(GPIOA, GPIO_PIN_4, GPIO_PIN_SET);
HAL_GPIO_WritePin(GPIOA, GPIO_PIN_4, GPIO_PIN_RESET);
HAL_SPI_TransmitReceive(&hspi1, (uint8_t*)&NOP, data, 16, HAL_MAX_DELAY);
HAL_GPIO_WritePin(GPIOA, GPIO_PIN_4, GPIO_PIN_SET);
uint16_t value = ((data[0]<<8) | data[1]) & 0x3FFF;
angle = (float)value*0.02197f;
HAL_Delay(250);
}
2024-09-01 08:59 AM
Which part, the one where the document explains you're sending data out, and getting it back later?
That each 16-bit frame has a CS around it, the bus is symmetrical, so you send the read command in one burst, but get the response in the next, and send a new command or NOP.
So Read ADD[ANGLEUNC] then Read ADD[NOP], the data you get back when clocking out the NOP will be the ANGLEUNC value.
2024-09-01 09:14 AM
is my code in the above reply is correct?
2024-09-01 09:34 AM
I tried this and i get a value in the range of 0 to 360 degree but the live expressions doesn't seem to be updating