RPC Failure between RT1062 and Arduino Mega through Logic Level Shifter

Hi! We have been trying to connect an Arduino Mega and the RT1062 using serial communication (TX/RX) and although we have checked and double checked the connections the OpenMV IDE camera stops (signifying a lack of communication).

We know the Arduino Mega operates at 5V and the camera at 3.3V which is why we have been using a Logic Level Shifter (https://mm.digikey.com/Volume0/opasdata/d220001/medias/docus/1854/Bi-Directional-Logic-Level_HookupGuide.pdf)

We previously go


t it working with a 3.3V Arduino but decided to use the Mega due to issues with that arduino.

Attached are some images of our circuit at the level shifter. Any help is appreciated. Let me know what else I should upload to help identify the problem.

What’s your baud rate? Level shifters like that one can’t handle a high baud rate. You can make it run faster by lowering the pull up resistor values.

Our Baud Rate is 115200; we obtained this value from other OpenMV RT1062 V5 forums and the RPC examples in Arduino/OpenMV IDE.

Does the Level Shifter have the pull up resistors built in or do we have to include them in our circuit. If we have to include them, what are some optimal values?

Can you post a picture of the circuit in schematic form? I can’t tell from the picture of your breadboard.

Anyway, otherwise, try lowering the baud rate to 19200 on both the Arduino and OpenMV Cam.

Yes, the level shifter has pull up resistors, they are just kind of large at 10K.

Ill also mention that we have various other components connected to the same ground.

Use the 3.3V from the camera, not the Arduino. Otherwise, looks right, probably the baud rate is too high.

We tried changing the baud rate and also used 3.3V from the camera, but it still does not work.

I am attaching the code from the Arduino and the OpenMV cam just in case that might be the issue.

Sometimes when we connect the camera we get random letters or numbers, like D or 5 in the Arduino Serial monitor when we are expecting 1 or 0. In addition, while we get those random results the camera doesnt react.

ARDUINO IDE:


#include <openmvrpc.h>

openmv::rpc_scratch_buffer<256> scratch_buffer; 

//openmv::rpc_hardware_serial1_uart_master interface(19200); // Removed; trying UART 3 to see if the pins are damaged

openmv::rpc_hardware_serial3_uart_master interface(19200);

int find_patient()
{   //Color Tracking Thresholds (L Min, L Max, A Min, A Max, B Min, B Max)
    int8_t color_thresholds[6] = {0, 100, 12, 127, -6, 64}; // generic_red_thresholds
    uint8_t status = 0;  // initializes variable as BYTE; 0 (no detection) or 1 (detection)
    struct { uint16_t cx, cy; } find_red_rectangle_result;
    if (interface.call(F("find_red_rectangle"), color_thresholds, sizeof(color_thresholds), &status, sizeof(status))) {
        if (status==0){
          return 0;
        }else if (status==1){
          return 1;
        }
    }
}

void loop(){
  int status = find_patient(); //FUNCTION CALL
  Serial.println(status);
}

/////////////////////////////////

OPENMV IDE:


import sensor, struct
import time

sensor.reset()
sensor.set_pixformat(sensor.RGB565)
sensor.set_framesize(sensor.QVGA)
sensor.skip_frames(time=2000)
sensor.set_auto_whitebal(False)

clock = time.clock()

import rpc

# uart = UART(baudrate=115200, uart_port=1)
interface = rpc.rpc_uart_slave(baudrate=19200,uart_port=1)


# Function creates a drawing around the identified object.
def draw_detections(img, dects):
    for d in dects:
        c = d.corners()
        l = len(c)
        for i in range(l):
            img.draw_line(c[(i + 0) % l] + c[(i + 1) % l], color=(0, 255, 0))
        img.draw_rectangle(d.rect(), color=(255, 0, 0))

# Function for finding rectangle
def find_rectangle():
    while True:
        clock.tick()
        img = sensor.snapshot()

        # threshold below should be set to a high enough value to filter out noise
        # rectangles detected in the image which have low edge magnitudes. Rectangles
        # have larger edge magnitudes the larger and more contrasty they are...

        for r in img.find_rects(threshold=25000):
            img.draw_rectangle(r.rect(), color=(255, 0, 0))
            for p in r.corners():
                img.draw_circle(p[0], p[1], 5, color=(0, 255, 0))
            print(r)

        print("FPS %f" % clock.fps())

# Function for identifying red rectangle
def find_red_rectangle(data):
    sensor.set_pixformat(sensor.RGB565)
    sensor.set_framesize(sensor.QVGA)
    thresholds = struct.unpack("<bbbbbb", data)
    blobs = sensor.snapshot().find_blobs(
        [thresholds], pixels_threshold=500, area_threshold=500, merge=True, margin=20
    )
    if not blobs:
        #return bytes()  # No detections.
        return b'\x00'  # Means "no detection"
    for b in blobs:
        sensor.get_fb().draw_rectangle(b.rect(), color=(255, 0, 0))
        sensor.get_fb().draw_cross(b.cx(), b.cy(), color=(0, 255, 0))
    #out_blob = max(blobs, key=lambda b: b.density())
    #return struct.pack("<HH", out_blob.cx(), out_blob.cy())
    return b'\x01'  # Detection found

# Register callback with function ID 0
interface.register_callback(find_red_rectangle)

# Start the interface loop (blocking — handles commands from Arduino)
interface.loop()

I noticed you were missing:


void setup(){
  interface.begin();
}

In your posted Arduino script.

As for the baud rate, that needs to stay at 115200, 19200 is too slow and causes the timeouts to break in the protocol and link up won’t happen. I apologize for suggesting that. Tested it myself and saw the issue.

Things seem to work if you just put a series 1k resistor between rx and tx each way.

I tried a level shifter out with 1K pull up resistors and that worked too. 10k pull ups also.

Note, I replicated your setup with an Arduino Mega and the RT1062 using the code above.

1 Like

Thank you so much! We will try it, and keep in touch! Hope we dont have to bother you anymore, this project is due in 8 hours and we have been working on it for more than a month.