Skip to content
This repository was archived by the owner on Sep 30, 2019. It is now read-only.

Commit fde18b8

Browse files
committed
Fix merge conflict.
2 parents 76735db + 8d57283 commit fde18b8

File tree

5 files changed

+160
-20
lines changed

5 files changed

+160
-20
lines changed

Adafruit_GPIO/FT232H.py

+8-3
Original file line numberDiff line numberDiff line change
@@ -380,10 +380,15 @@ def output_pins(self, pins, write=True):
380380
def input(self, pin):
381381
"""Read the specified pin and return HIGH/true if the pin is pulled high,
382382
or LOW/false if pulled low."""
383-
if pin < 0 or pin > 15:
383+
return self.input_pins([pin])[0]
384+
385+
def input_pins(self, pins):
386+
"""Read multiple pins specified in the given list and return list of pin values
387+
GPIO.HIGH/True if the pin is pulled high, or GPIO.LOW/False if pulled low."""
388+
if [pin for pin in pins if pin < 0 or pin > 15]:
384389
raise ValueError('Pin must be between 0 and 15 (inclusive).')
385-
pins = self.mpsse_read_gpio()
386-
return ((pins >> pin) & 0x0001) == 1
390+
_pins = self.mpsse_read_gpio()
391+
return [((_pins >> pin) & 0x0001) == 1 for pin in pins]
387392

388393

389394
class SPI(object):

Adafruit_GPIO/GPIO.py

+43-1
Original file line numberDiff line numberDiff line change
@@ -71,6 +71,13 @@ def is_low(self, pin):
7171
"""Return true if the specified pin is pulled low."""
7272
return self.input(pin) == LOW
7373

74+
75+
# Basic implementation of multiple pin methods just loops through pins and
76+
# processes each one individually. This is not optimal, but derived classes can
77+
# provide a more optimal implementation that deals with groups of pins
78+
# simultaneously.
79+
# See MCP230xx or PCF8574 classes for examples of optimized implementations.
80+
7481
def output_pins(self, pins):
7582
"""Set multiple pins high or low at once. Pins should be a dict of pin
7683
name to pin value (HIGH/True for 1, LOW/False for 0). All provided pins
@@ -87,10 +94,18 @@ def setup_pins(self, pins):
8794
"""Setup multiple pins as inputs or outputs at once. Pins should be a
8895
dict of pin name to pin type (IN or OUT).
8996
"""
90-
# General implementation that can be improved by subclasses.
97+
# General implementation that can be optimized by derived classes.
9198
for pin, value in iter(pins.items()):
9299
self.setup(pin, value)
93100

101+
def input_pins(self, pins):
102+
"""Read multiple pins specified in the given list and return list of pin values
103+
GPIO.HIGH/True if the pin is pulled high, or GPIO.LOW/False if pulled low.
104+
"""
105+
# General implementation that can be optimized by derived classes.
106+
return [self.input(pin) for pin in pins]
107+
108+
94109
def add_event_detect(self, pin, edge):
95110
"""Enable edge detection events for a particular GPIO channel. Pin
96111
should be type IN. Edge must be RISING, FALLING or BOTH.
@@ -127,6 +142,19 @@ def cleanup(self, pin=None):
127142
"""
128143
raise NotImplementedError
129144

145+
146+
# helper functions useful to derived classes
147+
148+
def _validate_pin(self, pin):
149+
# Raise an exception if pin is outside the range of allowed values.
150+
if pin < 0 or pin >= self.NUM_GPIO:
151+
raise ValueError('Invalid GPIO value, must be between 0 and {0}.'.format(self.NUM_GPIO))
152+
153+
def _bit2(self, src, bit, val):
154+
bit = 1 << bit
155+
return (src | bit) if val else (src & ~bit)
156+
157+
130158
class RPiGPIOAdapter(BaseGPIO):
131159
"""GPIO implementation for the Raspberry Pi using the RPi.GPIO library."""
132160

@@ -171,6 +199,13 @@ def input(self, pin):
171199
"""
172200
return self.rpi_gpio.input(pin)
173201

202+
def input_pins(self, pins):
203+
"""Read multiple pins specified in the given list and return list of pin values
204+
GPIO.HIGH/True if the pin is pulled high, or GPIO.LOW/False if pulled low.
205+
"""
206+
# maybe rpi has a mass read... it would be more efficient to use it if it exists
207+
return [self.rpi_gpio.input(pin) for pin in pins]
208+
174209
def add_event_detect(self, pin, edge, callback=None, bouncetime=-1):
175210
"""Enable edge detection events for a particular GPIO channel. Pin
176211
should be type IN. Edge must be RISING, FALLING or BOTH. Callback is a
@@ -254,6 +289,13 @@ def input(self, pin):
254289
"""
255290
return self.bbio_gpio.input(pin)
256291

292+
def input_pins(self, pins):
293+
"""Read multiple pins specified in the given list and return list of pin values
294+
GPIO.HIGH/True if the pin is pulled high, or GPIO.LOW/False if pulled low.
295+
"""
296+
# maybe bbb has a mass read... it would be more efficient to use it if it exists
297+
return [self.bbio_gpio.input(pin) for pin in pins]
298+
257299
def add_event_detect(self, pin, edge, callback=None, bouncetime=-1):
258300
"""Enable edge detection events for a particular GPIO channel. Pin
259301
should be type IN. Edge must be RISING, FALLING or BOTH. Callback is a

Adafruit_GPIO/MCP230xx.py

100755100644
+14-15
Original file line numberDiff line numberDiff line change
@@ -50,10 +50,6 @@ def __init__(self, address, i2c=None, **kwargs):
5050
self.write_iodir()
5151
self.write_gppu()
5252

53-
def _validate_pin(self, pin):
54-
# Raise an exception if pin is outside the range of allowed values.
55-
if pin < 0 or pin >= self.NUM_GPIO:
56-
raise ValueError('Invalid GPIO value, must be between 0 and {0}.'.format(self.NUM_GPIO))
5753

5854
def setup(self, pin, value):
5955
"""Set the input or output mode for a specified pin. Mode should be
@@ -69,24 +65,19 @@ def setup(self, pin, value):
6965
raise ValueError('Unexpected value. Must be GPIO.IN or GPIO.OUT.')
7066
self.write_iodir()
7167

68+
7269
def output(self, pin, value):
7370
"""Set the specified pin the provided high/low value. Value should be
74-
either GPIO.HIGH/GPIO.LOW or a boolean (True = high).
71+
either GPIO.HIGH/GPIO.LOW or a boolean (True = HIGH).
7572
"""
76-
self._validate_pin(pin)
77-
# Set bit on or off.
78-
if value:
79-
self.gpio[int(pin/8)] |= 1 << (int(pin%8))
80-
else:
81-
self.gpio[int(pin/8)] &= ~(1 << (int(pin%8)))
82-
# Write GPIO state.
83-
self.write_gpio()
73+
self.output_pins({pin: value})
8474

8575
def output_pins(self, pins):
8676
"""Set multiple pins high or low at once. Pins should be a dict of pin
8777
name to pin value (HIGH/True for 1, LOW/False for 0). All provided pins
8878
will be set to the given values.
8979
"""
80+
[self._validate_pin(pin) for pin in pins.keys()]
9081
# Set each changed pin's bit.
9182
for pin, value in iter(pins.items()):
9283
if value:
@@ -96,15 +87,23 @@ def output_pins(self, pins):
9687
# Write GPIO state.
9788
self.write_gpio()
9889

90+
9991
def input(self, pin):
10092
"""Read the specified pin and return GPIO.HIGH/True if the pin is pulled
10193
high, or GPIO.LOW/False if pulled low.
10294
"""
103-
self._validate_pin(pin)
95+
return self.input_pins([pin])[0]
96+
97+
def input_pins(self, pins):
98+
"""Read multiple pins specified in the given list and return list of pin values
99+
GPIO.HIGH/True if the pin is pulled high, or GPIO.LOW/False if pulled low.
100+
"""
101+
[self._validate_pin(pin) for pin in pins]
104102
# Get GPIO state.
105103
gpio = self._device.readList(self.GPIO, self.gpio_bytes)
106104
# Return True if pin's bit is set.
107-
return (gpio[int(pin/8)] & 1 << (int(pin%8))) > 0
105+
return [(gpio[int(pin/8)] & 1 << (int(pin%8))) > 0 for pin in pins]
106+
108107

109108
def pullup(self, pin, enabled):
110109
"""Turn on the pull-up resistor for the specified pin if enabled is True,

Adafruit_GPIO/PCF8574.py

+94
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,94 @@
1+
'''
2+
Adafruit compatible using BaseGPIO class to represent a PCF8574/A IO expander
3+
Copyright (C) 2015 Sylvan Butler
4+
5+
Permission is hereby granted, free of charge, to any person obtaining a copy of
6+
this software and associated documentation files (the "Software"), to deal in
7+
the Software without restriction, including without limitation the rights to
8+
use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies
9+
of the Software, and to permit persons to whom the Software is furnished to do
10+
so, subject to the following conditions:
11+
12+
The above copyright notice and this permission notice shall be included in all
13+
copies or substantial portions of the Software.
14+
15+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21+
SOFTWARE.'''
22+
23+
import Adafruit_GPIO as GPIO
24+
import Adafruit_GPIO.I2C as I2C
25+
26+
27+
28+
IN = GPIO.IN
29+
OUT = GPIO.OUT
30+
HIGH = GPIO.HIGH
31+
LOW = GPIO.LOW
32+
33+
34+
class PCF8574(GPIO.BaseGPIO):
35+
"""Class to represent a PCF8574 or PCF8574A GPIO extender. Compatible
36+
with the Adafruit_GPIO BaseGPIO class so it can be used as a custom GPIO
37+
class for interacting with device.
38+
"""
39+
40+
NUM_GPIO = 8
41+
42+
def __init__(self, address=0x27, busnum=None, i2c=None, **kwargs):
43+
address = int(address)
44+
self.__name__ = \
45+
"PCF8574" if address in range(0x20, 0x28) else \
46+
"PCF8574A" if address in range(0x38, 0x40) else \
47+
"Bad address for PCF8574(A): 0x%02X not in range [0x20..0x27, 0x38..0x3F]" % address
48+
if self.__name__[0] != 'P':
49+
raise ValueError(self.__name__)
50+
# Create I2C device.
51+
i2c = i2c or I2C
52+
busnum = busnum or i2c.get_default_bus()
53+
self._device = i2c.get_i2c_device(address, busnum, **kwargs)
54+
# Buffer register values so they can be changed without reading.
55+
self.iodir = 0xFF # Default direction to all inputs is in
56+
self.gpio = 0x00
57+
self._write_pins()
58+
59+
60+
def _write_pins(self):
61+
self._device.writeRaw8(self.gpio | self.iodir)
62+
63+
def _read_pins(self):
64+
return self._device.readRaw8() & self.iodir
65+
66+
67+
def setup(self, pin, mode):
68+
self.setup_pins({pin: mode})
69+
70+
def setup_pins(self, pins):
71+
if False in [y for x,y in [(self._validate_pin(pin),mode in (IN,OUT)) for pin,mode in pins.iteritems()]]:
72+
raise ValueError('Invalid MODE, IN or OUT')
73+
for pin,mode in pins.iteritems():
74+
self.iodir = self._bit2(self.iodir, pin, mode)
75+
self._write_pins()
76+
77+
78+
def output(self, pin, value):
79+
self.output_pins({pin: value})
80+
81+
def output_pins(self, pins):
82+
[self._validate_pin(pin) for pin in pins.keys()]
83+
for pin,value in pins.iteritems():
84+
self.gpio = self._bit2(self.gpio, pin, bool(value))
85+
self._write_pins()
86+
87+
88+
def input(self, pin):
89+
return self.input_pins([pin])[0]
90+
91+
def input_pins(self, pins):
92+
[self._validate_pin(pin) for pin in pins]
93+
inp = self._read_pins()
94+
return [bool(inp & (1<<pin)) for pin in pins]

setup.py

+1-1
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,7 @@
1111
requires.append('spidev')
1212

1313
setup(name = 'Adafruit_GPIO',
14-
version = '0.9.2',
14+
version = '0.9.3',
1515
author = 'Tony DiCola',
1616
author_email = 'tdicola@adafruit.com',
1717
description = 'Library to provide a cross-platform GPIO interface on the Raspberry Pi and Beaglebone Black using the RPi.GPIO and Adafruit_BBIO libraries.',

0 commit comments

Comments
 (0)