├── .github └── workflows │ └── python-package.yml ├── .gitignore ├── LICENSE.txt ├── MANIFEST.in ├── README.md ├── __main__.spec ├── docs ├── en │ ├── animate.html │ ├── assemble.html │ ├── bbox.html │ ├── bignav.html │ ├── bool.html │ ├── caching.html │ ├── crvalgo.html │ ├── examples.html │ ├── expimp.html │ ├── fillet.html │ ├── geomcore.html │ ├── geomprop.html │ ├── gui.html │ ├── helloworld.html │ ├── index.html │ ├── installation.html │ ├── interactive_object.html │ ├── internal.html │ ├── kinematic.html │ ├── lincycle.html │ ├── markers.html │ ├── nav.html │ ├── navigation.html │ ├── nut.html │ ├── ops3d.html │ ├── other.html │ ├── platonic.html │ ├── prim0d.html │ ├── prim1d.html │ ├── prim2d.html │ ├── prim3d.html │ ├── reflect.html │ ├── scriptcad.html │ ├── show.html │ ├── surfalgo.html │ ├── sweep.html │ ├── trans0.html │ ├── trans1.html │ └── trimesh.html ├── images │ ├── blacktocat.png │ ├── boolean.png │ ├── car.png │ ├── generic │ │ ├── bezier0.png │ │ ├── bezier1.png │ │ ├── bool20.png │ │ ├── bool21.png │ │ ├── bool22.png │ │ ├── bool23.png │ │ ├── box.png │ │ ├── box0.png │ │ ├── box1.png │ │ ├── chamfer0.png │ │ ├── chamfer1.png │ │ ├── chamfer2.png │ │ ├── chamfer3.png │ │ ├── circle0.png │ │ ├── circle1.png │ │ ├── circle2.png │ │ ├── circle3.png │ │ ├── circle_arc0.png │ │ ├── complextrans0.png │ │ ├── complextrans1.png │ │ ├── cone0.png │ │ ├── cone1.png │ │ ├── cone2.png │ │ ├── cone3.png │ │ ├── convex_hull0.png │ │ ├── cylinder0.png │ │ ├── cylinder1.png │ │ ├── cylinder2.png │ │ ├── cylinder3.png │ │ ├── difference.png │ │ ├── difference0.png │ │ ├── difference1.png │ │ ├── difference2.png │ │ ├── ellipse0.png │ │ ├── ellipse1.png │ │ ├── ellipse2.png │ │ ├── ellipse3.png │ │ ├── endpoints0.png │ │ ├── extrude0.png │ │ ├── extrude1.png │ │ ├── extrude2.png │ │ ├── extrude3.png │ │ ├── fill0.png │ │ ├── fill1.png │ │ ├── fillet0.png │ │ ├── fillet1.png │ │ ├── fillet2.png │ │ ├── fillet3.png │ │ ├── fillet4.png │ │ ├── fillet5.png │ │ ├── halfspace0.png │ │ ├── halfspace1.png │ │ ├── helix0.png │ │ ├── helix1.png │ │ ├── helix2.png │ │ ├── helix3.png │ │ ├── infplane0.png │ │ ├── infplane01.png │ │ ├── infplane1.png │ │ ├── infplane2.png │ │ ├── interpolate0.png │ │ ├── interpolate1.png │ │ ├── interpolate2.png │ │ ├── interpolate20.png │ │ ├── interpolate3.png │ │ ├── intersect.png │ │ ├── intersect0.png │ │ ├── intersect1.png │ │ ├── intersect2.png │ │ ├── invtrans0.png │ │ ├── invtrans1.png │ │ ├── invtrans2.png │ │ ├── invtrans3.png │ │ ├── loft0.png │ │ ├── loft1.png │ │ ├── loft2.png │ │ ├── loft3.png │ │ ├── loft4.png │ │ ├── loft5.png │ │ ├── multitrans0.png │ │ ├── multitrans1.png │ │ ├── ngon0.png │ │ ├── ngon1.png │ │ ├── ngon2.png │ │ ├── ngon3.png │ │ ├── ngon4.png │ │ ├── ngon5.png │ │ ├── nulltrans01.png │ │ ├── offset0.png │ │ ├── platonic0.png │ │ ├── platonic1.png │ │ ├── platonic2.png │ │ ├── platonic3.png │ │ ├── platonic4.png │ │ ├── polygon0.png │ │ ├── polygon1.png │ │ ├── polyhedron0.png │ │ ├── polysegment0.png │ │ ├── polysegment1.png │ │ ├── rectangle0.png │ │ ├── rectangle1.png │ │ ├── rectangle2.png │ │ ├── rectangle3.png │ │ ├── revol0.png │ │ ├── revol1.png │ │ ├── revol2.png │ │ ├── revol20.png │ │ ├── revol3.png │ │ ├── rotate_array0.png │ │ ├── rotate_array1.png │ │ ├── rotate_array20.png │ │ ├── rotate_array21.png │ │ ├── rounded_polysegment0.png │ │ ├── ruled0.png │ │ ├── ruled1.png │ │ ├── ruled2.png │ │ ├── ruled3.png │ │ ├── section0.png │ │ ├── section1.png │ │ ├── segment0.png │ │ ├── short_rotate0.png │ │ ├── short_rotate1.png │ │ ├── sphere0.png │ │ ├── sphere1.png │ │ ├── sphere2.png │ │ ├── sphere3.png │ │ ├── sqrmirror0.png │ │ ├── sqrmirror1.png │ │ ├── sweep0.png │ │ ├── sweep1.png │ │ ├── sweep2.png │ │ ├── sweep3.png │ │ ├── sweep4.png │ │ ├── textshape0.png │ │ ├── textshape1.png │ │ ├── thicksolid0.png │ │ ├── thicksolid1.png │ │ ├── torus0.png │ │ ├── torus1.png │ │ ├── torus2.png │ │ ├── torus3.png │ │ ├── torus4.png │ │ ├── torus5.png │ │ ├── tube0.png │ │ ├── tube1.png │ │ ├── uniform_points0.png │ │ ├── unify0.png │ │ ├── unify1.png │ │ ├── union.png │ │ ├── union0.png │ │ ├── union1.png │ │ ├── union2.png │ │ ├── wb_segment0.png │ │ └── zencad-logo.png │ ├── git-assume-unchanged.sh │ ├── gui.png │ └── helloworld.png ├── index.html ├── main.css └── ru │ ├── animate.html │ ├── assemble.html │ ├── bbox.html │ ├── bignav.html │ ├── bool.html │ ├── caching.html │ ├── crvalgo.html │ ├── examples.html │ ├── expimp.html │ ├── fillet.html │ ├── geomcore.html │ ├── geomprop.html │ ├── gui.html │ ├── helloworld.html │ ├── index.html │ ├── installation.html │ ├── installatton.html │ ├── interactive_object.html │ ├── internal.html │ ├── kinematic.html │ ├── lincycle.html │ ├── markers.html │ ├── nav.html │ ├── navigation.html │ ├── nut.html │ ├── ops3d.html │ ├── other.html │ ├── platonic.html │ ├── prim0d.html │ ├── prim1d.html │ ├── prim2d.html │ ├── prim3d.html │ ├── reflect.html │ ├── scriptcad.html │ ├── show.html │ ├── surfalgo.html │ ├── sweep.html │ ├── trans0.html │ ├── trans1.html │ └── trimesh.html ├── doxygen └── Doxyfile ├── mangen ├── HIDE │ └── en │ │ ├── animate.md │ │ ├── assemble.md │ │ ├── bool.md │ │ ├── caching.md │ │ ├── crvalgo.md │ │ ├── expimp.md │ │ ├── fillet.md │ │ ├── geomcore.md │ │ ├── geomprop.md │ │ ├── gui.md │ │ ├── helloworld.md │ │ ├── index.md │ │ ├── installation.md │ │ ├── interactive_object.md │ │ ├── internal.md │ │ ├── kinematic.md │ │ ├── nav.md │ │ ├── nut.md │ │ ├── ops3d.md │ │ ├── other.md │ │ ├── platonic.md │ │ ├── prim0d.md │ │ ├── prim1d.md │ │ ├── prim2d.md │ │ ├── prim3d.md │ │ ├── reflect.md │ │ ├── scriptcad.md │ │ ├── show.md │ │ ├── surfalgo.md │ │ ├── sweep.md │ │ ├── trans0.md │ │ └── trimesh.md ├── en │ └── nav.md ├── images │ ├── blacktocat.png │ ├── boolean.png │ ├── car.png │ ├── gui.png │ ├── helloworld.png │ └── imagen.py ├── main.css ├── main.py ├── ru │ ├── animate.md │ ├── assemble.md │ ├── bbox.md │ ├── bignav.md │ ├── bool.md │ ├── caching.md │ ├── crvalgo.md │ ├── expimp.md │ ├── fillet.md │ ├── geomcore.md │ ├── geomprop.md │ ├── gui.md │ ├── helloworld.md │ ├── index.md │ ├── installation.md │ ├── interactive_object.md │ ├── internal.md │ ├── kinematic.md │ ├── nav.md │ ├── ops3d.md │ ├── other.md │ ├── prim0d.md │ ├── prim1d.md │ ├── prim2d.md │ ├── prim3d.md │ ├── reflect.md │ ├── scriptcad.md │ ├── show.md │ ├── surfalgo.md │ ├── sweep.md │ ├── trans0.md │ └── trimesh.md └── writer.py ├── requirements.txt ├── setup.py ├── tools ├── build_dists.sh ├── clean.sh ├── pep8-format.sh ├── pre-commit ├── publish.sh ├── pyinstaller_invoke.sh ├── pyinstaller_make.sh └── reinstall_local.sh ├── utest ├── api.py ├── boolean_test.py ├── convert.py ├── curve2_test.py ├── curve3_test.py ├── examples.py ├── general_transformation_test.py ├── make_test.py ├── math_test.py ├── ops1d2d_test.py ├── ops3d_test.py ├── prim1d_test.py ├── prim2d_test.py ├── prim3d_test.py ├── reflection.py ├── start-all.py ├── trans_test.py └── widgets_test.py └── zencad ├── __init__.py ├── __main__.py ├── animate.py ├── assemble.py ├── axis.py ├── bbox.py ├── color.py ├── convert ├── api.py ├── svg.py └── test.svg ├── curve.py ├── examples ├── 0.Base │ ├── csg.py │ └── helloworld.py ├── 1.GeomPrim │ ├── 1.prim3d │ │ ├── box.py │ │ ├── cone.py │ │ ├── cylinder.py │ │ ├── halfspace.py │ │ ├── platonic.py │ │ ├── sphere.py │ │ └── torus.py │ ├── 2.prim2d │ │ ├── circle.py │ │ ├── ellipse.py │ │ ├── fillet_ngon.py │ │ ├── interpolate2.py │ │ ├── ngon.py │ │ ├── polygon.py │ │ ├── rectangle.py │ │ ├── textshape.py │ │ └── widewire.py │ └── 3.prim1d │ │ ├── bezier.py │ │ ├── bspline.py │ │ ├── helix.py │ │ ├── interpolate.py │ │ ├── polysegment.py │ │ ├── rounded_polysegment.py │ │ └── segment.py ├── 2.Operations │ ├── 1.AphineTrans │ │ ├── rotate_array.py │ │ ├── scale.py │ │ └── short_rotate.py │ ├── 2.Operations │ │ ├── loft.py │ │ ├── offset.py │ │ └── thicksolid.py │ ├── 3.Sweep │ │ ├── extrude.py │ │ ├── pipe_shell.py │ │ ├── pipe_shell_frenet.py │ │ ├── revol.py │ │ ├── revol2.py │ │ ├── tube.py │ │ └── tube_by_points.py │ ├── 4.Mesh │ │ └── triangulate.py │ ├── boolean.py │ └── unify.py ├── 3.Animation │ ├── base.py │ ├── camera.py │ ├── change_color.py │ ├── color.py │ └── pacman.py ├── 4.Assemble │ ├── EulerAngles.py │ ├── manual-control-2.py │ ├── manual-control.py │ └── robot.py ├── Integration │ ├── pillow │ │ ├── senku.png │ │ ├── smile.png │ │ └── smile.py │ ├── skimage-mechanicus │ │ ├── cube.py │ │ ├── image.png │ │ └── mech.py │ ├── svg.py │ └── trimesh │ │ ├── README.md │ │ ├── bulbasaur.STL │ │ └── bulbasaur.py ├── MiniGames │ ├── tennis.py │ └── tetris.py ├── Models │ ├── bottle.py │ ├── cup.py │ ├── logo.py │ ├── nut.py │ └── organizer │ │ ├── assembly.py │ │ ├── case.py │ │ └── organizer.py ├── OpenscadLike │ ├── csg.py │ └── logo.py └── fonts │ ├── mandarinc.ttf │ └── testfont.ttf ├── geom ├── boolops.py ├── boolops_base.py ├── curve.py ├── curve2.py ├── curve_algo.py ├── exttrans.py ├── face.py ├── general_transformation.py ├── near.py ├── offset.py ├── operations.py ├── platonic.py ├── project.py ├── reflect_helpers.py ├── sew.py ├── shape.py ├── shell.py ├── solid.py ├── surface.py ├── sweep.py ├── sweep_law.py ├── trans.py ├── transformable.py ├── unify.py ├── unify_ops.py ├── wire.py └── wire_builder.py ├── geombase.py ├── geometry_core_installer.py ├── gui ├── actions.py ├── display.py ├── display_only.py ├── display_unbounded.py ├── info_widget.py ├── libinstaller.py ├── mainwindow.py ├── settingswdg.py └── util.py ├── gutil.py ├── industrial-robot.svg ├── interactive ├── __init__.py ├── assemble.py ├── axis.py ├── displayable.py ├── interactive_object.py ├── line.py ├── point.py └── shape.py ├── internal_models ├── __init__.py └── knight.py ├── lazifier.py ├── libs ├── kinematic.py ├── malgo.py └── screw.py ├── opencascade_types.py ├── scene.py ├── settings.py ├── showapi.py ├── techpriest.jpg ├── util.py ├── version.py └── zencad_logo.png /.gitignore: -------------------------------------------------------------------------------- 1 | # Byte-compiled / optimized / DLL files 2 | __pycache__/ 3 | *.py[cod] 4 | *$py.class 5 | 6 | # C extensions 7 | *.so 8 | 9 | # Distribution / packaging 10 | .Python 11 | env/ 12 | build/ 13 | develop-eggs/ 14 | dist/ 15 | downloads/ 16 | eggs/ 17 | .eggs/ 18 | lib/ 19 | lib64/ 20 | parts/ 21 | sdist/ 22 | var/ 23 | wheels/ 24 | *.egg-info/ 25 | .installed.cfg 26 | *.egg 27 | .idea 28 | 29 | # PyInstaller 30 | # Usually these files are written by a python script from a template 31 | # before PyInstaller builds the exe, so as to inject date/other infos into it. 32 | *.manifest 33 | *.spec 34 | !__main__.spec 35 | 36 | # Installer logs 37 | pip-log.txt 38 | pip-delete-this-directory.txt 39 | 40 | # Unit test / coverage reports 41 | htmlcov/ 42 | .tox/ 43 | .coverage 44 | .coverage.* 45 | .cache 46 | nosetests.xml 47 | coverage.xml 48 | *.cover 49 | .hypothesis/ 50 | 51 | # Translations 52 | *.mo 53 | *.pot 54 | 55 | # Django stuff: 56 | *.log 57 | local_settings.py 58 | 59 | # Flask stuff: 60 | instance/ 61 | .webassets-cache 62 | 63 | # Scrapy stuff: 64 | .scrapy 65 | 66 | # Sphinx documentation 67 | docs/_build/ 68 | 69 | # PyBuilder 70 | target/ 71 | 72 | # Jupyter Notebook 73 | .ipynb_checkpoints 74 | 75 | # pyenv 76 | .python-version 77 | 78 | # celery beat schedule file 79 | celerybeat-schedule 80 | 81 | # SageMath parsed files 82 | *.sage.py 83 | 84 | # dotenv 85 | .env 86 | 87 | # virtualenv 88 | .venv 89 | venv/ 90 | ENV/ 91 | 92 | # Spyder project settings 93 | .spyderproject 94 | .spyproject 95 | 96 | # Rope project settings 97 | .ropeproject 98 | 99 | # mkdocs documentation 100 | /site 101 | 102 | # mypy 103 | .mypy_cache/ 104 | 105 | 106 | *.dump 107 | *.zen 108 | .evalcache 109 | .evalfile 110 | test/screens/*.png 111 | 112 | *.stl 113 | *.brep 114 | mangen/images/generic/*.png 115 | 116 | 117 | doxygen/html 118 | doxygen/latex 119 | -------------------------------------------------------------------------------- /LICENSE.txt: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2019-2021 mirmik 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. -------------------------------------------------------------------------------- /MANIFEST.in: -------------------------------------------------------------------------------- 1 | recursive-include *.py 2 | 3 | include industrial-robot.svg 4 | include techpriest.jpg 5 | include zencad_logo.png 6 | 7 | include zencad/examples/Integration/mechanicus/image.png 8 | include zencad/examples/fonts/mandarinc.ttf 9 | include zencad/examples/fonts/testfont.ttf -------------------------------------------------------------------------------- /__main__.spec: -------------------------------------------------------------------------------- 1 | # -*- mode: python ; coding: utf-8 -*- 2 | import os 3 | import sys 4 | 5 | block_cipher = None 6 | 7 | datas = [] 8 | for (p, d, f) in os.walk("./zencad/"): 9 | datas.extend([(os.path.join(p,a), os.path.relpath(p, start=".")) for a in f]) 10 | 11 | datas.append(("zencad/industrial-robot.svg", "zencad")) 12 | datas.append(("zencad/techpriest.jpg", "zencad")) 13 | datas.append(("zencad/zencad_logo.png", "zencad")) 14 | 15 | path = os.getcwd() 16 | zenframe_path = os.path.join(os.getcwd(), "..", "zenframe") 17 | 18 | a = Analysis(['zencad/__main__.py'], 19 | pathex=[path, zenframe_path], 20 | binaries=[], 21 | datas=datas, 22 | hiddenimports=["zenframe", "PyQt5", "PyQt5.sip"], 23 | hookspath=[], 24 | runtime_hooks=[], 25 | excludes=[], 26 | win_no_prefer_redirects=False, 27 | win_private_assemblies=False, 28 | cipher=block_cipher, 29 | noarchive=True) 30 | pyz = PYZ(a.pure, a.zipped_data, 31 | cipher=block_cipher) 32 | exe = EXE(pyz, 33 | a.scripts, 34 | [], 35 | exclude_binaries=True, 36 | name='ZenCad.exe' if sys.platform == "win32" else 'ZenCad', 37 | debug=False, 38 | bootloader_ignore_signals=False, 39 | strip=False, 40 | upx=True, 41 | console=True ) 42 | coll = COLLECT(exe, 43 | a.binaries, 44 | a.zipfiles, 45 | a.datas, 46 | strip=False, 47 | upx=True, 48 | upx_exclude=[], 49 | name='ZenCad') 50 | -------------------------------------------------------------------------------- /docs/en/examples.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | ZenCad 5 | 6 | 7 | 8 | 9 | 21 |
22 | 57 |
English version in preparation. COMMING SOON.

58 |
59 |
60 | 61 | 62 | -------------------------------------------------------------------------------- /docs/en/markers.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | ZenCad 5 | 6 | 7 | 8 | 9 | 21 |
22 | 57 |
English version in preparation. COMMING SOON.

58 |
59 |
60 | 61 | 62 | -------------------------------------------------------------------------------- /docs/en/navigation.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | ZenCad 5 | 6 | 7 | 8 | 9 | 21 |
22 | 57 |
English version in preparation. COMMING SOON.

58 |
59 |
60 | 61 | 62 | -------------------------------------------------------------------------------- /docs/images/blacktocat.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/blacktocat.png -------------------------------------------------------------------------------- /docs/images/boolean.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/boolean.png -------------------------------------------------------------------------------- /docs/images/car.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/car.png -------------------------------------------------------------------------------- /docs/images/generic/bezier0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/bezier0.png -------------------------------------------------------------------------------- /docs/images/generic/bezier1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/bezier1.png -------------------------------------------------------------------------------- /docs/images/generic/bool20.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/bool20.png -------------------------------------------------------------------------------- /docs/images/generic/bool21.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/bool21.png -------------------------------------------------------------------------------- /docs/images/generic/bool22.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/bool22.png -------------------------------------------------------------------------------- /docs/images/generic/bool23.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/bool23.png -------------------------------------------------------------------------------- /docs/images/generic/box.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/box.png -------------------------------------------------------------------------------- /docs/images/generic/box0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/box0.png -------------------------------------------------------------------------------- /docs/images/generic/box1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/box1.png -------------------------------------------------------------------------------- /docs/images/generic/chamfer0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/chamfer0.png -------------------------------------------------------------------------------- /docs/images/generic/chamfer1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/chamfer1.png -------------------------------------------------------------------------------- /docs/images/generic/chamfer2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/chamfer2.png -------------------------------------------------------------------------------- /docs/images/generic/chamfer3.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/chamfer3.png -------------------------------------------------------------------------------- /docs/images/generic/circle0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/circle0.png -------------------------------------------------------------------------------- /docs/images/generic/circle1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/circle1.png -------------------------------------------------------------------------------- /docs/images/generic/circle2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/circle2.png -------------------------------------------------------------------------------- /docs/images/generic/circle3.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/circle3.png -------------------------------------------------------------------------------- /docs/images/generic/circle_arc0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/circle_arc0.png -------------------------------------------------------------------------------- /docs/images/generic/complextrans0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/complextrans0.png -------------------------------------------------------------------------------- /docs/images/generic/complextrans1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/complextrans1.png -------------------------------------------------------------------------------- /docs/images/generic/cone0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/cone0.png -------------------------------------------------------------------------------- /docs/images/generic/cone1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/cone1.png -------------------------------------------------------------------------------- /docs/images/generic/cone2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/cone2.png -------------------------------------------------------------------------------- /docs/images/generic/cone3.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/cone3.png -------------------------------------------------------------------------------- /docs/images/generic/convex_hull0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/convex_hull0.png -------------------------------------------------------------------------------- /docs/images/generic/cylinder0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/cylinder0.png -------------------------------------------------------------------------------- /docs/images/generic/cylinder1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/cylinder1.png -------------------------------------------------------------------------------- /docs/images/generic/cylinder2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/cylinder2.png -------------------------------------------------------------------------------- /docs/images/generic/cylinder3.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/cylinder3.png -------------------------------------------------------------------------------- /docs/images/generic/difference.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/difference.png -------------------------------------------------------------------------------- /docs/images/generic/difference0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/difference0.png -------------------------------------------------------------------------------- /docs/images/generic/difference1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/difference1.png -------------------------------------------------------------------------------- /docs/images/generic/difference2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/difference2.png -------------------------------------------------------------------------------- /docs/images/generic/ellipse0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/ellipse0.png -------------------------------------------------------------------------------- /docs/images/generic/ellipse1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/ellipse1.png -------------------------------------------------------------------------------- /docs/images/generic/ellipse2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/ellipse2.png -------------------------------------------------------------------------------- /docs/images/generic/ellipse3.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/ellipse3.png -------------------------------------------------------------------------------- /docs/images/generic/endpoints0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/endpoints0.png -------------------------------------------------------------------------------- /docs/images/generic/extrude0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/extrude0.png -------------------------------------------------------------------------------- /docs/images/generic/extrude1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/extrude1.png -------------------------------------------------------------------------------- /docs/images/generic/extrude2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/extrude2.png -------------------------------------------------------------------------------- /docs/images/generic/extrude3.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/extrude3.png -------------------------------------------------------------------------------- /docs/images/generic/fill0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/fill0.png -------------------------------------------------------------------------------- /docs/images/generic/fill1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/fill1.png -------------------------------------------------------------------------------- /docs/images/generic/fillet0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/fillet0.png -------------------------------------------------------------------------------- /docs/images/generic/fillet1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/fillet1.png -------------------------------------------------------------------------------- /docs/images/generic/fillet2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/fillet2.png -------------------------------------------------------------------------------- /docs/images/generic/fillet3.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/fillet3.png -------------------------------------------------------------------------------- /docs/images/generic/fillet4.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/fillet4.png -------------------------------------------------------------------------------- /docs/images/generic/fillet5.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/fillet5.png -------------------------------------------------------------------------------- /docs/images/generic/halfspace0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/halfspace0.png -------------------------------------------------------------------------------- /docs/images/generic/halfspace1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/halfspace1.png -------------------------------------------------------------------------------- /docs/images/generic/helix0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/helix0.png -------------------------------------------------------------------------------- /docs/images/generic/helix1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/helix1.png -------------------------------------------------------------------------------- /docs/images/generic/helix2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/helix2.png -------------------------------------------------------------------------------- /docs/images/generic/helix3.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/helix3.png -------------------------------------------------------------------------------- /docs/images/generic/infplane0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/infplane0.png -------------------------------------------------------------------------------- /docs/images/generic/infplane01.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/infplane01.png -------------------------------------------------------------------------------- /docs/images/generic/infplane1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/infplane1.png -------------------------------------------------------------------------------- /docs/images/generic/infplane2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/infplane2.png -------------------------------------------------------------------------------- /docs/images/generic/interpolate0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/interpolate0.png -------------------------------------------------------------------------------- /docs/images/generic/interpolate1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/interpolate1.png -------------------------------------------------------------------------------- /docs/images/generic/interpolate2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/interpolate2.png -------------------------------------------------------------------------------- /docs/images/generic/interpolate20.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/interpolate20.png -------------------------------------------------------------------------------- /docs/images/generic/interpolate3.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/interpolate3.png -------------------------------------------------------------------------------- /docs/images/generic/intersect.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/intersect.png -------------------------------------------------------------------------------- /docs/images/generic/intersect0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/intersect0.png -------------------------------------------------------------------------------- /docs/images/generic/intersect1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/intersect1.png -------------------------------------------------------------------------------- /docs/images/generic/intersect2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/intersect2.png -------------------------------------------------------------------------------- /docs/images/generic/invtrans0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/invtrans0.png -------------------------------------------------------------------------------- /docs/images/generic/invtrans1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/invtrans1.png -------------------------------------------------------------------------------- /docs/images/generic/invtrans2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/invtrans2.png -------------------------------------------------------------------------------- /docs/images/generic/invtrans3.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/invtrans3.png -------------------------------------------------------------------------------- /docs/images/generic/loft0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/loft0.png -------------------------------------------------------------------------------- /docs/images/generic/loft1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/loft1.png -------------------------------------------------------------------------------- /docs/images/generic/loft2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/loft2.png -------------------------------------------------------------------------------- /docs/images/generic/loft3.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/loft3.png -------------------------------------------------------------------------------- /docs/images/generic/loft4.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/loft4.png -------------------------------------------------------------------------------- /docs/images/generic/loft5.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/loft5.png -------------------------------------------------------------------------------- /docs/images/generic/multitrans0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/multitrans0.png -------------------------------------------------------------------------------- /docs/images/generic/multitrans1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/multitrans1.png -------------------------------------------------------------------------------- /docs/images/generic/ngon0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/ngon0.png -------------------------------------------------------------------------------- /docs/images/generic/ngon1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/ngon1.png -------------------------------------------------------------------------------- /docs/images/generic/ngon2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/ngon2.png -------------------------------------------------------------------------------- /docs/images/generic/ngon3.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/ngon3.png -------------------------------------------------------------------------------- /docs/images/generic/ngon4.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/ngon4.png -------------------------------------------------------------------------------- /docs/images/generic/ngon5.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/ngon5.png -------------------------------------------------------------------------------- /docs/images/generic/nulltrans01.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/nulltrans01.png -------------------------------------------------------------------------------- /docs/images/generic/offset0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/offset0.png -------------------------------------------------------------------------------- /docs/images/generic/platonic0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/platonic0.png -------------------------------------------------------------------------------- /docs/images/generic/platonic1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/platonic1.png -------------------------------------------------------------------------------- /docs/images/generic/platonic2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/platonic2.png -------------------------------------------------------------------------------- /docs/images/generic/platonic3.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/platonic3.png -------------------------------------------------------------------------------- /docs/images/generic/platonic4.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/platonic4.png -------------------------------------------------------------------------------- /docs/images/generic/polygon0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/polygon0.png -------------------------------------------------------------------------------- /docs/images/generic/polygon1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/polygon1.png -------------------------------------------------------------------------------- /docs/images/generic/polyhedron0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/polyhedron0.png -------------------------------------------------------------------------------- /docs/images/generic/polysegment0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/polysegment0.png -------------------------------------------------------------------------------- /docs/images/generic/polysegment1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/polysegment1.png -------------------------------------------------------------------------------- /docs/images/generic/rectangle0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/rectangle0.png -------------------------------------------------------------------------------- /docs/images/generic/rectangle1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/rectangle1.png -------------------------------------------------------------------------------- /docs/images/generic/rectangle2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/rectangle2.png -------------------------------------------------------------------------------- /docs/images/generic/rectangle3.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/rectangle3.png -------------------------------------------------------------------------------- /docs/images/generic/revol0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/revol0.png -------------------------------------------------------------------------------- /docs/images/generic/revol1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/revol1.png -------------------------------------------------------------------------------- /docs/images/generic/revol2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/revol2.png -------------------------------------------------------------------------------- /docs/images/generic/revol20.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/revol20.png -------------------------------------------------------------------------------- /docs/images/generic/revol3.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/revol3.png -------------------------------------------------------------------------------- /docs/images/generic/rotate_array0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/rotate_array0.png -------------------------------------------------------------------------------- /docs/images/generic/rotate_array1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/rotate_array1.png -------------------------------------------------------------------------------- /docs/images/generic/rotate_array20.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/rotate_array20.png -------------------------------------------------------------------------------- /docs/images/generic/rotate_array21.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/rotate_array21.png -------------------------------------------------------------------------------- /docs/images/generic/rounded_polysegment0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/rounded_polysegment0.png -------------------------------------------------------------------------------- /docs/images/generic/ruled0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/ruled0.png -------------------------------------------------------------------------------- /docs/images/generic/ruled1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/ruled1.png -------------------------------------------------------------------------------- /docs/images/generic/ruled2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/ruled2.png -------------------------------------------------------------------------------- /docs/images/generic/ruled3.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/ruled3.png -------------------------------------------------------------------------------- /docs/images/generic/section0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/section0.png -------------------------------------------------------------------------------- /docs/images/generic/section1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/section1.png -------------------------------------------------------------------------------- /docs/images/generic/segment0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/segment0.png -------------------------------------------------------------------------------- /docs/images/generic/short_rotate0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/short_rotate0.png -------------------------------------------------------------------------------- /docs/images/generic/short_rotate1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/short_rotate1.png -------------------------------------------------------------------------------- /docs/images/generic/sphere0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/sphere0.png -------------------------------------------------------------------------------- /docs/images/generic/sphere1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/sphere1.png -------------------------------------------------------------------------------- /docs/images/generic/sphere2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/sphere2.png -------------------------------------------------------------------------------- /docs/images/generic/sphere3.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/sphere3.png -------------------------------------------------------------------------------- /docs/images/generic/sqrmirror0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/sqrmirror0.png -------------------------------------------------------------------------------- /docs/images/generic/sqrmirror1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/sqrmirror1.png -------------------------------------------------------------------------------- /docs/images/generic/sweep0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/sweep0.png -------------------------------------------------------------------------------- /docs/images/generic/sweep1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/sweep1.png -------------------------------------------------------------------------------- /docs/images/generic/sweep2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/sweep2.png -------------------------------------------------------------------------------- /docs/images/generic/sweep3.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/sweep3.png -------------------------------------------------------------------------------- /docs/images/generic/sweep4.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/sweep4.png -------------------------------------------------------------------------------- /docs/images/generic/textshape0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/textshape0.png -------------------------------------------------------------------------------- /docs/images/generic/textshape1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/textshape1.png -------------------------------------------------------------------------------- /docs/images/generic/thicksolid0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/thicksolid0.png -------------------------------------------------------------------------------- /docs/images/generic/thicksolid1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/thicksolid1.png -------------------------------------------------------------------------------- /docs/images/generic/torus0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/torus0.png -------------------------------------------------------------------------------- /docs/images/generic/torus1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/torus1.png -------------------------------------------------------------------------------- /docs/images/generic/torus2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/torus2.png -------------------------------------------------------------------------------- /docs/images/generic/torus3.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/torus3.png -------------------------------------------------------------------------------- /docs/images/generic/torus4.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/torus4.png -------------------------------------------------------------------------------- /docs/images/generic/torus5.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/torus5.png -------------------------------------------------------------------------------- /docs/images/generic/tube0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/tube0.png -------------------------------------------------------------------------------- /docs/images/generic/tube1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/tube1.png -------------------------------------------------------------------------------- /docs/images/generic/uniform_points0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/uniform_points0.png -------------------------------------------------------------------------------- /docs/images/generic/unify0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/unify0.png -------------------------------------------------------------------------------- /docs/images/generic/unify1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/unify1.png -------------------------------------------------------------------------------- /docs/images/generic/union.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/union.png -------------------------------------------------------------------------------- /docs/images/generic/union0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/union0.png -------------------------------------------------------------------------------- /docs/images/generic/union1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/union1.png -------------------------------------------------------------------------------- /docs/images/generic/union2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/union2.png -------------------------------------------------------------------------------- /docs/images/generic/wb_segment0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/wb_segment0.png -------------------------------------------------------------------------------- /docs/images/generic/zencad-logo.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/generic/zencad-logo.png -------------------------------------------------------------------------------- /docs/images/git-assume-unchanged.sh: -------------------------------------------------------------------------------- 1 | git update-index --assume-unchanged generic/* -------------------------------------------------------------------------------- /docs/images/gui.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/gui.png -------------------------------------------------------------------------------- /docs/images/helloworld.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/docs/images/helloworld.png -------------------------------------------------------------------------------- /docs/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | Dominate 5 | 6 | 7 | 8 |

Если ваш браузер не поддерживает redirect, перейдите по ссылке:

9 |

10 | ZenCad/ru 11 |

12 |

13 | ZenCad/en 14 |

15 | 16 | -------------------------------------------------------------------------------- /docs/ru/markers.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | ZenCad 5 | 6 | 7 | 8 | 9 | 21 |
22 | 57 |

58 |
59 |
60 | 61 | 62 | -------------------------------------------------------------------------------- /docs/ru/navigation.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | ZenCad 5 | 6 | 7 | 8 | 9 | 21 |
22 | 57 |

58 |
59 |
60 | 61 | 62 | -------------------------------------------------------------------------------- /mangen/HIDE/en/animate.md: -------------------------------------------------------------------------------- 1 | # Анимация 2 | Графический интерфейс позволяет анимировать отображаемую сцену. 3 | Пример: 4 | 5 | ```python3 6 | s = box(10, center=True) 7 | controller = disp(s) 8 | nulltime = time.time() 9 | 10 | def animate(widget): 11 | trans = rotateZ(time.time() - nulltime) * right(30) 12 | controller.relocate(trans) 13 | 14 | show(animate=animate) 15 | ``` 16 | 17 | Здесь мы используем специальную функцию анимации `animate`, которая, используя объект контроллер, возвращенный функцией disp, в зависимости от текущего момента времени обновляет местоположение контролируемого объекта. 18 | В качестве параметра метода `relocate` выступает объект преобразования. (Подробнее в [Преобразования](trans0.html), [Комбинации преобразований](trans1.html)) 19 | 20 | Кроме параметра `animate` функция show имеет связанные параметры `preanimate` и `close_handle`. `preanimate` принимает функцию, вызывающуюся один раз до первой итерации `animate`, но уже после создания графического окружения. `close_handle` вызывается как обработчик при завершении процесса. -------------------------------------------------------------------------------- /mangen/HIDE/en/caching.md: -------------------------------------------------------------------------------- 1 | # Кэширование и ленивые объекты. 2 | 3 | Особенностью скриптового cad является необходимость перезапуска скрипта генерации геометрии при каждом обновлении модели. С ростом размера модели это приводит к значительному росту времени, требующегося на расчёт и отрисовку геометрии. С целью решения этой проблемы вычислительно ёмкие операции ZenCad закешированы и ленифицированы силами библиотеки [evalcache](https://github.com/mirmik/evalcache). 4 | 5 | Вместо непосредственного расчета, evalcache строит дерево построения модели на основе хэшключей генерируемых объектов. Библиотека сохраняет в кэше на жестком диске все произведенные вычисления и в случае, если объект уже был расчитан ранее, достаёт его из кэша. evalcache отслеживает изменения параметров в дереве модели и на лету обновляет переставшие быть актуальными объекты вычисления. 6 | 7 | ### Отладка в условиях работы с ленивыми вычислениями. 8 | Так как evalcache выполняет вычисления только в момент, когда объект в действительности запрошен, а не тогда, когда он объявлен, могут возникать проблемы с пониманием точки возникновения возможной ошибки. Также могут возникать проблемы из-за неявного раскрытия ленивых объектов на некоторых операциях. 9 | 10 | Для отладки и понимания точки возникновения ошибки можно применять следующие опции: 11 | 12 | ```python 13 | zencad.lazy.diag=True # Активировать вывод информации об операциях библиотеки кеширования. 14 | zencad.lazy.fastdo=True # Выполнять запрос объекта в момент его создания. 15 | zencad.lazy.encache=False # Запретить сохранение в кэш. 16 | zencad.lazy.decache=False # Запретить загрузку из кэша. 17 | 18 | zencad.lazy.onbool=False # Запретить автоматическое раскрытие на булевых операциях 19 | zencad.lazy.onstr=False # Запретить автоматическое раскрытие при преобразовании к строке. 20 | 21 | zencad.lazy.onplace=True # Раскрывать объект в момент его создания (не рекомендуется, может нарушать логику). 22 | ``` 23 | 24 | Дополнительные опции можно найти в документации к коду библиотеки evalcache. 25 | 26 | ---- 27 | ### Где лежит кэш? 28 | По умолчанию кеш располагается по локальному адресу `~/.zencadcache`, где _~_ - домашний директорий пользователя. -------------------------------------------------------------------------------- /mangen/HIDE/en/expimp.md: -------------------------------------------------------------------------------- 1 | # Экспорт/Импорт 2 | 3 | Операции экспорта/импорта отличаются от большинства операций библиотеки zencad тем, что производятся не только над объектами в памяти программы, но и над файлами. Для работы с файлами библиотека кэширования evalcache использует специальный механизм. Благодаря ему операции импорта учитывают изменения содержимого файлов, а операции экспорта не выполняются без необходимости. 4 | 5 | --- 6 | ## STL 7 | Создать файл мешсети формата STL, находящийся по пути `path`, из твердотельной модели `model`. 8 | Параметр `delta` определяет степень детализации. Чем меньше `delta`, тем меньше размер полигонов. 9 | ```python3 10 | to_stl(model, path, delta) 11 | ``` 12 | 13 | --- 14 | ## BREP 15 | Создать файл brep представления формата BREP, находящийся по пути `path`, из твердотельной модели `model`. 16 | ```python3 17 | to_brep(model, path) 18 | ``` 19 | 20 | Считать файл brep представления формата BREP, находящийся по пути `path`. Вернуть полученную модель. 21 | ```python3 22 | m = from_brep(path) 23 | ``` -------------------------------------------------------------------------------- /mangen/HIDE/en/fillet.md: -------------------------------------------------------------------------------- 1 | # Топологически зависимые преобразования 2 | 3 | Существует класс операций, требующий в качестве параметра выбрать элемент топологии модели. В интерактивных CAD мы можем, используя указатель мыши, выделить такой элемент и указать в качестве параметра. Этот метод недоступен в скриптовом CAD. Общий подход ZenCad состоит в том, что такой элемент задаётся методом "ближайшей точки". При задании аргумента, вместо элемента топологии задаётся точка. Выбранным считается элемент, растояние до которого от элемента топологии будет минимальным. 4 | 5 | --- 6 | ## Fillet 7 | Операция скругления тела. 8 | Если тело объёмное - модификации подвергаются ребра. Если плоское - вершины. 9 | Скругления задаются радиусом `r` и масивом ближайших точек `refs`. Если `refs == None`, выбранными считаются все элементы топологии. 10 | 11 | ```python 12 | fillet(proto=model, r=radius, refs=referencedPoints) 13 | fillet(proto=model, r=radius) 14 | model.fillet(radius, referencedPoints) 15 | model.fillet(radius) 16 | ``` 17 | ![](../images/generic/fillet0.png) 18 | ![](../images/generic/fillet1.png) 19 | ![](../images/generic/fillet2.png) 20 | ![](../images/generic/fillet3.png) 21 | ![](../images/generic/fillet4.png) 22 | ![](../images/generic/fillet5.png) 23 | 24 | --- 25 | ## Chamfer 26 | Операция взятия фаски тела. В отличие от скругления применяется только к объёмным телам. 27 | Фаска задаётся расстоянием `r`, взятым от ребра до линии фаски и масивом ближайших точек `refs`. Если `refs == None`, выбранными считаются все элементы топологии. 28 | 29 | TODO: несиметричная фаска. 30 | 31 | ```python 32 | chamfer(proto=model, r=radius, refs=referencedPoints) 33 | ``` 34 | ![](../images/generic/chamfer0.png) 35 | ![](../images/generic/chamfer1.png) 36 | ![](../images/generic/chamfer2.png) 37 | ![](../images/generic/chamfer3.png) 38 | 39 | --- 40 | ## Thicksolid 41 | Операция создания тонкостенного объёмного тела. 42 | Задаётся прототипной моделью `shp` и массивом точек, ближайших к удаляемым граням `refs`. 43 | Также задаётся толщина стенок `t`. Если толщина стенок положительная, стенки наращиваются наружу. Если отрицательная - внутрь. 44 | 45 | ```python 46 | thicksolid(proto=model, t=thickness, refs=referencedPoints) 47 | ``` 48 | 49 | ![](../images/generic/thicksolid0.png) 50 | ![](../images/generic/thicksolid1.png) -------------------------------------------------------------------------------- /mangen/HIDE/en/geomprop.md: -------------------------------------------------------------------------------- 1 | # Геометрические характеристики. 2 | Раздел посвящен измерению геометрических характеристик конструируемой геометрии. 3 | 4 | Поскольку понятия плотности и масштаба весьма эфемерны для вычислительной библиотеки, все вычисления проводятся в условных единицах. Перевод величин в систему си требует дополнительных вычислений. 5 | 6 | ---------------------------------------- 7 | ## Встроенные методы 8 | Shape имеет ряд методов, позволяющих запросить геометрическую информацию. 9 | 10 | ### Центр масс. 11 | shape.center() -> point3 12 | shape.cmradius() -> vector3 13 | 14 | ### Объём. 15 | shape.mass() -> float 16 | 17 | ### Матрица инерции. 18 | shape.matrix_of_inertia() -> matrix33 19 | 20 | ### Статические моменты. 21 | shape.static_moments() -> float, float, float 22 | 23 | ### Момент инерции относительно оси. 24 | UNDER_CONSTRUCT 25 | 26 | ### Радиус инерции. 27 | UNDER_CONSTRUCT 28 | 29 | ----------------------------------------- 30 | ## Измерение систем тел 31 | UNDER_CONSTRUCT -------------------------------------------------------------------------------- /mangen/HIDE/en/gui.md: -------------------------------------------------------------------------------- 1 | # Графический интерфейс, основные моменты. 2 | 3 | ![gui.png](../images/gui.png) 4 | 5 | ## Вызов 6 | Окно графического интерфейса может быть вызвано следующими способами: 7 | 8 | * Вызов `zencad.show()` в интерпретаторе python. 9 | * Выполнение `python3 -m pip zencad` в среде терминала. (usage: `python3 -m pip zencad [filepath]`) 10 | * Вызов утилиты командной строки `zencad` (usage: `zencad [filepath]`) 11 | 12 | ## Обновление модели по обновлению файла источника 13 | Визуализатор отслеживает изменения файла, источника геометрии. По обновлению источника, программа автоматически начинает перевыполнение скрипта. Следует учесть, что реализация этой функциональности выполняется путём изменения работы функции `zencad.show()` (То есть, есть разница в запуске скрипта из терминала, или из программы визуализатора). 14 | 15 | ## Встроенный текстовый редактор 16 | Визуализатор имеет встроенный виджет текстового редактора, который может быть использован для быстрого редактирования или проведения экспериментов. Отображение редактора `View/'Hide editor'` 17 | 18 | ## Встроенная консоль 19 | ZenCad также ретранслирует вывод терминала на встроенную консоль. Отображение консоли `View/'Hide console'`. 20 | Это может использоваться в случае, когда вывод основного терминала недоступен. 21 | 22 | ## Маркеры, определение координат 23 | Для установки маркеров следует используются клавиши `Q(F1)`, `W(F2)`. После установки координаты маркера выводятся в соответствующем поле. Если установлены оба маркера, дистанция между ними отображается в поле Distance. 24 | 25 | ## 3D навигация 26 | Вращение: MouseLeftClick/Alt + MouseMove 27 | Смещение: MouseRightClick/Shift + MouseMove 28 | Масштабирование: PgUp/PgDown/MouseWheel 29 | 30 | Визуализатор поддерживает два режима ориентации. Ортогональную ориентацию (ось Z всегда направлена вверх) и режим свободного вращения. Переключение между ними - `Navigation/'Axionometric view'`, `Navigation/'Free rotation view'` -------------------------------------------------------------------------------- /mangen/HIDE/en/helloworld.md: -------------------------------------------------------------------------------- 1 | # Привет, друг. 2 | 3 | Вот пример, демонстрирующий принцип построения моделей в zencad. 4 | ```python 5 | from zencad import * 6 | 7 | a = box(200, 200, 200, center = True) 8 | b = sphere(120) 9 | c = sphere(60) 10 | 11 | model = a - b + c 12 | 13 | display(model) 14 | 15 | show() 16 | ``` 17 | 18 | ------------------ 19 | ## Что происходит: 20 | ```python 21 | from zencad import * 22 | ``` 23 | В первой строчке мы импортируем в текущее пространство пространство имён zencad. В данном случае, нас интересуют функции `box`, `sphere`, `display`, `show`. 24 |
25 |
26 | 27 | 28 | ```python 29 | a = box(200, 200, 200, center = True) 30 | b = sphere(120) 31 | c = sphere(60) 32 | ``` 33 | Подготавливаем геометрические примитивы. Создаётся объект box с размерами 200x200x200 и смещением геометрического центра в начало координат. Также создаются две сферы радиусом 120 и 60. 34 |
35 |
36 | 37 | 38 | ```python 39 | model = a - b + c 40 | ``` 41 | Вычисляем модель с применением булевых операций. Сперва из куба будет вычтена большая сфера. Потом добавлена малая. Порядок слагаемых в данном случае важен, поскольку операции объединения и разности геометрических тел некомутативны. 42 |
43 |
44 | 45 | 46 | ```python 47 | display(model) 48 | ``` 49 | Функция display передаёт объект в сцену для последующего отображения. 50 |
51 |
52 | 53 | 54 | ```python 55 | show() 56 | ``` 57 | Отображаем виджет сцены. 58 | 59 | --------------------------- 60 | ## Если всё прошло благополучно: 61 | ![](../images/helloworld.png) 62 | -------------------------------------------------------------------------------- /mangen/HIDE/en/index.md: -------------------------------------------------------------------------------- 1 |
ZenCad.
2 | 3 |
4 |

Скриптовый CAD для праведных прогеров.

5 | ![](../images/generic/zencad-logo.png) 6 |
7 | 8 | ------------- 9 | ## Что это? 10 | _ZenCad_ - это библиотека параметрического 3д моделирования. библиотека исповедует идею создания 3д модели путём написания скрипта и ноги её растут из системы _OpenScad_. В отличие от _OpenScad_, библиотека использует геометрическое ядро граничного представления _OpenCascade_ и язык общего назначения _Python_. 11 | 12 | _ZenCad_ может использоваться как самостоятельная система быстрого прототипирования для целей макетирования или 3д печати, так и в комплексе с библиотеками экосистемы _Python_, в частности для построения 3д моделий на основе расчетов выполненных в таких системах как scipy и sympy. 13 | 14 | -------------- 15 | # Быстрый старт. 16 | 17 | ------------ 18 | ## Установка. 19 | ```sh 20 | python3 -m pip install zencad 21 | ``` 22 | 23 | -------------- 24 | ## Запуск графической оболочки. 25 | ```sh 26 | zencad 27 | 28 | # alternate: 29 | python3 -m pip zencad 30 | ``` 31 | 32 | ------------- 33 | ## HelloWorld 34 | ```python 35 | #!/usr/bin/env python3 36 | #coding: utf-8 37 | 38 | from zencad import * 39 | 40 | box = box(200, 200, 200, center = True) 41 | sphere1 = sphere(120) 42 | sphere2 = sphere(60) 43 | 44 | model = box - sphere1 + sphere2 45 | 46 | display(model) 47 | show() 48 | ``` 49 | 50 | --------- 51 | ## Ссылки 52 | github: [https://github.com/mirmik/zencad](https://github.com/mirmik/zencad) 53 | pypi: [https://pypi.org/project/zencad](https://pypi.org/project/zencad) 54 | 55 | -------------------------------------------------------------------------------- /mangen/HIDE/en/installation.md: -------------------------------------------------------------------------------- 1 | # Установка 2 | 3 | Система ZenCad протестирована на Linux (семейство Debian), Windows. 4 | 5 | ## Установка pypi 6 | ```python 7 | python3 -m pip install zencad 8 | ``` 9 | 10 | ## Особенности установки на различных ОС. 11 | ### Установка Windows. 12 | На текущий момент может понадобиться установка vcredist2019. 13 | 14 | ### Установка MacOS. 15 | Версия для MacOS в разработке. 16 | 17 | ### Установка standalone версии (Windows). 18 | StandAlone версия может быть найдена в [здесь](https://github.com/mirmik/zencad/releases). StandAlone версия может отстовать от основной ветки. 19 | 20 | ## Установка из исходного кода. 21 | Для установки из исходного кода потребуется собрать, или получить, собранными бинарные зависимости: 22 | * [pyservoce](https://github.com/mirmik/servoce) 23 | * [OpenCascade(необходимой версии)](https://www.opencascade.com/content/overview) 24 | Особенности компиляции под разные ОС могут различаться. 25 | 26 | -------------------------------------------------------------------------------- /mangen/HIDE/en/kinematic.md: -------------------------------------------------------------------------------- 1 | # Библиотека кинематики. 2 | 3 | Данная библиотека является дополнением к системе [сборок](assemble.html) и позволяет управлять перемещением элементов сборок в терминах обобщенных кинематических координат, а так же осуществлять некоторые действия на кинематическими цепями. 4 | 5 | Библиотека определяет дополнительные типы unit: 6 | 7 | zencad.libs.kinematic.rotator - поворотное звено 8 | zencad.libs.kinematic.actuator - актуаторное звено 9 | 10 | UNDER_CONSTRUCT -------------------------------------------------------------------------------- /mangen/HIDE/en/nav.md: -------------------------------------------------------------------------------- 1 | * [Main page](index.html) 2 | * [Helloworld example](helloworld.html) 3 | * [Installation](installation.html) 4 | * Basic conceptions 5 | * [Scripting CAD](scriptcad.html) 6 | * [Boundary representation](geomcore.html) 7 | * [Lazy evaluations](caching.html) 8 | * Basic primitives and utilities 9 | * [Solid primitives](prim3d.html) 10 | * [Plane primitives](prim2d.html) 11 | * [Lines and cycles](prim1d.html) 12 | * [Points, vectors, utilities](prim0d.html) 13 | * Transformations, geometric operations 14 | * [Aphine transform](trans0.html) 15 | * [Boolean operations](bool.html) 16 | * [Topologically dependent operations](fillet.html) 17 | * [Reference geometry](ops3d.html) 18 | * [Sweep operations](sweep.html) 19 | * [Triangulate and meshing](trimesh.html) 20 | * [Other operations](other.html) 21 | * Reflection and analysis 22 | * [Geometric reflection](reflect.html) 23 | * [Curve analysis](crvalgo.html) 24 | * [Surface analysis](surfalgo.html) 25 | * [Geometric properties](geomprop.html) 26 | * Visualization 27 | * [Displaying](show.html) 28 | * [Interactive object](interactive_object.html) 29 | * [Hierarchical models](assemble.html) 30 | * [Animation](animate.html) 31 | * [Graphical user interface](gui.html) 32 | * [Export/Import](expimp.html) 33 | * [Internal ZenCad's kitchen](internal.html) -------------------------------------------------------------------------------- /mangen/HIDE/en/nut.md: -------------------------------------------------------------------------------- 1 | # Библиотека резьбовых соединений 2 | UNDER_CONSTRUCT -------------------------------------------------------------------------------- /mangen/HIDE/en/ops3d.md: -------------------------------------------------------------------------------- 1 | # Ссылочная геометрия 2 | 3 | --- 4 | ## Cмещение. 5 | Путём смещения оболочек, строит утолщённое/утончённое тело на основании прототипа _proto_ и радиуса утолщения _r_. Если _r_ положительный, оболочка смещается наружу, если отрицательный - внутрь. 6 | 7 | Сигнатура: 8 | ```python 9 | offset(proto, r) 10 | ``` 11 | 12 | Пример: 13 | ```python 14 | offset(cone(r1=15,r2=10,h=20), r=5) 15 | ``` 16 | ![](../images/generic/offset0.png) 17 | 18 | --- 19 | ## Линейчатая поверхность. 20 | Строит грань, задаваемую линейчатое поверхностью, опирающейся на линии _a_, _b_. 21 | 22 | Сигнатура: 23 | ```python 24 | ruled(a, b) 25 | ``` 26 | 27 | Пример: 28 | ```python 29 | ruled(circle(r=20, wire=True), circle(r=20, wire=True).up(20)) 30 | ruled(circle(r=20, wire=True), circle(r=20, wire=True).rotZ(math.pi/2*3).up(20)) 31 | ruled( 32 | interpolate([(0,0),(-4,10),(4,20),(-6,30),(6,40)]), 33 | interpolate([(0,0),(-2,10),(2,20),(-4,30),(4,40)]).up(20), 34 | ) 35 | ``` 36 | 37 | ![](../images/generic/ruled0.png) 38 | ![](../images/generic/ruled1.png) 39 | ![](../images/generic/ruled2.png) 40 | ![](../images/generic/ruled3.png) 41 | 42 | --- 43 | ## Увязка 44 | Построение оболочки на масиве каркасных линий _profiles_. При активации опции _shell_ вместо твёрдого тела строится оболочка. Активации опции _smooth_ изменяет режим линейчатой поверхности на гладкую апроксимацию. При активной апроксимации опция _maxdegree_ ограничивает максимальную степень полинома. 45 | 46 | Сигнатура: 47 | ```python 48 | loft(profiles, smooth=False, shell=False, maxdegree=4) 49 | ``` 50 | 51 | Пример: 52 | ```python 53 | ``` 54 | 55 | ![](../images/generic/loft0.png) 56 | ![](../images/generic/loft1.png) 57 | ![](../images/generic/loft2.png) 58 | ![](../images/generic/loft3.png) 59 | ![](../images/generic/loft4.png) 60 | ![](../images/generic/loft5.png) 61 | -------------------------------------------------------------------------------- /mangen/HIDE/en/other.md: -------------------------------------------------------------------------------- 1 | # Прочие операции. 2 | 3 | В этом разделе перечислены операции не подходящие ни к одному другому разделу. 4 | 5 | ## unify 6 | Данная операция упрощает геометрическое представление объекта, путём удаления лишних рёбер и объединения гранией. 7 | 8 | Может выполняться над двумерными и трёхмерными объектами. 9 | 10 | Сигнатура: 11 | ```python 12 | unify(shp) 13 | ``` 14 | 15 | Пример: 16 | ```python 17 | unify(cylinder(r=10, h=10) + cylinder(r=10, h=10).move(5,5)) 18 | ``` 19 | 20 | | До | После | 21 | |---|---| 22 | | ![](../images/generic/unify0.png) | ![](../images/generic/unify1.png) | 23 | -------------------------------------------------------------------------------- /mangen/HIDE/en/platonic.md: -------------------------------------------------------------------------------- 1 | # Платоновы тела 2 | 3 | Построение платоновых тел. 4 | Библиотека основана на https://github.com/qalle2/plato.scad 5 | 6 | |Правильный многогранник|Число вершин|Число рёбер|Число граней|Число сторон у грани|Число рёбер примыкающих к вершине|Тип пространственной симметрии| 7 | |---|---|---|---|---|---|---| 8 | |Тетраэдр|4|6|4|3|3|Td| 9 | |Гексаэдр|8|12|6|4|3|Oh| 10 | |Октаэдр|6|12|8|3|4|Oh| 11 | |Додекаэдр|20|30|12|5|3|Ih| 12 | |Икосаэдр|12|30|20|3|5|Ih| 13 | 14 | Библиотека позволяет указывать размеры тел через радиус описанной окружности _r_ или через длину ребра _a_. 15 | 16 | Сигнатуры: 17 | ```python 18 | zencad.platonic.tetrahedron(r=1, a=None, shell=False) 19 | zencad.platonic.hexahedron(r=1, a=None, shell=False) 20 | zencad.platonic.octahedron(r=1, a=None, shell=False) 21 | zencad.platonic.dodecahedron(r=1, a=None, shell=False) 22 | zencad.platonic.icosahedron(r=1, a=None, shell=False) 23 | 24 | # Альтернативный синтаксис 25 | zencad.platonic.platonic(nfaces, r=1, a=None, shell=False) 26 | ``` 27 | 28 | Пример: 29 | ```python 30 | # Через радиус: 31 | tetrahedron(10) 32 | hexahedron(10) 33 | octahedron(r=10) 34 | dodecahedron(r=10) 35 | icosahedron(10) 36 | 37 | # Через длину ребра: 38 | icosahedron(a=10) 39 | 40 | # Альтернативный синтакис: 41 | zencad.platonic.platonic(4, 10) 42 | zencad.platonic.platonic(6, 10) 43 | zencad.platonic.platonic(8, 10) 44 | zencad.platonic.platonic(12, 10) 45 | zencad.platonic.platonic(20, 10) 46 | ``` 47 | 48 |
49 | ![](../images/generic/platonic0.png) 50 | ![](../images/generic/platonic1.png) 51 | ![](../images/generic/platonic2.png) 52 | ![](../images/generic/platonic3.png) 53 | ![](../images/generic/platonic4.png) 54 |
-------------------------------------------------------------------------------- /mangen/HIDE/en/prim0d.md: -------------------------------------------------------------------------------- 1 | # Точка, вектор, вспомогательные функции. 2 | 3 | В библиотеки ZenCad есть некоторые вспомогательные математические объекты и функции для работы с ними. 4 | 5 | --- 6 | ## Точка. 7 | Некоторые функции ZenCad используют в качестве параметров точки или массивы точек. Для создания объекта точки можно использовать функцию `point3`. Кроме того, часто функция может сама сформировать точки по списку или кортежу координат. 8 | ```python 9 | point3(0,3,6) 10 | 11 | #Equivalent calls 12 | interpolate([point3(0,0,0), point3(0,0,10), point3(10,0,10)]) 13 | interpolate([(0,0,0), (0,0,10), (10,0,10)]) 14 | interpolate(points([(0,0,0), (0,0,10), (10,0,10)])) 15 | ``` 16 | 17 | Точка может быть отображена функцией display, как соответствующая такой точке вершина. 18 | 19 | --- 20 | ## Вектор. 21 | Иногда кроме указаний точек используются объекты-векторы для указания направлений. Принцип работы с векторами аналогичен работе с точками. 22 | ```python 23 | vector3(1,2,3) 24 | 25 | interpolate(pnts=[(0,0,0), (0,0,10), (10,0,10)], tangs=[(0,0,1), (1,0,0), (0,1,0)]) 26 | ``` 27 | 28 | Вектор не может быть отображен непосредственно. 29 | 30 | --- 31 | ## Операции над точками и векторами. 32 | Точки и вектора могут использоваться в математических операциях в соответствиями с правилами линейной алгебры. 33 | 34 | ```python 35 | pnt - pnt -> vec 36 | pnt + vec -> pnt 37 | vec + vec -> vec 38 | vec - vec -> vec 39 | ``` 40 | 41 | --- 42 | ## Функции vectors, points. 43 | Функции vectors и points явно создают массивы точек из массивов координат. 44 | ```python 45 | points([(0,0,0), (0,0,10), (10,0,10)]) 46 | vectors([(0,0,1), (1,0,0), (0,1,0)]) 47 | ``` 48 | 49 | --- 50 | ## Пустое примитив. nullshape. 51 | Пустой примитив. Может участвовать в булевых операциях. 52 | 53 | Пример использования в цикле: 54 | ```python 55 | it = nullshape() 56 | for i in range(7): 57 | it = it + box(20).translate(10*i,10*i,10*i) 58 | 59 | #alternate: union([box(20).translate(10*i,10*i,10*i) for i in range(7)]) 60 | ``` 61 | 62 | --- 63 | ## Функция deg. 64 | API ZenCad использует радианы для задания углов. Использование градусов требует масштабирования численного коэффициента. Именно этим и занимается функция deg: 65 | `deg(180)` соответствует `math.pi`. 66 | 67 | Код функции deg: 68 | ```python 69 | def deg(grad): 70 | return float(grad) / 180.0 * math.pi 71 | ``` -------------------------------------------------------------------------------- /mangen/HIDE/en/reflect.md: -------------------------------------------------------------------------------- 1 | # Рефлексия 2 | Сложные геометрические объекты состоят из более простых. Данная группа функций и методов позволяет расскладывать сложные объекты на образующие их компоненты. 3 | 4 | Для работы с эими фунциями рекомендуется изучить топологическое устройство brep моделей в ядре _OpenCascade_. (Начать ознаклмление можно с раздела [Введение в BREP представление геометрических моделей](geomcore.html)) 5 | 6 | --------------------------- 7 | ## Массивы базовых объектов 8 | Это семейство методов позволяет извлечь и отфильтровать необходимые базовые объекты. 9 | 10 | Все методы имеют однотипную сигнатуру, возвращают массив объектов соответствующего типа. Необязательная опция _filter_ позволяет отфильтровать выборку по необходимому условию. 11 | ```python 12 | shape.vertices(filter=None) # -> [point3] 13 | shape.solids(filter=None) # -> [Shape; future:Solid] 14 | shape.faces(filter=None) # -> [Face] 15 | shape.edges(filter=None) # -> [Edge] 16 | shape.wires(filter=None) # -> [Shape; future:Wire] 17 | shape.shells(filter=None) # -> [Shape; future:Shell] 18 | shape.compounds(filter=None) # -> [Shape; future:Compound] 19 | shape.compsolids(filter=None) # -> [Shape; future:Compsolid] 20 | ``` 21 | 22 | --------------------------------------------------- 23 | ## Взятие базового объекта по методу ближайшей точки 24 | Иногда требуется извлечь из сложного объекта конкретный базовый объект. 25 | В этом случае можно использовать метод базовой точки. 26 | 27 | Следующие функции реализуют метод ближайшей точке и возвращают ближайший к _pnt_ базовый объект соответствующего типа, принадлежащий сложному объекту _shp_. 28 | 29 | ```python 30 | near_edge(shp, pnt) # -> Edge 31 | near_face(shp, pnt) # -> Face 32 | near_vertex(shp, pnt) # -> point3 33 | ``` -------------------------------------------------------------------------------- /mangen/HIDE/en/scriptcad.md: -------------------------------------------------------------------------------- 1 | # Скриптовые CAD системы. 2 | 3 | Скриптовые CAD стоят особняком от общепринятых интерактивных CAD. Если в интерактивном CAD вы создаёте модель при помощи мыши и набора инструментов на панели слева или сверху, то в скриптовом CAD вы пишете программу, по которой строится ваша модель. Таким образом генерируемая модель по умолчанию получает хорошую параметрируемость и регуляризацию. Если при смене базовых параметров геометрии в интерактивном CAD вам может потребоваться перекроить всю модель, в скриптовом CAD вам потребуется просто заменить пару констант. 4 | 5 | С другой стороны скриптовый CAD может быть не очень дружелюбен к пользователю. Нужно иметь определённый навык для чтения модели в виде програмного кода. Тем не менее, успех OpenScad показывает необходимость человечества в инструментах такого типа. 6 | 7 | Скриптовый CAD хорош в написании деталей машин и прочих изделиях с точно выверенными и обоснованными поверхностями. А вот попытка нарисовать на нем Венеру Милосскую ни к чему хорошему не приведет. Для художественных целей существует другой класс систем. 8 | 9 | Строго говоря, хотя в девизе zencad написано "CAD system for righteous programmers", zencad by design является в большей степени библиотекой с функциональность cad, нежели законченной CAD системой. zencad проектировался как инструмент, который может интегрироваться с библиотеками экосистемы python с целью решения задач построения аналитических поверхностей, визуализации данных полунатурного моделирования и прочих задач, предполагающих интеграцию с зоопарком библиотек экосистемы python. 10 | 11 | ![](../images/car.png) -------------------------------------------------------------------------------- /mangen/HIDE/en/surfalgo.md: -------------------------------------------------------------------------------- 1 | # Классы поверхностей. 2 | 3 | ----------------- 4 | ## Классы поверхностей. 5 | В ZenCad существуют следующие классы поверхностей: 6 | 7 | * Face 8 | * Surface (NotReleased) 9 | 10 | -------------------- 11 | ## Поиск нормали 12 | В точке поверхности, соответствующей параметрам _u_, _v_. По умолчанию _u_ и _v_ равны нулю. 13 | 14 | Сигнатура: 15 | ```python 16 | surf.normal(u=0,v=0) 17 | ``` 18 | 19 | -------------------------------------------------------------------------------- /mangen/en/nav.md: -------------------------------------------------------------------------------- 1 | * [Main page](index.html) 2 | * [Helloworld example](helloworld.html) 3 | * [Installation](installation.html) 4 | * Basic conceptions 5 | * [Scripting CAD](scriptcad.html) 6 | * [Boundary representation](geomcore.html) 7 | * [Lazy evaluations](caching.html) 8 | * Basic primitives and utilities 9 | * [Solid primitives](prim3d.html) 10 | * [Plane primitives](prim2d.html) 11 | * [Lines and cycles](prim1d.html) 12 | * [Points, vectors, utilities](prim0d.html) 13 | * Transformations, geometric operations 14 | * [Aphine transform](trans0.html) 15 | * [Boolean operations](bool.html) 16 | * [Topologically dependent operations](fillet.html) 17 | * [Reference geometry](ops3d.html) 18 | * [Sweep operations](sweep.html) 19 | * [Triangulate and meshing](trimesh.html) 20 | * [Other operations](other.html) 21 | * Reflection and analysis 22 | * [Geometric reflection](reflect.html) 23 | * [Curve analysis](crvalgo.html) 24 | * [Surface analysis](surfalgo.html) 25 | * [Geometric properties](geomprop.html) 26 | * [Bounding box](bbox.html) 27 | * Visualization 28 | * [Displaying](show.html) 29 | * [Interactive object](interactive_object.html) 30 | * [Hierarchical models](assemble.html) 31 | * [Animation](animate.html) 32 | * [Graphical user interface](gui.html) 33 | * [Export/Import](expimp.html) 34 | * [Internal ZenCad's kitchen](internal.html) 35 | -------------------------------------------------------------------------------- /mangen/images/blacktocat.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/mangen/images/blacktocat.png -------------------------------------------------------------------------------- /mangen/images/boolean.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/mangen/images/boolean.png -------------------------------------------------------------------------------- /mangen/images/car.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/mangen/images/car.png -------------------------------------------------------------------------------- /mangen/images/gui.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/mangen/images/gui.png -------------------------------------------------------------------------------- /mangen/images/helloworld.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/mangen/images/helloworld.png -------------------------------------------------------------------------------- /mangen/ru/animate.md: -------------------------------------------------------------------------------- 1 | :ru 2 | # Анимация 3 | Графический интерфейс позволяет анимировать отображаемую сцену. 4 | Пример: 5 | :en 6 | # Animation 7 | The graphical interface allows you to animate the displayed scene. 8 | Example: 9 | :: 10 | 11 | ```python3 12 | s = box(10, center=True) 13 | controller = disp(s) 14 | nulltime = time.time() 15 | 16 | def animate(widget): 17 | trans = rotateZ(time.time() - nulltime) * right(30) 18 | controller.relocate(trans) 19 | 20 | show(animate=animate) 21 | ``` 22 | 23 | :ru 24 | Здесь мы используем специальную функцию анимации `animate`, которая, используя объект контроллер, возвращенный функцией disp, в зависимости от текущего момента времени обновляет местоположение контролируемого объекта. 25 | В качестве параметра метода `relocate` выступает объект преобразования. (Подробнее в [Преобразования](trans0.html), [Комбинации преобразований](trans1.html)) 26 | 27 | Кроме параметра `animate` функция show имеет связанные параметры `preanimate` и `close_handle`. `preanimate` принимает функцию, вызывающуюся один раз до первой итерации `animate`, но уже после создания графического окружения. `close_handle` вызывается как обработчик при завершении процесса. 28 | :en 29 | Here we use a special animation function `animate`, which, using the controller object returned by the disp function, updates the location of the controlled object based on the current moment in time. 30 | The transformation object is used as a parameter of the `relocate` method. (More details in [Transformations](trans0.html), [Transformations](trans1.html)) 31 | 32 | In addition to the `animate` parameter, the show function has associated` preanimate` and `close_handle` parameters. `preanimate` takes a function that is called once before the first iteration of` animate`, but after the graphical environment has been created. `close_handle` is called as a handler when the process ends. 33 | :: -------------------------------------------------------------------------------- /mangen/ru/bbox.md: -------------------------------------------------------------------------------- 1 | :ru 2 | # Ограничивающая коробка 3 | 4 | Ограничивающая коробка - это это минимальный основанный на осях Ox, Oy, Oz параллелепипед, описывающий геометрическую форму shape. 5 | :en 6 | # Bounding box 7 | 8 | The bounding box is a minimal Ox, Oy, Oz-based box that describes the geometric shape shape. 9 | :: 10 | 11 | --- 12 | :ru 13 | ## shape.bbox 14 | Построить ограничивающую коробку на основе формы shape. 15 | :en 16 | ## shape.bbox 17 | Construct a bounding box based on the shape. 18 | :: 19 | 20 | Пример 21 | ```python 22 | shp = sphere(10) 23 | bbox = shp.bbox() 24 | ``` 25 | 26 | :ru 27 | ## Поля. 28 | :en 29 | ## Fields. 30 | :: 31 | ```python3 32 | bbox.xmin 33 | bbox.ymin 34 | bbox.zmin 35 | bbox.xmax 36 | bbox.ymax 37 | bbox.zmax 38 | ``` 39 | 40 | :ru 41 | ## Методы. 42 | :en 43 | ## Methods. 44 | :: 45 | bbox.xrange() 46 | bbox.yrange() 47 | bbox.zrange() 48 | 49 | :ru 50 | ## Построить коробку как форму. 51 | :en 52 | ## To Shape. 53 | :: 54 | Пример 55 | ```python 56 | shp = sphere(10) 57 | bbox = shp.bbox() 58 | disp(bbox.shape()) 59 | ``` 60 | -------------------------------------------------------------------------------- /mangen/ru/geomprop.md: -------------------------------------------------------------------------------- 1 | :ru 2 | # Геометрические характеристики. 3 | Раздел посвящен измерению геометрических характеристик конструируемой геометрии. 4 | 5 | Поскольку понятия плотности и масштаба весьма эфемерны для вычислительной библиотеки, все вычисления проводятся в условных единицах. Перевод величин в систему си требует дополнительных вычислений. 6 | :en 7 | # Geometric characteristics. 8 | The section is devoted to measuring the geometric characteristics of the constructed geometry. 9 | 10 | Since the concepts of density and scale are very ephemeral for the computational library, all calculations are carried out in arbitrary units. Converting values to the si system requires additional calculations. 11 | :: 12 | 13 | ---------------------------------------- 14 | :ru 15 | ## Встроенные методы 16 | Shape имеет ряд методов, позволяющих запросить геометрическую информацию. 17 | :en 18 | ## Built-in methods 19 | Shape has a number of methods for querying geometric information. 20 | :: 21 | 22 | ---- 23 | :ru 24 | ### Центр масс. 25 | :en 26 | :: 27 | ```python 28 | shape.center() -> point3 29 | shape.cmradius() -> vector3 30 | ``` 31 | 32 | ---- 33 | :ru 34 | ### Объём. 35 | :en 36 | ### Center of mass. 37 | :: 38 | ```python 39 | shape.mass() -> float 40 | ``` 41 | 42 | ---- 43 | :ru 44 | ### Матрица инерции. 45 | :en 46 | ### Matrix of inertia. 47 | :: 48 | ```python 49 | shape.matrix_of_inertia() -> matrix33 50 | ``` 51 | 52 | --- 53 | :ru 54 | ### Статические моменты. 55 | :en 56 | ### Static moments. 57 | :: 58 | ```python 59 | shape.static_moments() -> float, float, float 60 | ``` 61 | 62 | --- 63 | :ru 64 | ### Момент инерции относительно оси. 65 | :en 66 | ### Moment of inertia about the axis. 67 | :: 68 | UNDER_CONSTRUCTION 69 | 70 | ------ 71 | :ru 72 | ### Радиус инерции. 73 | :en 74 | ### Radius of gyration. 75 | :: 76 | UNDER_CONSTRUCTION 77 | 78 | ----------------------------------------- 79 | :ru 80 | ## Измерение систем тел 81 | :en 82 | ## Measuring body systems 83 | :: 84 | UNDER_CONSTRUCT 85 | -------------------------------------------------------------------------------- /mangen/ru/installation.md: -------------------------------------------------------------------------------- 1 | :ru 2 | # Установка 3 | 4 | Система ZenCad протестирована на Linux (семейство Debian), Windows. 5 | 6 | ## Установка pypi 7 | ```python 8 | python3 -m pip install zencad 9 | ``` 10 | 11 | ## Особенности установки на различных ОС. 12 | ### Установка Windows. 13 | На текущий момент может понадобиться установка vcredist2019. 14 | 15 | ### Установка MacOS. 16 | Версия для MacOS в разработке. 17 | 18 | ### Установка standalone версии (Windows). 19 | StandAlone версия может быть найдена в [здесь](https://github.com/mirmik/zencad/releases). StandAlone версия может отстовать от основной ветки. 20 | 21 | ## Установка из исходного кода. 22 | Для установки из исходного кода потребуется собрать, или получить, собранными бинарные зависимости: 23 | :en 24 | # Installation 25 | 26 | ZenCad system is tested on Linux (Debian family), Windows. 27 | 28 | ## Installing pypi 29 | ```python 30 | python3 -m pip install zencad 31 | ``` 32 | 33 | ## Features of installation on various OS. 34 | ### Installing Windows. 35 | At the moment, you may need to install vcredist2019. 36 | 37 | ### Installing MacOS. 38 | MacOS version in development. 39 | 40 | ### Installing standalone version (Windows). 41 | The StandAlone version can be found at [here](https://github.com/mirmik/zencad/releases). The StandAlone version may lag behind the mainline. 42 | 43 | ## Installing from source. 44 | To install from the source code, you need to build, or get the compiled binary dependencies: 45 | :: 46 | 47 | * [pythonocc-core](https://github.com/tpaviot/pythonocc-core) 48 | * [OpenCascade](https://www.opencascade.com/content/overview) -------------------------------------------------------------------------------- /mangen/ru/kinematic.md: -------------------------------------------------------------------------------- 1 | # Библиотека кинематики. 2 | 3 | Данная библиотека является дополнением к системе [сборок](assemble.html) и позволяет управлять перемещением элементов сборок в терминах обобщенных кинематических координат, а так же осуществлять некоторые действия на кинематическими цепями. 4 | 5 | Библиотека определяет дополнительные типы unit: 6 | 7 | zencad.libs.kinematic.rotator - поворотное звено 8 | zencad.libs.kinematic.actuator - актуаторное звено 9 | 10 | UNDER_CONSTRUCT -------------------------------------------------------------------------------- /mangen/ru/nav.md: -------------------------------------------------------------------------------- 1 | * [Главная страница](index.html) 2 | * [Разбор helloworld](helloworld.html) 3 | * [Установка](installation.html) 4 | * Основные концепции 5 | * [Скриптовый CAD](scriptcad.html) 6 | * [BREP представление](geomcore.html) 7 | * [Ленивые вычисления](caching.html) 8 | * Базовые примитивы и утилиты 9 | * [Объёмные примитивы](prim3d.html) 10 | * [Плоские примитивы](prim2d.html) 11 | * [Линии и циклы](prim1d.html) 12 | * [Точки, вектора, утилиты](prim0d.html) 13 | * Преобразования, операции над геометрическими телами 14 | * [Афинные преобразования](trans0.html) 15 | * [Булевы операции](bool.html) 16 | * [Топологически зависимые преобразования](fillet.html) 17 | * [Ссылочная геометрия](ops3d.html) 18 | * [Траекторная развёртка](sweep.html) 19 | * [Триангуляция и меш](trimesh.html) 20 | * [Прочие операции](other.html) 21 | * Рефлексия и анализ 22 | * [Рефлексия геометрии](reflect.html) 23 | * [Анализ кривых](crvalgo.html) 24 | * [Анализ поверхностей](surfalgo.html) 25 | * [Геометрические характеристики](geomprop.html) 26 | * [Ограничивающая коробка](bbox.html) 27 | * Визуализация 28 | * [Отображение](show.html) 29 | * [Интерактивный объект](interactive_object.html) 30 | * [Иерархические модели](assemble.html) 31 | * [Анимация](animate.html) 32 | * [Графический интерфейс](gui.html) 33 | * [Экспорт/Импорт](expimp.html) 34 | * [Внутренняя кухня ZenCad](internal.html) 35 | -------------------------------------------------------------------------------- /mangen/ru/other.md: -------------------------------------------------------------------------------- 1 | :ru 2 | # Прочие операции. 3 | 4 | В этом разделе перечислены операции не подходящие ни к одному другому разделу. 5 | 6 | --- 7 | ## unify 8 | Данная операция упрощает геометрическое представление объекта, путём удаления лишних рёбер и объединения гранией. 9 | 10 | Может выполняться над двумерными и трёхмерными объектами. 11 | :en 12 | # Other operations. 13 | 14 | This section lists operations that do not fit into any other section. 15 | 16 | --- 17 | ## unify 18 | This operation simplifies the geometric representation of an object by removing unnecessary edges and merging with a face. 19 | 20 | Can be performed on 2D and 3D objects. 21 | :: 22 | 23 | Сигнатура: 24 | ```python 25 | unify(shp) 26 | ``` 27 | 28 | Пример: 29 | ```python 30 | unify(cylinder(r=10, h=10) + cylinder(r=10, h=10).move(5,5)) 31 | ``` 32 | :ru 33 | | До | После | 34 | :en 35 | | Before | After | 36 | :: 37 | |---|---| 38 | | ![](../images/generic/unify0.png) | ![](../images/generic/unify1.png) | 39 | -------------------------------------------------------------------------------- /mangen/ru/surfalgo.md: -------------------------------------------------------------------------------- 1 | :ru 2 | # Классы поверхностей. 3 | :en 4 | # Classes of surfaces. 5 | :: 6 | 7 | ----------------- 8 | :ru 9 | ## Классы поверхностей. 10 | В ZenCad существуют следующие классы поверхностей: 11 | :en 12 | ## Surface classes. 13 | The following surface classes exist in ZenCad: 14 | :: 15 | 16 | * Face 17 | * Surface 18 | 19 | -------------------- 20 | :ru 21 | ## Поиск нормали 22 | В точке поверхности, соответствующей параметрам _u_, _v_. По умолчанию _u_ и _v_ равны нулю. 23 | :en 24 | ## Find normal 25 | At the point on the surface corresponding to the parameters _u_, _v_. By default, _u_ and _v_ are zero. 26 | :: 27 | 28 | Сигнатура: 29 | ```python 30 | surf.normal(u=0,v=0) 31 | ``` 32 | 33 | -------------------------------------------------------------------------------- /mangen/writer.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | # coding: utf-8 3 | 4 | import dominate 5 | import markdown2 6 | import os 7 | import shutil 8 | 9 | 10 | def build_file(path, doc): 11 | dirpath = os.path.join("build", os.path.dirname(path)) 12 | if not os.path.exists(dirpath): 13 | os.makedirs(dirpath) 14 | 15 | f = open(os.path.join("build", path), "w") 16 | f.write(str(doc)) 17 | 18 | 19 | def copy_file(dst, src): 20 | shutil.copyfile(src=src, dst=os.path.join("build", dst)) 21 | 22 | 23 | def remove_file(path): 24 | os.remove(os.path.join("build", path)) 25 | 26 | 27 | def copy_tree(dst, src): 28 | cmd = "cp -rf {src} {dst}".format(src=src, dst=os.path.join("build", dst)) 29 | os.system(cmd) 30 | -------------------------------------------------------------------------------- /requirements.txt: -------------------------------------------------------------------------------- 1 | psutil 2 | numpy 3 | pillow 4 | evalcache>=1.14.0 5 | requests 6 | wheel 7 | zenframe 8 | six -------------------------------------------------------------------------------- /setup.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | 3 | from wheel.bdist_wheel import bdist_wheel as bdist_wheel_ 4 | from setuptools import setup, Extension, Command 5 | from distutils.util import get_platform 6 | 7 | import glob 8 | import sys 9 | import os 10 | 11 | directory = os.path.dirname(os.path.realpath(__file__)) 12 | 13 | 14 | setup( 15 | name="zencad", 16 | packages=["zencad"], 17 | python_requires='>3.6.0', 18 | version="1.3.3", 19 | license="MIT", 20 | description="CAD system for righteous zen programmers ", 21 | author="mirmik", 22 | author_email="mirmikns@yandex.ru", 23 | url="https://github.com/mirmik/zencad", 24 | long_description=open(os.path.join( 25 | directory, "README.md"), "r", encoding="utf8").read(), 26 | long_description_content_type="text/markdown", 27 | keywords=["testing", "cad"], 28 | classifiers=[], 29 | package_data={ 30 | "zencad": [ 31 | "industrial-robot.svg", 32 | "zencad_logo.png", 33 | "bird.jpg", 34 | "techpriest.jpg", 35 | "geom/*", 36 | "geom2/*", 37 | "convert/*", 38 | "libs/*", 39 | "gui/*", 40 | "interactive/*", 41 | "convert/*", 42 | "internal_models/*", 43 | "examples/*", 44 | "examples/**/*", 45 | "examples/**/**/*", 46 | ] 47 | }, 48 | include_package_data=True, 49 | install_requires=[ 50 | "psutil", 51 | "numpy", 52 | "pillow", 53 | "evalcache>=1.14.0", 54 | 'zenframe', 55 | "requests", 56 | "six", 57 | ], 58 | extras_require={ 59 | 'gui': [ 60 | 'PyQt5', 61 | 'PyQt5-sip', 62 | "pyopengl" 63 | ] 64 | }, 65 | entry_points={"console_scripts": [ 66 | "zencad=zencad.__main__:main" 67 | ]}, 68 | ) 69 | -------------------------------------------------------------------------------- /tools/build_dists.sh: -------------------------------------------------------------------------------- 1 | ./setup.py bdist_wheel 2 | ./setup.py sdist 3 | -------------------------------------------------------------------------------- /tools/clean.sh: -------------------------------------------------------------------------------- 1 | git clean -fxd -------------------------------------------------------------------------------- /tools/pep8-format.sh: -------------------------------------------------------------------------------- 1 | set -x 2 | 3 | for file in ./**/*.py; do 4 | autopep8 --in-place "$file" 5 | done 6 | 7 | for file in ./**/**/*.py; do 8 | autopep8 --in-place "$file" 9 | done -------------------------------------------------------------------------------- /tools/pre-commit: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | 3 | import os 4 | import re 5 | import shutil 6 | import subprocess 7 | import sys 8 | import tempfile 9 | 10 | 11 | def system(*args, **kwargs): 12 | print("PRE-HOOK: invoke:", args, kwargs) 13 | kwargs.setdefault('stdout', subprocess.PIPE) 14 | proc = subprocess.Popen(args, **kwargs) 15 | out, err = proc.communicate() 16 | return out 17 | 18 | 19 | def main(): 20 | modified = re.compile('^[AM]+\s+(?P.*\.py)', re.MULTILINE) 21 | files = system('git', 'status', '--porcelain') 22 | print("PRE-HOOK: autopep8 for files:", files) 23 | files = modified.findall(files.decode("utf-8")) 24 | 25 | for f in files: 26 | output = system('autopep8', f, '--in-place') 27 | 28 | if output: 29 | print(output) 30 | sys.exit(-1) 31 | 32 | system("git", "add", f) 33 | 34 | 35 | if __name__ == '__main__': 36 | main() -------------------------------------------------------------------------------- /tools/publish.sh: -------------------------------------------------------------------------------- 1 | python3 -m twine upload dist/* --repository-url https://upload.pypi.org/legacy/ 2 | -------------------------------------------------------------------------------- /tools/pyinstaller_invoke.sh: -------------------------------------------------------------------------------- 1 | ./dist/ZenCad/ZenCad -------------------------------------------------------------------------------- /tools/pyinstaller_make.sh: -------------------------------------------------------------------------------- 1 | rm -r dist build 2 | pyinstaller __main__.spec -------------------------------------------------------------------------------- /tools/reinstall_local.sh: -------------------------------------------------------------------------------- 1 | ./setup.py install --user -------------------------------------------------------------------------------- /utest/api.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | # coding:utf-8 3 | 4 | import sys 5 | import traceback 6 | print("api.py") 7 | 8 | 9 | sys.path.insert(0, "..") 10 | 11 | print("import") 12 | try: 13 | print("import zenframe") 14 | import zenframe 15 | 16 | print("import traceback") 17 | import traceback 18 | 19 | print("import unittest") 20 | import unittest 21 | 22 | print("import PyQt5") 23 | import PyQt5 24 | 25 | print("import zencad") 26 | import zencad 27 | 28 | print("import tests") 29 | import prim1d_test 30 | import prim2d_test 31 | import prim3d_test 32 | import ops3d_test 33 | import ops1d2d_test 34 | import boolean_test 35 | import math_test 36 | import trans_test 37 | import general_transformation_test 38 | import curve3_test 39 | import curve2_test 40 | import make_test 41 | #import widgets_test 42 | import convert 43 | import reflection 44 | except Exception as ex: 45 | print(ex) 46 | traceback.print_exc() 47 | 48 | 49 | print("import ... finish") 50 | 51 | 52 | def execute_test(test): 53 | print() 54 | print("TEST:") 55 | result = unittest.TextTestRunner(verbosity=2).run( 56 | unittest.TestLoader().loadTestsFromModule(test) 57 | ) 58 | 59 | if len(result.errors) != 0 or len(result.failures) != 0: 60 | sys.exit(-1) 61 | 62 | 63 | if __name__ == "__main__": 64 | print("main") 65 | # execute_test(widgets_test) # Fault on travis (Gui compatible) 66 | execute_test(math_test) 67 | execute_test(reflection) 68 | execute_test(prim1d_test) 69 | execute_test(prim2d_test) 70 | execute_test(prim3d_test) 71 | execute_test(ops3d_test) 72 | execute_test(ops1d2d_test) 73 | execute_test(boolean_test) 74 | execute_test(trans_test) 75 | execute_test(general_transformation_test) 76 | execute_test(curve3_test) 77 | execute_test(curve2_test) 78 | execute_test(convert) 79 | execute_test(make_test) 80 | -------------------------------------------------------------------------------- /utest/boolean_test.py: -------------------------------------------------------------------------------- 1 | import unittest 2 | import zencad 3 | from functools import cmp_to_key 4 | import evalcache 5 | import zencad.util 6 | 7 | 8 | def rounded_list(a): 9 | return [round(f, 5) for f in a] 10 | 11 | 12 | def lexsort(a): 13 | a = evalcache.unlazy_if_need(a) 14 | 15 | def comparator(a, b): 16 | return 1 if a > b else -1 17 | 18 | a = [zencad.util.point3(round(f.x, 4), round( 19 | f.y, 4), round(f.z, 4)) for f in a] 20 | return sorted(a, key=cmp_to_key(comparator)) 21 | 22 | 23 | class BooleanProbe(unittest.TestCase): 24 | def setUp(self): 25 | zencad.lazy.encache = False 26 | zencad.lazy.decache = False 27 | zencad.lazy.fastdo = True 28 | 29 | def test_union_probe(self): 30 | a = zencad.box(10) 31 | b = zencad.sphere(10) 32 | c = zencad.cone(5, 2, h=20) 33 | 34 | f1 = zencad.union([a, b, c]) 35 | f2 = a + b + c 36 | f3 = zencad.union([c, a, b]) 37 | f4 = c + a + b 38 | 39 | self.assertEqual(lexsort(f1.vertices()), lexsort(f2.vertices())) 40 | self.assertEqual(lexsort(f1.vertices()), lexsort(f3.vertices())) 41 | #self.assertEqual(lexsort(f1.vertices()), lexsort(f4.vertices())) 42 | 43 | def test_intersect_probe(self): 44 | a = zencad.box(10) 45 | b = zencad.sphere(10) 46 | c = zencad.cone(5, 2, h=20) 47 | 48 | f1 = zencad.intersect([a, b, c]) 49 | f2 = a ^ b ^ c 50 | f3 = zencad.intersect([c, a, b]) 51 | f4 = c ^ a ^ b 52 | 53 | #self.assertEqual(lexsort(f1.vertices()), lexsort(f2.vertices())) 54 | #self.assertEqual(lexsort(f1.vertices()), lexsort(f3.vertices())) 55 | #self.assertEqual(lexsort(f1.vertices()), lexsort(f4.vertices())) 56 | 57 | def test_difference_probe(self): 58 | a = zencad.box(10) 59 | b = zencad.sphere(10) 60 | c = zencad.cone(5, 2, h=20) 61 | 62 | f1 = zencad.difference([a, b, c]) 63 | f2 = a - b - c 64 | f3 = zencad.difference([c, a, b]) 65 | f4 = c - a - b 66 | 67 | #self.assertEqual(lexsort(f1.vertices()), lexsort(f2.vertices())) 68 | #self.assertEqual(lexsort(f3.vertices()), lexsort(f4.vertices())) 69 | -------------------------------------------------------------------------------- /utest/convert.py: -------------------------------------------------------------------------------- 1 | import unittest 2 | import zencad 3 | from functools import cmp_to_key 4 | import evalcache 5 | import zencad.util 6 | import os 7 | 8 | import tempfile 9 | 10 | 11 | class ConvertProbe(unittest.TestCase): 12 | def setUp(self): 13 | zencad.lazy.encache = False 14 | zencad.lazy.decache = False 15 | zencad.lazy.fastdo = True 16 | 17 | def test_stl_probe(self): 18 | zencad.to_stl(zencad.box(10), os.path.join( 19 | tempfile.gettempdir(), "tempstl.stl"), 0.01) 20 | 21 | def test_brep_probe(self): 22 | zencad.to_brep(zencad.box(10), os.path.join( 23 | tempfile.gettempdir(), "tempbrep.brep")) 24 | m = zencad.from_brep(os.path.join( 25 | tempfile.gettempdir(), "tempbrep.brep")) 26 | 27 | self.assertEqual(len(m.unlazy().vertices()), 8) 28 | -------------------------------------------------------------------------------- /utest/curve2_test.py: -------------------------------------------------------------------------------- 1 | import unittest 2 | import zencad 3 | import numpy 4 | import math 5 | 6 | 7 | class Curve2(unittest.TestCase): 8 | def setUp(self): 9 | zencad.lazy.encache = False 10 | zencad.lazy.decache = False 11 | zencad.lazy.fastdo = True 12 | 13 | def test_api(self): 14 | print("TODO Curve2") 15 | -------------------------------------------------------------------------------- /utest/curve3_test.py: -------------------------------------------------------------------------------- 1 | import unittest 2 | import zencad 3 | import numpy 4 | import math 5 | 6 | 7 | class Curve3(unittest.TestCase): 8 | def setUp(self): 9 | zencad.lazy.encache = False 10 | zencad.lazy.decache = False 11 | zencad.lazy.fastdo = True 12 | 13 | def test_api(self): 14 | a = zencad.interpolate([(0, 0, 0), (0, 0, 1)], [ 15 | (0, 0, 1), (0, 0, 1)], closed=False) 16 | b = zencad.interpolate([(0, 0, 0), (0, 0, 1)], closed=False) 17 | 18 | self.assertEqual(a.value(0), zencad.point3(0, 0, 0)) 19 | self.assertEqual(a.value(1), zencad.point3(0, 0, 1)) 20 | self.assertEqual(a.value(0.5), zencad.point3(0, 0, 0.5)) 21 | 22 | def test_hadaptor(self): 23 | a = zencad.interpolate([(0, 0, 0), (0, 0, 1)], [ 24 | (0, 0, 1), (0, 0, 1)], closed=False) 25 | crv = zencad.curve.Curve(a.Curve()) 26 | hadaptor = crv.HCurveAdaptor() 27 | 28 | 29 | def test_law_sweep(self): 30 | import zencad.geom.sweep_law as sl 31 | a = zencad.interpolate([(0, 0, 0), (0, 0, 1)], [ 32 | (0, 0, 1), (0, 0, 1)], closed=False) 33 | crv = zencad.curve.Curve(a.Curve()) 34 | trilaw = sl.law_corrected_frenet_trihedron() 35 | sl.law_spine_and_trihedron(crv, trilaw) 36 | -------------------------------------------------------------------------------- /utest/examples.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | 3 | import zencad 4 | import sys 5 | import os 6 | import subprocess 7 | 8 | fast = False 9 | if "--fast" in sys.argv: 10 | fast = True 11 | 12 | examples = zencad.util.examples_paths(root="../zencad/examples") 13 | 14 | if fast or "TRAVIS_OS_NAME" in os.environ: 15 | print("Travis. Filter examples.") 16 | examples = [e for e in examples if not "Embeded" in e] 17 | examples = [e for e in examples if not "Integration" in e] 18 | examples = [e for e in examples if not "Models/logo" in e] 19 | 20 | 21 | for epath in examples: 22 | cmd = sys.executable + " -m zencad --no-show " + epath 23 | print(cmd) 24 | 25 | exit_code = subprocess.call(cmd, shell=True) 26 | if exit_code != 0: 27 | print(exit_code) 28 | raise Exception("Error in example {0}".format(epath)) 29 | -------------------------------------------------------------------------------- /utest/general_transformation_test.py: -------------------------------------------------------------------------------- 1 | import unittest 2 | import zencad 3 | import math 4 | 5 | 6 | def early(a, b): 7 | if abs(a.x - b.x) > 0.0001: 8 | return False 9 | if abs(a.y - b.y) > 0.0001: 10 | return False 11 | if abs(a.z - b.z) > 0.0001: 12 | return False 13 | return True 14 | 15 | 16 | def vertex_set_issame(a, b): 17 | for x in a: 18 | for y in b: 19 | if early(x, y): 20 | break 21 | else: 22 | return False 23 | 24 | for x in b: 25 | for y in a: 26 | if early(x, y): 27 | break 28 | else: 29 | return False 30 | 31 | return True 32 | 33 | 34 | class GeneralTransformation(unittest.TestCase): 35 | def setUp(self): 36 | zencad.lazy.encache = False 37 | zencad.lazy.decache = False 38 | zencad.lazy.fastdo = True 39 | 40 | def test_scale(self): 41 | b = zencad.box(10, 10, 10) 42 | t = zencad.box(20, 30, 40) 43 | scale = zencad.scaleXYZ(2, 3, 4) 44 | 45 | r = scale(b) 46 | r = b.transform(scale) 47 | 48 | self.assertTrue(vertex_set_issame(r.vertices(), t.vertices())) 49 | 50 | def test_scaleX(self): 51 | b = zencad.box(10, 10, 10) 52 | t = zencad.box(20, 10, 10) 53 | scale = zencad.scaleX(2) 54 | 55 | r = scale(b) 56 | r = b.transform(scale) 57 | 58 | self.assertTrue(vertex_set_issame(r.vertices(), t.vertices())) 59 | 60 | def test_scaleY(self): 61 | b = zencad.box(10, 10, 10) 62 | t = zencad.box(10, 30, 10) 63 | scale = zencad.scaleY(3) 64 | 65 | r = scale(b) 66 | r = b.transform(scale) 67 | 68 | self.assertTrue(vertex_set_issame(r.vertices(), t.vertices())) 69 | 70 | def test_scaleZ(self): 71 | b = zencad.box(10, 10, 10) 72 | t = zencad.box(10, 10, 40) 73 | scale = zencad.scaleZ(4) 74 | 75 | r = scale(b) 76 | r = b.transform(scale) 77 | 78 | self.assertTrue(vertex_set_issame(r.vertices(), t.vertices())) 79 | -------------------------------------------------------------------------------- /utest/make_test.py: -------------------------------------------------------------------------------- 1 | import unittest 2 | import zencad 3 | 4 | 5 | class MakeProbber(unittest.TestCase): 6 | def setUp(self): 7 | zencad.lazy.encache = False 8 | zencad.lazy.decache = False 9 | zencad.lazy.fastdo = True 10 | 11 | def test_make_wire(self): 12 | s0 = zencad.wire.segment((0,0,0), (1,0,0)) 13 | s1 = zencad.wire.segment((1,0,0), (1,1,0)) 14 | s2 = zencad.wire.segment((1,1,0), (0,1,0)) 15 | w = zencad.wire.make_wire([s0, s1, s2]) 16 | 17 | def test_make_face(self): 18 | s0 = zencad.wire.segment((0,0,0), (1,0,0)) 19 | s1 = zencad.wire.segment((1,0,0), (1,1,0)) 20 | s2 = zencad.wire.segment((1,1,0), (0,1,0)) 21 | s3 = zencad.wire.segment((0,1,0), (0,0,0)) 22 | w = zencad.wire.make_wire([s0, s1, s2, s3]) 23 | f = zencad.face.fill(w) 24 | 25 | def test_make_shell(self): 26 | sphere = zencad.sphere(10) 27 | face = sphere.faces()[0] 28 | self.assertTrue(face.shapetype() == "face") 29 | shell = zencad.geom.shell.make_shell([face]) -------------------------------------------------------------------------------- /utest/ops1d2d_test.py: -------------------------------------------------------------------------------- 1 | import unittest 2 | import zencad 3 | 4 | 5 | class Ops1d2dProbe(unittest.TestCase): 6 | def setUp(self): 7 | zencad.lazy.encache = False 8 | zencad.lazy.decache = False 9 | zencad.lazy.fastdo = True 10 | 11 | def test_fill(self): 12 | zencad.fill(zencad.circle(5, wire=True)).unlazy() 13 | zencad.circle(5, wire=True).fill().unlazy() 14 | 15 | def test_interpolate(self): 16 | zencad.interpolate([(0, 0, 0), (1, 1, 0), (1, 1, 1)]) 17 | zencad.interpolate(pnts=[(0, 0, 0), (1, 1, 0), (1, 1, 1)], closed=True) 18 | zencad.interpolate( 19 | [(0, 0, 0), (1, 1, 0), (1, 1, 1)], [ 20 | (0, 0, 0), (1, 1, 0), (1, 1, 1)] 21 | ) 22 | zencad.interpolate( 23 | pnts=[(0, 0, 0), (1, 1, 0), (1, 1, 1)], 24 | tangs=[(0, 0, 0), (1, 0, 0), (0, 0, 1)], 25 | closed=True, 26 | ) 27 | 28 | def test_sew(self): 29 | pnts = [(0, 0, 0), (1, 1, 1), (1, 0, 0)] 30 | zencad.sew( 31 | [ 32 | zencad.segment(pnts[0], pnts[1]), 33 | zencad.segment(pnts[1], pnts[2]), 34 | zencad.segment(pnts[2], pnts[0]), 35 | ] 36 | ) 37 | 38 | def test_fillet2d(self): 39 | zencad.square(20).fillet2d(1) 40 | zencad.square(20).fillet2d(r=1) 41 | zencad.fillet2d(shp=zencad.square(20), r=1) 42 | 43 | zencad.square(20).fillet2d(1, [(0, 0, 0)]) 44 | zencad.square(20).fillet2d(refs=[(0, 0, 0)], r=1) 45 | zencad.fillet2d(shp=zencad.square(20), refs=[(0, 0, 0)], r=1) 46 | 47 | def test_chamfer2d(self): 48 | # not supported 49 | pass 50 | -------------------------------------------------------------------------------- /utest/prim1d_test.py: -------------------------------------------------------------------------------- 1 | import unittest 2 | import zencad 3 | 4 | 5 | class Prim1dProbber(unittest.TestCase): 6 | def setUp(self): 7 | zencad.lazy.encache = False 8 | zencad.lazy.decache = False 9 | zencad.lazy.fastdo = True 10 | 11 | def test_segment_probe(self): 12 | zencad.segment((0, 0, 0), (10, 20, 30)) 13 | 14 | def test_polysegment_probe(self): 15 | pnts = [(0, 0, 0), (10, 20, 30), (10, 21, 35), (10, 22, 40)] 16 | zencad.polysegment(pnts, closed=False) 17 | zencad.polysegment(pnts, closed=True) 18 | 19 | def test_interpolate_probe(self): 20 | pnts = [(0, 0, 0), (10, 20, 30), (10, 21, 35), (10, 22, 40)] 21 | tangs = [(0, 0, 1), (1, 0, 0), (0, 1, 0), (0, 0, 0)] 22 | zencad.interpolate(pnts, closed=False) 23 | zencad.interpolate(pnts, closed=True) 24 | zencad.interpolate(pnts, tangs, closed=False) 25 | zencad.interpolate(pnts, tangs, closed=True) 26 | 27 | def test_circle_arc_probe(self): 28 | zencad.circle_arc((0, 0), (1, 1), (1, 2)) 29 | 30 | def test_helix_probe(self): 31 | r = 20 32 | h = 20 33 | step = 2 34 | angle = zencad.deg(15) 35 | zencad.helix(r, h, step, left=True) 36 | zencad.helix(r, h, step, angle=angle, left=True) 37 | zencad.helix(r, h, step, left=False) 38 | zencad.helix(r, h, step, angle=angle, left=False) 39 | 40 | def test_bezier_probe(self): 41 | zencad.bezier([(0, 0, 0), (0, 1, 0), (1, 1, 0)]) 42 | -------------------------------------------------------------------------------- /utest/reflection.py: -------------------------------------------------------------------------------- 1 | import unittest 2 | import zencad 3 | 4 | 5 | class ReflectionProbber(unittest.TestCase): 6 | def setUp(self): 7 | zencad.lazy.encache = False 8 | zencad.lazy.decache = False 9 | zencad.lazy.fastdo = True 10 | 11 | def test_types_probe(self): 12 | m = zencad.box(10, 10, 10) 13 | 14 | self.assertEqual(m.faces()[0].shapetype().unlazy(), "face") 15 | self.assertEqual(m.wires()[0].shapetype().unlazy(), "wire") 16 | self.assertEqual(m.edges()[0].shapetype().unlazy(), "edge") 17 | self.assertEqual(m.solids()[0].shapetype().unlazy(), "solid") 18 | -------------------------------------------------------------------------------- /utest/start-all.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | 3 | import os 4 | import sys 5 | 6 | os.system(sys.executable + " widgets_test.py") 7 | os.system(sys.executable + " api.py") 8 | os.system(sys.executable + " examples.py") 9 | -------------------------------------------------------------------------------- /utest/widgets_test.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | # coding:utf-8 3 | 4 | import unittest 5 | import zencad 6 | 7 | #from PyQt5.QtWidgets import * 8 | #from PyQt5.QtCore import * 9 | #from PyQt5.QtGui import * 10 | 11 | #from zencad.gui.settingswdg import SettingsWidget 12 | 13 | #qapp = QApplication([]) 14 | 15 | 16 | class WidgetsTest(unittest.TestCase): 17 | def test_segment_probe(self): 18 | pass 19 | # settings = SettingsWidget() 20 | -------------------------------------------------------------------------------- /zencad/assemble.py: -------------------------------------------------------------------------------- 1 | from zencad.interactive.assemble import * 2 | -------------------------------------------------------------------------------- /zencad/axis.py: -------------------------------------------------------------------------------- 1 | import zencad.util 2 | from OCC.Core.Geom import Geom_Line 3 | from OCC.Core.gp import gp_Lin, gp_Pnt, gp_Dir, gp_XYZ 4 | 5 | 6 | class Axis: 7 | def __init__(self, *xyz): 8 | self._coords = zencad.util.as_indexed(xyz) 9 | 10 | def to_Geom_Line(self): 11 | return Geom_Line( 12 | gp_Lin( 13 | gp_Pnt(0, 0, 0), 14 | gp_Dir( 15 | gp_XYZ( 16 | self._coords[0], 17 | self._coords[1], 18 | self._coords[2])))) 19 | -------------------------------------------------------------------------------- /zencad/bbox.py: -------------------------------------------------------------------------------- 1 | from OCC.Core.Bnd import Bnd_Box 2 | 3 | 4 | class BoundaryBox: 5 | def __init__(self, xl=None, xh=None, yl=None, yh=None, zl=None, zh=None): 6 | if isinstance(xl, Bnd_Box): 7 | self.assign_Bnd_Box(xl) 8 | return 9 | 10 | if (xl is None): 11 | self.assign_coords(0, 0, 0, 0, 0, 0) 12 | self.inited = False 13 | return 14 | 15 | self.assign_coords(xl, xh, yl, yh, zl, zh) 16 | 17 | def assign_coords(self, xl, xh, yl, yh, zl, zh): 18 | self.xmin = xl 19 | self.xmax = xh 20 | self.ymin = yl 21 | self.ymax = yh 22 | self.zmin = zl 23 | self.zmax = zh 24 | self.inited = True 25 | 26 | def assign(self, box): 27 | self.xmin = box.xmin 28 | self.xmax = box.xmax 29 | self.ymin = box.ymin 30 | self.ymax = box.ymax 31 | self.zmin = box.zmin 32 | self.zmax = box.zmax 33 | self.inited = True 34 | 35 | def assign_Bnd_Box(self, Box): 36 | a, b, c, d, e, f = Box.Get() 37 | self.xmin = a 38 | self.xmax = d 39 | self.ymin = b 40 | self.ymax = e 41 | self.zmin = c 42 | self.zmax = f 43 | self.inited = True 44 | 45 | def add(self, bbox): 46 | if self.inited is False: 47 | self.assign(bbox) 48 | 49 | else: 50 | self.xmin = min(self.xmin, bbox.xmin) 51 | self.ymin = min(self.ymin, bbox.ymin) 52 | self.zmin = min(self.zmin, bbox.zmin) 53 | self.xmax = max(self.xmax, bbox.xmax) 54 | self.ymax = max(self.ymax, bbox.ymax) 55 | self.zmax = max(self.zmax, bbox.zmax) 56 | 57 | def xrange(self): return (self.xmin, self.xmax) 58 | def yrange(self): return (self.ymin, self.ymax) 59 | def zrange(self): return (self.zmin, self.zmax) 60 | 61 | def xlength(self): return self.xmax - self.xmin 62 | def ylength(self): return self.ymax - self.ymin 63 | def zlength(self): return self.zmax - self.zmin 64 | 65 | def shape(self): 66 | from zencad.geom.solid import box 67 | return box(self.xlength(), self.ylength(), self.zlength()).move(self.xmin, self.ymin, self.zmin) 68 | -------------------------------------------------------------------------------- /zencad/convert/test.svg: -------------------------------------------------------------------------------- 1 | 2 | < path d = "M 10.0 0.0 L 10.0 -20.0 L 0.0 -20.0 L 0.0 -10.0 L -5.0 -10.0 L -5.00000000000006 -6.92820323027545 A 10.0 8.0 0 0 0 -5.00000000000006 6.92820323027545 L -5.0 10.0 L 5.0 10.0 L 5.00000000000021 6.92820323027531 A 10.0 8.0 0 0 0 10.0 0.0 M 3.0 0.0 A 3.0 3.0 0 0 1 -2.999999999999999 6.661338147750939e-16 A 3.0 3.0 0 0 1 3.0 0.0" fill = "rgb(50%,0%,50%)" fill-opacity = "1" / > < /svg > 3 | -------------------------------------------------------------------------------- /zencad/curve.py: -------------------------------------------------------------------------------- 1 | from OCC.Core.BRepBuilderAPI import BRepBuilderAPI_MakeEdge 2 | from OCC.Core.gp import gp_Pnt, gp_Vec 3 | 4 | from zencad.util import point3 5 | 6 | import evalcache 7 | -------------------------------------------------------------------------------- /zencad/examples/0.Base/csg.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | # coding: utf-8 3 | 4 | from zencad import * 5 | 6 | m1 = box(15, center=True) + sphere(10) 7 | m2 = box(15, center=True) ^ sphere(10) 8 | m3 = box(15, center=True) - sphere(10) 9 | 10 | display(m1.left(24)) 11 | display(m2) 12 | display(m3.right(24)) 13 | 14 | show() 15 | -------------------------------------------------------------------------------- /zencad/examples/0.Base/helloworld.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | # coding: utf-8 3 | 4 | from zencad import * 5 | 6 | print("HelloWorld!") 7 | 8 | a = box(200, 200, 200, center=True) 9 | b = sphere(120) 10 | c = sphere(60) 11 | 12 | model = a - b + c 13 | 14 | display(model) 15 | 16 | show() 17 | -------------------------------------------------------------------------------- /zencad/examples/1.GeomPrim/1.prim3d/box.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | """ 3 | ZenCad API example: box 4 | """ 5 | 6 | from zencad import * 7 | 8 | box_a = 10 9 | box_b = 15 10 | box_c = 20 11 | 12 | # About center option: 13 | b0 = box(box_a, box_b, box_c) 14 | b0c = box(box_a, box_b, box_c, center=True) 15 | disp(b0, color=color.magenta) 16 | disp(b0c, color=color.cian) 17 | 18 | # API variants: 19 | m1 = box(box_a) 20 | m2 = box(box_a, box_b, box_c) 21 | m3 = box(size=(box_a, box_b, box_c)) 22 | disp(m1.right(30 * 1), color=color.red) 23 | disp(m2.right(30 * 2), color=color.green) 24 | disp(m3.right(30 * 3), color=color.blue) 25 | 26 | # Mister Cube: 27 | mister_cube = ( 28 | box(40, center=True) 29 | - box(8, center=True).translate(10,-20,8) 30 | - box(8, center=True).translate(-10,-20,8) 31 | + box(4, center=True).translate(10,-18,8) 32 | + box(4, center=True).translate(-10,-18,8) 33 | - box(20, 8, 4, center=True).translate(0,-20,-8) 34 | + box(8, center=True).translate(24,0,0) 35 | + box(8, center=True).translate(-24,0,0) 36 | + box(8, center=True).translate(10,0,-24) 37 | + box(8, center=True).translate(-10,0,-24) 38 | + box(20,20,10, center=True).rotateZ(deg(40)).translate(1,0,25) 39 | + box(30,30,10, center=True).rotateZ(deg(40)).translate(1,0,35) 40 | ) 41 | 42 | disp(mister_cube.translate(50,100,28)) 43 | 44 | show() 45 | -------------------------------------------------------------------------------- /zencad/examples/1.GeomPrim/1.prim3d/cone.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | """ 3 | ZenCad API example: cone 4 | """ 5 | 6 | from zencad import * 7 | 8 | # Basic and centered variants: 9 | m0 = cone(r1=10, r2=5, h=20) 10 | m1 = cone(r1=10, r2=5, h=20, center=True) 11 | disp(m0, color=(1, 0, 1, 0.5)) 12 | disp(m1, color=(0, 1, 1, 0.5)) 13 | 14 | # Sector of cone: 15 | m = cone(r1=10, r2=5, h=20, yaw=deg(90)) 16 | disp(m.left(30)) 17 | 18 | # Reversed cone: 19 | m = cone(r1=5, r2=10, h=20) 20 | disp(m.right(30)) 21 | 22 | # Sharp cone: 23 | m0 = cone(r1=10, r2=0, h=20) 24 | m1 = cone(r1=0, r2=10, h=20) 25 | disp(m0.move(0, 30, 0)) 26 | disp(m1.move(30, 30, 0)) 27 | 28 | show() 29 | -------------------------------------------------------------------------------- /zencad/examples/1.GeomPrim/1.prim3d/cylinder.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | # coding: utf-8 3 | 4 | from zencad import * 5 | 6 | m0 = cylinder(r=10, h=20) 7 | m1 = cylinder(r=10, h=20, yaw=deg(90)) 8 | 9 | m0c = cylinder(r=10, h=20, center=True) 10 | m1c = cylinder(r=10, h=20, yaw=deg(90), center=True) 11 | 12 | display(m0.right(30 * 0)) 13 | display(m1.right(30 * 1)) 14 | 15 | display(m0c.right(30 * 2)) 16 | display(m1c.right(30 * 3)) 17 | 18 | #Mr. Cylinder 19 | mister_cylinder = union([ 20 | cylinder(r=10, h=20), 21 | cylinder(r=5, h=5).up(20), 22 | cylinder(r=2, h=12, center=True).rotateY(deg(90)).back(10).up(6), 23 | cylinder(r=2, h=2, center=True).rotateX(deg(90)).back(10).up(14).moveX(5), 24 | cylinder(r=2, h=2, center=True).rotateX(deg(90)).back(10).up(14).moveX(-5), 25 | ]) 26 | disp(mister_cylinder.move(45,60,0)) 27 | 28 | show() 29 | -------------------------------------------------------------------------------- /zencad/examples/1.GeomPrim/1.prim3d/halfspace.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | # coding: utf-8 3 | """ 4 | ZenCad API example: halfspace 5 | 6 | Halfspace is special solid that used to boolean operation. 7 | In fact, we can't display halspace, but we can use it for intersection 8 | or for substutution. 9 | """ 10 | 11 | from zencad import * 12 | 13 | # Substitution example: 14 | m0 = sphere(10) 15 | m1 = m0 - halfspace().rotateY(deg(120)) 16 | m2 = m1 - halfspace().mirrorXY().up(3) 17 | m3 = m2 - halfspace().rotateX(deg(-90)).rotateZ(deg(45)).back(3) 18 | 19 | disp(m0.right(0)) 20 | disp(m1.right(25)) 21 | disp(m2.right(50)) 22 | disp(m3.right(75)) 23 | 24 | clr = (0.6, 0.6, 0.8, 0.8) 25 | disp((m0-m1).right(25), color=clr) 26 | disp((m1-m2).right(50), color=clr) 27 | disp((m2-m3).right(75), color=clr) 28 | 29 | # Intersection example: 30 | m0 = sphere(10) 31 | m1 = m0 ^ halfspace().rotateY(deg(120)) 32 | m2 = m1 ^ halfspace().mirrorXY().up(3) 33 | m3 = m2 ^ halfspace().rotateX(deg(-90)).rotateZ(deg(45)).back(3) 34 | 35 | disp(m0.right(0).forw(25)) 36 | disp(m1.right(25).forw(25)) 37 | disp(m2.right(50).forw(25)) 38 | disp(m3.right(75).forw(25)) 39 | 40 | clr = (0.6, 0.6, 0.8, 0.8) 41 | disp((m0-m1).right(25).forw(25), color=clr) 42 | disp((m1-m2).right(50).forw(25), color=clr) 43 | disp((m2-m3).right(75).forw(25), color=clr) 44 | 45 | show() 46 | -------------------------------------------------------------------------------- /zencad/examples/1.GeomPrim/1.prim3d/platonic.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | # coding: utf-8 3 | 4 | from zencad import * 5 | 6 | tetra = tetrahedron(10) 7 | hexa = hexahedron(10) 8 | octa = octahedron(10) 9 | dodeca = dodecahedron(10) 10 | icosa = icosahedron(10) 11 | 12 | disp(tetra) 13 | disp(hexa.movX(20)) 14 | disp(octa.movX(40)) 15 | disp(dodeca.movX(60)) 16 | disp(icosa.movX(80)) 17 | 18 | show() 19 | -------------------------------------------------------------------------------- /zencad/examples/1.GeomPrim/1.prim3d/sphere.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | """ 3 | ZenCad API example: sphere 4 | """ 5 | 6 | from zencad import * 7 | 8 | m1 = sphere(r=10) 9 | m2 = sphere(r=10, yaw=deg(135)) 10 | m3 = sphere(r=10, pitch=(deg(20), deg(60))) 11 | m4 = sphere(r=10, yaw=deg(135), pitch=(deg(10), deg(45))) 12 | 13 | display(m1) 14 | display(m2.right(30)) 15 | display(m3.right(60)) 16 | display(m4.right(90)) 17 | 18 | # Pacman 19 | pacman = ( 20 | sphere(r=10, yaw=deg(360-45)).rotateY(deg(90)).rotateX(deg(-55)) 21 | - sphere(r=3).move(5,-7,8) 22 | - sphere(r=3).move(-5,-7,8) 23 | + sphere(r=1).move(4,-5,6) 24 | + sphere(r=1).move(-4,-5,6) 25 | ) 26 | disp(pacman.move(45,50,0), color.yellow) 27 | disp(sphere(r=2).move(45,35,-2)) 28 | disp(sphere(r=2).move(45,25,-2)) 29 | 30 | show() 31 | -------------------------------------------------------------------------------- /zencad/examples/1.GeomPrim/1.prim3d/torus.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | """ 3 | ZenCad API example: torus 4 | """ 5 | 6 | from zencad import * 7 | 8 | tor_r1 = 5 9 | tor_r2 = 2 10 | tor_u = deg(135) 11 | tor_v1 = deg(-90) 12 | tor_v2 = deg(180) 13 | 14 | m0 = torus(r1=tor_r1, r2=tor_r2) 15 | m1 = torus(r1=tor_r1, r2=tor_r2, yaw=tor_u) 16 | m2 = torus(r1=tor_r1, r2=tor_r2, pitch=(tor_v1, tor_v2)) 17 | m3 = torus(r1=tor_r1, r2=tor_r2, pitch=(tor_v1, tor_v2), yaw=tor_u) 18 | 19 | display(m0.right(20 * 0)) 20 | display(m1.right(20 * 1)) 21 | display(m2.right(20 * 2)) 22 | display(m3.right(20 * 3)) 23 | 24 | show() 25 | -------------------------------------------------------------------------------- /zencad/examples/1.GeomPrim/2.prim2d/circle.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | """ 3 | ZenCad API example: circle 4 | last update: 04.10.2019 5 | """ 6 | 7 | from zencad import * 8 | 9 | m0 = circle(r=10) 10 | m1 = circle(r=10, angle=deg(90)) 11 | m2 = circle(r=10, angle=(deg(45), deg(90))) 12 | 13 | m3 = circle(r=10, wire=True) 14 | m4 = circle(r=10, angle=deg(90), wire=True) 15 | m5 = circle(r=10, angle=(deg(45), deg(90)), wire=True) 16 | 17 | pacman = ( 18 | circle(r=10, angle=(deg(-135), deg(135))) - 19 | circle(r=1).forw(5) 20 | ) 21 | 22 | disp(m0.right(30), color.red) 23 | disp(m1.right(60), color.green) 24 | disp(m2.right(90), color.white) 25 | disp(m3.right(30).back(30), color.red) 26 | disp(m4.right(60).back(30), color.green) 27 | disp(m5.right(90).back(30), color.white) 28 | 29 | disp(pacman.forw(30).right(30), color.yellow) 30 | for w in pacman.wires(): disp(w.forw(30).right(60)) 31 | 32 | show() 33 | -------------------------------------------------------------------------------- /zencad/examples/1.GeomPrim/2.prim2d/ellipse.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | """ 3 | ZenCad API example: ellipse 4 | """ 5 | 6 | from zencad import * 7 | 8 | el_r1 = 7 9 | el_r2 = 5 10 | el_a1 = deg(-45) 11 | el_a2 = deg(180) 12 | 13 | m0 = ellipse(r1=el_r1, r2=el_r2) 14 | m1 = ellipse(r1=el_r1, r2=el_r2, angle=(el_a1, el_a2)) 15 | 16 | m2 = ellipse(r1=el_r1, r2=el_r2, wire=True) 17 | m3 = ellipse(r1=el_r1, r2=el_r2, angle=(el_a1, el_a2), wire=True) 18 | 19 | m4 = ellipse(r1=el_r1, r2=el_r2, wire=True) 20 | m5 = ellipse(r1=el_r2, r2=el_r1, wire=True) 21 | 22 | m6 = ellipse(r1=el_r1, r2=el_r2, angle=(0, deg(135)), wire=True) 23 | m7 = ellipse(r1=el_r2, r2=el_r1, angle=(0, deg(135)), wire=True) 24 | 25 | display(m0.translate( 0, 0, 0), color.red) 26 | display(m1.translate(20, 0, 0), color.yellow) 27 | display(m2.translate( 0, 15, 0), color.red) 28 | display(m3.translate(20, 15, 0), color.yellow) 29 | 30 | display(m4.translate(40, 0, 0), color.green) 31 | display(m5.translate(60, 0, 0), color.blue) 32 | display(m6.translate(40, 0, 1), color.magenta) 33 | display(m7.translate(60, 0, 1), color.cian) 34 | 35 | show() 36 | -------------------------------------------------------------------------------- /zencad/examples/1.GeomPrim/2.prim2d/fillet_ngon.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | # coding: utf-8 3 | 4 | from zencad import * 5 | import evalcache 6 | import functools 7 | 8 | 9 | ng = ngon(r=10, n=6) 10 | radius = 4 11 | radius2 = 8 12 | 13 | # Fillter all vertices 14 | m1 = ngon(r=10, n=6).fillet2d(radius) 15 | 16 | # Generator can be used for array filtering 17 | m2 = ng.fillet2d(radius, [v for v in ng.vertices() if v.x < 0]) 18 | 19 | # We can use lazy lambda for improve caching algorithm 20 | m3 = ng.fillet2d(radius, lazy(lambda: [v for v in ng.vertices() if v.y < 0])()) 21 | 22 | # One more syntax variant (and inaccuracy of float when comparing) 23 | m4 = ng.fillet2d(radius, evalcache.select(ng.vertices(), lambda v: abs(v.y) < 0.001)) 24 | 25 | # Advanced version with indexing of sorted array of points 26 | def comparator(a, b): 27 | """sort by yx_order""" 28 | xdiff = a.x - b.x 29 | ydiff = a.y - b.y 30 | if abs(ydiff) > 0.001: 31 | return ydiff 32 | if abs(xdiff) > 0.001: 33 | return xdiff 34 | return 0 35 | vtxs = sorted(ng.vertices(), key=functools.cmp_to_key(comparator)) 36 | m5 = fillet2d(ng, radius, [vtxs[0], vtxs[3], vtxs[4]]) 37 | m5 = fillet2d(m5, radius2, [vtxs[1], vtxs[2], vtxs[5]]) 38 | 39 | display(m1) 40 | display(m2.right(30)) 41 | display(m3.right(60)) 42 | display(m4.right(90)) 43 | display(m5.right(120)) 44 | 45 | show() 46 | -------------------------------------------------------------------------------- /zencad/examples/1.GeomPrim/2.prim2d/interpolate2.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | """ 3 | ZenCad API example: interpolate2 4 | last update: 06.07.2020 5 | """ 6 | 7 | from zencad import * 8 | 9 | POINTS = points2([ 10 | [(0,0,0), (10,0,7), (20,0,5)], 11 | [(0,5,0), (10,5,7.5), (20,5,7)], 12 | [(0,10,2), (10,10,8), (20,10,5)], 13 | [(0,15,1.3), (10,15,8.5), (20,15,6)], 14 | ]) 15 | 16 | m = interpolate2(POINTS) 17 | disp(m) 18 | disp(POINTS, color=color.red) 19 | 20 | show() 21 | -------------------------------------------------------------------------------- /zencad/examples/1.GeomPrim/2.prim2d/ngon.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | """ 3 | ZenCad API example: ngon 4 | last update: 04.10.2019 5 | """ 6 | 7 | from zencad import * 8 | 9 | m0 = ngon(r=10, n=3) 10 | m1 = ngon(r=10, n=5) 11 | m2 = ngon(r=10, n=8) 12 | m3 = ngon(r=10, n=256) 13 | 14 | disp(m0) 15 | disp(m1.right(30)) 16 | disp(m2.right(60)) 17 | disp(m3.right(90)) 18 | 19 | NMin = 3 20 | NMax = 12 21 | 22 | for i in range(NMin, NMax + 1): 23 | k = (i-NMin) / (NMax - NMin) 24 | disp(ngon(r=10, n=i).right((i-NMin)*30).forw(30), Color(k**2, k, 1-k)) 25 | 26 | show() 27 | -------------------------------------------------------------------------------- /zencad/examples/1.GeomPrim/2.prim2d/polygon.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | """ 3 | ZenCad API example: polygon 4 | """ 5 | 6 | from zencad import * 7 | 8 | m = polygon([(0,0),(0,10),(20,20),(10,0)]) 9 | 10 | disp(m) 11 | show() -------------------------------------------------------------------------------- /zencad/examples/1.GeomPrim/2.prim2d/rectangle.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | """ 3 | ZenCad API example: rectangle 4 | last update: 04.10.2019 5 | """ 6 | 7 | 8 | from zencad import * 9 | 10 | m0 = rectangle(a=10, b=6, center=True) 11 | m1 = rectangle(a=10, b=6) 12 | m2 = rectangle(6, center=True) 13 | m3 = square(6) 14 | 15 | display(m0, color=color.yellow) 16 | display(m1.up(0.3), color=color.green) 17 | display(m2.forw(10), color=color.red) 18 | display(m3.forw(10).up(0.3), color=color.white) 19 | 20 | show() 21 | -------------------------------------------------------------------------------- /zencad/examples/1.GeomPrim/2.prim2d/textshape.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | """ 3 | ZenCad API example: textshape 4 | date: 04.10.2019 5 | """ 6 | 7 | import os 8 | from zencad import * 9 | 10 | zencad_example_directory = zencad.moduledir + "/examples" 11 | 12 | testfont = os.path.join(zencad_example_directory, "fonts/testfont.ttf") 13 | mandarinc = os.path.join(zencad_example_directory, "fonts/mandarinc.ttf") 14 | 15 | register_font(testfont) 16 | register_font(mandarinc) 17 | 18 | m0 = textshape(text="ZenCad", fontname="Ubuntu Mono", size=100) 19 | m1 = textshape(text="ZenCad", fontname="Mandarinc", size=100) 20 | 21 | disp(m0, color.white) 22 | disp(m0.rotateX(deg(90)).translate(0, 70, 0)) 23 | 24 | disp(m1.translate( 0, 200, 0), color.green) 25 | disp(m1.rotateX(deg(90)).translate( 0, 270, 0), color.yellow) 26 | 27 | #########################Advanced Example######################################## 28 | x = 400 29 | y = 100 30 | z = 50 31 | deep = 10 32 | 33 | #find the geometric center of the textshape 34 | m1center = m1.center() 35 | m2 = ( 36 | box(x, y, z) 37 | - m1.extrude(deep).up(z-deep).translate(x/2 - m1center.x, y/2 - m1center.y, 0) 38 | ) 39 | 40 | disp(m2.forw(400)) 41 | ################################################################################ 42 | 43 | show() 44 | -------------------------------------------------------------------------------- /zencad/examples/1.GeomPrim/2.prim2d/widewire.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | """ 3 | ZenCad API example: widewire 4 | """ 5 | 6 | from zencad import * 7 | 8 | wr = wire_builder() 9 | wr.line(10,10) 10 | wr.line(20,20) 11 | wr.line(30,0) 12 | wr.interpolate([ 13 | [40, -20], 14 | [30, -40] 15 | ]) 16 | wr.interpolate([ 17 | [50, -60], 18 | [60, -110] 19 | ]) 20 | 21 | w = widewire(wr.doit(), 5) 22 | 23 | disp(wr.doit(), zencad.color.red) 24 | disp(w) 25 | show() 26 | -------------------------------------------------------------------------------- /zencad/examples/1.GeomPrim/3.prim1d/bezier.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | 3 | """ 4 | ZenCad API example: bezier.py 5 | """ 6 | 7 | from zencad import * 8 | 9 | pnts = points([(0, 0, 0), (0, 10, 0), (10, 10)]) 10 | 11 | m0 = bezier(pnts) 12 | m1 = bezier(pnts, weights=[1,2,1]) 13 | m2 = bezier(pnts, weights=[1,3,1]) 14 | 15 | disp(m0, color=(1,0,0)) 16 | disp(m1, color=(0,1,0)) 17 | disp(m2, color=(0,0,1)) 18 | disp(pnts) 19 | 20 | show() 21 | -------------------------------------------------------------------------------- /zencad/examples/1.GeomPrim/3.prim1d/bspline.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | 3 | """ 4 | ZenCad API example: bspline.py 5 | # https://pages.mtu.edu/~shene/COURSES/cs3621/NOTES/spline/B-spline/bspline-ex-1.html 6 | # https://en.wikipedia.org/wiki/B-spline 7 | """ 8 | 9 | from zencad import * 10 | 11 | knots_total = 5 12 | m0 = bspline( 13 | poles = points([(0, 0, 0), (0, 10, 0), (10, 10)]), 14 | knots = [ i * 1 / (knots_total-1) for i in range(knots_total) ], 15 | muls = [1] * knots_total, 16 | degree=1 17 | ) 18 | 19 | knots_total = 6 20 | m1 = bspline( 21 | poles = points([(0, -10, 0), (0, 10, 0), (20, 10)]), 22 | knots = [ i * 1 / (knots_total-1) for i in range(knots_total) ], 23 | muls = [1,1,1,1,1,1], 24 | degree=2 25 | ) 26 | 27 | knots_total = 7 28 | m2 = bspline( 29 | poles = points([(0, -10), (0, 10), (10, 10), (10, 30)]), 30 | knots = [ i * 1 / (knots_total-1) for i in range(knots_total) ], 31 | muls = [1]*knots_total, 32 | degree=2 33 | ) 34 | 35 | disp(m0.moveX(10), color=(0,0,1)) 36 | disp(m1.moveX(10), color=(0,1,0)) 37 | disp(m2.moveX(10), color=(1,0,0)) 38 | 39 | show() 40 | -------------------------------------------------------------------------------- /zencad/examples/1.GeomPrim/3.prim1d/helix.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | """ 3 | ZenCad API example: helix.py 4 | """ 5 | 6 | from zencad import * 7 | 8 | m1 = helix(r=10, h=40, step=4) 9 | m2 = helix(r=10, h=40, step=4, left=True) 10 | m3 = helix(r=10, h=40, step=4, angle=deg(10)) 11 | m4 = helix(r=10, h=40, step=4, angle=deg(-10)) 12 | 13 | disp(m1) 14 | disp(m2.right(30)) 15 | disp(m3.right(60)) 16 | disp(m4.right(90)) 17 | 18 | show() 19 | -------------------------------------------------------------------------------- /zencad/examples/1.GeomPrim/3.prim1d/interpolate.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | 3 | from zencad import * 4 | 5 | m = interpolate([ 6 | (0, 0), 7 | (10, 0), 8 | (20, 10), 9 | (0, 5, 10), 10 | ], 11 | tangs=[ 12 | None, 13 | None, 14 | None, 15 | None 16 | ]) 17 | 18 | disp(m) 19 | show() 20 | -------------------------------------------------------------------------------- /zencad/examples/1.GeomPrim/3.prim1d/polysegment.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | 3 | """ 4 | ZenCad API example: polysegment.py 5 | """ 6 | 7 | from zencad import * 8 | 9 | pnts = points([(0, 0, 0), (0, 10, 10), (0, 10, 20), (0, -10, 20), (0, -10, 10)]) 10 | 11 | m0 = polysegment(pnts) 12 | m1 = polysegment(pnts, closed=True) 13 | m2 = polysegment(pnts, closed=True).fill() 14 | m3 = polysegment(pnts + [(0, 0, 0)]) 15 | m4 = polysegment(pnts + [(0, 0, 0)]).fill() 16 | 17 | disp(m0) 18 | disp(m1.left(20)) 19 | disp(m2.left(40)) 20 | disp(m3.left(20).forw(30)) 21 | disp(m4.left(40).forw(30)) 22 | 23 | show() 24 | -------------------------------------------------------------------------------- /zencad/examples/1.GeomPrim/3.prim1d/rounded_polysegment.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | #coding: utf-8 3 | 4 | from zencad import * 5 | 6 | POINTS = [ 7 | (0,0,0), 8 | (0,0,20), 9 | (0,20,40), 10 | (-90,20,40), 11 | (-90,20,20), 12 | (0,20,0), 13 | ] 14 | 15 | POINTS2 = [(0,0), (20,0), (20,20)] 16 | 17 | m0 = rounded_polysegment(POINTS, r=10) 18 | m1 = rounded_polysegment(POINTS, r=10, closed=True) 19 | m2 = rounded_polysegment(POINTS2, r=5, closed=True).fill() 20 | 21 | disp(m0) 22 | disp(m1.moveY(40),color=color.green) 23 | disp(m2.moveY(80),color=color.yellow) 24 | 25 | for p in POINTS: disp(point3(p), color.red) 26 | for p in POINTS: disp(point3(p).moveY(40), color.red) 27 | for p in POINTS2: disp(point3(p).moveY(80), color.red) 28 | 29 | show() -------------------------------------------------------------------------------- /zencad/examples/1.GeomPrim/3.prim1d/segment.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | 3 | """ 4 | ZenCad API example: segment.py 5 | """ 6 | 7 | from zencad import * 8 | 9 | m = segment((10, 0, 0), (10, 20, 30)) 10 | display(m) 11 | 12 | show() 13 | -------------------------------------------------------------------------------- /zencad/examples/2.Operations/1.AphineTrans/rotate_array.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | """ 3 | ZenCad API example: rotate_array 4 | """ 5 | 6 | from zencad import * 7 | import zencad.internal_models 8 | 9 | a = box(15, center=True) 10 | b = cylinder(r=15, h=10) 11 | c = ellipse(10,5) 12 | d = square(10, center=True, wire=True) 13 | 14 | k1 = rotate_array(n=6, unit=True)(a.right(25)) 15 | k2 = rotate_array(n=4, yaw=deg(180), endpoint=True, unit=True)(a.right(25)) 16 | k3 = rotate_array(n=4, yaw=deg(180), endpoint=False, unit=True)(a.right(25)) 17 | k4 = rotate_array2(n=4, r=25, yaw=(0,deg(180)), roll=(0,deg(-60)), endpoint=True, unit=True)( 18 | a.rotX(deg(-90))) 19 | 20 | m1 = unify(rotate_array(n=6)(b.right(20))) 21 | m2 = rotate_array2(n=12, r=20)(c.rotZ(deg(90))) 22 | m3 = rotate_array2(n=60, r=20, yaw=(0,deg(270)), roll=(0,deg(360)), array=True)(d) 23 | 24 | S = 70 25 | 26 | disp(b).forw(S) 27 | disp(c).right(S).forw(S) 28 | disp(d).right(S*2).forw(S) 29 | 30 | disp(m1).right(0).forw(S*2) 31 | disp(m2).right(S).forw(S*2) 32 | for m in m3: disp(m).right(S*2).forw(S*2) 33 | 34 | disp(k1).forw(0) 35 | disp(k2, color.red).right(S).forw(0) 36 | disp(k3, color.green).right(S*2).forw(0) 37 | disp(k4, color.blue).right(S*3).forw(0) 38 | show() 39 | -------------------------------------------------------------------------------- /zencad/examples/2.Operations/1.AphineTrans/scale.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | """ 3 | ZenCad API example: scale 4 | """ 5 | 6 | from zencad import * 7 | 8 | a = sphere(10) 9 | 10 | m0 = a.scale(1.5) 11 | m1 = a.scaleXYZ(1.3, 2, 0.5) 12 | m2 = a.scaleX(1.5) 13 | m3 = a.scaleY(1.5) 14 | m4 = a.scaleZ(1.5) 15 | 16 | disp(m0.movX(0)) 17 | disp(m1.movX(30)) 18 | disp(m2.movX(60)) 19 | disp(m3.movX(90)) 20 | disp(m4.movX(120)) 21 | 22 | show() 23 | -------------------------------------------------------------------------------- /zencad/examples/2.Operations/1.AphineTrans/short_rotate.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | """ 3 | ZenCad API example: short_rotate 4 | last update: 24.10.2019 5 | 6 | Detail: 7 | Short rotate application example. 8 | 9 | That operation very useful if you need rotate object axis 10 | by source axis vector and target axis vector. 11 | Otherwise, With common rotation operation you should evaluate 12 | rotation axis and rotation angle. 13 | 14 | In that example you can play with `src` and `tgt` arrays. 15 | Practice shooting :). 16 | """ 17 | 18 | from zencad import * 19 | from zencad.interactive import arrow, line 20 | 21 | u = 20 22 | 23 | # Parameters 24 | angle = deg(60) 25 | arrl, arrw, arrh = 2, 1, 15 26 | 27 | src = points([ 28 | (-1, -2, 1), 29 | (1, -2, 1), 30 | (-2, 1, 0), 31 | ]) 32 | 33 | tgt = points([ 34 | (1, 2, 1), 35 | (1, 1, 0), 36 | (2, 2, 3) 37 | ]) 38 | 39 | clr = [color.red, color.green, color.blue] 40 | 41 | # Scale 42 | for i in range(len(src)): 43 | for j in range(3): 44 | src[i][j] *= u 45 | tgt[i][j] *= u 46 | 47 | # Make short rotate transformation 48 | transes = [translate(*src[i]) * short_rotate((0, 0, 1), 49 | tgt[i] - src[i]) for i in range(len(src))] 50 | 51 | # Make cylinders geometry 52 | cyl = cylinder(r=5, h=10, center=True) 53 | tgt_cyls = [trans(cyl) for trans in transes] 54 | 55 | # Draw cylinders 56 | for t in tgt_cyls: 57 | disp(t) 58 | 59 | # Draw arrows 60 | for i in range(len(src)): 61 | arr = arrow(src[i], tgt[i], arrlen=arrl, width=arrw, color=clr[i]) 62 | disp(arr) 63 | 64 | # Draw white cube. 65 | N = 4 66 | for i in range(N): 67 | for j in range(N): 68 | for k in range(N): 69 | if i < N-1: 70 | disp(line(point3(i*u, j*u, k*u), point3(i*u+u, j*u, k*u))) 71 | if j < N-1: 72 | disp(line(point3(i*u, j*u, k*u), point3(i*u, j*u+u, k*u))) 73 | if k < N-1: 74 | disp(line(point3(i*u, j*u, k*u), point3(i*u, j*u, k*u+u))) 75 | 76 | for i in range(len(tgt)): 77 | if tgt[i] in src: 78 | disp(textshape("BOOM!!!!", os.path.join(zencad.moduledir, "examples/fonts/mandarinc.ttf"), 79 | 20, True).rotateX(deg(90)).translate(*tgt[i]).up(15), color=color.red) 80 | 81 | show() 82 | -------------------------------------------------------------------------------- /zencad/examples/2.Operations/2.Operations/loft.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | # coding: utf-8 3 | 4 | from zencad import * 5 | 6 | arr = [ 7 | circle(r=20, wire=True), 8 | ellipse(30, 25, wire=True).up(20), 9 | circle(r=20, wire=True).up(40), 10 | circle(r=15, wire=True).up(50), 11 | circle(r=16, wire=True).up(60), 12 | ] 13 | 14 | m0 = loft(arr) 15 | m1 = loft(arr, smooth=True, maxdegree=10, shell=True) 16 | m2 = loft(arr, smooth=True, maxdegree=10) 17 | m3 = thicksolid(loft(arr, smooth=True, maxdegree=10), refs=[(0,0,60)], t=-2) 18 | 19 | disp(m0) 20 | disp(m1).right(80) 21 | disp(m2).right(160) 22 | disp(m3).right(240) 23 | 24 | for w in arr: disp(w, color.red).right(80) 25 | 26 | show() -------------------------------------------------------------------------------- /zencad/examples/2.Operations/2.Operations/offset.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | # coding: utf-8 3 | 4 | from zencad import * 5 | 6 | m = cone(r1=10, r2=5, h=10) 7 | m = offset(m, 2) 8 | 9 | disp(m) 10 | show() -------------------------------------------------------------------------------- /zencad/examples/2.Operations/2.Operations/thicksolid.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | 3 | from zencad import * 4 | from zencad.geom.offset import _shapefix_solid 5 | 6 | m = box(20) 7 | m = thicksolid(m, refs=[(0, 5, 5)], t=1) 8 | 9 | disp(m) 10 | show() 11 | -------------------------------------------------------------------------------- /zencad/examples/2.Operations/3.Sweep/extrude.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | """ 3 | ZenCad API example: extrude 4 | """ 5 | 6 | from zencad import * 7 | 8 | base = ngon(10,6) 9 | 10 | m0 = extrude(base, 10) 11 | m1 = extrude(base, (5,0,10)) 12 | m2 = extrude(base, (5,5,10)) 13 | 14 | disp(m0) 15 | disp(m1.forw(30)) 16 | disp(m2.forw(60)) 17 | show() -------------------------------------------------------------------------------- /zencad/examples/2.Operations/3.Sweep/pipe_shell.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | """ 3 | ZenCad API example: pipe_shell 4 | """ 5 | 6 | from zencad import * 7 | 8 | a = circle(r=20) 9 | b = circle(r=10).up(10) 10 | 11 | proto_wires = [ 12 | circle(10, wire=True), 13 | ellipse(10, 16, wire=True), 14 | ellipse(10, 20, wire=True), 15 | ellipse(10, 13, wire=True), 16 | circle(10, wire=True) 17 | ] 18 | 19 | spine = interpolate( 20 | [(0, 0, 0), (40, 0, 50), (80, 0, 100)], 21 | tangs=[(0, 0, 1), None, (0, 0, 1)]) 22 | 23 | uniform = spine.uniform(len(proto_wires)) 24 | 25 | wires = [ 26 | (move(*spine.d0(uniform[i])) * short_rotate((0, 0, 1), spine.d1(uniform[i])))( 27 | p) for i, p in enumerate(proto_wires)] 28 | 29 | m0 = pipe_shell(wires, spine, solid=True) 30 | m1 = pipe_shell(wires, spine, solid=False) 31 | 32 | disp(wires, color.red) 33 | disp(spine, color.red) 34 | disp([w.forw(50) for w in wires], color.red) 35 | 36 | disp(m0.forw(50)) 37 | disp(m1.forw(100)) 38 | 39 | show() 40 | -------------------------------------------------------------------------------- /zencad/examples/2.Operations/3.Sweep/pipe_shell_frenet.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | """ 3 | ZenCad API example: pipe_shell_frenet 4 | """ 5 | 6 | from zencad import * 7 | 8 | ps = [(20, 0, 0), (20, 0, 10), (30, 0, 5)] 9 | 10 | profile = polysegment(ps, closed=True) 11 | spine = helix(h=100, r=20, step=30) 12 | 13 | m0 = pipe_shell([profile], spine, frenet=False) 14 | m1 = pipe_shell([profile], spine, frenet=True, solid=False) 15 | m2 = pipe_shell([profile], spine, frenet=True, solid=True) 16 | 17 | disp(m0.right(140), color.red) 18 | disp(m1.right(70)) 19 | disp(m2) 20 | 21 | show() -------------------------------------------------------------------------------- /zencad/examples/2.Operations/3.Sweep/revol.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | """ 3 | ZenCad API example: revol 4 | """ 5 | 6 | 7 | from zencad import * 8 | 9 | # Make revols: 10 | a1 = square(10, center=True) 11 | a2 = circle(10) 12 | a3 = ngon(r=10, n=8) 13 | 14 | b1 = a1.rotateX(deg(90)).right(40) 15 | b2 = a2.rotateX(deg(90)).right(40) 16 | b3 = a3.rotateX(deg(90)).right(40) 17 | 18 | m1 = revol(b1) 19 | m2 = revol(a2, r=40) 20 | m3 = revol(b3) 21 | 22 | # Display revols: 23 | display(m1.left(110), color=color.mech) 24 | display(m2, color=color.mech) 25 | display(m3.right(110), color=color.mech) 26 | 27 | # Display it step by step: 28 | display(m1.left(110).forw(110), color=color.transmech) 29 | display(m2.forw(110), color=color.transmech) 30 | display(m3.right(110).forw(110), color=color.transmech) 31 | display(b1.left(110).forw(110)) 32 | display(b2.forw(110)) 33 | display(b3.right(110).forw(110)) 34 | display(a1.left(110).forw(110)) 35 | display(a2.forw(110)) 36 | display(a3.right(110).forw(110)) 37 | 38 | # Sector option example: 39 | y1 = revol(b1, yaw=math.pi) 40 | y2 = revol(b2, yaw=math.pi/2) 41 | y3 = revol(b3, yaw=-math.pi) 42 | display(y1.left(110).forw(220)) 43 | display(y2.forw(220)) 44 | display(y3.right(110).forw(220)) 45 | 46 | show() 47 | -------------------------------------------------------------------------------- /zencad/examples/2.Operations/3.Sweep/revol2.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | """ 3 | ZenCad API example: revol2 4 | """ 5 | 6 | from zencad import * 7 | 8 | proto0 = square(10, center=True) 9 | m00 = revol2(profile=proto0, r=20) 10 | m01 = revol2(profile=proto0, r=20, yaw=(0,deg(180)), roll=(0,deg(60))) 11 | m02 = revol2(profile=proto0, r=20, roll=(0,deg(720))) 12 | 13 | proto1 = square(10) 14 | m10 = revol2(profile=proto1, r=20) 15 | m11 = revol2(profile=proto1, r=20, yaw=(0,deg(180)), roll=(0,deg(60))) 16 | m12 = revol2(profile=proto1, r=20, n=60, yaw=(0,deg(360)), roll=(0,deg(360))) 17 | 18 | hl(proto0) 19 | display(m00) 20 | display(m01.movX(60)) 21 | display(m02.movX(120)) 22 | 23 | hl(proto1.movY(60)) 24 | display(m10.movY(60)) 25 | display(m11.movX(60).movY(60)) 26 | display(m12.movX(120).movY(60)) 27 | 28 | SECTS = False 29 | N = 120 30 | 31 | show() 32 | -------------------------------------------------------------------------------- /zencad/examples/2.Operations/3.Sweep/tube.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | # """ 3 | # ZenCad API example: tube 4 | # """ 5 | # Not suported yet 6 | 7 | # from zencad import * 8 | 9 | # POINTS = points([ 10 | # (0, 0, 5), 11 | # (0, 0, 20), 12 | # (5, 0, 25), 13 | # (20, 0, 25), 14 | # (25, 5, 25), 15 | # (25, 25, 25), 16 | # (25, 30, 30), 17 | # (25, 30, 50), 18 | # (20, 30, 55), 19 | # (5, 30, 55), 20 | # (0, 30, 50), 21 | # (0, 30, 5), 22 | # (0, 25, 0), 23 | # (0, 5, 0), 24 | # ]) 25 | 26 | # SPINE = sew([ 27 | # segment(POINTS[0], POINTS[1]), 28 | # interpolate([POINTS[1], POINTS[2]], tangs=[(0, 0, 1), (1, 0, 0)]), 29 | # segment(POINTS[2], POINTS[3]), 30 | # interpolate([POINTS[3], POINTS[4]], tangs=[(1, 0, 0), (0, 1, 0)]), 31 | # segment(POINTS[4], POINTS[5]), 32 | # interpolate([POINTS[5], POINTS[6]], tangs=[(0, 1, 0), (0, 0, 1)]), 33 | # segment(POINTS[6], POINTS[7]), 34 | # interpolate([POINTS[7], POINTS[8]], tangs=[(0, 0, 1), (-1, 0, 0)]), 35 | # segment(POINTS[8], POINTS[9]), 36 | # interpolate([POINTS[9], POINTS[10]], tangs=[(-1, 0, 0), (0, 0, -1)]), 37 | # segment(POINTS[10], POINTS[11]), 38 | # interpolate([POINTS[11], POINTS[12]], tangs=[(0, 0, -1), (0, -1, 0)]), 39 | # segment(POINTS[12], POINTS[13]), 40 | # interpolate([POINTS[13], POINTS[0]], tangs=[(0, -1, 0), (0, 0, 1)]), 41 | # ]) 42 | 43 | # OUTER_SHELL = tube(spine=SPINE, r=3) 44 | # INTERNAL_SHELL = tube(spine=SPINE, r=2) 45 | 46 | # MODEL = make_solid([INTERNAL_SHELL, OUTER_SHELL]) 47 | # CUTTED_MODEL = MODEL - halfspace() - halfspace().rotX(-deg(90)) - \ 48 | # halfspace().rotY(deg(90)) 49 | 50 | # S = 60 51 | # disp(MODEL) 52 | 53 | # disp(CUTTED_MODEL).right(S*1) 54 | 55 | # disp(INTERNAL_SHELL, color=(0.0, 0.0, 0.8, 0.7)).right(S*2) 56 | # disp(CUTTED_MODEL).right(S*2) 57 | 58 | # disp(INTERNAL_SHELL, color=(0.0, 0.0, 0.8, 0.7)).right(S*3) 59 | 60 | 61 | # show() 62 | -------------------------------------------------------------------------------- /zencad/examples/2.Operations/3.Sweep/tube_by_points.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | # Not suported yet 3 | # """ 4 | # ZenCad API example: tube_by_points 5 | # """ 6 | 7 | # from zencad import * 8 | 9 | # POINTS = [ 10 | # (0,0,0), 11 | # (0,0,20), 12 | # (0,20,40), 13 | # (-90,20,40), 14 | # (-90,20,20), 15 | # (0,20,0), 16 | # ] 17 | # spine = rounded_polysegment(POINTS, r=10) 18 | 19 | # a, a_start, a_finish = tube(spine, r=5, bounds=True) 20 | # b, b_start, b_finish = tube(spine, r=3, bounds=True) 21 | 22 | # c = a_start.fill() - b_start.fill() 23 | # d = a_finish.fill() - b_finish.fill() 24 | 25 | # m = sew([a,b,c,d]) 26 | 27 | # disp(m) 28 | # disp(a).forw(60) 29 | # disp(spine, color.green).forw(120) 30 | # ctrs = disp(points(POINTS), color.red) 31 | # for c in ctrs: c.forw(120) 32 | # show() 33 | -------------------------------------------------------------------------------- /zencad/examples/2.Operations/4.Mesh/triangulate.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | 3 | 4 | from zencad import * 5 | 6 | lazy.encache = False 7 | lazy.decache = False 8 | lazy.cached = False 9 | lazy.fastdo = True 10 | 11 | m0 = box(10, center=True) 12 | nodes, triangles = triangulate(m0, 0.5) 13 | 14 | nodes_unlazy = nodes.unlazy() 15 | nsize = len(nodes_unlazy) 16 | 17 | triangles_unlazy = triangles.unlazy() 18 | tsize = len(triangles_unlazy) 19 | 20 | print(f"Nodes: len:{nsize} : {nodes_unlazy}") 21 | print(f"Triangles: len:{tsize} : {triangles_unlazy}") 22 | 23 | m1 = polyhedron(nodes, triangles) 24 | 25 | disp(m0) 26 | disp(m1.right(20)) 27 | 28 | ################## 29 | 30 | m2 = cylinder(r=5, h=10, center=True) 31 | nodes, triangles = triangulate(m2, 0.5) 32 | 33 | nodes_unlazy = nodes.unlazy() 34 | nsize = len(nodes_unlazy) 35 | 36 | triangles_unlazy = triangles.unlazy() 37 | tsize = len(triangles_unlazy) 38 | 39 | print(f"Nodes: len:{nsize}") 40 | print(f"Triangles: len:{tsize}") 41 | 42 | m3 = polyhedron(nodes, triangles) 43 | 44 | disp(m2.forw(20)) 45 | disp(m3.forw(20).right(20)) 46 | 47 | ################## 48 | 49 | m4 = sphere(5) 50 | nodes, triangles = triangulate(m4, 0.5) 51 | 52 | nodes_unlazy = nodes.unlazy() 53 | nsize = len(nodes_unlazy) 54 | 55 | triangles_unlazy = triangles.unlazy() 56 | tsize = len(triangles_unlazy) 57 | 58 | print(f"Nodes: len:{nsize}") 59 | print(f"Triangles: len:{tsize}") 60 | 61 | m5 = polyhedron(nodes, triangles) 62 | 63 | disp(m4.forw(40)) 64 | disp(m5.forw(40).right(20)) 65 | 66 | ##################### 67 | 68 | show() 69 | -------------------------------------------------------------------------------- /zencad/examples/2.Operations/boolean.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | # coding: utf-8 3 | 4 | from zencad import * 5 | 6 | c1 = 100 7 | c2 = 130 8 | c3 = c2 / 2 + 20 9 | 10 | base = box(c1, c1, c1, center=True) 11 | 12 | f1 = ngon(r=35, n=3) 13 | f2 = ngon(r=35, n=5) 14 | f3 = circle(35) 15 | 16 | s1 = linear_extrude(f1, c2, center=True) 17 | s2 = linear_extrude(f2, c2, center=True).rotateY(deg(90)) 18 | s3 = linear_extrude(f3, c2, center=True).rotateX(deg(90)) 19 | 20 | m1 = base - s1 - s2 - s3 21 | m2 = base ^ s1 ^ s2 ^ s3 22 | m3 = s1 + s2 + s3 23 | 24 | ystep = 240 25 | xstep = 240 26 | 27 | fontname = "FreeSans" 28 | 29 | t1 = textshape("difference", fontname, 40) 30 | t1c = t1.center() 31 | t1 = t1.translate(-t1c.x, -t1c.y, 0).rotateZ(deg(45)) 32 | 33 | t2 = textshape("intersect", fontname, 40) 34 | t2c = t2.center() 35 | t2 = t2.translate(-t2c.x, -t2c.y, 0).rotateZ(deg(45)) 36 | 37 | t3 = textshape("union", fontname, 40) 38 | t3c = t3.center() 39 | t3 = t3.translate(-t3c.x, -t3c.y, 0).rotateZ(deg(45)) 40 | 41 | display(base.forw(ystep)) 42 | 43 | display(s1) 44 | display(s2.left(xstep)) 45 | display(s3.right(xstep)) 46 | 47 | display(m1.back(ystep)) 48 | display(m2.left(xstep).back(ystep)) 49 | display(m3.right(xstep).back(ystep)) 50 | 51 | display(t1.back(ystep).up(c3), color=(1, 1, 0)) 52 | display(t2.left(xstep).back(ystep).up(c3), color=(1, 1, 0)) 53 | display(t3.right(xstep).back(ystep).up(c3), color=(1, 1, 0)) 54 | 55 | disp(s1.left(xstep).back(ystep), color=(0.5, 0, 0, 0.95)) 56 | disp(s2.left(xstep).back(ystep), color=(0.5, 0, 0, 0.95)) 57 | disp(s3.left(xstep).back(ystep), color=(0.5, 0, 0, 0.95)) 58 | 59 | disp(s1.back(ystep), color=(0.5, 0, 0, 0.95)) 60 | disp(s2.back(ystep), color=(0.5, 0, 0, 0.95)) 61 | disp(s3.back(ystep), color=(0.5, 0, 0, 0.95)) 62 | 63 | show() 64 | -------------------------------------------------------------------------------- /zencad/examples/2.Operations/unify.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | # coding: utf-8 3 | 4 | from zencad import * 5 | 6 | m = circle(10) + square(17, center=True) 7 | 8 | m0 = m 9 | m1 = unify(m) 10 | m2 = m.extrude(10) 11 | m3 = unify(m).extrude(10) 12 | 13 | display(m0) 14 | display(m1.right(30)) 15 | display(m2.forw(30)) 16 | display(m3.right(30).forw(30)) 17 | 18 | show() 19 | -------------------------------------------------------------------------------- /zencad/examples/3.Animation/base.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | # coding: utf-8 3 | 4 | from zencad import * 5 | import time 6 | 7 | s = box(10, center=True) 8 | controller = disp(s) 9 | 10 | nulltime = time.time() 11 | 12 | def animate(widget): 13 | trans = rotateZ(time.time() - nulltime) * right(30) 14 | controller.relocate(trans) 15 | 16 | show(animate=animate) 17 | -------------------------------------------------------------------------------- /zencad/examples/3.Animation/camera.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | # coding: utf-8 3 | 4 | from zencad import * 5 | import time 6 | 7 | s = box(10, center=True) 8 | controller = disp(s) 9 | 10 | 11 | def animate(wdg): 12 | if not wdg.mousedown: 13 | wdg.set_eye(zencad.rotateZ(zencad.deg(-0.8))(wdg.eye()), orthogonal=True) 14 | 15 | 16 | show(animate=animate) 17 | -------------------------------------------------------------------------------- /zencad/examples/3.Animation/change_color.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | """ 3 | ZenCad API example: Color object animation. 4 | last update: 13.10.2019 5 | """ 6 | 7 | from zencad import * 8 | import random 9 | 10 | s = icosahedron(10) 11 | #s = dodecahedron(10) 12 | #s = icosahedron(10).fillet(2) 13 | 14 | controller = disp(s) 15 | transparent = 0.05 16 | 17 | clr = Color(0.5, 0.5, 0.5, transparent) 18 | 19 | 20 | def animate(wdg): 21 | global clr 22 | 23 | def change(old): 24 | new = old + random.uniform(-0.02, 0.02) 25 | if new > 1 or new < 0: 26 | return old 27 | return new 28 | 29 | clr = Color(change(clr.r), change(clr.g), change(clr.b), transparent) 30 | controller.set_color(clr) 31 | 32 | 33 | show(animate=animate) 34 | -------------------------------------------------------------------------------- /zencad/examples/3.Animation/color.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | """ 3 | ZenCad API example: Color object animation. 4 | last update: 13.10.2019 5 | """ 6 | 7 | from zencad import * 8 | import random 9 | 10 | #s = icosahedron(10) 11 | s = dodecahedron(10) 12 | #s = icosahedron(10).fillet(2) 13 | 14 | controller = disp(s) 15 | transparent = 0.05 16 | 17 | clr = Color(0.5, 0.5, 0.5, transparent) 18 | 19 | 20 | def animate(wdg): 21 | global clr 22 | 23 | def change(old): 24 | new = old + random.uniform(-0.02, 0.02) 25 | if new > 1 or new < 0: 26 | return old 27 | return new 28 | 29 | clr = Color(change(clr.r), change(clr.g), change(clr.b), transparent) 30 | controller.set_color(clr) 31 | 32 | 33 | show(animate=animate) 34 | -------------------------------------------------------------------------------- /zencad/examples/3.Animation/pacman.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | # coding: utf-8 3 | 4 | from zencad import * 5 | import zencad.assemble 6 | import time 7 | 8 | 9 | class Pacman(zencad.assemble.unit): 10 | def __init__(self): 11 | super().__init__() 12 | self.rot0 = zencad.assemble.rotator(axis=(0, 1, 0), parent=self) 13 | self.rot1 = zencad.assemble.rotator(axis=(0, 1, 0), parent=self) 14 | 15 | self.part0 = zencad.assemble.unit() 16 | self.part1 = zencad.assemble.unit() 17 | 18 | angle = deg(180) 19 | upper = (sphere(r=30, yaw=angle) 20 | - sphere(r=10).move(-25, 20, 15) 21 | - sphere(r=10).move(-25, 20, -15) 22 | ) 23 | self.part0.add(upper.rotateZ(0).rotateX(deg(90)), color.yellow) 24 | self.part0.add(sphere(3).move(-20, 12, 15), color.green) 25 | self.part0.add(sphere(3).move(-20, -12, 15), color.blue) 26 | self.part1.add( 27 | sphere(r=30, yaw=angle).rotateZ(-angle).rotateX(deg(90)), color.yellow) 28 | 29 | self.rot0.link(self.part0) 30 | self.rot1.link(self.part1) 31 | 32 | 33 | pacman = Pacman() 34 | pacman.rot0.set_coord(deg(30)) 35 | pacman.rot1.set_coord(-deg(30)) 36 | 37 | disp(pacman) 38 | 39 | R = 30 40 | N = 4 41 | 42 | sph0 = disp(sphere(r=3)) 43 | sph1 = disp(sphere(r=3)) 44 | sph2 = disp(sphere(r=3)) 45 | sph3 = disp(sphere(r=3)) 46 | 47 | sph0.relocate(move(-R)) 48 | sph1.relocate(move(-R*2)) 49 | sph2.relocate(move(-R*3)) 50 | sph3.relocate(move(-R*4)) 51 | 52 | spharr = [sph0, sph1, sph2, sph3] 53 | 54 | lastiter = 0 55 | start_time = time.time() 56 | 57 | 58 | def animate(wdg): 59 | global lastiter 60 | t = time.time() - start_time 61 | t = t + 0 62 | 63 | T = 1 64 | if t > T*4*2: 65 | return 66 | 67 | iteration = int((t + T) / (2*T)) 68 | if lastiter != iteration: 69 | spharr[lastiter].hide(True) 70 | lastiter = iteration 71 | 72 | lt = t - int(t / (2*T)) * 2*T 73 | 74 | if 0 < lt < T: 75 | pacman.rot0.set_coord(deg(30) * (T - lt)) 76 | pacman.rot1.set_coord(-deg(30) * (T - lt)) 77 | 78 | if T < lt < 2*T: 79 | pacman.rot0.set_coord(deg(30) * (lt-T)) 80 | pacman.rot1.set_coord(-deg(30) * (lt-T)) 81 | 82 | pacman.relocate(translate(-t*R/T/2, 0, 0)) 83 | pacman.location_update() 84 | 85 | 86 | show(animate=animate) 87 | -------------------------------------------------------------------------------- /zencad/examples/4.Assemble/EulerAngles.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | 3 | # ZenCad Example: SimpleAssemble.py 4 | 5 | from zencad import * 6 | import time 7 | import zencad.assemble 8 | 9 | yaw_unit = zencad.assemble.unit() 10 | pitch_unit = zencad.assemble.unit(parent=yaw_unit) 11 | roll_unit = zencad.assemble.unit(parent=pitch_unit) 12 | model_unit = zencad.assemble.unit( 13 | parent=roll_unit, 14 | parts=[box(20,10,5,center=True) + box(10,20,5,center=True)]) 15 | 16 | yaw_unit.add_triedron(length=25, arrlen=2) 17 | pitch_unit.add_triedron(length=20, arrlen=2) 18 | roll_unit.add_triedron(length=15, arrlen=2) 19 | 20 | # Display ROOT unit 21 | disp(yaw_unit) 22 | 23 | T = 4 24 | W = deg(60) 25 | starttime = time.time() 26 | def animate(wdg): 27 | fromstart = time.time() - starttime 28 | 29 | if fromstart < T: 30 | yaw_unit.relocate(rotateZ(fromstart / T * W), deep=True) 31 | elif fromstart < 2*T: 32 | pitch_unit.relocate(rotateY((fromstart - T) / T * W), deep=True) 33 | elif fromstart < 3*T: 34 | roll_unit.relocate(rotateX((fromstart - 2*T) / T * W), deep=True) 35 | 36 | 37 | show(animate = animate) -------------------------------------------------------------------------------- /zencad/examples/4.Assemble/manual-control.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | """ 3 | ZenCad example: manual-control 4 | 5 | We can control current object position in real time. 6 | In that example we create special widget to change link`s positions by sliders. 7 | """ 8 | 9 | from zencad import * 10 | import zencad.assemble 11 | 12 | from PyQt5.QtWidgets import * 13 | from PyQt5.QtCore import * 14 | from PyQt5.QtGui import * 15 | 16 | CTRWIDGET = None 17 | SLDS = None 18 | 19 | 20 | class Slider(QSlider): 21 | def __init__(self): 22 | super().__init__(Qt.Horizontal) 23 | self.setRange(0, 10000) 24 | self.setValue(5000) 25 | self.setSingleStep(1) 26 | 27 | 28 | class link(zencad.assemble.unit): 29 | def __init__(self, h=40, axis=(0, 1, 0)): 30 | super().__init__() 31 | self.add(cylinder(5, h) + cylinder(6, 10, 32 | center=True).transform(up(h) * short_rotate((0, 0, 1), axis))) 33 | self.rotator = zencad.assemble.rotator( 34 | parent=self, axis=axis, location=up(h)) 35 | 36 | 37 | a = link(axis=(0, 1, 0)) 38 | b = link(axis=(1, 0, 0)) 39 | c = link(axis=(0, 1, 0)) 40 | d = link(axis=(1, 0, 0)) 41 | 42 | a.rotator.link(b) 43 | b.rotator.link(c) 44 | c.rotator.link(d) 45 | d.rotator.output.add(cone(5, 12, 40).up(10) + cylinder(5, 10)) 46 | 47 | LINKS = [a, b, c, d] 48 | 49 | disp(a) 50 | 51 | 52 | def preanimate(widget, animate_thread): 53 | global CTRWIDGET, SLDS 54 | CTRWIDGET = QWidget() 55 | layout = QVBoxLayout() 56 | SLDS = [Slider() for i in range(len(LINKS))] 57 | 58 | for sld in SLDS: 59 | layout.addWidget(sld) 60 | 61 | CTRWIDGET.setLayout(layout) 62 | CTRWIDGET.setWindowFlags(Qt.WindowStaysOnTopHint | Qt.Dialog) 63 | CTRWIDGET.show() 64 | 65 | 66 | def animate(wdg): 67 | for i in range(len(LINKS)): 68 | LINKS[i].rotator.set_coord( 69 | (SLDS[i].value() - 5000) / 10000 * math.pi * 2) 70 | a.location_update() 71 | 72 | 73 | def close_handle(): 74 | CTRWIDGET.close() 75 | 76 | 77 | show(animate=animate, preanimate=preanimate, close_handle=close_handle) 78 | -------------------------------------------------------------------------------- /zencad/examples/Integration/pillow/senku.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/zencad/examples/Integration/pillow/senku.png -------------------------------------------------------------------------------- /zencad/examples/Integration/pillow/smile.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/zencad/examples/Integration/pillow/smile.png -------------------------------------------------------------------------------- /zencad/examples/Integration/pillow/smile.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | 3 | from zencad import * 4 | from PIL import Image 5 | import numpy 6 | import evalcache 7 | 8 | 9 | @lazy 10 | def numpy_highmap(arr): 11 | result = numpy.ndarray(arr.shape, dtype=point3) 12 | 13 | for i in range(arr.shape[0]): 14 | for j in range(arr.shape[1]): 15 | result[i, j] = point3(i, j, arr[i, j]) 16 | 17 | return result 18 | 19 | 20 | img = Image.open('senku.png').convert('L') 21 | arr = numpy.asarray(img) 22 | 23 | pnts = numpy_highmap((1-arr/255)*8) 24 | m = interpolate2(pnts, degmin=3, degmax=7) 25 | 26 | disp(m) 27 | show() 28 | -------------------------------------------------------------------------------- /zencad/examples/Integration/skimage-mechanicus/cube.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | 3 | import numpy as np 4 | 5 | import sys 6 | from skimage import measure, io 7 | from itertools import chain 8 | 9 | import time 10 | import math 11 | import zencad 12 | 13 | from zencad import * 14 | import mech 15 | 16 | mechanicus, base, ignore = mech.build() 17 | 18 | cube = box(1000, center=True) 19 | 20 | mech = [disp(mechanicus, color=(1, 1, 1)) for i in range(0, 6)] 21 | base = [disp(base, color=(0.2, 0.2, 0.2)) for i in range(0, 6)] 22 | 23 | 24 | def animate(wdg): 25 | t = time.time() 26 | trans = rotateZ(t) * translate(0, 0, 500) 27 | mech[0].relocate(trans) 28 | base[0].relocate(trans) 29 | mech[1].relocate(rotateX(deg(180)) * trans) 30 | base[1].relocate(rotateX(deg(180)) * trans) 31 | mech[2].relocate(rotateX(deg(90)) * trans) 32 | base[2].relocate(rotateX(deg(90)) * trans) 33 | mech[3].relocate(rotateX(deg(90)) * rotateX(deg(180)) * trans) 34 | base[3].relocate(rotateX(deg(90)) * rotateX(deg(180)) * trans) 35 | mech[4].relocate(rotateY(deg(90)) * trans) 36 | base[4].relocate(rotateY(deg(90)) * trans) 37 | mech[5].relocate(rotateY(deg(90)) * rotateX(deg(180)) * trans) 38 | base[5].relocate(rotateY(deg(90)) * rotateX(deg(180)) * trans) 39 | 40 | 41 | display(cube, color=(0.3, 0.2, 0.2)) 42 | show(animate=animate) 43 | -------------------------------------------------------------------------------- /zencad/examples/Integration/skimage-mechanicus/image.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/zencad/examples/Integration/skimage-mechanicus/image.png -------------------------------------------------------------------------------- /zencad/examples/Integration/svg.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | #coding: utf-8 3 | 4 | from tempfile import mkstemp 5 | from zencad import * 6 | lazy.fastdo = True 7 | 8 | m0 = \ 9 | ( 10 | zencad.rectangle(10,20) 11 | + zencad.rectangle(10,20,center=True) 12 | + zencad.ellipse(10,8) 13 | -zencad.circle(5) 14 | ) 15 | 16 | svg = to_svg_string(m0) 17 | m1 = from_svg_string(svg) 18 | 19 | fd, path = mkstemp() 20 | to_svg(m0, path) 21 | m2 = from_svg(path) 22 | 23 | disp(m0) 24 | disp(m1.right(25)) 25 | disp(m2.right(50)) 26 | 27 | ### 28 | 29 | m3 = box(20, center=True) - torus(7,3) - torus(7,3).rotX(deg(90)) + box(10, center=True).up(15) 30 | m3 = m3.rotateX(deg(70)).rotateY(deg(30)) 31 | m4 = m3 ^ infplane() 32 | 33 | hl(m3.move(0,45)) 34 | disp(m4.move(0,45)) 35 | disp(m4.move(35,45)) 36 | 37 | # BSPLINE : TODO 38 | #svg = to_svg_string(m4) 39 | #m5 = from_svg_string(svg) 40 | 41 | #disp(m5.move(70,45)) 42 | 43 | show() 44 | -------------------------------------------------------------------------------- /zencad/examples/Integration/trimesh/README.md: -------------------------------------------------------------------------------- 1 | Models: 2 | Bulbasaur: https://www.thingiverse.com/thing:327753 3 | -------------------------------------------------------------------------------- /zencad/examples/Integration/trimesh/bulbasaur.STL: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/zencad/examples/Integration/trimesh/bulbasaur.STL -------------------------------------------------------------------------------- /zencad/examples/Integration/trimesh/bulbasaur.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | 3 | import zencad 4 | 5 | try: 6 | import trimesh 7 | except: 8 | raise Exception( 9 | "You should install `trimesh` module for start this script") 10 | 11 | h = 10 12 | r = 30 13 | 14 | mesh = trimesh.load('bulbasaur.STL') 15 | bulb = zencad.polyhedron(mesh.vertices, mesh.faces) 16 | 17 | x, y, z = bulb.center() 18 | bulb = bulb.move(-x, -y, -z) 19 | bbox = bulb.bbox() 20 | bulb = bulb.up(-bbox.zrange()[0] + h) 21 | base = zencad.cylinder(r, h) 22 | 23 | m = base + bulb 24 | 25 | zencad.disp(m) 26 | zencad.show() 27 | -------------------------------------------------------------------------------- /zencad/examples/Models/bottle.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | # coding: utf-8 3 | 4 | from zencad import * 5 | import zencad.geom.surface as surface 6 | import zencad.geom.curve2 as curve2 7 | 8 | lazy.fastdo = True 9 | lazy.encache = False 10 | lazy.decache = False 11 | 12 | height = 70 13 | width = 50 14 | thickness = 30 15 | 16 | # BASE 17 | pnt1 = point3(-width / 2, 0, 0) 18 | pnt2 = point3(-width / 2, -thickness / 4, 0) 19 | pnt3 = point3(0, -thickness / 2, 0) 20 | pnt4 = point3(width / 2, -thickness / 4, 0) 21 | pnt5 = point3(width / 2, 0, 0) 22 | 23 | edge1 = segment(pnt1, pnt2) 24 | edge2 = circle_arc(pnt2, pnt3, pnt4) 25 | edge3 = segment(pnt4, pnt5) 26 | 27 | wire = sew([edge1, edge2, edge3]) 28 | profile = sew([wire, wire.mirrorX()]) 29 | body = profile.fill().extrude(height) 30 | body = fillet(body, thickness / 12) 31 | hl(body.forw(140)) 32 | 33 | # NECK 34 | neck_radius = thickness / 4.0 35 | neck_height = height / 10 36 | neck = cylinder(r=neck_radius, h=neck_height).up(height) 37 | body = body + neck 38 | hl(body.forw(100)) 39 | 40 | # THICK 41 | body = thicksolid(body, -thickness / 50, [point3(0, 0, height + height / 10)]) 42 | hl(body.forw(60)) 43 | 44 | # THREAD 45 | cylsurf1 = surface.cylinder(neck_radius * 0.99) 46 | cylsurf2 = surface.cylinder(neck_radius * 1.05) 47 | 48 | major = 2 * math.pi 49 | minor = neck_height / 10 50 | angle = math.atan2(neck_height / 4, 2 * math.pi) 51 | 52 | ellipse1 = curve2.ellipse(major, minor).rotate(angle) 53 | arc1 = cylsurf1.map(curve2.trimmed_curve2(ellipse1, 0, math.pi)) 54 | segment1 = cylsurf1.map(curve2.segment( 55 | ellipse1.value(0), ellipse1.value(math.pi))) 56 | 57 | ellipse2 = curve2.ellipse(major, minor / 4).rotate(angle) 58 | arc2 = cylsurf2.map(curve2.trimmed_curve2(ellipse2, 0, math.pi)) 59 | segment2 = cylsurf2.map(curve2.segment( 60 | ellipse2.value(0), ellipse2.value(math.pi))) 61 | 62 | m1 = sew([arc1, segment1]) 63 | m2 = sew([arc2, segment2]) 64 | thread = loft([m1, m2]).up(height + neck_height / 2) 65 | 66 | hl(m1.up(height + neck_height / 2).right(80)) 67 | hl(m2.up(height + neck_height / 2).right(60)) 68 | hl(thread.right(40)) 69 | 70 | # FINAL 71 | m = thread + body 72 | 73 | display(m) 74 | show() 75 | -------------------------------------------------------------------------------- /zencad/examples/Models/cup.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | # coding: utf-8 3 | 4 | from zencad import * 5 | 6 | thikness = 2.5 7 | height = 90 8 | radius = 40 9 | handle_radius = 5 10 | 11 | pnts = points([(-5, -5), (0, 0), (27, 40), (25, 50), (5, 60), (-5, 60)]) 12 | 13 | tangs = vectors([(1, 1), (1, 1), (0, 0), (0, 0), (0, 0), (0, 0)]) 14 | 15 | # Base: 16 | base = cylinder(r=radius, h=height) 17 | hole = cylinder(r=radius - thikness, h=height - thikness).up(thikness) 18 | 19 | # Handle: 20 | spine = interpolate(pnts, tangs).rotateX(deg(90)) 21 | profile = circle(handle_radius).rotateY( 22 | deg(45)).translate(pnts[0].x, 0, pnts[0].y) 23 | handle = pipe(spine=spine, shp=profile) 24 | 25 | # Assemble: 26 | cup = base + handle.right(40).up(17) - hole 27 | 28 | # Display: 29 | hl(spine.right(100).up(17).forw(20)) 30 | hl(profile.right(100).up(17).forw(20)) 31 | hl(handle.right(100).up(17).back(20)) 32 | display(cup) 33 | 34 | show() 35 | -------------------------------------------------------------------------------- /zencad/examples/Models/logo.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | # coding: utf-8 3 | 4 | import evalcache 5 | from zencad import * 6 | 7 | mandarinc = os.path.join(zencad.moduledir, "examples", "fonts/mandarinc.ttf") 8 | fontpath = register_font(mandarinc) 9 | 10 | NUT_RENDER = True 11 | DISPLAY_BOLT = False 12 | 13 | 14 | @lazy 15 | def instrument_metric_nut(drad, step, h): 16 | H = step * math.tan(deg(60)) 17 | 18 | pseg = polysegment( 19 | points( 20 | [ 21 | (drad + H / 2, 0, 0), 22 | (drad - H / 4, 0, -(3 / 8 * step)), 23 | (drad - H / 4, 0, -(5 / 8 * step)), 24 | (drad + H / 2, 0, -step), 25 | ] 26 | ), 27 | closed=True, 28 | ) 29 | 30 | path = helix(r=drad, h=h, step=step) 31 | base = pipe_shell(spine=path, arr=[pseg], frenet=True) 32 | return base 33 | 34 | 35 | @lazy 36 | def metric_nut(d, step, h, render=False): 37 | H = step * math.tan(deg(60)) 38 | drad = d / 2 - 3 / 8 * H 39 | cil = cylinder(r=d / 2, h=h) 40 | instr = instrument_metric_nut(drad=drad, step=step, h=h + step) 41 | 42 | if render: 43 | print("Please wait. It may take a while.") 44 | return cil - instr 45 | else: 46 | return cil 47 | 48 | 49 | nut = metric_nut(8, 1.25, 50, render=NUT_RENDER) 50 | 51 | bolt = ( 52 | nut.up(15.3) 53 | + cylinder(r=8 / 2, h=10).up(5.3) 54 | + linear_extrude(ngon(r=7.1, n=6), (0, 0, 5.3)) 55 | ).rotateY(deg(90)) 56 | 57 | l = 70.68 58 | w = 13.5 59 | h = 8.5 60 | 61 | base = loft([ 62 | rectangle(l, w, center=True, wire=True), 63 | rectangle(l+5, w+5, center=True, wire=True).down(h) 64 | ]) 65 | bolt = bolt.left(l/2 - 2.3) 66 | 67 | m = textshape("ZenCad", "Mandarinc", 20) 68 | m = m.translate(- m.center()) 69 | m = m.extrude(6) + base 70 | m = m - bolt 71 | 72 | if DISPLAY_BOLT: 73 | disp(bolt) 74 | 75 | disp(m, color=(0.6, 1, 1, 0.3)) 76 | show() 77 | -------------------------------------------------------------------------------- /zencad/examples/Models/nut.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | # coding: utf-8 3 | 4 | from zencad import * 5 | 6 | 7 | @lazy 8 | def instrument_metric_nut(drad, step, h): 9 | H = step * math.tan(deg(60)) 10 | 11 | pseg = polysegment( 12 | points( 13 | [ 14 | (drad + H / 2, 0, 0), 15 | (drad - H / 4, 0, -(3 / 8 * step)), 16 | (drad - H / 4, 0, -(5 / 8 * step)), 17 | (drad + H / 2, 0, -step), 18 | ] 19 | ), 20 | closed=True, 21 | ) 22 | 23 | path = helix(r=drad, h=h, step=step) 24 | base = pipe_shell([pseg], path, frenet=True) 25 | return base 26 | 27 | 28 | @lazy 29 | def metric_nut(d, step, h): 30 | H = step * math.tan(deg(60)) 31 | drad = d / 2 - 3 / 8 * H 32 | cil = cylinder(r=d / 2, h=h) 33 | instr = instrument_metric_nut(drad=drad, step=step, h=h + step) 34 | ret = cil - instr 35 | 36 | return ret 37 | 38 | 39 | nut = metric_nut(8, 1.25, 40) 40 | 41 | m = ( 42 | nut.up(25.3) 43 | + cylinder(r=8 / 2, h=20).up(5.3) 44 | + linear_extrude(ngon(r=7.1, n=6), (0, 0, 5.3)) 45 | ) 46 | 47 | if len(sys.argv) > 1 and sys.argv[1] == "summ": 48 | m = m + m.rotateX(deg(45)).forw(25).up(10) 49 | 50 | if len(sys.argv) > 1 and sys.argv[1] == "summ2": 51 | m = m + m.rotateX(deg(45)).forw(25).up(10) 52 | m = m + m.right(40) + m.right(80) 53 | 54 | display(m) 55 | show() 56 | -------------------------------------------------------------------------------- /zencad/examples/Models/organizer/assembly.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | 3 | import case 4 | import organizer 5 | from zencad import * 6 | 7 | w = 27 8 | h = 20 9 | l = 64 10 | t = 1.5 11 | r = 27 / 2 - 4 12 | z = 1 13 | s = 0.965 14 | 15 | d = 5 16 | d2 = 5 17 | 18 | m = 3 19 | n = 5 20 | 21 | st = organizer.organizer(m, n, w, h, l, t, d, d2) 22 | cs = case.case(w, h, l, t, r, z, s) 23 | 24 | ucs = union( 25 | [ 26 | cs.translate(t * 1.5 + (w + t) * i, 0, t + (h + t) * j) 27 | for i in range(0, m) 28 | for j in range(0, n) 29 | ] 30 | ) 31 | 32 | disp(ucs) 33 | disp(st, color=(1, 1, 1)) 34 | show() 35 | -------------------------------------------------------------------------------- /zencad/examples/Models/organizer/case.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | # coding: utf-8 3 | 4 | from zencad import * 5 | 6 | 7 | def case(w, h, l, t, r, z, s): 8 | w = w * s 9 | h = h * 0.95 10 | 11 | return ( 12 | box(w, l, h) 13 | - box(w - 2 * t, l - 2 * t, h - t).translate(t, t, t) 14 | - cylinder(r=r, h=t + 1).rotateX(deg(90)).translate(w / 2, t + 0.5, h) 15 | + box(w - 2 * t, z * 2, h - r).translate(t, -z * 2, 0) 16 | - box(w - 2 * t - 2 * z, z, h - r - z).translate(t + z, -z, z) 17 | - box(w - 2 * t - 6 * z, z, h - r - 2 * z).translate(t + z * 3, -2 * z, 2 * z) 18 | ) 19 | 20 | 21 | if __name__ == "__main__": 22 | m = case(w=27, h=20, l=64, t=1.5, r=27 / 2 - 4, z=1, s=0.965) 23 | 24 | display(m) 25 | show() 26 | -------------------------------------------------------------------------------- /zencad/examples/Models/organizer/organizer.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | # coding: utf-8 3 | 4 | from zencad import * 5 | 6 | 7 | def section(w, h, l, t, d, d2): 8 | return ( 9 | box(2 * t + w, t + l, 2 * t + h) 10 | - box(w, l, h).translate(t, 0, t) 11 | - box(w - 2 * d, l, h + 2 * t).translate(t + d, 0, 0) 12 | - box(w, l + t, h - d2).translate(t, 0, d2 + t) 13 | ) 14 | 15 | 16 | # n, m - параметры матрицы. 17 | # w,h,l - параметры нишы. 18 | # t - толщина стенок. 19 | # d - выступ поддержки. 20 | # d2 - высота заднего бампера. 21 | def organizer(m, n, w, h, l, t, d, d2): 22 | sect = section(w, h, l, t, d, d2) 23 | line = union([sect.translate(j * (w + t), 0, 0) for j in range(0, m)]) 24 | 25 | arr = [] 26 | for i in range(0, n): 27 | arr.append(line.up(i * (h + t))) 28 | 29 | arr.append(box(w * m + t * (m + 1), l + t, t)) 30 | arr.append(box(w * m + t * (m + 1), l + t, t).up(n * (h + t))) 31 | 32 | return union(arr) 33 | 34 | 35 | if __name__ == "__main__": 36 | m = organizer(3, 5, 27, 20, 64, 1.5, 5, 5) 37 | 38 | display(m) 39 | show() 40 | -------------------------------------------------------------------------------- /zencad/examples/OpenscadLike/csg.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | # coding: utf-8 3 | 4 | from zencad import * 5 | 6 | m1 = box(15, center=True) + sphere(10) 7 | m2 = box(15, center=True) ^ sphere(10) 8 | m3 = box(15, center=True) - sphere(10) 9 | 10 | display(m1.left(24)) 11 | display(m2) 12 | display(m3.right(24)) 13 | 14 | show() 15 | -------------------------------------------------------------------------------- /zencad/examples/OpenscadLike/logo.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | # coding: utf-8 3 | 4 | from zencad import * 5 | 6 | 7 | def logo(size=50): 8 | hole = size / 2 9 | cylinderHeight = size * 1.25 10 | 11 | cil = cylinder(r=hole / 2, h=cylinderHeight, center=True) 12 | m = sphere(r=size / 2) - cil - cil.rotateX(deg(90)) - cil.rotateY(deg(90)) 13 | 14 | return m, cil 15 | 16 | 17 | m, cil = logo(50) 18 | 19 | hl(cil.rotateX(deg(90))) 20 | disp(m) 21 | 22 | show() 23 | -------------------------------------------------------------------------------- /zencad/examples/fonts/mandarinc.ttf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/zencad/examples/fonts/mandarinc.ttf -------------------------------------------------------------------------------- /zencad/examples/fonts/testfont.ttf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/zencad/examples/fonts/testfont.ttf -------------------------------------------------------------------------------- /zencad/geom/boolops_base.py: -------------------------------------------------------------------------------- 1 | from OCC.Core.BRepAlgoAPI import BRepAlgoAPI_Fuse, BRepAlgoAPI_Cut, BRepAlgoAPI_Common 2 | 3 | 4 | def occ_pair_union(a, b): 5 | algo = BRepAlgoAPI_Fuse(a, b) 6 | algo.Build() 7 | if not algo.IsDone(): 8 | raise Exception("warn: union algotithm failed\n") 9 | return algo.Shape() 10 | 11 | 12 | def occ_pair_difference(a, b): 13 | algo = BRepAlgoAPI_Cut(a, b) 14 | algo.Build() 15 | if not algo.IsDone(): 16 | raise Exception("warn: difference algotithm failed\n") 17 | return algo.Shape() 18 | 19 | 20 | def occ_pair_intersect(a, b): 21 | algo = BRepAlgoAPI_Common(a, b) 22 | algo.Build() 23 | if not algo.IsDone(): 24 | raise Exception("warn: intersect algotithm failed\n") 25 | return algo.Shape() 26 | -------------------------------------------------------------------------------- /zencad/geom/curve2.py: -------------------------------------------------------------------------------- 1 | from OCC.Core.BRepBuilderAPI import BRepBuilderAPI_MakeFace 2 | from OCC.Core.Geom import Geom_CylindricalSurface 3 | from OCC.Core.Geom2d import Geom2d_Ellipse, Geom2d_Curve 4 | from OCC.Core.gp import gp_Pnt, gp_Vec, gp_Ax3, gp_Dir, gp_Ax2d, gp_Dir2d, gp_Pnt2d, gp_Trsf2d 5 | from OCC.Core.Geom2d import Geom2d_TrimmedCurve 6 | from OCC.Core.GCE2d import GCE2d_MakeSegment 7 | 8 | from zencad.util import point3, vector3 9 | from zencad.lazifier import * 10 | 11 | import evalcache 12 | 13 | 14 | class Curve2: 15 | def __init__(self, crv): 16 | self._crv = crv 17 | 18 | def Curve2(self): 19 | return self._crv 20 | 21 | def rotate(self, angle): 22 | trsf = gp_Trsf2d() 23 | trsf.SetRotation(gp_Pnt2d(0, 0), angle) 24 | return Curve2(Geom2d_Curve.DownCast(self._crv.Transformed(trsf))) 25 | 26 | def value(self, arg): 27 | return self.Curve2().Value(arg) 28 | 29 | 30 | class nocached_curve2_generator(evalcache.LazyObject): 31 | """ Decorator for heavy functions. 32 | It use caching for lazy data restoring.""" 33 | 34 | def __init__(self, *args, **kwargs): 35 | evalcache.LazyObject.__init__(self, *args, **kwargs) 36 | 37 | def __call__(self, *args, **kwargs): 38 | return self.lazyinvoke( 39 | self, args, kwargs, 40 | encache=False, 41 | decache=False, 42 | cls=evalcache.LazyObject 43 | ) 44 | 45 | 46 | def _ellipse(r1, r2): 47 | return Curve2(Geom2d_Ellipse(gp_Ax2d(gp_Pnt2d(0, 0), gp_Dir2d(1, 0)), r1, r2)) 48 | 49 | 50 | @lazy.lazy(cls=nocached_curve2_generator) 51 | def ellipse(r1, r2): 52 | return _ellipse(r1, r2) 53 | 54 | 55 | def _trimmed_curve2(crv, a, b): 56 | return Curve2(Geom2d_TrimmedCurve(crv.Curve2(), a, b)) 57 | 58 | 59 | @lazy.lazy(cls=nocached_curve2_generator) 60 | def trimmed_curve2(crv, a, b): 61 | return _trimmed_curve2(crv, a, b) 62 | 63 | 64 | def _segment(a, b): 65 | return Curve2(GCE2d_MakeSegment(a, b).Value()) 66 | 67 | 68 | @lazy.lazy(cls=nocached_curve2_generator) 69 | def segment(a, b): 70 | return _segment(a, b) 71 | -------------------------------------------------------------------------------- /zencad/geom/general_transformation.py: -------------------------------------------------------------------------------- 1 | import sys 2 | import numpy 3 | import pickle 4 | import base64 as b64 5 | 6 | from OCC.Core.gp import gp_GTrsf, gp_Trsf, gp_Mat, gp_Vec, gp_Ax1, gp_Ax2, gp_Pnt, gp_Dir, gp_XYZ, gp_Quaternion 7 | 8 | import zencad.util 9 | #from zencad.util import point3, vector3 10 | 11 | 12 | class GeneralTransformation: 13 | def __init__(self, gtrsf): 14 | self._gtrsf = gtrsf 15 | 16 | def __call__(self, obj): 17 | return obj.transform(self) 18 | 19 | def __mul__(self, oth): 20 | return Transformation(self._gtrsf.Multiplied(oth._gtrsf)) 21 | 22 | def __getstate__(self): 23 | mat = self._gtrsf.VectorialPart() 24 | tra = self._gtrsf.TranslationPart() 25 | 26 | col1 = mat.Column(0) 27 | col2 = mat.Column(1) 28 | col3 = mat.Column(2) 29 | 30 | return { 31 | "col1": (col1.X(), col1.Y(), col1.Z()), 32 | "col2": (col2.X(), col2.Y(), col2.Z()), 33 | "col3": (col3.X(), col3.Y(), col3.Z()), 34 | "transl": (tra.X(), tra.Y(), tra.Z()), 35 | } 36 | 37 | def __setstate__(self, dct): 38 | col1 = dct["col1"] 39 | col2 = dct["col2"] 40 | col3 = dct["col3"] 41 | tra = dct["transl"] 42 | 43 | mat = gp_Mat(col1, col2, col3) 44 | 45 | _gtrsf = gp_GTrsf() 46 | _gtrsf.SetVectorialPart(mat) 47 | _gtrsf.SetTranslation(*tra) 48 | 49 | def __repr__(self): 50 | return b64.b64encode(pickle.dumps(self)).decode("utf-8") 51 | 52 | def __str__(self): 53 | return super().__str__() 54 | 55 | 56 | def scaleX(a): return scaleXYZ(a, 1, 1) 57 | 58 | 59 | def scaleY(a): return scaleXYZ(1, a, 1) 60 | 61 | 62 | def scaleZ(a): return scaleXYZ(1, 1, a) 63 | 64 | 65 | def scaleXYZ(x, y, z): 66 | gtrsf = gp_GTrsf() 67 | gtrsf.SetVectorialPart(gp_Mat(x, 0, 0, 0, y, 0, 0, 0, z)) 68 | return GeneralTransformation(gtrsf) 69 | -------------------------------------------------------------------------------- /zencad/geom/offset.py: -------------------------------------------------------------------------------- 1 | from OCC.Core.TopTools import TopTools_ListOfShape 2 | from OCC.Core.BRepOffsetAPI import BRepOffsetAPI_MakeThickSolid, BRepOffsetAPI_MakeOffsetShape 3 | from OCC.Core.ShapeFix import ShapeFix_Solid 4 | 5 | from zencad.geom.near import _near_face 6 | from zencad.geom.shape import Shape, shape_generator 7 | from zencad.lazifier import * 8 | 9 | 10 | def _thicksolid(proto, t, refs): 11 | facesToRemove = TopTools_ListOfShape() 12 | 13 | for p in refs: 14 | facesToRemove.Append(_near_face(proto, p).Face()) 15 | 16 | algo = BRepOffsetAPI_MakeThickSolid() 17 | algo.MakeThickSolidByJoin(proto.Shape(), facesToRemove, t, 1.e-3) 18 | 19 | return Shape(algo.Shape()) 20 | 21 | 22 | @lazy.lazy(cls=shape_generator) 23 | def thicksolid(proto, t, refs): 24 | return _thicksolid(proto, t, refs) 25 | 26 | 27 | def _offset(shp, off): 28 | algo = BRepOffsetAPI_MakeOffsetShape() 29 | algo.PerformByJoin(shp.Shape(), off, 1e-6) 30 | algo.Build() 31 | return Shape(algo.Shape()) 32 | 33 | 34 | @lazy.lazy(cls=shape_generator) 35 | def offset(*args, **kwargs): 36 | return _offset(*args, **kwargs) 37 | 38 | 39 | def _shapefix_solid(shp): 40 | algo2 = ShapeFix_Solid(shp.Shape()) 41 | algo2.Perform() 42 | return Shape(algo2.Solid()) 43 | 44 | 45 | @lazy.lazy(cls=shape_generator) 46 | def shapefix_solid(shp): 47 | return _shapefix_solid(shp) 48 | -------------------------------------------------------------------------------- /zencad/geom/project.py: -------------------------------------------------------------------------------- 1 | from OCC.Core.GeomAPI import GeomAPI_ProjectPointOnCurve 2 | from zencad.util import to_Pnt, point3 3 | 4 | 5 | def project_point_on_curve(pnt, crv): 6 | algo = GeomAPI_ProjectPointOnCurve(to_Pnt(pnt), crv.Curve()) 7 | return point3(algo.NearestPoint()) 8 | 9 | 10 | def project(pnt, tgt): 11 | return project_point_on_curve(pnt, tgt) 12 | -------------------------------------------------------------------------------- /zencad/geom/reflect_helpers.py: -------------------------------------------------------------------------------- 1 | from OCC.Core.TopAbs import TopAbs_VERTEX, TopAbs_FACE, TopAbs_WIRE, TopAbs_EDGE, TopAbs_SOLID, TopAbs_SHELL, TopAbs_COMPOUND, TopAbs_COMPSOLID 2 | from OCC.Core.TopoDS import TopoDS_Face, TopoDS_Edge, TopoDS_Wire, TopoDS_Vertex, topods, TopoDS_Shell, TopoDS_Solid, TopoDS_Compound, TopoDS_CompSolid 3 | 4 | 5 | class shape_type: 6 | def __init__(self, convert, construct): 7 | self.convert = convert 8 | self.construct = construct 9 | 10 | 11 | shape_types = { 12 | TopAbs_FACE: shape_type(convert=topods.Face, construct=TopoDS_Face), 13 | TopAbs_VERTEX: shape_type(convert=topods.Vertex, construct=TopoDS_Vertex), 14 | TopAbs_WIRE: shape_type(convert=topods.Wire, construct=TopoDS_Wire), 15 | TopAbs_EDGE: shape_type(convert=topods.Edge, construct=TopoDS_Edge), 16 | TopAbs_SOLID: shape_type(convert=topods.Solid, construct=TopoDS_Solid), 17 | TopAbs_SHELL: shape_type(convert=topods.Shell, construct=TopoDS_Shell), 18 | TopAbs_COMPOUND: shape_type(convert=topods.Compound, construct=TopoDS_Compound), 19 | TopAbs_COMPSOLID: shape_type(convert=topods.CompSolid, construct=TopoDS_CompSolid), 20 | } 21 | -------------------------------------------------------------------------------- /zencad/geom/surface.py: -------------------------------------------------------------------------------- 1 | from OCC.Core.BRepBuilderAPI import BRepBuilderAPI_MakeFace 2 | from OCC.Core.Geom import Geom_CylindricalSurface 3 | from OCC.Core.gp import gp_Pnt, gp_Vec, gp_Ax3, gp_Dir 4 | 5 | from zencad.util import point3, vector3 6 | from zencad.lazifier import * 7 | from zencad.geom.curve import Curve 8 | from OCC.Core.BRepLib import breplib 9 | 10 | from OCC.Core.GeomFill import GeomFill_Sweep, GeomFill_Location 11 | from OCC.Core.BRepBuilderAPI import BRepBuilderAPI_MakeEdge 12 | 13 | import evalcache 14 | 15 | from zencad.geom.shape import Shape 16 | 17 | 18 | class Surface: 19 | def __init__(self, surf): 20 | self._surf = surf 21 | 22 | def Surface(self): 23 | return self._surf 24 | 25 | def v_iso_curve(self, parameter): 26 | return Curve(self.Surface().VIso(parameter)) 27 | 28 | def u_iso_curve(self, parameter): 29 | return Curve(self.Surface().UIso(parameter)) 30 | 31 | def urange(self): 32 | u1, u2, v1, v2 = self._surf.Bounds() 33 | return u1, u2 34 | 35 | def vrange(self): 36 | u1, u2, v1, v2 = self._surf.Bounds() 37 | return v1, v2 38 | 39 | def map(self, tcrv): 40 | mk = BRepBuilderAPI_MakeEdge(tcrv.Curve2(), self.Surface()) 41 | edge = mk.Edge() 42 | breplib.BuildCurves3d(edge) 43 | return Shape(edge) 44 | 45 | 46 | class nocached_surface_generator(evalcache.LazyObject): 47 | """ Decorator for heavy functions. 48 | It use caching for lazy data restoring.""" 49 | 50 | def __init__(self, *args, **kwargs): 51 | evalcache.LazyObject.__init__(self, *args, **kwargs) 52 | 53 | def __call__(self, *args, **kwargs): 54 | return self.lazyinvoke( 55 | self, args, kwargs, 56 | encache=False, 57 | decache=False, 58 | cls=evalcache.LazyObject 59 | ) 60 | 61 | 62 | def _cylinder(r): 63 | return Surface(Geom_CylindricalSurface(gp_Ax3(gp_Pnt(0, 0, 0), gp_Dir(0, 0, 1)), r)) 64 | 65 | 66 | @lazy.lazy(cls=nocached_surface_generator) 67 | def cylinder(r): 68 | return _cylinder(r) 69 | 70 | 71 | def _sweep_surface(slaw, llaw, tol, cont, maxdegree, maxsegm): 72 | """Кинематическое построение поверхности по законам сечения и расположения""" 73 | 74 | algo = GeomFill_Sweep(llaw.Law()) 75 | algo.SetTolerance(tol) 76 | algo.Build(slaw.Law(), GeomFill_Location, cont, maxdegree, maxsegm) 77 | 78 | return Surface(algo.Surface()) 79 | -------------------------------------------------------------------------------- /zencad/geom/sweep_law.py: -------------------------------------------------------------------------------- 1 | from OCC.Core.GeomFill import GeomFill_Frenet, GeomFill_EvolvedSection, GeomFill_CorrectedFrenet, GeomFill_CurveAndTrihedron 2 | from OCC.Core.Law import Law_Constant 3 | 4 | 5 | class LawFunction: 6 | def __init__(self, law): 7 | self.law = law 8 | 9 | def Law(self): 10 | return self.law 11 | 12 | 13 | class LawSection: 14 | def __init__(self, law): 15 | self.law = law 16 | 17 | def Law(self): 18 | return self.law 19 | 20 | 21 | class LawLocation: 22 | def __init__(self, law): 23 | self.law = law 24 | 25 | def Law(self): 26 | return self.law 27 | 28 | 29 | class LawTrihedron: 30 | def __init__(self, law): 31 | self.law = law 32 | 33 | def Law(self): 34 | return self.law 35 | 36 | 37 | def law_constant_function(radius, range): 38 | aFunc = Law_Constant() 39 | aFunc.Set(radius, range[0], range[1]) 40 | return LawFunction(aFunc) 41 | 42 | 43 | def law_evolved_section(crv, lawfunc): 44 | return LawSection(GeomFill_EvolvedSection(crv.Curve(), lawfunc.Law())) 45 | 46 | 47 | def law_spine_and_trihedron(crv, trilaw): 48 | aLoc = GeomFill_CurveAndTrihedron(trilaw.Law()) 49 | aLoc.SetCurve(crv.HCurveAdaptor()) 50 | return LawLocation(aLoc) 51 | 52 | 53 | def law_corrected_frenet_trihedron(): 54 | return LawTrihedron(GeomFill_CorrectedFrenet()) 55 | 56 | 57 | def law_frenet_trihedron(): 58 | return LawTrihedron(GeomFill_Frenet()) 59 | -------------------------------------------------------------------------------- /zencad/gui/display_only.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | 3 | import zencad.gui.display 4 | import zencad.showapi 5 | import sys 6 | 7 | from OCC.Display.backend import load_pyqt5, load_backend 8 | from OCC.Display.backend import get_qt_modules 9 | import OCC.Core.BRepPrimAPI 10 | 11 | from PyQt5 import QtCore, QtGui, QtWidgets, QtOpenGL 12 | 13 | from zenframe.configuration import Configuration 14 | if Configuration.FILTER_QT_WARNINGS: 15 | QtCore.QLoggingCategory.setFilterRules('qt.qpa.xcb=false') 16 | 17 | 18 | QAPP = None 19 | 20 | 21 | def init_display_only_mode() -> zencad.gui.display.DisplayWidget: 22 | global QAPP 23 | 24 | if QAPP is not None: 25 | raise Exception("QApplication is inited early") 26 | 27 | QAPP = QtWidgets.QApplication(sys.argv[1:]) 28 | zencad.showapi.DISPLAY = zencad.gui.display.DisplayWidget() 29 | 30 | 31 | def exec_display_only_mode(): 32 | zencad.showapi.DISPLAY.show() 33 | QAPP.exec() 34 | sys.exit() 35 | 36 | 37 | if __name__ == "__main__": 38 | init_display_only_mode() 39 | 40 | my_box = OCC.Core.BRepPrimAPI.BRepPrimAPI_MakeBox(10., 20., 30.).Shape() 41 | zencad.showapi.DISPLAY._display.DisplayShape(my_box, update=True) 42 | 43 | exec_display_only_mode() 44 | -------------------------------------------------------------------------------- /zencad/gui/display_unbounded.py: -------------------------------------------------------------------------------- 1 | import sys 2 | import io 3 | import os 4 | import time 5 | import traceback 6 | import subprocess 7 | import runpy 8 | import signal 9 | import json 10 | 11 | from zenframe.retransler import ConsoleRetransler 12 | from zenframe.communicator import Communicator 13 | from zenframe.client import Client 14 | 15 | from zencad.gui.display import DisplayWidget 16 | from zenframe.finisher import setup_interrupt_handlers 17 | 18 | from zenframe.util import print_to_stderr 19 | -------------------------------------------------------------------------------- /zencad/gui/util.py: -------------------------------------------------------------------------------- 1 | from PyQt5.QtWidgets import * 2 | from PyQt5.QtCore import * 3 | from PyQt5.QtGui import * 4 | 5 | import os 6 | import tempfile 7 | 8 | 9 | def create_temporary_file(zencad_template=False): 10 | path = tempfile.mktemp(".py") 11 | 12 | if zencad_template: 13 | f = open(path, "w") 14 | f.write( 15 | "#!/usr/bin/env python3\n#coding: utf-8\n\nfrom zencad import *\n\nm=box(10)\ndisp(m)\n\nshow()\n" 16 | ) 17 | f.close() 18 | 19 | return path 20 | 21 | 22 | def open_file_dialog(parent, directory=""): 23 | filters = "*.py;;*.*" 24 | defaultFilter = "*.py" 25 | 26 | if directory == tempfile.gettempdir(): 27 | directory = "." 28 | 29 | path = QFileDialog.getOpenFileName( 30 | parent, "Open File", directory, filters, defaultFilter 31 | ) 32 | 33 | return path 34 | 35 | 36 | def save_file_dialog(parent): 37 | filters = "*.py;;*.*" 38 | defaultFilter = "*.py" 39 | 40 | path = QFileDialog.getSaveFileName( 41 | parent, "Save File", "", filters, defaultFilter 42 | ) 43 | 44 | return path 45 | 46 | 47 | def open_online_manual(): 48 | QDesktopServices.openUrl( 49 | QUrl("https://mirmik.github.io/zencad", QUrl.TolerantMode) 50 | ) 51 | 52 | 53 | def pythonocc_directory(): 54 | try: 55 | import OCC 56 | except: 57 | return None 58 | 59 | return os.path.dirname(OCC.__file__) 60 | 61 | 62 | def pythonocc_core_directory(): 63 | try: 64 | import OCC.Core 65 | except: 66 | return None 67 | 68 | return os.path.dirname(OCC.Core.__file__) -------------------------------------------------------------------------------- /zencad/interactive/__init__.py: -------------------------------------------------------------------------------- 1 | from zencad.interactive.interactive_object import point3 2 | 3 | from zencad.interactive.point import PointInteractiveObject 4 | from zencad.interactive.axis import AxisInteractiveObject 5 | from zencad.interactive.shape import ShapeInteractiveObject 6 | from zencad.interactive.line import line, arrow 7 | from zencad.interactive.interactive_object import InteractiveObject 8 | 9 | from OCC.Core.Geom import Geom_CartesianPoint 10 | import OCC.Core 11 | 12 | from zencad.axis import Axis 13 | from zencad.color import Color 14 | from zencad.geom.shape import Shape 15 | 16 | 17 | def create_interactive_object(obj, color=None): 18 | if isinstance(obj, InteractiveObject): 19 | return obj 20 | 21 | if isinstance(color, (tuple, list)): 22 | color = Color(*color) 23 | 24 | if isinstance(obj, ( 25 | OCC.Core.TopoDS.TopoDS_Edge, 26 | OCC.Core.TopoDS.TopoDS_Wire, 27 | OCC.Core.TopoDS.TopoDS_Vertex, 28 | OCC.Core.TopoDS.TopoDS_Face, 29 | OCC.Core.TopoDS.TopoDS_Compound, 30 | OCC.Core.TopoDS.TopoDS_CompSolid, 31 | OCC.Core.TopoDS.TopoDS_Shell, 32 | OCC.Core.TopoDS.TopoDS_Solid, 33 | OCC.Core.TopoDS.TopoDS_Shape 34 | )): 35 | obj = Shape(obj) 36 | 37 | if isinstance(obj, Shape): 38 | return ShapeInteractiveObject(obj, color) 39 | elif isinstance(obj, Axis): 40 | return AxisInteractiveObject(obj, color) 41 | elif isinstance(obj, (Geom_CartesianPoint, point3)): 42 | return PointInteractiveObject(obj, color) 43 | 44 | else: 45 | raise Exception("unresolved type", obj.__class__) 46 | 47 | 48 | __all__ = [ 49 | "line", 50 | "arrow" 51 | ] 52 | -------------------------------------------------------------------------------- /zencad/interactive/axis.py: -------------------------------------------------------------------------------- 1 | from zencad.interactive.interactive_object import InteractiveObject 2 | 3 | from OCC.Core.AIS import AIS_Axis 4 | 5 | 6 | class AxisInteractiveObject(InteractiveObject): 7 | def __init__(self, axis, color): 8 | self.axis = axis 9 | super().__init__(AIS_Axis(axis.to_Geom_Line()), color=color) 10 | -------------------------------------------------------------------------------- /zencad/interactive/displayable.py: -------------------------------------------------------------------------------- 1 | class Displayable: 2 | def bind_to_scene(self, scene): 3 | raise NotImplementedError() 4 | -------------------------------------------------------------------------------- /zencad/interactive/line.py: -------------------------------------------------------------------------------- 1 | from zencad.interactive.interactive_object import InteractiveObject 2 | from zencad.color import Color as color 3 | from zencad.util import to_Pnt, to_Vec, point3 4 | 5 | from OCC.Core.Geom import Geom_CartesianPoint 6 | from OCC.Core.Prs3d import Prs3d_Drawer, Prs3d_ArrowAspect, Prs3d_LineAspect 7 | from OCC.Core.AIS import AIS_Line 8 | from OCC.Core.Aspect import Aspect_TOL_SOLID 9 | 10 | 11 | class LineInteractiveObject(InteractiveObject): 12 | def __init__(self, p1, p2, width, color): 13 | self.p1 = point3(p1) 14 | self.p2 = point3(p2) 15 | 16 | super().__init__(self.make_ais(), color) 17 | 18 | self.width = width if width else 1 19 | self.set_line_aspect(self.width) 20 | 21 | def make_ais(self): 22 | p1 = Geom_CartesianPoint(to_Pnt(self.p1)) 23 | p2 = Geom_CartesianPoint(to_Pnt(self.p2)) 24 | return AIS_Line(p1, p2) 25 | 26 | def set_points(self, p1, p2): 27 | self.p1 = point3(p1) 28 | self.p2 = point3(p2) 29 | p1 = Geom_CartesianPoint(to_Pnt(self.p1)) 30 | p2 = Geom_CartesianPoint(to_Pnt(self.p2)) 31 | self.ais_object.SetPoints(p1, p2) 32 | 33 | def set_line_aspect(self, width, aspect_type=Aspect_TOL_SOLID): 34 | self.width = width 35 | 36 | lineAspect = Prs3d_LineAspect( 37 | self._color.to_Quantity_Color(), 38 | aspect_type, 39 | self.width) 40 | 41 | self.ais_object.Attributes().SetLineAspect(lineAspect) 42 | 43 | def set_arrow_aspect(self, arrlen): 44 | arrowAspect = Prs3d_ArrowAspect() 45 | arrowAspect.SetLength(arrlen) 46 | self.ais_object.Attributes().SetArrowAspect(arrowAspect) 47 | self.ais_object.Attributes().SetLineArrowDraw(True) 48 | 49 | 50 | def line(p1, p2, color=color(1, 1, 1), width=1) -> LineInteractiveObject: 51 | iobj = LineInteractiveObject(p1, p2, color=color, width=width) 52 | return iobj 53 | 54 | 55 | def arrow(p1, p2, color=color(1, 1, 1), arrlen=1, width=1) -> LineInteractiveObject: 56 | iobj = LineInteractiveObject(p1, p2, color=color, width=width) 57 | iobj.set_arrow_aspect(arrlen) 58 | return iobj 59 | -------------------------------------------------------------------------------- /zencad/interactive/point.py: -------------------------------------------------------------------------------- 1 | from zencad.interactive.interactive_object import InteractiveObject 2 | 3 | from OCC.Core.Geom import Geom_CartesianPoint 4 | from OCC.Core.AIS import AIS_Point 5 | 6 | from zencad.geombase import point3 7 | from zencad.color import default_point_color 8 | 9 | class PointInteractiveObject(InteractiveObject): 10 | def __init__(self, point, color): 11 | if isinstance(point, point3): 12 | pnt = point.Pnt() 13 | point = Geom_CartesianPoint(pnt) 14 | 15 | if color is None: 16 | color = default_point_color() 17 | 18 | self.point = point 19 | super().__init__(AIS_Point(point), color=color) 20 | -------------------------------------------------------------------------------- /zencad/interactive/shape.py: -------------------------------------------------------------------------------- 1 | from zencad.interactive.interactive_object import InteractiveObject 2 | from zencad.color import Color 3 | 4 | from OCC.Core.AIS import AIS_Shape 5 | from zencad.bbox import BoundaryBox 6 | 7 | 8 | class ShapeInteractiveObject(InteractiveObject): 9 | def __init__(self, shape, color, border_color=Color(0, 0, 0), wire_color=None): 10 | self.shape = shape 11 | super().__init__(AIS_Shape(self.shape._shp), 12 | color=color, 13 | border_color=border_color, 14 | wire_color=wire_color) 15 | 16 | def boundbox(self): 17 | bbox = self.ais_object.BoundingBox() 18 | return BoundaryBox(bbox) 19 | -------------------------------------------------------------------------------- /zencad/internal_models/__init__.py: -------------------------------------------------------------------------------- 1 | from .knight import knight as knight 2 | -------------------------------------------------------------------------------- /zencad/opencascade_types.py: -------------------------------------------------------------------------------- 1 | from OCC.Core.TColgp import TColgp_Array1OfPnt, TColgp_HArray1OfPnt, TColgp_Array2OfPnt, TColgp_Array1OfVec 2 | from OCC.Core.TColStd import TColStd_Array1OfReal, TColStd_Array1OfInteger 3 | 4 | from zencad.util import to_Pnt, to_Vec 5 | 6 | 7 | def opencascade_array1_of_pnt(arr): 8 | ret = TColgp_Array1OfPnt(1, len(arr)) 9 | for i in range(len(arr)): 10 | ret.SetValue(i + 1, to_Pnt(arr[i])) 11 | return ret 12 | 13 | 14 | def opencascade_h_array1_of_pnt(arr): 15 | ret = TColgp_HArray1OfPnt(1, len(arr)) 16 | for i in range(len(arr)): 17 | ret.SetValue(i + 1, to_Pnt(arr[i])) 18 | return ret 19 | 20 | 21 | def opencascade_array1_of_vec(arr): 22 | ret = TColgp_Array1OfVec(1, len(arr)) 23 | for i in range(len(arr)): 24 | ret.SetValue(i + 1, to_Vec(arr[i])) 25 | return ret 26 | 27 | 28 | def opencascade_array2_of_pnt(arr): 29 | ret = TColgp_Array2OfPnt(1, len(arr), 1, len(arr[0])) 30 | for r in range(len(arr)): 31 | for c in range(len(arr[0])): 32 | ret.SetValue(r+1, c+1, to_Pnt(arr[r][c])) 33 | return ret 34 | 35 | 36 | def opencascade_array1_of_real(arr): 37 | ret = TColStd_Array1OfReal(1, len(arr)) 38 | for i in range(len(arr)): 39 | ret.SetValue(i + 1, float(arr[i])) 40 | return ret 41 | 42 | 43 | def opencascade_array1_of_int(arr): 44 | ret = TColStd_Array1OfInteger(1, len(arr)) 45 | for i in range(len(arr)): 46 | ret.SetValue(i + 1, int(arr[i])) 47 | return ret 48 | -------------------------------------------------------------------------------- /zencad/scene.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | 3 | import evalcache 4 | 5 | from zencad.interactive import * 6 | 7 | from zencad.axis import Axis 8 | from zencad.geom.shape import Shape, LazyObjectShape 9 | from zencad.util import to_Vertex, to_GeomPoint 10 | from zencad.color import default_color 11 | from zencad.interactive import create_interactive_object 12 | from zencad.bbox import BoundaryBox 13 | 14 | import OCC.Core 15 | 16 | import numpy 17 | 18 | 19 | class Scene: 20 | """Коллекция интерактивных объектов для выведения на дисплей. 21 | TODO: Возможно, необходимо расширить функции объекта и 22 | сделать его интерфейсным для работы с дисплеем вместо 23 | самого дисплея. Это позволит снизить сложность кастомизации 24 | визуального пространства для пользователя. 25 | NOTE: нельзя создать DisplayWidget заранее, потому что это 26 | повлечет необходимость создания qapplication при инициализации 27 | библиотек.""" 28 | 29 | def __init__(self): 30 | self.interactives = [] 31 | self.display = None 32 | 33 | def add(self, obj, color=default_color()): 34 | from zencad.interactive.displayable import Displayable 35 | 36 | obj = evalcache.unlazy_if_need(obj) 37 | 38 | if isinstance(obj, Displayable): 39 | obj.bind_to_scene(self) 40 | iobj = obj 41 | else: 42 | iobj = create_interactive_object(obj, color) 43 | self.add(iobj) 44 | 45 | return iobj 46 | 47 | def add_interactive_object(self, iobj): 48 | self.interactives.append(iobj) 49 | 50 | if self.display is not None: 51 | self.display.display_interactive_object(iobj) 52 | 53 | def boundbox(self): 54 | box = BoundaryBox() 55 | for inter in self.interactives: 56 | bbox = inter.boundbox() 57 | box.add(bbox) 58 | return box 59 | -------------------------------------------------------------------------------- /zencad/settings.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | import os 3 | import sys 4 | 5 | from PyQt5.QtCore import * 6 | from zenframe.settings import BaseSettings, default_text_editor_os 7 | 8 | 9 | class ZencadSettings(BaseSettings): 10 | def __init__(self): 11 | list_of_settings = { 12 | "gui": { 13 | "text_editor": default_text_editor_os(), 14 | "start_widget": True, 15 | "bind_widget": True 16 | }, 17 | "view": { 18 | "default_color": (0.6, 0.6, 0.8, 0), 19 | "default_chordial_deviation": 0.1 20 | }, 21 | "memory": { 22 | "recents": [], 23 | "hsplitter_position": (300, 500), 24 | "vsplitter_position": (500, 300), 25 | "console_hidden": False, 26 | "texteditor_hidden": False, 27 | "wsize": None 28 | }, 29 | "markers": { 30 | "size": 1 31 | } 32 | } 33 | 34 | super().__init__("ZenCad", "settings", list_of_settings) 35 | 36 | 37 | Settings = ZencadSettings() 38 | Settings.restore() 39 | 40 | if __name__ == "__main__": 41 | print(Settings.list_of_settings) 42 | -------------------------------------------------------------------------------- /zencad/techpriest.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/zencad/techpriest.jpg -------------------------------------------------------------------------------- /zencad/util.py: -------------------------------------------------------------------------------- 1 | import math 2 | import os 3 | import numpy 4 | import sys 5 | 6 | from OCC.Core.gp import gp_Pnt, gp_Vec, gp_Dir, gp_XYZ, gp_Quaternion 7 | from OCC.Core.TopoDS import TopoDS_Vertex 8 | from OCC.Core.BRep import BRep_Tool 9 | from OCC.Core.BRepBuilderAPI import BRepBuilderAPI_MakeVertex 10 | from OCC.Core.Geom import Geom_CartesianPoint 11 | 12 | import zencad.geom.transformable 13 | import evalcache 14 | 15 | from zencad.geombase import * 16 | 17 | 18 | def as_indexed(arg): 19 | if len(arg) != 1: 20 | return tuple(arg) 21 | return arg 22 | 23 | 24 | def deg(grad): 25 | return float(grad) / 180.0 * math.pi 26 | 27 | 28 | def deg2rad(d): 29 | return deg(d) 30 | 31 | 32 | def rad2deg(d): 33 | return float(d) * 180.0 / math.pi 34 | 35 | 36 | def angle_pair(arg): 37 | if isinstance(arg, tuple) or isinstance(arg, list): 38 | return arg 39 | 40 | if (arg >= 0): 41 | return (0, arg) 42 | else: 43 | return (arg, 0) 44 | 45 | 46 | def examples_paths(root=None): 47 | import zencad 48 | ret = [] 49 | 50 | if root is None: 51 | root = os.path.join(zencad.moduledir, "examples") 52 | else: 53 | root = os.path.abspath(root) 54 | 55 | for path, subdirs, files in os.walk(root): 56 | subdirs[:] = [d for d in subdirs if not d.startswith('__pycache__')] 57 | for name in files: 58 | if os.path.splitext(name)[1] == ".py": 59 | ret.append(os.path.join(path, name)) 60 | 61 | return ret 62 | 63 | 64 | def examples_dict(root=None): 65 | import zencad 66 | if root is None: 67 | root = os.path.join(zencad.moduledir, "examples") 68 | 69 | dct = {} 70 | dct["__files__"] = set() 71 | 72 | for d in os.listdir(root): 73 | dpath = os.path.join(root, d) 74 | 75 | if d == "__pycache__" or d == "fonts": 76 | continue 77 | 78 | if os.path.isdir(dpath): 79 | dct[d] = examples_dict(dpath) 80 | else: 81 | dct["__files__"].add(d) 82 | 83 | return dct 84 | -------------------------------------------------------------------------------- /zencad/version.py: -------------------------------------------------------------------------------- 1 | import pkg_resources 2 | import sys 3 | 4 | try: 5 | __version__ = pkg_resources.get_distribution("zencad").version 6 | except: 7 | __version__ = "Unresolved???" 8 | 9 | if sys.version_info[1] >= 10: 10 | __occt_version__ = "7.6.2" 11 | __pythonocc_version__ = "7.6.2" 12 | 13 | else: 14 | __occt_version__ = "7.5.1" 15 | __pythonocc_version__ = "7.5.1" 16 | -------------------------------------------------------------------------------- /zencad/zencad_logo.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mirmik/zencad/f9ea105ddd0162a051c074a4451eae6faa809029/zencad/zencad_logo.png --------------------------------------------------------------------------------