First program help, Variables across Tabs?

Hello all,

I've been lurking for a few weeks, and I bought a Duemilanove one week ago. I've also been through a few of the tut programs and reference sections.

This is my first attempt at a program.

I've got a simple program to change a seven segment display in relation to an input pot.

I'm on my fourth rev. of this program and after many beers (thinking fluid) I've managed to clean it up from a mess of IF statements and other goofyness to a Switch statement that calls functions. I was happy....

But now I've moved my functions to another tab for clarity. Everything still worked until I began to use variables for pin names. How do you declare a global variable for multiple tabs? I thought all tabs without an extension were compiled "as one"..?

I've moved the variables from tab to tab, but still no luck.

I've searched the forum and heard terms like, "extern" and other over-my-head concepts. Should I just stay away from using tabs? I'd really like a way to make the functions portable, as they will be handy in future programs.

Also, any criticism on bad coding habits are welcomed, as I am just learning.

First Tab: (Main Program)

/******************************************************************
 * Testing analog input & mapping function
 * Testing named LED pins for portability
 
************************ SCHEMATIC *******************************
   Center leg of Pot on analog 5, Other legs on +5V & GND
   7Seg commCath wired on pins 3-9 through 500ohm R's
******************************************************************/

const int myPot = 5; // Pin number used for the POT
int potVal; // Stores value of pot reading

void setup()
{
// Set LED Pin numbers:
  const int segA = 4;
  const int segB = 3;
  const int segC = 7;
  const int segD = 8;
  const int segE = 9;
  const int segF = 5;
  const int segG = 6;

// Set output pins:
  pinMode(segA, OUTPUT);
  pinMode(segB, OUTPUT);
  pinMode(segC, OUTPUT);
  pinMode(segD, OUTPUT);
  pinMode(segE, OUTPUT);
  pinMode(segF, OUTPUT);
  pinMode(segG, OUTPUT);
}

void loop()
{
  potVal = analogRead(myPot);
  potVal = map(potVal, 0, 1000, 0, 9);

  switch (potVal){     // Call the appropriate function to display the digit.
      case 0: zero();  break;
      case 1: one();   break;
      case 2: two();   break;
      case 3: three(); break;
      case 4: four();  break;
      case 5: five();  break;
      case 6: six();   break;
      case 7: seven(); break;
      case 8: eight(); break;
      case 9: nine();  break;
    }
}                              // Wash, Rinse and repeat...

Second Tab: (Digit Functions: Does not recognize pin names)

void zero()  // Function to display # 0
{
  digitalWrite(segA, HIGH);
  digitalWrite(segB, HIGH);
  digitalWrite(segC, HIGH);
  digitalWrite(segD, HIGH);
  digitalWrite(segE, HIGH);
  digitalWrite(segF, HIGH);
  digitalWrite(segG, LOW);
}

void one()  // Function to display # 1
{
  digitalWrite(segA, LOW);
  digitalWrite(segB, HIGH);
  digitalWrite(segC, HIGH);
  digitalWrite(segD, LOW);
  digitalWrite(segE, LOW);
  digitalWrite(segF, LOW);
  digitalWrite(segG, LOW);
}
    
void two()  // Function to display # 2
{
  digitalWrite(segA, HIGH);
  digitalWrite(segB, HIGH);
  digitalWrite(segC, LOW);
  digitalWrite(segD, HIGH);
  digitalWrite(segE, HIGH);
  digitalWrite(segF, LOW);
  digitalWrite(segG, HIGH);
}

void three()  // Function to display # 3
{
  digitalWrite(segA, HIGH);
  digitalWrite(segB, HIGH);
  digitalWrite(segC, HIGH);
  digitalWrite(segD, HIGH);
  digitalWrite(segE, LOW);
  digitalWrite(segF, LOW);
  digitalWrite(segG, HIGH);
}

void four()  // Function to display # 4
{
  digitalWrite(segA, LOW);
  digitalWrite(segB, HIGH);
  digitalWrite(segC, HIGH);
  digitalWrite(segD, LOW);
  digitalWrite(segE, LOW);
  digitalWrite(segF, HIGH);
  digitalWrite(segG, HIGH);
}
  
void five()  // Function to display # 5
{
  digitalWrite(segA, HIGH);
  digitalWrite(segB, LOW);
  digitalWrite(segC, HIGH);
  digitalWrite(segD, HIGH);
  digitalWrite(segE, LOW);
  digitalWrite(segF, HIGH);
  digitalWrite(segG, HIGH);
}

void six()  // Function to display # 6
{
  digitalWrite(segA, HIGH);
  digitalWrite(segB, LOW);
  digitalWrite(segC, HIGH);
  digitalWrite(segD, HIGH);
  digitalWrite(segE, HIGH);
  digitalWrite(segF, HIGH);
  digitalWrite(segG, HIGH);
}

void seven()  // Function to display # 7
{
  digitalWrite(segA, HIGH);
  digitalWrite(segB, HIGH);
  digitalWrite(segC, HIGH);
  digitalWrite(segD, LOW);
  digitalWrite(segE, LOW);
  digitalWrite(segF, HIGH);
  digitalWrite(segG, LOW);
}

void eight()  // Function to display # 8
{
  digitalWrite(segA, HIGH);
  digitalWrite(segB, HIGH);
  digitalWrite(segC, HIGH);
  digitalWrite(segD, HIGH);
  digitalWrite(segE, HIGH);
  digitalWrite(segF, HIGH);
  digitalWrite(segG, HIGH);
}

void nine()  // Function to display # 9
{
  digitalWrite(segA, HIGH);
  digitalWrite(segB, HIGH);
  digitalWrite(segC, HIGH);
  digitalWrite(segD, HIGH);
  digitalWrite(segE, LOW);
  digitalWrite(segF, HIGH);
  digitalWrite(segG, HIGH);  
}

On the other tabs, you need to declare (but not value) the global variable, using the extern keyword, which says that the actual memory for this variable is declared in an external function.

Thanks for the quick response!

I'm still lost on using "extern". Where can I go to research this as it is not in the reference?

Google?

Any C book will describe the keyword.

It's just placed in front of the declaration of a variable:

extern int whatever;

Brilliant!

I changed:

const int segA = 4;         //<---Old Code
extern const int segA = 4; //<---New Code

(For each segment) in the main tab outside of setup().

Now the functions tab is able to use it.

I love it when a plan comes together! I now can control an LED display with a knob...world domination coming soon!!!

Thanks PaulS.

Actually its enough to just declare
const int segA = 4;
in the first module

then in the other module(s) you declare:

extern const int segA; // without the =4 part

The whole purpose of the extern keyword is to tell the compiler of the second module that segA is an integer constant that. has memory space allocated for it somewhere else.

This is interesting. I've so far avoided using multiple tabs. Where will the additional tab's contents be saved? I assume in the same folder as the main tab is (Which would require copying those files to other application folders for reusing)?
How about using the #include directive? Couldn't that be used to avoid using the extern keyword on every variable then?

Aftersome expirimenting, I found the extern keyword was not needed in this case after all. Rookie mistake: I defined the constants in the setup function.

When I moved them outside all functions, the second tab used them as normal with no extern needed.

Here's an example:

TAB 1:

/**************************************************
 * Testing multi-tab variables
 **************************************************/

const int myPin = 13;

void setup()
{
  pinMode(myPin, OUTPUT);
}

void loop()
{
  myFunction();
}

TAB 2:

void myFunction()
{
  digitalWrite(myPin, HIGH);
  delay(250);
  digitalWrite(myPin, LOW);
  delay(250);
}

Raron: A new pde file is added in your program folder for every tab.