Freesteel Blog » Getting life out of makerbot cupcake

Getting life out of makerbot cupcake

Tuesday, December 20th, 2011 at 12:31 pm Written by:

Over in DOeS Liverpool, where I have been banished, there is this cobbled together Makerbot Industries Cupcake CNC.

The only software that runs it is ReplicatorG, a big Java GUI system behemoth (rather like Tunnel), which is great if all you want to do is go from STL files to 3D volume-filled plastic builds.

If you want to do something interesting, like make shapes without the use of a crappy STL file or adjust the geometry in response to build feedback mechanisms (the way CADCAM has got to go, but can’t so long as machine tools continue to operate as non-interactive batch processors), then you need to get behind this prescriptive interface.

This we have done, after an enormous amount of dead time. The secret was getting the baud-rate right. (There is this USB to serial port wire too.)

The code in ReplicatorG is very difficult to scavenge, containing as it does 3 copies of Skeinforge, like so much junk DNA. It’s made to work, not for repurposing.

The way through was the document of the protocol here and the source code for the firmware here.

I finally was able to write a program to operate the way I want — without a batch process. [the single file code for everything below is here]:

def gospiral():
    go(0, 0, 0)
    for th in range(0, 500, 2):
        rth = math.radians(th*1.8)
        c, s = math.cos(rth), math.sin(rth)
        res = go(th*c, th*s, 0)
    go(0, 0, 0)

The go() function transmits the position vector to the machine and pauses if the buffer is getting full. (Buffer is 512 on this device.) It took ages for us to identify the code using the ReplicatorG debug mode and the documents — as though it wasn’t the most important function in the whole darn set-up.

 
def go(x, y, z, cycletime=5000):
    while getbuffsize() < 300:
        time.sleep(0.5)
    return runcommand("x81"+struct.pack("<iiii", x, y, z, cycletime))

To communicate with the device you need to install pyserial, which gets everything done.

We connect to it as easily as this:

import serial
ser = serial.Serial(11, 38400, timeout=1)

The command form is byte “xd5” followed by the number of bytes in the payload of the command, then the payload bytes themselves, and finally the cyclic redundancy check byte calculation.

def runcommand(payload):
    ser.write("xd5"+chr(len(payload))+payload+crc(payload))
    first = ser.read()
    if first == '':
        raise Exception("No response")
    if first != 'xd5':
        raise Exception("Bad leading byte")
    length = ord(ser.read())
    rec = "".join(ser.read()  for i in range(length))
    rcrc = ser.read()
    if rcrc != crc(rec):
        raise Exception("Return crc mismatch")
    return rec

Don’t forget that cyclic redundancy check byte:

def crc(payload):
    b = 0
    for c in payload:
       b = (b ^ ord(c)) & 0xff
       for i in range(8):
           if b & 0x01:
               b = ((b >> 1) ^ 0x8c)
           else:
               b = b >> 1
    return chr(b)

And finally here are some random other functions to help work it out:

# prints 'Cupcake'
def getversion():
    return runcommand("x14x1cx00")

def getpos():
    res = runcommand("x04")
    return struct.unpack("<iiis", res[1:])

# setpos(0,0,0) would set current point to home
def setpos(x, y, z):
	return runcommand("x82"+struct.pack("<iii", x, y, z))
	
def abort():
	return runcommand("x07")
	
def getbuffsize():
    res = runcommand("x02")
    return struct.unpack("<i", res[1:])[0]

What to do now?

Well, printing plastic is quite complicated and I know I’d run out of enthusiasm short of what can be done using ReplicatorG. So I thought about drawing something.

If we can replace the plastic extruder with a felt tip pen, and the build platform with a post-it note, then all I need is for a way to convert a photo into a sequence of lines which can be drawn.

The Python Image Library has an edge detection algorithm:

import PIL.ImageFilter
import PIL.ImageOps

i = Image.open("PB250118.JPG")
j = i.filter(PIL.ImageFilter.FIND_EDGES)
j = PIL.ImageOps.invert(j)
j = PIL.ImageOps.grayscale(j)
#j.save("test0.bmp");
j.show()

How do I convert this into a sequence of paths? I was wondering about turning the above into a simple 3D triangulated relief surface and running the pencil milling algorithm against it.

If the pencil milling algorithm can be called from Python (or is implemented in Python), then we can have a full end-to-end process from photograph to drawing the picture in a single readable file, which means the process is hackable and can be experimentally adapted to other purposes, such as etching, artistically plotting with different colours, or cutting chocolate.

Personalize your mobile phone by scratching your picture on it. First it needs to touch-probe the shape of the surface, and then wrap the image onto it in 3D.

3 Comments

  • 1. Cupcake software | Linkfr&hellip replies at 22nd December 2011, 6:35 am :

    […] Getting life out of makerbot cupcake – Freesteel […]

  • 2. Freesteel&hellip replies at 30th December 2011, 2:27 pm :

    […] big idea is to use this 3D printer makerbot as a 2D plotter (by the application of a rubber band and a felt tip pen) to draw a representation […]

  • 3. The long dark tea time of&hellip replies at 13th January 2012, 10:04 am :

    […] I have been doing experiments through the interface of a home-built 3D printer, completely bypassing their UI application to […]

Leave a comment

XHTML: You can use these tags: <a href="" title=""> <abbr title=""> <acronym title=""> <blockquote cite=""> <code> <em> <strong>