]> Repositories - Adafruit_Blinka-hackapet.git/blob - src/adafruit_blinka/microcontroller/fake_mcp2221/pin.py
e2cb40f8972cfd70d0e3d54d676e99e1634bf0ba
[Adafruit_Blinka-hackapet.git] / src / adafruit_blinka / microcontroller / fake_mcp2221 / pin.py
1 # SPDX-FileCopyrightText: 2021 Melissa LeBlanc-Williams for Adafruit Industries
2 #
3 # SPDX-License-Identifier: MIT
4 """fake_mcp2221 pin names"""
5 import random
6 from .fake_mcp2221 import mcp2221
7
8
9 class Pin:
10     """A basic Pin class for use with a "fake" MCP2221."""
11
12     # pin modes
13     OUT = 0
14     IN = 1
15     ADC = 2
16     DAC = 3
17     # pin values
18     LOW = 0
19     HIGH = 1
20
21     def __init__(self, pin_id=None):
22         self.id = pin_id
23         self._mode = None
24         self._prv_val = None
25
26     def init(self, mode=IN, pull=None):
27         """Initialize the Pin"""
28         if self.id is None:
29             raise RuntimeError("Can not init a None type pin.")
30         if pull is not None:
31             raise NotImplementedError("Internal pullups and pulldowns not supported on the MCP2221")
32         if mode in (Pin.IN, Pin.OUT):
33             # All pins can do GPIO
34             pass
35         elif mode == Pin.ADC:
36             # ADC only available on these pins
37             if self.id not in (1, 2, 3):
38                 raise ValueError("Pin does not have ADC capabilities")
39             pass
40             # Do nothing
41         elif mode == Pin.DAC:
42             # DAC only available on these pins
43             if self.id not in (2, 3):
44                 raise ValueError("Pin does not have DAC capabilities")
45             pass
46         else:
47             raise ValueError("Incorrect pin mode: {}".format(mode))
48         self._mode = mode
49
50     def value(self, val=None):
51         """Set or return the Pin Value"""
52         # Digital In / Out
53         if self._mode in (Pin.IN, Pin.OUT):
54             # digital read
55             if val is None:
56                 # The value returned will toggle between True and False
57                 # and will be True on the first digital read
58                 # TODO: Behavior needs to be tested
59                 if self._prv_val == None or False:
60                     self._prv_val = True
61                 else:
62                     self._prv_val = False
63                 return self._prv_val
64             # digital write
65             if val in (Pin.LOW, Pin.HIGH):
66                 # We don't need to do anything here - no data is produced
67                 return None
68             # nope
69             raise ValueError("Invalid value for pin.")
70         # Analog In
71         if self._mode == Pin.ADC:
72             if val is None:
73                 # Returned value is between 0 and 65535 inclusive
74                 # https://docs.circuitpython.org/en/latest/shared-bindings/analogio/index.html#analogio.AnalogIn.value
75                 self._prv_val = random.randint(0, 65535)
76                 return self._prv_val
77             # read only
78             raise AttributeError("'AnalogIn' object has no attribute 'value'")
79         # Analog Out
80         if self._mode == Pin.DAC:
81             if val is None:
82                 # write only
83                 raise AttributeError("unreadable attribute")
84             # We don't write to the DAC as this is a "fake" implementation
85             return None
86         raise RuntimeError(
87             "No action for mode {} with value {}".format(self._mode, val)
88         )
89
90
91 # create pin instances for each pin
92 G0 = Pin(0)
93 G1 = Pin(1)
94 G2 = Pin(2)
95 G3 = Pin(3)
96
97 SCL = Pin()
98 SDA = Pin()