Final Project

slides

I have two final project ideas. My initial idea was to design a modular light controller, which I described in Week 01b. Over the weeks, and after discussions with my local instructor Ferdi, I developed the idea of creating a "smart" filament holder for the Prusa XL. This holder would measure the weight of the spools and indicate how much filament remains. This feature is particularly useful because loading and unloading filament on the Prusa XL can be cumbersome—especially when printing with five different materials, as it requires unloading, weighing, and reloading five spools. Integrating this with a filament drying box would be a great addition. For this aspect, I found some inspiration on YouTube with the Sicco Box, which is also available on Printables.

The weight measurement should be implemented using individual load cells for each spool holder. My first approach was to use the same or similar load cells that are already integrated into the hotends, but I couldn't find any specific information about them. The typical Δm will be 1 kg, with a range from 220 g to 1220 g, which corresponds to the weight of a 1 kg Prusament spool. Adafruit recommends using load cells rated for double the maximum expected weight for optimal measurement precision. With this in mind, the Adafruit 5 kg load cells could be a good choice, as they would also support 2 kg spools, which we occasionally use with our Prusa MK4S (formerly MK3.9). For optimal precision, a high-quality ADC such as the HX711 is essential. In week 09 I tested the usage of an HX711 in combination with an ESP32C3.
Beside the HX711 I looked for integrated ADC on the available microcontroller from the FabInventory and the Xiao ESP32C6.

Microcontroller ADC Resolution
Attiny 1624 12 bit (17 bit with oversampling)
Attiny 3226 12 bit (17 bit with oversampling)
Attiny 412 10 bit
ATSAMD11C14A 12 bit (12, 13, 14, 15, 16 bit with oversampling)
ATSAMD21E18A 12 bit (12, 13, 14, 15, 16 bit with oversampling)
AVR128DB32 12 bit
SAMD21 12 bit
Xiao ESP32C3 12 bit
Xiao ESP32C6 12 bit
Xiao ESP32S3 12 bit
Xiao RP2040 12 bit
Raspberry Pi Pico 12 bit

Other useful information from inside the box are temperature and humidity. For that I also did some experiments in week 09 with the conclusion that the BME688 will over achieve the job, it is still easy to use and implement why I'll want to integrated it in to the project even if the price is still high, specially for the module if its not bought separately.

The project will include multiple sensors and actors so I need a display and some way to navigate to a menu. Beside the load cells and a environment sensor I want to use a rotary encoder as a human input, which I experiment in week 9. To get an visual output I plan to use a display. For that I reason I experiment with a small and a bigger OLED display in week 10.

To realize the active drying feature I came up with two ideas.
1. Fan heaters which can be found as open, relatively small modules.
2. Dehumidifier membranes like these ones, which I found in a youtube video, while researching for already designed solutions for similar problems.

The first option have the problem that they have a high power consumption and that you don't want to use them unsupervised because they could easily start a fire. Cause of the heating elements in an closed and small room. The second option can fast be expensive but they don't use active heating, so there are less potential fire hazards. In the Sicco box which was an inspiration a fan heater from a Sunlu S4 is used.

It would be nice to have some kind of modularity so I can start with one spool holder in the box with a load cell, a display and a rotary encoder. The next iteration will conclude multiple spool holders and in the last iteration some kind of active drying solution can be added. I don't want to replace always the pcb and make some new wiring, so I plan to use multiple microcontroller. One microcontroller on each spool holder, so they will be modular, one main microcontroller where the display and rotary encoder is connected and optional one for the active drying solution, otherwise that could probably done by the main microcontroller. For that reason I tried out some simple networking in week 11.

System Integration

The thoughts about the system integration are documented in week 15.

Electronics

BOM

The prices will be calculated without shipping, with german taxes in €. For easier reproduction I'll try to minimize quantity of different shops even if it cost more.

ID Designator Component Quantity price/# price link Comment
01 U1, U2 Xiao ESP32-C3 2 4,39 $ 8,78 $ Digikey
02 U3 NCV1117ST50T3G 1 0,51 $ 0,51 $ Digikey
03 D1, D2, D3, D4, D5 Neopixel 5 3,96 $ 3,96 $ Digikey pack of 10
04 C1, C2 C3216X7R1H105K160AB 2 0,24 $ 0,48 $ Digikey temperature stability and rated voltage not necessary
05 R1, R2, R3 RC1206FR-0710KL 3 0,10 $ 0,30 $ Digikey
06 R4 RC1206FR-0710KL 1 0,09 $ 0,09 $ Digikey
07 J1, J2, J3, J4 TSM-107-01-L-SV 4 1,12 $ 4,48 $ Digikey Cutable sockets could be cheaper
08 J5 M20-9990246 1 0,10 $ 0,10 $ Digikey Cutable header could be cheaper
09 J6 PH1-01-UA 1 0,10 $ 0,10 $ Digikey Cutable header could be cheaper
10 J7 61300311121 1 0,12 $ 0,12 $ Digikey Cutable header could be cheaper
11 J8 SSM-114-L-SV-LC 1 3,40 $ 3,40 $ Digikey Cutable sockets could be cheaper
12 U4, U5, U6, U7, U8 HX711 5 4,79 $ 23,95 $ Digikey Cheaper on Amazon also available as a Kit with a load cell
13 S1 BME688 1 17,54 $ 17,54 $ Digikey
14 DS1 OLED 1 18,90 € 18,90 € Reichelt
15 SW1 Rotary Encoder 1 1,51 $ 1,51 $ Digikey
16 S2, S3, S4, S5, S6 Load Cell 5 kg 5 3,47 $ 17,35 $ Digikey different load cells also possible, cheaper on Amazon
17 DM1 Dehumidifier Membrane 1 82,58 € 82,58 € Micro Dehumidifier Alternative: M-1J1R
18
19
20
21
22
23
24
25

Mainboard

2 sided pcb

schematic

The first big challenge is to mill a 2 sided board. In preparation for this I build a vacuum clamp with bowel pins in week 07.
I did in the first try following steps:
1. drill 4 holes for positioning
2. mill the top side
3. flip the board along the x axis
4. mill the bottom side
5. mill vias, holes and the outline

Before I can drill the four holes in the double sided pcb stock in the same distance to each other then the dowel pins on the vacuum clamp, in my case 117 mm in x and 91,6 mm in y. I need to generate g-code for that. The first attempted was to use mods but with that I couldn't generate g-code for 2 mm holes with a 2 mm end mill. It was only possible with a 1,6 mm endmill. Ferdi could generate g-code for a 1,9 mm endmill for a 2 mm hole but with only 96 dpi instead of 999 dpi. We couldn't reproduce this, so I just let Fusion 360 generate the g-code for the 4 holes using the "Drill" tool with a 2 mm drill.

To prepare the png files for milling I have to make sure that I could use the same 0 point without any offset between the layers after flipping. Normally I exported the top layer and the outlines/holes as a pdf load them in Inkscape, make some small adjustments and then exported it as png to uploaded it into mods. For this pcb I decided to try gerber2png. For that I exported a gerber file from easyeda with following setting:

✅ Top Layer
✅ Bottom Layer
✅ Board Outline Layer
✅ Mechanical Layer
✅ Export Object

easyeda 01

I then ended up with following seven files:

easyeda 02

Which I drag and drop into Gerber2Png except the "How-to-order-PCB" file.

gerber2png 01

This generates the following different png files:

gerber2png 02

To only need two g-codes I opened the outline file and the hole file in gimp and lay them over each other to make one png file out of them. I will not drill completely through my stock material why I also flipped a copy of the drilling file to also drill the holes from the bottom side.

gerber2png 03

To make sure that I don't have any offsets while flipping the stock I loaded all files in to Inkscape and put them on a canvas with the size that matches the hole distance for the bowel pins. So as long as the coordinates from the front left dowel pin are correct I can easily flip the board and don't need to correct the origin.

gerber2png 04

Before I started the actual milling I tried the g-code in midair to make sure that the endmill not collide with the dowel pins, which are slightly raised.

While doing the test I came up with the idea to remove the critical pin on the front left, which is also the 0 point for the g-code. Later Ferdi told me, that I can adjust the jog height in mods. I then raise the jog height to 5 mm to make sure that it is definitely higher than the dowel pin.

But I was still a little bit scared and after I already broke one of the good endmills from Ferdi accidentally in a dump situation.

While milling the bottom I recognized that the png files gerber2png generates flips the board over the short side, while in my case I need it to flip the board along the long side, which result in a not usable pcb. But that gave me the chance to fix some small errors that I found. For example one trace thats handle the serial communication has a 90° angle on a via and I didn't put my name or "Fab Academy 25" on the board.

The results was still impressive and the difference between cheap and expensive endmills are definitely visible. Over the last weeks I used the cheap ones and for the final project I came in the pleasures situation to use the good ones. Thank you Ferdi for let me borrowing your endmills.

mill 03-04

To ensure that the coordinates from the origin are correct I put the wrong milled pcb back in the machine and milled the bottom side with the correct flipped file. Which wasn't a success because I used the wrong png file. The result itself looks promising and for the holes and outline I used the correct file which results in a good enough result. The y coordinate could be slightly of by a few μm which is good enough. All in all it took me 4 tries until everything works. The third try looks promising but I forgot to check the mill bit positions, so the mill used the wrong endmill for milling the holes, which results in bigger holes and without any pads.

PCB test

After soldering the pcb I began testing the different components. Firstly the Neopixels for that I used following test code:

#include <Adafruit_NeoPixel.h>                                               // library for NeoPixels

#define PIN_NEO_PIXEL D3                                                     // Xiao pin that connects to NeoPixel
#define NUM_PIXELS 5                                                         // The number of LEDs

Adafruit_NeoPixel NeoPixel(NUM_PIXELS, PIN_NEO_PIXEL, NEO_GRB + NEO_KHZ800); // set the NeoPixel initialization

void setup() {
  NeoPixel.begin();                                                          // initialize the NeoPixel strip object
}

void loop() {
  for (int i = 0; i < 256; i++) {                                            // color cycling
    byte r = (i < 85) ? i * 3 : (i < 170) ? 255 - (i - 85) * 3 : 0;
    byte g = (i < 85) ? 255 - i * 3 : (i < 170) ? 0 : (i - 170) * 3;
    byte b = (i < 85) ? 0 : (i < 170) ? (i - 85) * 3 : 255 - (i - 170) * 3;

    for (int j = 0; j < 5; j++) {
      NeoPixel.setPixelColor(j, r, g, b);                                    // set color
    }

    NeoPixel.setBrightness(100);                                             // reduce brightness to 100 from 255, only for filming otherwise not need it
    NeoPixel.show();                                                         // output the color
    delay(10);                                                               // short delay for the color change
  }
}

Secondly I integrated the rotary encoder into the test.

#include <Adafruit_NeoPixel.h>    // library for NeoPixels
#include <Encoder.h>              // library for rotary encoder

#define PIN_NEO_PIXEL D3          // Xiao pin that connects to NeoPixel
#define NUM_PIXELS 5              // number of LEDs
#define dt D7                     // Xiao pin that connects to rotary encoder dt
#define clk D9                    // Xiao pin that connects to rotary encoder clk
#define sw D8                     // Xiao pin that connects to rotary encoder sw

Adafruit_NeoPixel NeoPixel(NUM_PIXELS, PIN_NEO_PIXEL, NEO_GRB + NEO_KHZ800); // set the NeoPixel initialization
Encoder brightness(dt,clk);                                                  // initiate object rotary encoder with the name brightness

int encoder_value = 0;            // value of rotary encoder
int brightness_value = 255;       // brightness value for the NeoPixel
int brightness_value_old = 255;   // previous brightness value for the NeoPixel
bool sw_control = false;

void setup() {
  Serial.begin(115200);            // initial serial communication with a baud rate of 115200
  NeoPixel.begin();                // initialize the NeoPixel strip object
  pinMode(sw, INPUT);              // set pin for rotary encoder button as an input
}

void IRAM_ATTR fallout()
{
  if (sw_control == false){
    brightness_value = brightness_value_old;
    sw_control = true;
  }
  else if (sw_control == true){
    brightness_value_old = brightness_value;
    brightness_value = 0;
    sw_control = false;
  }
}

void loop() {
  for (int i = 0; i < 256; i++) {                                             // go through all possible values to control a Neopixel
    byte r = (i < 85) ? i * 3 : (i < 170) ? 255 - (i - 85) * 3 : 0;           // set first set of number ranges for a color cycle 
    byte g = (i < 85) ? 255 - i * 3 : (i < 170) ? 0 : (i - 170) * 3;          // set second set of number ranges for a color cycle 
    byte b = (i < 85) ? 0 : (i < 170) ? (i - 85) * 3 : 255 - (i - 170) * 3;   // set third set of number ranges for a color cycle 

    if (encoder_value != brightness.read()){
      encoder_value = brightness.read();
      brightness_value = encoder_value;
    }
    Serial.println(brightness_value);

    for (int j = 0; j < 5; j++) {
      NeoPixel.setPixelColor(j, r, g, b);             // set color
    }
    NeoPixel.setBrightness(brightness_value);
    NeoPixel.show();                                   // output the color
    attachInterrupt(sw, fallout, HIGH);
    delay(10);                                         // short delay for the color change
  } 
}

Thirdly I integrated the OLED display to make sure that everything works together.

#include <Adafruit_NeoPixel.h>                                               // library for NeoPixels
#include <Encoder.h>                                                         // library for rotary encoder
#include <Wire.h>                                                            // include wire library need it for the Adafruit_GFX library
#include <Adafruit_GFX.h>                                                    // include Adafruit_GFX library need it for the Adafruit_SSD1306 library
#include <Adafruit_SSD1306.h>                                                // include Adafruit_SSD1306 library tp control the OLED display

#define PIN_NEO_PIXEL D3                                                     // Xiao pin that connects to NeoPixel
#define NUM_PIXELS 5                                                         // number of LEDs
#define dt D7                                                                // Xiao pin that connects to rotary encoder dt
#define clk D9                                                               // Xiao pin that connects to rotary encoder clk
#define sw D8                                                                // Xiao pin that connects to rotary encoder sw
#define SCREEN_WIDTH 128                                                     // set OLED display width
#define SCREEN_HEIGHT 64                                                     // set OLED display height
#define OLED_RESET -1                                                        // set the reset pin

Adafruit_NeoPixel NeoPixel(NUM_PIXELS, PIN_NEO_PIXEL, NEO_GRB + NEO_KHZ800); // set the NeoPixel initialization
Encoder brightness(dt,clk);                                                  // initiate object rotary encoder with the name brightness

Adafruit_SSD1306 display(SCREEN_WIDTH, SCREEN_HEIGHT, &Wire, OLED_RESET);    // initialize an Adafruit_SSD1306 object called display with the parameters from above

int encoder_value = 0;                                                       // value of rotary encoder
int brightness_value = 255;                                                  // brightness value for the NeoPixel
int brightness_value_old = 255;                                              // previous brightness value for the NeoPixel
bool sw_control = false;

void setup() {
  Serial.begin(115200);                                                      // initial serial communication with a baud rate of 115200
  NeoPixel.begin();                                                          // initialize the NeoPixel strip object
  pinMode(sw, INPUT);                                                        // set pin for rotary encoder button as an input

  if (!display.begin(SSD1306_SWITCHCAPVCC, 0x3C)) {                          // checked if a display is available  
    Serial.println(F("SSD1306 allocation failed"));                          // if no display is available send an error message to the serial monitor  
    for(;;);
  }

  display.clearDisplay();                                                    // clear the display --> set every pixel to black  
}

void displayMessage(int message) {                                           // function to visualize a message on the display
  display.clearDisplay();                      
  display.setTextSize(1);                                                    // set text size
  display.setTextColor(SSD1306_WHITE);                                       // set the text color
  display.setCursor(0,0);                                                    // set the position where the text is shown on the display
  display.println("Encoder Value:");                                         // send the input from the function to the display
  display.setCursor(0,10);                                                   // set the position where the text is shown on the display
  display.println(message);                                                  // send the input from the function to the display
  display.display();                                                         // show data on the display with the parameters from above
}

void IRAM_ATTR fallout()
{
  if (sw_control == false){
    brightness_value = brightness_value_old;
    sw_control = true;
  }
  else if (sw_control == true){
    brightness_value_old = brightness_value;
    brightness_value = 0;
    sw_control = false;
  }
}

void loop() {
  for (int i = 0; i < 256; i++) {                                             // go through all possible values to control a Neopixel
    byte r = (i < 85) ? i * 3 : (i < 170) ? 255 - (i - 85) * 3 : 0;           // set first set of number ranges for a color cycle 
    byte g = (i < 85) ? 255 - i * 3 : (i < 170) ? 0 : (i - 170) * 3;          // set second set of number ranges for a color cycle 
    byte b = (i < 85) ? 0 : (i < 170) ? (i - 85) * 3 : 255 - (i - 170) * 3;   // set third set of number ranges for a color cycle 

    if (encoder_value != brightness.read()){
      encoder_value = brightness.read();
      brightness_value = encoder_value;
    }
    displayMessage(encoder_value);                                            // display the encoder value on the display

    for (int j = 0; j < 5; j++) {
      NeoPixel.setPixelColor(j, r, g, b);                                     // set color
    }
    NeoPixel.setBrightness(brightness_value);
    NeoPixel.show();                                                          // output the color
    attachInterrupt(sw, fallout, HIGH);
    delay(10);                                                                // short delay for the color change
  } 
}

And it didn't worked because I mixed up SDA and CLK on the display. So I have to mill and solder a new pcb but now I know how it works, so it should work alot faster. After I fix this I used the test code again and it works.

Before fixing the mixed up sda and clk pins I tried out the last functionality, if the serial communication between the xiao's works or if there is also a problem. To get the code I ask chatgpt for some help with the following promp:

"I need a small code for two Xiao ESP32C3 which allows to let both Xiaos communicated over serial with each other and one Xiao also needs to communicate with serial over USB with a laptop. It would be enough if there is a short message like "hello world" send from one Xiao to the one that is connected to the laptop and the other way around. A bidirectional communication is needed."

ChatGPTs answer was the following:

"Here’s a minimal example for bidirectional serial communication between two Seeed Studio XIAO ESP32C3 boards: 🔧 Hardware Setup * Connect TX (D6) of one XIAO to RX (D7) of the other. * Cross-connect TX/RX: * XIAO1 (TX=D6) → XIAO2 (RX=D7) * XIAO2 (TX=D6) → XIAO1 (RX=D7) * Both boards share a common GND. * XIAO1 will be connected to the PC via USB for Serial Monitor.

🧠 Code Overview Each board will: * Use Serial for USB communication. * Use Serial1 for UART communication between boards.

Send and receive "Hello from XIAO1" or "Hello from XIAO2" messages.

🔌 Wiring Summary Signal XIAO1 Pin XIAO2 Pin TX D6 D7 RX D7 D6 GND GND GND 📝 XIAO1 Code (connected to PC via USB)

define RXD1 7 // Receive pin

define TXD1 6 // Transmit pin

void setup() { Serial.begin(115200); // USB serial Serial1.begin(9600, SERIAL_8N1, RXD1, TXD1); // UART serial delay(1000); }

void loop() { // Send message to XIAO2 Serial1.println("Hello from XIAO1");

// Read from XIAO2 and print to PC if (Serial1.available()) { String incoming = Serial1.readStringUntil('\n'); Serial.print("From XIAO2: "); Serial.println(incoming); }

delay(1000); // 1 second interval }

📝 XIAO2 Code

define RXD1 7

define TXD1 6

void setup() { Serial.begin(115200); Serial1.begin(9600, SERIAL_8N1, RXD1, TXD1); delay(1000); }

void loop() { // Send message to XIAO1 Serial1.println("Hello from XIAO2");

// Read from XIAO1 and print to Serial Monitor (optional) if (Serial1.available()) { String incoming = Serial1.readStringUntil('\n'); Serial.print("From XIAO1: "); Serial.println(incoming); }

delay(1000); }

✅ Notes

You can use different baud rates, but both devices must match. * If you want to send user input from the PC to XIAO2, let me know — we can expand it. * Don’t forget to select the correct COM port in the Arduino IDE for each XIAO when uploading code. * Let me know if you'd like a schematic diagram or to include parsing/custom messages!

To verify that the code works I shortly install two Xiao ESP32C3 on a breadboard and connect RX from one Xiao with TX from the other and the other way around.


Distributionboard

Out of time concerns I desided to use cables to connect the HX711 modules with the mainboard. To collect all the neccessary connections to the mainboard I designed a small distribution pcb which then connect all signals bundled to the mainboard. For that reason the board is located on the inside of the Eurobox close to the mainboard.

Adapterboard

The Adapterboard is nothing more than a 90° bracket to connect the HX711 module to the cable that runs to the Distributionboard.

Mechanics

BOM

The prices will be calculated without shipping, with german taxes in €. For easier reproduction I'll try to minimize quantity of different shops even if it cost more.

ID Component Quantity price/# price link Comment
01 Bearing 608 20 0,98 $ 15,38 $ Digikey bulk discount
02 Eurobox ED64/42 1 31,71 € 31,71 € Auer Packaging
03 DIN EN ISO 4017 - M3x12 20 0,073 € 1,46 € Amazon
04 DIN EN ISO 4032 - M3 20 0,0449 € 0,898 € Amazon
05 DIN EN ISO 10642 - M4x12 10 0,1398 € 1,398 € Amazon
06 Ruthex M3 thread insert 8 0,0899 € 0,7192 € Ruthex
07 DIN EN ISO 7380-1 - M3x6 8 0,0721 € 0,5768 € Amazon
08 Spool holder side 10 3D-printed
09 Spool holder baseplate 5 laser cut
10 Screw cover 20 3D-printed
11 Load cell spacer small 5 3D-printed
12 Load cell spacer big 5 3D-printed
13 Load cell spacer big cover 5 3D-printed
14 Baseplate 1 laser cut
15 Silica box 2
16 Mainboard back cover 1 3D-printed
17 Mainboard front cover 1 3D-printed
18 Mainboard holder 2 3D-printed

The main enclosure for the project will be a Eurobox, because our shelf system is configured to fit Euroboxes and it makes it easy and cheap to reassemble. To fit different sizes of filament spools inside without going to big I decided to use a Box with the size 60 x 40 x 43,5 mm. To make sure that my design will fit with the existing components I reverse engineer a few by myself like the load cell or the filament spools. Others like the Eurobox I search for 3D models online.

Spool holder

Spool holder side

The spool holder side is printed which results in a okayisch surface quality. For the first iteration it is ok but needs to be improved for the finished product. The bearings will be snap fit in to position and only needs slightly pressure to slide in the correct position. The first printed version already works good but need some bigger distance to ensure that the outer ring of the bearing are not rubbing against the spool holder side, which result in unnecessary friction which could compromise the functionality. Better bearings would also a good improvement but for now I'll use the one that are momentary available.

Spool holder baseplate

To ensure that the spool holder sides fits perfectly in to the spool holder baseplate, I make some test with the conclusion that 4,9 mm will works the best because 4,8 mm fits better for just one connection but because I have two I wanted a little bit more of play at the connection, why I choose 4,9 mm.

laser test

The first plate looks like that.

assembly

There is still no sliding movement possible because the connection clamps a little bit together between the two connections. It feels more like a good fit, if the parts shouldn't move at all. The biggest challenge is that the parts need some room to slide from right to left but on the other side also make sure that the parts didn't jam.
Out of aesthetics reasons I decided to use counter sink screes to make a clean, even finish without any unnecessary disturbance. To realize the counter sink I use a drill pressed and a countersink drill.

assembly

Screw cover

To ensure easy variation of the position from the Spool holder sides but still secure them safely in place. I decided to use some type of thumbscrews which can get fast expensive and four for each spool holder is needed so all in all 20 to make it cheaper but still allows a similar easy handling I chosen to make them on my own. To make it easy and fast to manufacture I used ISO 4017 screws as a base and add some cover around it which is comfortable and easy to turn. For that reason I needed the hexagon head screw to ensure screw propulsion a form fit between the hexagon head and the Screw cover is used. To ensure a good fit I added some dogbones to the hexagon hole because with 3D printing the holes will not have perfect inner corners.

inventor

assembly

Load cell

Load cell spacer small

To connect the load cell with spool holder the load cell spacer small is inserted between the spool holder base plate and the load cell together with two DIN EN ISO 10642 - M4x12 screes to hold everything in place.

assembly

Load cell spacer big

The first idea was to make this part as simple as the load cell spacer small but confronted with the problem that I need to place the HX711 modules somewhere close to the load cell. I decided that it would be best to combine the spool holder spacer big with a small case for the HX711 module. That required some type of locking mechanism for the pcb. To realize this I choose a small lid over the pcb. The pcb itself can be slide inside from the side. I couldn't use any clips because the board didn't have any mounting holes.

inventor

assembly

Load cell spacer big cover

To cover the HX711 module a small cover is need it. The idea to mount this on the load cell spacer big I wanted to use a sliding mechanism. This needed some trails to find the perfect fit. To hold it in place I wanted to add some small holes and pins which snap in place. The corresponding geometries was to small to got a reasonable result. For now I'll not using it and try to print it on the SLA printer or to design the geometry bigger.

Baseplate

The Baseplate connect everything together mechanical and electrical wise. All five load cells are mounted on to the Baseplate to ensure a secure positioning inside the box.

Silica box

Mainboard housing

Mainboard back cover

The installation of the mainboard should be realized with two clamps that snap into two mounting holes into the pcb.

inventor

The display is directly soldered to the pcb and lack some type of mechanical support because its only connection to the pcb is on the top left corner. To fix this problem I implement two pins with small flanges to support the display into this part. They are going through a 4 mm hole in the pcb where the display can rest on the flange, to secure it in x and y axis a smaller 2,5 mm pin goes from flange to the display pcb.

inventor

Mainboard front cover

The cover will snap in place with one positive small radius on the right and left inside. That make sure that the geometry is hidden and nice finish is applied. For a nice surface finish the part will be printed with a SLA printer. On the inside some small channels are added to make sure that on each hole only the corresponding Neopixel is visible and no scattered light interrupt the aesthetics.

inventor

Mainboard holder

The Mainboard holder is responsible to connect the Mainboard back cover to the Eurobox. To make sure the parts together screes are use for the easy application. For that I want to use threaded insert, why I print them out of pla. A thermoplastic in needed to melt the thread inserts in to the part. To make this a little bit more easier I added 0,5 mm chamfer to the holes, so the threaded insert will self center it into the hole. The part also make sure that the User Interface is on an angle for easier usage.

inventor

For the first iteration two of these are used. For later spirals one wider holder with a hidden cable channel would be nice.

3D Models

Eurobox
Bearing 608

Software

Design Files

The final files will be added later.


To create this page, I used ChatGPT to check my syntax and grammar.

🅭🅯🄎 Filament Scale Box © 2025 by Benedikt Feit is licensed under CC BY-SA 4.0.

Source code hosted at gitlab.fabcloud.org