meerk40t 0.9.3001__py2.py3-none-any.whl → 0.9.7010__py2.py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- meerk40t/__init__.py +1 -1
- meerk40t/balormk/balor_params.py +167 -167
- meerk40t/balormk/clone_loader.py +457 -457
- meerk40t/balormk/controller.py +1566 -1512
- meerk40t/balormk/cylindermod.py +64 -0
- meerk40t/balormk/device.py +966 -1959
- meerk40t/balormk/driver.py +778 -591
- meerk40t/balormk/galvo_commands.py +1195 -0
- meerk40t/balormk/gui/balorconfig.py +237 -111
- meerk40t/balormk/gui/balorcontroller.py +191 -184
- meerk40t/balormk/gui/baloroperationproperties.py +116 -115
- meerk40t/balormk/gui/corscene.py +845 -0
- meerk40t/balormk/gui/gui.py +179 -147
- meerk40t/balormk/livelightjob.py +466 -382
- meerk40t/balormk/mock_connection.py +131 -109
- meerk40t/balormk/plugin.py +133 -135
- meerk40t/balormk/usb_connection.py +306 -301
- meerk40t/camera/__init__.py +1 -1
- meerk40t/camera/camera.py +514 -397
- meerk40t/camera/gui/camerapanel.py +1241 -1095
- meerk40t/camera/gui/gui.py +58 -58
- meerk40t/camera/plugin.py +441 -399
- meerk40t/ch341/__init__.py +27 -27
- meerk40t/ch341/ch341device.py +628 -628
- meerk40t/ch341/libusb.py +595 -589
- meerk40t/ch341/mock.py +171 -171
- meerk40t/ch341/windriver.py +157 -157
- meerk40t/constants.py +13 -0
- meerk40t/core/__init__.py +1 -1
- meerk40t/core/bindalias.py +550 -539
- meerk40t/core/core.py +47 -47
- meerk40t/core/cutcode/cubiccut.py +73 -73
- meerk40t/core/cutcode/cutcode.py +315 -312
- meerk40t/core/cutcode/cutgroup.py +141 -137
- meerk40t/core/cutcode/cutobject.py +192 -185
- meerk40t/core/cutcode/dwellcut.py +37 -37
- meerk40t/core/cutcode/gotocut.py +29 -29
- meerk40t/core/cutcode/homecut.py +29 -29
- meerk40t/core/cutcode/inputcut.py +34 -34
- meerk40t/core/cutcode/linecut.py +33 -33
- meerk40t/core/cutcode/outputcut.py +34 -34
- meerk40t/core/cutcode/plotcut.py +335 -335
- meerk40t/core/cutcode/quadcut.py +61 -61
- meerk40t/core/cutcode/rastercut.py +168 -148
- meerk40t/core/cutcode/waitcut.py +34 -34
- meerk40t/core/cutplan.py +1843 -1316
- meerk40t/core/drivers.py +330 -329
- meerk40t/core/elements/align.py +801 -669
- meerk40t/core/elements/branches.py +1844 -1507
- meerk40t/core/elements/clipboard.py +229 -219
- meerk40t/core/elements/element_treeops.py +4561 -2837
- meerk40t/core/elements/element_types.py +125 -105
- meerk40t/core/elements/elements.py +4329 -3617
- meerk40t/core/elements/files.py +117 -64
- meerk40t/core/elements/geometry.py +473 -224
- meerk40t/core/elements/grid.py +467 -316
- meerk40t/core/elements/materials.py +158 -94
- meerk40t/core/elements/notes.py +50 -38
- meerk40t/core/elements/offset_clpr.py +933 -912
- meerk40t/core/elements/offset_mk.py +963 -955
- meerk40t/core/elements/penbox.py +339 -267
- meerk40t/core/elements/placements.py +300 -83
- meerk40t/core/elements/render.py +785 -687
- meerk40t/core/elements/shapes.py +2618 -2092
- meerk40t/core/elements/trace.py +651 -563
- meerk40t/core/elements/tree_commands.py +415 -409
- meerk40t/core/elements/undo_redo.py +116 -58
- meerk40t/core/elements/wordlist.py +319 -200
- meerk40t/core/exceptions.py +9 -9
- meerk40t/core/laserjob.py +220 -220
- meerk40t/core/logging.py +63 -63
- meerk40t/core/node/blobnode.py +83 -86
- meerk40t/core/node/bootstrap.py +105 -103
- meerk40t/core/node/branch_elems.py +40 -31
- meerk40t/core/node/branch_ops.py +45 -38
- meerk40t/core/node/branch_regmark.py +48 -41
- meerk40t/core/node/cutnode.py +29 -32
- meerk40t/core/node/effect_hatch.py +375 -257
- meerk40t/core/node/effect_warp.py +398 -0
- meerk40t/core/node/effect_wobble.py +441 -309
- meerk40t/core/node/elem_ellipse.py +404 -309
- meerk40t/core/node/elem_image.py +1082 -801
- meerk40t/core/node/elem_line.py +358 -292
- meerk40t/core/node/elem_path.py +259 -201
- meerk40t/core/node/elem_point.py +129 -102
- meerk40t/core/node/elem_polyline.py +310 -246
- meerk40t/core/node/elem_rect.py +376 -286
- meerk40t/core/node/elem_text.py +445 -418
- meerk40t/core/node/filenode.py +59 -40
- meerk40t/core/node/groupnode.py +138 -74
- meerk40t/core/node/image_processed.py +777 -766
- meerk40t/core/node/image_raster.py +156 -113
- meerk40t/core/node/layernode.py +31 -31
- meerk40t/core/node/mixins.py +135 -107
- meerk40t/core/node/node.py +1427 -1304
- meerk40t/core/node/nutils.py +117 -114
- meerk40t/core/node/op_cut.py +462 -335
- meerk40t/core/node/op_dots.py +296 -251
- meerk40t/core/node/op_engrave.py +414 -311
- meerk40t/core/node/op_image.py +755 -369
- meerk40t/core/node/op_raster.py +787 -522
- meerk40t/core/node/place_current.py +37 -40
- meerk40t/core/node/place_point.py +329 -126
- meerk40t/core/node/refnode.py +58 -47
- meerk40t/core/node/rootnode.py +225 -219
- meerk40t/core/node/util_console.py +48 -48
- meerk40t/core/node/util_goto.py +84 -65
- meerk40t/core/node/util_home.py +61 -61
- meerk40t/core/node/util_input.py +102 -102
- meerk40t/core/node/util_output.py +102 -102
- meerk40t/core/node/util_wait.py +65 -65
- meerk40t/core/parameters.py +709 -707
- meerk40t/core/planner.py +875 -785
- meerk40t/core/plotplanner.py +656 -652
- meerk40t/core/space.py +120 -113
- meerk40t/core/spoolers.py +706 -705
- meerk40t/core/svg_io.py +1836 -1549
- meerk40t/core/treeop.py +534 -445
- meerk40t/core/undos.py +278 -124
- meerk40t/core/units.py +784 -680
- meerk40t/core/view.py +393 -322
- meerk40t/core/webhelp.py +62 -62
- meerk40t/core/wordlist.py +513 -504
- meerk40t/cylinder/cylinder.py +247 -0
- meerk40t/cylinder/gui/cylindersettings.py +41 -0
- meerk40t/cylinder/gui/gui.py +24 -0
- meerk40t/device/__init__.py +1 -1
- meerk40t/device/basedevice.py +322 -123
- meerk40t/device/devicechoices.py +50 -0
- meerk40t/device/dummydevice.py +163 -128
- meerk40t/device/gui/defaultactions.py +618 -602
- meerk40t/device/gui/effectspanel.py +114 -0
- meerk40t/device/gui/formatterpanel.py +253 -290
- meerk40t/device/gui/warningpanel.py +337 -260
- meerk40t/device/mixins.py +13 -13
- meerk40t/dxf/__init__.py +1 -1
- meerk40t/dxf/dxf_io.py +766 -554
- meerk40t/dxf/plugin.py +47 -35
- meerk40t/external_plugins.py +79 -79
- meerk40t/external_plugins_build.py +28 -28
- meerk40t/extra/cag.py +112 -116
- meerk40t/extra/coolant.py +403 -0
- meerk40t/extra/encode_detect.py +198 -0
- meerk40t/extra/ezd.py +1165 -1165
- meerk40t/extra/hershey.py +835 -340
- meerk40t/extra/imageactions.py +322 -316
- meerk40t/extra/inkscape.py +630 -622
- meerk40t/extra/lbrn.py +424 -424
- meerk40t/extra/outerworld.py +284 -0
- meerk40t/extra/param_functions.py +1542 -1556
- meerk40t/extra/potrace.py +257 -253
- meerk40t/extra/serial_exchange.py +118 -0
- meerk40t/extra/updater.py +602 -453
- meerk40t/extra/vectrace.py +147 -146
- meerk40t/extra/winsleep.py +83 -83
- meerk40t/extra/xcs_reader.py +597 -0
- meerk40t/fill/fills.py +781 -335
- meerk40t/fill/patternfill.py +1061 -1061
- meerk40t/fill/patterns.py +614 -567
- meerk40t/grbl/control.py +87 -87
- meerk40t/grbl/controller.py +990 -903
- meerk40t/grbl/device.py +1081 -768
- meerk40t/grbl/driver.py +989 -771
- meerk40t/grbl/emulator.py +532 -497
- meerk40t/grbl/gcodejob.py +783 -767
- meerk40t/grbl/gui/grblconfiguration.py +373 -298
- meerk40t/grbl/gui/grblcontroller.py +485 -271
- meerk40t/grbl/gui/grblhardwareconfig.py +269 -153
- meerk40t/grbl/gui/grbloperationconfig.py +105 -0
- meerk40t/grbl/gui/gui.py +147 -116
- meerk40t/grbl/interpreter.py +44 -44
- meerk40t/grbl/loader.py +22 -22
- meerk40t/grbl/mock_connection.py +56 -56
- meerk40t/grbl/plugin.py +294 -264
- meerk40t/grbl/serial_connection.py +93 -88
- meerk40t/grbl/tcp_connection.py +81 -79
- meerk40t/grbl/ws_connection.py +112 -0
- meerk40t/gui/__init__.py +1 -1
- meerk40t/gui/about.py +2042 -296
- meerk40t/gui/alignment.py +1644 -1608
- meerk40t/gui/autoexec.py +199 -0
- meerk40t/gui/basicops.py +791 -670
- meerk40t/gui/bufferview.py +77 -71
- meerk40t/gui/busy.py +170 -133
- meerk40t/gui/choicepropertypanel.py +1673 -1469
- meerk40t/gui/consolepanel.py +706 -542
- meerk40t/gui/devicepanel.py +687 -581
- meerk40t/gui/dialogoptions.py +110 -107
- meerk40t/gui/executejob.py +316 -306
- meerk40t/gui/fonts.py +90 -90
- meerk40t/gui/functionwrapper.py +252 -0
- meerk40t/gui/gui_mixins.py +729 -0
- meerk40t/gui/guicolors.py +205 -182
- meerk40t/gui/help_assets/help_assets.py +218 -201
- meerk40t/gui/helper.py +154 -0
- meerk40t/gui/hersheymanager.py +1430 -846
- meerk40t/gui/icons.py +3422 -2747
- meerk40t/gui/imagesplitter.py +555 -508
- meerk40t/gui/keymap.py +354 -344
- meerk40t/gui/laserpanel.py +892 -806
- meerk40t/gui/laserrender.py +1470 -1232
- meerk40t/gui/lasertoolpanel.py +805 -793
- meerk40t/gui/magnetoptions.py +436 -0
- meerk40t/gui/materialmanager.py +2917 -0
- meerk40t/gui/materialtest.py +1722 -1694
- meerk40t/gui/mkdebug.py +646 -359
- meerk40t/gui/mwindow.py +163 -140
- meerk40t/gui/navigationpanels.py +2605 -2467
- meerk40t/gui/notes.py +143 -142
- meerk40t/gui/opassignment.py +414 -410
- meerk40t/gui/operation_info.py +310 -299
- meerk40t/gui/plugin.py +494 -328
- meerk40t/gui/position.py +714 -669
- meerk40t/gui/preferences.py +901 -650
- meerk40t/gui/propertypanels/attributes.py +1461 -1131
- meerk40t/gui/propertypanels/blobproperty.py +117 -114
- meerk40t/gui/propertypanels/consoleproperty.py +83 -80
- meerk40t/gui/propertypanels/gotoproperty.py +77 -0
- meerk40t/gui/propertypanels/groupproperties.py +223 -217
- meerk40t/gui/propertypanels/hatchproperty.py +489 -469
- meerk40t/gui/propertypanels/imageproperty.py +2244 -1384
- meerk40t/gui/propertypanels/inputproperty.py +59 -58
- meerk40t/gui/propertypanels/opbranchproperties.py +82 -80
- meerk40t/gui/propertypanels/operationpropertymain.py +1890 -1638
- meerk40t/gui/propertypanels/outputproperty.py +59 -58
- meerk40t/gui/propertypanels/pathproperty.py +389 -380
- meerk40t/gui/propertypanels/placementproperty.py +1214 -383
- meerk40t/gui/propertypanels/pointproperty.py +140 -136
- meerk40t/gui/propertypanels/propertywindow.py +313 -181
- meerk40t/gui/propertypanels/rasterwizardpanels.py +996 -912
- meerk40t/gui/propertypanels/regbranchproperties.py +76 -0
- meerk40t/gui/propertypanels/textproperty.py +770 -755
- meerk40t/gui/propertypanels/waitproperty.py +56 -55
- meerk40t/gui/propertypanels/warpproperty.py +121 -0
- meerk40t/gui/propertypanels/wobbleproperty.py +255 -204
- meerk40t/gui/ribbon.py +2468 -2210
- meerk40t/gui/scene/scene.py +1100 -1051
- meerk40t/gui/scene/sceneconst.py +22 -22
- meerk40t/gui/scene/scenepanel.py +439 -349
- meerk40t/gui/scene/scenespacewidget.py +365 -365
- meerk40t/gui/scene/widget.py +518 -505
- meerk40t/gui/scenewidgets/affinemover.py +215 -215
- meerk40t/gui/scenewidgets/attractionwidget.py +315 -309
- meerk40t/gui/scenewidgets/bedwidget.py +120 -97
- meerk40t/gui/scenewidgets/elementswidget.py +137 -107
- meerk40t/gui/scenewidgets/gridwidget.py +785 -745
- meerk40t/gui/scenewidgets/guidewidget.py +765 -765
- meerk40t/gui/scenewidgets/laserpathwidget.py +66 -66
- meerk40t/gui/scenewidgets/machineoriginwidget.py +86 -86
- meerk40t/gui/scenewidgets/nodeselector.py +28 -28
- meerk40t/gui/scenewidgets/rectselectwidget.py +589 -346
- meerk40t/gui/scenewidgets/relocatewidget.py +33 -33
- meerk40t/gui/scenewidgets/reticlewidget.py +83 -83
- meerk40t/gui/scenewidgets/selectionwidget.py +2952 -2756
- meerk40t/gui/simpleui.py +357 -333
- meerk40t/gui/simulation.py +2431 -2094
- meerk40t/gui/snapoptions.py +208 -203
- meerk40t/gui/spoolerpanel.py +1227 -1180
- meerk40t/gui/statusbarwidgets/defaultoperations.py +480 -353
- meerk40t/gui/statusbarwidgets/infowidget.py +520 -483
- meerk40t/gui/statusbarwidgets/opassignwidget.py +356 -355
- meerk40t/gui/statusbarwidgets/selectionwidget.py +172 -171
- meerk40t/gui/statusbarwidgets/shapepropwidget.py +754 -236
- meerk40t/gui/statusbarwidgets/statusbar.py +272 -260
- meerk40t/gui/statusbarwidgets/statusbarwidget.py +268 -270
- meerk40t/gui/statusbarwidgets/strokewidget.py +267 -251
- meerk40t/gui/themes.py +200 -78
- meerk40t/gui/tips.py +591 -0
- meerk40t/gui/toolwidgets/circlebrush.py +35 -35
- meerk40t/gui/toolwidgets/toolcircle.py +248 -242
- meerk40t/gui/toolwidgets/toolcontainer.py +82 -77
- meerk40t/gui/toolwidgets/tooldraw.py +97 -90
- meerk40t/gui/toolwidgets/toolellipse.py +219 -212
- meerk40t/gui/toolwidgets/toolimagecut.py +25 -132
- meerk40t/gui/toolwidgets/toolline.py +39 -144
- meerk40t/gui/toolwidgets/toollinetext.py +79 -236
- meerk40t/gui/toolwidgets/toollinetext_inline.py +296 -0
- meerk40t/gui/toolwidgets/toolmeasure.py +160 -216
- meerk40t/gui/toolwidgets/toolnodeedit.py +2088 -2074
- meerk40t/gui/toolwidgets/toolnodemove.py +92 -94
- meerk40t/gui/toolwidgets/toolparameter.py +754 -668
- meerk40t/gui/toolwidgets/toolplacement.py +108 -108
- meerk40t/gui/toolwidgets/toolpoint.py +68 -59
- meerk40t/gui/toolwidgets/toolpointlistbuilder.py +294 -0
- meerk40t/gui/toolwidgets/toolpointmove.py +183 -0
- meerk40t/gui/toolwidgets/toolpolygon.py +288 -403
- meerk40t/gui/toolwidgets/toolpolyline.py +38 -196
- meerk40t/gui/toolwidgets/toolrect.py +211 -207
- meerk40t/gui/toolwidgets/toolrelocate.py +72 -72
- meerk40t/gui/toolwidgets/toolribbon.py +598 -113
- meerk40t/gui/toolwidgets/tooltabedit.py +546 -0
- meerk40t/gui/toolwidgets/tooltext.py +98 -89
- meerk40t/gui/toolwidgets/toolvector.py +213 -204
- meerk40t/gui/toolwidgets/toolwidget.py +39 -39
- meerk40t/gui/usbconnect.py +98 -91
- meerk40t/gui/utilitywidgets/buttonwidget.py +18 -18
- meerk40t/gui/utilitywidgets/checkboxwidget.py +90 -90
- meerk40t/gui/utilitywidgets/controlwidget.py +14 -14
- meerk40t/gui/utilitywidgets/cyclocycloidwidget.py +343 -340
- meerk40t/gui/utilitywidgets/debugwidgets.py +148 -0
- meerk40t/gui/utilitywidgets/handlewidget.py +27 -27
- meerk40t/gui/utilitywidgets/harmonograph.py +450 -447
- meerk40t/gui/utilitywidgets/openclosewidget.py +40 -40
- meerk40t/gui/utilitywidgets/rotationwidget.py +54 -54
- meerk40t/gui/utilitywidgets/scalewidget.py +75 -75
- meerk40t/gui/utilitywidgets/seekbarwidget.py +183 -183
- meerk40t/gui/utilitywidgets/togglewidget.py +142 -142
- meerk40t/gui/utilitywidgets/toolbarwidget.py +8 -8
- meerk40t/gui/wordlisteditor.py +985 -931
- meerk40t/gui/wxmeerk40t.py +1444 -1169
- meerk40t/gui/wxmmain.py +5578 -4112
- meerk40t/gui/wxmribbon.py +1591 -1076
- meerk40t/gui/wxmscene.py +1635 -1453
- meerk40t/gui/wxmtree.py +2410 -2089
- meerk40t/gui/wxutils.py +1769 -1099
- meerk40t/gui/zmatrix.py +102 -102
- meerk40t/image/__init__.py +1 -1
- meerk40t/image/dither.py +429 -0
- meerk40t/image/imagetools.py +2778 -2269
- meerk40t/internal_plugins.py +150 -130
- meerk40t/kernel/__init__.py +63 -12
- meerk40t/kernel/channel.py +259 -212
- meerk40t/kernel/context.py +538 -538
- meerk40t/kernel/exceptions.py +41 -41
- meerk40t/kernel/functions.py +463 -414
- meerk40t/kernel/jobs.py +100 -100
- meerk40t/kernel/kernel.py +3809 -3571
- meerk40t/kernel/lifecycles.py +71 -71
- meerk40t/kernel/module.py +49 -49
- meerk40t/kernel/service.py +147 -147
- meerk40t/kernel/settings.py +383 -343
- meerk40t/lihuiyu/controller.py +883 -876
- meerk40t/lihuiyu/device.py +1181 -1069
- meerk40t/lihuiyu/driver.py +1466 -1372
- meerk40t/lihuiyu/gui/gui.py +127 -106
- meerk40t/lihuiyu/gui/lhyaccelgui.py +377 -363
- meerk40t/lihuiyu/gui/lhycontrollergui.py +741 -651
- meerk40t/lihuiyu/gui/lhydrivergui.py +470 -446
- meerk40t/lihuiyu/gui/lhyoperationproperties.py +238 -237
- meerk40t/lihuiyu/gui/tcpcontroller.py +226 -190
- meerk40t/lihuiyu/interpreter.py +53 -53
- meerk40t/lihuiyu/laserspeed.py +450 -450
- meerk40t/lihuiyu/loader.py +90 -90
- meerk40t/lihuiyu/parser.py +404 -404
- meerk40t/lihuiyu/plugin.py +101 -102
- meerk40t/lihuiyu/tcp_connection.py +111 -109
- meerk40t/main.py +231 -165
- meerk40t/moshi/builder.py +788 -781
- meerk40t/moshi/controller.py +505 -499
- meerk40t/moshi/device.py +495 -442
- meerk40t/moshi/driver.py +862 -696
- meerk40t/moshi/gui/gui.py +78 -76
- meerk40t/moshi/gui/moshicontrollergui.py +538 -522
- meerk40t/moshi/gui/moshidrivergui.py +87 -75
- meerk40t/moshi/plugin.py +43 -43
- meerk40t/network/console_server.py +102 -57
- meerk40t/network/kernelserver.py +10 -9
- meerk40t/network/tcp_server.py +142 -140
- meerk40t/network/udp_server.py +103 -77
- meerk40t/network/web_server.py +390 -0
- meerk40t/newly/controller.py +1158 -1144
- meerk40t/newly/device.py +874 -732
- meerk40t/newly/driver.py +540 -412
- meerk40t/newly/gui/gui.py +219 -188
- meerk40t/newly/gui/newlyconfig.py +116 -101
- meerk40t/newly/gui/newlycontroller.py +193 -186
- meerk40t/newly/gui/operationproperties.py +51 -51
- meerk40t/newly/mock_connection.py +82 -82
- meerk40t/newly/newly_params.py +56 -56
- meerk40t/newly/plugin.py +1214 -1246
- meerk40t/newly/usb_connection.py +322 -322
- meerk40t/rotary/gui/gui.py +52 -46
- meerk40t/rotary/gui/rotarysettings.py +240 -232
- meerk40t/rotary/rotary.py +202 -98
- meerk40t/ruida/control.py +291 -91
- meerk40t/ruida/controller.py +138 -1088
- meerk40t/ruida/device.py +672 -231
- meerk40t/ruida/driver.py +534 -472
- meerk40t/ruida/emulator.py +1494 -1491
- meerk40t/ruida/exceptions.py +4 -4
- meerk40t/ruida/gui/gui.py +71 -76
- meerk40t/ruida/gui/ruidaconfig.py +239 -72
- meerk40t/ruida/gui/ruidacontroller.py +187 -184
- meerk40t/ruida/gui/ruidaoperationproperties.py +48 -47
- meerk40t/ruida/loader.py +54 -52
- meerk40t/ruida/mock_connection.py +57 -109
- meerk40t/ruida/plugin.py +124 -87
- meerk40t/ruida/rdjob.py +2084 -945
- meerk40t/ruida/serial_connection.py +116 -0
- meerk40t/ruida/tcp_connection.py +146 -0
- meerk40t/ruida/udp_connection.py +73 -0
- meerk40t/svgelements.py +9671 -9669
- meerk40t/tools/driver_to_path.py +584 -579
- meerk40t/tools/geomstr.py +5583 -4680
- meerk40t/tools/jhfparser.py +357 -292
- meerk40t/tools/kerftest.py +904 -890
- meerk40t/tools/livinghinges.py +1168 -1033
- meerk40t/tools/pathtools.py +987 -949
- meerk40t/tools/pmatrix.py +234 -0
- meerk40t/tools/pointfinder.py +942 -942
- meerk40t/tools/polybool.py +940 -940
- meerk40t/tools/rasterplotter.py +1660 -547
- meerk40t/tools/shxparser.py +989 -901
- meerk40t/tools/ttfparser.py +726 -446
- meerk40t/tools/zinglplotter.py +595 -593
- {meerk40t-0.9.3001.dist-info → meerk40t-0.9.7010.dist-info}/LICENSE +21 -21
- {meerk40t-0.9.3001.dist-info → meerk40t-0.9.7010.dist-info}/METADATA +150 -139
- meerk40t-0.9.7010.dist-info/RECORD +445 -0
- {meerk40t-0.9.3001.dist-info → meerk40t-0.9.7010.dist-info}/WHEEL +1 -1
- {meerk40t-0.9.3001.dist-info → meerk40t-0.9.7010.dist-info}/top_level.txt +0 -1
- {meerk40t-0.9.3001.dist-info → meerk40t-0.9.7010.dist-info}/zip-safe +1 -1
- meerk40t/balormk/elementlightjob.py +0 -159
- meerk40t-0.9.3001.dist-info/RECORD +0 -437
- test/bootstrap.py +0 -63
- test/test_cli.py +0 -12
- test/test_core_cutcode.py +0 -418
- test/test_core_elements.py +0 -144
- test/test_core_plotplanner.py +0 -397
- test/test_core_viewports.py +0 -312
- test/test_drivers_grbl.py +0 -108
- test/test_drivers_lihuiyu.py +0 -443
- test/test_drivers_newly.py +0 -113
- test/test_element_degenerate_points.py +0 -43
- test/test_elements_classify.py +0 -97
- test/test_elements_penbox.py +0 -22
- test/test_file_svg.py +0 -176
- test/test_fill.py +0 -155
- test/test_geomstr.py +0 -1523
- test/test_geomstr_nodes.py +0 -18
- test/test_imagetools_actualize.py +0 -306
- test/test_imagetools_wizard.py +0 -258
- test/test_kernel.py +0 -200
- test/test_laser_speeds.py +0 -3303
- test/test_length.py +0 -57
- test/test_lifecycle.py +0 -66
- test/test_operations.py +0 -251
- test/test_operations_hatch.py +0 -57
- test/test_ruida.py +0 -19
- test/test_spooler.py +0 -22
- test/test_tools_rasterplotter.py +0 -29
- test/test_wobble.py +0 -133
- test/test_zingl.py +0 -124
- {test → meerk40t/cylinder}/__init__.py +0 -0
- /meerk40t/{core/element_commands.py → cylinder/gui/__init__.py} +0 -0
- {meerk40t-0.9.3001.dist-info → meerk40t-0.9.7010.dist-info}/entry_points.txt +0 -0
meerk40t/newly/controller.py
CHANGED
@@ -1,1144 +1,1158 @@
|
|
1
|
-
"""
|
2
|
-
Newly Controller
|
3
|
-
"""
|
4
|
-
import math
|
5
|
-
import struct
|
6
|
-
import time
|
7
|
-
|
8
|
-
from meerk40t.core.cutcode.rastercut import RasterCut
|
9
|
-
from meerk40t.newly.mock_connection import MockConnection
|
10
|
-
from meerk40t.newly.usb_connection import USBConnection
|
11
|
-
|
12
|
-
|
13
|
-
class NewlyController:
|
14
|
-
"""
|
15
|
-
Newly Controller
|
16
|
-
"""
|
17
|
-
|
18
|
-
def __init__(
|
19
|
-
self,
|
20
|
-
service,
|
21
|
-
x=0,
|
22
|
-
y=0,
|
23
|
-
force_mock=False,
|
24
|
-
):
|
25
|
-
self._machine_index = 0
|
26
|
-
self.service = service
|
27
|
-
self.force_mock = force_mock
|
28
|
-
self.is_shutdown = False # Shutdown finished.
|
29
|
-
|
30
|
-
|
31
|
-
self.usb_log
|
32
|
-
|
33
|
-
|
34
|
-
|
35
|
-
self.
|
36
|
-
self.
|
37
|
-
|
38
|
-
|
39
|
-
self.
|
40
|
-
self.
|
41
|
-
self.
|
42
|
-
|
43
|
-
|
44
|
-
self.
|
45
|
-
|
46
|
-
|
47
|
-
self.
|
48
|
-
|
49
|
-
|
50
|
-
self.
|
51
|
-
|
52
|
-
|
53
|
-
|
54
|
-
|
55
|
-
|
56
|
-
|
57
|
-
self.
|
58
|
-
self.
|
59
|
-
self.
|
60
|
-
self.
|
61
|
-
self.
|
62
|
-
self.
|
63
|
-
self.
|
64
|
-
self.
|
65
|
-
self.
|
66
|
-
self.
|
67
|
-
self.
|
68
|
-
self.
|
69
|
-
|
70
|
-
|
71
|
-
|
72
|
-
|
73
|
-
|
74
|
-
|
75
|
-
self.
|
76
|
-
self.
|
77
|
-
self.
|
78
|
-
self.
|
79
|
-
self.
|
80
|
-
self.
|
81
|
-
self.
|
82
|
-
self.
|
83
|
-
self.
|
84
|
-
self.
|
85
|
-
self.
|
86
|
-
self.
|
87
|
-
|
88
|
-
|
89
|
-
|
90
|
-
|
91
|
-
self.
|
92
|
-
self.
|
93
|
-
self.
|
94
|
-
|
95
|
-
def __call__(self, cmd, *args, **kwargs):
|
96
|
-
if isinstance(cmd, str):
|
97
|
-
# Any string data sent is latin-1 encoded.
|
98
|
-
self._command_buffer.append(cmd.encode("latin-1"))
|
99
|
-
else:
|
100
|
-
self._command_buffer.append(cmd)
|
101
|
-
|
102
|
-
def set_disable_connect(self, status):
|
103
|
-
self._disable_connect = status
|
104
|
-
|
105
|
-
def added(self):
|
106
|
-
pass
|
107
|
-
|
108
|
-
def service_detach(self):
|
109
|
-
pass
|
110
|
-
|
111
|
-
def shutdown(self, *args, **kwargs):
|
112
|
-
self.is_shutdown = True
|
113
|
-
|
114
|
-
@property
|
115
|
-
def connected(self):
|
116
|
-
if self.connection is None:
|
117
|
-
return False
|
118
|
-
return self.connection.is_open(self._machine_index)
|
119
|
-
|
120
|
-
@property
|
121
|
-
def is_connecting(self):
|
122
|
-
if self.connection is None:
|
123
|
-
return False
|
124
|
-
return self._is_opening
|
125
|
-
|
126
|
-
def abort_connect(self):
|
127
|
-
self._abort_open = True
|
128
|
-
self.usb_log("Connect Attempts Aborted")
|
129
|
-
|
130
|
-
def disconnect(self):
|
131
|
-
try:
|
132
|
-
self.connection.close(self._machine_index)
|
133
|
-
except (ConnectionError, ConnectionRefusedError, AttributeError):
|
134
|
-
pass
|
135
|
-
self.connection = None
|
136
|
-
# Reset error to allow another attempt
|
137
|
-
self.set_disable_connect(False)
|
138
|
-
|
139
|
-
def connect_if_needed(self):
|
140
|
-
if self._disable_connect:
|
141
|
-
# After many failures automatic connects are disabled. We require a manual connection.
|
142
|
-
self.abort_connect()
|
143
|
-
self.connection = None
|
144
|
-
raise ConnectionRefusedError(
|
145
|
-
"NewlyController was unreachable. Explicit connect required."
|
146
|
-
)
|
147
|
-
if self.connection is None:
|
148
|
-
if self.service.setting(bool, "mock", False) or self.force_mock:
|
149
|
-
self.connection = MockConnection(self.usb_log)
|
150
|
-
name = self.service.
|
151
|
-
self.connection.send = self.service.channel(f"{name}/send")
|
152
|
-
self.connection.recv = self.service.channel(f"{name}/recv")
|
153
|
-
else:
|
154
|
-
self.connection = USBConnection(self.usb_log)
|
155
|
-
self.
|
156
|
-
|
157
|
-
|
158
|
-
|
159
|
-
|
160
|
-
|
161
|
-
|
162
|
-
|
163
|
-
|
164
|
-
|
165
|
-
|
166
|
-
|
167
|
-
if self.
|
168
|
-
|
169
|
-
|
170
|
-
|
171
|
-
|
172
|
-
|
173
|
-
|
174
|
-
|
175
|
-
self._is_opening = False
|
176
|
-
self.
|
177
|
-
|
178
|
-
|
179
|
-
|
180
|
-
|
181
|
-
|
182
|
-
|
183
|
-
|
184
|
-
|
185
|
-
|
186
|
-
|
187
|
-
|
188
|
-
|
189
|
-
|
190
|
-
|
191
|
-
|
192
|
-
|
193
|
-
self.
|
194
|
-
|
195
|
-
|
196
|
-
|
197
|
-
|
198
|
-
|
199
|
-
|
200
|
-
|
201
|
-
|
202
|
-
|
203
|
-
|
204
|
-
|
205
|
-
|
206
|
-
|
207
|
-
|
208
|
-
|
209
|
-
|
210
|
-
|
211
|
-
|
212
|
-
|
213
|
-
self.
|
214
|
-
|
215
|
-
self.
|
216
|
-
self.
|
217
|
-
self
|
218
|
-
self.
|
219
|
-
|
220
|
-
|
221
|
-
self.
|
222
|
-
self.
|
223
|
-
self.
|
224
|
-
self.
|
225
|
-
self.
|
226
|
-
|
227
|
-
self.
|
228
|
-
self.
|
229
|
-
self.
|
230
|
-
self.
|
231
|
-
self.
|
232
|
-
self.
|
233
|
-
self.
|
234
|
-
|
235
|
-
self.
|
236
|
-
self.
|
237
|
-
self.
|
238
|
-
self.
|
239
|
-
self.
|
240
|
-
|
241
|
-
|
242
|
-
|
243
|
-
|
244
|
-
|
245
|
-
|
246
|
-
|
247
|
-
|
248
|
-
|
249
|
-
|
250
|
-
|
251
|
-
|
252
|
-
|
253
|
-
|
254
|
-
|
255
|
-
|
256
|
-
|
257
|
-
self.
|
258
|
-
self.
|
259
|
-
self.
|
260
|
-
self.
|
261
|
-
self.
|
262
|
-
self.
|
263
|
-
|
264
|
-
|
265
|
-
|
266
|
-
|
267
|
-
|
268
|
-
|
269
|
-
|
270
|
-
|
271
|
-
|
272
|
-
|
273
|
-
"""
|
274
|
-
|
275
|
-
|
276
|
-
|
277
|
-
|
278
|
-
|
279
|
-
|
280
|
-
|
281
|
-
|
282
|
-
|
283
|
-
|
284
|
-
|
285
|
-
|
286
|
-
|
287
|
-
|
288
|
-
|
289
|
-
|
290
|
-
|
291
|
-
|
292
|
-
|
293
|
-
|
294
|
-
|
295
|
-
|
296
|
-
|
297
|
-
|
298
|
-
|
299
|
-
|
300
|
-
|
301
|
-
|
302
|
-
|
303
|
-
|
304
|
-
|
305
|
-
|
306
|
-
|
307
|
-
|
308
|
-
|
309
|
-
|
310
|
-
|
311
|
-
|
312
|
-
|
313
|
-
|
314
|
-
self.
|
315
|
-
self.
|
316
|
-
self.
|
317
|
-
self.
|
318
|
-
|
319
|
-
|
320
|
-
|
321
|
-
|
322
|
-
|
323
|
-
|
324
|
-
|
325
|
-
|
326
|
-
|
327
|
-
|
328
|
-
|
329
|
-
|
330
|
-
|
331
|
-
|
332
|
-
|
333
|
-
|
334
|
-
|
335
|
-
|
336
|
-
self.
|
337
|
-
self.
|
338
|
-
self.
|
339
|
-
self.
|
340
|
-
self.
|
341
|
-
|
342
|
-
|
343
|
-
|
344
|
-
|
345
|
-
|
346
|
-
|
347
|
-
|
348
|
-
|
349
|
-
|
350
|
-
|
351
|
-
|
352
|
-
|
353
|
-
|
354
|
-
|
355
|
-
|
356
|
-
|
357
|
-
|
358
|
-
|
359
|
-
|
360
|
-
|
361
|
-
|
362
|
-
|
363
|
-
|
364
|
-
|
365
|
-
"""
|
366
|
-
|
367
|
-
|
368
|
-
|
369
|
-
|
370
|
-
|
371
|
-
|
372
|
-
|
373
|
-
|
374
|
-
|
375
|
-
|
376
|
-
|
377
|
-
|
378
|
-
|
379
|
-
|
380
|
-
|
381
|
-
|
382
|
-
|
383
|
-
|
384
|
-
|
385
|
-
|
386
|
-
|
387
|
-
|
388
|
-
|
389
|
-
|
390
|
-
|
391
|
-
|
392
|
-
|
393
|
-
|
394
|
-
|
395
|
-
|
396
|
-
|
397
|
-
|
398
|
-
|
399
|
-
|
400
|
-
|
401
|
-
|
402
|
-
self.
|
403
|
-
|
404
|
-
|
405
|
-
|
406
|
-
|
407
|
-
|
408
|
-
|
409
|
-
|
410
|
-
|
411
|
-
|
412
|
-
|
413
|
-
|
414
|
-
|
415
|
-
|
416
|
-
|
417
|
-
|
418
|
-
|
419
|
-
|
420
|
-
|
421
|
-
|
422
|
-
|
423
|
-
|
424
|
-
|
425
|
-
|
426
|
-
|
427
|
-
|
428
|
-
|
429
|
-
|
430
|
-
|
431
|
-
|
432
|
-
|
433
|
-
|
434
|
-
|
435
|
-
|
436
|
-
|
437
|
-
|
438
|
-
|
439
|
-
|
440
|
-
|
441
|
-
|
442
|
-
|
443
|
-
|
444
|
-
|
445
|
-
|
446
|
-
|
447
|
-
|
448
|
-
|
449
|
-
|
450
|
-
|
451
|
-
|
452
|
-
|
453
|
-
|
454
|
-
|
455
|
-
|
456
|
-
|
457
|
-
|
458
|
-
|
459
|
-
self
|
460
|
-
|
461
|
-
|
462
|
-
|
463
|
-
|
464
|
-
|
465
|
-
|
466
|
-
|
467
|
-
|
468
|
-
|
469
|
-
|
470
|
-
|
471
|
-
|
472
|
-
|
473
|
-
|
474
|
-
|
475
|
-
|
476
|
-
|
477
|
-
|
478
|
-
|
479
|
-
|
480
|
-
|
481
|
-
|
482
|
-
|
483
|
-
|
484
|
-
|
485
|
-
|
486
|
-
|
487
|
-
|
488
|
-
|
489
|
-
|
490
|
-
|
491
|
-
|
492
|
-
|
493
|
-
self.scanline(scanline,
|
494
|
-
scanline.clear()
|
495
|
-
|
496
|
-
|
497
|
-
|
498
|
-
|
499
|
-
|
500
|
-
|
501
|
-
|
502
|
-
|
503
|
-
|
504
|
-
|
505
|
-
|
506
|
-
|
507
|
-
|
508
|
-
|
509
|
-
|
510
|
-
|
511
|
-
|
512
|
-
|
513
|
-
|
514
|
-
|
515
|
-
|
516
|
-
|
517
|
-
|
518
|
-
|
519
|
-
|
520
|
-
|
521
|
-
|
522
|
-
|
523
|
-
|
524
|
-
|
525
|
-
|
526
|
-
|
527
|
-
|
528
|
-
|
529
|
-
|
530
|
-
|
531
|
-
|
532
|
-
|
533
|
-
|
534
|
-
|
535
|
-
|
536
|
-
|
537
|
-
|
538
|
-
|
539
|
-
|
540
|
-
|
541
|
-
|
542
|
-
|
543
|
-
|
544
|
-
|
545
|
-
|
546
|
-
|
547
|
-
|
548
|
-
|
549
|
-
|
550
|
-
|
551
|
-
|
552
|
-
|
553
|
-
|
554
|
-
|
555
|
-
|
556
|
-
|
557
|
-
|
558
|
-
|
559
|
-
|
560
|
-
|
561
|
-
|
562
|
-
|
563
|
-
|
564
|
-
|
565
|
-
|
566
|
-
|
567
|
-
|
568
|
-
|
569
|
-
|
570
|
-
|
571
|
-
|
572
|
-
|
573
|
-
|
574
|
-
|
575
|
-
|
576
|
-
|
577
|
-
|
578
|
-
|
579
|
-
|
580
|
-
|
581
|
-
|
582
|
-
|
583
|
-
|
584
|
-
|
585
|
-
|
586
|
-
|
587
|
-
|
588
|
-
|
589
|
-
|
590
|
-
|
591
|
-
|
592
|
-
|
593
|
-
|
594
|
-
|
595
|
-
|
596
|
-
|
597
|
-
|
598
|
-
|
599
|
-
|
600
|
-
|
601
|
-
|
602
|
-
|
603
|
-
|
604
|
-
self.
|
605
|
-
if
|
606
|
-
self(
|
607
|
-
|
608
|
-
self.
|
609
|
-
|
610
|
-
|
611
|
-
|
612
|
-
|
613
|
-
|
614
|
-
|
615
|
-
|
616
|
-
|
617
|
-
|
618
|
-
|
619
|
-
|
620
|
-
|
621
|
-
|
622
|
-
|
623
|
-
|
624
|
-
|
625
|
-
|
626
|
-
|
627
|
-
|
628
|
-
|
629
|
-
|
630
|
-
"""
|
631
|
-
|
632
|
-
|
633
|
-
|
634
|
-
|
635
|
-
|
636
|
-
|
637
|
-
|
638
|
-
|
639
|
-
|
640
|
-
|
641
|
-
|
642
|
-
|
643
|
-
|
644
|
-
|
645
|
-
|
646
|
-
|
647
|
-
|
648
|
-
|
649
|
-
|
650
|
-
|
651
|
-
|
652
|
-
|
653
|
-
|
654
|
-
|
655
|
-
|
656
|
-
|
657
|
-
|
658
|
-
|
659
|
-
|
660
|
-
|
661
|
-
|
662
|
-
|
663
|
-
|
664
|
-
self.
|
665
|
-
self.
|
666
|
-
|
667
|
-
|
668
|
-
|
669
|
-
|
670
|
-
|
671
|
-
|
672
|
-
|
673
|
-
|
674
|
-
|
675
|
-
|
676
|
-
self.
|
677
|
-
self
|
678
|
-
self.
|
679
|
-
|
680
|
-
|
681
|
-
|
682
|
-
self.
|
683
|
-
|
684
|
-
|
685
|
-
|
686
|
-
|
687
|
-
|
688
|
-
|
689
|
-
self(
|
690
|
-
self.
|
691
|
-
|
692
|
-
|
693
|
-
|
694
|
-
|
695
|
-
self(
|
696
|
-
self
|
697
|
-
self(f"
|
698
|
-
self.close_job()
|
699
|
-
|
700
|
-
def
|
701
|
-
self.realtime_job()
|
702
|
-
self.mode = "
|
703
|
-
self(f"
|
704
|
-
self(
|
705
|
-
|
706
|
-
|
707
|
-
|
708
|
-
self.
|
709
|
-
self
|
710
|
-
self(f"
|
711
|
-
self(f"
|
712
|
-
self.close_job()
|
713
|
-
|
714
|
-
def
|
715
|
-
self.realtime_job()
|
716
|
-
self.mode = "
|
717
|
-
self(f"
|
718
|
-
self(f"
|
719
|
-
self.close_job()
|
720
|
-
|
721
|
-
def
|
722
|
-
self.realtime_job()
|
723
|
-
self.mode = "
|
724
|
-
self(f"
|
725
|
-
self(f"
|
726
|
-
self.close_job()
|
727
|
-
|
728
|
-
def
|
729
|
-
self.realtime_job()
|
730
|
-
self.
|
731
|
-
self
|
732
|
-
|
733
|
-
|
734
|
-
|
735
|
-
|
736
|
-
self(
|
737
|
-
self.
|
738
|
-
self
|
739
|
-
self
|
740
|
-
|
741
|
-
|
742
|
-
|
743
|
-
self.
|
744
|
-
self.
|
745
|
-
self.close_job()
|
746
|
-
|
747
|
-
def
|
748
|
-
self.realtime_job()
|
749
|
-
self.mode = "
|
750
|
-
self("
|
751
|
-
self.
|
752
|
-
|
753
|
-
|
754
|
-
|
755
|
-
|
756
|
-
|
757
|
-
|
758
|
-
|
759
|
-
|
760
|
-
|
761
|
-
|
762
|
-
|
763
|
-
|
764
|
-
|
765
|
-
|
766
|
-
|
767
|
-
|
768
|
-
|
769
|
-
|
770
|
-
|
771
|
-
|
772
|
-
self
|
773
|
-
|
774
|
-
|
775
|
-
self.
|
776
|
-
|
777
|
-
|
778
|
-
|
779
|
-
|
780
|
-
|
781
|
-
|
782
|
-
|
783
|
-
|
784
|
-
|
785
|
-
|
786
|
-
|
787
|
-
self.
|
788
|
-
|
789
|
-
|
790
|
-
|
791
|
-
|
792
|
-
|
793
|
-
|
794
|
-
|
795
|
-
|
796
|
-
def
|
797
|
-
|
798
|
-
|
799
|
-
|
800
|
-
|
801
|
-
self.
|
802
|
-
|
803
|
-
def
|
804
|
-
|
805
|
-
|
806
|
-
|
807
|
-
|
808
|
-
|
809
|
-
|
810
|
-
|
811
|
-
|
812
|
-
|
813
|
-
|
814
|
-
|
815
|
-
|
816
|
-
|
817
|
-
|
818
|
-
|
819
|
-
|
820
|
-
|
821
|
-
|
822
|
-
|
823
|
-
|
824
|
-
self.
|
825
|
-
|
826
|
-
|
827
|
-
|
828
|
-
|
829
|
-
|
830
|
-
|
831
|
-
|
832
|
-
|
833
|
-
|
834
|
-
self.
|
835
|
-
self.
|
836
|
-
|
837
|
-
|
838
|
-
|
839
|
-
|
840
|
-
|
841
|
-
|
842
|
-
|
843
|
-
|
844
|
-
self.
|
845
|
-
|
846
|
-
self.
|
847
|
-
|
848
|
-
|
849
|
-
self.
|
850
|
-
|
851
|
-
|
852
|
-
|
853
|
-
|
854
|
-
|
855
|
-
|
856
|
-
|
857
|
-
|
858
|
-
|
859
|
-
|
860
|
-
|
861
|
-
|
862
|
-
|
863
|
-
|
864
|
-
|
865
|
-
|
866
|
-
|
867
|
-
|
868
|
-
|
869
|
-
|
870
|
-
|
871
|
-
|
872
|
-
|
873
|
-
|
874
|
-
|
875
|
-
|
876
|
-
|
877
|
-
|
878
|
-
|
879
|
-
|
880
|
-
|
881
|
-
new_dc
|
882
|
-
|
883
|
-
|
884
|
-
|
885
|
-
|
886
|
-
|
887
|
-
|
888
|
-
|
889
|
-
|
890
|
-
|
891
|
-
|
892
|
-
|
893
|
-
|
894
|
-
|
895
|
-
|
896
|
-
|
897
|
-
|
898
|
-
|
899
|
-
|
900
|
-
if
|
901
|
-
#
|
902
|
-
|
903
|
-
|
904
|
-
|
905
|
-
|
906
|
-
self.
|
907
|
-
|
908
|
-
|
909
|
-
|
910
|
-
|
911
|
-
|
912
|
-
|
913
|
-
|
914
|
-
|
915
|
-
|
916
|
-
|
917
|
-
|
918
|
-
|
919
|
-
|
920
|
-
|
921
|
-
|
922
|
-
|
923
|
-
|
924
|
-
|
925
|
-
|
926
|
-
|
927
|
-
|
928
|
-
|
929
|
-
|
930
|
-
|
931
|
-
|
932
|
-
|
933
|
-
|
934
|
-
|
935
|
-
|
936
|
-
|
937
|
-
|
938
|
-
|
939
|
-
|
940
|
-
|
941
|
-
|
942
|
-
|
943
|
-
|
944
|
-
|
945
|
-
|
946
|
-
|
947
|
-
|
948
|
-
|
949
|
-
|
950
|
-
|
951
|
-
|
952
|
-
|
953
|
-
|
954
|
-
|
955
|
-
|
956
|
-
|
957
|
-
|
958
|
-
|
959
|
-
|
960
|
-
|
961
|
-
|
962
|
-
|
963
|
-
|
964
|
-
|
965
|
-
|
966
|
-
|
967
|
-
|
968
|
-
|
969
|
-
|
970
|
-
|
971
|
-
|
972
|
-
|
973
|
-
|
974
|
-
|
975
|
-
|
976
|
-
|
977
|
-
|
978
|
-
|
979
|
-
|
980
|
-
|
981
|
-
|
982
|
-
|
983
|
-
|
984
|
-
if
|
985
|
-
|
986
|
-
|
987
|
-
|
988
|
-
|
989
|
-
|
990
|
-
|
991
|
-
|
992
|
-
|
993
|
-
|
994
|
-
|
995
|
-
|
996
|
-
|
997
|
-
|
998
|
-
|
999
|
-
|
1000
|
-
|
1001
|
-
|
1002
|
-
|
1003
|
-
|
1004
|
-
|
1005
|
-
|
1006
|
-
|
1007
|
-
|
1008
|
-
|
1009
|
-
|
1010
|
-
|
1011
|
-
|
1012
|
-
|
1013
|
-
|
1014
|
-
|
1015
|
-
|
1016
|
-
|
1017
|
-
|
1018
|
-
|
1019
|
-
|
1020
|
-
|
1021
|
-
|
1022
|
-
|
1023
|
-
|
1024
|
-
|
1025
|
-
|
1026
|
-
|
1027
|
-
|
1028
|
-
|
1029
|
-
|
1030
|
-
|
1031
|
-
|
1032
|
-
|
1033
|
-
|
1034
|
-
|
1035
|
-
if
|
1036
|
-
|
1037
|
-
|
1038
|
-
|
1039
|
-
|
1040
|
-
|
1041
|
-
|
1042
|
-
|
1043
|
-
|
1044
|
-
|
1045
|
-
|
1046
|
-
|
1047
|
-
|
1048
|
-
|
1049
|
-
|
1050
|
-
|
1051
|
-
|
1052
|
-
|
1053
|
-
|
1054
|
-
|
1055
|
-
|
1056
|
-
|
1057
|
-
|
1058
|
-
|
1059
|
-
|
1060
|
-
|
1061
|
-
|
1062
|
-
|
1063
|
-
|
1064
|
-
|
1065
|
-
|
1066
|
-
self.
|
1067
|
-
self
|
1068
|
-
|
1069
|
-
|
1070
|
-
|
1071
|
-
|
1072
|
-
|
1073
|
-
|
1074
|
-
|
1075
|
-
|
1076
|
-
|
1077
|
-
|
1078
|
-
|
1079
|
-
|
1080
|
-
|
1081
|
-
|
1082
|
-
|
1083
|
-
|
1084
|
-
|
1085
|
-
|
1086
|
-
|
1087
|
-
|
1088
|
-
|
1089
|
-
|
1090
|
-
|
1091
|
-
|
1092
|
-
|
1093
|
-
|
1094
|
-
|
1095
|
-
|
1096
|
-
|
1097
|
-
|
1098
|
-
|
1099
|
-
|
1100
|
-
|
1101
|
-
|
1102
|
-
|
1103
|
-
|
1104
|
-
|
1105
|
-
|
1106
|
-
|
1107
|
-
|
1108
|
-
|
1109
|
-
|
1110
|
-
|
1111
|
-
|
1112
|
-
|
1113
|
-
|
1114
|
-
|
1115
|
-
|
1116
|
-
|
1117
|
-
|
1118
|
-
|
1119
|
-
|
1120
|
-
|
1121
|
-
|
1122
|
-
|
1123
|
-
|
1124
|
-
|
1125
|
-
|
1126
|
-
|
1127
|
-
|
1128
|
-
|
1129
|
-
|
1130
|
-
|
1131
|
-
|
1132
|
-
|
1133
|
-
|
1134
|
-
|
1135
|
-
|
1136
|
-
|
1137
|
-
|
1138
|
-
|
1139
|
-
|
1140
|
-
|
1141
|
-
|
1142
|
-
|
1143
|
-
|
1144
|
-
|
1
|
+
"""
|
2
|
+
Newly Controller
|
3
|
+
"""
|
4
|
+
import math
|
5
|
+
import struct
|
6
|
+
import time
|
7
|
+
|
8
|
+
from meerk40t.core.cutcode.rastercut import RasterCut
|
9
|
+
from meerk40t.newly.mock_connection import MockConnection
|
10
|
+
from meerk40t.newly.usb_connection import USBConnection
|
11
|
+
|
12
|
+
|
13
|
+
class NewlyController:
|
14
|
+
"""
|
15
|
+
Newly Controller
|
16
|
+
"""
|
17
|
+
|
18
|
+
def __init__(
|
19
|
+
self,
|
20
|
+
service,
|
21
|
+
x=0,
|
22
|
+
y=0,
|
23
|
+
force_mock=False,
|
24
|
+
):
|
25
|
+
self._machine_index = 0
|
26
|
+
self.service = service
|
27
|
+
self.force_mock = force_mock
|
28
|
+
self.is_shutdown = False # Shutdown finished.
|
29
|
+
|
30
|
+
self.usb_log = service.channel(f"{service.safe_label}/usb", buffer_size=500)
|
31
|
+
self.usb_log.watch(lambda e: service.signal("pipe;usb_status", e))
|
32
|
+
|
33
|
+
# Load Primary Pens
|
34
|
+
self.sp0 = self.service.setting(int, "sp0", 0)
|
35
|
+
self.sp1 = self.service.setting(int, "sp1", 1)
|
36
|
+
self.sp2 = self.service.setting(int, "sp2", 2)
|
37
|
+
|
38
|
+
self.connection = None
|
39
|
+
self._is_opening = False
|
40
|
+
self._abort_open = False
|
41
|
+
self._disable_connect = False
|
42
|
+
|
43
|
+
self._job_x = None
|
44
|
+
self._job_y = None
|
45
|
+
|
46
|
+
self._last_x = x
|
47
|
+
self._last_y = y
|
48
|
+
|
49
|
+
self._last_updated_x = x
|
50
|
+
self._last_updated_y = y
|
51
|
+
|
52
|
+
#######################
|
53
|
+
# Preset Modes.
|
54
|
+
#######################
|
55
|
+
|
56
|
+
self._set_pen = None
|
57
|
+
self._set_cut_dc = None
|
58
|
+
self._set_move_dc = None
|
59
|
+
self._set_mode = None
|
60
|
+
self._set_speed = None
|
61
|
+
self._set_power = None
|
62
|
+
self._set_pwm_freq = None
|
63
|
+
self._set_relative = None
|
64
|
+
self._set_bit_depth = None
|
65
|
+
self._set_bit_width = None
|
66
|
+
self._set_backlash = None
|
67
|
+
self._set_corner_speed = None
|
68
|
+
self._set_acceleration_length = None
|
69
|
+
|
70
|
+
#######################
|
71
|
+
# Current Set Modes.
|
72
|
+
#######################
|
73
|
+
|
74
|
+
self._pen = None
|
75
|
+
self._cut_dc = None
|
76
|
+
self._move_dc = None
|
77
|
+
self._mode = None
|
78
|
+
self._speed = None
|
79
|
+
self._power = None
|
80
|
+
self._pwm_frequency = None
|
81
|
+
self._relative = None
|
82
|
+
self._bit_depth = None
|
83
|
+
self._bit_width = None
|
84
|
+
self._backlash = None
|
85
|
+
self._corner_speed = None
|
86
|
+
self._acceleration_length = None
|
87
|
+
|
88
|
+
self._realtime = False
|
89
|
+
|
90
|
+
self.mode = "init"
|
91
|
+
self.paused = False
|
92
|
+
self._command_buffer = []
|
93
|
+
self._signal_updates = self.service.setting(bool, "signal_updates", True)
|
94
|
+
|
95
|
+
def __call__(self, cmd, *args, **kwargs):
|
96
|
+
if isinstance(cmd, str):
|
97
|
+
# Any string data sent is latin-1 encoded.
|
98
|
+
self._command_buffer.append(cmd.encode("latin-1"))
|
99
|
+
else:
|
100
|
+
self._command_buffer.append(cmd)
|
101
|
+
|
102
|
+
def set_disable_connect(self, status):
|
103
|
+
self._disable_connect = status
|
104
|
+
|
105
|
+
def added(self):
|
106
|
+
pass
|
107
|
+
|
108
|
+
def service_detach(self):
|
109
|
+
pass
|
110
|
+
|
111
|
+
def shutdown(self, *args, **kwargs):
|
112
|
+
self.is_shutdown = True
|
113
|
+
|
114
|
+
@property
|
115
|
+
def connected(self):
|
116
|
+
if self.connection is None:
|
117
|
+
return False
|
118
|
+
return self.connection.is_open(self._machine_index)
|
119
|
+
|
120
|
+
@property
|
121
|
+
def is_connecting(self):
|
122
|
+
if self.connection is None:
|
123
|
+
return False
|
124
|
+
return self._is_opening
|
125
|
+
|
126
|
+
def abort_connect(self):
|
127
|
+
self._abort_open = True
|
128
|
+
self.usb_log("Connect Attempts Aborted")
|
129
|
+
|
130
|
+
def disconnect(self):
|
131
|
+
try:
|
132
|
+
self.connection.close(self._machine_index)
|
133
|
+
except (ConnectionError, ConnectionRefusedError, AttributeError):
|
134
|
+
pass
|
135
|
+
self.connection = None
|
136
|
+
# Reset error to allow another attempt
|
137
|
+
self.set_disable_connect(False)
|
138
|
+
|
139
|
+
def connect_if_needed(self):
|
140
|
+
if self._disable_connect:
|
141
|
+
# After many failures automatic connects are disabled. We require a manual connection.
|
142
|
+
self.abort_connect()
|
143
|
+
self.connection = None
|
144
|
+
raise ConnectionRefusedError(
|
145
|
+
"NewlyController was unreachable. Explicit connect required."
|
146
|
+
)
|
147
|
+
if self.connection is None:
|
148
|
+
if self.service.setting(bool, "mock", False) or self.force_mock:
|
149
|
+
self.connection = MockConnection(self.usb_log)
|
150
|
+
name = self.service.safe_label
|
151
|
+
self.connection.send = self.service.channel(f"{name}/send")
|
152
|
+
self.connection.recv = self.service.channel(f"{name}/recv")
|
153
|
+
else:
|
154
|
+
self.connection = USBConnection(self.usb_log)
|
155
|
+
if self.connection is None:
|
156
|
+
self._is_opening = False
|
157
|
+
self.set_disable_connect(True)
|
158
|
+
self.usb_log("Could not connect to the controller.")
|
159
|
+
self.usb_log("Automatic connections disabled.")
|
160
|
+
raise ConnectionRefusedError("Could not connect to the controller.")
|
161
|
+
|
162
|
+
self._is_opening = True
|
163
|
+
self._abort_open = False
|
164
|
+
count = 0
|
165
|
+
while not self.connection.is_open(self._machine_index):
|
166
|
+
try:
|
167
|
+
if self.connection.open(self._machine_index) < 0:
|
168
|
+
raise ConnectionError
|
169
|
+
self.init_laser()
|
170
|
+
except (ConnectionError, ConnectionRefusedError):
|
171
|
+
time.sleep(0.3)
|
172
|
+
count += 1
|
173
|
+
# self.usb_log(f"Error-Routine pass #{count}")
|
174
|
+
if self.is_shutdown or self._abort_open:
|
175
|
+
self._is_opening = False
|
176
|
+
self._abort_open = False
|
177
|
+
return
|
178
|
+
if self.connection.is_open(self._machine_index):
|
179
|
+
self.connection.close(self._machine_index)
|
180
|
+
if count >= 10:
|
181
|
+
# We have failed too many times.
|
182
|
+
self._is_opening = False
|
183
|
+
self.set_disable_connect(True)
|
184
|
+
self.usb_log("Could not connect to the controller.")
|
185
|
+
self.usb_log("Automatic connections disabled.")
|
186
|
+
raise ConnectionRefusedError("Could not connect to the controller.")
|
187
|
+
time.sleep(0.3)
|
188
|
+
continue
|
189
|
+
self._is_opening = False
|
190
|
+
self._abort_open = False
|
191
|
+
|
192
|
+
def sync(self):
|
193
|
+
self._last_updated_x, self._last_updated_y = self._last_x, self._last_y
|
194
|
+
|
195
|
+
def update(self):
|
196
|
+
last_x, last_y = self.service.view.iposition(
|
197
|
+
self._last_updated_x, self._last_updated_y
|
198
|
+
)
|
199
|
+
x, y = self.service.view.iposition(self._last_x, self._last_y)
|
200
|
+
self.sync()
|
201
|
+
if self._signal_updates:
|
202
|
+
self.service.signal("driver;position", (last_x, last_y, x, y))
|
203
|
+
|
204
|
+
#######################
|
205
|
+
# MODE SHIFTS
|
206
|
+
#######################
|
207
|
+
|
208
|
+
def realtime_job(self, job=None):
|
209
|
+
"""
|
210
|
+
Starts a realtime job, which runs on file0
|
211
|
+
@return:
|
212
|
+
"""
|
213
|
+
if self.mode != "init":
|
214
|
+
return
|
215
|
+
self._realtime = True
|
216
|
+
self.mode = "realtime"
|
217
|
+
self(f"ZZZFile{0}")
|
218
|
+
self._clear_settings()
|
219
|
+
|
220
|
+
def _clear_settings(self):
|
221
|
+
self._set_pen = None
|
222
|
+
self._set_cut_dc = None
|
223
|
+
self._set_move_dc = None
|
224
|
+
self._set_mode = None
|
225
|
+
self._set_speed = None
|
226
|
+
self._set_power = None
|
227
|
+
self._set_pwm_freq = None
|
228
|
+
self._set_relative = None
|
229
|
+
self._set_bit_depth = None
|
230
|
+
self._set_bit_width = None
|
231
|
+
self._set_backlash = None
|
232
|
+
self._set_corner_speed = None
|
233
|
+
self._set_acceleration_length = None
|
234
|
+
|
235
|
+
self._pen = None
|
236
|
+
self._cut_dc = None
|
237
|
+
self._move_dc = None
|
238
|
+
self._mode = None
|
239
|
+
self._speed = None
|
240
|
+
self._power = None
|
241
|
+
self._pwm_frequency = None
|
242
|
+
self._relative = None
|
243
|
+
self._bit_depth = None
|
244
|
+
self._bit_width = None
|
245
|
+
self._backlash = None
|
246
|
+
self._corner_speed = None
|
247
|
+
self._acceleration_length = None
|
248
|
+
|
249
|
+
def _set_move_mode(self):
|
250
|
+
"""
|
251
|
+
Move mode is done for any major movements usually starting out an execution.
|
252
|
+
|
253
|
+
e.g.
|
254
|
+
VP100;VK100;SP2;SP2;VQ15;VJ24;VS10;DA0;
|
255
|
+
@return:
|
256
|
+
"""
|
257
|
+
self.mode = "move"
|
258
|
+
self._set_pen = self.sp2
|
259
|
+
self._set_cut_dc = self.service.cut_dc
|
260
|
+
self._set_move_dc = self.service.move_dc
|
261
|
+
self._set_mode = "move"
|
262
|
+
self._set_speed = self.service.moving_speed
|
263
|
+
self._set_power = None
|
264
|
+
self._set_pwm_freq = None
|
265
|
+
self._set_relative = True
|
266
|
+
self._set_bit_depth = None
|
267
|
+
self._set_bit_width = None
|
268
|
+
self._set_backlash = None
|
269
|
+
self._set_corner_speed = None
|
270
|
+
self._set_acceleration_length = None
|
271
|
+
|
272
|
+
def _set_goto_mode(self):
|
273
|
+
"""
|
274
|
+
Goto mode is done for minor between movements, where we don't need to set the power to 0, since we will be
|
275
|
+
using PU; commands.
|
276
|
+
|
277
|
+
e.g.
|
278
|
+
SP2;SP2;VQ15;VJ24;VS10;PR;PU2083,-5494;
|
279
|
+
|
280
|
+
@return:
|
281
|
+
"""
|
282
|
+
self._set_pen = self.sp2
|
283
|
+
self._set_mode = "goto"
|
284
|
+
self._set_speed = self.service.moving_speed
|
285
|
+
self._set_relative = True
|
286
|
+
|
287
|
+
def _set_frame_mode(self):
|
288
|
+
"""
|
289
|
+
Frame mode is the standard framing operation settings.
|
290
|
+
e.g.
|
291
|
+
SP0;VS20;PR;PD9891,0;PD0,-19704;PD-9891,0;PD0,19704;ZED;
|
292
|
+
|
293
|
+
@return:
|
294
|
+
"""
|
295
|
+
|
296
|
+
self._set_cut_dc = self.service.cut_dc
|
297
|
+
self._set_move_dc = self.service.move_dc
|
298
|
+
self._set_pen = self.sp0
|
299
|
+
self._set_power = 0
|
300
|
+
self._set_relative = True
|
301
|
+
self._set_mode = "frame"
|
302
|
+
self._set_speed = self.service.moving_speed
|
303
|
+
if self.service.pwm_enabled:
|
304
|
+
self._set_pwm_freq = self.service.pwm_frequency
|
305
|
+
|
306
|
+
def _set_vector_mode(self):
|
307
|
+
"""
|
308
|
+
Vector mode typically is just the PD commands for a vector.
|
309
|
+
|
310
|
+
e.g.
|
311
|
+
PR;SP1;DA65;VS187;PD0,-2534;PD1099,0;PD0,2534;PD-1099,0;
|
312
|
+
@return:
|
313
|
+
"""
|
314
|
+
self._set_pen = self.sp1
|
315
|
+
self._set_cut_dc = self.service.cut_dc
|
316
|
+
self._set_move_dc = self.service.move_dc
|
317
|
+
self._set_mode = "vector"
|
318
|
+
self._set_speed = self.service.default_cut_speed
|
319
|
+
self._set_power = self.service.default_cut_power
|
320
|
+
if self.service.pwm_enabled:
|
321
|
+
self._set_pwm_freq = self.service.pwm_frequency
|
322
|
+
self._set_relative = True
|
323
|
+
self._set_bit_depth = None
|
324
|
+
self._set_bit_width = None
|
325
|
+
self._set_backlash = None
|
326
|
+
|
327
|
+
def _set_raster_mode(self):
|
328
|
+
"""
|
329
|
+
Raster mode is the typical preamble and required settings for running a raster. This usually consists of
|
330
|
+
YF, YZ, XF, XZ, and small PU commands.
|
331
|
+
|
332
|
+
EG.
|
333
|
+
BT1;DA77;BC0;BD3;SP0;VQ20;VJ10;VS18;YF...
|
334
|
+
@return:
|
335
|
+
"""
|
336
|
+
self._set_pen = self.sp0
|
337
|
+
self._set_cut_dc = self.service.cut_dc
|
338
|
+
self._set_move_dc = self.service.move_dc
|
339
|
+
self._set_mode = "raster"
|
340
|
+
self._corner_speed = None
|
341
|
+
self._acceleration_length = None
|
342
|
+
if self.service.pwm_enabled:
|
343
|
+
self._set_pwm_freq = self.service.pwm_frequency
|
344
|
+
self._set_relative = True
|
345
|
+
self._set_bit_depth = 1
|
346
|
+
self._set_bit_width = 1
|
347
|
+
self._set_speed = self.service.default_raster_speed
|
348
|
+
self._set_power = self.service.default_raster_power
|
349
|
+
|
350
|
+
def _write_frame(self, outline):
|
351
|
+
self.mode = "frame"
|
352
|
+
if outline is not None:
|
353
|
+
x, y = self._last_x, self._last_y
|
354
|
+
self("DW")
|
355
|
+
for pt in outline:
|
356
|
+
self.frame(*pt)
|
357
|
+
self.frame(*outline[0])
|
358
|
+
self.goto(x, y) # Return to initial x, y if different from outline.
|
359
|
+
self._clear_settings()
|
360
|
+
self("ZED")
|
361
|
+
|
362
|
+
def _execute_job(self):
|
363
|
+
self.service.laser_status = "active"
|
364
|
+
self("ZED")
|
365
|
+
cmd = b";".join(self._command_buffer) + b";"
|
366
|
+
try:
|
367
|
+
self.connect_if_needed()
|
368
|
+
self.connection.write(index=self._machine_index, data=cmd)
|
369
|
+
except ConnectionError:
|
370
|
+
pass
|
371
|
+
self._command_buffer.clear()
|
372
|
+
self._clear_settings()
|
373
|
+
self.service.laser_status = "idle"
|
374
|
+
|
375
|
+
def open_job(self, job=None):
|
376
|
+
"""
|
377
|
+
Opens a job at the declared file_index
|
378
|
+
|
379
|
+
@return:
|
380
|
+
"""
|
381
|
+
|
382
|
+
outline = None
|
383
|
+
try:
|
384
|
+
outline = job.outline
|
385
|
+
except AttributeError:
|
386
|
+
pass
|
387
|
+
if outline is not None:
|
388
|
+
self.set_xy(*outline[0])
|
389
|
+
self._job_x, self._job_y = outline[0]
|
390
|
+
self._realtime = False
|
391
|
+
self._clear_settings()
|
392
|
+
self(f"ZZZFile{self.service.file_index}")
|
393
|
+
self._write_frame(outline)
|
394
|
+
self("GZ")
|
395
|
+
self._clear_settings()
|
396
|
+
|
397
|
+
def close_job(self, job=None):
|
398
|
+
"""
|
399
|
+
Closes the file and sends.
|
400
|
+
@return:
|
401
|
+
"""
|
402
|
+
if not self._command_buffer:
|
403
|
+
return
|
404
|
+
if self.mode in ("realtime", "init"):
|
405
|
+
# Job contains no instructions.
|
406
|
+
self.mode = "init"
|
407
|
+
self._command_buffer.clear()
|
408
|
+
return
|
409
|
+
if not self._realtime and self._job_x is not None and self._job_y is not None:
|
410
|
+
self.goto_rel(self._job_x, self._job_y)
|
411
|
+
|
412
|
+
self._execute_job()
|
413
|
+
self.mode = "init"
|
414
|
+
if self.service.autoplay and not self._realtime:
|
415
|
+
self.replay(self.service.file_index)
|
416
|
+
|
417
|
+
def program_mode(self):
|
418
|
+
self._set_vector_mode()
|
419
|
+
|
420
|
+
def rapid_mode(self):
|
421
|
+
pass
|
422
|
+
|
423
|
+
#######################
|
424
|
+
# Raster Events
|
425
|
+
#######################
|
426
|
+
|
427
|
+
def scanline(self, bits, right=False, left=False, top=False, bottom=False):
|
428
|
+
"""
|
429
|
+
Send a scanline movement.
|
430
|
+
|
431
|
+
@param bits: list of bits.
|
432
|
+
@param right: Moving right?
|
433
|
+
@param left: Moving left?
|
434
|
+
@param top: Moving top?
|
435
|
+
@param bottom: Moving bottom?
|
436
|
+
@return:
|
437
|
+
"""
|
438
|
+
self._commit_settings()
|
439
|
+
cmd = None
|
440
|
+
if left: # left movement
|
441
|
+
cmd = bytearray(b"YF")
|
442
|
+
bits = bits[::-1]
|
443
|
+
elif right:
|
444
|
+
cmd = bytearray(b"YZ")
|
445
|
+
bits = bits[::-1]
|
446
|
+
elif top:
|
447
|
+
cmd = bytearray(b"XF")
|
448
|
+
bits = bits[::-1]
|
449
|
+
elif bottom:
|
450
|
+
cmd = bytearray(b"XZ")
|
451
|
+
bits = bits[::-1]
|
452
|
+
if cmd is None:
|
453
|
+
return # 0,0 goes nowhere.
|
454
|
+
count = len(bits)
|
455
|
+
byte_length = int(math.ceil(count / 8))
|
456
|
+
cmd += struct.pack(">i", count)[1:]
|
457
|
+
binary = "".join([str(b) for b in bits])
|
458
|
+
cmd += int(binary, 2).to_bytes(byte_length, "little")
|
459
|
+
self(cmd)
|
460
|
+
if left:
|
461
|
+
self._last_x -= count
|
462
|
+
elif right:
|
463
|
+
self._last_x += count
|
464
|
+
elif top:
|
465
|
+
self._last_y -= count
|
466
|
+
elif bottom:
|
467
|
+
self._last_y += count
|
468
|
+
|
469
|
+
def _raster_jog(self, x, y, raster_cut):
|
470
|
+
self.goto(x, y)
|
471
|
+
self._set_raster_mode()
|
472
|
+
self.set_settings(raster_cut.settings)
|
473
|
+
self._set_mode = "raster"
|
474
|
+
self._commit_settings()
|
475
|
+
|
476
|
+
def raster(self, raster_cut: RasterCut):
|
477
|
+
"""
|
478
|
+
Run a raster cut with scanlines and default actions.
|
479
|
+
|
480
|
+
@param raster_cut:
|
481
|
+
@return:
|
482
|
+
"""
|
483
|
+
|
484
|
+
scanline = []
|
485
|
+
increasing = True
|
486
|
+
|
487
|
+
def commit_scanline():
|
488
|
+
if scanline:
|
489
|
+
# If there is a scanline commit the scanline.
|
490
|
+
if raster_cut.horizontal:
|
491
|
+
# Horizontal Raster.
|
492
|
+
if increasing:
|
493
|
+
self.scanline(scanline, right=True)
|
494
|
+
scanline.clear()
|
495
|
+
else:
|
496
|
+
self.scanline(scanline, left=True)
|
497
|
+
scanline.clear()
|
498
|
+
else:
|
499
|
+
# Vertical raster.
|
500
|
+
if increasing:
|
501
|
+
self.scanline(scanline, bottom=True)
|
502
|
+
scanline.clear()
|
503
|
+
else:
|
504
|
+
self.scanline(scanline, top=True)
|
505
|
+
scanline.clear()
|
506
|
+
|
507
|
+
self("IN")
|
508
|
+
self._clear_settings()
|
509
|
+
|
510
|
+
previous_x, previous_y = raster_cut.plot.initial_position_in_scene()
|
511
|
+
|
512
|
+
self._raster_jog(previous_x, previous_y, raster_cut)
|
513
|
+
|
514
|
+
if raster_cut.horizontal:
|
515
|
+
self.mode = "raster_horizontal"
|
516
|
+
for x, y, on in raster_cut.plot.plot():
|
517
|
+
dx = x - previous_x
|
518
|
+
dy = y - previous_y
|
519
|
+
if dx < 0 and increasing or dx > 0 and not increasing:
|
520
|
+
# X direction has switched.
|
521
|
+
commit_scanline()
|
522
|
+
increasing = not increasing
|
523
|
+
if dy != 0:
|
524
|
+
# We are moving in the Y direction.
|
525
|
+
commit_scanline()
|
526
|
+
if abs(dy) > self.service.max_raster_jog:
|
527
|
+
self._raster_jog(x, y, raster_cut)
|
528
|
+
else:
|
529
|
+
self._relative = True
|
530
|
+
self("PR")
|
531
|
+
self._goto(x, y) # remain standard rastermode
|
532
|
+
if dx != 0:
|
533
|
+
# Normal move, extend bytes.
|
534
|
+
scanline.extend([int(on)] * abs(dx))
|
535
|
+
previous_x, previous_y = x, y
|
536
|
+
else:
|
537
|
+
self.mode = "raster_vertical"
|
538
|
+
for x, y, on in raster_cut.plot.plot():
|
539
|
+
dx = x - previous_x
|
540
|
+
dy = y - previous_y
|
541
|
+
if dy < 0 and increasing or dy > 0 and not increasing:
|
542
|
+
# Y direction has switched.
|
543
|
+
commit_scanline()
|
544
|
+
increasing = not increasing
|
545
|
+
if dx != 0:
|
546
|
+
# We are moving in the X direction.
|
547
|
+
commit_scanline()
|
548
|
+
if abs(dx) > self.service.max_raster_jog:
|
549
|
+
self._raster_jog(x, y, raster_cut)
|
550
|
+
else:
|
551
|
+
self._relative = True
|
552
|
+
self("PR")
|
553
|
+
self._goto(x, y) # remain standard rastermode
|
554
|
+
if dy != 0:
|
555
|
+
# Normal move, extend bytes
|
556
|
+
scanline.extend([int(on)] * abs(dy))
|
557
|
+
previous_x, previous_y = x, y
|
558
|
+
commit_scanline()
|
559
|
+
|
560
|
+
#######################
|
561
|
+
# SETS FOR PLOTLIKES
|
562
|
+
#######################
|
563
|
+
|
564
|
+
def set_settings(self, settings):
|
565
|
+
"""
|
566
|
+
Sets the primary settings. Rapid, frequency, speed, and timings.
|
567
|
+
|
568
|
+
@param settings: The current settings dictionary
|
569
|
+
@return:
|
570
|
+
"""
|
571
|
+
if "speed" in settings:
|
572
|
+
self._set_speed = settings.get("speed")
|
573
|
+
if "power" in settings:
|
574
|
+
self._set_power = settings.get("power")
|
575
|
+
if "pwm_frequency" in settings:
|
576
|
+
self._set_pwm_freq = settings.get("pwm_frequency")
|
577
|
+
|
578
|
+
#######################
|
579
|
+
# PLOTLIKE SHORTCUTS
|
580
|
+
#######################
|
581
|
+
|
582
|
+
def raw(self, data):
|
583
|
+
data = bytes(data, "latin1")
|
584
|
+
try:
|
585
|
+
self.connect_if_needed()
|
586
|
+
self.connection.write(index=self._machine_index, data=data)
|
587
|
+
except ConnectionError:
|
588
|
+
return
|
589
|
+
|
590
|
+
def frame(self, x, y):
|
591
|
+
self._set_frame_mode()
|
592
|
+
self._mark(x, y)
|
593
|
+
|
594
|
+
def mark(self, x, y, settings=None, power=None, speed=None):
|
595
|
+
"""
|
596
|
+
Mark either sets default vector settings or sets the settings based on the settings object provided.
|
597
|
+
@param x:
|
598
|
+
@param y:
|
599
|
+
@param settings:
|
600
|
+
@param power: power during switch
|
601
|
+
@param speed: speed for marking
|
602
|
+
@return:
|
603
|
+
"""
|
604
|
+
self._set_vector_mode()
|
605
|
+
if settings is not None:
|
606
|
+
self.set_settings(settings)
|
607
|
+
if power is not None:
|
608
|
+
self._set_power = power
|
609
|
+
if speed is not None:
|
610
|
+
self._set_speed = speed
|
611
|
+
self._mark(x, y)
|
612
|
+
|
613
|
+
def _mark(self, x, y):
|
614
|
+
dx = int(round(x - self._last_x))
|
615
|
+
dy = int(round(y - self._last_y))
|
616
|
+
if dx == 0 and dy == 0:
|
617
|
+
return
|
618
|
+
self._commit_settings()
|
619
|
+
if self._relative:
|
620
|
+
self(f"PD{dy},{dx}")
|
621
|
+
self._last_x += dx
|
622
|
+
self._last_y += dy
|
623
|
+
else:
|
624
|
+
x = int(round(x))
|
625
|
+
y = int(round(y))
|
626
|
+
self(f"PD{y},{x}")
|
627
|
+
self._last_x, self._last_y = x, y
|
628
|
+
|
629
|
+
def goto(self, x, y):
|
630
|
+
"""
|
631
|
+
Goto position.
|
632
|
+
@param x:
|
633
|
+
@param y:
|
634
|
+
@return:
|
635
|
+
"""
|
636
|
+
self.goto_rel(x, y)
|
637
|
+
|
638
|
+
def goto_abs(self, x, y):
|
639
|
+
"""
|
640
|
+
Goto given absolute coords value.
|
641
|
+
@param x:
|
642
|
+
@param y:
|
643
|
+
@return:
|
644
|
+
"""
|
645
|
+
self._set_move_mode()
|
646
|
+
self._relative = False
|
647
|
+
self._goto(x, y)
|
648
|
+
|
649
|
+
def goto_rel(self, x, y):
|
650
|
+
"""
|
651
|
+
Positions are given in absolute coords, but the motion sent to the laser is relative.
|
652
|
+
@param x:
|
653
|
+
@param y:
|
654
|
+
@return:
|
655
|
+
"""
|
656
|
+
self._set_move_mode()
|
657
|
+
self._goto(x, y)
|
658
|
+
|
659
|
+
def _goto(self, x, y):
|
660
|
+
dx = int(round(x - self._last_x))
|
661
|
+
dy = int(round(y - self._last_y))
|
662
|
+
if dx == 0 and dy == 0:
|
663
|
+
return
|
664
|
+
self._commit_settings()
|
665
|
+
if self._relative:
|
666
|
+
self(f"PU{dy},{dx}")
|
667
|
+
self._last_x += dx
|
668
|
+
self._last_y += dy
|
669
|
+
else:
|
670
|
+
x = int(round(x))
|
671
|
+
y = int(round(y))
|
672
|
+
self(f"PU{y},{x}")
|
673
|
+
self._last_x, self._last_y = x, y
|
674
|
+
|
675
|
+
def set_xy(self, x, y):
|
676
|
+
self.realtime_job()
|
677
|
+
self.mode = "jog"
|
678
|
+
self.goto_rel(x, y)
|
679
|
+
self.close_job()
|
680
|
+
|
681
|
+
def get_last_xy(self):
|
682
|
+
return self._last_x, self._last_y
|
683
|
+
|
684
|
+
#######################
|
685
|
+
# Command Shortcuts
|
686
|
+
#######################
|
687
|
+
|
688
|
+
def move_frame(self, file_index):
|
689
|
+
self.realtime_job()
|
690
|
+
self.mode = "move_frame"
|
691
|
+
self(f"ZK{file_index}")
|
692
|
+
self.close_job()
|
693
|
+
|
694
|
+
def draw_frame(self, file_index):
|
695
|
+
self.realtime_job()
|
696
|
+
self.mode = "draw_frame"
|
697
|
+
self(f"ZH{file_index}")
|
698
|
+
self.close_job()
|
699
|
+
|
700
|
+
def replay(self, file_index):
|
701
|
+
self.realtime_job()
|
702
|
+
self.mode = "replay"
|
703
|
+
self(f"ZG{file_index}")
|
704
|
+
self.close_job()
|
705
|
+
|
706
|
+
def home_speeds(self, x_speed, y_speed, m_speed):
|
707
|
+
self.realtime_job()
|
708
|
+
self.mode = "home_speeds"
|
709
|
+
self(f"VX{int(round(x_speed / 10))}")
|
710
|
+
self(f"VY{int(round(y_speed / 10))}")
|
711
|
+
self(f"VM{int(round(m_speed / 10))}")
|
712
|
+
self.close_job()
|
713
|
+
|
714
|
+
def z_relative(self, amount, speed=100):
|
715
|
+
self.realtime_job()
|
716
|
+
self.mode = "zmove"
|
717
|
+
self(f"CV{int(round(speed / 10))}")
|
718
|
+
self(f"CR{int(round(amount))}")
|
719
|
+
self.close_job()
|
720
|
+
|
721
|
+
def z_absolute(self, z_position, speed=100):
|
722
|
+
self.realtime_job()
|
723
|
+
self.mode = "zmove"
|
724
|
+
self(f"CV{int(round(speed / 10))}")
|
725
|
+
self(f"CU{int(round(z_position))}")
|
726
|
+
self.close_job()
|
727
|
+
|
728
|
+
def w_relative(self, amount, speed=100):
|
729
|
+
self.realtime_job()
|
730
|
+
self.mode = "wmove"
|
731
|
+
self(f"WV{int(round(speed / 10))}")
|
732
|
+
self(f"WR{int(round(amount))}")
|
733
|
+
self.close_job()
|
734
|
+
|
735
|
+
def w_absolute(self, w_position, speed=100):
|
736
|
+
self.realtime_job()
|
737
|
+
self.mode = "wmove"
|
738
|
+
self(f"WV{int(round(speed / 10))}")
|
739
|
+
self(f"WU{int(round(w_position))}")
|
740
|
+
self.close_job()
|
741
|
+
|
742
|
+
def pulse(self, pulse_time_ms):
|
743
|
+
self.realtime_job()
|
744
|
+
self.dwell(pulse_time_ms)
|
745
|
+
self.close_job()
|
746
|
+
|
747
|
+
def home(self):
|
748
|
+
self.realtime_job()
|
749
|
+
self.mode = "home"
|
750
|
+
self("RS")
|
751
|
+
self._last_x = 0
|
752
|
+
self._last_y = 0
|
753
|
+
self.close_job()
|
754
|
+
|
755
|
+
def origin(self):
|
756
|
+
self.realtime_job()
|
757
|
+
self.mode = "origin"
|
758
|
+
self.goto(0, 0)
|
759
|
+
self.close_job()
|
760
|
+
|
761
|
+
def abort(self):
|
762
|
+
self.realtime_job()
|
763
|
+
self.mode = "abort"
|
764
|
+
self("ZQ")
|
765
|
+
self.close_job()
|
766
|
+
|
767
|
+
def wait(self, time_in_ms):
|
768
|
+
while time_in_ms > 255:
|
769
|
+
time_in_ms -= 255
|
770
|
+
self("TX255")
|
771
|
+
if time_in_ms > 0:
|
772
|
+
self(f"TX{int(round(time_in_ms))}")
|
773
|
+
|
774
|
+
def dwell(self, time_in_ms, settings=None):
|
775
|
+
self.mode = "pulse"
|
776
|
+
if self.service.pwm_enabled:
|
777
|
+
self._set_pwm_freq = self.service.pwm_frequency
|
778
|
+
if settings is not None:
|
779
|
+
# Settings based speed, power, pwm_freq
|
780
|
+
if "power" in settings:
|
781
|
+
self._set_power = settings.get("power")
|
782
|
+
if "pwm_frequency" in settings:
|
783
|
+
self._set_pwm_freq = settings.get("pwm_frequency")
|
784
|
+
# self.set_settings(settings)
|
785
|
+
else:
|
786
|
+
self._set_power = 1000.0
|
787
|
+
self._set_power *= self.service.max_pulse_power / 100.0
|
788
|
+
self._commit_pwmfreq()
|
789
|
+
self._commit_power()
|
790
|
+
while time_in_ms > 255:
|
791
|
+
time_in_ms -= 255
|
792
|
+
self("TO255")
|
793
|
+
if time_in_ms > 0:
|
794
|
+
self(f"TO{int(round(time_in_ms))}")
|
795
|
+
|
796
|
+
def pause(self):
|
797
|
+
self.realtime_job()
|
798
|
+
self.mode = "pause"
|
799
|
+
self("ZT")
|
800
|
+
self.close_job()
|
801
|
+
self.paused = True
|
802
|
+
|
803
|
+
def resume(self):
|
804
|
+
self.realtime_job()
|
805
|
+
self.mode = "resume"
|
806
|
+
self("ZG")
|
807
|
+
self.close_job()
|
808
|
+
self.paused = False
|
809
|
+
|
810
|
+
def wait_finished(self):
|
811
|
+
# No known method to force the laser to single state.
|
812
|
+
pass
|
813
|
+
|
814
|
+
def init_laser(self):
|
815
|
+
self.usb_log("Ready")
|
816
|
+
|
817
|
+
def power(self, power):
|
818
|
+
"""
|
819
|
+
Accepts power in percent, automatically converts to power_ratio
|
820
|
+
|
821
|
+
@param power:
|
822
|
+
@return:
|
823
|
+
"""
|
824
|
+
self._set_power = power
|
825
|
+
|
826
|
+
#######################
|
827
|
+
# Commit settings
|
828
|
+
#######################
|
829
|
+
|
830
|
+
def _commit_settings(self):
|
831
|
+
if self._set_speed is not None:
|
832
|
+
# If set speed is set, we set all the various speed chart lookup properties.
|
833
|
+
settings = self._get_chart_settings_for_speed(self._set_speed)
|
834
|
+
self._set_corner_speed = int(round(settings["corner_speed"]))
|
835
|
+
self._set_acceleration_length = int(round(settings["acceleration_length"]))
|
836
|
+
self._set_backlash = int(round(settings["backlash"]))
|
837
|
+
|
838
|
+
self.commit_mode()
|
839
|
+
self._commit_pwmfreq()
|
840
|
+
self._commit_dc()
|
841
|
+
if self._mode != "raster":
|
842
|
+
self._commit_pen()
|
843
|
+
self._commit_power()
|
844
|
+
if self._mode == "raster":
|
845
|
+
self._commit_raster()
|
846
|
+
self._commit_pen()
|
847
|
+
if self._mode != "vector":
|
848
|
+
self._commit_corner_speed()
|
849
|
+
self._commit_acceleration_length()
|
850
|
+
self._commit_speed()
|
851
|
+
self._commit_relative_mode()
|
852
|
+
|
853
|
+
def commit_mode(self):
|
854
|
+
if self._set_mode is None:
|
855
|
+
# Quick fail.
|
856
|
+
return
|
857
|
+
new_mode = self._set_mode
|
858
|
+
self._set_mode = None
|
859
|
+
if new_mode != self._mode:
|
860
|
+
self._mode = new_mode
|
861
|
+
|
862
|
+
# Old speed and power are void on mode change.
|
863
|
+
self._speed = None
|
864
|
+
self._power = None
|
865
|
+
self._corner_speed = None
|
866
|
+
self._acceleration_length = None
|
867
|
+
self._backlash = None
|
868
|
+
|
869
|
+
#######################
|
870
|
+
# Commit DC Info
|
871
|
+
#######################
|
872
|
+
|
873
|
+
def _commit_cut_dc(self):
|
874
|
+
if self._set_cut_dc is None and self._cut_dc is not None:
|
875
|
+
# Quick Fail.
|
876
|
+
return
|
877
|
+
|
878
|
+
# Fetch Requested.
|
879
|
+
new_dc = self._set_cut_dc
|
880
|
+
self._set_cut_dc = None
|
881
|
+
if new_dc is None:
|
882
|
+
# Nothing set, set default.
|
883
|
+
new_dc = self.service.cut_dc
|
884
|
+
if new_dc != self._cut_dc:
|
885
|
+
# DC is different
|
886
|
+
self._cut_dc = new_dc
|
887
|
+
self(f"VP{self._cut_dc}")
|
888
|
+
|
889
|
+
def _commit_move_dc(self):
|
890
|
+
if self._set_move_dc is None and self._move_dc is not None:
|
891
|
+
# Quick Fail.
|
892
|
+
return
|
893
|
+
|
894
|
+
# Fetch Requested.
|
895
|
+
new_dc = self._set_move_dc
|
896
|
+
self._set_move_dc = None
|
897
|
+
if new_dc is None:
|
898
|
+
# Nothing set, set default.
|
899
|
+
new_dc = self.service.move_dc
|
900
|
+
if new_dc != self._move_dc:
|
901
|
+
# DC is different
|
902
|
+
self._move_dc = new_dc
|
903
|
+
self(f"VK{self._move_dc}")
|
904
|
+
|
905
|
+
def _commit_dc(self):
|
906
|
+
self._commit_cut_dc()
|
907
|
+
self._commit_move_dc()
|
908
|
+
|
909
|
+
#######################
|
910
|
+
# Commit Pen
|
911
|
+
#######################
|
912
|
+
|
913
|
+
def _commit_pen(self):
|
914
|
+
if self._set_pen is None and self._pen is not None:
|
915
|
+
# Quick Fail.
|
916
|
+
return
|
917
|
+
|
918
|
+
# Fetch Requested.
|
919
|
+
new_pen = self._set_pen
|
920
|
+
self._set_pen = None
|
921
|
+
if new_pen is None:
|
922
|
+
# Nothing set, set default.
|
923
|
+
new_pen = 0
|
924
|
+
if new_pen != self._pen:
|
925
|
+
# PEN is different
|
926
|
+
self._pen = new_pen
|
927
|
+
self(f"SP{self._pen}")
|
928
|
+
|
929
|
+
#######################
|
930
|
+
# Commit Power
|
931
|
+
#######################
|
932
|
+
|
933
|
+
def _map_power(self, power):
|
934
|
+
if self.mode == "pulse":
|
935
|
+
power /= 10.0
|
936
|
+
return int(round(power))
|
937
|
+
power /= 1000.0 # Scale to 0-1
|
938
|
+
power *= self.service.max_power # Scale by max power %
|
939
|
+
power *= 255.0 / 100.0 # range between 000 and 255
|
940
|
+
if power > 255:
|
941
|
+
return 255
|
942
|
+
if power <= 0:
|
943
|
+
return 0
|
944
|
+
return int(round(power))
|
945
|
+
|
946
|
+
def _commit_power(self):
|
947
|
+
"""
|
948
|
+
Write power information. If the _set_power is set then it takes priority. Otherwise, the power remains set to
|
949
|
+
what it was previously set to. If no power is set, then power is set to the default cut power.
|
950
|
+
|
951
|
+
@return:
|
952
|
+
"""
|
953
|
+
if self._set_power is None and self._power is not None:
|
954
|
+
return # quick fail.
|
955
|
+
|
956
|
+
new_power = self._set_power
|
957
|
+
self._set_power = None
|
958
|
+
|
959
|
+
if new_power is None:
|
960
|
+
return
|
961
|
+
|
962
|
+
# Premap the power setting.
|
963
|
+
new_power = self._map_power(new_power)
|
964
|
+
|
965
|
+
if new_power != self._power:
|
966
|
+
# Already set power is not the new_power setting.
|
967
|
+
self._power = new_power
|
968
|
+
self(f"DA{new_power}")
|
969
|
+
|
970
|
+
def _commit_pwmfreq(self):
|
971
|
+
"""
|
972
|
+
Write pwm frequency information.
|
973
|
+
@return:
|
974
|
+
"""
|
975
|
+
if self._set_pwm_freq is None and self._pwm_frequency is not None:
|
976
|
+
# Quick Fail.
|
977
|
+
return
|
978
|
+
|
979
|
+
# Fetch Requested.
|
980
|
+
new_freq = self._set_pwm_freq
|
981
|
+
self._set_pwm_freq = None
|
982
|
+
if new_freq is None:
|
983
|
+
return
|
984
|
+
if new_freq != self._pwm_frequency:
|
985
|
+
# Frequency is needed, and different
|
986
|
+
self._pwm_frequency = new_freq
|
987
|
+
self(f"PL{self._pwm_frequency}")
|
988
|
+
|
989
|
+
#######################
|
990
|
+
# Commit speed settings
|
991
|
+
#######################
|
992
|
+
|
993
|
+
def _commit_speed(self):
|
994
|
+
if self._set_speed is None and self._speed is not None:
|
995
|
+
return
|
996
|
+
new_speed = self._set_speed
|
997
|
+
self._set_speed = None
|
998
|
+
if new_speed is not None and new_speed != self._speed:
|
999
|
+
self._speed = new_speed
|
1000
|
+
if self._mode == "vector":
|
1001
|
+
self(f"VS{self._map_vector_speed(new_speed)}")
|
1002
|
+
else:
|
1003
|
+
self(f"VS{self._map_raster_speed(new_speed)}")
|
1004
|
+
|
1005
|
+
def _get_chart_settings_for_speed(self, speed):
|
1006
|
+
"""
|
1007
|
+
Get charted settings for a particular speed. Given a speed this provides other required settings for this
|
1008
|
+
same speed.
|
1009
|
+
|
1010
|
+
@param speed:
|
1011
|
+
@return:
|
1012
|
+
"""
|
1013
|
+
chart = self.service.speedchart
|
1014
|
+
smallest_difference = float("inf")
|
1015
|
+
closest_index = None
|
1016
|
+
for i, c in enumerate(chart):
|
1017
|
+
chart_speed = c.get("speed", 0)
|
1018
|
+
delta_speed = chart_speed - speed
|
1019
|
+
if chart_speed > speed and smallest_difference > delta_speed:
|
1020
|
+
smallest_difference = delta_speed
|
1021
|
+
closest_index = i
|
1022
|
+
if closest_index is not None:
|
1023
|
+
return chart[closest_index]
|
1024
|
+
return chart[-1]
|
1025
|
+
|
1026
|
+
def _map_raster_speed(self, speed):
|
1027
|
+
v = int(round(speed / 10))
|
1028
|
+
if v == 0:
|
1029
|
+
v = 1
|
1030
|
+
return v
|
1031
|
+
|
1032
|
+
def _map_vector_speed(self, speed):
|
1033
|
+
if speed >= 93:
|
1034
|
+
return int(round(speed / 10))
|
1035
|
+
if speed >= 15:
|
1036
|
+
return 162 + int(round(speed))
|
1037
|
+
if speed >= 5:
|
1038
|
+
return 147 + int(round(speed * 2))
|
1039
|
+
if speed >= 1:
|
1040
|
+
return 132 + int(round(speed * 5))
|
1041
|
+
else:
|
1042
|
+
return 127 + int(round(speed * 10))
|
1043
|
+
|
1044
|
+
#######################
|
1045
|
+
# Commit Speed Chart
|
1046
|
+
#######################
|
1047
|
+
|
1048
|
+
def _commit_corner_speed(self):
|
1049
|
+
if self._set_corner_speed is None and self._corner_speed is not None:
|
1050
|
+
# Quick Fail.
|
1051
|
+
return
|
1052
|
+
|
1053
|
+
# Fetch Requested.
|
1054
|
+
new_corner_speed = self._set_corner_speed
|
1055
|
+
self._set_corner_speed = None
|
1056
|
+
if new_corner_speed is None:
|
1057
|
+
# Nothing set, set default.
|
1058
|
+
return
|
1059
|
+
if new_corner_speed != self._corner_speed:
|
1060
|
+
# Corner_speed is different
|
1061
|
+
self._corner_speed = new_corner_speed
|
1062
|
+
self(f"VQ{int(round(self._corner_speed))}")
|
1063
|
+
|
1064
|
+
def _commit_acceleration_length(self):
|
1065
|
+
if (
|
1066
|
+
self._set_acceleration_length is None
|
1067
|
+
and self._acceleration_length is not None
|
1068
|
+
):
|
1069
|
+
# Quick Fail.
|
1070
|
+
return
|
1071
|
+
|
1072
|
+
# Fetch Requested.
|
1073
|
+
new_acceleration_length = self._set_acceleration_length
|
1074
|
+
self._set_acceleration_length = None
|
1075
|
+
if new_acceleration_length is None:
|
1076
|
+
# Nothing set, set default.
|
1077
|
+
return
|
1078
|
+
if new_acceleration_length != self._acceleration_length:
|
1079
|
+
# Acceleration Length is different
|
1080
|
+
self._acceleration_length = new_acceleration_length
|
1081
|
+
self(f"VJ{int(round(self._acceleration_length))}")
|
1082
|
+
|
1083
|
+
#######################
|
1084
|
+
# Commit Relative Mode
|
1085
|
+
#######################
|
1086
|
+
|
1087
|
+
def _commit_relative_mode(self):
|
1088
|
+
if self._set_relative is None and self._relative is not None:
|
1089
|
+
return
|
1090
|
+
new_relative = self._set_relative
|
1091
|
+
self._set_relative = None
|
1092
|
+
|
1093
|
+
if new_relative is None:
|
1094
|
+
new_relative = True
|
1095
|
+
|
1096
|
+
if new_relative != self._relative:
|
1097
|
+
self._relative = new_relative
|
1098
|
+
if self._relative:
|
1099
|
+
self("PR")
|
1100
|
+
else:
|
1101
|
+
self("PA")
|
1102
|
+
|
1103
|
+
#######################
|
1104
|
+
# Commit Raster
|
1105
|
+
#######################
|
1106
|
+
|
1107
|
+
def _commit_raster_bitdepth(self):
|
1108
|
+
if self._set_bit_depth is None and self._bit_depth is not None:
|
1109
|
+
# Quick Fail.
|
1110
|
+
return
|
1111
|
+
|
1112
|
+
# Fetch Requested.
|
1113
|
+
new_bitdepth = self._set_bit_depth
|
1114
|
+
self._set_bit_depth = None
|
1115
|
+
if new_bitdepth is None:
|
1116
|
+
# Nothing set, set default.
|
1117
|
+
return
|
1118
|
+
if new_bitdepth != self._bit_depth:
|
1119
|
+
# Bitdepth is different
|
1120
|
+
self._bit_depth = new_bitdepth
|
1121
|
+
self(f"BT{self._bit_depth}")
|
1122
|
+
|
1123
|
+
def _commit_raster_bitwidth(self):
|
1124
|
+
if self._set_bit_width is None and self._bit_width is not None:
|
1125
|
+
# Quick Fail.
|
1126
|
+
return
|
1127
|
+
|
1128
|
+
# Fetch Requested.
|
1129
|
+
new_bitwidth = self._set_bit_width
|
1130
|
+
self._set_bit_width = None
|
1131
|
+
if new_bitwidth is None:
|
1132
|
+
# Nothing set, set default.
|
1133
|
+
return
|
1134
|
+
if new_bitwidth != self._bit_width:
|
1135
|
+
# Bitdepth is different
|
1136
|
+
self._bit_width = new_bitwidth
|
1137
|
+
self(f"BD{self._bit_width}")
|
1138
|
+
|
1139
|
+
def _commit_raster_backlash(self):
|
1140
|
+
if self._set_backlash is None and self._backlash is not None:
|
1141
|
+
# Quick Fail.
|
1142
|
+
return
|
1143
|
+
|
1144
|
+
# Fetch Requested.
|
1145
|
+
new_backlash = self._set_backlash
|
1146
|
+
self._set_backlash = None
|
1147
|
+
if new_backlash is None:
|
1148
|
+
# Nothing set, set default.
|
1149
|
+
return
|
1150
|
+
if new_backlash != self._backlash:
|
1151
|
+
# backlash is different
|
1152
|
+
self._backlash = new_backlash
|
1153
|
+
self(f"BC{self._backlash}")
|
1154
|
+
|
1155
|
+
def _commit_raster(self):
|
1156
|
+
self._commit_raster_bitdepth()
|
1157
|
+
self._commit_raster_backlash()
|
1158
|
+
self._commit_raster_bitwidth()
|