Ground Control is the program which allows you to control the Maslow CNC machine.
Note: Ground Control has been superseeded by Web Control which is a community led project. For new installs consider using Web Control instead.
======================
Ground Control is the program which allows you to control the Maslow CNC machine.
From within Ground Control, you can move the machine to where you want to begin a cut, calibrate the machine, open and run a g-code file, or monitor the progress of an ongoing cut.
At present, the UI looks like this:
Ground Control is written in Python. It was chosen because it has good cross platform support and is relatively simple to work with.
Two of the goals of Ground Control are:
1) It runs on as many platforms as possible. 2) It is as easy as possible for members of the community to contribute to making the program better.
For Windows and OS X binaries, see the releases page.
For help installing binaries, see the installation guides.
Ground control documentation is available on the project wiki.
For help in using Ground Control, see the users guide.
Ground Control is built using the 2.7.x version of the Python language. 2.7 was chosen instead of 3.x because the support for compiling binaries for the 3.x version is not good enough yet.
Maslow uses the Kivy framework for the UI and the pyserial module for USB communication.
You might also consider taking a look at Virtual Environments to save you from python version headaches later on. This is not a prerequisite for installation on any platform.
To setup your computer to run Ground Control from the source code, first download and install Python version 2.7.x.
Once you have installed Python 2.7.x, open the command prompt and type
python --version
You should then see something similar to this:
Python 2.7.11
If python does not open, it is most likely an issue with the PATH
environment variable.
For more information about configuring the PATH
in Windows, see superuser: How to add python to the windows path.
Next, you need to install Kivy and Pyserial. Fortunately, python comes with a built in package manager, pip
which will install both of them for you.
To install pyserial, type:
python -m pip install pyserial
Installing Kivy is a little more complicated. First, check to make sure your version of pip
is up to date by running:
python -m pip install --upgrade pip wheel setuptools
then install dependencies:
python -m pip install docutils pygments pypiwin32 kivy.deps.sdl2 kivy.deps.glew
and finally install Kivy:
python -m pip install kivy
To install Python on OS X, first install Homebrew
/usr/bin/ruby -e "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/master/install)"
then install Python:
brew install python
Install required dependencies:
pip install -r requirements_osx.txt
Python is bundled with all major linux distributions. You can confirm the version of python you have installed with:
python --version
See documentation for your linux distro on how to install Python 2.7.x if it is not installed.
Once Python 2.7.x is installed, install required dependencies:
pip install -r requirements_linux.txt
Ground Control can be run from the command line. From within the project folder, run the following:
python main.py
If you have any questions or issues with this process please get in touch through the Maslow forums.
If you had any issues which you were able to resolve, please consider raising a Pull Request on this README.md
file with corrections or additions. For more information, see How To Contribute below.
Maslow is an open source project, get involved!
If you find a bug in the software, report it on the issues page.
If you have an idea for a new feature, let us know in the Maslow forums.
If you want to get involved, say hi in the Maslow forums.
If you've already jumped in and started making the software better, feel free to submit a pull request! You can learn more about how to do that here Github Help: Creating a pull request
Kivy uses groundcontrol.kv as a description language for most of the widgets in GroundControl; some tips:
Class References:
root.X
refers to things inside the class. You can add your own variables, but they don't get initialized in time to be used (so root.data doesn't work)
but you can use app.X
to refer to things in the app namespace, so app.data
will always work. BUT you must define the variable in DataStructures/data.py
;
things put in the data dict at runtime will not work.
Formatting:
You can include format strings and logic in the .kv file; eg text: "{Z: %.2f}"%app.data.zPos
will automatically expand/update when app.data.zPos
changes.
But, if it's a text input field, you need to hook the field to an event -- changing the text in the box will not update app.data.zPos
.
Referring to UI bits in code:
If you want to refer to a widget in the code, you need to give it an id, and you need to put a id:id
statement after the widget definition starts
Otherwise, you won't be able to access it in the code. If you put an id:id
statement in place but you don't declare a widget with that id, it will
crash when you bring up the widget.
Attributes:
Most attributes (eg. text_size
, multiline
, disabled
, etc) are not inheritable (you can't set the attribute in the "GridLayout" portion);
they have to be decorated on each control.
Layouts:
GridLayout's et al don't support "span" to span columns or rows. If you want to do that kind of thing, redo the grid to the large size and put
sub-GridLayouts in the cells. Try to make the cells the same size so they line up nicely.
The Layouts will not actually work unless you have rows
& columns
attributes in them. The log file will complain about this, so watch for it.
You can auto-size-to-the-minimum sometimes with size_hint_x: None
. But if you give it a 2 (ie, size_hint_x: 2
for 2%), it always works
kinda (it always works but may not do what you expected).
Coordinate Systems:
Kivy defines things as origin is bottom-left, an increasing Y is up, increasing X is right.
Please use self.origin
in the code -- if you draw something, 0,0 is the bottom-left of the application, not the bottom-left of your widget.
Events:
Always bind to the on_touch_up
event. If you bind to the on_touch_down
instead, you get a behavior that looks like a click-through:
on_touch_down
, and pop-up a menu with a button on it.on_touch_up
event, it will fire as soon as the click is releasedCanvasSize=4
). Don't do CamelCase
; do camelCase
instead.self.x
) or in the global-space (CanvasSize
), or in App-space
(app.data.X
or self.data.X
after init)
If you use a variable without the self.
, it will work but it won't be persisted, so it can be annoying to figure out what (didn't) happened.self.
(eg, self.recomputethis()
-- and the self arg gets passed in automagically)__init__
self.done
is executed, call your callback function, and your parent can get data out of
your dialog and is responsible for closing you. But see rule #5.self.data.gcode_queue.put('GCode-Here')