Skip to content

Commit

Permalink
Loft feature (#33)
Browse files Browse the repository at this point in the history
* feat: loft feature

* feat: partstudio loft interface

* feat: add test for loft

* lint

* fix: bad plane selection
  • Loading branch information
kyle-tennison authored May 9, 2024
1 parent 747d7c4 commit c196d45
Show file tree
Hide file tree
Showing 6 changed files with 158 additions and 2 deletions.
7 changes: 7 additions & 0 deletions src/onpy/api/model.py
Original file line number Diff line number Diff line change
Expand Up @@ -204,3 +204,10 @@ class Plane(Feature):

btType: str = "BTMFeature-134"
featureType: str = "cPlane"


class Loft(Feature):
"""Represents a Loft Feature"""

btType: str = "BTMFeature-134"
featureType: str = "loft"
16 changes: 15 additions & 1 deletion src/onpy/elements/partstudio.py
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@
from onpy.api.versioning import WorkspaceWVM
from onpy.util.exceptions import OnPyFeatureError
from onpy.util.misc import unwrap
from onpy.features import Sketch, Extrude, Plane, OffsetPlane
from onpy.features import Sketch, Extrude, Plane, OffsetPlane, Loft
from onpy.features.query.list import QueryList

from typing import TYPE_CHECKING, override
Expand Down Expand Up @@ -93,6 +93,20 @@ def add_extrude(
"""
return Extrude(partstudio=self, targets=targets, distance=distance, name=name)

def add_loft(self, start: QueryList, end: QueryList, name: str = "Loft") -> Loft:
"""Adds a new loft feature to the partstudio
Args:
start: The start point(s) of the loft
end: The end point(s) of the loft
name: An optional name for the loft feature
Returns:
A Loft object
"""

return Loft(partstudio=self, start_face=start, end_face=end, name=name)

def add_offset_plane(
self, target: Plane, distance: float, name: str = "Offset Plane"
) -> OffsetPlane:
Expand Down
1 change: 1 addition & 0 deletions src/onpy/features/__init__.py
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
from onpy.features.extrude import Extrude
from onpy.features.sketch import Sketch
from onpy.features.planes import Plane, OffsetPlane, DefaultPlane
from onpy.features.loft import Loft
2 changes: 1 addition & 1 deletion src/onpy/features/extrude.py
Original file line number Diff line number Diff line change
Expand Up @@ -31,7 +31,7 @@ def __init__(
@property
@override
def id(self) -> str | None:
return unwrap(self._id, message="Feature id unbound")
return unwrap(self._id, message="Extrude feature id unbound")

@property
@override
Expand Down
129 changes: 129 additions & 0 deletions src/onpy/features/loft.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,129 @@
"""OnShape extrusion feature"""

from typing import TYPE_CHECKING, override
from onpy.api.model import Feature, FeatureAddResponse
from onpy.features.base import Feature, Extrudable
import onpy.api.model as model
from onpy.util.misc import unwrap
from onpy.features.query.list import QueryList

if TYPE_CHECKING:
from onpy.elements.partstudio import PartStudio


class Loft(Feature):
"""Interface to lofting between two 2D profiles"""

def __init__(
self,
partstudio: "PartStudio",
start_face: QueryList,
end_face: QueryList,
name: str = "Loft",
) -> None:

self._partstudio = partstudio
self._id: str | None = None
self._name = name

self.start_face = start_face
self.end_face = end_face

self._upload_feature()

@property
@override
def partstudio(self) -> "PartStudio":
return self._partstudio

@property
@override
def id(self) -> str:
return unwrap(self._id, "Loft feature id unbound")

@property
@override
def name(self) -> str:
return self._name

@property
@override
def entities(self):
raise NotImplementedError()

@override
def _load_response(self, response: FeatureAddResponse) -> None:
self._id = response.feature.featureId

@override
def _to_model(self) -> model.Loft:

return model.Loft(
name=self.name,
suppressed=False,
parameters=[
{
"btType": "BTMParameterEnum-145",
"namespace": "",
"enumName": "ToolBodyType",
"value": "SOLID",
"parameterId": "bodyType",
},
{
"btType": "BTMParameterEnum-145",
"namespace": "",
"enumName": "NewBodyOperationType",
"value": "NEW",
"parameterId": "operationType",
},
{
"btType": "BTMParameterEnum-145",
"namespace": "",
"enumName": "NewSurfaceOperationType",
"value": "NEW",
"parameterId": "surfaceOperationType",
},
{
"btType": "BTMParameterArray-2025",
"items": [
{
"btType": "BTMArrayParameterItem-1843",
"parameters": [
{
"btType": "BTMParameterQueryList-148",
"queries": [
{
"btType": "BTMIndividualQuery-138",
"deterministicIds": [
e.transient_id
for e in self.start_face._available
],
}
],
"parameterId": "sheetProfileEntities",
}
],
},
{
"btType": "BTMArrayParameterItem-1843",
"parameters": [
{
"btType": "BTMParameterQueryList-148",
"queries": [
{
"btType": "BTMIndividualQuery-138",
"deterministicIds": [
e.transient_id
for e in self.end_face._available
],
}
],
"parameterId": "sheetProfileEntities",
}
],
},
],
"parameterId": "sheetProfilesArray",
},
],
)
5 changes: 5 additions & 0 deletions tests/test_features.py
Original file line number Diff line number Diff line change
Expand Up @@ -45,6 +45,11 @@ def test_sketch_extrude():
targets=offset_sketch.queries.contains_point((0, 0, 3)), distance=-3
)

# try to extrude between the sketches
loft_start = partstudio.add_sketch(partstudio.features.top_plane)
loft_start.add_circle((1, 0), 2)
partstudio.add_loft(loft_start.queries.largest(), offset_sketch.queries.largest())

doc.delete()


Expand Down

0 comments on commit c196d45

Please sign in to comment.