Ed Nisley's Blog: Shop notes, electronics, firmware, machinery, 3D printing, laser cuttery, and curiosities. Contents: 100% human thinking, 0% AI slop.
All the tests are at 500 mA, approximately half the camera’s load. Oddly, the numeric values along the mA·h axis work out pretty close to the actual runtime in hours:
Sony – 1:30
Wasabi D – 1:15
Wasabi B – 0:40
Given that a typical bike ride takes an hour, the two year old Wasabi B battery’s 40 minute runtime isn’t useful. The Wasabi D battery is a bit over a year old and looks very much like the B battery did last year.
The Wasabi batteries march through the camera and charger in order, so each one gets used about once a week. The Sony battery gets used once every half-dozen complete cycles, just so I have a standard “good” battery.
The Sony and Wasabi B cells over the course of two years:
Sony NP-BX1 – OEM Wasabi – 2015-10 2014-10 2014-01
Much to my surprise, the Wasabi batteries started out slightly better than the Sony OEM battery, at least as measured by the available voltage and energy. The camera runs from an internal switching power supply, so the area under the curve (basically equal to energy in W·h) above the cutoff voltage is all that matters.
In round numbers, I can expect 100 cycles out of each battery before the run time drops below the ride time; at $10/battery, that’s a dime a ride. Any claims that the batteries can be recharged “1000 times!” may be true, but they’ll have a useless fraction of their original capacity by then.
Back in the day, you could install a Genuine HP 09872-60066 Digitizing Sight in your Genuine HP 7475A plotter, maneuver the sight to an interesting point on the paper, press the Enter button, send the point’s coordinates through the serial port to the computer, then do whatever you like with the numbers.
Here in the future, I twiddled the demo code that draws Superformula patterns to send a digitization command and await the response at the end of each plot. I can then change the paper, press the Enter button, and get the next plot: exactly what I need for the upcoming Poughkeepsie Mini Maker Faire.
The only gotcha turns out to be that, having hacked the Chiplotle interface to use hardware handshaking, there’s no way to tell when the outgoing buffer has drained. Until that happens, the plotter can’t respond to the digitizing command and, eventually, Chiplotle kvetches about not hearing anything.
The least awful solution seems to be sleeping for 40 seconds (!) while the plotter trudges through the last line of the legend (!!), then continuing apace:
print "Waiting for plotter... ignore timeout errors!"
sleep(40)
while NoneType is type(plt.status):
sleep(5)
print "Load more paper, then ..."
print " ... Press ENTER on the plotter to continue"
plt.clear_digitizer()
plt.digitize_point()
plotstatus = plt.status
while (NoneType is type(plotstatus)) or (0 == int(plotstatus) & 0x04):
plotstatus = plt.status
print "Digitized: " + str(plt.digitized_point)
When the interface times out, Chiplotle doesn’t set the status code to anything in particular (which makes sense), so you can’t do anything useful with it. Therefore, the operand order in the last while statement matters: you can’t convert a value of type NoneType into anything else.
The other change wraps the entire plotting loop with an always-and-forever loop: hit Ctrl-C to break out at the end of the day.
You can’t change the new plot’s paper size, because the digitizing command preempts the Enter button that’s part of the Enter+Size combination. That makes perfect sense, even in retrospect.
Testing that gave me the opportunity to run all the pens, refilled and OEM, through their paces:
As part of a discussion on the M2 forums about using rice to dehumidify 3D printer filament, I replaced the 500 g bag of silica gel in the basement safe with a bowl containing 200 g of long-grain brown rice from our rice supply and let it sit for a while:
Basement Safe Humidity – Rice vs. Silica Gel – 2015-10-31
The abrupt drop in humidity from 52% to the logger’s minimum 15% marks the point where I replaced the rice with a fresh bag of silica gel, with a door opening shortly thereafter. The basement air outside the safe varied between 52% and 54% during that time, so the air inside the safe trended upward toward that goal.
The rice still weighed exactly 200 g after its stay in the safe, so we can conclude it hadn’t absorbed or released any water.
Conclusion: nope, rice doesn’t work as a dehumidifier…
A defunct desk lamp emerged from the clutter and cried out for bright, new LEDs. This adapter puts a small LED ring and nine white LEDs on the original lamp head:
Ring Light Mount – in operation
Peering into the business end, before mounting it on the lamp, shows some abrasive adjustment on the inside layer:
Ring Light Mount – LEDs installed
That layer printed over a quick-and-easy support spider:
Ring Light Mount – solid model – bottom
The Slic3r preview looking down through the layer just over the support shows that the perimeter of those LED holes doesn’t have much support:
Ring Light Mount – Slic3r preview – bridge layer
The obvious threads drooped in the predictable way, so I just clipped them off, sanded the high spots into submission, and epoxied everything in place:
Ring Light Mount – LED wiring
That nice Hilbert Curve infill is completely wasted inside the OEM shade, but the smooth curve around the rim had to be on the top surface.
Rather than beefing up the support, you should print the bottom ring (or the top rim) separately, then glue it back on, but I wanted to see how well simple support worked with PETG.
It came out reasonably well:
Ring Light Mount – support spider
That’s far more hair than usual, even for PETG, because I made the spider’s legs exactly three thread widths wide. Slic3r reduced the single infill thread to, literally, a hair that didn’t stick to the platform; the model now has four-thread-wide legs.
Slic3r’s automatic support would do a better job of holding up the underside, albeit with more plastic and printing time:
Ring Light Mount – Slic3r preview – auto support
The top view looks about like you’d expect:
Ring Light Mount – solid model – top
Those two solid models show the small hole for the LED ring wiring, which I drilled into the as-printed plastic. The original layout included just the LED ring, with the wire through a big central hole, but then I realized the wall wart had enough moxie for a few more LEDs. So it goes.
Anyhow, the lamp provides just enough illumination below my big monitors to suffice. The gooseneck might not be quite long enough, but that’ll be another project…
The OpenSCAD source code:
// LED Ring Light Mount
// Ed Nisley KE4ZNU October 2015
DoSupport = true;
//- Extrusion parameters must match reality!
ThreadThick = 0.25;
ThreadWidth = 0.40;
HoleWindage = 0.2;
Protrusion = 0.1; // make holes end cleanly
inch = 25.4;
function IntegerMultiple(Size,Unit) = Unit * ceil(Size / Unit);
//----------------------
// Dimensions
NumSides = 8*4; // number of sides on each "cylinder"
LENGTH = 0;
ID = 1;
OD = 2;
Shade = [6.0,45.2,47.5]; // threaded end of OEM lamp shade
RingLED = [4.5,36.0,51.0];
SpotLED = [2.0,0,5.0]; // discrete LEDs in center
NumSpots = 8; // discrete LEDs around the one in the middle
Support = [(RingLED[LENGTH] - 1*ThreadThick),0,(RingLED[OD] - 4*ThreadWidth)];
NumSupports = NumSides/2;
ThreadBase = RingLED[LENGTH] + SpotLED[LENGTH];
OAHeight = ThreadBase + Shade[LENGTH];
//----------------------
// Useful routines
module PolyCyl(Dia,Height,ForceSides=0) { // based on nophead's polyholes
Sides = (ForceSides != 0) ? ForceSides : (ceil(Dia) + 2);
FixDia = Dia / cos(180/Sides);
cylinder(r=(FixDia + HoleWindage)/2,
h=Height,
$fn=Sides);
}
//----------------------
// Build it
difference() {
union() { // overall shape
translate([0,0,ThreadBase])
rotate_extrude(convexity = 2, $fn=NumSides)
translate([Shade[OD]/2,0])
circle(r=Shade[LENGTH],$fn=NumSides);
cylinder(d=(Shade[OD] + 2*Shade[LENGTH]),h=ThreadBase,$fn=NumSides);
translate([0,0,ThreadBase])
cylinder(d=Shade[OD],h=Shade[LENGTH],$fn=NumSides);
}
translate([0,0,ThreadBase - Protrusion])
cylinder(d=(Shade[ID] + HoleWindage),h=(Shade[LENGTH] + 2*Protrusion),$fn=NumSides); // opening for shade thread
translate([0,0,-Protrusion])
cylinder(d=(RingLED[OD] + HoleWindage),h=(RingLED[LENGTH] + Protrusion),$fn=NumSides); // opening for LED ring
rotate(180/NumSides) // LED ring power wire
translate([RingLED[ID]/2,0,0])
rotate(180/6)
PolyCyl(2.5,OAHeight,6);
rotate(180/8 - 180/NumSides)
PolyCyl(SpotLED[OD],OAHeight,8); // central LED SpotLED
for (i=[0:NumSpots-1]) // surrounding spots
rotate(i*360/NumSpots - 180/NumSides)
translate([(RingLED[ID] - 2*SpotLED[OD])/2,0,0])
rotate(180/8)
PolyCyl(SpotLED[OD],OAHeight,8);
}
//-- Support structure
if (DoSupport)
color("Yellow")
rotate(180/NumSides) // align bars to flat internal faces
for (i=[0:NumSupports/2 - 1]) {
rotate(i * 360 / NumSupports)
translate([0,0,Support[LENGTH]/2])
cube([Support[OD],4*ThreadWidth,Support[LENGTH]],center=true);
}
Our Larval Engineer asked for help with an OpenSCAD model of a 3D printable claw that, she says, has nothing at all to do with the upcoming Night of Little Horrors. Not having had an excuse to fiddle with the new (and lightly documented) sweep() functions, I gnawed on the sweep-drop.scad example until this popped out:
Swept Claw – solid model
That might be too aggressively sloped up near the top, but it’s a start.
The OpenSCAD source code:
use <sweep.scad>
use <scad-utils/transformations.scad>
function shape() = [[0,-25],[0,25],[100,0]];
function path(t) = [100*(1+sin(-90-t*90)), 0, (100 * t)];
step = 0.01;
path_transforms = [for (t=[0:step:1-step])
translation(path(t)) *
scaling([0.5*(1-t) + 0.1,0.75*(1-t) + 0.1,1])];
sweep(shape(), path_transforms);
It’s perfectly manifold and slices just as you’d expect; you could affix it to a mounting bracket easily enough.
Some notes on what’s going on…
The t index determines all the other values as a function of the layer from the base at t=0 to the top at t=0.99.
The shape() defines the overall triangular blade cross-section at the base; change the points / size to make it look like you want.
The path() defines the XYZ translation of each slab that’s extruded from the shape() cross-section. I think the Z value sets the offset & thickness of each slab. The constant 100 in the X value interacts with the overall size of the shape(). The 90 values inside the sin() function set the phase & scale t so the claw bends the right way; that took some fiddling.
The parameters in scaling() determine how the shape() shrinks along the path() as a function of the t parameter. The 0.1 Finagle Constants prevent the claw from tapering to a non-printable point at the tip. I think the Z value must be 1.000 to avoid weird non-manifold issues: the slabs must remain whatever thickness the sweep functions set them to be.
It compiles & renders almost instantly: much faster than I expected from the demos.
The folks who can (and do!) figure that kind of model (and the libraries behind it) from first principles have my undying admiration!
The south- and snowplow-facing numbers on the mailbox weren’t up to the challenge:
Mailbox – faded numbers
I wiped the crud off the reflective labels with denatured alcohol before painting, but that was the extent of the surface preparation.
I’m not getting graded on my ability to paint within the lines using a foam brush and that’s a Good Thing:
Mailbox – repainted numbers
That’s Rustoleum Rusty Metal Primer, chosen entirely because it was oil-based, outdoor-rated, and near the front of the shelf. I’m not going to topcoat it; that stuff is on its own. The slight color variations show still-wet primer here & there.
The north-facing numbers were in better shape, so a few dabs covered the obvious problems.
Hey, I wiped that peeling paint off the top of the box, too…