Introduction: Holocron Lamp for the Discerning Jedi
With the wave of your hand, the Holocron opens up keeping you on the light-side.
It's a Holocron lamp using the force open and close. With the wave of a hand over the top any discerning Jedi can access the path the the light.
This project is based around the Particle Photon IoT dev board, and I have to say this has been a joy to work on! In the trailer you can see a few images and videos from the start to the finish.
Step 1: The Cinematic Trailer
Step 2: Parts You Need
Infrared (940nm) LED (5mm)×4
Infrared (940nm) Receiver Diode ×1
MPSA13 NPN Darlington Pair×2
Resistor 47.5 ohm×8
Resistor 10k ohm×2
Resistor 180ohm×4
Resistor 100k ohm×1
Gold PLA for the main enclosure×1
Jumper wires (generic)×20
Breadboard (generic)×1
tinned copper wire×1
superglue×1heatshrink×1
t-glase petg blue×1
heatshrink as required×1
super glue and activator×1
Step 3: Concept Idea
First step was to think of everything I needed to make this work, I settled on an IR proximity sensor, a servo for the movement and some super-bright white LED's for the light.
Step 4: First Steps
Firstly I prototype the electronics on the breadboard and fleshed out all the details in the code. It works! this was obviously a relief.
Once all the code and circuitry had been proven it was time to begin printing the enclosure. I chose to use gold as this is a traditional Holocron material, the enclosure is designed to be press fit together, meaning there is hardly any need for support structure when printing.
Step 5: 3D Printing
Total printing time ran into about 30 hours, so best leave plenty of time!
Once I had the main enclosure parts printed it was time to customize the electronics and build them in.
Step 6: Firstly Add the IR (infrared) LED's Into the Holes Using As a Guide
Step 7: Connect and Solder the Cathodes (google Is Your Friend If Unsure!)
Step 8: Add 180R Anode Resistors
Step 9: Add Wires and Make Sure Your Label Them!
Step 10: Add Wires to the IR Receiver Diode (the Black One) and Add Heatshrink to Stop Shorting. Don't Forget the Label!
Step 11: Post LED's Through From the Underside
Step 12: Add Superglue to Secure Them
Step 13: Add Super Bright LED's As Shown, Cathodes in the Centre
Step 14: Solder the Cathodes
Step 15: Bend the Anodes to Secure
Step 16: Add Annode Resistors, Repeate 3 More Times (for Each Side)
Step 17: Add Tinned Copper Wire Bus Bar Connecting the LED's Together
Step 18: Add Wires to the Bus Bars and Remember to Add a Label
Step 19: Add the Servo, You May Need to Add Spacers Depending on the Model Chosen
Step 20: Drop the Wires Through the Centre
Step 21: Add the Remaining 3D Printed Parts, No Glue Required!
Step 22: Tidy Up the Breadboard So It's Nice and Neat (this Step It Optional But Helps!)
Step 23: (optional)Make a 9 Pin Single Connector So It's Easier to Fix Wires to the Breadboard
Step 24: The Cable Assembly and Connector Drop Through the Rack Part of the Assembly
Step 25: Final Assembly and Testing
Step 26: Add the Final Side Parts and Blue Lenses
T-Glase PETG Filament was used for the blue translucent parts
Step 27: 4 Sides Assembled. the Just Press Fit Together
Step 28: Add the Top Blue Lenses
Step 29: Not Only Will the Holocron Work With the Force.....
Step 30: ...it Also Works As an IoT Device for Those Not As Strong in the Force
Step 31: The Completed Holocron Lamp!
Step 32: The Holocron Enclosure
The Fusion360 model of the design can be found here
https://myhub.autodesk360.com/ue299db70/shares/public/SHabee1QT1a327cf2b7a8eeea6ffeb49753e
You can also just use the attached STL files for 3D printing
Attachments
Step 33: The Holocron Firmware for the Particle Core Board
/*
Holocron Particle Firmware V1.0 Dave Clarke 18/02/16IR Proximty circuit modified from instructables https://www.instructables.com/id/Simple-IR-proximity-sensor-with-Arduino All other rights reserved. */
int readIR(); // prototype void ServoControl(); // prototype void ServoControlReset(); // prototype
Servo myservo; // Create servo object
bool toggle = false; // Used as a one shot bool TheForce = false; // Variable to know cloud function used. bool powerON = true; // initial start up flag
int pos = 0; // initial servo position int IRemitter = D1; // IR Emiter LED on D1 int IRpin = A0; // IR Photodiode on pin A0 int ambientIR; // variable to store the IR coming from the ambient int obstacleIR; // variable to store the IR coming from the object int value[10]; // variable to store the IR values int distance = 0; // variable that will tell if there is an obstacle or not int mainLED = A6; // control for the main lights int closed = 20; // Servo closed angle int open = 155; // servo open angle
void setup() { // Initialise pin modes and assign servo pin myservo.attach(D0); pinMode(mainLED, OUTPUT); pinMode(IRemitter, OUTPUT);
// Debug - Variables published to Cloud Variables Particle.variable("distance", distance); Particle.variable("ambientIR", ambientIR); Particle.variable("obstacleIR", obstacleIR);
// Cloud function interface Particle.function("force", RemoteSwitch);
//initial states digitalWrite(mainLED, LOW); digitalWrite(IRemitter, LOW); myservo.write(closed);
}
void loop() { distance = readIR(10); // Read value from IR sensor and store in distance Variable if ((distance > 15 || TheForce == true) && toggle == false) // open up lamp and turn on the lights { for(pos = closed; pos <= open; pos++) // goes from 5 degrees to 115 degrees { // in steps of 1 degree ServoControl(pos); // Set Servo Position and Control LED Brightness } ServoControlReset(); // When finished, reset variables etc. } if ((distance > 15 || TheForce == true) && toggle == true) // turn off lamp and close { for(pos = open; pos > closed; pos--) // goes from 115 degrees to 5 degrees { ServoControl(pos); // Set Servo Position and Control LED Brightness } ServoControlReset(); // When finished, reset variables etc. } }
// Function to read IR Proximity sensor int readIR(int times) { for(int x = 0; x < times; x++) { digitalWrite(IRemitter,LOW); // turning the IR LEDs off to read the IR coming from the ambient delay(1); // minimum delay necessary to read values ambientIR = analogRead(IRpin); // storing IR coming from the ambient digitalWrite(IRemitter,HIGH); // turning the IR LEDs on to read the IR coming from the obstacle delay(1); // minimum delay necessary to read values obstacleIR = analogRead(IRpin); // storing IR coming from the obstacle value[x] = ambientIR-obstacleIR; // calculating changes in IR values and storing it for future average } for(int y = 0; y < times; y++) { distance+=value[y]; // calculating the average based on the "accuracy" } if (powerON == true) { delay(1000); // prevent bogus readings from servo noise on power up powerON = false; } else { //no start up delay } return(distance/times); // return the final value }
// Function for Cloud Variable Remote Switch bool RemoteSwitch(String command) { if (command == "theforce") { return TheForce = true; } }
// Servo position control and LED brightness void ServoControl(int ServoPosition) { int LEDmap = ServoPosition; LEDmap = map(LEDmap, closed, open, 0, 255); // Map servo position to LED brightness myservo.write(ServoPosition); // tell servo to go to position in variable 'pos' delay(26); // waits 25ms for the servo to reach the position analogWrite(mainLED, LEDmap); //ramp light on using PWM Pin }
// After servo has reached final position, reset variables and wait. void ServoControlReset(void) { toggle = !toggle; // toggle switch state TheForce = false; // Toggle The Force when using could remote switch on distance = 0; // reest distance to stop accidental operation if (toggle == false) // Make sure LED is High for open and low for closed { digitalWrite(mainLED, LOW); } else { digitalWrite(mainLED, HIGH); } delay(1000); // prevent operation too quickly }