<jupyter_start><jupyter_text>@Copyright (C): 2010-2019, Shenzhen Yahboom Tech  @Author: Malloy.Yuan  @Date: 2019-07-17 10:10:02  @LastEditors: Malloy.Yuan  @LastEditTime: 2019-09-17 17:54:19    Handle Control CarIn this example, we will remotely control Jetbot using a gamepad controller connected to the web browser machine.  Create Handle controllerFirst, we need to create an instance of the 'Controller' widget, which we will use to drive our Jetbot. The "Controller" widget accepts an "index" parameter that specifies the number of controllers.1. Open [http://html5gamepad.com](http://html5gamepad.com).  2. If you press the button of the handle you are using3. Record the corresponding index number that pops up when you press the buttonNext, we will use this index to create and display the controller.<jupyter_code>import ipywidgets.widgets as widgets
controller = widgets.Controller(index=0)  #Replace with the index number of the controller you just tested
display(controller)<jupyter_output><empty_output><jupyter_text>Import some module<jupyter_code>#Import function library path
from servoserial import ServoSerial
from jetbot import Robot
import traitlets
from jetbot import Camera
from jetbot import bgr8_to_jpeg
from jetbot import Heartbeat
import threading
import time
# Thread function operation library
import inspect
import ctypes

import traitlets
from IPython.display import display
from jetbot import Camera, bgr8_to_jpeg
import os
from uuid import uuid1<jupyter_output><empty_output><jupyter_text>Create and open a display camera initialization instance<jupyter_code>camera = Camera.instance(width=224, height=224)
image = widgets.Image(format='jpeg', width=224, height=224)  # this width and height doesn't necessarily have to match the camera
camera_link = traitlets.dlink((camera, 'value'), (image, 'value'), transform=bgr8_to_jpeg)
display(image)<jupyter_output><empty_output><jupyter_text>Add heartbeat connection<jupyter_code>def handle_heartbeat_status(change):
    if change['new'] == Heartbeat.Status.dead:
        camera_link.unlink()
        robot.stop()

heartbeat = Heartbeat(period=0.5)
# Append the callback function to the heartbeat state
heartbeat.observe(handle_heartbeat_status, names='status')<jupyter_output><empty_output><jupyter_text>Create a method to actively stop the process<jupyter_code>def _async_raise(tid, exctype):
    """raises the exception, performs cleanup if needed"""
    tid = ctypes.c_long(tid)
    if not inspect.isclass(exctype):
        exctype = type(exctype)
    res = ctypes.pythonapi.PyThreadState_SetAsyncExc(tid, ctypes.py_object(exctype))
    if res == 0:
        raise ValueError("invalid thread id")
    elif res != 1:
        # """if it returns a number greater than one, you're in trouble,
        # and you should call it again with exc=NULL to revert the effect"""
        ctypes.pythonapi.PyThreadState_SetAsyncExc(tid, None)
        
def stop_thread(thread):
    _async_raise(thread.ident, SystemExit)<jupyter_output><empty_output><jupyter_text>Method for creating up, down, left, and right movements of a PTZ camera separately<jupyter_code>'''Servo Part'''
servo_device = ServoSerial() 
def camUpFunction():
    global updownpulse
    updownpulse+=15
    if updownpulse>4095:
        updownpulse=4095
    servo_device.Servo_serial_control(2, updownpulse)

def camDownFunction():
    global updownpulse
    updownpulse-=15
    if updownpulse<1300:
        updownpulse=1300
    servo_device.Servo_serial_control(2, updownpulse)

def camLeftFunction():
    global leftrightpulse
    leftrightpulse+=15
    if leftrightpulse>3600:
        leftrightpulse=3600
    servo_device.Servo_serial_control(1, leftrightpulse)

def camRightFunction():
    global leftrightpulse
    leftrightpulse-=15
    if leftrightpulse<600:
        leftrightpulse=600
    servo_device.Servo_serial_control(1, leftrightpulse)

def camservoInitFunction():
    global leftrightpulse, updownpulse
    leftrightpulse = 2048
    updownpulse = 2048
    servo_device.Servo_serial_control(1, 2048)
    time.sleep(0.1)
    servo_device.Servo_serial_control(2, 2048)<jupyter_output><empty_output><jupyter_text>Initialize the position of the PTZ cameraRun the following cell code to initialize the PTZ project to the initial location<jupyter_code>camservoInitFunction()<jupyter_output><empty_output><jupyter_text>Load the Robot classThis class allows us to easily control the JetBot motor<jupyter_code>robot = Robot()<jupyter_output><empty_output><jupyter_text>Create onboard breathing light method<jupyter_code>def BLN_Onboard():
    global i , k
    i = k = 0
    while True:
        if k == 0:
            robot.set_bln(i)
            i += 0.01
            if( i >= 1 ):
                k = 1
            time.sleep(0.005)
        elif k == 1:
            robot.set_bln(i)
            i -=0.01
            if i <= 0 :
                k = 0
            time.sleep(0.005)<jupyter_output><empty_output><jupyter_text>Turn on the onboard breathing light independent process by running the cell code below<jupyter_code>thread1 = threading.Thread(target=BLN_Onboard)
# thread1.setDaemon(True)
thread1.start()<jupyter_output><empty_output><jupyter_text>Create a handle to control the movement of Jetbot in real time Please use the ANOLOG button in the middle of the handle to switch to the simulation mode before using.Program features:          1. Left rocker control Jetbot movement, right rocker control the servo movement          2. Press the SELECT button to reset the PTZ angle          3. Press the L side button No.1 to control the PTZ rise, press the L side button No.2 to control the gimbal decline.In the default code, the Yahboom handle is used by default. For other handles, please refer to the key table to change the value.          If you are using Yahboom accessory, please use the code section ---1     If you are using the Xbox360's handle, please use the code section ---2<jupyter_code>def jetbot_motion():
    count1 = count2 = count3 = count4 =  count5 = 0
    while 1:
        #Robot car Left and right DC motor
        #Handle control code---1(Jetbot Yahboom handle)
        #Yahboom Rocker reset value is 0.0039,
        #In order to prevent the motor from being abnormal, the following code is added to operate.
        if controller.axes[1].value <= 0.1:
            if (controller.axes[0].value <= 0.1 and controller.axes[0].value >= -0.1 
                and controller.axes[1].value <= 0.1 and controller.axes[1].value >= -0.1):
                robot.stop()
            else:
                robot.set_motors(-controller.axes[1].value + controller.axes[0].value, -controller.axes[1].value - controller.axes[0].value)
            
            time.sleep(0.01)
        else:
            robot.set_motors(-controller.axes[1].value - controller.axes[0].value, -controller.axes[1].value + controller.axes[0].value)
            time.sleep(0.01)
          #Handle control code---2(Xbox360手柄)
#         if controller.axes[1].value <= 0:
#             robot.set_motors(-controller.axes[1].value + controller.axes[0].value, -controller.axes[1].value - controller.axes[0].value)
#             time.sleep(0.01)
#         else:
#             robot.set_motors(-controller.axes[1].value - controller.axes[0].value, -controller.axes[1].value + controller.axes[0].value)
#             time.sleep(0.01)

        #Servo control camera up and down 
        if controller.axes[2].value == 1:
            count1  += 1
            if count1 >= 3:
                camDownFunction()
                count1 = 0
        elif controller.axes[2].value == -1:
            count1  += 1
            if count1 >= 3:
                camUpFunction()
                count1 = 0
        else:
            count1 = 0
        #Servo control camera left and right
        if controller.axes[5].value == 1:
            count2  += 1
            if count2 >= 3:
                camRightFunction()
                count2 = 0
        elif controller.axes[5].value == -1:
            count2  += 1
            if count2 >= 3:
                camLeftFunction()
                count2 = 0
        else:
            count2 = 0
        #Servo control camera up down, left and right is reset
        if controller.buttons[8].value == True:
            count3 += 1
            if count3 >= 3:
                camservoInitFunction()
                count3 = 0
        else:
            count3 = 0
        
        #Servo control servo rise and decline
        if controller.buttons[6].value == True:
            count4 += 1
            if count4 >= 3:
                robot.set_vertical_motors(1)
                count4 = 0
        elif controller.buttons[4].value == True:
            count4 += 1
            if count4 >= 3:
                robot.set_vertical_motors(-1)
                count4 = 0
        else:
            robot.set_vertical_motors(0)
            count4 = 0<jupyter_output><empty_output><jupyter_text>Control the independent process of Jetbot motion in real time by running the cell code below to open the handle<jupyter_code>thread2 = threading.Thread(target=jetbot_motion)
thread2.setDaemon(True)
thread2.start()<jupyter_output><empty_output><jupyter_text>Ending onboard breathing RGB process<jupyter_code>stop_thread(thread1)<jupyter_output><empty_output><jupyter_text>Ending Jetbot movement process<jupyter_code>stop_thread(thread2)
robot.stop()<jupyter_output><empty_output>
{'fraction_non_alphanumeric': 0.08721980240093488, 'fraction_numerical': 0.030702220333581217, 'mean_word_length': 2.9872935196950445, 'pattern_counts': {'":': 0, '<': 64, '<?xml version=': 0, '>': 69, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'chain_length': '14', 'dir': 'jupyter-structured-clean-dedup', 'id': '588053', 'license': 'MIT', 'n_tokens_mistral': 3061, 'n_tokens_neox': 2785, 'n_words': 812, 'path': 'notebooks/10.Using of Handle/Handle control.ipynb', 'repo_name': 'Hoehlenbaer/jetbot', 'size': '9413'}