eric6/MicroPython/MicroPythonDevices.py

branch
micropython
changeset 7054
fb84d8489bc1
child 7058
bdd583f96e96
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/eric6/MicroPython/MicroPythonDevices.py	Sun Jul 07 18:48:17 2019 +0200
@@ -0,0 +1,220 @@
+# -*- coding: utf-8 -*-
+
+# Copyright (c) 2019 Detlev Offenbach <detlev@die-offenbachs.de>
+#
+
+"""
+Module implementing some utility functions and the MicroPythonDevice base
+class.
+"""
+
+from __future__ import unicode_literals
+
+import logging
+
+from PyQt5.QtCore import QObject
+
+import Globals
+import UI.PixmapCache
+
+
+SupportedBoards = {
+    "esp": {
+        "ids": [
+            (0x1A86, 0x7523),       # HL-340
+            (0x10C4, 0xEA60),       # CP210x
+            (0x0403, 0x6015),       # Sparkfun ESP32 VID, PID
+        ],
+        "description": "ESP8266, ESP32",
+        "icon": "esp32Device",
+    },
+    
+    "adafruit": {
+        "ids": [
+            (0x239A, 0x8015),       # Adafruit Feather M0 CircuitPython
+            (0x239A, 0x8023),       # Adafruit Feather M0 Express CircuitPython
+            (0x239A, 0x801B),       # Adafruit Feather M0 Express CircuitPython
+            (0x239A, 0x8014),       # Adafruit Metro M0 CircuitPython
+            (0x239A, 0x8019),       # Adafruit CircuitPlayground
+                                    #   Express CircuitPython
+            (0x239A, 0x801D),       # Adafruit Gemma M0
+            (0x239A, 0x801F),       # Adafruit Trinket M0
+            (0x239A, 0x8012),       # Adafruit ItsyBitsy M0
+            (0x239A, 0x8021),       # Adafruit Metro M4
+            (0x239A, 0x8025),       # Adafruit Feather RadioFruit
+            (0x239A, 0x8026),       # Adafruit Feather M4
+            (0x239A, 0x8028),       # Adafruit pIRKey M0
+            (0x239A, 0x802A),       # Adafruit Feather 52840
+            (0x239A, 0x802C),       # Adafruit Itsy M4
+            (0x239A, 0x802E),       # Adafruit CRICKit M0
+            (0x239A, 0xD1ED),       # Adafruit HalloWing M0
+            (0x239A, 0x8030),       # Adafruit NeoTrellis M4
+            (0x239A, 0x8032),       # Grand Central
+            (0x2B04, 0xC00C),       # Particle Argon
+            (0x2B04, 0xC00D),       # Particle Boron
+            (0x2B04, 0xC00E),       # Particle Xenon
+            (0x239A, 0x8034),       # future board
+            (0x239A, 0x8036),       # future board
+            (0x239A, 0x8038),       # future board
+            (0x239A, 0x803A),       # future board
+            (0x239A, 0x803C),       # future board
+            (0x239A, 0x803E),       # future board
+            (0x239A, None),         # Any Adafruit Boards
+        ],
+        "description": "Adafruit CircuitPython",
+        "icon": "adafruitDevice",
+    },
+    
+    "bbc_microbit": {
+        "ids": [
+            (0x0D28, 0x0204),       # micro:bit USB VID, PID
+        ],
+        "description": "BBC micro:bit",
+        "icon": "microbitDevice",
+    },
+}
+
+
+def getSupportedDevices():
+    """
+    Function to get a list of supported MicroPython devices.
+    
+    @return set of tuples with the board type and description
+    @rtype set of tuples of (str, str)
+    """
+    boards = []
+    for board in SupportedBoards:
+        boards.append(
+            (board, SupportedBoards[board]["description"]))
+    return boards
+
+
+def getFoundDevices():
+    """
+    Function to check the serial ports for supported MicroPython devices.
+    
+    @return set of tuples with the board type, a description and the serial
+        port it is connected at
+    @rtype set of tuples of (str, str, str)
+    """
+    from PyQt5.QtSerialPort import QSerialPortInfo
+    
+    foundDevices = []
+    
+    availablePorts = QSerialPortInfo.availablePorts()
+    for port in availablePorts:
+        vid = port.vendorIdentifier()
+        pid = port.productIdentifier()
+        for board in SupportedBoards:
+            if ((vid, pid) in SupportedBoards[board]["ids"] or
+                    (vid, None) in SupportedBoards[board]["ids"]):
+                foundDevices.append(
+                    (board, SupportedBoards[board]["description"],
+                     port.portName()))
+                break
+        else:
+            logging.debug("Unknown device: (0x%04x:0x%04x)", vid, pid)
+    
+    return foundDevices
+
+
+def getDeviceIcon(boardName, iconFormat=True):
+    """
+    Function to get the icon for the given board.
+    
+    @param boardName name of the board
+    @type str
+    @param iconFormat flag indicating to get an icon or a pixmap
+    @type bool
+    @return icon for the board (iconFormat == True) or
+        a pixmap (iconFormat == False)
+    @rtype QIcon or QPixmap
+    """
+    if boardName in SupportedBoards:
+        iconName = SupportedBoards[boardName]["icon"]
+    else:
+        # return a generic MicroPython icon
+        iconName = "micropython48"
+    
+    if iconFormat:
+        return UI.PixmapCache.getIcon(iconName)
+    else:
+        return UI.PixmapCache.getPixmap(iconName)
+
+
+def getDevice(deviceType):
+    """
+    Public method to instantiate a specific MicroPython device interface.
+    
+    @param deviceType type of the device interface
+    @type str
+    @return instantiated device interface
+    @rtype MicroPythonDevice
+    """
+    # TODO: not implemented yet
+    return None
+
+
+class MicroPythonDevice(QObject):
+    """
+    Base class for the more specific MicroPython devices.
+    """
+    def __init__(self, parent=None):
+        """
+        Constructor
+        
+        @param parent reference to the parent object
+        @type QObject
+        """
+        super(MicroPythonDevice, self).__init__(parent)
+    
+    def supportedActions(self):
+        """
+        Public method to get the names of the supported actions.
+        
+        @return tuple of supported actions out of "repl", "run", "files",
+            "chart"
+        @rtype tuple of str
+        """
+        return tuple()
+    
+    def findDevice(self, deviceType):
+        """
+        Public method to find the first device of a specific type.
+        
+        @param deviceType device type
+        @type str
+        @return tuple containing the port the device is connected to and its
+            serial number
+        @rtype tuple of (str, str)
+        """
+        from PyQt5.QtSerialPort import QSerialPortInfo
+        
+        availablePorts = QSerialPortInfo.availablePorts()
+        for port in availablePorts:
+            vid = port.vendorIdentifier()
+            pid = port.productIdentifier()
+            for board in SupportedBoards:
+                if ((vid, pid) in SupportedBoards[board] or
+                        (vid, None) in SupportedBoards[board]):
+                    portName = port.portName()
+                    serialNumber = port.serialNumber()
+                    return (self.__portPath(portName), serialNumber)
+        
+        return (None, None)
+    
+    def __portPath(self, portName):
+        """
+        Private method to get the full path of a given port.
+        
+        @param portName name of the port the path shall be determined for
+        @type str
+        @return full port path
+        @rtype str
+        """
+        if Globals.isWindowsPlatform():
+            # return name unchanged
+            return portName
+        else:
+            # assume Posix system (Linux or macOS)
+            return "/dev/{0}".format(portName)

eric ide

mercurial