{{ :elektronik:graviertes_schild:header.jpg?nolink&3000 |}}
====== Graviertes RGB-Schild ======
Vor zwei Jahren habe ich mir eine T8 CNC aus China besorgt. Diese eignet sich sehr gut um ein Plexiglas zu beschriften.
Nun braucht man neben dem gravierten Plexiglas nur noch eine Möglichkeit dieses zu illuminieren. Darauf hin ist dieses Projekt entstanden. =)
Ales erstes habe ich es natürlich mit meinem Namen versucht. Als zweites, für ein Geschenk ein Bibeltext. Diesen zweiten Versuch möchte ich hier auch zeigen, da er mir sehr gefällt.
Hier mal ein Video:\\
{{:elektronik:graviertes_schild:video.mp4|}}
===== Aufbau =====
Das RGB-Schild besteht aus:
* Arduino Nano
* Plexiglasscheibe (ich habe meine vom [[https://www.conrad.de/de/p/acrylglasscheibe-l-x-b-100-mm-x-50-mm-materialstaerke-3-mm-transparent-1-st-530646.html|Conrad]])
* 3D-gedruckter Sockel
* WS2812B-LED-Streifen
* USB-Kabel zur Versorgung
===== Bilder =====
{{:elektronik:graviertes_schild:schild_vorne.jpg?direct&300|}}
\\ fertiges Schild
{{:elektronik:graviertes_schild:fraesmaschiene.jpg?direct&300|}}
\\ verwendete Graviermaschine
{{:elektronik:graviertes_schild:schild_unten.jpg?direct&300|}}
\\ Platine und LED-Streifen ist eingeklebt
{{:elektronik:graviertes_schild:schild_gravierung.jpg?direct&300|}}
\\ von hinten gravierter Text
===== Gravieren =====
Die Vektordaten für die Gravur habe ich mit Inkscape erzeugt.
Das Problem ist allerdings, das die üblichen Vektorschriften nur bedingt nutzbar sind. Man sollte eine Schriftart haben, die nur aus einer Linie besteht. Eine Gravurschriftart.
Für Inkscape gibt es hier das Plugin [[https://wiki.evilmadscientist.com/Hershey_Text|Hershey Text]].
Die mit Inkscape erzeugte SVG-Datei habe ich anschließend in [[https://estlcam.de/|Estlcam]] zu einer NC-Datei verarbeitet, welche ich mit meiner Gravurmaschine nutzen kann.
Wichtig ist natürlich das Objekt vor dem Konvertieren zu spiegeln, damit man den Text "von hinten" eingravieren kann.
| {{:elektronik:graviertes_schild:graviertext.svg?300|}} |
Nachdem das Schild graviert ist und die Aussparung für das Schild im 3D-Druck mit einer Nagelfeile auf die richtige Größe gebracht wurde, kann man es einkleben.
===== Anschluss =====
Der LED-Streifen wird an VCC und GND vom Arduino angeschlossen.
Der Daten-Pin des Streifens an **D2** des Arduinos.
===== Software =====
Als externe Bibliothek wird [[https://github.com/ratkins/RGBConverter|RGBConverter]] und [[https://github.com/adafruit/Adafruit_NeoPixel|Adafruit NeoPixel]] benötigt.
Die Software spielt eine RGB-Animation ab (funktioniert ohne PC). Die LEDs können aber auch über entsprechende Befehle vom PC aus gesteuert werden.
++++ led_schild.ino |
#include
#include
#include
Adafruit_NeoPixel pixels = Adafruit_NeoPixel(5, 2, NEO_GRB + NEO_KHZ800);
String serialBuffer = "";
byte pixelBuffer[5][3];
bool animation_active = true;
void setup() {
pixels.begin();
pixels.show();
Serial.begin(115200);
eepromRead();
}
void loop() {
//Serial-Bsp.: s;255;000;000;255;000;000;255;000;000;255;000;000;255;000;000
decodeSerial();
if(animation_active) animation();
}
unsigned long time_last;
double colordistance = 0.10;
double counter = 0.0;
void animation() {
unsigned long time = millis();
if(time-time_last>5) {
for(int i = 0; i<5; i++) {
double h = counter + colordistance * (i+1);
if(h>1.0) h -= 1.0;
byte rgb[3];
RGBConverter conv;
conv.hslToRgb(h, 1.0, 0.30, rgb);
for(int j = 0; j<3; j++) {
pixelBuffer[i][j] = rgb[j];
}
if(counter < 1.0) counter+=0.0003; else counter = 0.0;
}
showPixel();
time_last = time;
}
}
void showPixel() {
for(int i = 0;i<5;i++) {
pixels.setPixelColor(i, pixels.Color(pixelBuffer[i][0],pixelBuffer[i][1],pixelBuffer[i][2]));
}
pixels.show();
}
void decodeSerial() {
if (Serial.available() > 0) {
char incomingByte = Serial.read();
if(incomingByte!='\n') {
serialBuffer += incomingByte;
} else {
if(serialBuffer[0]=='e' && serialBuffer.length()==1) {
eepromSave();
}
if(serialBuffer[0]=='s' && serialBuffer.length()==61) {
bool seperatorCheck = true;
int p = 1;
while(p<=57) {
if(serialBuffer[p]!=';') seperatorCheck = false;
p += 4;
}
if(seperatorCheck) {
animation_active = false;
int pos = 2;
for(int i = 0;i<5;i++) {
for(int j = 0;j<3;j++) {
pixelBuffer[i][j] = serialBuffer.substring(pos,pos+2).toInt();
pos+=4;
}
}
showPixel();
}
}
serialBuffer = "";
}
}
}
void eepromSave() {
for(int i = 0;i<5;i++) {
EEPROM.update(i*3 + 0, pixelBuffer[i][0]);
EEPROM.update(i*3 + 1, pixelBuffer[i][1]);
EEPROM.update(i*3 + 2, pixelBuffer[i][1]);
}
}
void eepromRead() {
for(int i = 0;i<5;i++) {
pixelBuffer[i][0] = EEPROM.read(i*3 + 0);
pixelBuffer[i][1] = EEPROM.read(i*3 + 1);
pixelBuffer[i][2] = EEPROM.read(i*3 + 2);
}
showPixel();
}
++++
Und hier noch eine Alternative für ein gelbes Bild mit leichtem und sanftem Helligkeits/Farbflackern.
Benutzt die [[https://github.com/rlogiacco/CircularBuffer|CircularBuffer]]-Library. Ist durch die vielen Buffer relativ ressourcenhungrig umgesetzt. Aber funktioniert.
++++ led_schild.ino - Farbflackern |
#include
#include
#include
#include
Adafruit_NeoPixel pixels = Adafruit_NeoPixel(5, 2, NEO_GRB + NEO_KHZ800);
String serialBuffer = "";
byte pixelBuffer[5][3];
bool animation_active = true;
void setup() {
pixels.begin();
pixels.show();
Serial.begin(115200);
eepromRead();
}
void loop() {
//Serial-Bsp.: s;255;000;000;255;000;000;255;000;000;255;000;000;255;000;000
decodeSerial();
if(animation_active) animation();
}
unsigned long time_last;
CircularBuffer history_buffer[5][3];
void animation() {
unsigned long time = millis();
if(time-time_last>20) {
for(int i = 0; i<5; i++) {
byte rgb[3];
RGBConverter conv;
float h = 0.00 + (random(300)/1000.0);
float s = 1.0;
float l = 0.0 + (random(800)/1000.0);
history_buffer[i][0].push(h);
history_buffer[i][1].push(s);
history_buffer[i][2].push(l);
float mean[] = { 0, 0, 0 };
for(int j = 0; j<3; j++) {
float sum = 0.0;
for(uint8_t k = 0; k < history_buffer[i][j].size()-1; k++) {
sum += history_buffer[i][j][k];
}
mean[j] = sum / history_buffer[i][j].size();
}
conv.hslToRgb(mean[0], mean[1], mean[2], rgb);
for(int j = 0; j<3; j++) {
pixelBuffer[i][j] = rgb[j];
}
}
showPixel();
time_last = time;
}
}
void showPixel() {
for(int i = 0;i<5;i++) {
pixels.setPixelColor(i, pixels.Color(pixelBuffer[i][0],pixelBuffer[i][1],pixelBuffer[i][2]));
}
pixels.show();
}
void decodeSerial() {
if (Serial.available() > 0) {
char incomingByte = Serial.read();
if(incomingByte!='\n') {
serialBuffer += incomingByte;
} else {
if(serialBuffer[0]=='e' && serialBuffer.length()==1) {
eepromSave();
}
if(serialBuffer[0]=='s' && serialBuffer.length()==61) {
bool seperatorCheck = true;
int p = 1;
while(p<=57) {
if(serialBuffer[p]!=';') seperatorCheck = false;
p += 4;
}
if(seperatorCheck) {
animation_active = false;
int pos = 2;
for(int i = 0;i<5;i++) {
for(int j = 0;j<3;j++) {
pixelBuffer[i][j] = serialBuffer.substring(pos,pos+2).toInt();
pos+=4;
}
}
showPixel();
}
}
serialBuffer = "";
}
}
}
void eepromSave() {
for(int i = 0;i<5;i++) {
EEPROM.update(i*3 + 0, pixelBuffer[i][0]);
EEPROM.update(i*3 + 1, pixelBuffer[i][1]);
EEPROM.update(i*3 + 2, pixelBuffer[i][1]);
}
}
void eepromRead() {
for(int i = 0;i<5;i++) {
pixelBuffer[i][0] = EEPROM.read(i*3 + 0);
pixelBuffer[i][1] = EEPROM.read(i*3 + 1);
pixelBuffer[i][2] = EEPROM.read(i*3 + 2);
}
showPixel();
}
++++
===== 3D Modell =====
{{:elektronik:graviertes_schild:plexiglasschild.stl?h=200&w=300&bgcolor=#ffffff|Sockel}}
{{tag>[arduino led graviermaschine WS2812B]}}
\\ ~~DISQUS~~