Arduino Mini CNC Yapımı
Arduino Mini CNC projesi son günlerde çok popüler olan bir proje yabancı kaynaklarda ve ülkemizde çokça yapılmakta ve paylaşılmakta.Hatta o kadar çok yapılıyor ki ikinci el bozuk CD/DVC satıcıları bile bu işe uyanıp fiyatları artırmışlar.
Projemizde kullanılan malzemelerin temin edilmesi gerçekten çok kolay.Aşağıdaki verdiğimiz malzeme listesini eksiksiz bir şekilde temin edin ardından yapıma başlayalım.
Malzemeler
- Arduino UNO
- L293B veya L293D motor sürücü (2 adet)
- Bozuk CD/DVC (2 adet)
- Servo motor
Öncelikle CD veya DVD okuyucuların içlerini sökmeniz gerekiyor bize gerekli olan kısım motor ve kayar mekanizma.
Daha sonra sürücüleri biri dikey diğeri yatay olacak şekilde resimlerde görüldüğü gibi sabitleyin.Dikey olan sistem üzerine birde servo motor kızağı eklemeniz gerekmekte, servo motor yazı yazılırken kalemi kaldırıp indirmektedir.Bu sayede daha güzel ve kusursuz yazı yazmayı sağlamaktadır.
Arduino kodunu indir
#include <Servo.h> #include <Stepper.h> #define LINE_BUFFER_LENGTH 512 const int penZUp = 80; const int penZDown = 40; const int penServoPin = 6; const int stepsPerRevolution = 20; Servo penServo; Stepper myStepperY(stepsPerRevolution, 2,3,4,5); Stepper myStepperX(stepsPerRevolution, 8,9,10,11); struct point { float x; float y; float z; }; struct point actuatorPos; float StepInc = 1; int StepDelay = 0; int LineDelay = 50; int penDelay = 50; float StepsPerMillimeterX = 6.0; float StepsPerMillimeterY = 6.0; float Xmin = 0; float Xmax = 40; float Ymin = 0; float Ymax = 40; float Zmin = 0; float Zmax = 1; float Xpos = Xmin; float Ypos = Ymin; float Zpos = Zmax; boolean verbose = false; void setup() { // Setup Serial.begin( 9600 ); penServo.attach(penServoPin); penServo.write(penZUp); delay(200); // Decrease if necessary myStepperX.setSpeed(250); myStepperY.setSpeed(250); Serial.println("Mini CNC Plotter alive and kicking!"); Serial.print("X range is from "); Serial.print(Xmin); Serial.print(" to "); Serial.print(Xmax); Serial.println(" mm."); Serial.print("Y range is from "); Serial.print(Ymin); Serial.print(" to "); Serial.print(Ymax); Serial.println(" mm."); } void loop() { delay(200); char line[ LINE_BUFFER_LENGTH ]; char c; int lineIndex; bool lineIsComment, lineSemiColon; lineIndex = 0; lineSemiColon = false; lineIsComment = false; while (1) { while ( Serial.available()>0 ) { c = Serial.read(); if (( c == '\n') || (c == '\r') ) { if ( lineIndex > 0 ) { line[ lineIndex ] = '\0'; if (verbose) { Serial.print( "Received : "); Serial.println( line ); } processIncomingLine( line, lineIndex ); lineIndex = 0; } else { } lineIsComment = false; lineSemiColon = false; Serial.println("ok"); } else { if ( (lineIsComment) || (lineSemiColon) ) { if ( c == ')' ) lineIsComment = false; } else { if ( c <= ' ' ) { } else if ( c == '/' ) { } else if ( c == '(' ) { lineIsComment = true; } else if ( c == ';' ) { lineSemiColon = true; } else if ( lineIndex >= LINE_BUFFER_LENGTH-1 ) { Serial.println( "ERROR - lineBuffer overflow" ); lineIsComment = false; lineSemiColon = false; } else if ( c >= 'a' && c <= 'z' ) { line[ lineIndex++ ] = c-'a'+'A'; } else { line[ lineIndex++ ] = c; } } } } } } void processIncomingLine( char* line, int charNB ) { int currentIndex = 0; char buffer[ 64 ]; struct point newPos; newPos.x = 0.0; newPos.y = 0.0; while( currentIndex < charNB ) { switch ( line[ currentIndex++ ] ) { case 'U': penUp(); break; case 'D': penDown(); break; case 'G': buffer[0] = line[ currentIndex++ ]; buffer[1] = '\0'; switch ( atoi( buffer ) ){ case 0: case 1: char* indexX = strchr( line+currentIndex, 'X' ); char* indexY = strchr( line+currentIndex, 'Y' ); if ( indexY <= 0 ) { newPos.x = atof( indexX + 1); newPos.y = actuatorPos.y; } else if ( indexX <= 0 ) { newPos.y = atof( indexY + 1); newPos.x = actuatorPos.x; } else { newPos.y = atof( indexY + 1); indexY = '\0'; newPos.x = atof( indexX + 1); } drawLine(newPos.x, newPos.y ); // Serial.println("ok"); actuatorPos.x = newPos.x; actuatorPos.y = newPos.y; break; } break; case 'M': buffer[0] = line[ currentIndex++ ]; buffer[1] = line[ currentIndex++ ]; buffer[2] = line[ currentIndex++ ]; buffer[3] = '\0'; switch ( atoi( buffer ) ){ case 300: { char* indexS = strchr( line+currentIndex, 'S' ); float Spos = atof( indexS + 1); // Serial.println("ok"); if (Spos == 30) { penDown(); } if (Spos == 50) { penUp(); } break; } case 114: Serial.print( "Absolute position : X = " ); Serial.print( actuatorPos.x ); Serial.print( " - Y = " ); Serial.println( actuatorPos.y ); break; default: Serial.print( "Command not recognized : M"); Serial.println( buffer ); } } } } void drawLine(float x1, float y1) { if (verbose) { Serial.print("fx1, fy1: "); Serial.print(x1); Serial.print(","); Serial.print(y1); Serial.println(""); } if (x1 >= Xmax) { x1 = Xmax; } if (x1 <= Xmin) { x1 = Xmin; } if (y1 >= Ymax) { y1 = Ymax; } if (y1 <= Ymin) { y1 = Ymin; } if (verbose) { Serial.print("Xpos, Ypos: "); Serial.print(Xpos); Serial.print(","); Serial.print(Ypos); Serial.println(""); } if (verbose) { Serial.print("x1, y1: "); Serial.print(x1); Serial.print(","); Serial.print(y1); Serial.println(""); } // Koordinatları çeviriyor x1 = (int)(x1*StepsPerMillimeterX); y1 = (int)(y1*StepsPerMillimeterY); float x0 = Xpos; float y0 = Ypos; // Koordinatları buluyor long dx = abs(x1-x0); long dy = abs(y1-y0); int sx = x0<x1 ? StepInc : -StepInc; int sy = y0<y1 ? StepInc : -StepInc; long i; long over = 0; if (dx > dy) { for (i=0; i<dx; ++i) { myStepperX.step(sx); over+=dy; if (over>=dx) { over-=dx; myStepperY.step(sy); } delay(StepDelay); } } else { for (i=0; i<dy; ++i) { myStepperY.step(sy); over+=dx; if (over>=dy) { over-=dy; myStepperX.step(sx); } delay(StepDelay); } } if (verbose) { Serial.print("dx, dy:"); Serial.print(dx); Serial.print(","); Serial.print(dy); Serial.println(""); } if (verbose) { Serial.print("Going to ("); Serial.print(x0); Serial.print(","); Serial.print(y0); Serial.println(")"); } delay(LineDelay); // Pozisyon yükleniyor Xpos = x1; Ypos = y1; } // Kalem durumu void penUp() { penServo.write(penZUp); delay(LineDelay); Zpos=Zmax; if (verbose) { Serial.println("Kalem Aşağı!"); } } // Lowers pen void penDown() { penServo.write(penZDown); delay(LineDelay); Zpos=Zmin; if (verbose) { Serial.println("Kalem Yukarı."); } }
Projenin devre şeması aşağıdaki gibidir.
Processing kodları
import java.awt.event.KeyEvent; import javax.swing.JOptionPane; import processing.serial.*; Serial port = null; // select and modify the appropriate line for your operating system // leave as null to use interactive port (press 'p' in the program) String portname = null; //String portname = Serial.list()[0]; // Mac OS X //String portname = "/dev/ttyUSB0"; // Linux //String portname = "COM6"; // Windows boolean streaming = false; float speed = 0.001; String[] gcode; int i = 0; void openSerialPort() { if (portname == null) return; if (port != null) port.stop(); port = new Serial(this, portname, 9600); port.bufferUntil('\n'); } void selectSerialPort() { String result = (String) JOptionPane.showInputDialog(frame, "Select the serial port that corresponds to your Arduino board.", "Select serial port", JOptionPane.QUESTION_MESSAGE, null, Serial.list(), 0); if (result != null) { portname = result; openSerialPort(); } } void setup() { size(500, 250); openSerialPort(); } void draw() { background(0); fill(255); int y = 24, dy = 12; text("INSTRUCTIONS", 12, y); y += dy; text("p: select serial port", 12, y); y += dy; text("1: set speed to 0.001 inches (1 mil) per jog", 12, y); y += dy; text("2: set speed to 0.010 inches (10 mil) per jog", 12, y); y += dy; text("3: set speed to 0.100 inches (100 mil) per jog", 12, y); y += dy; text("arrow keys: jog in x-y plane", 12, y); y += dy; text("page up & page down: jog in z axis", 12, y); y += dy; text("$: display grbl settings", 12, y); y+= dy; text("h: go home", 12, y); y += dy; text("0: zero machine (set home to the current location)", 12, y); y += dy; text("g: stream a g-code file", 12, y); y += dy; text("x: stop streaming g-code (this is NOT immediate)", 12, y); y += dy; y = height - dy; text("current jog speed: " + speed + " inches per step", 12, y); y -= dy; text("current serial port: " + portname, 12, y); y -= dy; } void keyPressed() { if (key == '1') speed = 0.001; if (key == '2') speed = 0.01; if (key == '3') speed = 0.1; if (!streaming) { if (keyCode == LEFT) port.write("G91\nG20\nG00 X-" + speed + " Y0.000 Z0.000\n"); if (keyCode == RIGHT) port.write("G91\nG20\nG00 X" + speed + " Y0.000 Z0.000\n"); if (keyCode == UP) port.write("G91\nG20\nG00 X0.000 Y" + speed + " Z0.000\n"); if (keyCode == DOWN) port.write("G91\nG20\nG00 X0.000 Y-" + speed + " Z0.000\n"); if (keyCode == KeyEvent.VK_PAGE_UP) port.write("G91\nG20\nG00 X0.000 Y0.000 Z" + speed + "\n"); if (keyCode == KeyEvent.VK_PAGE_DOWN) port.write("G91\nG20\nG00 X0.000 Y0.000 Z-" + speed + "\n"); if (key == 'h') port.write("G90\nG20\nG00 X0.000 Y0.000 Z0.000\n"); if (key == 'v') port.write("$0=75\n$1=74\n$2=75\n"); //if (key == 'v') port.write("$0=100\n$1=74\n$2=75\n"); if (key == 's') port.write("$3=10\n"); if (key == 'e') port.write("$16=1\n"); if (key == 'd') port.write("$16=0\n"); if (key == '0') openSerialPort(); if (key == 'p') selectSerialPort(); if (key == '$') port.write("$$\n"); } if (!streaming && key == 'g') { gcode = null; i = 0; File file = null; println("Loading file..."); selectInput("Select a file to process:", "fileSelected", file); } if (key == 'x') streaming = false; } void fileSelected(File selection) { if (selection == null) { println("Window was closed or the user hit cancel."); } else { println("User selected " + selection.getAbsolutePath()); gcode = loadStrings(selection.getAbsolutePath()); if (gcode == null) return; streaming = true; stream(); } } void stream() { if (!streaming) return; while (true) { if (i == gcode.length) { streaming = false; return; } if (gcode[i].trim().length() == 0) i++; else break; } println(gcode[i]); port.write(gcode[i] + '\n'); i++; } void serialEvent(Serial p) { String s = p.readStringUntil('\n'); println(s.trim()); if (s.trim().startsWith("ok")) stream(); if (s.trim().startsWith("error")) stream(); // XXX: really? }
Merhaba 3 eksen cnc plotter yapmak istiyorum. Proje aşamalarında bir takım sorunla karşılaştım. Cnc shield kartın Z+ ucuna sg90 sensörünü bağladığımda sensörü döndüremiyorun fakat x ve y eksenleri hareket ediyor.(gcodesender programında). Sg90 servo motorunu sadece arduino ile hazır kod attığımdad çalışmaktadır. Bunun sorunu sizce nedir? Yardımcı olabilecek var mıdır?
Slm bunu android cihazlarla nasıl kontrol ederiz bu konuda hiç bir çalışma yok
Benservo motoru kulanmak istemiyorum servo yerine lazer diot atacam onun kodunu nasıl ayarlaya bilirim