aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorLionel <lionel.miquel46@gmail.com>2018-12-12 15:56:05 +0100
committerLionel <lionel.miquel46@gmail.com>2018-12-12 22:44:53 +0100
commit0a7e66f5d187e76bb9902c5cd2e3d5196739d5e3 (patch)
tree48b8ba84049cf27d33173c6e35e65851036b383b
parent6f9abf1f236f8662e9953ef666913130d3e26e6e (diff)
downloadaneatocli-0a7e66f5d187e76bb9902c5cd2e3d5196739d5e3.tar.gz
aneatocli-0a7e66f5d187e76bb9902c5cd2e3d5196739d5e3.zip
Added all the main file. I'm not implementing OAuth for the moment.
Working on account logging func
-rw-r--r--.gitignore1
-rw-r--r--aneatocli.py126
-rw-r--r--botvac.py199
-rw-r--r--requirements.txt2
-rw-r--r--robotCreds.json1
-rw-r--r--robotstate.json1
6 files changed, 330 insertions, 0 deletions
diff --git a/.gitignore b/.gitignore
new file mode 100644
index 0000000..0d20b64
--- /dev/null
+++ b/.gitignore
@@ -0,0 +1 @@
+*.pyc
diff --git a/aneatocli.py b/aneatocli.py
new file mode 100644
index 0000000..f6cac4f
--- /dev/null
+++ b/aneatocli.py
@@ -0,0 +1,126 @@
+"""
+aneatocli : a Neato Robot command and state querying cli.
+
+Usage:
+ aneatocli.py --go | --start-cleaning
+ aneatocli.py --stp | --stop-cleaning
+ aneatocli.py --pse | --pause-cleaning
+ aneatocli.py --res | --resume-cleaning
+ aneatocli.py --base |--send-to-base
+ aneatocli.py --gc | --get-commands
+ aneatocli.py --lsec | --load-secrets
+ aneatocli.py --acc | -account
+ aneatocli.py -h | --help
+ aneatocli.py -v | --version
+
+Options:
+ -h , --help Show this message.
+ -v , --version Show version.
+ --go , --start-cleaning Tell the robot to start cleaning.
+ --stp , --stop-cleaning Tell the robot to stop cleaning.
+ --pse , --pause-cleaning Tell the robot to pause cleaning.
+ --res , --resume-cleaning Tell the robot to resume cleaning.
+ --base ,--sendtobase Tell the robot to go back to its dock.
+ --gc , --get-commands Get the available commands.
+ --lsec , --load-secrets Get the Serial Number and the secret. You will be prompted for login.
+
+"""
+from sys import exit
+from os.path import exists as chkf
+from pprint import pprint
+import json
+global robot
+
+def loadCreds()
+ try:
+ with open("robotCreds.json","r") as json_file:
+ creds=json.load(json_file)
+ print("Your serial number is "+creds["serialID"]
+ +". \n Your secret is "+creds["secretID"]
+ +".\n Your robot "+creds["name"]+" have the following traits"+creds["traits"])
+ robot = Robot(creds["serialID"],creds["secretID"],creds["traits"],creds["name"])
+ except:
+ print("Cannot log your robot(s) with the provided infos.")
+
+def getCmds():
+ cmds=robot.state["availableCommands"]
+ try:
+ with open("robotstate.json", "w") as json_file:
+ json.dump(cmds, json_file)
+ print("File robotstate.json created")
+ except:
+ raise
+ exit()
+
+def startC():
+ if robot.state["availableCommands"]["start"]:
+d robot.start_cleaning()
+ else:
+ print("Cannot start the robot.")
+
+def stopC():
+ if robot.state["availableCommands"]["stop"]:
+ robot.stop_cleaning()
+ else:
+ print("Cannot stop the robot.")
+
+
+def pauseC():
+ if robot.state["availableCommands"]["pause"]:
+ robot.pause_cleaning()
+ else:
+ print("Cannot pause the robot.")
+
+def resumeC():
+ if robot.state["availableCommands"]["resume"]:
+ robot.resume_cleaning()
+ else:
+ print("Cannot resume the robot.")
+
+def go2B():
+ if robot.state["availableCommands"]["goToBase"]:
+ robot.send_to_base()
+ else:
+ print("Cannot send the robot to base.")
+
+
+
+
+def funCall(simpleArg, verboseArg, func, *args):
+ if arguments[simpleArg] or arguments[verboseArg]:
+ func( *args )
+
+
+
+
+getSecrets()
+
+try:
+ from pybotvac import Robot
+except:
+ print("pybotvac package is not installed.\n\nPlease run 'pip install pybotvac' from your command prompt\n")
+ exit()
+
+try:
+ from docopt import docopt
+
+except:
+ print("docopt package is not installed.\n\nPlease run 'pip install docopt==0.6.2' from your command prompt\n")
+ exit()
+
+if __name__ == '__main__':
+ arguments = docopt(__doc__, version='aneatocli 0.1')
+ #nts:useful pour debugging
+ pprint(arguments)
+
+
+
+funCall("--go","--start-cleaning",startC)
+funCall("--stp","--stop-cleaning",stopC)
+funCall("--pse","--pause-cleaning",pauseC)
+funCall("--res","--resume-cleaning",resumeC)
+funCall("--base","--send-to-base",go2B)
+funCall("--gc","--get-commands",getCmds)
+funCall("--lsec","--load-secrets",loadCreds)
+
+
diff --git a/botvac.py b/botvac.py
new file mode 100644
index 0000000..9731d36
--- /dev/null
+++ b/botvac.py
@@ -0,0 +1,199 @@
+#!/usr/bin/env python
+# -*- coding: utf-8 -*-
+# Form implementation generated from reading ui file 'botvac.ui'
+#
+# Created by: PyQt4 UI code generator 4.12.1
+#
+# WARNING! All changes made in this file will be lost!
+
+from PyQt4 import QtCore, QtGui
+#!/usr/bin/env python
+from subprocess import call as run
+from subprocess import check_output
+from os.path import exists as chkf
+import sys
+import json
+
+reload(sys)
+sys.setdefaultencoding('utf8')
+try:
+ _fromUtf8 = QtCore.QString.fromUtf8
+except AttributeError:
+ def _fromUtf8(s):
+ return s
+
+try:
+ _encoding = QtGui.QApplication.UnicodeUTF8
+ def _translate(context, text, disambig):
+ return QtGui.QApplication.translate(context, text, disambig, _encoding)
+except AttributeError:
+ def _translate(context, text, disambig):
+ return QtGui.QApplication.translate(context, text, disambig)
+
+class Ui_MainWindow(object):
+ def setupUi(self, MainWindow):
+ MainWindow.setObjectName(_fromUtf8("MainWindow"))
+ MainWindow.resize(472, 323)
+ self.centralwidget = QtGui.QWidget(MainWindow)
+ self.centralwidget.setObjectName(_fromUtf8("centralwidget"))
+ self.verticalLayout = QtGui.QVBoxLayout(self.centralwidget)
+ self.verticalLayout.setObjectName(_fromUtf8("verticalLayout"))
+ self.tabWidget = QtGui.QTabWidget(self.centralwidget)
+ self.tabWidget.setObjectName(_fromUtf8("tabWidget"))
+ self.tab = QtGui.QWidget()
+ self.tab.setObjectName(_fromUtf8("tab"))
+ self.verticalLayout_2 = QtGui.QVBoxLayout(self.tab)
+ self.verticalLayout_2.setMargin(0)
+ self.verticalLayout_2.setObjectName(_fromUtf8("verticalLayout_2"))
+ self.startButton = QtGui.QPushButton(self.tab)
+ sizePolicy = QtGui.QSizePolicy(QtGui.QSizePolicy.Minimum, QtGui.QSizePolicy.Expanding)
+ sizePolicy.setHorizontalStretch(0)
+ sizePolicy.setVerticalStretch(0)
+ sizePolicy.setHeightForWidth(self.startButton.sizePolicy().hasHeightForWidth())
+ self.startButton.setSizePolicy(sizePolicy)
+ self.startButton.setObjectName(_fromUtf8("startButton"))
+ self.verticalLayout_2.addWidget(self.startButton)
+ self.pauseButton = QtGui.QPushButton(self.tab)
+ sizePolicy = QtGui.QSizePolicy(QtGui.QSizePolicy.Minimum, QtGui.QSizePolicy.Expanding)
+ sizePolicy.setHorizontalStretch(0)
+ sizePolicy.setVerticalStretch(0)
+ sizePolicy.setHeightForWidth(self.pauseButton.sizePolicy().hasHeightForWidth())
+ self.pauseButton.setSizePolicy(sizePolicy)
+ self.pauseButton.setObjectName(_fromUtf8("pauseButton"))
+ self.verticalLayout_2.addWidget(self.pauseButton)
+ self.resumeButton = QtGui.QPushButton(self.tab)
+ sizePolicy = QtGui.QSizePolicy(QtGui.QSizePolicy.Minimum, QtGui.QSizePolicy.Expanding)
+ sizePolicy.setHorizontalStretch(0)
+ sizePolicy.setVerticalStretch(0)
+ sizePolicy.setHeightForWidth(self.resumeButton.sizePolicy().hasHeightForWidth())
+ self.resumeButton.setSizePolicy(sizePolicy)
+ self.resumeButton.setObjectName(_fromUtf8("resumeButton"))
+ self.verticalLayout_2.addWidget(self.resumeButton)
+ self.stopButton = QtGui.QPushButton(self.tab)
+ sizePolicy = QtGui.QSizePolicy(QtGui.QSizePolicy.Minimum, QtGui.QSizePolicy.Expanding)
+ sizePolicy.setHorizontalStretch(0)
+ sizePolicy.setVerticalStretch(0)
+ sizePolicy.setHeightForWidth(self.stopButton.sizePolicy().hasHeightForWidth())
+ self.stopButton.setSizePolicy(sizePolicy)
+ self.stopButton.setObjectName(_fromUtf8("stopButton"))
+ self.verticalLayout_2.addWidget(self.stopButton)
+ self.send2baseButton = QtGui.QPushButton(self.tab)
+ sizePolicy = QtGui.QSizePolicy(QtGui.QSizePolicy.Minimum, QtGui.QSizePolicy.Expanding)
+ sizePolicy.setHorizontalStretch(0)
+ sizePolicy.setVerticalStretch(0)
+ sizePolicy.setHeightForWidth(self.send2baseButton.sizePolicy().hasHeightForWidth())
+ self.send2baseButton.setSizePolicy(sizePolicy)
+ self.send2baseButton.setObjectName(_fromUtf8("send2baseButton"))
+ self.verticalLayout_2.addWidget(self.send2baseButton)
+ self.tabWidget.addTab(self.tab, _fromUtf8(""))
+ self.tab_2 = QtGui.QWidget()
+ self.tab_2.setObjectName(_fromUtf8("tab_2"))
+ self.verticalLayout_3 = QtGui.QVBoxLayout(self.tab_2)
+ self.verticalLayout_3.setMargin(0)
+ self.verticalLayout_3.setObjectName(_fromUtf8("verticalLayout_3"))
+ self.textEdit = QtGui.QTextEdit(self.tab_2)
+ self.textEdit.setReadOnly(True)
+ self.textEdit.setObjectName(_fromUtf8("textEdit"))
+ self.verticalLayout_3.addWidget(self.textEdit)
+ self.tabWidget.addTab(self.tab_2, _fromUtf8(""))
+ self.verticalLayout.addWidget(self.tabWidget)
+ MainWindow.setCentralWidget(self.centralwidget)
+ self.menubar = QtGui.QMenuBar(MainWindow)
+ self.menubar.setGeometry(QtCore.QRect(0, 0, 472, 26))
+ self.menubar.setObjectName(_fromUtf8("menubar"))
+ self.menuAbout = QtGui.QMenu(self.menubar)
+ self.menuAbout.setObjectName(_fromUtf8("menuAbout"))
+ MainWindow.setMenuBar(self.menubar)
+ self.actionNeato_Account = QtGui.QAction(MainWindow)
+ self.actionNeato_Account.setObjectName(_fromUtf8("actionNeato_Account"))
+ self.actionMy_robot = QtGui.QAction(MainWindow)
+ self.actionMy_robot.setObjectName(_fromUtf8("actionMy_robot"))
+ self.actionThis_software = QtGui.QAction(MainWindow)
+ self.actionThis_software.setObjectName(_fromUtf8("actionThis_software"))
+ self.menuAbout.addAction(self.actionMy_robot)
+ self.menubar.addAction(self.menuAbout.menuAction())
+
+
+
+
+ def getAvailCmds():
+ run(["python","aneatocli.py","--gc"])
+ with open("robotstate.json","r") as json_file:
+ data=json.load(json_file)
+
+ def setbuttonState(dictstr,obj):
+ if data[dictstr]:
+ obj.setEnabled(True)
+ else:
+ obj.setEnabled(False)
+ setbuttonState("start",self.startButton)
+ setbuttonState("stop",self.stopButton)
+ setbuttonState("pause",self.pauseButton)
+ setbuttonState("resume",self.resumeButton)
+ setbuttonState("goToBase",self.send2baseButton)
+
+ getAvailCmds()
+
+ # Penser à râfraichir l'état du robot de manière moins dégueulasse avec UN thread (même si c'est chaud en python wlh. Au moins toutes les 10-15secondes
+
+
+
+ def __start(self):
+ run(["python","aneatocli.py","--go"])
+ getAvailCmds()
+
+ def __stop(self):
+ run(["python","aneatocli.py","--stp"])
+ getAvailCmds()
+
+ def __pause(self):
+ run(["python","aneatocli.py","--pse"])
+ getAvailCmds()
+
+
+
+ def __resume(self):
+ run(["python","aneatocli.py","--res"])
+ getAvailCmds()
+
+
+ def __return(self):
+ run(["python","aneatocli.py","--base"])
+ getAvailCmds()
+
+ self.startButton.clicked.connect(__start)
+ self.stopButton.clicked.connect(__stop)
+ self.pauseButton.clicked.connect(__pause)
+ self.resumeButton.clicked.connect(__resume)
+ self.send2baseButton.clicked.connect(__return)
+
+
+
+ self.retranslateUi(MainWindow)
+ self.tabWidget.setCurrentIndex(0)
+ QtCore.QMetaObject.connectSlotsByName(MainWindow)
+
+ def retranslateUi(self, MainWindow):
+ MainWindow.setWindowTitle(_translate("MainWindow", "Neato Control", None))
+ self.startButton.setText(_translate("MainWindow", "Start", None))
+ self.pauseButton.setText(_translate("MainWindow", "Pause", None))
+ self.resumeButton.setText(_translate("MainWindow", "Resume", None))
+ self.stopButton.setText(_translate("MainWindow", "Stop", None))
+ self.send2baseButton.setText(_translate("MainWindow", "Send to base", None))
+ self.tabWidget.setTabText(self.tabWidget.indexOf(self.tab), _translate("MainWindow", "Commands", None))
+ self.tabWidget.setTabText(self.tabWidget.indexOf(self.tab_2), _translate("MainWindow", "Info", None))
+ self.menuAbout.setTitle(_translate("MainWindow", "My robot", None))
+ self.actionNeato_Account.setText(_translate("MainWindow", "Neato Account", None))
+ self.actionMy_robot.setText(_translate("MainWindow", "Account Infos", None))
+ self.actionThis_software.setText(_translate("MainWindow", "This software", None))
+
+
+if __name__ == "__main__":
+ import sys
+ app = QtGui.QApplication(sys.argv)
+ MainWindow = QtGui.QMainWindow()
+ ui = Ui_MainWindow()
+ ui.setupUi(MainWindow)
+ MainWindow.show()
+ sys.exit(app.exec_())
+
diff --git a/requirements.txt b/requirements.txt
new file mode 100644
index 0000000..c90b336
--- /dev/null
+++ b/requirements.txt
@@ -0,0 +1,2 @@
+pybotvac
+docopt==0.6.2 \ No newline at end of file
diff --git a/robotCreds.json b/robotCreds.json
new file mode 100644
index 0000000..aa5d934
--- /dev/null
+++ b/robotCreds.json
@@ -0,0 +1 @@
+{"serialID":"xxx","secretID":"xxx","traits":"xxx","name":"yourrobotname"}
diff --git a/robotstate.json b/robotstate.json
new file mode 100644
index 0000000..4f8c09d
--- /dev/null
+++ b/robotstate.json
@@ -0,0 +1 @@
+{"start": false, "goToBase": false, "pause": true, "stop": true, "resume": false} \ No newline at end of file