element14 Community
element14 Community
    Register Log In
  • Site
  • Search
  • Log In Register
  • About Us
  • Community Hub
    Community Hub
    • What's New on element14
    • Feedback and Support
    • Benefits of Membership
    • Personal Blogs
    • Members Area
    • Achievement Levels
  • Learn
    Learn
    • Ask an Expert
    • eBooks
    • element14 presents
    • Learning Center
    • Tech Spotlight
    • STEM Academy
    • Webinars, Training and Events
    • Learning Groups
  • Technologies
    Technologies
    • 3D Printing
    • FPGA
    • Industrial Automation
    • Internet of Things
    • Power & Energy
    • Sensors
    • Technology Groups
  • Challenges & Projects
    Challenges & Projects
    • Design Challenges
    • element14 presents Projects
    • Project14
    • Arduino Projects
    • Raspberry Pi Projects
    • Project Groups
  • Products
    Products
    • Arduino
    • Avnet Boards Community
    • Dev Tools
    • Manufacturers
    • Multicomp Pro
    • Product Groups
    • Raspberry Pi
    • RoadTests & Reviews
  • Store
    Store
    • Visit Your Store
    • Choose another store...
      • Europe
      •  Austria (German)
      •  Belgium (Dutch, French)
      •  Bulgaria (Bulgarian)
      •  Czech Republic (Czech)
      •  Denmark (Danish)
      •  Estonia (Estonian)
      •  Finland (Finnish)
      •  France (French)
      •  Germany (German)
      •  Hungary (Hungarian)
      •  Ireland
      •  Israel
      •  Italy (Italian)
      •  Latvia (Latvian)
      •  
      •  Lithuania (Lithuanian)
      •  Netherlands (Dutch)
      •  Norway (Norwegian)
      •  Poland (Polish)
      •  Portugal (Portuguese)
      •  Romania (Romanian)
      •  Russia (Russian)
      •  Slovakia (Slovak)
      •  Slovenia (Slovenian)
      •  Spain (Spanish)
      •  Sweden (Swedish)
      •  Switzerland(German, French)
      •  Turkey (Turkish)
      •  United Kingdom
      • Asia Pacific
      •  Australia
      •  China
      •  Hong Kong
      •  India
      •  Korea (Korean)
      •  Malaysia
      •  New Zealand
      •  Philippines
      •  Singapore
      •  Taiwan
      •  Thailand (Thai)
      • Americas
      •  Brazil (Portuguese)
      •  Canada
      •  Mexico (Spanish)
      •  United States
      Can't find the country/region you're looking for? Visit our export site or find a local distributor.
  • Translate
  • Profile
  • Settings
7-Segment Display
  • Challenges & Projects
  • Project14
  • 7-Segment Display
  • More
  • Cancel
7-Segment Display
Blog Raspberry Pi Pico multicore demo using HC-SR04 ultrasonic ranger and a 4-digit 7-segment display
  • Blog
  • Forum
  • Documents
  • Polls
  • Files
  • Events
  • Mentions
  • Sub-Groups
  • Tags
  • More
  • Cancel
  • New
  • Share
  • More
  • Cancel
Group Actions
  • Group RSS
  • More
  • Cancel
Engagement
  • Author Author: BigG
  • Date Created: 28 May 2022 4:15 PM Date Created
  • Views 22670 views
  • Likes 9 likes
  • Comments 2 comments
  • ultrasonic ranger
  • hc-sr04
  • multi-core
  • raspberry pi pico
  • 7-segment display
Related
Recommended

Raspberry Pi Pico multicore demo using HC-SR04 ultrasonic ranger and a 4-digit 7-segment display

BigG
BigG
28 May 2022

Introduction

Inspired by the Pi Pico with 7-segment display blog, written by ntewinkel, I decided to give it a go as I had a 4-digit 7-segment display in box that had never been used before.

Little did I realise what's involved to get a 4-digit display to work using just a microcontroller. I have to say it's all rather clever to trick the eye like that.

Once I figure out what's involved and I had figured out whether my unknown branded display was common anode or cathode I gave it a quick test using the SevSeg library for Arduino and after a bit of trial and error it worked thanks to a bit of help from Fritzing in working out which connection was which.

image

Of course I couldn't help myself when it comes to over-complicating matters.

So it didn't take long before I reasoned that the Pico's multicore feature would provide some very useful benefits here. I just had to think of an application. Then, while thinking about what sort of multicore application I could come up with, I spotted a HC-SR04 ultrasonic ranger in another box and thought, aha, these two devices could work well together in this context as both were timing critical.

Getting it to work

After a quick search online and I found a very interesting library for the HC-SR04 ultrasonic ranger designed just for the Arduino Nano RP2040 Connect, which made use of Programmable I/O (PIO).

The library is called NanoConnectHcSr04 and can be found on GitHub: https://github.com/MrYsLab/NanoConnectHcSr04

I was eager to see if I could get this to work via Pico's Core1 processor.

At first I was not very confident as when I first tested multicore (you can read all about it in my blog) it would lock up if any delays were inserted. Well, I was rather pleased to see that this has been resolved. It actually worked.

It was now a case of merging the two examples for my test application.

To get this to work, I reasoned that as the Pico has plenty of memory and that RAM is shared between both cores, the simplest thing to do is make all variables global. This ensured static allocation of memory during runtime. I also wanted both cores to run independently so I used the non-blocking method where the main core would poll to check if data was available to read from Core 1. The result was then sent via UART to the serial monitor via the main core.

And here's the code:

/*
 Copyright (c) 2020-2021 Alan Yorinks All rights reserved (NanoConnectHcSr04 library).
 This example constantly reads and prints the distance measured by an HC-SR04 Ultrasonic distance sensor.

 This program is free software; you can redistribute it and/or
 modify it under the terms of the GNU AFFERO GENERAL PUBLIC LICENSE
 Version 3 as published by the Free Software Foundation; either
 or (at your option) any later version.
 This library is distributed in the hope that it will be useful,f
 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 receivSketch uses 82844 bytes (0%) of program storage space. Maximum is 16777216 bytes.ed a copy of the GNU AFFERO GENERAL PUBLIC LICENSE
 along with this library; if not, write to the Free Software
 Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
 
 SevSeg Library Copyright 2020 Dean Reading
 
 This example demonstrates a very simple use of the SevSeg library with a 4
 digit display. It displays a counter that counts up, showing deci-seconds.
 */


#include "pico/multicore.h"
#include "hardware/irq.h"

#include <NanoConnectHcSr04.h>
#include "SevSeg.h"

// D16 == trigger, D17 == echo
// Using pio0 and sm 0
NanoConnectHcSr04 sonar(16,17, pio0, 0); //Instantiate HR-SR04 controller object

SevSeg sevseg; //Instantiate a seven segment controller object

// distance value returned
static float c1_value = 0.0;
static float c0_value = 0.0;

static unsigned long timer = 0L;
static int deciSeconds = 0;

static byte numDigits = 4;
static byte digitPins[] = {15, 14, 13, 12};
static byte segmentPins[] = {11, 10, 19, 20, 21, 18, 22, 26};
static bool resistorsOnSegments = false; // 'false' means resistors are on digit pins
static byte hardwareConfig = COMMON_ANODE; // See README.md for options
static bool updateWithDelays = false; // Default 'false' is Recommended
static bool leadingZeros = false; // Use 'true' if you'd like to keep the leading zeros
static bool disableDecPoint = false; // Use 'true' if your decimal point doesn't exist or isn't connected

  
void core1_entry() {
    
  while (1) {
    // Function pointer is passed to us via the FIFO
    // We have one incoming int32_t as a parameter, and will provide an
    // int32_t return value by simply pushing it back on the FIFO
    // which also indicates the result is ready.

    // put your main code here, to run repeatedly:
    c1_value = sonar.readSonar();
    
    // Sanity check on values received
    if (c1_value > 0.0 && c1_value < 200.0) {
      // Send results back to core 0
      if (multicore_fifo_wready()) multicore_fifo_push_blocking(c1_value);
    }
  } 
}


void setup() {
 
  Serial.begin(115200);
  while (!Serial) {;;}
  Serial.println("\r\nPico PIO Multicore 7Segment Display SonicRanger\r\n");

  sevseg.begin(hardwareConfig, numDigits, digitPins, segmentPins, resistorsOnSegments,
  updateWithDelays, leadingZeros, disableDecPoint);
  sevseg.setBrightness(90);

  timer = millis();

  multicore_launch_core1(core1_entry);

}

void loop() {

    if (multicore_fifo_rvalid()) {

      c0_value = multicore_fifo_pop_blocking();
      Serial.println(c0_value);
      
    }
  
  if (millis() - timer >= 100) {
    timer += 100;
    deciSeconds++; // 100 milliSeconds is equal to 1 deciSecond
    
    if (deciSeconds == 10000) { // Reset to 0 after counting for 1000 seconds.
      deciSeconds=0;
    }
    sevseg.setNumber(deciSeconds, 1);
  }

  sevseg.refreshDisplay(); // Must run repeatedly
    
}

The Demo

And finally, here's the demo:

You don't have permission to edit metadata of this video.
Edit media
x
image
Upload Preview
image

Addendum: RangeFinder using 7-Segment Display

Of course it's very easy to then amend the code so that the range finder distance is displayed on the 7-segment display.

One gotcha worth mentioning is that when I commented out the while (!Serial) I discovered that I needed to add in a delay in setup otherwise core1 locked up.

void setup() {
 
  //Serial.begin(115200);
  delay(1000);
  //while (!Serial) {;;}
  //Serial.println("\r\nPico PIO Multicore 7Segment Display SonicRanger\r\n");

  sevseg.begin(hardwareConfig, numDigits, digitPins, segmentPins, resistorsOnSegments,
  updateWithDelays, leadingZeros, disableDecPoint);
  sevseg.setBrightness(90);

  //timer = millis();

  multicore_launch_core1(core1_entry);
  
}

Then to display the distance all I did was the following:

void loop() {

  if (multicore_fifo_rvalid()) {
  
    c0_value = multicore_fifo_pop_blocking();
    //Serial.println(c0_value);
    sevseg.setNumber(int(c0_value*10), 1);
  
  }
 
  sevseg.refreshDisplay(); // Must run repeatedly
    
}

It's as simple as that. And here's a short video:

You don't have permission to edit metadata of this video.
Edit media
x
image
Upload Preview
image

  • Sign in to reply
  • BigG
    BigG over 3 years ago in reply to robogary

    Thanks. Is this microPython? I'm using C++/C via Arduino IDE.

    • Cancel
    • Vote Up 0 Vote Down
    • Sign in to reply
    • More
    • Cancel
  • robogary
    robogary over 3 years ago

    Nice here is some Ping code without using a specific library.

    PingTrigger=Pin(9,Pin.OUT)
    PingEcho=Pin(8,Pin.IN)

    def Ping():
    echotries=0
    PingTrigger.low()
    utime.sleep_us(2) # note sleep_us is for microsecs
    PingTrigger.high()
    utime.sleep_us(10)
    PingTrigger.low()
    while ((PingEcho.value() == 0) and (echotries<30)):
    EchoStartTime = utime.ticks_us()
    echotries=echotries+1
    # This check bails out of the loop on a problem with a long echo or failed echo, I havent been able to prove its needed.

    while PingEcho.value()==1:
    EchoHeard = utime.ticks_us()
    PingDeltaTime=EchoHeard-EchoStartTime
    PingDistance_cm =(PingDeltaTime*.0343)/2 # sound is 343.2 m/s .0343 cm/usec
    PingDistance_in=(PingDistance_cm)/2.54
    #print ("Measured distance is ",PingDistance_cm, "cm" )
    print ("Measured distance is ",PingDistance_in, "inches" )
    #print ("Echotries =", echotries)
    return PingDistance_in

    • Cancel
    • Vote Up 0 Vote Down
    • Sign in to reply
    • More
    • Cancel
element14 Community

element14 is the first online community specifically for engineers. Connect with your peers and get expert answers to your questions.

  • Members
  • Learn
  • Technologies
  • Challenges & Projects
  • Products
  • Store
  • About Us
  • Feedback & Support
  • FAQs
  • Terms of Use
  • Privacy Policy
  • Legal and Copyright Notices
  • Sitemap
  • Cookies

An Avnet Company © 2025 Premier Farnell Limited. All Rights Reserved.

Premier Farnell Ltd, registered in England and Wales (no 00876412), registered office: Farnell House, Forge Lane, Leeds LS12 2NE.

ICP 备案号 10220084.

Follow element14

  • X
  • Facebook
  • linkedin
  • YouTube