noob questions about i2c

hey there all you brilliant coders
after spending a week figuring out my code wasn't working for lack of a semicolon, i thought i would ask the experts first before hitting my head against the wall trying to figure out i2c....
so what i want to do is take 3 analog joy stick readings from a slave arduino and send them via wire to the master unit
and hopefully export 4 sets of sensor data from the master through the slave via wire then onto my PC via usb

so far the controller looks like

int va1 = 0;
int va2 = 0;
int va3 = 0;

void setup(){
  Serial.begin(9600); 
}

void loop()
{
  
  va1 = analogRead(5); 
  va1 = map(va1, 0, 1023, 0, -180);
  va2 = analogRead(7);
  va2 = map(va2, 0, 1023, 0, 180);
  va3 = analogRead(6);
  va3 = map(va3, 0, 1023, 0, 180);
   
  Serial.print(va1);
    Serial.print(" ");
  Serial.print(va2);
    Serial.print(" ");
  Serial.print(va3);
    Serial.print(" ");
  delay(20);  
}

the masters code is rather to long for posting as a hole but the sensor values are 3 digit and can be negative value, tho that could be easily be made positives with a bit of math if sending a negative value turns out to be a pain

so what do people think?

c_batchelar:
so what do people think?

I think that this is the only question you posted.

What's the issue you're having?

You are not using I2C, you are using UART.

after spending a week figuring out my code wasn't working for lack of a semicolon

I thought it was that your code wasn't compiling for lack of a semicolon?

send 3 sets of values from a slave to master, while sending four sets of values from a master through the slave to pc

AWOL:

after spending a week figuring out my code wasn't working for lack of a semicolon

I thought it was that your code wasn't compiling for lack of a semicolon?

sorry ive pulled an all nighter and its quarter past 5 in the morning were i am i meant was

luisilva:
You are not using I2C, you are using UART.

and yes UART for the slave to computer component which i know is as easy as using the serial print functions but added to give the reasons why im sending the data

Your code seams good to me, to send 3 values through UART (serial, not I2C - I2C is other thing) to "someone else" it can be a mastar Arduino or a PC or other.
Maybe you can change this:

  Serial.print(va3);
    Serial.print(" ");

to this:

  Serial.println(va3);

This way, you will have each set of values in only one line.

luisilva:
Your code seams good to me, to send 3 values through UART (serial, not I2C - I2C is other thing) to "someone else" it can be a mastar Arduino or a PC or other.
Maybe you can change this:

  Serial.print(va3);

Serial.print(" ");




to this:


Serial.println(va3);




This way, you will have each set of values in only one line.

thanks that made things alot easier to read

so if i place this on the masters loop

{
  Wire.beginTransmission(4);
  Wire.write(temp);
  Wire.write(xaxis);
  Wire.write(yaxis);
  Wire.write(depth);
  Wire.endTransmission();
  delay(50);
}

and this on the slave

#include <Wire.h>

void setup()
{
  Wire.begin(4);                // join i2c bus with address #4
  Wire.onReceive(receiveEvent); // register event
  Serial.begin(9600);           // start serial for output
}

void loop()
{
  delay(100);
}

void receiveEvent(4)
{
  while(1 < Wire.available());
  {
    int temp = Wire.read();
    Serial.print(temp);
    Serial.print(", ");
    int xaxis = Wire.read();
    Serial.print(xaxis);
    Serial.print(", ");
    int yaxis = Wire.read();
    Serial.print(yaxis);
    Serial.print(", ")
    int depth = Wire.read();
    Serial.println(depth);
  }
}

would it receive and print each of the valuesor am i barking up the wrong tree

I don't know, I never did that, but I have this 2 examples:

MASTER send:

// Wire Master Writer
// by Nicholas Zambetti <http://www.zambetti.com>

// Demonstrates use of the Wire library
// Writes data to an I2C/TWI slave device
// Refer to the "Wire Slave Receiver" example for use with this

// Created 29 March 2006

// This example code is in the public domain.


#include <Wire.h>

void setup()
{
  Wire.begin(); // join i2c bus (address optional for master)
}

byte x = 0;

void loop()
{
  Wire.beginTransmission(4); // transmit to device #4
  Wire.write("x is ");        // sends five bytes
  Wire.write(x);              // sends one byte
  Wire.endTransmission();    // stop transmitting

  x++;
  delay(500);
}

SLAVE receive:

// Wire Slave Receiver
// by Nicholas Zambetti <http://www.zambetti.com>

// Demonstrates use of the Wire library
// Receives data as an I2C/TWI slave device
// Refer to the "Wire Master Writer" example for use with this

// Created 29 March 2006

// This example code is in the public domain.


#include <Wire.h>

void setup()
{
  Wire.begin(4);                // join i2c bus with address #4
  Wire.onReceive(receiveEvent); // register event
  Serial.begin(9600);           // start serial for output
}

void loop()
{
  delay(100);
}

// function that executes whenever data is received from master
// this function is registered as an event, see setup()
void receiveEvent(int howMany)
{
  while (1 < Wire.available()) // loop through all but the last
  {
    char c = Wire.read(); // receive byte as a character
    Serial.print(c);         // print the character
  }
  int x = Wire.read();    // receive byte as an integer
  Serial.println(x);         // print the integer
}

The main difference from your code to this code is that you "don't care about" the Wire.available(). You see that you have 1 byte to read, and then "don't careening about for that" you read 4 bytes. I think that don't makes sense.

i see what you mean so would

#include <Wire.h>

void setup()
{
  Wire.begin(4);                // join i2c bus with address #4
  Wire.onReceive(receiveEvent); // register event
  Serial.begin(9600);           // start serial for output
}

void loop()
{
  delay(100);
}

void receiveEvent()
{
  while(1 < Wire.available());
  {
    int temp = Wire.read();
    Serial.print(temp);
    Serial.print(", ");
    int xaxis = Wire.read();
    Serial.print(xaxis);
    Serial.print(", ");
    int yaxis = Wire.read();
    Serial.print(yaxis);
    Serial.print(", ")
    int depth = Wire.read();
    Serial.println(depth);
  }
}

be better for the slave?

I'm sorry, but I don't see the difference.

ok so officially completely lost, so dose any one know of an idiots guide to i2c for arduino?
something that says why you use the commands?

There is your code:

  while(1 < Wire.available());
  {
    int temp = Wire.read();
    Serial.print(temp);
    Serial.print(", ");
    int xaxis = Wire.read();
    Serial.print(xaxis);
    Serial.print(", ");
    int yaxis = Wire.read();
    Serial.print(yaxis);
    Serial.print(", ")
    int depth = Wire.read();
    Serial.println(depth);
  }

There is the code of the example:

  while (1 < Wire.available()) // loop through all but the last
  {
    char c = Wire.read(); // receive byte as a character
    Serial.print(c);         // print the character
  }
  int x = Wire.read();    // receive byte as an integer
  Serial.println(x);         // print the integer

The code of the example only receive the exact amount of bytes, because it is repeated while there are bytes to be received:

  while (1 < Wire.available()) // loop through all but the last

But you, don't care about that.
One thing even worst, that only now I see, is that you are stopping your code while you have someting to receive:

  while(1 < Wire.available());

(this ' ; ' is telling to "do nothing" while it have bytes to receive)
And then you go read all the bytes (after they are lost).

In your place, I will do something like:

void receiveEvent(int howMany)
{
  while (1 < Wire.available()) // loop through all but the last
  {
    char c = Wire.read(); // receive byte as a character
    Serial.print(c);         // print the character
    Serial.print(", ");
  }
  int x = Wire.read();    // receive byte as an integer
  Serial.println(x);         // print the integer
}

Note that you don't need to call the variables exactly what hold. It can be called c but hold one temperature, and the next time the loop repeats the same c can hold the xaxis.

ok so im about half way through a video on you tube and im beginning to see who this works better

void receiveEvent(int howMany)
{
  while (1 < Wire.available()) // loop through all but the last
  {
    char c = Wire.read(); // receive byte as a character
    Serial.print(c);         // print the character
    Serial.print(", ");
  }
  int x = Wire.read();    // receive byte as an integer
  Serial.println(x);         // print the integer
}

so this should list the data something like
23,44,55,66,88
23,44,55,66,88
23,44,55,66,88
am i correct ?

c_batchelar:
(...)
so this should list the data something like
23,44,55,66,88
23,44,55,66,88
23,44,55,66,88
am i correct ?

With spaces following the comas:
23, 44, 55, 66, 88
23, 44, 55, 66, 88
23, 44, 55, 66, 88

c_batchelar:
am i correct ?

No.

char c = Wire.read(); // receive byte as a character
Serial.print(c);         // print the character
Serial.print(", ");

You read one char at a time, and print it to the screen, followed by a comma and space.

23,44,55,66,88

Your sample has two chars and a space, so given the same code, no, that would be impossible. If c is defined as an int (or cast as one when being sent to serial print), then it's possible to have multi-character numbers, because Serial print will convert 0x17 (Decimal 23) to '2' followed by '3'.

Arrch:

c_batchelar:
am i correct ?

No.

char c = Wire.read(); // receive byte as a character

Serial.print(c);        // print the character
Serial.print(", ");




You read one char at a time, and print it to the screen, followed by a comma and space.



23,44,55,66,88




Your sample has two chars and a space, so given the same code, no, that would be impossible. If c is defined as an int (or cast as one when being sent to serial print), then it's possible to have multi-character numbers, because Serial print will convert 0x17 (Decimal 23) to '2' followed by '3'.

makes perfect sense also means all int values will need to be between 0 and 255 if im not mistaken

c_batchelar:
makes perfect sense also means all int values will need to be between 0 and 255 if im not mistaken

-128 to 127 for int
0 to 255 for unsigned int

No. Type int is a 2-byte number which runs from -32000 to +32000 ( whatever ), and unsigned int is 0 to 65000

0 to 255 is a 1-byte number.