Examples

Profiling

ocp_freecad_cam.api.Job.profile() allows creating tool paths that follow face/edge contours.

import cadquery as cq

from ocp_freecad_cam import Endmill, Job

wp = cq.Workplane().box(5, 5, 2)

top = wp.faces(">Z").workplane()
profile_shape = wp.faces("<Z")

tool = Endmill(diameter="1 mm")
job = Job(top, wp).profile(profile_shape, tool)
../_images/cq_profile.png

2.5D Pocketing

ocp_freecad_cam.api.Job.pocket() creates tool paths for pocketing / clearing holes.

import cadquery as cq

from ocp_freecad_cam import Endmill, Job

wp = (
    cq.Workplane()
    .rect(10, 10)
    .extrude(5)
    .faces(">Z")
    .workplane()
    .rect(8, 8)
    .cutBlind(-2)
    .faces(">Z")
    .rect(10, 2)
    .cutBlind(-2)
)

pocket = wp.faces(">Z[1]")
top = wp.faces(">Z").workplane()
tool = Endmill(diameter=1)
job = Job(top, wp).pocket(pocket, tool=tool, pattern="offset")
../_images/cq_pocket.png

Open pockets

Open pockets are tricky even in the GUI of FreeCAD. A clever trick that can be employed in our case:

  1. Select the desired operation faces

  2. Offset them larger (for example 1/3 tool diameter)

  3. Cut the offset faces with the part/compound/solid

  4. Fuse the result with the original faces

The result is a face that has been offset only the open directions.

../_images/b3d_open_pocket.png

Drill

ocp_freecad_cam.api.Job.drill() creates tool paths for drilling holes

import cadquery as cq

from ocp_freecad_cam import Drill, Job

wp = (
    cq.Workplane()
    .box(5, 5, 2)
    .faces(">Z")
    .workplane()
    .pushPoints([(-1.5, -1.5), (0, 1.5), (0.5, -1)])
    .circle(0.5)
    .cutThruAll()
)

top = wp.faces(">Z").workplane()
hole_edges = wp.faces("<Z").objects[0].innerWires()


tool = Drill(diameter="1 mm")
job = Job(top, wp).drill(hole_edges, tool)
../_images/cq_drill.png

Helix

ocp_freecad_cam.api.Job.drill() creates tool paths for milling holes using helical motion

import cadquery as cq

from ocp_freecad_cam import Endmill, Job

wp = (
    cq.Workplane()
    .box(5, 5, 2)
    .faces(">Z")
    .workplane()
    .pushPoints([(-1.5, -1.5), (0, 1.5), (0.5, -1)])
    .circle(0.5)
    .cutThruAll()
)

top = wp.faces(">Z").workplane()
hole_edges = wp.faces("<Z").objects[0].innerWires()


tool = Endmill(diameter="0.5 mm")
job = Job(top, wp).helix(hole_edges, tool)
../_images/cq_helix.png

Adaptive

ocp_freecad_cam.api.Job.adaptive() creates clearing/profiling tool paths using adaptive algorithms.

import cadquery as cq

from ocp_freecad_cam import Endmill, Job
from ocp_freecad_cam.api_util import Expression

wp = (
    cq.Workplane()
    .rect(10, 10)
    .extrude(5)
    .faces(">Z")
    .workplane()
    .rect(8, 8)
    .cutBlind(-1)
    .faces(">Z")
    .rect(10, 2)
    .cutBlind(-1)
)

pocket = wp.faces(">Z[1]")
top = wp.faces(">Z").workplane()
tool = Endmill(diameter=1)
job = Job(top, wp).adaptive(
    pocket,
    tool=tool,
    step_over=50,
    start_depth=Expression("0 mm"),
)
../_images/cq_adaptive.png