"""
Contains definitions for Python 3 APIs so they can be used in the editor for
autocomplete and call tips.

Copyright (c) 2015-2017 Nicholas H.Tollervey and others (see the AUTHORS file).

This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.

This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
GNU General Public License for more details.

You should have received a copy of the GNU General Public License
along with this program.  If not, see <http://www.gnu.org/licenses/>.
"""


PI_APIS = [
    _(
        "gpiozero.AnalogInputDevice(*args, **kwargs) \nRepresents an analog input device connected to SPI (serial interface).\n\nTypical analog input devices are `analog to digital converters`_ (ADCs).\nSeveral classes are provided for specific ADC chips, including\n:class:`MCP3004`, :class:`MCP3008`, :class:`MCP3204`, and :class:`MCP3208`.\n\nThe following code demonstrates reading the first channel of an MCP3008\nchip attached to the Pi's SPI pins::\n\n    from gpiozero import MCP3008\n\n    pot = MCP3008(0)\n    print(pot.value)\n\nThe :attr:`value` attribute is normalized such that its value is always\nbetween 0.0 and 1.0 (or in special cases, such as differential sampling,\n-1 to +1). Hence, you can use an analog input to control the brightness of\na :class:`PWMLED` like so::\n\n    from gpiozero import MCP3008, PWMLED\n\n    pot = MCP3008(0)\n    led = PWMLED(17)\n    led.source = pot.values\n\n.. _analog to digital converters: https://en.wikipedia.org/wiki/Analog-to-digital_converter"
    ),
    _(
        "gpiozero.AngularServo(*args, **kwargs) \nExtends :class:`Servo` and represents a rotational PWM-controlled servo\nmotor which can be set to particular angles (assuming valid minimum and\nmaximum angles are provided to the constructor).\n\nConnect a power source (e.g. a battery pack or the 5V pin) to the power\ncable of the servo (this is typically colored red); connect the ground\ncable of the servo (typically colored black or brown) to the negative of\nyour battery pack, or a GND pin; connect the final cable (typically colored\nwhite or orange) to the GPIO pin you wish to use for controlling the servo.\n\nNext, calibrate the angles that the servo can rotate to. In an interactive\nPython session, construct a :class:`Servo` instance. The servo should move\nto its mid-point by default. Set the servo to its minimum value, and\nmeasure the angle from the mid-point. Set the servo to its maximum value,\nand again measure the angle::\n\n    >>> from gpiozero import Servo\n    >>> s = Servo(17)\n    >>> s.min() # measure the angle\n    >>> s.max() # measure the angle\n\nYou should now be able to construct an :class:`AngularServo` instance\nwith the correct bounds::\n\n    >>> from gpiozero import AngularServo\n    >>> s = AngularServo(17, min_angle=-42, max_angle=44)\n    >>> s.angle = 0.0\n    >>> s.angle\n    0.0\n    >>> s.angle = 15\n    >>> s.angle\n    15.0\n\n.. note::\n\n    You can set *min_angle* greater than *max_angle* if you wish to reverse\n    the sense of the angles (e.g. ``min_angle=45, max_angle=-45``). This\n    can be useful with servos that rotate in the opposite direction to your\n    expectations of minimum and maximum.\n\n:param int pin:\n    The GPIO pin which the device is attached to. See :ref:`pin_numbering`\n    for valid pin numbers.\n\n:param float initial_angle:\n    Sets the servo's initial angle to the specified value. The default is\n    0. The value specified must be between *min_angle* and *max_angle*\n    inclusive. ``None`` means to start the servo un-controlled (see\n    :attr:`value`).\n\n:param float min_angle:\n    Sets the minimum angle that the servo can rotate to. This defaults to\n    -90, but should be set to whatever you measure from your servo during\n    calibration.\n\n:param float max_angle:\n    Sets the maximum angle that the servo can rotate to. This defaults to\n    90, but should be set to whatever you measure from your servo during\n    calibration.\n\n:param float min_pulse_width:\n    The pulse width corresponding to the servo's minimum position. This\n    defaults to 1ms.\n\n:param float max_pulse_width:\n    The pulse width corresponding to the servo's maximum position. This\n    defaults to 2ms.\n\n:param float frame_width:\n    The length of time between servo control pulses measured in seconds.\n    This defaults to 20ms which is a common value for servos."
    ),
    _(
        "gpiozero.BadEventHandler() \nError raised when an event handler with an incompatible prototype is specified"
    ),
    _(
        "gpiozero.BadQueueLen() \nError raised when non-positive queue length is specified"
    ),
    _(
        "gpiozero.BadWaitTime() \nError raised when an invalid wait time is specified"
    ),
    _(
        'gpiozero.Button(*args, **kwargs) \nExtends :class:`DigitalInputDevice` and represents a simple push button\nor switch.\n\nConnect one side of the button to a ground pin, and the other to any GPIO\npin. Alternatively, connect one side of the button to the 3V3 pin, and the\nother to any GPIO pin, then set *pull_up* to ``False`` in the\n:class:`Button` constructor.\n\nThe following example will print a line of text when the button is pushed::\n\n    from gpiozero import Button\n\n    button = Button(4)\n    button.wait_for_press()\n    print("The button was pressed!")\n\n:param int pin:\n    The GPIO pin which the button is attached to. See :ref:`pin_numbering`\n    for valid pin numbers.\n\n:param bool pull_up:\n    If ``True`` (the default), the GPIO pin will be pulled high by default.\n    In this case, connect the other side of the button to ground. If\n    ``False``, the GPIO pin will be pulled low by default. In this case,\n    connect the other side of the button to 3V3.\n\n:param float bounce_time:\n    If ``None`` (the default), no software bounce compensation will be\n    performed. Otherwise, this is the length of time (in seconds) that the\n    component will ignore changes in state after an initial change.\n\n:param float hold_time:\n    The length of time (in seconds) to wait after the button is pushed,\n    until executing the :attr:`when_held` handler. Defaults to ``1``.\n\n:param bool hold_repeat:\n    If ``True``, the :attr:`when_held` handler will be repeatedly executed\n    as long as the device remains active, every *hold_time* seconds. If\n    ``False`` (the default) the :attr:`when_held` handler will be only be\n    executed once per hold.'
    ),
    _(
        "gpiozero.ButtonBoard(*args, **kwargs) \nExtends :class:`CompositeDevice` and represents a generic button board or\ncollection of buttons.\n\n:param int \\*pins:\n    Specify the GPIO pins that the buttons of the board are attached to.\n    You can designate as many pins as necessary.\n\n:param bool pull_up:\n    If ``True`` (the default), the GPIO pins will be pulled high by\n    default. In this case, connect the other side of the buttons to\n    ground. If ``False``, the GPIO pins will be pulled low by default. In\n    this case, connect the other side of the buttons to 3V3. This\n    parameter can only be specified as a keyword parameter.\n\n:param float bounce_time:\n    If ``None`` (the default), no software bounce compensation will be\n    performed. Otherwise, this is the length of time (in seconds) that the\n    buttons will ignore changes in state after an initial change. This\n    parameter can only be specified as a keyword parameter.\n\n:param float hold_time:\n    The length of time (in seconds) to wait after any button is pushed,\n    until executing the :attr:`when_held` handler. Defaults to ``1``. This\n    parameter can only be specified as a keyword parameter.\n\n:param bool hold_repeat:\n    If ``True``, the :attr:`when_held` handler will be repeatedly executed\n    as long as any buttons remain held, every *hold_time* seconds. If\n    ``False`` (the default) the :attr:`when_held` handler will be only be\n    executed once per hold. This parameter can only be specified as a\n    keyword parameter.\n\n:param \\*\\*named_pins:\n    Specify GPIO pins that buttons of the board are attached to,\n    associating each button with a property name. You can designate as\n    many pins as necessary and use any names, provided they're not already\n    in use by something else."
    ),
    _(
        "gpiozero.Buzzer(*args, **kwargs) \nExtends :class:`DigitalOutputDevice` and represents a digital buzzer\ncomponent.\n\nConnect the cathode (negative pin) of the buzzer to a ground pin; connect\nthe other side to any GPIO pin.\n\nThe following example will sound the buzzer::\n\n    from gpiozero import Buzzer\n\n    bz = Buzzer(3)\n    bz.on()\n\n:param int pin:\n    The GPIO pin which the buzzer is attached to. See :ref:`pin_numbering`\n    for valid pin numbers.\n\n:param bool active_high:\n    If ``True`` (the default), the buzzer will operate normally with the\n    circuit described above. If ``False`` you should wire the cathode to\n    the GPIO pin, and the anode to a 3V3 pin.\n\n:param bool initial_value:\n    If ``False`` (the default), the buzzer will be silent initially.  If\n    ``None``, the buzzer will be left in whatever state the pin is found in\n    when configured for output (warning: this can be on).  If ``True``, the\n    buzzer will be switched on initially."
    ),
    _(
        'gpiozero.CPUTemperature(*args, **kwargs) \nExtends :class:`InternalDevice` to provide a device which is active when\nthe CPU temperature exceeds the *threshold* value.\n\nThe following example plots the CPU\'s temperature on an LED bar graph::\n\n    from gpiozero import LEDBarGraph, CPUTemperature\n    from signal import pause\n\n    # Use minimums and maximums that are closer to "normal" usage so the\n    # bar graph is a bit more "lively"\n    temp = CPUTemperature(min_temp=50, max_temp=90)\n    graph = LEDBarGraph(5, 6, 13, 19, 25, pwm=True)\n    graph.source = temp.values\n    pause()\n\n:param str sensor_file:\n    The file from which to read the temperature. This defaults to the\n    sysfs file :file:`/sys/class/thermal/thermal_zone0/temp`. Whatever\n    file is specified is expected to contain a single line containing the\n    temperature in milli-degrees celsius.\n\n:param float min_temp:\n    The temperature at which :attr:`value` will read 0.0. This defaults to\n    0.0.\n\n:param float max_temp:\n    The temperature at which :attr:`value` will read 1.0. This defaults to\n    100.0.\n\n:param float threshold:\n    The temperature above which the device will be considered "active".\n    This defaults to 80.0.'
    ),
    _(
        "gpiozero.CamJamKitRobot(*args, **kwargs) \nExtends :class:`Robot` for the `CamJam #3 EduKit`_ robot controller.\n\nThe CamJam robot controller pins are fixed and therefore there's no need\nto specify them when constructing this class. The following example drives\nthe robot forward::\n\n    from gpiozero import CamJamKitRobot\n\n    robot = CamJamKitRobot()\n    robot.forward()\n\n.. _CamJam #3 EduKit: http://camjam.me/?page_id=1035"
    ),
    _(
        "gpiozero.CompositeDevice(*args, **kwargs) \nExtends :class:`Device`. Represents a device composed of multiple devices\nlike simple HATs, H-bridge motor controllers, robots composed of multiple\nmotors, etc.\n\nThe constructor accepts subordinate devices as positional or keyword\narguments.  Positional arguments form unnamed devices accessed via the\n:attr:`all` attribute, while keyword arguments are added to the device\nas named (read-only) attributes.\n\n:param list _order:\n    If specified, this is the order of named items specified by keyword\n    arguments (to ensure that the :attr:`value` tuple is constructed with a\n    specific order). All keyword arguments *must* be included in the\n    collection. If omitted, an alphabetically sorted order will be selected\n    for keyword arguments."
    ),
    _(
        "gpiozero.CompositeDeviceBadDevice() \nError raised when a composite device is constructed with an object that doesn't inherit from :class:`Device`"
    ),
    _(
        "gpiozero.CompositeDeviceBadName() \nError raised when a composite device is constructed with a reserved name"
    ),
    _(
        "gpiozero.CompositeDeviceBadOrder() \nError raised when a composite device is constructed with an incomplete order"
    ),
    _(
        "gpiozero.CompositeDeviceError() \nBase class for errors specific to the CompositeDevice hierarchy"
    ),
    _(
        "gpiozero.CompositeOutputDevice(*args, **kwargs) \nExtends :class:`CompositeDevice` with :meth:`on`, :meth:`off`, and\n:meth:`toggle` methods for controlling subordinate output devices.  Also\nextends :attr:`value` to be writeable.\n\n:param list _order:\n    If specified, this is the order of named items specified by keyword\n    arguments (to ensure that the :attr:`value` tuple is constructed with a\n    specific order). All keyword arguments *must* be included in the\n    collection. If omitted, an alphabetically sorted order will be selected\n    for keyword arguments."
    ),
    _(
        "gpiozero.Device(*args, **kwargs) \nRepresents a single device of any type; GPIO-based, SPI-based, I2C-based,\netc. This is the base class of the device hierarchy. It defines the\nbasic services applicable to all devices (specifically thhe :attr:`is_active`\nproperty, the :attr:`value` property, and the :meth:`close` method)."
    ),
    _(
        "gpiozero.DeviceClosed() \nError raised when an operation is attempted on a closed device"
    ),
    _(
        "gpiozero.DigitalInputDevice(*args, **kwargs) \nRepresents a generic input device with typical on/off behaviour.\n\nThis class extends :class:`InputDevice` with machinery to fire the active\nand inactive events for devices that operate in a typical digital manner:\nstraight forward on / off states with (reasonably) clean transitions\nbetween the two.\n\n:param float bounce_time:\n    Specifies the length of time (in seconds) that the component will\n    ignore changes in state after an initial change. This defaults to\n    ``None`` which indicates that no bounce compensation will be performed."
    ),
    _(
        "gpiozero.DigitalOutputDevice(*args, **kwargs) \nRepresents a generic output device with typical on/off behaviour.\n\nThis class extends :class:`OutputDevice` with a :meth:`blink` method which\nuses an optional background thread to handle toggling the device state\nwithout further interaction."
    ),
    _(
        "gpiozero.DistanceSensor(*args, **kwargs) \nExtends :class:`SmoothedInputDevice` and represents an HC-SR04 ultrasonic\ndistance sensor, as found in the `CamJam #3 EduKit`_.\n\nThe distance sensor requires two GPIO pins: one for the *trigger* (marked\nTRIG on the sensor) and another for the *echo* (marked ECHO on the sensor).\nHowever, a voltage divider is required to ensure the 5V from the ECHO pin\ndoesn't damage the Pi. Wire your sensor according to the following\ninstructions:\n\n1. Connect the GND pin of the sensor to a ground pin on the Pi.\n\n2. Connect the TRIG pin of the sensor a GPIO pin.\n\n3. Connect a 330Ω resistor from the ECHO pin of the sensor to a different\n   GPIO pin.\n\n4. Connect a 470Ω resistor from ground to the ECHO GPIO pin. This forms\n   the required voltage divider.\n\n5. Finally, connect the VCC pin of the sensor to a 5V pin on the Pi.\n\nThe following code will periodically report the distance measured by the\nsensor in cm assuming the TRIG pin is connected to GPIO17, and the ECHO\npin to GPIO18::\n\n    from gpiozero import DistanceSensor\n    from time import sleep\n\n    sensor = DistanceSensor(echo=18, trigger=17)\n    while True:\n        print('Distance: ', sensor.distance * 100)\n        sleep(1)\n\n:param int echo:\n    The GPIO pin which the ECHO pin is attached to. See\n    :ref:`pin_numbering` for valid pin numbers.\n\n:param int trigger:\n    The GPIO pin which the TRIG pin is attached to. See\n    :ref:`pin_numbering` for valid pin numbers.\n\n:param int queue_len:\n    The length of the queue used to store values read from the sensor.\n    This defaults to 30.\n\n:param float max_distance:\n    The :attr:`value` attribute reports a normalized value between 0 (too\n    close to measure) and 1 (maximum distance). This parameter specifies\n    the maximum distance expected in meters. This defaults to 1.\n\n:param float threshold_distance:\n    Defaults to 0.3. This is the distance (in meters) that will trigger the\n    ``in_range`` and ``out_of_range`` events when crossed.\n\n:param bool partial:\n    When ``False`` (the default), the object will not return a value for\n    :attr:`~SmoothedInputDevice.is_active` until the internal queue has\n    filled with values.  Only set this to ``True`` if you require values\n    immediately after object construction.\n\n.. _CamJam #3 EduKit: http://camjam.me/?page_id=1035"
    ),
    _(
        "gpiozero.Energenie(*args, **kwargs) \nExtends :class:`Device` to represent an `Energenie socket`_ controller.\n\nThis class is constructed with a socket number and an optional initial\nstate (defaults to ``False``, meaning off). Instances of this class can\nbe used to switch peripherals on and off. For example::\n\n    from gpiozero import Energenie\n\n    lamp = Energenie(1)\n    lamp.on()\n\n:param int socket:\n    Which socket this instance should control. This is an integer number\n    between 1 and 4.\n\n:param bool initial_value:\n    The initial state of the socket. As Energenie sockets provide no\n    means of reading their state, you must provide an initial state for\n    the socket, which will be set upon construction. This defaults to\n    ``False`` which will switch the socket off.\n\n.. _Energenie socket: https://energenie4u.co.uk/index.php/catalogue/product/ENER002-2PI"
    ),
    _(
        "gpiozero.EnergenieBadSocket() \nError raised when an invalid socket number is passed to :class:`Energenie`"
    ),
    _(
        "gpiozero.EnergenieSocketMissing() \nError raised when socket number is not specified"
    ),
    _(
        "gpiozero.EventsMixin(*args, **kwargs) \nAdds edge-detected :meth:`when_activated` and :meth:`when_deactivated`\nevents to a device based on changes to the :attr:`~Device.is_active`\nproperty common to all devices. Also adds :meth:`wait_for_active` and\n:meth:`wait_for_inactive` methods for level-waiting.\n\n.. note::\n\n    Note that this mixin provides no means of actually firing its events;\n    call :meth:`_fire_events` in sub-classes when device state changes to\n    trigger the events. This should also be called once at the end of\n    initialization to set initial states."
    ),
    _(
        "gpiozero.FishDish(*args, **kwargs) \nExtends :class:`TrafficLightsBuzzer` for the `Pi Supply FishDish`_: traffic\nlight LEDs, a button and a buzzer.\n\nThe FishDish pins are fixed and therefore there's no need to specify them\nwhen constructing this class. The following example waits for the button\nto be pressed on the FishDish, then turns on all the LEDs::\n\n    from gpiozero import FishDish\n\n    fish = FishDish()\n    fish.button.wait_for_press()\n    fish.lights.on()\n\n:param bool pwm:\n    If ``True``, construct :class:`PWMLED` instances to represent each\n    LED. If ``False`` (the default), construct regular :class:`LED`\n    instances.\n\n.. _Pi Supply FishDish: https://www.pi-supply.com/product/fish-dish-raspberry-pi-led-buzzer-board/"
    ),
    _(
        "gpiozero.GPIODevice(*args, **kwargs) \nExtends :class:`Device`. Represents a generic GPIO device and provides\nthe services common to all single-pin GPIO devices (like ensuring two\nGPIO devices do no share a :attr:`pin`).\n\n:param int pin:\n    The GPIO pin (in BCM numbering) that the device is connected to. If\n    this is ``None``, :exc:`GPIOPinMissing` will be raised. If the pin is\n    already in use by another device, :exc:`GPIOPinInUse` will be raised."
    ),
    _(
        "gpiozero.GPIODeviceClosed() \nDeprecated descendent of :exc:`DeviceClosed`"
    ),
    _(
        "gpiozero.GPIODeviceError() \nBase class for errors specific to the GPIODevice hierarchy"
    ),
    _(
        "gpiozero.GPIOPinInUse() \nError raised when attempting to use a pin already in use by another device"
    ),
    _(
        "gpiozero.GPIOPinMissing() \nError raised when a pin number is not specified"
    ),
    _("gpiozero.GPIOZeroError() \nBase class for all exceptions in GPIO Zero"),
    _("gpiozero.GPIOZeroWarning() \nBase class for all warnings in GPIO Zero"),
    _(
        "gpiozero.HoldMixin(*args, **kwargs) \nExtends :class:`EventsMixin` to add the :attr:`when_held` event and the\nmachinery to fire that event repeatedly (when :attr:`hold_repeat` is\n``True``) at internals defined by :attr:`hold_time`."
    ),
    _(
        "gpiozero.InputDevice(*args, **kwargs) \nRepresents a generic GPIO input device.\n\nThis class extends :class:`GPIODevice` to add facilities common to GPIO\ninput devices.  The constructor adds the optional *pull_up* parameter to\nspecify how the pin should be pulled by the internal resistors. The\n:attr:`~GPIODevice.is_active` property is adjusted accordingly so that\n``True`` still means active regardless of the :attr:`pull_up` setting.\n\n:param int pin:\n    The GPIO pin (in Broadcom numbering) that the device is connected to.\n    If this is ``None`` a :exc:`GPIODeviceError` will be raised.\n\n:param bool pull_up:\n    If ``True``, the pin will be pulled high with an internal resistor. If\n    ``False`` (the default), the pin will be pulled low."
    ),
    _(
        "gpiozero.InputDeviceError() \nBase class for errors specific to the InputDevice hierarchy"
    ),
    _(
        "gpiozero.InternalDevice(*args, **kwargs) \nExtends :class:`Device` to provide a basis for devices which have no\nspecific hardware representation. These are effectively pseudo-devices and\nusually represent operating system services like the internal clock, file\nsystems or network facilities."
    ),
    _(
        "gpiozero.LED(*args, **kwargs) \nExtends :class:`DigitalOutputDevice` and represents a light emitting diode\n(LED).\n\nConnect the cathode (short leg, flat side) of the LED to a ground pin;\nconnect the anode (longer leg) to a limiting resistor; connect the other\nside of the limiting resistor to a GPIO pin (the limiting resistor can be\nplaced either side of the LED).\n\nThe following example will light the LED::\n\n    from gpiozero import LED\n\n    led = LED(17)\n    led.on()\n\n:param int pin:\n    The GPIO pin which the LED is attached to. See :ref:`pin_numbering` for\n    valid pin numbers.\n\n:param bool active_high:\n    If ``True`` (the default), the LED will operate normally with the\n    circuit described above. If ``False`` you should wire the cathode to\n    the GPIO pin, and the anode to a 3V3 pin (via a limiting resistor).\n\n:param bool initial_value:\n    If ``False`` (the default), the LED will be off initially.  If\n    ``None``, the LED will be left in whatever state the pin is found in\n    when configured for output (warning: this can be on).  If ``True``, the\n    LED will be switched on initially."
    ),
    _(
        "gpiozero.LEDBarGraph(*args, **kwargs) \nExtends :class:`LEDCollection` to control a line of LEDs representing a\nbar graph. Positive values (0 to 1) light the LEDs from first to last.\nNegative values (-1 to 0) light the LEDs from last to first.\n\nThe following example demonstrates turning on the first two and last two\nLEDs in a board containing five LEDs attached to GPIOs 2 through 6::\n\n    from gpiozero import LEDBarGraph\n    from time import sleep\n\n    graph = LEDBarGraph(2, 3, 4, 5, 6)\n    graph.value = 2/5  # Light the first two LEDs only\n    sleep(1)\n    graph.value = -2/5 # Light the last two LEDs only\n    sleep(1)\n    graph.off()\n\nAs with other output devices, :attr:`source` and :attr:`values` are\nsupported::\n\n    from gpiozero import LEDBarGraph, MCP3008\n    from signal import pause\n\n    graph = LEDBarGraph(2, 3, 4, 5, 6, pwm=True)\n    pot = MCP3008(channel=0)\n    graph.source = pot.values\n    pause()\n\n:param int \\*pins:\n    Specify the GPIO pins that the LEDs of the bar graph are attached to.\n    You can designate as many pins as necessary.\n\n:param bool pwm:\n    If ``True``, construct :class:`PWMLED` instances for each pin. If\n    ``False`` (the default), construct regular :class:`LED` instances. This\n    parameter can only be specified as a keyword parameter.\n\n:param bool active_high:\n    If ``True`` (the default), the :meth:`on` method will set all the\n    associated pins to HIGH. If ``False``, the :meth:`on` method will set\n    all pins to LOW (the :meth:`off` method always does the opposite). This\n    parameter can only be specified as a keyword parameter.\n\n:param float initial_value:\n    The initial :attr:`value` of the graph given as a float between -1 and\n    +1.  Defaults to ``0.0``. This parameter can only be specified as a\n    keyword parameter."
    ),
    _(
        "gpiozero.LEDBoard(*args, **kwargs) \nExtends :class:`LEDCollection` and represents a generic LED board or\ncollection of LEDs.\n\nThe following example turns on all the LEDs on a board containing 5 LEDs\nattached to GPIO pins 2 through 6::\n\n    from gpiozero import LEDBoard\n\n    leds = LEDBoard(2, 3, 4, 5, 6)\n    leds.on()\n\n:param int \\*pins:\n    Specify the GPIO pins that the LEDs of the board are attached to. You\n    can designate as many pins as necessary. You can also specify\n    :class:`LEDBoard` instances to create trees of LEDs.\n\n:param bool pwm:\n    If ``True``, construct :class:`PWMLED` instances for each pin. If\n    ``False`` (the default), construct regular :class:`LED` instances. This\n    parameter can only be specified as a keyword parameter.\n\n:param bool active_high:\n    If ``True`` (the default), the :meth:`on` method will set all the\n    associated pins to HIGH. If ``False``, the :meth:`on` method will set\n    all pins to LOW (the :meth:`off` method always does the opposite). This\n    parameter can only be specified as a keyword parameter.\n\n:param bool initial_value:\n    If ``False`` (the default), all LEDs will be off initially. If\n    ``None``, each device will be left in whatever state the pin is found\n    in when configured for output (warning: this can be on). If ``True``,\n    the device will be switched on initially. This parameter can only be\n    specified as a keyword parameter.\n\n:param \\*\\*named_pins:\n    Specify GPIO pins that LEDs of the board are attached to, associating\n    each LED with a property name. You can designate as many pins as\n    necessary and use any names, provided they're not already in use by\n    something else. You can also specify :class:`LEDBoard` instances to\n    create trees of LEDs."
    ),
    _(
        "gpiozero.LEDCollection(*args, **kwargs) \nExtends :class:`CompositeOutputDevice`. Abstract base class for\n:class:`LEDBoard` and :class:`LEDBarGraph`."
    ),
    _(
        "gpiozero.LedBorg(*args, **kwargs) \nExtends :class:`RGBLED` for the `PiBorg LedBorg`_: an add-on board\ncontaining a very bright RGB LED.\n\nThe LedBorg pins are fixed and therefore there's no need to specify them\nwhen constructing this class. The following example turns the LedBorg\npurple::\n\n    from gpiozero import LedBorg\n\n    led = LedBorg()\n    led.color = (1, 0, 1)\n\n:param tuple initial_value:\n    The initial color for the LedBorg. Defaults to black ``(0, 0, 0)``.\n\n:param bool pwm:\n    If ``True`` (the default), construct :class:`PWMLED` instances for\n    each component of the LedBorg. If ``False``, construct regular\n    :class:`LED` instances, which prevents smooth color graduations.\n\n.. _PiBorg LedBorg: https://www.piborg.org/ledborg"
    ),
    _(
        'gpiozero.LightSensor(*args, **kwargs) \nExtends :class:`SmoothedInputDevice` and represents a light dependent\nresistor (LDR).\n\nConnect one leg of the LDR to the 3V3 pin; connect one leg of a 1µF\ncapacitor to a ground pin; connect the other leg of the LDR and the other\nleg of the capacitor to the same GPIO pin. This class repeatedly discharges\nthe capacitor, then times the duration it takes to charge (which will vary\naccording to the light falling on the LDR).\n\nThe following code will print a line of text when light is detected::\n\n    from gpiozero import LightSensor\n\n    ldr = LightSensor(18)\n    ldr.wait_for_light()\n    print("Light detected!")\n\n:param int pin:\n    The GPIO pin which the sensor is attached to. See :ref:`pin_numbering`\n    for valid pin numbers.\n\n:param int queue_len:\n    The length of the queue used to store values read from the circuit.\n    This defaults to 5.\n\n:param float charge_time_limit:\n    If the capacitor in the circuit takes longer than this length of time\n    to charge, it is assumed to be dark. The default (0.01 seconds) is\n    appropriate for a 1µF capacitor coupled with the LDR from the\n    `CamJam #2 EduKit`_. You may need to adjust this value for different\n    valued capacitors or LDRs.\n\n:param float threshold:\n    Defaults to 0.1. When the mean of all values in the internal queue\n    rises above this value, the area will be considered "light", and all\n    appropriate events will be fired.\n\n:param bool partial:\n    When ``False`` (the default), the object will not return a value for\n    :attr:`~SmoothedInputDevice.is_active` until the internal queue has\n    filled with values.  Only set this to ``True`` if you require values\n    immediately after object construction.\n\n.. _CamJam #2 EduKit: http://camjam.me/?page_id=623'
    ),
    _(
        "gpiozero.LineSensor(*args, **kwargs) \nExtends :class:`SmoothedInputDevice` and represents a single pin line sensor\nlike the TCRT5000 infra-red proximity sensor found in the `CamJam #3\nEduKit`_.\n\nA typical line sensor has a small circuit board with three pins: VCC, GND,\nand OUT. VCC should be connected to a 3V3 pin, GND to one of the ground\npins, and finally OUT to the GPIO specified as the value of the *pin*\nparameter in the constructor.\n\nThe following code will print a line of text indicating when the sensor\ndetects a line, or stops detecting a line::\n\n    from gpiozero import LineSensor\n    from signal import pause\n\n    sensor = LineSensor(4)\n    sensor.when_line = lambda: print('Line detected')\n    sensor.when_no_line = lambda: print('No line detected')\n    pause()\n\n:param int pin:\n    The GPIO pin which the sensor is attached to. See :ref:`pin_numbering`\n    for valid pin numbers.\n\n:param int queue_len:\n    The length of the queue used to store values read from the sensor. This\n    defaults to 5.\n\n:param float sample_rate:\n    The number of values to read from the device (and append to the\n    internal queue) per second. Defaults to 100.\n\n:param float threshold:\n    Defaults to 0.5. When the mean of all values in the internal queue\n    rises above this value, the sensor will be considered \"active\" by the\n    :attr:`~SmoothedInputDevice.is_active` property, and all appropriate\n    events will be fired.\n\n:param bool partial:\n    When ``False`` (the default), the object will not return a value for\n    :attr:`~SmoothedInputDevice.is_active` until the internal queue has\n    filled with values.  Only set this to ``True`` if you require values\n    immediately after object construction.\n\n.. _CamJam #3 EduKit: http://camjam.me/?page_id=1035"
    ),
    _(
        "gpiozero.LocalPin() \nAbstract base class representing pins attached locally to a Pi. This forms\nthe base class for local-only pin interfaces (:class:`RPiGPIOPin`,\n:class:`RPIOPin`, and :class:`NativePin`)."
    ),
    _(
        "gpiozero.MCP3001(*args, **kwargs) \nThe `MCP3001`_ is a 10-bit analog to digital converter with 1 channel\n\n.. _MCP3001: http://www.farnell.com/datasheets/630400.pdf"
    ),
    _(
        "gpiozero.MCP3002(*args, **kwargs) \nThe `MCP3002`_ is a 10-bit analog to digital converter with 2 channels\n(0-1).\n\n.. _MCP3002: http://www.farnell.com/datasheets/1599363.pdf"
    ),
    _(
        "gpiozero.MCP3004(*args, **kwargs) \nThe `MCP3004`_ is a 10-bit analog to digital converter with 4 channels\n(0-3).\n\n.. _MCP3004: http://www.farnell.com/datasheets/808965.pdf"
    ),
    _(
        "gpiozero.MCP3008(*args, **kwargs) \nThe `MCP3008`_ is a 10-bit analog to digital converter with 8 channels\n(0-7).\n\n.. _MCP3008: http://www.farnell.com/datasheets/808965.pdf"
    ),
    _(
        "gpiozero.MCP3201(*args, **kwargs) \nThe `MCP3201`_ is a 12-bit analog to digital converter with 1 channel\n\n.. _MCP3201: http://www.farnell.com/datasheets/1669366.pdf"
    ),
    _(
        "gpiozero.MCP3202(*args, **kwargs) \nThe `MCP3202`_ is a 12-bit analog to digital converter with 2 channels\n(0-1).\n\n.. _MCP3202: http://www.farnell.com/datasheets/1669376.pdf"
    ),
    _(
        "gpiozero.MCP3204(*args, **kwargs) \nThe `MCP3204`_ is a 12-bit analog to digital converter with 4 channels\n(0-3).\n\n.. _MCP3204: http://www.farnell.com/datasheets/808967.pdf"
    ),
    _(
        "gpiozero.MCP3208(*args, **kwargs) \nThe `MCP3208`_ is a 12-bit analog to digital converter with 8 channels\n(0-7).\n\n.. _MCP3208: http://www.farnell.com/datasheets/808967.pdf"
    ),
    _(
        "gpiozero.MCP3301(*args, **kwargs) \nThe `MCP3301`_ is a signed 13-bit analog to digital converter.  Please note\nthat the MCP3301 always operates in differential mode between its two\nchannels and the output value is scaled from -1 to +1.\n\n.. _MCP3301: http://www.farnell.com/datasheets/1669397.pdf"
    ),
    _(
        "gpiozero.MCP3302(*args, **kwargs) \nThe `MCP3302`_ is a 12/13-bit analog to digital converter with 4 channels\n(0-3). When operated in differential mode, the device outputs a signed\n13-bit value which is scaled from -1 to +1. When operated in single-ended\nmode (the default), the device outputs an unsigned 12-bit value scaled from\n0 to 1.\n\n.. _MCP3302: http://www.farnell.com/datasheets/1486116.pdf"
    ),
    _(
        "gpiozero.MCP3304(*args, **kwargs) \nThe `MCP3304`_ is a 12/13-bit analog to digital converter with 8 channels\n(0-7). When operated in differential mode, the device outputs a signed\n13-bit value which is scaled from -1 to +1. When operated in single-ended\nmode (the default), the device outputs an unsigned 12-bit value scaled from\n0 to 1.\n\n.. _MCP3304: http://www.farnell.com/datasheets/1486116.pdf"
    ),
    _(
        'gpiozero.MotionSensor(*args, **kwargs) \nExtends :class:`SmoothedInputDevice` and represents a passive infra-red\n(PIR) motion sensor like the sort found in the `CamJam #2 EduKit`_.\n\n.. _CamJam #2 EduKit: http://camjam.me/?page_id=623\n\nA typical PIR device has a small circuit board with three pins: VCC, OUT,\nand GND. VCC should be connected to a 5V pin, GND to one of the ground\npins, and finally OUT to the GPIO specified as the value of the *pin*\nparameter in the constructor.\n\nThe following code will print a line of text when motion is detected::\n\n    from gpiozero import MotionSensor\n\n    pir = MotionSensor(4)\n    pir.wait_for_motion()\n    print("Motion detected!")\n\n:param int pin:\n    The GPIO pin which the sensor is attached to. See :ref:`pin_numbering`\n    for valid pin numbers.\n\n:param int queue_len:\n    The length of the queue used to store values read from the sensor. This\n    defaults to 1 which effectively disables the queue. If your motion\n    sensor is particularly "twitchy" you may wish to increase this value.\n\n:param float sample_rate:\n    The number of values to read from the device (and append to the\n    internal queue) per second. Defaults to 100.\n\n:param float threshold:\n    Defaults to 0.5. When the mean of all values in the internal queue\n    rises above this value, the sensor will be considered "active" by the\n    :attr:`~SmoothedInputDevice.is_active` property, and all appropriate\n    events will be fired.\n\n:param bool partial:\n    When ``False`` (the default), the object will not return a value for\n    :attr:`~SmoothedInputDevice.is_active` until the internal queue has\n    filled with values.  Only set this to ``True`` if you require values\n    immediately after object construction.'
    ),
    _(
        'gpiozero.Motor(*args, **kwargs) \nExtends :class:`CompositeDevice` and represents a generic motor\nconnected to a bi-directional motor driver circuit (i.e.  an `H-bridge`_).\n\nAttach an `H-bridge`_ motor controller to your Pi; connect a power source\n(e.g. a battery pack or the 5V pin) to the controller; connect the outputs\nof the controller board to the two terminals of the motor; connect the\ninputs of the controller board to two GPIO pins.\n\n.. _H-bridge: https://en.wikipedia.org/wiki/H_bridge\n\nThe following code will make the motor turn "forwards"::\n\n    from gpiozero import Motor\n\n    motor = Motor(17, 18)\n    motor.forward()\n\n:param int forward:\n    The GPIO pin that the forward input of the motor driver chip is\n    connected to.\n\n:param int backward:\n    The GPIO pin that the backward input of the motor driver chip is\n    connected to.\n\n:param bool pwm:\n    If ``True`` (the default), construct :class:`PWMOutputDevice`\n    instances for the motor controller pins, allowing both direction and\n    variable speed control. If ``False``, construct\n    :class:`DigitalOutputDevice` instances, allowing only direction\n    control.'
    ),
    _(
        "gpiozero.OutputDevice(*args, **kwargs) \nRepresents a generic GPIO output device.\n\nThis class extends :class:`GPIODevice` to add facilities common to GPIO\noutput devices: an :meth:`on` method to switch the device on, a\ncorresponding :meth:`off` method, and a :meth:`toggle` method.\n\n:param int pin:\n    The GPIO pin (in BCM numbering) that the device is connected to. If\n    this is ``None`` a :exc:`GPIOPinMissing` will be raised.\n\n:param bool active_high:\n    If ``True`` (the default), the :meth:`on` method will set the GPIO to\n    HIGH. If ``False``, the :meth:`on` method will set the GPIO to LOW (the\n    :meth:`off` method always does the opposite).\n\n:param bool initial_value:\n    If ``False`` (the default), the device will be off initially.  If\n    ``None``, the device will be left in whatever state the pin is found in\n    when configured for output (warning: this can be on).  If ``True``, the\n    device will be switched on initially."
    ),
    _(
        "gpiozero.OutputDeviceBadValue() \nError raised when ``value`` is set to an invalid value"
    ),
    _(
        "gpiozero.OutputDeviceError() \nBase class for errors specified to the OutputDevice hierarchy"
    ),
    _(
        "gpiozero.PWMLED(*args, **kwargs) \nExtends :class:`PWMOutputDevice` and represents a light emitting diode\n(LED) with variable brightness.\n\nA typical configuration of such a device is to connect a GPIO pin to the\nanode (long leg) of the LED, and the cathode (short leg) to ground, with\nan optional resistor to prevent the LED from burning out.\n\n:param int pin:\n    The GPIO pin which the LED is attached to. See :ref:`pin_numbering` for\n    valid pin numbers.\n\n:param bool active_high:\n    If ``True`` (the default), the :meth:`on` method will set the GPIO to\n    HIGH. If ``False``, the :meth:`on` method will set the GPIO to LOW (the\n    :meth:`off` method always does the opposite).\n\n:param float initial_value:\n    If ``0`` (the default), the LED will be off initially. Other values\n    between 0 and 1 can be specified as an initial brightness for the LED.\n    Note that ``None`` cannot be specified (unlike the parent class) as\n    there is no way to tell PWM not to alter the state of the pin.\n\n:param int frequency:\n    The frequency (in Hz) of pulses emitted to drive the LED. Defaults\n    to 100Hz."
    ),
    _(
        "gpiozero.PWMOutputDevice(*args, **kwargs) \nGeneric output device configured for pulse-width modulation (PWM).\n\n:param int pin:\n    The GPIO pin which the device is attached to. See :ref:`pin_numbering`\n    for valid pin numbers.\n\n:param bool active_high:\n    If ``True`` (the default), the :meth:`on` method will set the GPIO to\n    HIGH. If ``False``, the :meth:`on` method will set the GPIO to LOW (the\n    :meth:`off` method always does the opposite).\n\n:param float initial_value:\n    If ``0`` (the default), the device's duty cycle will be 0 initially.\n    Other values between 0 and 1 can be specified as an initial duty cycle.\n    Note that ``None`` cannot be specified (unlike the parent class) as\n    there is no way to tell PWM not to alter the state of the pin.\n\n:param int frequency:\n    The frequency (in Hz) of pulses emitted to drive the device. Defaults\n    to 100Hz."
    ),
    _(
        'gpiozero.PiBoardInfo(revision, model, pcb_revision, released, soc, manufacturer, memory, storage, usb, ethernet, wifi, bluetooth, csi, dsi, headers) \nThis class is a :func:`~collections.namedtuple` derivative used to\nrepresent information about a particular model of Raspberry Pi. While it is\na tuple, it is strongly recommended that you use the following named\nattributes to access the data contained within.\n\n.. automethod:: physical_pin\n\n.. automethod:: physical_pins\n\n.. automethod:: pulled_up\n\n.. attribute:: revision\n\n    A string indicating the revision of the Pi. This is unique to each\n    revision and can be considered the "key" from which all other\n    attributes are derived. However, in itself the string is fairly\n    meaningless.\n\n.. attribute:: model\n\n    A string containing the model of the Pi (for example, "B", "B+", "A+",\n    "2B", "CM" (for the Compute Module), or "Zero").\n\n.. attribute:: pcb_revision\n\n    A string containing the PCB revision number which is silk-screened onto\n    the Pi (on some models).\n\n    .. note::\n\n        This is primarily useful to distinguish between the model B\n        revision 1.0 and 2.0 (not to be confused with the model 2B) which\n        had slightly different pinouts on their 26-pin GPIO headers.\n\n.. attribute:: released\n\n    A string containing an approximate release date for this revision of\n    the Pi (formatted as yyyyQq, e.g. 2012Q1 means the first quarter of\n    2012).\n\n.. attribute:: soc\n\n    A string indicating the SoC (`system on a chip`_) that this revision\n    of the Pi is based upon.\n\n.. attribute:: manufacturer\n\n    A string indicating the name of the manufacturer (usually "Sony" but a\n    few others exist).\n\n.. attribute:: memory\n\n    An integer indicating the amount of memory (in Mb) connected to the\n    SoC.\n\n    .. note::\n\n        This can differ substantially from the amount of RAM available\n        to the operating system as the GPU\'s memory is shared with the\n        CPU. When the camera module is activated, at least 128Mb of RAM\n        is typically reserved for the GPU.\n\n.. attribute:: storage\n\n    A string indicating the type of bootable storage used with this\n    revision of Pi, e.g. "SD", "MicroSD", or "eMMC" (for the Compute\n    Module).\n\n.. attribute:: usb\n\n    An integer indicating how many USB ports are physically present on\n    this revision of the Pi.\n\n    .. note::\n\n        This does *not* include the micro-USB port used to power the Pi.\n\n.. attribute:: ethernet\n\n    An integer indicating how many Ethernet ports are physically present\n    on this revision of the Pi.\n\n.. attribute:: wifi\n\n    A bool indicating whether this revision of the Pi has wifi built-in.\n\n.. attribute:: bluetooth\n\n    A bool indicating whether this revision of the Pi has bluetooth\n    built-in.\n\n.. attribute:: csi\n\n    An integer indicating the number of CSI (camera) ports available on\n    this revision of the Pi.\n\n.. attribute:: dsi\n\n    An integer indicating the number of DSI (display) ports available on\n    this revision of the Pi.\n\n.. attribute:: headers\n\n    A dictionary which maps header labels to dictionaries which map\n    physical pin numbers to :class:`PinInfo` tuples. For example, to obtain\n    information about pin 12 on header P1 you would query\n    ``headers[\'P1\'][12]``.\n\n.. _system on a chip: https://en.wikipedia.org/wiki/System_on_a_chip'
    ),
    _(
        "gpiozero.PiLiter(*args, **kwargs) \nExtends :class:`LEDBoard` for the `Ciseco Pi-LITEr`_: a strip of 8 very bright\nLEDs.\n\nThe Pi-LITEr pins are fixed and therefore there's no need to specify them\nwhen constructing this class. The following example turns on all the LEDs\nof the Pi-LITEr::\n\n    from gpiozero import PiLiter\n\n    lite = PiLiter()\n    lite.on()\n\n:param bool pwm:\n    If ``True``, construct :class:`PWMLED` instances for each pin. If\n    ``False`` (the default), construct regular :class:`LED` instances.\n\n:param bool initial_value:\n    If ``False`` (the default), all LEDs will be off initially. If\n    ``None``, each device will be left in whatever state the pin is found\n    in when configured for output (warning: this can be on). If ``True``,\n    the device will be switched on initially.\n\n.. _Ciseco Pi-LITEr: http://shop.ciseco.co.uk/pi-liter-8-led-strip-for-the-raspberry-pi/"
    ),
    _(
        "gpiozero.PiLiterBarGraph(*args, **kwargs) \nExtends :class:`LEDBarGraph` to treat the `Ciseco Pi-LITEr`_ as an\n8-segment bar graph.\n\nThe Pi-LITEr pins are fixed and therefore there's no need to specify them\nwhen constructing this class. The following example sets the graph value\nto 0.5::\n\n    from gpiozero import PiLiterBarGraph\n\n    graph = PiLiterBarGraph()\n    graph.value = 0.5\n\n:param bool pwm:\n    If ``True``, construct :class:`PWMLED` instances for each pin. If\n    ``False`` (the default), construct regular :class:`LED` instances.\n\n:param float initial_value:\n    The initial :attr:`value` of the graph given as a float between -1 and\n    +1. Defaults to ``0.0``.\n\n.. _Ciseco Pi-LITEr: http://shop.ciseco.co.uk/pi-liter-8-led-strip-for-the-raspberry-pi/"
    ),
    _(
        "gpiozero.PiTraffic(*args, **kwargs) \nExtends :class:`TrafficLights` for the `Low Voltage Labs PI-TRAFFIC`_:\nvertical traffic lights board when attached to GPIO pins 9, 10, and 11.\n\nThere's no need to specify the pins if the PI-TRAFFIC is connected to the\ndefault pins (9, 10, 11). The following example turns on the amber LED on\nthe PI-TRAFFIC::\n\n    from gpiozero import PiTraffic\n\n    traffic = PiTraffic()\n    traffic.amber.on()\n\nTo use the PI-TRAFFIC board when attached to a non-standard set of pins,\nsimply use the parent class, :class:`TrafficLights`.\n\n:param bool pwm:\n    If ``True``, construct :class:`PWMLED` instances to represent each\n    LED. If ``False`` (the default), construct regular :class:`LED`\n    instances.\n\n:param bool initial_value:\n    If ``False`` (the default), all LEDs will be off initially. If\n    ``None``, each device will be left in whatever state the pin is found\n    in when configured for output (warning: this can be on). If ``True``,\n    the device will be switched on initially.\n\n.. _Low Voltage Labs PI-TRAFFIC: http://lowvoltagelabs.com/products/pi-traffic/"
    ),
    _(
        "gpiozero.Pin() \nAbstract base class representing a GPIO pin or a pin from an IO extender.\n\nDescendents should override property getters and setters to accurately\nrepresent the capabilities of pins. The following functions *must* be\noverridden:\n\n* :meth:`_get_function`\n* :meth:`_set_function`\n* :meth:`_get_state`\n\nThe following functions *may* be overridden if applicable:\n\n* :meth:`close`\n* :meth:`_set_state`\n* :meth:`_get_frequency`\n* :meth:`_set_frequency`\n* :meth:`_get_pull`\n* :meth:`_set_pull`\n* :meth:`_get_bounce`\n* :meth:`_set_bounce`\n* :meth:`_get_edges`\n* :meth:`_set_edges`\n* :meth:`_get_when_changed`\n* :meth:`_set_when_changed`\n* :meth:`pi_info`\n* :meth:`output_with_state`\n* :meth:`input_with_pull`\n\n.. warning::\n\n    Descendents must ensure that pin instances representing the same\n    physical hardware are identical, right down to object identity. The\n    framework relies on this to correctly clean up resources at interpreter\n    shutdown."
    ),
    _(
        "gpiozero.PinEdgeDetectUnsupported() \nError raised when attempting to use edge detection on unsupported pins"
    ),
    _(
        "gpiozero.PinError() \nBase class for errors related to pin implementations"
    ),
    _(
        "gpiozero.PinFixedPull() \nError raised when attempting to set the pull of a pin with fixed pull-up"
    ),
    _(
        'gpiozero.PinInfo(number, function, pull_up) \nThis class is a :func:`~collections.namedtuple` derivative used to\nrepresent information about a pin present on a GPIO header. The following\nattributes are defined:\n\n.. attribute:: number\n\n    An integer containing the physical pin number on the header (starting\n    from 1 in accordance with convention).\n\n.. attribute:: function\n\n    A string describing the function of the pin. Some common examples\n    include "GND" (for pins connecting to ground), "3V3" (for pins which\n    output 3.3 volts), "GPIO9" (for GPIO9 in the Broadcom numbering\n    scheme), etc.\n\n.. attribute:: pull_up\n\n    A bool indicating whether the pin has a physical pull-up resistor\n    permanently attached (this is usually ``False`` but GPIO2 and GPIO3\n    are *usually* ``True``). This is used internally by gpiozero to raise\n    errors when pull-down is requested on a pin with a physical pull-up\n    resistor.'
    ),
    _(
        "gpiozero.PinInvalidEdges() \nError raised when attempting to assign an invalid edge detection to a pin"
    ),
    _(
        "gpiozero.PinInvalidFunction() \nError raised when attempting to change the function of a pin to an invalid value"
    ),
    _(
        "gpiozero.PinInvalidPull() \nError raised when attempting to assign an invalid pull-up to a pin"
    ),
    _(
        "gpiozero.PinInvalidState() \nError raised when attempting to assign an invalid state to a pin"
    ),
    _(
        "gpiozero.PinMultiplePins() \nError raised when multiple pins support the requested function"
    ),
    _(
        "gpiozero.PinNoPins() \nError raised when no pins support the requested function"
    ),
    _(
        "gpiozero.PinNonPhysical() \nWarning raised when a non-physical pin is specified in a constructor"
    ),
    _(
        "gpiozero.PinPWMError() \nBase class for errors related to PWM implementations"
    ),
    _(
        "gpiozero.PinPWMFixedValue() \nError raised when attempting to initialize PWM on an input pin"
    ),
    _(
        "gpiozero.PinPWMUnsupported() \nError raised when attempting to activate PWM on unsupported pins"
    ),
    _(
        "gpiozero.PinSetInput() \nError raised when attempting to set a read-only pin"
    ),
    _(
        "gpiozero.PinUnknownPi() \nError raised when gpiozero doesn't recognize a revision of the Pi"
    ),
    _(
        "gpiozero.PinWarning() \nBase class for warnings related to pin implementations"
    ),
    _(
        "gpiozero.PingServer(*args, **kwargs) \nExtends :class:`InternalDevice` to provide a device which is active when a\n*host* on the network can be pinged.\n\nThe following example lights an LED while a server is reachable (note the\nuse of :attr:`~SourceMixin.source_delay` to ensure the server is not\nflooded with pings)::\n\n    from gpiozero import PingServer, LED\n    from signal import pause\n\n    server = PingServer('my-server')\n    led = LED(4)\n    led.source_delay = 1\n    led.source = server.values\n    pause()\n\n:param str host:\n    The hostname or IP address to attempt to ping."
    ),
    _(
        "gpiozero.RGBLED(*args, **kwargs) \nExtends :class:`Device` and represents a full color LED component (composed\nof red, green, and blue LEDs).\n\nConnect the common cathode (longest leg) to a ground pin; connect each of\nthe other legs (representing the red, green, and blue anodes) to any GPIO\npins.  You can either use three limiting resistors (one per anode) or a\nsingle limiting resistor on the cathode.\n\nThe following code will make the LED purple::\n\n    from gpiozero import RGBLED\n\n    led = RGBLED(2, 3, 4)\n    led.color = (1, 0, 1)\n\n:param int red:\n    The GPIO pin that controls the red component of the RGB LED.\n\n:param int green:\n    The GPIO pin that controls the green component of the RGB LED.\n\n:param int blue:\n    The GPIO pin that controls the blue component of the RGB LED.\n\n:param bool active_high:\n    Set to ``True`` (the default) for common cathode RGB LEDs. If you are\n    using a common anode RGB LED, set this to ``False``.\n\n:param tuple initial_value:\n    The initial color for the RGB LED. Defaults to black ``(0, 0, 0)``.\n\n:param bool pwm:\n    If ``True`` (the default), construct :class:`PWMLED` instances for\n    each component of the RGBLED. If ``False``, construct regular\n    :class:`LED` instances, which prevents smooth color graduations."
    ),
    _(
        "gpiozero.Robot(*args, **kwargs) \nExtends :class:`CompositeDevice` to represent a generic dual-motor robot.\n\nThis class is constructed with two tuples representing the forward and\nbackward pins of the left and right controllers respectively. For example,\nif the left motor's controller is connected to GPIOs 4 and 14, while the\nright motor's controller is connected to GPIOs 17 and 18 then the following\nexample will drive the robot forward::\n\n    from gpiozero import Robot\n\n    robot = Robot(left=(4, 14), right=(17, 18))\n    robot.forward()\n\n:param tuple left:\n    A tuple of two GPIO pins representing the forward and backward inputs\n    of the left motor's controller.\n\n:param tuple right:\n    A tuple of two GPIO pins representing the forward and backward inputs\n    of the right motor's controller."
    ),
    _(
        "gpiozero.RyanteckRobot(*args, **kwargs) \nExtends :class:`Robot` for the `Ryanteck MCB`_ robot.\n\nThe Ryanteck MCB pins are fixed and therefore there's no need to specify\nthem when constructing this class. The following example drives the robot\nforward::\n\n    from gpiozero import RyanteckRobot\n\n    robot = RyanteckRobot()\n    robot.forward()\n\n.. _Ryanteck MCB: https://ryanteck.uk/add-ons/6-ryanteck-rpi-motor-controller-board-0635648607160.html"
    ),
    _(
        "gpiozero.SPIBadArgs() \nError raised when invalid arguments are given while constructing :class:`SPIDevice`"
    ),
    _(
        "gpiozero.SPIDevice(*args, **kwargs) \nExtends :class:`Device`. Represents a device that communicates via the SPI\nprotocol.\n\nSee :ref:`spi_args` for information on the keyword arguments that can be\nspecified with the constructor."
    ),
    _(
        "gpiozero.SPIError() \nBase class for errors related to the SPI implementation"
    ),
    _(
        "gpiozero.SPISoftwareFallback() \nWarning raised when falling back to the software implementation"
    ),
    _(
        "gpiozero.SPIWarning() \nBase class for warnings related to the SPI implementation"
    ),
    _(
        "gpiozero.Servo(*args, **kwargs) \nExtends :class:`CompositeDevice` and represents a PWM-controlled servo\nmotor connected to a GPIO pin.\n\nConnect a power source (e.g. a battery pack or the 5V pin) to the power\ncable of the servo (this is typically colored red); connect the ground\ncable of the servo (typically colored black or brown) to the negative of\nyour battery pack, or a GND pin; connect the final cable (typically colored\nwhite or orange) to the GPIO pin you wish to use for controlling the servo.\n\nThe following code will make the servo move between its minimum, maximum,\nand mid-point positions with a pause between each::\n\n    from gpiozero import Servo\n    from time import sleep\n\n    servo = Servo(17)\n    while True:\n        servo.min()\n        sleep(1)\n        servo.mid()\n        sleep(1)\n        servo.max()\n        sleep(1)\n\n:param int pin:\n    The GPIO pin which the device is attached to. See :ref:`pin_numbering`\n    for valid pin numbers.\n\n:param float initial_value:\n    If ``0`` (the default), the device's mid-point will be set\n    initially.  Other values between -1 and +1 can be specified as an\n    initial position. ``None`` means to start the servo un-controlled (see\n    :attr:`value`).\n\n:param float min_pulse_width:\n    The pulse width corresponding to the servo's minimum position. This\n    defaults to 1ms.\n\n:param float max_pulse_width:\n    The pulse width corresponding to the servo's maximum position. This\n    defaults to 2ms.\n\n:param float frame_width:\n    The length of time between servo control pulses measured in seconds.\n    This defaults to 20ms which is a common value for servos."
    ),
    _(
        'gpiozero.SharedMixin() \nThis mixin marks a class as "shared". In this case, the meta-class\n(GPIOMeta) will use :meth:`_shared_key` to convert the constructor\narguments to an immutable key, and will check whether any existing\ninstances match that key. If they do, they will be returned by the\nconstructor instead of a new instance. An internal reference counter is\nused to determine how many times an instance has been "constructed" in this\nway.\n\nWhen :meth:`close` is called, an internal reference counter will be\ndecremented and the instance will only close when it reaches zero.'
    ),
    _(
        'gpiozero.SmoothedInputDevice(*args, **kwargs) \nRepresents a generic input device which takes its value from the mean of a\nqueue of historical values.\n\nThis class extends :class:`InputDevice` with a queue which is filled by a\nbackground thread which continually polls the state of the underlying\ndevice. The mean of the values in the queue is compared to a threshold\nwhich is used to determine the state of the :attr:`is_active` property.\n\n.. note::\n\n    The background queue is not automatically started upon construction.\n    This is to allow descendents to set up additional components before the\n    queue starts reading values. Effectively this is an abstract base\n    class.\n\nThis class is intended for use with devices which either exhibit analog\nbehaviour (such as the charging time of a capacitor with an LDR), or those\nwhich exhibit "twitchy" behaviour (such as certain motion sensors).\n\n:param float threshold:\n    The value above which the device will be considered "on".\n\n:param int queue_len:\n    The length of the internal queue which is filled by the background\n    thread.\n\n:param float sample_wait:\n    The length of time to wait between retrieving the state of the\n    underlying device. Defaults to 0.0 indicating that values are retrieved\n    as fast as possible.\n\n:param bool partial:\n    If ``False`` (the default), attempts to read the state of the device\n    (from the :attr:`is_active` property) will block until the queue has\n    filled.  If ``True``, a value will be returned immediately, but be\n    aware that this value is likely to fluctuate excessively.'
    ),
    _(
        "gpiozero.SnowPi(*args, **kwargs) \nExtends :class:`LEDBoard` for the `Ryanteck SnowPi`_ board.\n\nThe SnowPi pins are fixed and therefore there's no need to specify them\nwhen constructing this class. The following example turns on the eyes, sets\nthe nose pulsing, and the arms blinking::\n\n    from gpiozero import SnowPi\n\n    snowman = SnowPi(pwm=True)\n    snowman.eyes.on()\n    snowman.nose.pulse()\n    snowman.arms.blink()\n\n:param bool pwm:\n    If ``True``, construct :class:`PWMLED` instances to represent each\n    LED. If ``False`` (the default), construct regular :class:`LED`\n    instances.\n\n:param bool initial_value:\n    If ``False`` (the default), all LEDs will be off initially. If\n    ``None``, each device will be left in whatever state the pin is found\n    in when configured for output (warning: this can be on). If ``True``,\n    the device will be switched on initially.\n\n.. _Ryanteck SnowPi: https://ryanteck.uk/raspberry-pi/114-snowpi-the-gpio-snowman-for-raspberry-pi-0635648608303.html"
    ),
    _(
        "gpiozero.SourceMixin(*args, **kwargs) \nAdds a :attr:`source` property to the class which, given an iterable, sets\n:attr:`value` to each member of that iterable until it is exhausted.  This\nmixin is generally included in novel output devices to allow their state to\nbe driven from another device.\n\n.. note::\n\n    Use this mixin *first* in the parent class list."
    ),
    _(
        "gpiozero.TimeOfDay(*args, **kwargs) \nExtends :class:`InternalDevice` to provide a device which is active when\nthe computer's clock indicates that the current time is between\n*start_time* and *end_time* (inclusive) which are :class:`~datetime.time`\ninstances.\n\nThe following example turns on a lamp attached to an :class:`Energenie`\nplug between 7 and 8 AM::\n\n    from datetime import time\n    from gpiozero import TimeOfDay, Energenie\n    from signal import pause\n\n    lamp = Energenie(0)\n    morning = TimeOfDay(time(7), time(8))\n    morning.when_activated = lamp.on\n    morning.when_deactivated = lamp.off\n    pause()\n\n:param ~datetime.time start_time:\n    The time from which the device will be considered active.\n\n:param ~datetime.time end_time:\n    The time after which the device will be considered inactive.\n\n:param bool utc:\n    If ``True`` (the default), a naive UTC time will be used for the\n    comparison rather than a local time-zone reading."
    ),
    _(
        "gpiozero.TrafficHat(*args, **kwargs) \nExtends :class:`TrafficLightsBuzzer` for the `Ryanteck Traffic HAT`_: traffic\nlight LEDs, a button and a buzzer.\n\nThe Traffic HAT pins are fixed and therefore there's no need to specify\nthem when constructing this class. The following example waits for the\nbutton to be pressed on the Traffic HAT, then turns on all the LEDs::\n\n    from gpiozero import TrafficHat\n\n    hat = TrafficHat()\n    hat.button.wait_for_press()\n    hat.lights.on()\n\n:param bool pwm:\n    If ``True``, construct :class:`PWMLED` instances to represent each\n    LED. If ``False`` (the default), construct regular :class:`LED`\n    instances.\n\n.. _Ryanteck Traffic HAT: https://ryanteck.uk/hats/1-traffichat-0635648607122.html"
    ),
    _(
        "gpiozero.TrafficLights(*args, **kwargs) \nExtends :class:`LEDBoard` for devices containing red, yellow, and green\nLEDs.\n\nThe following example initializes a device connected to GPIO pins 2, 3,\nand 4, then lights the amber (yellow) LED attached to GPIO 3::\n\n    from gpiozero import TrafficLights\n\n    traffic = TrafficLights(2, 3, 4)\n    traffic.amber.on()\n\n:param int red:\n    The GPIO pin that the red LED is attached to.\n\n:param int amber:\n    The GPIO pin that the amber LED is attached to.\n\n:param int green:\n    The GPIO pin that the green LED is attached to.\n\n:param bool pwm:\n    If ``True``, construct :class:`PWMLED` instances to represent each\n    LED. If ``False`` (the default), construct regular :class:`LED`\n    instances.\n\n:param bool initial_value:\n    If ``False`` (the default), all LEDs will be off initially. If\n    ``None``, each device will be left in whatever state the pin is found\n    in when configured for output (warning: this can be on). If ``True``,\n    the device will be switched on initially.\n\n:param int yellow:\n    The GPIO pin that the yellow LED is attached to. This is merely an\n    alias for the ``amber`` parameter - you can't specify both ``amber``\n    and ``yellow``."
    ),
    _(
        "gpiozero.TrafficLightsBuzzer(*args, **kwargs) \nExtends :class:`CompositeOutputDevice` and is a generic class for HATs with\ntraffic lights, a button and a buzzer.\n\n:param TrafficLights lights:\n    An instance of :class:`TrafficLights` representing the traffic lights\n    of the HAT.\n\n:param Buzzer buzzer:\n    An instance of :class:`Buzzer` representing the buzzer on the HAT.\n\n:param Button button:\n    An instance of :class:`Button` representing the button on the HAT."
    ),
    _(
        "gpiozero.ValuesMixin() \nAdds a :attr:`values` property to the class which returns an infinite\ngenerator of readings from the :attr:`value` property. There is rarely a\nneed to use this mixin directly as all base classes in GPIO Zero include\nit.\n\n.. note::\n\n    Use this mixin *first* in the parent class list."
    ),
    _(
        "gpiozero.pi_info(revision=None) \nReturns a :class:`PiBoardInfo` instance containing information about a\n*revision* of the Raspberry Pi.\n\n:param str revision:\n    The revision of the Pi to return information about. If this is omitted\n    or ``None`` (the default), then the library will attempt to determine\n    the model of Pi it is running on and return information about that."
    ),
    _(
        'picamera.Blue() \nRepresents the blue component of a :class:`Color` for use in\ntransformations.  Instances of this class can be constructed directly with\na float value, or by querying the :attr:`Color.blue` attribute. Addition,\nsubtraction, and multiplication are supported with :class:`Color`\ninstances. For example::\n\n    >>> Color(0, 0, 0) + Blue(0.2)\n    <Color "#000033">\n    >>> Color.from_hls(0.5, 0.5, 1.0) - Blue(1)\n    <Color "#00fe00">\n    >>> Blue(0.9) * Color(\'white\')\n    <Color "#ffffe5">'
    ),
    _(
        "picamera.BufferIO(obj) \nA stream which uses a :class:`memoryview` for storage.\n\nThis is used internally by picamera for capturing directly to an existing\nobject which supports the buffer protocol (like a numpy array). Because the\nunderlying storage is fixed in size, the stream also has a fixed size and\nwill raise an :exc:`IOError` exception if an attempt is made to write\nbeyond the end of the buffer (though seek beyond the end is supported).\n\nUsers should never need this class directly."
    ),
    _(
        "picamera.CircularIO(size) \nA thread-safe stream which uses a ring buffer for storage.\n\nCircularIO provides an in-memory stream similar to the :class:`io.BytesIO`\nclass. However, unlike :class:`io.BytesIO` its underlying storage is a\n`ring buffer`_ with a fixed maximum size. Once the maximum size is reached,\nwriting effectively loops round to the beginning to the ring and starts\noverwriting the oldest content.\n\nThe *size* parameter specifies the maximum size of the stream in bytes. The\n:meth:`read`, :meth:`tell`, and :meth:`seek` methods all operate\nequivalently to those in :class:`io.BytesIO` whilst :meth:`write` only\ndiffers in the wrapping behaviour described above. A :meth:`read1` method\nis also provided for efficient reading of the underlying ring buffer in\nwrite-sized chunks (or less).\n\nA re-entrant threading lock guards all operations, and is accessible for\nexternal use via the :attr:`lock` attribute.\n\nThe performance of the class is geared toward faster writing than reading\non the assumption that writing will be the common operation and reading the\nrare operation (a reasonable assumption for the camera use-case, but not\nnecessarily for more general usage).\n\n.. _ring buffer: https://en.wikipedia.org/wiki/Circular_buffer"
    ),
    _(
        'picamera.Color(*args, **kwargs) \nThe Color class is a tuple which represents a color as red, green, and\nblue components.\n\nThe class has a flexible constructor which allows you to create an instance\nfrom a variety of color systems including `RGB`_, `Y\'UV`_, `Y\'IQ`_, `HLS`_,\nand `HSV`_.  There are also explicit constructors for each of these systems\nto allow you to force the use of a system in your code. For example, an\ninstance of :class:`Color` can be constructed in any of the following\nways::\n\n    >>> Color(\'#f00\')\n    <Color "#ff0000">\n    >>> Color(\'green\')\n    <Color "#008000">\n    >>> Color(0, 0, 1)\n    <Color "#0000ff">\n    >>> Color(hue=0, saturation=1, value=0.5)\n    <Color "#7f0000">\n    >>> Color(y=0.4, u=-0.05, v=0.615)\n    <Color "#ff0f4c">\n\nThe specific forms that the default constructor will accept are enumerated\nbelow:\n\n.. tabularcolumns:: |p{40mm}|p{100mm}|\n\n+------------------------------+------------------------------------------+\n| Style                        | Description                              |\n+==============================+==========================================+\n| Single positional parameter  | Equivalent to calling                    |\n|                              | :meth:`Color.from_string`.               |\n+------------------------------+------------------------------------------+\n| Three positional parameters  | Equivalent to calling                    |\n|                              | :meth:`Color.from_rgb` if all three      |\n|                              | parameters are between 0.0 and 1.0, or   |\n|                              | :meth:`Color.from_rgb_bytes` otherwise.  |\n+------------------------------+                                          |\n| Three named parameters:      |                                          |\n| *r*, *g*, *b*                |                                          |\n+------------------------------+                                          |\n| Three named parameters:      |                                          |\n| *red*, *green*, *blue*       |                                          |\n+------------------------------+------------------------------------------+\n| Three named parameters:      | Equivalent to calling                    |\n| *y*, *u*, *v*                | :meth:`Color.from_yuv` if *y* is between |\n|                              | 0.0 and 1.0, *u* is between -0.436 and   |\n|                              | 0.436, and *v* is between -0.615 and     |\n|                              | 0.615, or :meth:`Color.from_yuv_bytes`   |\n|                              | otherwise.                               |\n+------------------------------+------------------------------------------+\n| Three named parameters:      | Equivalent to calling                    |\n| *y*, *i*, *q*                | :meth:`Color.from_yiq`.                  |\n+------------------------------+------------------------------------------+\n| Three named parameters:      | Equivalent to calling                    |\n| *h*, *l*, *s*                | :meth:`Color.from_hls`.                  |\n+------------------------------+                                          |\n| Three named parameters:      |                                          |\n| *hue*, *lightness*,          |                                          |\n| *saturation*                 |                                          |\n+------------------------------+------------------------------------------+\n| Three named parameters:      | Equivalent to calling                    |\n| *h*, *s*, *v*                | :meth:`Color.from_hsv`                   |\n+------------------------------+                                          |\n| Three named parameters:      |                                          |\n| *hue*, *saturation*, *value* |                                          |\n+------------------------------+------------------------------------------+\n| Three named parameters:      | Equivalent to calling                    |\n| *x*, *y*, *z*                | :meth:`Color.from_cie_xyz`               |\n+------------------------------+------------------------------------------+\n| Three named parameters:      | Equivalent to calling                    |\n| *l*, *a*, *b*                | :meth:`Color.from_cie_lab`               |\n+------------------------------+------------------------------------------+\n| Three named parameters:      | Equivalent to calling                    |\n| *l*, *u*, *v*                | :meth:`Color.from_cie_luv`               |\n+------------------------------+------------------------------------------+\n\nIf the constructor parameters do not conform to any of the variants in the\ntable above, a :exc:`ValueError` will be thrown.\n\nInternally, the color is *always* represented as 3 float values\ncorresponding to the red, green, and blue components of the color. These\nvalues take a value from 0.0 to 1.0 (least to full intensity). The class\nprovides several attributes which can be used to convert one color system\ninto another::\n\n    >>> Color(\'#f00\').hls\n    (0.0, 0.5, 1.0)\n    >>> Color.from_string(\'green\').hue\n    Hue(deg=120.0)\n    >>> Color.from_rgb_bytes(0, 0, 255).yuv\n    (0.114, 0.435912, -0.099978)\n\nAs :class:`Color` derives from tuple, instances are immutable. While this\nprovides the advantage that they can be used as keys in a dict, it does\nmean that colors themselves cannot be directly manipulated (e.g. by\nreducing the red component).\n\nHowever, several auxiliary classes in the module provide the ability to\nperform simple transformations of colors via operators which produce a new\n:class:`Color` instance. For example::\n\n    >>> Color(\'red\') - Red(0.5)\n    <Color "#7f0000">\n    >>> Color(\'green\') + Red(0.5)\n    <Color "#7f8000">\n    >>> Color.from_hls(0.5, 0.5, 1.0)\n    <Color "#00feff">\n    >>> Color.from_hls(0.5, 0.5, 1.0) * Lightness(0.8)\n    <Color "#00cbcc">\n    >>> (Color.from_hls(0.5, 0.5, 1.0) * Lightness(0.8)).hls\n    (0.5, 0.4, 1.0)\n\nFrom the last example above one can see that even attributes not directly\nstored by the color (such as lightness) can be manipulated in this fashion.\nIn this case a :class:`Color` instance is constructed from HLS (hue,\nlightness, saturation) values with a lightness of 0.5. This is multiplied\nby a :class:`Lightness` instance with a value of 0.8 which constructs a new\n:class:`Color` with the same hue and saturation, but a lightness of 0.5 *\n0.8 = 0.4.\n\nIf an instance is converted to a string (with :func:`str`) it will return a\nstring containing the 7-character HTML code for the color (e.g. "#ff0000"\nfor red). As can be seen in the examples above, a similar representation is\nreturned for :func:`repr`.\n\n.. _RGB: https://en.wikipedia.org/wiki/RGB_color_space\n.. _Y\'UV: https://en.wikipedia.org/wiki/YUV\n.. _Y\'IQ: https://en.wikipedia.org/wiki/YIQ\n.. _HLS: https://en.wikipedia.org/wiki/HSL_and_HSV\n.. _HSV: https://en.wikipedia.org/wiki/HSL_and_HSV'
    ),
    _(
        'picamera.Green() \nRepresents the green component of a :class:`Color` for use in\ntransformations.  Instances of this class can be constructed directly with\na float value, or by querying the :attr:`Color.green` attribute. Addition,\nsubtraction, and multiplication are supported with :class:`Color`\ninstances. For example::\n\n    >>> Color(0, 0, 0) + Green(0.1)\n    <Color "#001900">\n    >>> Color.from_yuv(1, -0.4, -0.6) - Green(1)\n    <Color "#50002f">\n    >>> (Green(0.5) * Color(\'white\')).rgb\n    (Red(1.0), Green(0.5), Blue(1.0))'
    ),
    _(
        "picamera.Hue(n=None, deg=None, rad=None) \nRepresents the hue of a :class:`Color` for use in transformations.\nInstances of this class can be constructed directly with a float value in\nthe range [0.0, 1.0) representing an angle around the `HSL hue wheel`_. As\nthis is a circular mapping, 0.0 and 1.0 effectively mean the same thing,\ni.e.  out of range values will be normalized into the range [0.0, 1.0).\n\nThe class can also be constructed with the keyword arguments ``deg`` or\n``rad`` if you wish to specify the hue value in degrees or radians instead,\nrespectively. Instances can also be constructed by querying the\n:attr:`Color.hue` attribute.\n\nAddition, subtraction, and multiplication are supported with :class:`Color`\ninstances. For example::\n\n    >>> Color(1, 0, 0).hls\n    (0.0, 0.5, 1.0)\n    >>> (Color(1, 0, 0) + Hue(deg=180)).hls\n    (0.5, 0.5, 1.0)\n\nNote that whilst multiplication by a :class:`Hue` doesn't make much sense,\nit is still supported. However, the circular nature of a hue value can lead\nto surprising effects. In particular, since 1.0 is equivalent to 0.0 the\nfollowing may be observed::\n\n    >>> (Hue(1.0) * Color.from_hls(0.5, 0.5, 1.0)).hls\n    (0.0, 0.5, 1.0)\n\n.. _HSL hue wheel: https://en.wikipedia.org/wiki/Hue"
    ),
    _(
        'picamera.Lightness() \nRepresents the lightness of a :class:`Color` for use in transformations.\nInstances of this class can be constructed directly with a float value, or\nby querying the :attr:`Color.lightness` attribute. Addition, subtraction,\nand multiplication are supported with :class:`Color` instances. For\nexample::\n\n    >>> Color(0, 0, 0) + Lightness(0.1)\n    <Color "#191919">\n    >>> Color.from_rgb_bytes(0x80, 0x80, 0) - Lightness(0.2)\n    <Color "#191900">\n    >>> Lightness(0.9) * Color(\'wheat\')\n    <Color "#f0cd8d">'
    ),
    _(
        "picamera.PiCamera(camera_num=0, stereo_mode='none', stereo_decimate=False, resolution=None, framerate=None, sensor_mode=0, led_pin=None, clock_mode='reset', framerate_range=None) \nProvides a pure Python interface to the Raspberry Pi's camera module.\n\nUpon construction, this class initializes the camera. The *camera_num*\nparameter (which defaults to 0) selects the camera module that the instance\nwill represent. Only the Raspberry Pi compute module currently supports\nmore than one camera.\n\nThe *sensor_mode*, *resolution*, *framerate*, *framerate_range*, and\n*clock_mode* parameters provide initial values for the :attr:`sensor_mode`,\n:attr:`resolution`, :attr:`framerate`, :attr:`framerate_range`, and\n:attr:`clock_mode` attributes of the class (these attributes are all\nrelatively expensive to set individually, hence setting them all upon\nconstruction is a speed optimization). Please refer to the attribute\ndocumentation for more information and default values.\n\nThe *stereo_mode* and *stereo_decimate* parameters configure dual cameras\non a compute module for sterescopic mode. These parameters can only be set\nat construction time; they cannot be altered later without closing the\n:class:`PiCamera` instance and recreating it. The *stereo_mode* parameter\ndefaults to ``'none'`` (no stereoscopic mode) but can be set to\n``'side-by-side'`` or ``'top-bottom'`` to activate a stereoscopic mode. If\nthe *stereo_decimate* parameter is ``True``, the resolution of the two\ncameras will be halved so that the resulting image has the same dimensions\nas if stereoscopic mode were not being used.\n\nThe *led_pin* parameter can be used to specify the GPIO pin which should be\nused to control the camera's LED via the :attr:`led` attribute. If this is\nnot specified, it should default to the correct value for your Pi platform.\nYou should only need to specify this parameter if you are using a custom\nDeviceTree blob (this is only typical on the `Compute Module`_ platform).\n\nNo preview or recording is started automatically upon construction.  Use\nthe :meth:`capture` method to capture images, the :meth:`start_recording`\nmethod to begin recording video, or the :meth:`start_preview` method to\nstart live display of the camera's input.\n\nSeveral attributes are provided to adjust the camera's configuration. Some\nof these can be adjusted while a recording is running, like\n:attr:`brightness`. Others, like :attr:`resolution`, can only be adjusted\nwhen the camera is idle.\n\nWhen you are finished with the camera, you should ensure you call the\n:meth:`close` method to release the camera resources::\n\n    camera = PiCamera()\n    try:\n        # do something with the camera\n        pass\n    finally:\n        camera.close()\n\nThe class supports the context manager protocol to make this particularly\neasy (upon exiting the :keyword:`with` statement, the :meth:`close` method\nis automatically called)::\n\n    with PiCamera() as camera:\n        # do something with the camera\n        pass\n\n.. versionchanged:: 1.8\n    Added *stereo_mode* and *stereo_decimate* parameters.\n\n.. versionchanged:: 1.9\n    Added *resolution*, *framerate*, and *sensor_mode* parameters.\n\n.. versionchanged:: 1.10\n    Added *led_pin* parameter.\n\n.. versionchanged:: 1.11\n    Added *clock_mode* parameter, and permitted setting of resolution as\n    appropriately formatted string.\n\n.. versionchanged:: 1.13\n    Added *framerate_range* parameter.\n\n.. _Compute Module: https://www.raspberrypi.org/documentation/hardware/computemodule/cmio-camera.md"
    ),
    _(
        "picamera.PiCameraAlphaStripping() \nRaised when picamera does alpha-byte stripping."
    ),
    _(
        "picamera.PiCameraAlreadyRecording() \nRaised when :meth:`~PiCamera.start_recording` or\n:meth:`~PiCamera.record_sequence` are called against a port which already\nhas an active recording."
    ),
    _(
        "picamera.PiCameraCircularIO(camera, size=None, seconds=None, bitrate=17000000, splitter_port=1) \nA derivative of :class:`CircularIO` which tracks camera frames.\n\nPiCameraCircularIO provides an in-memory stream based on a ring buffer. It\nis a specialization of :class:`CircularIO` which associates video frame\nmeta-data with the recorded stream, accessible from the :attr:`frames`\nproperty.\n\n.. warning::\n\n    The class makes a couple of assumptions which will cause the frame\n    meta-data tracking to break if they are not adhered to:\n\n    * the stream is only ever appended to - no writes ever start from\n      the middle of the stream\n\n    * the stream is never truncated (from the right; being ring buffer\n      based, left truncation will occur automatically); the exception\n      to this is the :meth:`clear` method.\n\nThe *camera* parameter specifies the :class:`PiCamera` instance that will\nbe recording video to the stream. If specified, the *size* parameter\ndetermines the maximum size of the stream in bytes. If *size* is not\nspecified (or ``None``), then *seconds* must be specified instead. This\nprovides the maximum length of the stream in seconds, assuming a data rate\nin bits-per-second given by the *bitrate* parameter (which defaults to\n``17000000``, or 17Mbps, which is also the default bitrate used for video\nrecording by :class:`PiCamera`).  You cannot specify both *size* and\n*seconds*.\n\nThe *splitter_port* parameter specifies the port of the built-in splitter\nthat the video encoder will be attached to. This defaults to ``1`` and most\nusers will have no need to specify anything different. If you do specify\nsomething else, ensure it is equal to the *splitter_port* parameter of the\ncorresponding call to :meth:`~PiCamera.start_recording`.  For example::\n\n    import picamera\n\n    with picamera.PiCamera() as camera:\n        with picamera.PiCameraCircularIO(camera, splitter_port=2) as stream:\n            camera.start_recording(stream, format='h264', splitter_port=2)\n            camera.wait_recording(10, splitter_port=2)\n            camera.stop_recording(splitter_port=2)\n\n.. attribute:: frames\n\n    Returns an iterator over the frame meta-data.\n\n    As the camera records video to the stream, the class captures the\n    meta-data associated with each frame (in the form of a\n    :class:`PiVideoFrame` tuple), discarding meta-data for frames which are\n    no longer fully stored within the underlying ring buffer.  You can use\n    the frame meta-data to locate, for example, the first keyframe present\n    in the stream in order to determine an appropriate range to extract."
    ),
    _(
        "picamera.PiCameraClosed() \nRaised when a method is called on a camera which has already been closed."
    ),
    _(
        "picamera.PiCameraDeprecated() \nRaised when deprecated functionality in picamera is used."
    ),
    _("picamera.PiCameraError() \nBase class for PiCamera errors."),
    _(
        "picamera.PiCameraFallback() \nRaised when picamera has to fallback on old functionality."
    ),
    _(
        "picamera.PiCameraMMALError(status, prefix='') \nRaised when an MMAL operation fails for whatever reason."
    ),
    _(
        "picamera.PiCameraNotRecording() \nRaised when :meth:`~PiCamera.stop_recording` or\n:meth:`~PiCamera.split_recording` are called against a port which has no\nrecording active."
    ),
    _(
        "picamera.PiCameraPortDisabled(msg) \nRaised when attempting a buffer operation on a disabled port.\n\nThis exception is intended for the common use-case of attempting to get\nor send a buffer just when a component is shutting down (e.g. at script\nteardown) and simplifies the trivial response (ignore the error and shut\ndown quietly). For example::\n\n    def _callback(self, port, buf):\n        try:\n            buf = self.outputs[0].get_buffer(False)\n        except PiCameraPortDisabled:\n            return True # shutting down\n        # ..."
    ),
    _(
        "picamera.PiCameraResizerEncoding() \nRaised when picamera uses a resizer purely for encoding purposes."
    ),
    _(
        "picamera.PiCameraRuntimeError() \nRaised when an invalid sequence of operations is attempted with a\n:class:`PiCamera` object."
    ),
    _(
        "picamera.PiCameraValueError() \nRaised when an invalid value is fed to a :class:`~PiCamera` object."
    ),
    _("picamera.PiCameraWarning() \nBase class for PiCamera warnings."),
    _(
        'picamera.PiCookedMultiImageEncoder(parent, camera_port, input_port, format, resize, **options) \nEncoder for "cooked" (encoded) multiple image output.\n\nThis encoder descends from :class:`PiMultiImageEncoder` but includes no\nnew functionality as video-port based encodes (which is all this class\nis used for) don\'t support Exif tag output.'
    ),
    _(
        'picamera.PiCookedOneImageEncoder(parent, camera_port, input_port, format, resize, **options) \nEncoder for "cooked" (encoded) single image output.\n\nThis encoder extends :class:`PiOneImageEncoder` to include Exif tags in the\noutput.'
    ),
    _(
        "picamera.PiCookedVideoEncoder(parent, camera_port, input_port, format, resize, **options) \nVideo encoder for encoded recordings.\n\nThis class is a derivative of :class:`PiVideoEncoder` and only exists to\nprovide naming symmetry with the image encoder classes."
    ),
    _(
        "picamera.PiEncoder(parent, camera_port, input_port, format, resize, **options) \nBase implementation of an MMAL encoder for use by PiCamera.\n\nThe *parent* parameter specifies the :class:`PiCamera` instance that has\nconstructed the encoder. The *camera_port* parameter provides the MMAL\ncamera port that the encoder should enable for capture (this will be the\nstill or video port of the camera component). The *input_port* parameter\nspecifies the MMAL port that the encoder should connect to its input.\nSometimes this will be the same as the camera port, but if other components\nare present in the pipeline (e.g. a splitter), it may be different.\n\nThe *format* parameter specifies the format that the encoder should\nproduce in its output. This is specified as a string and will be one of\nthe following for image encoders:\n\n* ``'jpeg'``\n* ``'png'``\n* ``'gif'``\n* ``'bmp'``\n* ``'yuv'``\n* ``'rgb'``\n* ``'rgba'``\n* ``'bgr'``\n* ``'bgra'``\n\nAnd one of the following for video encoders:\n\n* ``'h264'``\n* ``'mjpeg'``\n\nThe *resize* parameter is either ``None`` (indicating no resizing\nshould take place), or a ``(width, height)`` tuple specifying the\nresolution that the output of the encoder should be resized to.\n\nFinally, the *options* parameter specifies additional keyword arguments\nthat can be used to configure the encoder (e.g. bitrate for videos, or\nquality for images).\n\n.. attribute:: camera_port\n\n    The :class:`~mmalobj.MMALVideoPort` that needs to be activated and\n    deactivated in order to start/stop capture. This is not necessarily the\n    port that the encoder component's input port is connected to (for\n    example, in the case of video-port based captures, this will be the\n    camera video port behind the splitter).\n\n.. attribute:: encoder\n\n    The :class:`~mmalobj.MMALComponent` representing the encoder, or\n    ``None`` if no encoder component has been created (some encoder classes\n    don't use an actual encoder component, for example\n    :class:`PiRawImageMixin`).\n\n.. attribute:: event\n\n    A :class:`threading.Event` instance used to synchronize operations\n    (like start, stop, and split) between the control thread and the\n    callback thread.\n\n.. attribute:: exception\n\n    If an exception occurs during the encoder callback, this attribute is\n    used to store the exception until it can be re-raised in the control\n    thread.\n\n.. attribute:: format\n\n    The image or video format that the encoder is expected to produce. This\n    is equal to the value of the *format* parameter.\n\n.. attribute:: input_port\n\n    The :class:`~mmalobj.MMALVideoPort` that the encoder should be\n    connected to.\n\n.. attribute:: output_port\n\n    The :class:`~mmalobj.MMALVideoPort` that produces the encoder's output.\n    In the case no encoder component is created, this should be the\n    camera/component output port responsible for producing data. In other\n    words, this attribute **must** be set on initialization.\n\n.. attribute:: outputs\n\n    A mapping of ``key`` to ``(output, opened)`` tuples where ``output``\n    is a file-like object, and ``opened`` is a bool indicating whether or\n    not we opened the output object (and thus whether we are responsible\n    for eventually closing it).\n\n.. attribute:: outputs_lock\n\n    A :func:`threading.Lock` instance used to protect access to\n    :attr:`outputs`.\n\n.. attribute:: parent\n\n    The :class:`PiCamera` instance that created this PiEncoder instance.\n\n.. attribute:: pool\n\n    A pointer to a pool of MMAL buffers.\n\n.. attribute:: resizer\n\n    The :class:`~mmalobj.MMALResizer` component, or ``None`` if no resizer\n    component has been created."
    ),
    _(
        "picamera.PiFramerateRange(low, high) \nThis class is a :func:`~collections.namedtuple` derivative used to store\nthe low and high limits of a range of framerates. It is recommended that\nyou access the information stored by this class by attribute rather than\nposition (for example: ``camera.framerate_range.low`` rather than\n``camera.framerate_range[0]``).\n\n.. attribute:: low\n\n    The lowest framerate that the camera is permitted to use (inclusive).\n    When the :attr:`~picamera.PiCamera.framerate_range` attribute is\n    queried, this value will always be returned as a\n    :class:`~fractions.Fraction`.\n\n.. attribute:: high\n\n    The highest framerate that the camera is permitted to use (inclusive).\n    When the :attr:`~picamera.PiCamera.framerate_range` attribute is\n    queried, this value will always be returned as a\n    :class:`~fractions.Fraction`.\n\n.. versionadded:: 1.13"
    ),
    _(
        "picamera.PiImageEncoder(parent, camera_port, input_port, format, resize, **options) \nEncoder for image capture.\n\nThis derivative of :class:`PiEncoder` extends the :meth:`_create_encoder`\nmethod to configure the encoder for a variety of encoded image outputs\n(JPEG, PNG, etc.)."
    ),
    _(
        "picamera.PiMultiImageEncoder(parent, camera_port, input_port, format, resize, **options) \nEncoder for multiple image capture.\n\nThis class extends :class:`PiImageEncoder` to handle an iterable of outputs\ninstead of a single output. The :meth:`~PiEncoder._callback_write` method\nis extended to terminate capture when the iterable is exhausted, while\n:meth:`PiEncoder._open_output` is overridden to begin iteration and rely\non the new :meth:`_next_output` method to advance output to the next item\nin the iterable."
    ),
    _(
        "picamera.PiNullSink(parent, source) \nImplements an :class:`~mmalobj.MMALNullSink` which can be used in place of\na renderer.\n\nThe *parent* parameter specifies the :class:`PiCamera` instance which\nconstructed this :class:`~mmalobj.MMALNullSink`. The *source* parameter\nspecifies the :class:`~mmalobj.MMALPort` which the null-sink should connect\nto its input.\n\nThe null-sink can act as a drop-in replacement for :class:`PiRenderer` in\nmost cases, but obviously doesn't implement attributes like ``alpha``,\n``layer``, etc. as it simply dumps any incoming frames. This is also the\nreason that this class doesn't derive from :class:`PiRenderer` like all\nother classes in this module."
    ),
    _(
        "picamera.PiOneImageEncoder(parent, camera_port, input_port, format, resize, **options) \nEncoder for single image capture.\n\nThis class simply extends :meth:`~PiEncoder._callback_write` to terminate\ncapture at frame end (i.e. after a single frame has been received)."
    ),
    _(
        "picamera.PiOverlayRenderer(parent, source, resolution=None, format=None, layer=0, alpha=255, fullscreen=True, window=None, crop=None, rotation=0, vflip=False, hflip=False) \nRepresents an :class:`~mmalobj.MMALRenderer` with a static source for\noverlays.\n\nThis class descends from :class:`PiRenderer` and adds a static *source* for\nthe :class:`~mmalobj.MMALRenderer`. The *source* must be an object that\nsupports the :ref:`buffer protocol <bufferobjects>` in one of the supported\nformats.\n\nThe optional *resolution* parameter specifies the size of the *source* as a\n``(width, height)`` tuple. If this is omitted or ``None`` then the\nresolution is assumed to be the same as the parent camera's current\n:attr:`~PiCamera.resolution`. The optional *format* parameter specifies the\nencoding of the *source*. This can be one of the unencoded formats:\n``'yuv'``, ``'rgb'``, ``'rgba'``, ``'bgr'``, or ``'bgra'``. If omitted or\n``None``, *format* will be guessed based on the size of *source* (assuming\n3 bytes for `RGB`_, and 4 bytes for `RGBA`_).\n\nThe length of *source* must take into account that widths are rounded up to\nthe nearest multiple of 32, and heights to the nearest multiple of 16.  For\nexample, if *resolution* is ``(1280, 720)``, and *format* is ``'rgb'`` then\n*source* must be a buffer with length 1280 x 720 x 3 bytes, or 2,764,800\nbytes (because 1280 is a multiple of 32, and 720 is a multiple of 16 no\nextra rounding is required).  However, if *resolution* is ``(97, 57)``, and\n*format* is ``'rgb'`` then *source* must be a buffer with length 128 x 64 x\n3 bytes, or 24,576 bytes (pixels beyond column 97 and row 57 in the source\nwill be ignored).\n\nThe *layer*, *alpha*, *fullscreen*, and *window* parameters are the same\nas in :class:`PiRenderer`.\n\n.. _RGB: https://en.wikipedia.org/wiki/RGB\n.. _RGBA: https://en.wikipedia.org/wiki/RGBA_color_space\n\n.. versionchanged:: 1.13\n    Added *format* parameter"
    ),
    _(
        "picamera.PiPreviewRenderer(parent, source, resolution=None, layer=2, alpha=255, fullscreen=True, window=None, crop=None, rotation=0, vflip=False, hflip=False) \nRepresents an :class:`~mmalobj.MMALRenderer` which uses the camera's\npreview as a source.\n\nThis class descends from :class:`PiRenderer` and adds an\n:class:`~mmalobj.MMALConnection` to connect the renderer to an MMAL port.\nThe *source* parameter specifies the :class:`~mmalobj.MMALPort` to connect\nto the renderer.\n\nThe *layer*, *alpha*, *fullscreen*, and *window* parameters are the same\nas in :class:`PiRenderer`."
    ),
    _(
        'picamera.PiRawImageMixin(parent, camera_port, input_port, format, resize, **options) \nMixin class for "raw" (unencoded) image capture.\n\nThe :meth:`_callback_write` method is overridden to manually calculate when\nto terminate output.'
    ),
    _(
        'picamera.PiRawMixin(parent, camera_port, input_port, format, resize, **options) \nMixin class for "raw" (unencoded) output.\n\nThis mixin class overrides the initializer of :class:`PiEncoder`, along\nwith :meth:`_create_resizer` and :meth:`_create_encoder` to configure the\npipeline for unencoded output. Specifically, it disables the construction\nof an encoder, and sets the output port to the input port passed to the\ninitializer, unless resizing is required (either for actual resizing, or\nfor format conversion) in which case the resizer\'s output is used.'
    ),
    _(
        "picamera.PiRawMultiImageEncoder(parent, camera_port, input_port, format, resize, **options) \nMultiple image encoder for unencoded capture.\n\nThis class is a derivative of :class:`PiMultiImageEncoder` and the\n:class:`PiRawImageMixin` class intended for use with\n:meth:`~PiCamera.capture_sequence` when it is called with an unencoded\nimage format.\n\n.. warning::\n\n    This class creates an inheritance diamond. Take care to determine the\n    MRO of super-class calls."
    ),
    _(
        "picamera.PiRawOneImageEncoder(parent, camera_port, input_port, format, resize, **options) \nSingle image encoder for unencoded capture.\n\nThis class is a derivative of :class:`PiOneImageEncoder` and the\n:class:`PiRawImageMixin` class intended for use with\n:meth:`~PiCamera.capture` (et al) when it is called with an unencoded image\nformat.\n\n.. warning::\n\n    This class creates an inheritance diamond. Take care to determine the\n    MRO of super-class calls."
    ),
    _(
        "picamera.PiRawVideoEncoder(parent, camera_port, input_port, format, resize, **options) \nVideo encoder for unencoded recordings.\n\nThis class is a derivative of :class:`PiVideoEncoder` and the\n:class:`PiRawMixin` class intended for use with\n:meth:`~PiCamera.start_recording` when it is called with an unencoded\nformat.\n\n.. warning::\n\n    This class creates an inheritance diamond. Take care to determine the\n    MRO of super-class calls."
    ),
    _(
        "picamera.PiRenderer(parent, layer=0, alpha=255, fullscreen=True, window=None, crop=None, rotation=0, vflip=False, hflip=False) \nWraps :class:`~mmalobj.MMALRenderer` for use by PiCamera.\n\nThe *parent* parameter specifies the :class:`PiCamera` instance that has\nconstructed this renderer. The *layer* parameter specifies the layer that\nthe renderer will inhabit. Higher numbered layers obscure lower numbered\nlayers (unless they are partially transparent). The initial opacity of the\nrenderer is specified by the *alpha* parameter (which defaults to 255,\nmeaning completely opaque). The *fullscreen* parameter which defaults to\n``True`` indicates whether the renderer should occupy the entire display.\nFinally, the *window* parameter (which only has meaning when *fullscreen*\nis ``False``) is a four-tuple of ``(x, y, width, height)`` which gives the\nscreen coordinates that the renderer should occupy when it isn't\nfull-screen.\n\nThis base class isn't directly used by :class:`PiCamera`, but the two\nderivatives defined below, :class:`PiOverlayRenderer` and\n:class:`PiPreviewRenderer`, are used to produce overlays and the camera\npreview respectively."
    ),
    _(
        "picamera.PiResolution(width, height) \nA :func:`~collections.namedtuple` derivative which represents a resolution\nwith a :attr:`width` and :attr:`height`.\n\n.. attribute:: width\n\n    The width of the resolution in pixels\n\n.. attribute:: height\n\n    The height of the resolution in pixels\n\n.. versionadded:: 1.11"
    ),
    _(
        "picamera.PiVideoEncoder(parent, camera_port, input_port, format, resize, **options) \nEncoder for video recording.\n\nThis derivative of :class:`PiEncoder` configures itself for H.264 or MJPEG\nencoding.  It also introduces a :meth:`split` method which is used by\n:meth:`~PiCamera.split_recording` and :meth:`~PiCamera.record_sequence` to\nredirect future output to a new filename or object. Finally, it also\nextends :meth:`PiEncoder.start` and :meth:`PiEncoder._callback_write` to\ntrack video frame meta-data, and to permit recording motion data to a\nseparate output object."
    ),
    _(
        "picamera.PiVideoFrame(index, frame_type, frame_size, video_size, split_size, timestamp, complete) \nThis class is a :func:`~collections.namedtuple` derivative used to store\ninformation about a video frame. It is recommended that you access the\ninformation stored by this class by attribute name rather than position\n(for example: ``frame.index`` rather than ``frame[0]``).\n\n.. attribute:: index\n\n    Returns the zero-based number of the frame. This is a monotonic counter\n    that is simply incremented every time the camera starts outputting a\n    new frame. As a consequence, this attribute cannot be used to detect\n    dropped frames. Nor does it necessarily represent actual frames; it\n    will be incremented for SPS headers and motion data buffers too.\n\n.. attribute:: frame_type\n\n    Returns a constant indicating the kind of data that the frame contains\n    (see :class:`PiVideoFrameType`). Please note that certain frame types\n    contain no image data at all.\n\n.. attribute:: frame_size\n\n    Returns the size in bytes of the current frame. If a frame is written\n    in multiple chunks, this value will increment while :attr:`index`\n    remains static. Query :attr:`complete` to determine whether the frame\n    has been completely output yet.\n\n.. attribute:: video_size\n\n    Returns the size in bytes of the entire video up to this frame.  Note\n    that this is unlikely to match the size of the actual file/stream\n    written so far. This is because a stream may utilize buffering which\n    will cause the actual amount written (e.g. to disk) to lag behind the\n    value reported by this attribute.\n\n.. attribute:: split_size\n\n    Returns the size in bytes of the video recorded since the last call to\n    either :meth:`~PiCamera.start_recording` or\n    :meth:`~PiCamera.split_recording`. For the reasons explained above,\n    this may differ from the size of the actual file/stream written so far.\n\n.. attribute:: timestamp\n\n    Returns the presentation timestamp (PTS) of the frame. This represents\n    the point in time that the Pi received the first line of the frame from\n    the camera.\n\n    The timestamp is measured in microseconds (millionths of a second).\n    When the camera's clock mode is ``'reset'`` (the default), the\n    timestamp is relative to the start of the video recording.  When the\n    camera's :attr:`~PiCamera.clock_mode` is ``'raw'``, it is relative to\n    the last system reboot. See :attr:`~PiCamera.timestamp` for more\n    information.\n\n    .. warning::\n\n        Currently, the camera occasionally returns \"time unknown\" values in\n        this field which picamera represents as ``None``. If you are\n        querying this property you will need to check the value is not\n        ``None`` before using it. This happens for SPS header \"frames\",\n        for example.\n\n.. attribute:: complete\n\n    Returns a bool indicating whether the current frame is complete or not.\n    If the frame is complete then :attr:`frame_size` will not increment\n    any further, and will reset for the next frame.\n\n.. versionchanged:: 1.5\n    Deprecated :attr:`header` and :attr:`keyframe` attributes and added the\n    new :attr:`frame_type` attribute instead.\n\n.. versionchanged:: 1.9\n    Added the :attr:`complete` attribute."
    ),
    _(
        "picamera.PiVideoFrameType() \nThis class simply defines constants used to represent the type of a frame\nin :attr:`PiVideoFrame.frame_type`. Effectively it is a namespace for an\nenum.\n\n.. attribute:: frame\n\n    Indicates a predicted frame (P-frame). This is the most common frame\n    type.\n\n.. attribute:: key_frame\n\n    Indicates an intra-frame (I-frame) also known as a key frame.\n\n.. attribute:: sps_header\n\n    Indicates an inline SPS/PPS header (rather than picture data) which is\n    typically used as a split point.\n\n.. attribute:: motion_data\n\n    Indicates the frame is inline motion vector data, rather than picture\n    data.\n\n.. versionadded:: 1.5"
    ),
    _(
        "picamera.Red() \nRepresents the red component of a :class:`Color` for use in\ntransformations. Instances of this class can be constructed directly with a\nfloat value, or by querying the :attr:`Color.red` attribute. Addition,\nsubtraction, and multiplication are supported with :class:`Color`\ninstances. For example::\n\n    >>> Color.from_rgb(0, 0, 0) + Red(0.5)\n    <Color \"#7f0000\">\n    >>> Color('#f00') - Color('#900').red\n    <Color \"#660000\">\n    >>> (Red(0.1) * Color('red')).red\n    Red(0.1)"
    ),
    _(
        'picamera.Saturation() \nRepresents the saturation of a :class:`Color` for use in transformations.\nInstances of this class can be constructed directly with a float value, or\nby querying the :attr:`Color.saturation` attribute. Addition, subtraction,\nand multiplication are supported with :class:`Color` instances. For\nexample::\n\n    >>> Color(0.9, 0.9, 0.6) + Saturation(0.1)\n    <Color "#ebeb92">\n    >>> Color(\'red\') - Saturation(1)\n    <Color "#7f7f7f">\n    >>> Saturation(0.5) * Color(\'wheat\')\n    <Color "#e4d9c3">'
    ),
    _(
        "picamera.mmal_check(status, prefix='') \nChecks the return status of an mmal call and raises an exception on\nfailure.\n\nThe *status* parameter is the result of an MMAL call. If *status* is\nanything other than MMAL_SUCCESS, a :exc:`PiCameraMMALError` exception is\nraised. The optional *prefix* parameter specifies a prefix message to place\nat the start of the exception's message to provide some context."
    ),
    _(
        "picamera.str() \nstr(object='') -> str\nstr(bytes_or_buffer[, encoding[, errors]]) -> str\n\nCreate a new string object from the given object. If encoding or\nerrors is specified, then the object must expose a data buffer\nthat will be decoded using the given encoding and error handler.\nOtherwise, returns the result of object.__str__() (if defined)\nor repr(object).\nencoding defaults to sys.getdefaultencoding().\nerrors defaults to 'strict'."
    ),
    _(
        "guizero.App(title='guizero', width=500, height=500, layout='auto', bgcolor=None) \nToplevel widget of Tk which represents mostly the main window\nof an application. It has an associated Tcl interpreter."
    ),
    _(
        "guizero.Box(master, layout='auto', grid=None, align=None) \nFrame widget which may contain other widgets and can have a 3D border."
    ),
    _(
        "guizero.ButtonGroup(master, options, selected, horizontal=False, command=None, grid=None, align=None) \nFrame widget which may contain other widgets and can have a 3D border."
    ),
    _(
        "guizero.CheckBox(master, text, command=None, grid=None, align=None) \nCheckbutton widget which is either in on- or off-state."
    ),
    _(
        "guizero.Combo(master, options, selected=None, command=None, grid=None, align=None) \nOptionMenu which allows the user to select a value from a menu."
    ),
    _(
        "guizero.MenuBar(master, toplevel, options) \nMenu widget which allows displaying menu bars, pull-down menus and pop-up menus."
    ),
    _(
        "guizero.Picture(master, image, grid=None, align=None) \nLabel widget which can display text and bitmaps."
    ),
    _(
        "guizero.PushButton(master, command, args=None, text='Button', icon=None, pady=10, padx=10, grid=None, align=None) \nButton widget."
    ),
    _(
        "guizero.RadioButton(master, text, value, variable, command=None, grid=None, align=None) \nRadiobutton widget which shows only one of several buttons in on-state."
    ),
    _(
        "guizero.Slider(master, start=0, end=100, horizontal=True, command=None, grid=None, align=None) \nScale widget which can display a numerical scale."
    ),
    _(
        "guizero.Text(master, text='', size=12, color='black', font='Helvetica', grid=None, align=None) \nLabel widget which can display text and bitmaps."
    ),
    _(
        "guizero.TextBox(master, text='', width=10, grid=None, align=None) \nEntry widget which allows displaying simple text."
    ),
    _(
        "guizero.Tk(screenName=None, baseName=None, className='Tk', useTk=1, sync=0, use=None) \nToplevel widget of Tk which represents mostly the main window\nof an application. It has an associated Tcl interpreter."
    ),
    _(
        "guizero.Waffle(master, height=3, width=3, dim=20, pad=5, color='white', dotty=False, remember=False, grid=None, align=None) \nFrame widget which may contain other widgets and can have a 3D border."
    ),
    _(
        "guizero.exit() \nexit([status])\n\nExit the interpreter by raising SystemExit(status).\nIf the status is omitted or None, it defaults to zero (i.e., success).\nIf the status is an integer, it will be used as the system exit status.\nIf it is another kind of object, it will be printed and the system\nexit status will be one (i.e., failure)."
    ),
    _(
        "networkzero.DifferentThreadError() \nCommon base class for all non-exit exceptions."
    ),
    _(
        "networkzero.InvalidAddressError(address, errno=None) \nCommon base class for all non-exit exceptions."
    ),
    _(
        "networkzero.NetworkZeroError() \nCommon base class for all non-exit exceptions."
    ),
    _(
        "networkzero.SocketAlreadyExistsError() \nCommon base class for all non-exit exceptions."
    ),
    _(
        "networkzero.SocketInterruptedError(after_n_seconds) \nCommon base class for all non-exit exceptions."
    ),
    _(
        "networkzero.SocketTimedOutError(n_seconds) \nCommon base class for all non-exit exceptions."
    ),
    _(
        "networkzero.action_and_params(commandline) \nTreat a command line as an action followed by parameter\n\n:param commandline: a string containing at least an action\n:returns: action, [param1, param2, ...]"
    ),
    _(
        "networkzero.address(address=None) \nConvert one of a number of inputs into a valid ip:port string.\n\nElements which are not provided are filled in as follows:\n    \n    * IP Address: the system is asked for the set of IP addresses associated \n      with the machine and the first one is used, preferring those matching\n      `address` if it is a wildcard.\n    * Port number: a random port is selected from the pool of dynamically-available \n      port numbers.\n  \nThis means you can pass any of: nothing; a hostname; an IP address; an IP address with wildcards; a port number\n\nIf an IP address is supplied but is invalid, an InvalidAddressError\nexception is raised.\n\n:param address: (optional) Any of: an IP address, a port number, or both\n\n:returns: a valid ip:port string for this machine"
    ),
    _(
        'networkzero.advertise(name, address=None, fail_if_exists=False, ttl_s=20) \nAdvertise a name at an address\n\nStart to advertise service `name` at address `address`. If\nthe address is not supplied, one is constructed and this is\nreturned by the function. ie this is a typical use::\n\n    address = nw0.advertise("myservice")\n    \n:param name: any text\n:param address: either "ip:port" or None\n:param fail_if_exists: fail if this name is already registered?\n:param ttl_s: the advert will persist for this many seconds other beacons\n:returns: the address given or constructed'
    ),
    _(
        "networkzero.bytes_to_string(data) \nTake bytes and return a base64-encoded unicode string equivalent\n\n:param data: a bytes object\n:returns: base64-encoded unicode object"
    ),
    _(
        'networkzero.discover(name, wait_for_s=60) \nDiscover a service by name\n\nLook for an advert to a named service::\n\n    address = nw0.discover("myservice")\n    \n:param name: any text\n:param wait_for_s: how many seconds to wait before giving up\n:returns: the address found or None'
    ),
    _(
        "networkzero.discover_all() \nProduce a list of all known services and their addresses\n\nAsk for all known services as a list of 2-tuples: (name, address)\nThis could, eg, be used to form a dictionary of services::\n\n    services = dict(nw0.discover_all())\n    \n:returns: a list of 2-tuples [(name, address), ...]"
    ),
    _(
        "networkzero.discover_group(group, separator='/', exclude=None) \nProduce a list of all services and their addresses in a group\n\nA group is an optional form of namespace within the discovery mechanism.\nIf an advertised name has the form <group><sep><name> it is deemed to\nbelong to <group>. Note that the service's name is still the full\nstring <group><sep><name>. The group concept is simply for discovery and\nto assist differentiation, eg, in a classroom group.\n\n:param group: the name of a group prefix\n:param separator: the separator character [/]\n:param exclude: an iterable of names to exclude (or None)\n\n:returns: a list of 2-tuples [(name, address), ...]"
    ),
    _(
        "networkzero.networkzero.config() \nCommon configuration elements for networkzero"
    ),
    _(
        "networkzero.networkzero.discovery() \nAdvertise and collect advertisements of network services\n\nThe discovery module offers:\n\n    * A UDP broadcast socket which:\n      \n      - Listens for and keeps track of service adverts from this and other \n        machines & processes\n      - Broadcasts services advertised by this process\n\n    * A ZeroMQ socket which allow any process on this machine to \n      communicate with its broadcast socket\n\nIn other words, we have a beacon which listens to instructions\nfrom processes on this machine while sending out and listening \nto adverts broadcast to/from all machines on the network.\n\nThe beacon is started automatically in a daemon thread when the first \nattempt is made to advertise or discover. If another process already \nhas a beacon running (ie if this beacon can't bind to its port) this \nbeacon thread will shut down with no further action.\n\nThe module-level functions to advertise and discover will open a connection\nto a ZeroMQ socket on this machine (which might be hosted by this or by another\nprocess) and will use this socket to send commands to the beacon thread which\nwill update or return its internal list of advertised services.\n\nAs an additional convenience, the :func:`advertise` function will, if given no\nspecific address, generate a suitable ip:port pair by interrogating the system.\nThis functionality is actually in :func:`networkzero.address` (qv)."
    ),
    _(
        "networkzero.send_message_to(address, message=None, wait_for_reply_s=<Forever>) \nSend a message and return the reply\n\n:param address: a nw0 address (eg from `nw0.discover`)\n:param message: any simple Python object, including text & tuples\n:param wait_for_reply_s: how many seconds to wait for a reply [default: forever]\n\n:returns: the reply returned from the address or None if out of time"
    ),
    _(
        "networkzero.send_news_to(address, topic, data=None) \nPublish news to all subscribers\n\n:param address: a nw0 address, eg from `nw0.advertise`\n:param topic: any text object\n:param data: any simple Python object including test & tuples [default: empty]"
    ),
    _(
        "networkzero.send_reply_to(address, reply=None) \nReply to a message previously received\n\n:param address: a nw0 address (eg from `nw0.advertise`)\n:param reply: any simple Python object, including text & tuples"
    ),
    _(
        "networkzero.string_to_bytes(data) \nTake a base64-encoded unicode string and return the equivalent bytes\n\n:param data: a base64-encoded unicode object\n:returns: the equivalent bytes"
    ),
    _(
        "networkzero.wait_for_message_from(address, wait_for_s=<Forever>, autoreply=False) \nWait for a message\n\n:param address: a nw0 address (eg from `nw0.advertise`)\n:param wait_for_s: how many seconds to wait for a message before giving up [default: forever]\n:param autoreply: whether to send an empty reply [default: No]\n\n:returns: the message received from another address or None if out of time"
    ),
    _(
        "networkzero.wait_for_news_from(address, prefix='', wait_for_s=<Forever>) \nWait for news whose topic starts with `prefix`.\n\n:param address: a nw0 address, eg from `nw0.discover`\n:param prefix: any text object [default: all messages]\n:param wait_for_s: how many seconds to wait before giving up [default: forever]\n\n:returns: a 2-tuple of (topic, data) or (None, None) if out of time"
    ),
]
