Question about running motors and printing to screen

Hello, I’ve just finished setting up a basic motor control circuit (2 Unos - one has a RF24 radio and a controller, the other has another RF24 and a L298 motor driver with 2 motors connected).

everything is set up correctly, and the code works, but something weird has happened.
this is the code for the motor operating Uno:

#include <nRF24L01.h>
#include <printf.h>
#include <RF24.h>
#include <RF24_config.h>
#include <SPI.h>

RF24 radio(7, 8);
byte addresses[][6] = {"1Node", "2Node"};

#define ENA 2
#define ENB 4
#define IN1 3
#define IN2 5
#define IN3 6
#define IN4 9

void setup() {
  radio.begin();
  radio.setPALevel(RF24_PA_LOW);
  radio.openWritingPipe(addresses[0]);
  radio.openReadingPipe(1, addresses[1]);

  motorBegin();

  Serial.begin(9600);
}

void loop() {
  
  char package = getPackage(); //recieve data transmission
  char in1, in2, in3, in4;
  Unpack(package,&in1,&in2,&in3,&in4); //decode the data pack into the corresponding variables

// print to screen //
  Serial.print("in1 = ");
  Serial.print(int(in1));
  Serial.print("   in2 = ");
  Serial.print(int(in2));
  Serial.print("   in3 = ");
  Serial.print(int(in3));
  Serial.print("   in4 = ");
  Serial.println(int(in4));


  OperateMotors(in1,in2,in3,in4);
}

void motorBegin(){
  pinMode(ENA,OUTPUT);
  pinMode(ENB,OUTPUT);
  pinMode(IN1,OUTPUT);
  pinMode(IN2,OUTPUT);
  pinMode(IN3,OUTPUT);
  pinMode(IN4,OUTPUT);  

  digitalWrite(ENA,HIGH);
  digitalWrite(ENB,HIGH);
}

char getPackage() {
  char package = 0;
  radio.startListening();

  if (radio.available()) {
    while (radio.available()) {                                   // While there is data ready
      radio.read( &package, sizeof(package) );
    }

    radio.stopListening();                                        // First, stop listening so we can talk
    radio.write( package, sizeof(package) );                      // Send the final one back.
    radio.startListening();
  }

  return package;
}

void Unpack(char package, char* in1, char* in2, char* in3, char* in4){
  *in4 = package/8;
  package -= *in4*8;
  *in3 = package/4;
  package -= *in3*4;
  *in2 = package/2;
  package -= *in2*2;
  *in1 = package;  
  return;
}

void OperateMotors(int in1, int in2, int in3, int in4){
  if(in1 == 1) digitalWrite(IN1,HIGH);
  if(in1 == 0) digitalWrite(IN1,LOW);

  if(in2 == 1) digitalWrite(IN2,HIGH);
  if(in2 == 0) digitalWrite(IN2,LOW);

  if(in3 == 1) digitalWrite(IN3,HIGH);
  if(in3 == 0) digitalWrite(IN3,LOW);

  if(in4 == 1) digitalWrite(IN4,HIGH);
  if(in4 == 0) digitalWrite(IN4,LOW);
  
}

when this code runs - everything is well - the motors turn as expected, but, if i erase the “print to screen” part (or the “Serial.begin(9600)” line) - the motors seem to run on a very small current, not enough to move. (if i erase the print to screen partially the motors seem to get a part of the current).

why does this happen? what’s the connection between a serial print and the current sent to the motors?

thanks!

Edit your post and put code tags (</> icon) around the code to format it correctly and get rid of the smiley

Did you read this before posting a programming question ?

I did, must've missed that part :o
anyway, thanks for comment, fixed it now

I suspect this line

  char package = getPackage(); //recieve data transmission

returns 0 if there is no message - which will be most of the time. And the Print statements are acting as a short (but important) delay in the repetition of loop() which allows time for a message to arrive.

You should arrange your code so that the values for the motors remain unchanged when no message is received.

...R
Simple nRF24L01+ Tutorial

thanks a lot!
this answer, however, raises the question of how do i tell the difference between "no message" and "stop".
(is it even possible in my current situation when i'm using a single thumb joystick to control both motors?)

FlameBlade:
this answer, however, raises the question of how do i tell the difference between "no message" and "stop".

The way I do it is I send a message at regular intervals (maybe 10 times per second) even if the data does not change.

On the receiving side I have a timer and if no message arrives for (say) 1 second (i.e. 10 messages are missed) the program knows that there has been a communication failure.

...R

Robin2:
The way I do it is I send a message at regular intervals (maybe 10 times per second) even if the data does not change.

On the receiving side I have a timer and if no message arrives for (say) 1 second (i.e. 10 messages are missed) the program knows that there has been a communication failure.

...R

That's a good solution, but the reason i erased those lines in the first place was that i wanted to optimize the response time between the command and the execution.

But it did give me the idea - if the problem is that getPackage() returns too many '0', because it is called at a much higher rate than the transmitter is sending data, why not wait for the data?
so i changed the reading function from this:

if (radio.available()) {
    while (radio.available()) {                                   // While there is data ready
      radio.read( &package, sizeof(package) );
    }
}

to this:

while (!radio.available()) {}
    while (radio.available()) {                                   // While there is data ready
      radio.read( &package, sizeof(package) );
    }

It seems to have solved the problem, so many thanks for the help!
(BTW - if you have any idea of how to further optimize this delay time i'd love to hear it)[/code][/code]

void Unpack(char package, char* in1, char* in2, char* in3, char* in4){

You should read up on pass-by-reference. A function that uses pass-by-reference looks a whole lot neater, and accomplishes the same thing as passing a bunch of pointers.