#!/usr/bin/env python # coding=utf-8 # MIT License # # Copyright (C) 2021 Kontron Electronics GmbH # # Permission is hereby granted, free of charge, to any person obtaining # a copy of this software and associated documentation files # (the "Software"), to deal in the Software without restriction, # including without limitation the rights to use, copy, modify, merge, # publish, distribute, sublicense, and/or sell copies of the Software, # and to permit persons to whom the Software is furnished to do so, # subject to the following conditions: # # The above copyright notice and this permission notice shall be included # in all copies or substantial portions of the Software. # # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS # OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, # FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL # THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER # LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING # FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER # DEALINGS IN THE SOFTWARE. # # For further details see LICENSE.txt. # ----------------------------------------------------------------------------- # Attention: # The PiXtend Python Library v2 (PPLv2) was developed as a Python # library / module to make use of the inheritance functionality of Python. # However, since the library must access the hardware based SPI bus on the # Raspberry Pi only ONE single instance of the PiXtendV2S or PiXtendV2L # class per PiXtend is allowed! The PPLv2 as well as the SPI bus is not # capable of aggregating (multiplexing) multiple instances of either # PiXtend class. Please keep this in mind when developing your application. # We suggest building one central program which creates the PiXtend object # and all other programs, functions, threads use inter-process communication # with the main program to send data to the PiXtend board to manipulate the # analog and/or digital outputs or to get information from the inputs. # ----------------------------------------------------------------------------- from __future__ import print_function # Import PiXtend V2 class from pixtendv2l import PiXtendV2L import time import sys strSlogan1 = "PiXtend Python Library v2 (PPLv2) demo." strSlogan2 = "PiXtend Python Library v2 (PPLv2) demo finished." # ----------------------------------------------------------------- # Print Art and Slogan # ----------------------------------------------------------------- print("") print(" ____ _ _ ____ __ _ _____ __") print(" / __ \\(_) |/ / /____ ____ ____/ / | | / /__ \\ / /") print(" / /_/ / /| / __/ _ \\/ __ \\/ __ / | | / /__/ / ____ / /") print(" / ____/ // / /_/ __/ / / / /_/ / | |/ // __/ /___/ / /__") print("/_/ /_//_/|_\\__/\\___/_/ /_/\\__,_/ |___//____/ /____/") print("") print(strSlogan1) print("") # ----------------------------------------------------------------- # Create instance - SPI communication starts automatically # ----------------------------------------------------------------- # PiXtend V2 -L- with DAC, Analog Output active, default/factory setting p = PiXtendV2L() # PiXtend V2 -L- with CAN-Bus active, physical jumper set from AO to CAN, # the DAC device in the PPLv2 has to be disabled. Comment out the above line # and comment in the line below to be able to use the CAN-Bus along side or # from within Python. This requires PPLv2 Version 0.1.4 or later. #p = PiXtendV2L(disable_dac=True) # ----------------------------------------------------- # Main Program # ----------------------------------------------------- if p is not None: print("Running Main Program - Hit Ctrl + C to exit") # Set some variables needed in the main loop is_config = False cycle_counter = 0 while True: try: # Check if SPI communication is running and the received data is correct if p.crc_header_in_error is False and p.crc_data_in_error is False: cycle_counter += 1 if not is_config: is_config = True print("One time configuration: Setting the relays and digital outputs in an alternating pattern") print("The value False = OFF and the value True = ON") print("") # Setting the relays and digital outputs to a pattern which can be toggled later. # Side effect: the LEDs on the PiXtend V2 -L- board alternate nicely back and forth. p.relay0 = p.ON p.relay1 = p.OFF p.relay2 = p.ON p.relay3 = p.OFF p.digital_out0 = p.ON p.digital_out1 = p.OFF p.digital_out2 = p.ON p.digital_out3 = p.OFF p.digital_out4 = p.ON p.digital_out5 = p.OFF p.digital_out6 = p.ON p.digital_out7 = p.OFF p.digital_out8 = p.ON p.digital_out9 = p.OFF p.digital_out10 = p.ON p.digital_out11 = p.OFF # clear the text on screen str_text = " \n" for i in range(0, 43, 1): str_text += " \n" str_text += " " # Print text to console print(str_text, end="\r") # Reset cursor for i in range(0, 44, 1): sys.stdout.write("\x1b[A") # Print the info text to console str_text = "Cycle No.: {0}\n".format(cycle_counter) str_text += " \n" str_text += "PiXtend V2 -L- Info:\n" str_text += "Firmware: {0}\n".format(p.firmware) str_text += "Hardware: {0}\n".format(p.hardware) str_text += "Model: {0}\n".format(chr(p.model_in)) str_text += " \n" str_text += "Digital Inputs:\n" str_text += "DigitalIn00: {0}\n".format(p.digital_in0) str_text += "DigitalIn01: {0}\n".format(p.digital_in1) str_text += "DigitalIn02: {0}\n".format(p.digital_in2) str_text += "DigitalIn03: {0}\n".format(p.digital_in3) str_text += "DigitalIn04: {0}\n".format(p.digital_in4) str_text += "DigitalIn05: {0}\n".format(p.digital_in5) str_text += "DigitalIn06: {0}\n".format(p.digital_in6) str_text += "DigitalIn07: {0}\n".format(p.digital_in7) str_text += "DigitalIn08: {0}\n".format(p.digital_in8) str_text += "DigitalIn09: {0}\n".format(p.digital_in9) str_text += "DigitalIn10: {0}\n".format(p.digital_in10) str_text += "DigitalIn11: {0}\n".format(p.digital_in11) str_text += "DigitalIn12: {0}\n".format(p.digital_in12) str_text += "DigitalIn13: {0}\n".format(p.digital_in13) str_text += "DigitalIn14: {0}\n".format(p.digital_in14) str_text += "DigitalIn15: {0}\n".format(p.digital_in15) str_text += " \n" str_text += "Digital Outputs:\n" str_text += "DigitalOut00: {0}\n".format(p.digital_out0) str_text += "DigitalOut01: {0}\n".format(p.digital_out1) str_text += "DigitalOut02: {0}\n".format(p.digital_out2) str_text += "DigitalOut03: {0}\n".format(p.digital_out3) str_text += "DigitalOut04: {0}\n".format(p.digital_out4) str_text += "DigitalOut05: {0}\n".format(p.digital_out5) str_text += "DigitalOut06: {0}\n".format(p.digital_out6) str_text += "DigitalOut07: {0}\n".format(p.digital_out7) str_text += "DigitalOut08: {0}\n".format(p.digital_out8) str_text += "DigitalOut09: {0}\n".format(p.digital_out9) str_text += "DigitalOut10: {0}\n".format(p.digital_out10) str_text += "DigitalOut11: {0}\n".format(p.digital_out11) str_text += " \n" str_text += "Relays:\n" str_text += "Relay0: {0}\n".format(p.relay0) str_text += "Relay1: {0}\n".format(p.relay1) str_text += "Relay2: {0}\n".format(p.relay2) str_text += "Relay3: {0}\n".format(p.relay3) str_text += " " # Print text to console print(str_text, end="\r") # Reset cursor for i in range(0, 44, 1): sys.stdout.write("\x1b[A") # Toggle the relays and digital outputs on and off p.relay0 = not p.relay0 p.relay1 = not p.relay1 p.relay2 = not p.relay2 p.relay3 = not p.relay3 p.digital_out0 = not p.digital_out0 p.digital_out1 = not p.digital_out1 p.digital_out2 = not p.digital_out2 p.digital_out3 = not p.digital_out3 p.digital_out4 = not p.digital_out4 p.digital_out5 = not p.digital_out5 p.digital_out6 = not p.digital_out6 p.digital_out7 = not p.digital_out7 p.digital_out8 = not p.digital_out8 p.digital_out9 = not p.digital_out9 p.digital_out10 = not p.digital_out10 p.digital_out11 = not p.digital_out11 else: for i in range(0, 45, 1): print("") print("") print("Communication error, the data from the microcontroller is not correct!") print("Leaving the application. Please check that the Raspberry Pi can communicate") print("with the microcontroller on the PiXtend V2 -L- board.") print("") p.digital_out0 = p.OFF p.digital_out1 = p.OFF p.digital_out2 = p.OFF p.digital_out3 = p.OFF p.digital_out4 = p.OFF p.digital_out5 = p.OFF p.digital_out6 = p.OFF p.digital_out7 = p.OFF p.digital_out8 = p.OFF p.digital_out9 = p.OFF p.digital_out10 = p.OFF p.digital_out11 = p.OFF p.relay0 = p.OFF p.relay1 = p.OFF p.relay2 = p.OFF p.relay3 = p.OFF time.sleep(0.25) p.close() del p p = None break # Wait some time, SPI communication will continue in the background time.sleep(1) # Catch errors and if an error is caught, leave the program except IOError as e: # Print out the caught error and leave program print ("I/O error({0}): {1}".format(e.errno, e.strerror)) p.close() time.sleep(0.25) del p p = None break except ValueError as ve: # Print out the caught error and leave program print ("Value error({0}): {1}".format(ve.errno, ve.strerror)) p.close() time.sleep(0.25) del p p = None break except RuntimeError as re: # Print out the caught error and leave program print ("Runtime error({0}): {1}".format(re.errno, re.strerror)) p.close() time.sleep(0.25) del p p = None break except KeyboardInterrupt: # Keyboard interrupt caught, Ctrl + C, now clean up and leave program for i in range(0, 45, 1): print("") print(strSlogan2) p.digital_out0 = p.OFF p.digital_out1 = p.OFF p.digital_out2 = p.OFF p.digital_out3 = p.OFF p.digital_out4 = p.OFF p.digital_out5 = p.OFF p.digital_out6 = p.OFF p.digital_out7 = p.OFF p.digital_out8 = p.OFF p.digital_out9 = p.OFF p.digital_out10 = p.OFF p.digital_out11 = p.OFF p.relay0 = p.OFF p.relay1 = p.OFF p.relay2 = p.OFF p.relay3 = p.OFF time.sleep(0.25) p.close() del p p = None break