repo cleanup + MCU lectures 13-02-2025
@@ -18,7 +18,7 @@ When designing the drone I wanted to do everything parametric. So im going to tr
|
||||
I've had a little bit of experience in fusion. Mostly with making basic cases. But now I wanna learn how to design everything perfectly parametric so if I need to change a length everything will scale with it without me needing to fix some things
|
||||
|
||||
### Previous experience with Fusion360
|
||||
I've had some expierence using fusion with my university for making cases in projects. but it was never explicitly thought to me.
|
||||
I've had some experience using fusion with my university for making cases in projects. but it was never explicitly thought to me.
|
||||
|
||||
|
||||
### Designing parametrically
|
||||
@@ -151,7 +151,7 @@ After that I created a sketch on the front surface with a offset so I could extr
|
||||
After that I sketched the motor arms and sketched holes on top to cut the holes.
|
||||
|
||||
### Parameters
|
||||
The parameter menu is very nice in Onshape It is on the side of the screen and it doesn't close automaticly when modeling. Which is very nice.
|
||||
The parameter menu is very nice in Onshape It is on the side of the screen and it doesn't close automatically when modeling. Which is very nice.
|
||||
|
||||

|
||||
|
||||
@@ -184,7 +184,7 @@ Then the Z Euler rotation should appear.
|
||||
|
||||
After clicking that I went into the modifiers menu and added a Generator and enabled additive. This makes sure that the Z angle only keeps going up. So it keeps spinning indefinitely.
|
||||
|
||||
After that you can select everything and press `Control + L` and then link animation data so all the propelors do the same. Then it should look like this. And if you press space they should start spinning.
|
||||
After that you can select everything and press `Control + L` and then link animation data so all the propellors do the same. Then it should look like this. And if you press space they should start spinning.
|
||||
|
||||

|
||||
|
||||
|
@@ -19,21 +19,21 @@ everything is a circle or square or triangle. You can make anything with any pri
|
||||
### OpenScad
|
||||
Bas is teaching us how to use OpenScad
|
||||
|
||||

|
||||

|
||||
Everything needs to be within a function because otherwise it won't interact with eachother
|
||||
|
||||
If you place a # you can sort of debug and see where the shape is. Instead of blindly placing things
|
||||
|
||||

|
||||

|
||||
|
||||
You can declare variables by name=value;
|
||||
|
||||
Example:
|
||||

|
||||

|
||||
|
||||
|
||||
You can also do equations in openScad
|
||||

|
||||

|
||||
|
||||
The order of declaring variables matters. I found that out the hard way. because some variable wasn't working until I switched order.
|
||||
|
||||
|
@@ -0,0 +1,68 @@
|
||||
# Hardware debugging
|
||||
|
||||
## Microcontroller programming
|
||||
|
||||
### FabAcademy controller families
|
||||
* Atiny
|
||||
* SAMD
|
||||
* RP2050
|
||||
* ESP32
|
||||
|
||||
### Atiny
|
||||
* Programming: UPDI
|
||||
* Sandbox board: Adrianino
|
||||
* 20Mhz
|
||||
|
||||
### SAMD
|
||||
* programming: JTAG
|
||||
|
||||
### RP2040
|
||||
dual core ARM controller.
|
||||
hardcoded bootloader.
|
||||
|
||||
### ESP32 S3,C3,C6
|
||||
* Wifi bluetooth
|
||||
* RISC-V 160MHz
|
||||
|
||||
### choosing a programming language
|
||||
* MicroPython, Not power efficient
|
||||
* C/C++, Runs anywhere most power efficient
|
||||
* Circuitpython, less efficient than micropython but easier
|
||||
* Rust, Can work but its difficult. Same as C/C++
|
||||
|
||||
|
||||
### First steps when using microcontroller
|
||||
Make a LED blink
|
||||
|
||||
|
||||
|
||||
|
||||
logic analyzer to see signal (wokwi) (similar to oscilloscope)
|
||||
|
||||
define your problem into smaller pieces (same goes for coding)
|
||||
|
||||
|
||||
don't jump to conclusion. Most of the cases of hardware design fails is in the user.
|
||||
Write down everything you did.
|
||||
rubber ducky method
|
||||
|
||||
Use a microscope
|
||||
Don't panic when something doesn't work
|
||||
Check the
|
||||
* Traces
|
||||
* Soldering
|
||||
* Chips
|
||||
* Connections
|
||||
|
||||
Tools:
|
||||
* Multimeter
|
||||
* * Parallel measurement (check the cables)
|
||||
* * Continuity
|
||||
* * Diodes
|
||||
* Logic analyzer
|
||||
* Oscilloscope
|
||||
|
||||
|
||||
|
||||
|
||||
Step -> svg file
|
@@ -4,54 +4,55 @@
|
||||
## The laser cutter (BRM 90130)
|
||||
Today we got a tour on how to use the laser cutter and how it works and maintenance. This is our laser cutter. We first got thought the safety instructions. We always need to stand on the red platform and always watch the lasercutter while its busy.
|
||||
|
||||

|
||||

|
||||
|
||||
//TODO: add parameters of the laser
|
||||
### Where the laser gets made
|
||||
On the back of the machine there is a hatch and under there the laser gets generated.
|
||||
|
||||

|
||||

|
||||
You see a spiral tube with at the end a mirror that shoots the laser into the cutting chamber.
|
||||
|
||||

|
||||

|
||||
Here is a closer image of the mirror that shoots it into the chamber. The 3 screws on the mirror are to align the mirror. If the mirrors are misaligned the laser won't aim well or aim at all.
|
||||
|
||||
### The nozzle and calibration
|
||||

|
||||

|
||||
This is the nozzle. There is also a mirror there to redirect the laser down onto the material. There are a total of 3 mirrors. One in the laser chamber. and 1 on the arm of the nozzle and one on top of the nozzle to direct it down onto the material. The blue tube is a air tube that goes into the nozzle that constantly blows air so the material and gasses don't end up inside. We also did a test with and without the air tube. This is the result.
|
||||
|
||||

|
||||

|
||||
|
||||
The top square is without and the one below that is with the air tube attached. You can see that there is a small difference in how it cut. What I also noticed is there are a lot less flames when the tube is plugged in.
|
||||
|
||||
You can also disassemble the nozzle to clean the lens inside.
|
||||

|
||||

|
||||

|
||||

|
||||
The lens needs to be pointed up with the curved side so the laser collects and concentrates on one point and all the light gets bend to the center. otherwise you get cuts like this.
|
||||
|
||||

|
||||

|
||||
The top line cut is with a unfocused laser and the bottom line is with a focussed laser.
|
||||
But how do I focus the laser?
|
||||
There is a special tool to help you with that.
|
||||

|
||||

|
||||

|
||||

|
||||
|
||||
You place this on top of the material and then you can unscrew the nozzle a bit till it drops down on top of the plate like this.
|
||||
|
||||

|
||||

|
||||
|
||||
After you've tightened the nozzle again its focused and ready for cutting.
|
||||
|
||||
### Laser cutting machine safety
|
||||
Always stand near the laser cutting machine on the red platform. In case a fire breaks out spray it out with the water spray bottle on the side of the machine.
|
||||

|
||||

|
||||
|
||||
### Turning the machine on
|
||||
When we first turned on the machine it made a lot of noise. Laser cutters are very noisy machines. The power switch is the big red switch on the side.
|
||||
|
||||

|
||||

|
||||
|
||||
When you turn the switch you also need to press the green button to reset the machine. And turn the auxiliary switch on the enable the air pumps. You also need to enable the air filtration systems. That can be done using the red button on the power strip.
|
||||

|
||||

|
||||
|
||||
After that you need to wait for a minute for the systems to start up. After that we can finally begin cutting!
|
||||
|
||||
@@ -68,9 +69,9 @@ For testing the laser cutter we're gonna use cardboard, acrylic and wood.
|
||||
#### Cutting test
|
||||
Cutting cardboard is really easy but don't do it too slow otherwise you get what we got. We accidentally burned the cardboard during the cutting test when lasering the name in the cardboard. It probably burned because the heat was near one location for too long.
|
||||
|
||||

|
||||

|
||||
This is the result of our cutting. Cardboard got a really wide curve that you can cut.
|
||||

|
||||

|
||||
But when looking at the backside you do see a difference with how much it burned. From there I think the best values for cardboard are high power and high speed 100s/100p or medium speed and low power 40s/25p.
|
||||
|
||||
We also had one small little incident when we where cutting out the letters. The laser was too too each letter so the cardboard got hot and burned a little. We also noticed that our laser couldn't output a laser at 10 power. So that's why we stopped measuring it in the rest of the tests.
|
||||
@@ -78,42 +79,42 @@ These tests up here could be a fluke because all the minimum powers where left u
|
||||
|
||||
#### Karf test
|
||||
So we did all the test with exactly 10 centimeters. So there are 11 cuts.
|
||||

|
||||

|
||||
(100-97,45)/11=0.23181818181mm karf distance per line/cut
|
||||
|
||||
We also did a test with a full length piece to test if there are any biases.
|
||||

|
||||

|
||||
(100-99.62)/2=0.19mm
|
||||
|
||||
There is definitely some bias but that could be because cardboard can be squishy so maybe that's it.
|
||||
|
||||
#### Curve test
|
||||
In the first test we used 150 speed and 15 power. There the curves and edges of the laser where super good for example if you look at the E.
|
||||

|
||||

|
||||
|
||||
The second test we did with 200 speed and 15 power and there you can see around the edges that it burned more and the letters less. So either the minimum power needed to be decreased or the speed needs to be decreased for it to look better.
|
||||

|
||||

|
||||
|
||||
### Acrylic 4mm yellow
|
||||
|
||||
#### Cutting test
|
||||
We used the same test method as the cardboard but we found out that for 4mm thick acrylic you need high power and a super slow speed.
|
||||
|
||||

|
||||

|
||||
We first made the big one but we didn't have enough data on what speed and power where the best so we made an additional one with 10 speed and varying powers so we could figure out which where best. On an extra note: We dropped the big one and these 2 came out. With the smaller one the 2 fell out when we picked it up.
|
||||
|
||||
#### Kerf test
|
||||
We did multiple kerf tests because with the first one the material dropped down during the cutting because we didn't have the order of the cutting right. The second time we didn't have the tool at the correct height so the laser wasn't focussed properly. The last time we had everything right and that is our most accurate reading.
|
||||

|
||||

|
||||
First image where it dropped during cutting
|
||||

|
||||

|
||||
Second image where the Z offset wasn't right
|
||||

|
||||

|
||||
Third image where we did everything right
|
||||
|
||||
#### Focus test
|
||||
One of the lines of the focus test didn't go right because it was near an edge and the line bend. So we can't use of the lines to conclude something.
|
||||

|
||||

|
||||
You can see it start off thin then get a bit wider and then smaller. So the laser is focused, unfocused then focused. It's hard to see but its visible with the middle line
|
||||
|
||||
#### Extra Acrylic things
|
||||
@@ -122,20 +123,20 @@ You can mend acrylic together using acetone. You can also remove the laser frequ
|
||||
### Wood 9mm thick
|
||||
With 9 mm wood we had a lot of issues with cutting it. Because it is so thick it chars really easily and it's almost impossible to cut without charring
|
||||
|
||||

|
||||

|
||||
|
||||
#### Cutting test
|
||||
We tried to cut the wood but it really was engraving. We needed to add more passes along the wood, because we where trying to cut 9 millimeter thick wood.
|
||||
On the outer line we did 4 passes with 20 speed and 80 power and that didn't even cut through.
|
||||

|
||||

|
||||
We also did a couple of extra tests with Henk where he configured the laser. We got very close to cutting without charring but we weren't completely through.
|
||||
|
||||

|
||||

|
||||

|
||||

|
||||
|
||||
#### Focus test
|
||||
Here we aligned the laser to the middle. So on the outer parts you see that the line is thicker and in the middle it's going thin again.
|
||||

|
||||

|
||||
|
||||
### Extra notes for laser cutting
|
||||
When designing watch out with copy pasting lines and don't overlap them. Then you will get duplicate lines and also duplicate cuts.
|
||||
@@ -153,24 +154,24 @@ After brainstorming for a while I'm gonna make a drawer construction kit. It's g
|
||||
### Drawings
|
||||
I first have drawn out every part I needed and the necessary cuts and connections to make it sturdy. I ended up with this. I really like drawing first before I construct it because I can visualize the box better and make changes before I design it digitally.
|
||||
|
||||

|
||||

|
||||

|
||||

|
||||
|
||||
### Designing
|
||||
I started by designing my base for my construction kit in fusion360 as a sketch.
|
||||

|
||||

|
||||
I have made the teeth on the outside so I could extrude them as a separate body so I could use the pattern tool to attach them to the sides.
|
||||
|
||||
### Patterns
|
||||
|
||||
Once I extruded the teeth as separate bodies I could use the pattern tool to automatically generate the rest of the teeth.
|
||||

|
||||

|
||||
Using that tool I made the multiple bodies into one body.
|
||||
For some reason I couldn't enter the a variable in the Quantity section of the pattern tool. Even through I have set the Variable to not be a unit.
|
||||
|
||||
### Combining bodies
|
||||
After I did that four times I was left with a lot of separate bodies. So to combine them I went into the Modify tab and then selected combine.
|
||||

|
||||

|
||||
|
||||
### Kerf and press fit
|
||||
|
||||
@@ -179,28 +180,28 @@ After I did that four times I was left with a lot of separate bodies. So to comb
|
||||
### Turning the 3D model into a SVG file
|
||||
|
||||
Here I've had some struggles because when using Fusions build in export utility it only exports the sketches. After that I creating a new sketch and then projecting the 3D design onto the sketch.
|
||||

|
||||

|
||||
But the issue with this is that it isn't 100% accurate
|
||||
|
||||
Then I tried the Shaper Origin tool. But that crashed my fusion when I tried running it. After struggling for a while Michelle came to me and showed me the drawing tab of Fusion where you can define flat drawings of your 3d models and export them as svg.
|
||||
The tab is found here.
|
||||

|
||||

|
||||
|
||||
Once you press that this menu will pop up
|
||||
|
||||

|
||||

|
||||
|
||||
The standard settings are fine. You maybe wanna increase the sheet size to get your full design on it.
|
||||
|
||||

|
||||

|
||||
|
||||
Now you will enter this screen. You wanna set the scale to 1:1 and change the orientation to the top (if you've designed from the top).
|
||||
|
||||

|
||||

|
||||
You can Left click to place your design on the paper. Once you've placed everything you can select the outer borders and press delete.
|
||||
|
||||

|
||||

|
||||

|
||||

|
||||
|
||||
So you end up with this.
|
||||
|
||||
@@ -209,7 +210,7 @@ Now you can export the file as DXF file that LightBurn can understand.
|
||||
### Result lasercutting
|
||||
I didn't complete this weeks assignment because I didn't have enough time and I still needed to fix stuff for my internship. This is the furthest I got. I ended up at the issue that the teeth weren't aligned properly.
|
||||
|
||||

|
||||

|
||||
|
||||
## Vinyl cutter
|
||||
https://modsproject.org/ (made during fabacedemy) (using for making pcb's, cnc machine and roland vinyl cutter)
|
||||
|
BIN
docs/Assignments/week_4_programming/image-1.png
Normal file
After Width: | Height: | Size: 93 KiB |
BIN
docs/Assignments/week_4_programming/image-2.png
Normal file
After Width: | Height: | Size: 86 KiB |
BIN
docs/Assignments/week_4_programming/image.png
Normal file
After Width: | Height: | Size: 201 KiB |
158
docs/Assignments/week_4_programming/lecuteNotes.md
Normal file
@@ -0,0 +1,158 @@
|
||||
# Lecture notes
|
||||
## Architecture
|
||||
RISC-V (Reduced instruction set)
|
||||
Use EEPROM to save configuration or other things (easy to write to from program)
|
||||
FLASH (harder to write to)
|
||||
|
||||
|
||||
## Microcontrollers
|
||||
* AVR
|
||||
* ARM
|
||||
|
||||
RP2040
|
||||
With PIO you can create custom periphirals
|
||||
|
||||
## Programming
|
||||
Python recommended but I'm using C++ anyway.
|
||||
Rust is also usable but very hard to set up.
|
||||
|
||||
bootloader, Program to load programs
|
||||
|
||||
Arduino
|
||||
board + toolchain + libraries + IDE + bootloader + Header programming
|
||||
|
||||
|
||||
Simulation: WowKi
|
||||
tinkercircuit
|
||||
|
||||
|
||||
this week:
|
||||
Browse through the datasheet of your microcontroller
|
||||
write a program for a microcontroller
|
||||
simulate it.
|
||||
|
||||
try multiple dev environments
|
||||
|
||||
## Lecture notes local thursday
|
||||
|
||||
First C got introduced and then 20 years ago C++ got introduced. And the arduino IDE by a clever italian.
|
||||
|
||||
LED's blink at 400-600 Terahertz humans can't see that but chickens can.
|
||||
Micropython can't run on every microcontroller
|
||||
C++ runs on anything
|
||||
Rust isn't matured enough for microcontrollers and embedded
|
||||
|
||||
|
||||
sending code to the avr microcontrollers
|
||||
`avrdude`
|
||||
|
||||
You can run AVR's without bootloader's
|
||||
|
||||
Arduino bootloader connects the board to the arduino software.
|
||||
|
||||
The bus in a microcontroller is a data highway
|
||||
I2C multiplexer. Can add more pins to a microcontroller using I2C or you can add several devices with the same address.
|
||||
ADC - analog digital convertor
|
||||
DAC - digital analog converter
|
||||
|
||||
In the past 5 volt was used. Nowadays a lot of 3.3 volt is used.
|
||||
|
||||
Always add a LED on a custom board.
|
||||
|
||||
Arduino uno made 20 years ago.
|
||||
|
||||
PlatformIO
|
||||
|
||||
### RP2040
|
||||
Add the board library to the arduino boards manager.
|
||||
`File > Prefrences > additional boards url's`
|
||||
then add it in this link. `https://github.com/earlephilhower/arduino-pico/releases/download/global/package_rp2040_index.json`
|
||||
Then you can select the board in the connect menu and then it installs the toolchain.
|
||||
|
||||
|
||||
comment in your code. Comment why it works.
|
||||
|
||||
What happens when you press compile and upload
|
||||
`Starts compiling > Starts linking > opens communication with microcontroller > uploads firmware > done`
|
||||
|
||||
|
||||
basic arduino commands
|
||||
* digitalWrite(pin, LOW/HIGH)
|
||||
|
||||
|
||||
One of the most used things. Pulse Width Modulation (PWM).
|
||||
|
||||
Current flows from high to low
|
||||
|
||||
Connecting a LED using the microcontroller as a ground is better but it also reverses the programming LOW and HIGH.
|
||||
It's better because it can handle more power when it is the ground of the led
|
||||
|
||||
## PlatformIO + vscode
|
||||
|
||||
benefits using vscode
|
||||
* Intellisense
|
||||
* Git in the editor
|
||||
|
||||
First create new project
|
||||
|
||||
Then you can select the MCU and the framework
|
||||
|
||||
### For unsupported boards:
|
||||
Click the nearest board. And follow the community instructions
|
||||
|
||||
|
||||
Change platformio.ini
|
||||
from
|
||||
```ini
|
||||
[env:pico]
|
||||
platform = https://github.com/maxgerhardt/platform-raspberrypi.git
|
||||
board = pico
|
||||
framework = arduino
|
||||
board_build.core = earlephilhower
|
||||
```
|
||||
|
||||
to
|
||||
```ini
|
||||
[env]
|
||||
platform = https://github.com/maxgerhardt/platform-raspberrypi.git
|
||||
framework = arduino
|
||||
board_build.core = earlephilhower
|
||||
board_build.filesystem_size = 0.5m
|
||||
[env:seeed_xiao_rp2040]
|
||||
board = seeed_xiao_rp2040
|
||||
```
|
||||
### What is every folder
|
||||
* src - for source code
|
||||
* lib - project specific libraries
|
||||
|
||||
### How to add libraries
|
||||
Click the platformIO icon
|
||||
Then click the libraries button
|
||||
Then you can search a library and click add to project.
|
||||
|
||||

|
||||
|
||||
After that it will edit platformio.ini and there you will see the library added to the project. It's also in `.pio/libdeps`
|
||||
|
||||
## Micropython
|
||||
With micropython an OS is installed.
|
||||
You can get the firmware for here. https://micropython.org/download/RPI_PICO/
|
||||
|
||||
To upload the firmware you need to connect it to your laptop and set the microcontroller in boot mode by pressing: hold boot > click reset > release boot. Now it will appear on your laptop as a drive. Now you can delete the old UF2 file and drop in the new micropython firmware. It should automaticly unmount itself and start the micropython firmware.
|
||||
|
||||
Now if you install the Raspberry Pi Pico package on vscode you can create a new project and once the project is created and you've connected the microcontroller. A new project will pop up with a terminal under it.
|
||||
|
||||

|
||||
|
||||
`Control + Shift + P` in vscode
|
||||
|
||||

|
||||
|
||||
Make sure the file is named boot.py otherwise it won't start when the microcontroller gets power.
|
||||
|
||||
Pulseview - to view .vcd files from logic analysers
|
||||
|
||||
## Very important
|
||||
On linux machines you need to install platformio-udev. Otherwise you can't upload to your board.
|
||||
|
||||
|
153
docs/Assignments/week_4_programming/programming.md
Normal file
@@ -0,0 +1,153 @@
|
||||
# Embedded programming
|
||||
|
||||
## Introduction
|
||||
I'm very familiar with coding in C++ because of my university. At the moment im studying computer sciences at the Applied University of Amsterdam.
|
||||
|
||||
## First code before deciding to using existing code
|
||||
I first wanted to create the drone firmware myself. But then I looked through some research papers and existing programs and saw all the math that was needed to keep it upright. Then I decided to modify an existing program.
|
||||
This was my first attempts at getting the sensor to read
|
||||
|
||||
### Issues with old code
|
||||
|
||||
### Using the wrong library for the BNO085
|
||||
First used the wrong library I used the Adafruit bno0xx library instead of the Sparkfun bno08x library. The Example script below this reads the BNO085 sensor and returns the values in the arduino serial console.
|
||||
|
||||
??? failure
|
||||
|
||||
```cpp
|
||||
#include "conf.h"
|
||||
#include <Adafruit_BNO08x.h>
|
||||
#include <sh2.h>
|
||||
#include <sh2_SensorValue.h>
|
||||
#include <sh2_err.h>
|
||||
#include <sh2_hal.h>
|
||||
#include <sh2_util.h>
|
||||
#include <shtp.h>
|
||||
|
||||
Adafruit_BNO08x bno08x(BNOINTERRUPTSIG);
|
||||
sh2_SensorValue_t sensorValue;
|
||||
|
||||
void setup() {
|
||||
Serial.begin(9600);
|
||||
Serial.println("setup started");
|
||||
// Setup all ESC
|
||||
// ledcAttach(MOTOR1, PWMFREQ, PWMRESOLUTION);
|
||||
// ledcAttach(MOTOR2, PWMFREQ, PWMRESOLUTION);
|
||||
// ledcAttach(MOTOR3, PWMFREQ, PWMRESOLUTION);
|
||||
// ledcAttach(MOTOR4, PWMFREQ, PWMRESOLUTION);
|
||||
Serial.print("Setup Started");
|
||||
}
|
||||
|
||||
void loop() {
|
||||
// put your main code here, to run repeatedly:
|
||||
sleep(3)
|
||||
if (!bno08x.begin_I2C()) {
|
||||
Serial.println("Failed to find BNO08x chip");
|
||||
sleep(1);
|
||||
}
|
||||
|
||||
|
||||
Serial.print("Game Rotation Vector - r: ");
|
||||
Serial.print(sensorValue.un.gameRotationVector.real);
|
||||
Serial.print(" i: ");
|
||||
Serial.print(sensorValue.un.gameRotationVector.i);
|
||||
Serial.print(" j: ");
|
||||
Serial.print(sensorValue.un.gameRotationVector.j);
|
||||
Serial.print(" k: ");
|
||||
Serial.println(sensorValue.un.gameRotationVector.k);
|
||||
}
|
||||
|
||||
//https://randomnerdtutorials.com/esp32-pwm-arduino-ide/
|
||||
//https://github.com/adafruit/Adafruit_BNO08x/blob/master/examples/rotation_vector/rotation_vector.ino#L25
|
||||
```
|
||||
|
||||
??? example
|
||||
|
||||
```cpp
|
||||
#include <SparkFun_BNO080_Arduino_Library.h>
|
||||
#include <Wire.h>
|
||||
#include "conf.h"
|
||||
|
||||
BNO080 myIMU;
|
||||
|
||||
void setup() {
|
||||
Serial.begin(9600);
|
||||
Serial.println("setup started");
|
||||
// Setup all ESC
|
||||
// ledcAttach(MOTOR1, PWMFREQ, PWMRESOLUTION);
|
||||
// ledcAttach(MOTOR2, PWMFREQ, PWMRESOLUTION);
|
||||
// ledcAttach(MOTOR3, PWMFREQ, PWMRESOLUTION);
|
||||
// ledcAttach(MOTOR4, PWMFREQ, PWMRESOLUTION);
|
||||
Serial.print("Setup Started");
|
||||
|
||||
Wire.begin();
|
||||
myIMU.begin();
|
||||
Wire.setClock(400000); //Increase I2C data rate to 400kHz
|
||||
myIMU.enableRotationVector(50); //Send data update every 50ms}
|
||||
}
|
||||
|
||||
|
||||
void loop() {
|
||||
|
||||
if (myIMU.dataAvailable() == true) {
|
||||
float roll = (myIMU.getRoll()) * 180.0 / PI; // Convert roll to degrees
|
||||
float pitch = (myIMU.getPitch()) * 180.0 / PI; // Convert pitch to degrees
|
||||
float yaw = (myIMU.getYaw()) * 180.0 / PI; // Convert yaw / heading to degrees
|
||||
|
||||
Serial.print(roll, 1);
|
||||
Serial.print(F(","));
|
||||
Serial.print(pitch, 1);
|
||||
Serial.print(F(","));
|
||||
Serial.print(yaw, 1);
|
||||
|
||||
Serial.println();
|
||||
}
|
||||
}
|
||||
void calibrateESC() {
|
||||
ledcWrite(MOTOR1, 1100);
|
||||
ledcWrite(MOTOR2, 1100);
|
||||
ledcWrite(MOTOR3, 1100);
|
||||
ledcWrite(MOTOR4, 1100);
|
||||
}
|
||||
|
||||
//https://randomnerdtutorials.com/esp32-pwm-arduino-ide/
|
||||
//https://github.com/sparkfun/SparkFun_BNO080_Arduino_Library/blob/main/examples/Example24-UncalibratedGyro/Example24-UncalibratedGyro.ino
|
||||
```
|
||||
|
||||
## New driver
|
||||
After researching for a while and looking through other fab academy projects I found out that other people also made drones with micro controllers and used a pre-made driver that they customized (https://fab.cba.mit.edu/classes/863.23/Architecture/people/Zhixing/finalproject.html). After doing some research on how to keep the drone upright I also decided to use an existing driver because the math required for that is way above my level. Im gonna be using the [dRhemFlightVTOL](https://github.com/nickrehm/dRehmFlight/tree/master) driver. The only problem is that it doesn't support my Inertial measuring unit (BNO085). So I will have to customize the driver to make it work with it.
|
||||
|
||||
### Implementing the BNO085
|
||||
|
||||
### Hijacking the controls
|
||||
I need to reverse engineer the controls because now it just calls a function called radiocontrols() that manages the controls. There are 4 pwm channel that controls where the drone is going. I wanna make my own controller and simulate these pwm signals.
|
||||
```cpp
|
||||
thro_des = (channel_1_pwm - 1000.0) / 1000.0; // Between 0 and 1
|
||||
roll_des = (channel_2_pwm - 1500.0) / 500.0; // Between -1 and 1
|
||||
pitch_des = (channel_3_pwm - 1500.0) / 500.0; // Between -1 and 1
|
||||
yaw_des = (channel_4_pwm - 1500.0) / 500.0; // Between -1 and 1
|
||||
```
|
||||
From looking further in the code it has safety protocols when the channels go too low or too high so using that we have a range where the pwm speed should be.
|
||||
|
||||
```cpp
|
||||
// Triggers for failure criteria
|
||||
// Line 1260
|
||||
if (channel_1_pwm > maxVal || channel_1_pwm < minVal)
|
||||
check1 = 1;
|
||||
if (channel_2_pwm > maxVal || channel_2_pwm < minVal)
|
||||
check2 = 1;
|
||||
if (channel_3_pwm > maxVal || channel_3_pwm < minVal)
|
||||
check3 = 1;
|
||||
if (channel_4_pwm > maxVal || channel_4_pwm < minVal)
|
||||
check4 = 1;
|
||||
if (channel_5_pwm > maxVal || channel_5_pwm < minVal)
|
||||
check5 = 1;
|
||||
if (channel_6_pwm > maxVal || channel_6_pwm < minVal)
|
||||
check6 = 1;
|
||||
```
|
||||
In this case minVal is 800 an maxVal is 2200. So we need to stay between these ranges to control the drone. In theory you can send any value to the ESC because it calibrates to the lowest and highest values you give it but there is a range. From past experiences I have experienced that 12bit PWM is not sufficient, 16 bit is needed.
|
||||
|
||||
[ESC calibration](https://ardupilot.org/copter/docs/esc-calibration.html)
|
||||
|
||||
#### Attaching the esc's to the correct pin.
|
||||
|
Before Width: | Height: | Size: 38 KiB After Width: | Height: | Size: 38 KiB |
Before Width: | Height: | Size: 26 KiB After Width: | Height: | Size: 26 KiB |
Before Width: | Height: | Size: 251 KiB After Width: | Height: | Size: 251 KiB |
Before Width: | Height: | Size: 322 KiB After Width: | Height: | Size: 322 KiB |
Before Width: | Height: | Size: 256 KiB After Width: | Height: | Size: 256 KiB |
Before Width: | Height: | Size: 302 KiB After Width: | Height: | Size: 302 KiB |
Before Width: | Height: | Size: 306 KiB After Width: | Height: | Size: 306 KiB |
Before Width: | Height: | Size: 282 KiB After Width: | Height: | Size: 282 KiB |
Before Width: | Height: | Size: 497 KiB After Width: | Height: | Size: 497 KiB |
Before Width: | Height: | Size: 372 KiB After Width: | Height: | Size: 372 KiB |
Before Width: | Height: | Size: 446 KiB After Width: | Height: | Size: 446 KiB |
Before Width: | Height: | Size: 361 KiB After Width: | Height: | Size: 361 KiB |
Before Width: | Height: | Size: 500 KiB After Width: | Height: | Size: 500 KiB |
Before Width: | Height: | Size: 391 KiB After Width: | Height: | Size: 391 KiB |
Before Width: | Height: | Size: 227 KiB After Width: | Height: | Size: 227 KiB |
Before Width: | Height: | Size: 285 KiB After Width: | Height: | Size: 285 KiB |
Before Width: | Height: | Size: 453 KiB After Width: | Height: | Size: 453 KiB |
Before Width: | Height: | Size: 425 KiB After Width: | Height: | Size: 425 KiB |
Before Width: | Height: | Size: 357 KiB After Width: | Height: | Size: 357 KiB |
Before Width: | Height: | Size: 554 KiB After Width: | Height: | Size: 554 KiB |
Before Width: | Height: | Size: 544 KiB After Width: | Height: | Size: 544 KiB |
Before Width: | Height: | Size: 334 KiB After Width: | Height: | Size: 334 KiB |
Before Width: | Height: | Size: 305 KiB After Width: | Height: | Size: 305 KiB |
Before Width: | Height: | Size: 317 KiB After Width: | Height: | Size: 317 KiB |
Before Width: | Height: | Size: 274 KiB After Width: | Height: | Size: 274 KiB |
Before Width: | Height: | Size: 424 KiB After Width: | Height: | Size: 424 KiB |
Before Width: | Height: | Size: 252 KiB After Width: | Height: | Size: 252 KiB |
Before Width: | Height: | Size: 236 KiB After Width: | Height: | Size: 236 KiB |
Before Width: | Height: | Size: 357 KiB After Width: | Height: | Size: 357 KiB |
Before Width: | Height: | Size: 191 KiB After Width: | Height: | Size: 191 KiB |
Before Width: | Height: | Size: 113 KiB After Width: | Height: | Size: 113 KiB |
Before Width: | Height: | Size: 142 KiB After Width: | Height: | Size: 142 KiB |
Before Width: | Height: | Size: 227 KiB After Width: | Height: | Size: 227 KiB |
Before Width: | Height: | Size: 96 KiB After Width: | Height: | Size: 96 KiB |
Before Width: | Height: | Size: 143 KiB After Width: | Height: | Size: 143 KiB |
Before Width: | Height: | Size: 743 KiB After Width: | Height: | Size: 743 KiB |
Before Width: | Height: | Size: 671 KiB After Width: | Height: | Size: 671 KiB |
Before Width: | Height: | Size: 144 KiB After Width: | Height: | Size: 144 KiB |
Before Width: | Height: | Size: 156 KiB After Width: | Height: | Size: 156 KiB |
Before Width: | Height: | Size: 647 KiB After Width: | Height: | Size: 647 KiB |
Before Width: | Height: | Size: 282 KiB After Width: | Height: | Size: 282 KiB |
Before Width: | Height: | Size: 862 KiB After Width: | Height: | Size: 862 KiB |
Before Width: | Height: | Size: 773 KiB After Width: | Height: | Size: 773 KiB |
Before Width: | Height: | Size: 899 KiB After Width: | Height: | Size: 899 KiB |
Before Width: | Height: | Size: 976 KiB After Width: | Height: | Size: 976 KiB |
Before Width: | Height: | Size: 139 KiB After Width: | Height: | Size: 139 KiB |
Before Width: | Height: | Size: 304 KiB After Width: | Height: | Size: 304 KiB |
@@ -1,131 +0,0 @@
|
||||
# Coding the drone
|
||||
|
||||
## What does every part of my code do?
|
||||
### #include
|
||||
`#include` includes an external library into the project so you can use it.
|
||||
|
||||
//TODO: add docs about working code not broken code
|
||||
|
||||
## Issues
|
||||
|
||||
### Using the wrong library for the BNO085
|
||||
First used the wrong library I used the Adafruit bno0xx library instead of the Sparkfun bno08x library. The Example script below this reads the BNO085 sensor and returns the values in the arduino serial console.
|
||||
|
||||
??? failure
|
||||
|
||||
```cpp
|
||||
#include "conf.h"
|
||||
#include <Adafruit_BNO08x.h>
|
||||
#include <sh2.h>
|
||||
#include <sh2_SensorValue.h>
|
||||
#include <sh2_err.h>
|
||||
#include <sh2_hal.h>
|
||||
#include <sh2_util.h>
|
||||
#include <shtp.h>
|
||||
|
||||
Adafruit_BNO08x bno08x(BNOINTERRUPTSIG);
|
||||
sh2_SensorValue_t sensorValue;
|
||||
|
||||
void setup() {
|
||||
Serial.begin(9600);
|
||||
Serial.println("setup started");
|
||||
// Setup all ESC
|
||||
// ledcAttach(MOTOR1, PWMFREQ, PWMRESOLUTION);
|
||||
// ledcAttach(MOTOR2, PWMFREQ, PWMRESOLUTION);
|
||||
// ledcAttach(MOTOR3, PWMFREQ, PWMRESOLUTION);
|
||||
// ledcAttach(MOTOR4, PWMFREQ, PWMRESOLUTION);
|
||||
Serial.print("Setup Started");
|
||||
}
|
||||
|
||||
void loop() {
|
||||
// put your main code here, to run repeatedly:
|
||||
sleep(3)
|
||||
if (!bno08x.begin_I2C()) {
|
||||
Serial.println("Failed to find BNO08x chip");
|
||||
sleep(1);
|
||||
}
|
||||
|
||||
|
||||
Serial.print("Game Rotation Vector - r: ");
|
||||
Serial.print(sensorValue.un.gameRotationVector.real);
|
||||
Serial.print(" i: ");
|
||||
Serial.print(sensorValue.un.gameRotationVector.i);
|
||||
Serial.print(" j: ");
|
||||
Serial.print(sensorValue.un.gameRotationVector.j);
|
||||
Serial.print(" k: ");
|
||||
Serial.println(sensorValue.un.gameRotationVector.k);
|
||||
}
|
||||
|
||||
//https://randomnerdtutorials.com/esp32-pwm-arduino-ide/
|
||||
//https://github.com/adafruit/Adafruit_BNO08x/blob/master/examples/rotation_vector/rotation_vector.ino#L25
|
||||
```
|
||||
|
||||
??? example
|
||||
|
||||
```cpp
|
||||
#include <SparkFun_BNO080_Arduino_Library.h>
|
||||
#include <Wire.h>
|
||||
#include "conf.h"
|
||||
|
||||
BNO080 myIMU;
|
||||
|
||||
void setup() {
|
||||
Serial.begin(9600);
|
||||
Serial.println("setup started");
|
||||
// Setup all ESC
|
||||
// ledcAttach(MOTOR1, PWMFREQ, PWMRESOLUTION);
|
||||
// ledcAttach(MOTOR2, PWMFREQ, PWMRESOLUTION);
|
||||
// ledcAttach(MOTOR3, PWMFREQ, PWMRESOLUTION);
|
||||
// ledcAttach(MOTOR4, PWMFREQ, PWMRESOLUTION);
|
||||
Serial.print("Setup Started");
|
||||
|
||||
Wire.begin();
|
||||
myIMU.begin();
|
||||
Wire.setClock(400000); //Increase I2C data rate to 400kHz
|
||||
myIMU.enableRotationVector(50); //Send data update every 50ms}
|
||||
}
|
||||
|
||||
|
||||
void loop() {
|
||||
|
||||
if (myIMU.dataAvailable() == true) {
|
||||
float roll = (myIMU.getRoll()) * 180.0 / PI; // Convert roll to degrees
|
||||
float pitch = (myIMU.getPitch()) * 180.0 / PI; // Convert pitch to degrees
|
||||
float yaw = (myIMU.getYaw()) * 180.0 / PI; // Convert yaw / heading to degrees
|
||||
|
||||
Serial.print(roll, 1);
|
||||
Serial.print(F(","));
|
||||
Serial.print(pitch, 1);
|
||||
Serial.print(F(","));
|
||||
Serial.print(yaw, 1);
|
||||
|
||||
Serial.println();
|
||||
}
|
||||
}
|
||||
void calibrateESC() {
|
||||
ledcWrite(MOTOR1, 1100);
|
||||
ledcWrite(MOTOR2, 1100);
|
||||
ledcWrite(MOTOR3, 1100);
|
||||
ledcWrite(MOTOR4, 1100);
|
||||
}
|
||||
|
||||
//https://randomnerdtutorials.com/esp32-pwm-arduino-ide/
|
||||
//https://github.com/sparkfun/SparkFun_BNO080_Arduino_Library/blob/main/examples/Example24-UncalibratedGyro/Example24-UncalibratedGyro.ino
|
||||
```
|
||||
|
||||
## New driver
|
||||
After researching for a while and looking through other fab academy projects I found out that other people also made drones with micro controllers and used a pre-made driver that they customized (https://fab.cba.mit.edu/classes/863.23/Architecture/people/Zhixing/finalproject.html). After doing some research on how to keep the drone upright I also decided to use an existing driver because the math required for that is way above my level.
|
||||
|
||||
### The new driver
|
||||
Im gonna be using the [dRhemFlightVTOL](https://github.com/nickrehm/dRehmFlight/tree/master) driver. The only problem is that it doesn't support my Inertial measuring unit (BNO085). So I will have to customize the driver to make it work with it.
|
||||
|
||||
|
||||
//TODO: reverse engineer the driver and see what all pwm channels do from the controller
|
||||
//TODO: See if i can use playstation controller as RC controller
|
||||
|
||||
```cpp
|
||||
thro_des = (channel_1_pwm - 1000.0) / 1000.0; // Between 0 and 1
|
||||
roll_des = (channel_2_pwm - 1500.0) / 500.0; // Between -1 and 1
|
||||
pitch_des = (channel_3_pwm - 1500.0) / 500.0; // Between -1 and 1
|
||||
yaw_des = (channel_4_pwm - 1500.0) / 500.0; // Between -1 and 1
|
||||
```
|
@@ -58,4 +58,13 @@ I've also made a render of the drone to visualize it for other people. Making th
|
||||
|
||||
<video controls src="../assets/assets_week_2/blender/droneRender.mp4" title="Title"></video>
|
||||
|
||||
## Feedback from Bas and Henk
|
||||
I've gotten some feedback on my design and about the use of screens. Maybe I should only use speakers or use LED matrixes. After thinking about it I think im going to give LED matrixes a spin.
|
||||
|
||||
## CAM and machines
|
||||
|
||||
|
||||
## BOM (bill of materials)
|
||||
| item | price | link |
|
||||
| :---- | ----- | -------- |
|
||||
| item1 | 999 | link.com |
|
24
src/workshopCode/ledExampleRP2040/ledExampleRP2040.ino
Normal file
@@ -0,0 +1,24 @@
|
||||
void setup() {
|
||||
pinMode(PIN_LED_R, OUTPUT);
|
||||
pinMode(PIN_LED_G, OUTPUT);
|
||||
pinMode(PIN_LED_B, OUTPUT);
|
||||
|
||||
Serial.begin(9600);
|
||||
|
||||
digitalWrite(PIN_LED_R, HIGH);
|
||||
digitalWrite(PIN_LED_G, HIGH);
|
||||
digitalWrite(PIN_LED_B, HIGH);
|
||||
|
||||
}
|
||||
|
||||
void loop() {
|
||||
|
||||
digitalWrite(LED_BUILTIN, 0); //Turn the led on RP2040 is reversed
|
||||
|
||||
Serial.println("on");
|
||||
delay(10);
|
||||
digitalWrite(LED_BUILTIN, 1);
|
||||
Serial.println("off");
|
||||
delay(10);
|
||||
|
||||
}
|