Gas station without pumps

2019 September 14

About halfway through my 6-month break

Filed under: Uncategorized — gasstationwithoutpumps @ 22:52
Tags: ,

In Grading done!, I posted a to-do list for the six months I have off until I start teaching again in January.  I’m now three months into that period, so I thought I would revisit the list:

  • Review senior portfolios for about 50 graduating seniors. DONE
  • Rewrite the Applied Analog Electronics textbook.  I have about 161 to-do notes left in the book from teaching the last two quarters—some from student comments, some from observations made while grading. I’m down to 70 to-do notes, so I’m a little ahead of schedule.  If I can maintain an average of one note removed per day, I’ll be done by Nov 24.  I’ve been wondering whether I should release an interim version of the book, with the additions and corrections so far, for anyone who need the book for fall quarter or fall semester.  I’ve not had enough sales to indicate that any class but mine has ever adopted the book, but if even one or two readers would benefit from a September edition before the December one, I could do another release.
  • Read the Student Evaluation of Teaching forms for both quarters and think about how to improve the class based on them.  This will probably require a beer or two, as I know that some of the students really hated the class (based on anonymous comments on Piazza).  I’ll wait on that until my stress level has gone down a bit, or I won’t be receptive to even the good ideas. I still haven’t done this—I should do it soon, as it could affect some of the book rewrites.
  • Design a senior project involving testing hearing aids—perhaps contacting faculty at the hearing-aid research center at DTU.  Maybe visit DTU in Copenhagen? I’ve not done anything about this, and it is looking unlikely.
  • Visit my dad in Boulder. DONE  (I’ll probably want to visit him again, but I’m not sure when.)
  • Get a new range hood installed (I promised this to my wife last summer). No progress.  I have a range hood selected, but installing it will require professional help, so I haven’t ordered it yet.
  • Get a new refrigerator (the old one is rusty and the interior light doesn’t work) No progress. I found a couple of refrigerators that would fit the space, but haven’t ordered anything.
  • Get a new desktop computer and monitor—perhaps a Mac mini? No progress. I’ve been using the “MacBook Air (11-inch, Early 2014)” machine that I use for lecturing from, even though one of the touchpad switches is broken.
  • Remove the ivy and blackberry vines in the backyard (that is a never-ending project, as the vines have covered about 50′ by 20′ to almost head height) I cleared a small area, and I’ve been keeping it clear, but it is only a tiny piece of the area that needs clearing.
  • Clean solar panels Not done yet, but something I could tackle tomorrow.  It has been really hot lately, so getting wet from using the hose and a squeegee on a 20′ pole does not sound bad.
  • Fix my desk lamp (the one I made)—the copper tubing has suffered from metal fatigue, partly as a result of the cat playing with it and bending it over.  I’m trying to decide between remaking the copper supports (out of copper tubing again) or soldering on copper pieces to splint the fatigued part. No progress.
  • Mow the front lawn (easy! I can do it in an hour or two next weekend) I’ve mowed the front lawn a few times this summer.  It doesn’t look great (the “grass” consists of many different species of weeds), but it is not as bad as in June.
  • Mow the back lawn (probably impossible) Still seems impossible, but I should at least blaze a path back to the compost heap.
  • Sort all my old screws, bolts, and nuts by size and put them in accessible storage boxes. No progress.
  • Clear the breakfast-room floor of electronics, magazines, catalogs, … that have accumulated while I was grading. I’ve done this a couple of times this summer.  Stuff keeps re-accumulating, though. I’ll probably do it once more before my trip to the Oregon Shakespeare Festival, so my wife can have a clean breakfast room while I’m away.  (She has work and can’t go up to Ashland, so I’m going with my son.)
  • Clear the bedroom floor of hardware, books, magazines, and stuff that has accumulated over the last decade.  But where will I put it all? No progress
  • Replace the soap dishes in the bathroom (I like the design of one that has cracked, but I can’t find another like it). No progress.
  • Hire someone to haul the truck load of debris on my driveway to the dump. I’ve added more to the pile, but not hired anyone yet.  This is way overdue.
  • Get an architect to design wheelchair access to my house (I don’t need it, and hope I never will, but I’d rather it were in place before I need it). No progress.
  • Get a new gate designed, built, and installed on the driveway.  The old one rotted away, so I’m thinking of going with concrete pillars and a steel gate this time, instead of redwood. No progress.
  • Clean solar panels. Why was this on the list twice?  I’ll be lucky to get it done once!
  • Clear leaves, twigs, and dirt out of gutters. No progress.
  • Install path lights, if I can find any that look decent. I bought some cheap solar path lights from American Science and Surplus, but they were a waste of money (even if not much money). My wife decided that they looked awful and they only stay lit for about an hour after sunset, so they are neither decorative nor functional.
  • Get my annual eye exam (6 months overdue). DONE
  • Get a physical therapist or sports-medicine specialist to advise me how to run without exacerbating my hip osteoarthritis. I had one appointment with a physical therapist, but I did not find his advice very useful. He basically suggested not running, gave me some stretching exercises, and chatted with his assistants—not a particularly valuable half-hour session for over $500. I have started working with a personal trainer at UCSC, for $24–30 an hour ($24 is the price for the 3-session intro package with a student trainer, $30 is the price for single sessions, with discounts down to $27 if you buy 10 sessions).  I’m doing the personal training once a week, with two other workout sessions a week on my own.
  • Join a gym and learn to use fitness equipment (for example, I’d like to learn to run on a tilted treadmill, so that I can do a stress echocardiogram test without fearing for my balance). I’ve got a membership at the UCSC gym, for $$22.84/month (going up in October).  I can’t use payroll deduction, because I don’t get a paycheck while on unpaid leave of absence. The gym has not been too busy during the summer, but if it gets super busy when the students come back, then I might discontinue the membership.

    I have been doing mainly upper-body exercises at the gym, but I’ve also been practicing running on the treadmill.  I just noticed today, though, that I’ve been training at the wrong pace.  What I’ve been doing is upping either the incline or the pace every 30 seconds until I can’t take the pace any more, but I’ve been keeping the numeric values of the %incline and mph roughly the same—starting at 5mph at 5% slope and gradually increasing to around 7.5 mph at 7% or 7.5% slope.  But the stress test I took in December had me stopping at 4.3mph and 10% slope.  So I should probably be working at a slower pace and greater slope (maybe aiming for 5mph and 15% slope).

    The Bruce protocol calls for 3.4mph and 14% slope in stage 3, but that would not get me to my maximum heart rate.  I think I can manage stage 5 of the Bruce protocol (5mph at 18% slope, 14 METs) for a short while, because I can sometimes sustain 14 METs for 30 seconds (7.5mph at 7% slope), but I’ve not tested myself at a slower pace and higher slope.  One problem I have is that the protocol (both the Bruce protocol and the modified one my cardiologist used) calls for a long time at an awkward pace that is between a brisk walking pace (4mph) and a slow jog (6mph).

    I’ll probably switch my treadmill training to staying at 5mph and just increasing the incline by 1% every 30 seconds.  That will help me feel balanced on the treadmill, even at the awkward pace, which was the main limiting factor for me last December.  I do know that the test was stopped well below my maximum heart rate, as I’ve been routinely seeing heart rate over 170bpm on the treadmill, and the cardiologist had me stop at 163bpm last December.

  • Repaint the garage door (scrape, sand, prime, paint) No progress.
  • Paint the book room door. No progress.
  • Fix or replace garage-door opener. No progress.
  • Spot sand and apply Danish oil to wood floor where old finish has worn away. No progress.
  • Do some robotics—perhaps continuing work on the bot I started for the mechatronics class, perhaps a balance bot, perhaps making a board for precisely positioning the gear motors that I have, perhaps a drawbot, perhaps a true digital clock with mechanical digits. No progress.
  • Find something useful to make with my 3D printer. I don’t know whether I’ve found anything useful, but I have done some fun 3D printing this summer.
  • Do some weaving—I’ve not woven in over a decade, but I still have a lot of yarn and looms taking up a big chunk of the house. No progress.
  • Figure out what charities (or political organizations) to give more money to. My wife and I sat down and made a list of charities to give to this year, and came up with amounts to give.  I’ve only written a couple of the checks so far, but I’ll do more in the next couple of months.  I’ll probably want to take some money out of my 
  • Look for something interesting to do with other people once I retire (most of my hobbies are solitary). No progress.
  • Brew a batch of mead (I’ve not made any since the Loma Prieta earthquake in 1989). No progress.
  • Improve documentation for PteroDAQ. No progress.  More important is to move PteroDAQ out of the Mercurial repository on BitBucket, since Atlassian is trying to get rid of all their Mercurial customers.
  • Port PteroDAQ to new processors? No progress.
  • Temperature-compensated VCO. No progress.
  • VCO using one op amp and one FET (is it even possible?) No progress.
  • Torque-measuring rig for small gear motors.  Both stall torque and torque vs. speed. No progress.

So, as expected, most of the possible summer projects have shown no progress.

Make magazine is back

Filed under: Uncategorized — gasstationwithoutpumps @ 21:43
Tags: ,

In Make magazine has folded, I passed on the news that “Maker Media halted operations and laid off all staff. That means no more Make magazine and no more Bay Area Maker Faire.”  I was particularly bummed, because I had just renewed my subscription!

Yesterday, I got email saying

The Next Issue of Make: Magazine Is Officially Off to the Printer!

Thank You sincerely for being a dedicated subscriber to Make: magazine! As Executive Editor, I’m thrilled to let you know the next issue is headed soon to your mailbox! When you receive it, you’ll find some exciting new elements.

In June 2009, Maker Media went out of business. Make: Community, a new organization formed by Dale Dougherty acquired the assets of Maker Media, including Make: magazineMake: Community is an association of makers whose mission is to serve and grow the global maker community. Through the support of its members, Make: Community will resume publication of Make: magazine.
Please join us at make.co.

So it looks like my subscription will continue.  I wonder how long make.co will last.

2019 September 5

Move to Github half done

Filed under: Uncategorized — gasstationwithoutpumps @ 11:36
Tags: , , , ,

As I mentioned in BitBucket being killed by Atlassian, I am moving all my BitBucket Mercurial repositories to GitHub as Git repositories.  So far, I’ve moved my two private repositories (my textbook and a beacon-dectector project), because they had no wiki or issues associated with the repository.  Moving them to GitHub was very easy, as GitHub has an importer that does almost all the work of importing the repository itself from BitBucket.  Unfortunately, their importer supposedly does not handle importing the issue history nor the wiki, which is a shame.

That leaves me with the harder task of importing the  PteroDAQ project, which I’ll have to do in the next month, because there are pointers to it in my book, and these pointers will need to be updated for the end-of-December release.  There are some scripts on the web for doing the issue and wiki transfers, but they are not part of the standard GitHub suite of tools, and may be a bit iffy.  I’ll wait a little while to see whether there is a consensus on the best way to do the transfer (or whether GitHub provides a more powerful import tool).

I have not learned the git command-line tools yet, as I’ve been using GitHub Desktop to manage my new repositories.  Given that they have only the single main branch, no issue tracking, and nothing else fancy, I think that this GUI may be all I need.  I did have to create a .gitignore file that was a little more comprehensive than my .hgignore file was, to make sure that git did not pick up a bunch of intermediate files that shouldn’t be part of the repository.

 

2019 September 1

Cat drinking fountain completed

Filed under: Uncategorized — gasstationwithoutpumps @ 13:38
Tags: , , ,

In Beginning design of a cat drinking fountain I wrote

One of our cats likes to drinking from running water (a bathroom sink on a trickle setting), so my wife challenged me to make a drinking fountain for the cat that recirculates water in a water dish.  This project will be mainly physical design (3D printing, gluing things together) with a little electronics to control the pump.

I finished the cat fountain this week—the amazing thing is that I only had to print each part once, with the first design working!  (Well, that’s almost true—I printed a bunch of 2mm-thick test pieces for the hose clip, to try to get something that would hold firmly to the rim of the bowl, and I aborted one print of the hose clip after a couple of layers, when I realized that one part had not been made level on the bed before slicing.)  All the big pieces went together on the first try, and the first fully printed hose clip worked.

Unfortunately, the cats have not show any interest in the fountain yet.

Here is a top view of the fountain running. The rocks serve two purposes—to make the fountain quiet (avoiding the trickling noise of faucet left running) and providing some weight to keep the bowl from tipping. I don’t know whether the weight is enough if a cat rests both front paws on the rim—that has not been tested yet.

Here is a side view of the fountain, showing the base with the control knob for adjusting the flow rate.

Here is a side view of the fountain, showing the hose clip, which is glued together from two pieces, to avoid having to print any overhangs. The rounded-triangle bolt holes are visible on the side of the base.

Here is a bottom view of the fountain, showing the barrel jack for power, the support for the pump, and the hose from the pump.

Here is a top view of the base, showing how it is divided into 4 parts so that each part is small enough to be printed in the 110mm-diameter print area of the Monoprice Delta Mini. The parts are bolted together with M3-18mm bolts

I printed a nozzle for fountain also. I’ve been thinking of printing some other nozzle shapes, to see what produces the nicest stream. I was pleased by how well the nozzle fit into the ¼” ID hose—I had expected to end up with something either too large to fit or with barbs too small so that the nozzle fell out, but everything worked ok.  I would make the barbs slightly larger if I wanted something that would hold under pressure, though.

I’ve started using rounded-triangle holes for horizontal bolt holes.  The edges of the holes are three circular arcs, with the centers of the circles at the points of an equilateral triangle, and the radius being the side length of the triangle.  I make one of the vertices be in the positive z direction.  The arched shape is a little easier for the printer to print than the flat top of a circular hole, though for holes this small even circular holes print ok.

I designed in a little clearance between the parts, so that I would not need to sand things to make them fit.  The 0.15mm clearance I allowed seems to be about right—the pieces bolted together without problems and the fit seems to be pretty tight.

I drilled the melamine bowl with a 3/8″ Forstner bit, as that seemed to be exactly the right size for the 9.5mm inlet of the pump. Before drilling with the drill press, I covered both sides of the bowl where I was going to drill with transparent tape and taped a piece of MDF below the bowl to support the surface.  I got no cracking and the pump outlet fit tightly in the resulting hole.  I glued the pump to the bottom of the bowl with FlexEpox, which I also used to glue the two halves of the hose clamp together.

The controller is the design I used for the desk lamps—I happened to have one sitting around unused.  I didn’t even change the code, though I’ve been thinking about changing the range of the PWM, and possibly raising the PWM frequency. The pump sometimes makes a quiet, but slightly annoying noise at about 2.2kHz when set to low flow rates. The PWM frequency is nominally 2.344kHz at low output and 9.375kHz at high output (with a 9.6MHz clock), and the 2.2kHz sound is within the ±10% spec for the RC oscillator in the ATtiny13 chip.  I may not need as high a precision at low levels for the motor as I do for LEDs, so a simpler program that just uses a 256-step PWM at around 9kHz may be better.

A capacitor across the motor may also help to reduce the voltage fluctuation that causes the noise.  If the motor is drawing about 300mA and the power is off for about ¾ of the period (at 2.2kHz), then we’d need about 100µC from the capacitor.  If we want the voltage to drop 9V in that time, the average voltage is 4.5V and a 22µF capacitor would be about the right size.  Of course, I’d have to go to lower duty cycles, as the average voltage across the motor would be much higher than without the capacitor. Even very short duty cycles may not be low enough, as the capacitor charges very quickly and the slow discharge may leave the pump running at too high a speed—in that case I’d need to make the capacitor smaller.

(Update 2019 Sept 1: a 10µF ceramic capacitor does seem to quiet the 2.2kHz sound while still allowing the motor to be turned down to the point where it stalls. Of course, my tinnitus is loud enough that the fountain may still be making noise, but I just can’t hear it over the tinnitus.)

(Update 2019 Sept 9: the pump was still whining, even with the capacitor, so yesterday I did the right thing and reprogrammed the ATTiny13 in the controller to use a PWM of ~37.5kHz, instead of 2.2kHz.  The cats may still be able to hear it, as the cat range of hearing is about 48Hz–85kHz [https://doi.org/10.1016/0378-5955(85)90100-5], but I can’t hear it.)

The fountain takes about 2–3W (measured at the AC input to the power supply), so I’ve not looked into adding a power switch or a motion detector to turn the pump on and off.

As usual, I designed everything using OpenSCAD.

nozzle1.scad

// barbed nozzle(s) for pump
// Kevin Karplus
// 2019 August 12
//  Creative Commons Attribution-ShareAlike  (CC BY-SA 3.0)


module nozzle(ID=3, OD=6, final_OD=undef, length=undef, num_barbs=undef)
{
    $fa=5; $fs=0.1;
    barb_diam= 1.15*OD;
    barb_length= OD/3;
    thickness=(OD-ID)/2;

    assert(num_barbs!=undef || length!=undef);
    
    barb_count = num_barbs!=undef? num_barbs: max(1, min(4, length/barb_length -2));
    real_length = length!=undef? length: (barb_count+1)*barb_length;
    real_final_OD = final_OD==undef? OD: final_OD;
    
    
    flare_from = (barb_count+1)*barb_length;
    assert(flare_from < real_length || OD==real_final_OD);
    
    barbs = [for (i=[1:barb_count]) each [[barb_diam/2, i*barb_length], 
                                [OD/2, i*barb_length]] ];
    profile = concat( [[ID/2,0], [OD/2,0]], barbs,
        [   [OD/2, flare_from],
            [real_final_OD/2,real_length], 
            [real_final_OD/2-thickness,real_length],
            [ID/2,flare_from], 
            [ID/2,0]
        ]);
    echo(profile=profile);  
    rotate_extrude()
    {    polygon(profile);
    }

}

intersection()
{
    color("red")    nozzle(length=20, num_barbs=3, final_OD=10);
    color("blue",0.4) translate([0,-12,0]) rotate([30,0,0]) cube(36,center=true);
}

hose_clip_v6.scad

// cat dish hose clip
//
// Kevin Karplus 2019 Aug 25
//  Creative Commons Attribution-ShareAlike  (CC BY-SA 3.0)

//
// v1 uses linear_extrude for bowl rim, has wrong rim profile
// v2 uses rotate_extrude for bowl rim, rim profile angled wrong outside, too wide
// v3 has taller clip.  Rim profile is better, but still not right.
// v4 tweaked the rim profile, but still a little loose
// v5 tweaked the rim profile some more, but apparently in the wrong direction
// v6 seems to have an ok rim profile, though clipping it on the rim opens the 
//    fork a bit, so that the rim is only grasped near the top.

use <BOSL2/std.scad>
include <BOSL2/paths.scad>
include <BOSL2/rounding.scad>

pi=3.14159265358979;

$fa=0.3; $fs=0.1;

bowl_diam = 254;    // bowl diameter at rim


// rim profile
inside = [ [0,0], [-2,0], [-3,-0.3], [-4,-1], [-5.1,-2],  [-6.6,-4],
    [-7.2,-5], [-10,-10], [-16,-20], [-22,-30]];
L2 = reverse([for (pt=inside) pt+[0,3.4]]);
outside =  [ [0,0], [-1.9,-0.9], [-2.8,-1.4], [-4.7, -2.8], [-5.5,-3.5],[-6.5,-4.6],[-10,-9.9], [-13.6,-15], [-18.1,-21.6], [-22.3,-27.8], [-26,-33.6]
    ];

L4 = simplify2d_path(concat(outside,[outside[len(outside)-1]+[1,-3]], reverse(offset(outside,5)), 
        [[5,-5], [5,9]], 
        reverse(offset(L2,5)), [L2[0]+[-3,-1]], L2 , [[0,0]] ));


module rotate_extrude_at_origin(r=bowl_diam, arc_l=12)
// like linear_extrude but curving the extrusion by
// rotating about x=-r, to get an arc length of arc_l for point at origin
{
    angle = arc_l/r*180/pi;
    rotate([-90,0,0])
    translate([-r,0,0])rotate_extrude(angle=-angle) translate([r,0]) children();
}



module hose_clip(clip_thick=12)
{
    r= bowl_diam/2;
    angle = clip_thick/r *180/pi;
    difference()
    {    
       color("blue")rotate_extrude_at_origin(r=r, arc_l=clip_thick)
        {  polygon(L4);
            translate([0,-5])square([5,30]);
        }
        
        translate([-r,0,0]) rotate([0,-angle/2,0]) translate([r,0,0])
        {    translate([0,20,0]) rotate([0,90,0]) cylinder(d=9, h=11, center=true);
            translate([0,25,0]) cube([11,10,7.5], center=true);
        }
    }
}

module split(r=bowl_diam/2, arc_l=clip_thick, move_to=[15,0])
// split the children at the a plane through x=-r, with angle top_angle/2
//  to the xy plane, rotating so that top_angle is on xy plane, and
//  moving it over to move_to
{   
    // below cut plane
    intersection()
    {    children(); 
         rotate_extrude_at_origin(r=r, arc_l=arc_l/2)
          { translate([-r+0.001,-2*r]) square( [4*r,4*r]);
          }
    }
    
    // above cut plane
    top_angle = arc_l/r *180/pi;
    translate(point3d(move_to)) 
        rotate([0,180,0])  // rotate so top surface is now on bottom
        translate([0,0,-r*sin(top_angle/2)])  // top is xy plane
        rotate([0,top_angle/2,0])  // top is horizontal
    intersection()
    {   color("red") translate([-r,0,0]) rotate([0,top_angle/2,0]) translate([r,0,0])
                children(); 
        rotate_extrude_at_origin(r=r, arc_l=arc_l/2)
        { translate([-r+0.001,-2*r]) square( [4*r,4*r]);
        }
    }
}

// test rim shape
// hose_clip(2);

clip_thick=16;
split(arc_l=clip_thick) hose_clip(clip_thick);

cat_dish_base_v1.scad

// Base for running-water cat bowl
//
// Kevin Karplus 2019 Aug 24
//  Creative Commons Attribution-ShareAlike  (CC BY-SA 3.0)



// First some measurements and model for the pump
    pump_d=26;
    pump_h=25.7;
    outlet_d=6;
    wire_h = 15;

module pump()
{   $fa=4; $fs=0.1;
    cylinder(d=pump_d, h=pump_h-4);
    cylinder(d=21, h=pump_h);
    cylinder(d=9.5, h=35.7);
    translate([0,-3.7-6.88/2,pump_h-outlet_d/2])
       rotate([0,90,0]) 
         cylinder(d=outlet_d, h=10+pump_d/2);
    rotate([0,0,135+8.5])  translate([10,0,-wire_h]) 
       cylinder(d=1,h=wire_h);
    rotate([0,0,135-8.5])  translate([10,0,-wire_h]) 
       cylinder(d=1,h=wire_h);
}

// how much space should be left between matching surfaces?
clearance = 0.15;



module nth_circle(diam=127, thickness=18, arc=120)
// draw a part of a circular arc (no more than 180 degrees)
// with outer diameter diam and inner diam diam-2*thickness
{   $fa=1;
    intersection()
    {
        difference()
        {     circle(d=diam);
              circle(d=diam-2*thickness);
        }
        scale=diam*2;
        polygon(scale*[[0,0], [1,0], 
                [cos(arc/2), sin(arc/2)],
                [cos(arc), sin(arc)]
                ]);
    }
}


module overhanging_circle(arc=120, diam=127, outer=10, inner=8, overlap_degrees=20)
// Two circular arcs offset from one another, with thickness "outer"
// for the outer arc and "inner" for the inner arc.
// The outer arc starts on the x-axis, the inner one at "overlap_degrees".
//  
{
    color("red")
        nth_circle(arc=arc, diam=diam, thickness=outer-clearance/2);
    mid_diam = diam-2*outer-clearance;
    color("green")rotate([0,0,overlap_degrees]) 
        nth_circle(arc=arc, mid_diam, thickness=inner);
    color("purple")rotate([0,0,overlap_degrees]) 
        nth_circle(arc=arc-overlap_degrees, diam, thickness=inner+outer);
    echo ("max_dist = ", 0.5*norm([diam,0] - diam*[cos(arc),sin(arc)]),
          "or",  0.5*norm([diam,0] - mid_diam*[cos(arc+overlap_degrees),sin(arc+overlap_degrees)]) );
}


module rounded_triangle(side=1)
// intersection of three circles, centers at corners of equilateral triangle.
// On corner is on x axis.
{    intersection()
    {   translate([side/sqrt(3),0]) circle(r=side,$fn=60);
        translate([-side/(2*sqrt(3)), side/2])  circle(r=side, $fn=60);
        translate([-side/(2*sqrt(3)), -side/2])  circle(r=side, $fn=60);
   }
}

module rounded_beam(side=1, length=3, center=false)
// rounded_triangle beam from (0,0,0) to (0,0,length). 
// (0,0,-length/2) to (0,0,length/2) if center is set.
// Corners of beam as for rounded_triangle.
{    linear_extrude(height=length, center=center) rounded_triangle(side=side);
}

module screw_hole(side=3.5, cap_side=6, cap_depth=4, length=18)
// rounded_triangle screw hole, for horizontal screw holes
// Top of screw_hole at x=0, screw extends length+cap_depth along -x axis.
// Hole is oriented so that point of arch in +z direction.
// Default sizes are appropriate for M3 screws.
{
    rotate([0,-90,0])  // put beam along negative x-axis
    {
        rounded_beam(side=cap_side, length=cap_depth);
        rounded_beam(side=side, length=length+cap_depth);
    }
}

module drilled_overhang(arc=90, diam=127, outer=10, inner=8, overlap_degrees=10,
    height = 40,
    hole_d=3.5, cap_diam=6, cap_depth=4)
// make a part of the circular wall, with screw holes to line up sections
{    assert (outer> cap_depth+3, "Outer wall thick enough for screw hole");
    clearance_angle = atan(2*clearance/diam);
    difference()
    {    linear_extrude(height)
            overhanging_circle(arc=arc-clearance_angle, diam=diam, 
                outer=outer, inner=inner, 
                overlap_degrees=overlap_degrees);
        
        for (angle= [overlap_degrees/2, arc+overlap_degrees/2])
            for (z= [height/3, 2*height/3])
            {   
                translate([0,0,z])      // move beam up
                rotate([0,0,angle]) // put beam in correct orientation
                translate([diam/2+0.001,0,0]) // move out to circle
                screw_hole(side=hole_d, 
                    cap_side=cap_diam, cap_depth=cap_depth, 
                    length=outer+inner+0.1);
            }
    }
}

module controller_board()
// cut this module out of a drilled overhang to make room for the
//	controller board
{   
    $fa=2; $fs=0.1;
    hole_centers=60;
    width=36;
    mid_length=34;
    length= mid_length+ width;
    height=15;
    translate([0,0,-height])
    linear_extrude(2*height) polygon([ [length/2,0],  //point
        [mid_length/2,width/2], [-mid_length/2,width/2], // mid-length side
        [-length/2, width/4], [-length/2,0],  [-length/2, -width/4],// spread point (for wires)
        [-mid_length/2,-width/2], [mid_length/2,-width/2]
        ]);
    cylinder(d=8, h=32);
   
    translate([hole_centers/2,0,22])
        rotate([90,-90,0]) 
           screw_hole(side=3.5, cap_side=6, cap_depth=4, length=18);
    translate([-hole_centers/2,0,22])
        rotate([90,-90,0]) 
           screw_hole(side=3.5, cap_side=6, cap_depth=4, length=18);
}


module controller_panel(arc=110)
// minor bug:  the top edge has a cantilevered part that barely works---
//	the first layer of the cantilevered part does not bond to the
//	subsequent layers.
//      Possible fixes include removing the cantilevered part (cutting
//	the top back to just the front face, as was done on the power panel)
//	or tapering the cantilever so that it has a 45-degree slope to it.
{
    difference()
    {   overhang=10;
        drilled_overhang(arc=arc,overlap_degrees=overhang);
    
        rotate([0,0,overhang/2+arc/2-90])
        {
           translate([0,35,20])
            rotate([-90,0,0])  // make up be +y direction
               controller_board();
            translate([0,35+35+22,20]) cube(70,center=true);
        }
    }
}

module notch_panel(arc=80,height=40, diam=127)
// minor bug: the notch could be just a little tighter to
//  grasp the 1/4" ID vinyl tubing, rather than having it resting loose in
//  the notch.
{   
    hose_d=10;
    difference()
    {   drilled_overhang(diam=diam,arc=arc,overlap_degrees=10);
        
       translate([0,0,height-hose_d]) 
        rotate(arc/2)
        {   translate([0,-hose_d/2,0]) cube([diam+1,hose_d,hose_d+1]);
            rotate([0,90,0]) cylinder(d=hose_d,h=diam+1, $fs=0.1);
        }        
    }
    
}

module pump_panel(arc=90,height=40, diam=127)
// Bug:  There is nothing in this version to keep the pump from sliding off 
// the platform if the base rotates—a rim is needed around the pump.
// Minor bug: the platform is a little too high, as there was not enough
// clearance for the wall of the hose between the outlet of the pump and the 
// bottom of the bowl.
{
    offset=diam/2-33;

    platform_h = height-pump_h;
    scaled_offset = offset/ (pump_d/2);
    alpha=acos(1/scaled_offset);
    tangent1 = [cos(180+alpha),sin(180+alpha)];
    tangent2 = [cos(180-alpha),sin(180-alpha)];
     union()
    {
         color("blue")  drilled_overhang(arc=arc,overlap_degrees=10, height=height);
        rotate(arc/2) 
          translate([offset,0])
        difference()
        {   pump_angle=135;  // rotation to align outlet with notch
            union()
            {   cylinder(h=platform_h, d=pump_d, $fs=0.1, $fa=1);
                color("cyan") linear_extrude(platform_h) polygon(
                    [[0,0], 
                     10*[cos(135+pump_angle), sin(135+pump_angle)],
                     // tangent1*pump_d/2,
                     tangent1*pump_d+[offset,0],
                     [pump_d,0], 
                     tangent2*pump_d+[offset,0],
                     tangent2*pump_d/2
                     ]);

            } 
            // notch for pump wires
            rotate([0,0,135+pump_angle]) translate([10+1.8,0,0])
                cylinder(d=7.2,h=3*platform_h, center=true, $fa=1, $fs=0.1);
            
            // ghost of pump to check alignment---not part of model
            % translate([0,0,platform_h]) rotate([0,0,pump_angle]) pump();
        }  
    }
}


module power_panel(arc=80,diam=127,height=40)
// minor bug:  the hole for the socket for barrel adapter is 
//      slightly too small.
//      The socket can be screwed into the hole, but not slid in.  
//      Slight sanding with a riffler was enough to fix the problem.
{
    outer_face = diam/2-1;
    wall_t = 5;
    cut_w = 16;
    difference()
    {   overhang=10;
        drilled_overhang(diam=diam,arc=arc,overlap_degrees=overhang);
        
        rotate(arc/2+overhang/2)
        {  translate([0,0,height/2]) 
              rotate([0,90,0])  // drop into +x direction
                  cylinder(d=7.7, h=diam/2+1, $fs=0.1);
            translate([outer_face,-35,0]) cube(70);  // outer face
            translate([outer_face-wall_t-cut_w, -cut_w/2, 0]) // inner face
                cube([cut_w,cut_w,height+0.001]);
        }
    }
}

// comment out all but one panel for making STL files
 pump_panel();
 color("red") rotate([0,0,90])notch_panel();
 color("green") rotate([0,0,170]) controller_panel();
 color("purple") rotate([0,0,280]) power_panel();

2019 August 31

Shakespeare cookies v7

Today (2019 August 31), my son and I baked shortbread cookies using version 7 of the Shakespeare cookie cutter, which is a two-part design with a separate cutter and stamp:

Version 7 of the Shakespeare cookie cutter uses a simple outline for the cutter and a separate stamp for adding the facial features. Version 6 of the stamp failed, because I made the alignment markers too thin and they did not survive even gentle handling.

In addition to the new cutter and stamp, we also tried out the “cookie sticks” that I made for rolling the dough to a consistent 6mm thickness:

I made two different sticks: a straight one and one with a 90° corner. The OpenSCAD file also allows other angles, so I could have made 120° corners for a hexagon.  I made the sticks about as big as I could print on the Monoprice Delta Mini.

The hooks at the two end of the stick lock the sticks together.

I made enough of the sticks to make a rectangular frame almost as big as my cookie sheets. I ran out of the ugly green PLA filament after only 3 sticks, so I did the rest in the Hatchbox gold PLA filament.

I made the same shortbread dough as last time: 1 cup butter, 2 cups pastry flour, and ½ cup powdered sugar. I cleared a counter to make some workspace:

I had a cookie sheet,a rolling pin (a piece of birch dowel that I sanded and coated with mineral oil decades ago), a silicone baking mat, the cookie sticks, the cookie cutter and stamp, and a shallow bowl for flour.

The entire batch fills about 2/3 of the frame when rolled out:

For the first batch, we tried rolling the dough directly on the silicone baking mat, and removing the excess dough without moving the cookies.

The cookie sticks worked well for getting a uniform, consistent thickness to the dough, and 6mm is about the right thickness for these cookies. Having a complete frame around the dough meant that I did not have to worry about the cookie sticks shifting position, nor what the orientation of the rolling pin was.

The stamping is easily done on the cookies, but removing the excess dough from between the cookies was harder than we expected. It probably didn’t help that it was a warm afternoon and the dough got sticky quickly, even though we refrigerated it before rolling.

For the second rolling, we rolled the dough onto waxed paper, then transferred the cut-out cookies to a baking sheet lined with a silicone mat, doing the stamping only after the cookies were on the baking sheet.

We ended up with 19 cookies from the batch, and they came out pretty good:

This picture is a bit misleading as these were probably the best two of the nineteen.

The biggest problem was with dough getting stuck in the nose when stamping—it might be easier to do Tycho Brahe cookie cutters!

The second biggest problem was getting accurate alignment of the stamp with the cutter. For several of the cutters we were a millimeter off, resulting in an extraneous line at one of the alignment markers.

Despite these minor problems, the v7 cutters were much easier to use than previous versions, and I don’t have any immediate ideas for improvements (other than changing from a 3D-printed cutter to a injection-molded cutter, which would require a lot of changes and cost a few thousand dollars—something I’m not prepared for.

« Previous PageNext Page »

%d bloggers like this: