제조공정
| × | 2 | ||||
| × | 2 | ||||
| × | 1 | ||||
| × | 1 | ||||
| × | 1 |
|
| ||||
| ||||
|
아이디어
여러 비디오를 보고 라이트 페인팅에 대한 수많은 기사를 본 후, 나는 그것을 시도하기로 결정했습니다. 라이트 페인팅은 노출 시간이 매우 긴 카메라를 사용하여 작은 광원을 캡처하는 작업을 포함합니다. 이렇게 하면 단일 이미지에서 하나의 빛이 긴 줄무늬로 늘어납니다.
그러나 누군가가 더 자세한 그림을 만들거나 다양한 색상을 사용하고 싶다면 어떻게 해야 할까요? 이것이 내가 색상을 변경하고 이미지를 "페인트"할 수 있는 단일 RGB LED가 있는 2축 CNC 기계를 구축하는 아이디어를 생각해낸 방법입니다.
계획
이 프로젝트가 작동하려면 2축 CNC 기계, RGB LED, SD 카드 및 장노출 사진을 찍을 수 있는 카메라의 네 가지 주요 구성 요소가 필요합니다. 먼저 Arduino Mega는 SD 카드를 읽고 인쇄할 비트맵을 찾습니다.
그런 다음 이미지의 너비가 초과될 때마다 행 아래로 이동하면서 수평으로 가로질러 해당 LED를 켭니다. 마지막으로 조금 기다렸다가 다음 비트맵을 검색하고 더 이상 만들 이미지가 없을 때마다 중지합니다.
리그 구성
CNC 기계를 설계하고 제작한 경험으로 인해 이 단계는 그리 어렵지 않았습니다. 다른 프로젝트에서도 확장할 수 있는 모듈식 제품을 만들고 싶었기 때문에 평행 알루미늄 돌출부를 따라 움직이는 크로스바에 부착된 두 개의 타이밍 벨트를 사용하는 단순한 디자인으로 결정했습니다.
이를 통해 각 축의 길이를 사용자 정의할 수 있습니다. X축의 끝 부분에는 3D 인쇄된 엔드 캡이 있으며 그 중 하나에는 X축 스테퍼 모터 및 베어링용 마운트가 있습니다.
비트맵 읽기
비트맵 파일 형식은 단순함과 읽기 쉽기 때문에 선택했습니다. 파일 형식에 따라 파일 자체에 읽어야 하는 몇 가지 중요한 주소가 있습니다. 0x12(너비), 0x16(높이), 0x1C(색심도), 0xA(픽셀 데이터 위치), 마지막으로 0x36(픽셀 데이터가 일반적으로 있는 위치)입니다.
데이터는 2 또는 4바이트(16 또는 32비트)의 청크로 읽혀지며 포인터도 다음 주소로 이동합니다. 읽기 기능은 오프셋과 크기를 포함한 모든 중요한 데이터를 살펴보고 가져옵니다. 그런 다음 각 픽셀을 한 행씩 읽습니다.
이미지 준비
대부분의 카메라는 최대 30초의 노출 시간으로 제한되어 있기 때문에 해당 시간 동안 표시할 수 있는 총 픽셀 수는 약 288개로 제한됩니다. 이것은 약 18 x 16 이미지에 해당합니다. 내 이미지를 만들기 위해 김프를 로드하고 매우 간단한 픽셀 아트를 만들기 시작했습니다. 여기에는 포켓볼, 하트, 점프하는 마리오가 포함됩니다. 그런 다음 이 세 개의 이미지를 SD 카드의 루트 디렉터리에 있는 "bitmaps"라는 디렉터리에 넣었습니다. 프로그램은 이 폴더의 모든 이미지를 읽습니다.
회화 프로그램
스테퍼 모터에는 내부 위치 피드백 시스템이 없기 때문에 소프트웨어로 위치를 추적해야 합니다. 내가 작성한 프로그램은 쉽게 확장할 수 있도록 그리드 시스템으로 LED의 위치를 추적합니다. Arduino Mega가 시작되면 스테퍼 위치가 0, 0으로 설정된 다음 첫 번째 이미지를 찾아서 읽습니다. 그런 다음 LED가 5번 깜박여 사진 작가에게 촬영을 시작할 시간이 거의 되었음을 알립니다. 비트맵은 먼저 각 행을 반복하여 읽고 각 행 내에서 각 열을 읽습니다. 현재 행과 열을 알면 스테퍼 모터를 동일한 위치로 이동할 수 있습니다. 각 위치에서 LED는 해당 픽셀의 색상으로 변경됩니다.
(재)-이미지 생성
SD 카드를 삽입하고 모터용 12v 전원을 연결한 후 기계를 켤 시간이었습니다. 내 카메라에서는 고스트 효과를 최소화하기 위해 노출 시간 20초, 조리개 F36, ISO 100, 노출 보정 -5 스탑으로 설정했습니다. 그린 첫 번째 이미지는 여기에서 볼 수 있는 포켓볼입니다.
약간 흐릿하긴 해도 모양은 여전히 선명하게 보입니다. 그런 다음 하트 비트맵을 생성했습니다.
이 이미지는 9 x 9픽셀에 불과했기 때문에 각 개별 픽셀은 훨씬 덜 정의되었습니다. 마지막으로 마리오가 점프하는 모습을 그렸습니다.
이 사진에는 주로 밝은 색상의 픽셀이 많기 때문에 고스트 현상이 심합니다.
개선을 위한 향후 아이디어
내가 만든 라이트 페인팅은 처음에 생각했던 것보다 훨씬 잘 나왔지만 여전히 개선의 여지가 있습니다. 제가 가장 하고 싶은 일은 LED가 어두워진 상태에서 움직이고 정지 상태일 때만 켜지도록 하여 블러의 양을 줄이는 것입니다. 이 기술은 재생성된 이미지의 선명도를 크게 향상시킵니다.
섹션> <섹션 클래스="섹션 컨테이너 섹션 축소 가능" id="코드">//Adafruit에서 부분적으로 비트맵 읽기 기능#include섹션>#include #include "DRV8825.h#define MOTOR_STEPS 200#define RPM 150#define MICROSTEPS 4//핀 정의#define // STEPPER_X_DIR 7#define STEPPER_X_STEP 6#define STEPPER_X_EN 8#define STEPPER_Y_DIR 4#define STEPPER_Y_STEP 5#define STEPPER_Y_EN 12#define X 0#define Y 1#define X_DIR_FLAG -1 //1 또는 FL로 뒤집기 1 또는 -1 방향 반전#define STEPS_PER_MM (3.75 * MICROSTEPS) //1mm 이동에 필요한 단계#define SPACE_BETWEEN_POSITIONS 5 //이동당 5mm#define R A0#define G A1#define B A2#define SD_CS 22int currentPositions[] ={0, 0};DRV8825 스테퍼X(MOTOR_STEPS, STEPPER_X_DIR, STEPPER_X_STEP, STEPPER_X_EN);DRV8825 스테퍼Y(MOTOR_STEPS, STEPPER_Y_DIR, STEPPER_Y_STEP, STEPPER_Y_EN); 무효 설정(20)1; 직렬 init_steppers(); SD.begin(SD_CS); 생성 비트맵(); 스테퍼X.disable(); 스테퍼Y.disable(); while(1);}void 루프() {}void createBitmaps(){ 파일 디렉토리 =SD.open("비트맵"); while(true){ 파일 비트맵 =dir.openNextFile(); if(! 비트맵){ 휴식; } 페인트 비트맵(비트맵); 지연(15000); } }#define BUFFPIXEL 20void paintBitmap(파일 bmpFile){ int bmpWidth, bmpHeight; uint8_t bmpDepth; uint32_t bmpImageOffset; uint32_t 행 크기; // 항상 그런 것은 아님 =bmpWidth; 패딩이 있을 수 있음 uint8_t sdbuffer[3 * BUFFPIXEL]; // 픽셀 버퍼(픽셀당 R+G+B) uint8_t buffidx =sizeof(sdbuffer); // sdbuffer의 현재 위치 부울 goodBmp =false; // 유효한 헤더 구문 분석에서 true로 설정 부울 flip =true; // BMP는 아래에서 위로 저장됩니다. int w, h, row, col; uint8_t r, g, b; uint32_t 위치 =0, 시작 시간 =밀리(); 직렬.println(); Serial.print("이미지 불러오기 '"); Serial.print(bmpFile.name()); Serial.println('\''); // SD 카드에서 요청된 파일 열기 // BMP 헤더 구문 분석 if (read16(bmpFile) ==0x4D42) { // BMP 서명 Serial.print("파일 크기:"); Serial.println(read32(bmp파일)); (무효)read32(bmp파일); // 작성자 바이트 읽기 및 무시 bmpImageOffset =read32(bmpFile); // 이미지 데이터 시작 Serial.print("이미지 오프셋:"); Serial.println(bmpImageOffset, DEC); // DIB 헤더 읽기 Serial.print("헤더 크기:"); Serial.println(read32(bmp파일)); bmp폭 =read32(bmp파일); bmp높이 =read32(bmp파일); if (read16(bmpFile) ==1) { // # 평면 -- '1'이어야 함 bmpDepth =read16(bmpFile); // 픽셀당 비트 수 Serial.print("Bit Depth:"); Serial.println(bmpDepth); if ((bmpDepth ==24) &&(read32(bmpFile) ==0)) { // 0 =압축되지 않은 goodBmp =true; // 지원되는 BMP 형식 -- 계속하십시오! Serial.print("이미지 크기:"); Serial.print(bmpWidth); Serial.print('x'); Serial.println(bmp높이); // BMP 행은 (필요한 경우) 4바이트 경계로 채워집니다. rowSize =(bmpWidth * 3 + 3) &~3; // bmpHeight가 음수이면 이미지는 하향식 순서입니다. // 이것은 표준이 아니지만 야생에서 관찰되었습니다. if (bmpHeight <0) { bmpHeight =-bmpHeight; 뒤집기 =거짓; } // 로드할 자르기 영역 w =bmpWidth; h =bmp 높이; if(bmpWidth*bmpHeight>290){ //너무 큼 Serial.println("파일이 너무 커서 인쇄할 수 없습니다."); 반품; } for(uint8_t i=0; i<5;i++){ analogWrite(R, 150); 지연(500); analogWrite(R, 0); 지연(500); } for (row =0; row =sizeof(sdbuffer)) { // 실제로 bmpFile.read(sdbuffer, sizeof(sdbuffer)); 버피드x =0; // 인덱스를 시작으로 설정 } // 픽셀을 BMP에서 TFT 형식으로 변환하고 푸시하여 표시 b =sdbuffer[buffidx++]; g =sdbuffer[버피드x++]; r =sdbuffer[버피드x++]; moveToPosition(열, 행); 활성화 LED(r,g,b); // 최적화! //tft.pushColor(tft.Color565(r,g,b)); } // 끝 픽셀 analogWrite(R, 0); analogWrite(G, 0); analogWrite(B, 0); } // 스캔라인 종료 Serial.print("Loaded in "); Serial.print(millis() - 시작 시간); Serial.println("밀리초"); } // goodBmp 종료 } } bmpFile.close(); 이동 위치(0,0); if (!goodBmp) Serial.println("BMP 형식이 인식되지 않습니다.");}uint16_t read16(파일 f) { uint16_t 결과; ((uint8_t *)&결과)[0] =f.read(); // LSB((uint8_t *)&결과)[1] =f.read(); // MSB 반환 결과;}uint32_t read32(파일 f) { uint32_t 결과; ((uint8_t *)&결과)[0] =f.read(); // LSB((uint8_t *)&결과)[1] =f.read(); ((uint8_t *)&결과)[2] =f.read(); ((uint8_t *)&결과)[3] =f.read(); // MSB 반환 결과;}void activateLED(int r, int g, int b){ Serial.print(F("LED의 값:")); Serial.print(r); Serial.print(", "); Serial.print(g); Serial.print(", "); Serial.println(b); analogWrite(R, r); analogWrite(G, g); analogWrite(B, b);} 무효 moveToPosition(int x, int y){ int newPosX =(x-currentPositions[X])*STEPS_PER_MM*X_DIR_FLAG*SPACE_BETWEEN_POSITIONS; int newPosY =(y-currentPositions[Y])*STEPS_PER_MM*Y_DIR_FLAG*SPACE_BETWEEN_POSITIONS; stepperX.move(newPosX); stepperY.move(newPosY); 현재 위치[X] =x; 현재 위치[Y] =y; Serial.print("스테퍼 위치:"); Serial.print(현재 위치[X]); Serial.print(", "); Serial.println(currentPositions[Y]);} 무효 init_steppers(){ stepperX.begin(RPM); 스테퍼X.setEnableActiveState(낮음); 스테퍼X.enable(); stepperX.setMicrostep(MICROSTEPS); 스테퍼Y.begin(RPM); 스테퍼Y.setEnableActiveState(낮음); 스테퍼Y.enable(); stepperY.setMicrostep(MICROSTEPS);}
제조공정
모터는 시스템 연결에서 에너지를 변환할 때 필수적인 구성 요소입니다. 중요한 것은 모터를 찾는 전자 애호가의 경우 모터 효율이 높은 신뢰할 수 있는 모터를 찾는 것입니다. 따라서 이 기사에서는 nema23 스테퍼 모터, 핀 구성, 사양, 애플리케이션 및 연결에 사용하는 방법에 대해 설명합니다. 1. Nema 23 스테퍼 모터란 무엇입니까? NEMA 23은 대부분 높은 토크를 가진 하이브리드 바이폴라 스테퍼 모터입니다. 또한 모터는 전력을 생성하는 데 사용되는 2상 스테핑 모터입니다. 특히 계단 각도가 1.8도라는 점에서 눈에
인베스트먼트 주조 방법은 세라믹 슬러리에 담근 왁스 패턴을 사용하여 고객을 위한 금속 부품을 형성할 주형을 만듭니다. 왁스 패턴을 만들기 위해서는 제조사에서 툴링을 설계하고 제작해야 합니다. 고객은 제조업체로부터 맞춤형 부품을 받기 때문에 각 특정 프로젝트에 대해 툴링이 생성됩니다. 툴링 설계 및 제조는 다른 모든 매몰 주조 공정 단계 전에 이루어집니다. 일부 제조업체는 모든 도구를 사내에서 제작하고 다른 제조업체는 도구를 수행하기 위해 다른 회사와 계약합니다. 툴링과 관련하여 대부분의 비용은 프로젝트 초기에 인용됩니다. 툴