EV3 – minifig inventory

Este artigo é a parte 2 de 2 da série  EV3 and Chromecast

Now that communication with the Chromecast is working let’s make a small game with the few parts that I have in my “holiday bag”:

I’m using the LEGO Dimensions Toy Pad to read the NFC tags. I already scanned the ID’s of a blue and an orange tag and saved two JPEG images of the Frenchman LEGO minifigure and also the Invisible Woman (sorry, only had one minifig with me these holydays) on the web server folder so each time one of these NFC tags is recognized it’s JPEG image is presented on the TV.

The code is based on my tutorial for the using the LEGO Dimensions Toy Pad with ev3dev, I just updated it to work with Python 3:


#!/usr/bin/python3

import usb.core
import usb.util
from time import sleep
import pychromecast

TOYPAD_INIT = [0x55, 0x0f, 0xb0, 0x01, 0x28, 0x63, 0x29, 0x20, 0x4c, 0x45, 0x47, 0x4f, 0x20, 0x32, 0x30, 0x31, 0x34, 0xf7, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00]

OFF   = [0,0,0]
RED   = [255,0,0]
GREEN = [0,255,0]
BLUE  = [0,0,255]
ORANGE= [255,30,0]

ALL_PADS   = 0
CENTER_PAD = 1
LEFT_PAD   = 2
RIGHT_PAD  = 3

# Actions
TAG_INSERTED = 0
TAG_REMOVED  = 1

# UIDs can be retrieved with Android App (most probably in hexadecimal)
bluetag = (4, 77, 198, 218, 162, 64, 129)         # a Blue Tag from LEGO Dimensions
orangetag = (4, 91, 182, 122, 177, 73, 129)       # an Orange Tag from LEGO Dimensions

DELAY_PLAY = 1.75     # 1.5 NOT OK

def init_usb():
    global dev

    dev = usb.core.find(idVendor=0x0e6f, idProduct=0x0241)

    if dev is None:
        print('Device not found')
    else:
        print('Device found:')
        if dev.is_kernel_driver_active(0):
            dev.detach_kernel_driver(0)

        print(usb.util.get_string(dev, dev.iProduct))

        dev.set_configuration()
        dev.write(1,TOYPAD_INIT)

    return dev


def send_command(dev,command):

    # calculate checksum
    checksum = 0
    for word in command:
        checksum = checksum + word
        if checksum >= 256:
            checksum -= 256
        message = command+[checksum]

    # pad message
    while(len(message) < 32):
        message.append(0x00)

    # send message
    dev.write(1, message)

    return


def switch_pad(pad, colour):
    send_command(dev,[0x55, 0x06, 0xc0, 0x02, pad, colour[0], colour[1], colour[2],])
    return


def uid_compare(uid1, uid2):
    match = True
    for i in range(0,7):
        if (uid1[i] != uid2[i]) :
            match = False
    return match 


def main():

    # init chromecast
    chromecasts = pychromecast.get_chromecasts()
    cast = next(cc for cc in chromecasts if cc.device.friendly_name == "NOMAD")
    cast.wait()
    mc = cast.media_controller
    print("Blacking chromecast...")
    mc.play_media('http://192.168.43.104:3000/black.png', 'image/png')

    result=init_usb()
    # print(result)
    if dev != None :
        print('Running...')
        mc.stop()
        mc.play_media('http://192.168.43.104:3000/presentminifig.png', 'image/png')
        print('Present a minifg')

        while True:
            try:
                in_packet = dev.read(0x81, 32, timeout = 10)
                bytelist = list(in_packet)

                if not bytelist:
                    pass
                elif bytelist[0] != 0x56: # NFC packets start with 0x56
                    pass
                else:
                    pad_num = bytelist[2]
                    uid_bytes = bytelist[6:13]
#                    print(uid_bytes)
                    match_orange = uid_compare(uid_bytes, orangetag)
                    match_blue = uid_compare(uid_bytes, bluetag)

                    action = bytelist[5]
                    if action == TAG_INSERTED :
                        if match_orange:
                            switch_pad(pad_num, ORANGE)
                            mc.play_media('http://192.168.43.104:3000/french-man-2.png', 'image/png')
                        elif match_blue:
                            mc.play_media('http://192.168.43.104:3000/invisible-woman-2b.png', 'image/png')
                            switch_pad(pad_num, BLUE)
                        else:
                            # some other tag
                            switch_pad(pad_num, GREEN)
                    else:
                        # some tag removed
                        switch_pad(pad_num, OFF)
                        mc.stop()
                        # sleep(1)
                        mc.play_media('http://192.168.43.104:3000/presentminifig.png', 'image/png')
                        sleep(DELAY_PLAY)

            except usb.USBError:
                pass

        switch_pad(ALL_PADS,OFF)
    return

if __name__ == '__main__':
    main()
  

You probably need to install pyusb for python3. With Ubuntu I just needed

sudo apt install python3-usb

but it is not available for Debian Jessie so

sudo pip3 install pyusb --pre

(ev3dev is changing to Debian Stretch that also has python3-usb)