New to Arduino, is this feasible?

I've spent the day watching videos and reading info and I think an Arduino can do what I'm trying to do but before I spend too much time learning I'm hoping someone can give me a thumbs up or down on it. I am designing an automatic parts loader for a machine at work that will mostly be operated by pneumatics. We currently do this kind of thing with plc's supplied and programmed by an outside vendor and the cost of our last couple of projects went way over budget because of this. I'm hoping using an Arduino and learning the programming will be a viable alternative.

I need to:

  1. Send 12 volt signal to solenoid valve A which extends air cylinder A
  2. Read a completed circuit from switch at the end of Cylinder A travel
  3. Send 12 volt signal to solenoid valve B which extends air cylinder B
  4. Wait a set time (1 to 3 seconds) to allow cylinder B to extend
  5. Send 12 volt signal to solenoid valve C which begins the machine cycle
  6. Shut off 12 volts to solenoids A & B (either simultaneously or sequentially)
  7. Wait a set time (approx. 5 seconds) then shut off 12 volts to solenoid C
  8. Send 12 volt signal to solenoid valve D which extends air cylinder D
  9. Wait a set time (1-3 seconds) and then shut off 12 volts to solenoid D
  10. Wait a set time (1-3 seconds) then loop back to beginning and continue.

I would also need a way to tie in a start and stop switch.

So, A) can it be done with an Arduino? I've done enough searching to know that it can operate solenoids via relays or transistors but I don't know if it's possible to do the sequencing and timing that I will need.

B) What would be the recommended hardware for this project?

Thank you very much for your assistance!

Yes the Arduino can do this. I have a slightly similar project controlling 3 12v or 24v solenoid valves. My project creates water drops but the principle is the same.

When to start and stop the valves is totally up to you through the software.

As you have already found out you need to use relays or transistors between the Arduino and the valves. Transistors will work a little faster than relays but depending on the application this may not be important to you.

Thank you for the reply. After some further research I found a link on the forum to these:

http://www.ebay.com/itm/-/120771738406?

Seems like an inexpensive way to keep my soldering time to a minimum. I guess it's time to dive in and start learning the programming! Oh, the Uno has 14 in/out pins which seems like way more than I will need even if I add some bells and whistles, is there any reasom to jump up to the mega?

BTW....Very cool photos!

Have a look at planning and implementing a program. As well as program organization it shows how to manage time using millis()

The fact that you have a clear set of steps in your Original Post is a very good starting point.

...R

Written for a Arduino Mega using 1 8 relay card HL-58S and a single relay card. Need to check the logic on the single relay card but the HL-58S uses outputs driven LOW to activate the relays. The relays are good for about 10 Amps. Debounce on the start button. Stop should be HIGH to run. Use 10K resistors for pull down on your switches. This should run for about a month before it needs to be reset due to millis() overflow.
No promise but it should work. Keep your finger clear.
The single relay is for powering the relay card of 8 due to a LOW signal makes the active. You don't want it to start moving when you power it up.

// set pin configuration
const int SolRelayA        = 22;   // Relay A
const int SolRelayB        = 24;   // Relay B
const int SolRelayC        = 26;   // Relay C
const int SolRelayD        = 28;   // Relay D
const int SafetyRelay      = 32;   // Safety single Relay.
const int StopButton       = 34;   // Normally closed push pull switch
const int LimitSwitchA     = 36;   // Normally open limit switch
const int StartButton       = 34;   // Normally closed push pull switch
int StartButtonState       = LOW;  // Start Button Not Pressed
int LastStartButtonState   = LOW;  // Start Button Not Pressed
int StopButtonState        = LOW; // Stop Button is in Stopped Position ?
int LimitState             = LOW;  // Limit of Cylinder A not reached
int CycleStage             = 0;
int MachineRun             = LOW;
int StartButtonRead;
unsigned long CycleTime1;
unsigned long CycleTime2;
unsigned long CycleTime3;
unsigned long CycleTime4;
unsigned long lastDebounceTime;
unsigned long Time;
unsigned long Interval;
unsigned long debounceDelay;
void setup() {
  pinMode (SolRelayA,      OUTPUT); // Set the pins and relay states
  digitalWrite (SolRelayA,   HIGH); // Before setting the pin and state
  pinMode (SolRelayB,      OUTPUT); // Of the safety relay so when relay board
  digitalWrite (SolRelayB,   HIGH); // is powered relays are in their proper
  pinMode (SolRelayC,      OUTPUT); // state.
  digitalWrite (SolRelayC,   HIGH);
  pinMode (SolRelayD,      OUTPUT);
  digitalWrite (SolRelayD,   HIGH);
  pinMode (SafetyRelay,    OUTPUT); // Will provide VCC to JDVcc connection
  digitalWrite (SafetyRelay, HIGH); // on relay board for safety
  digitalWrite (SolRelayA,   HIGH);  pinMode (SafetyRelay, OUTPUT);
  pinMode (LimitSwitchA,    INPUT);
  pinMode (StartButton,     INPUT);
  pinMode (StopButton,      INPUT);
}
void loop() {
  // put your main code here, to run repeatedly:
  StopButtonState = digitalRead(StopButton);
  if (StopButtonState == HIGH) {
    int StartButtonRead = digitalRead(StartButton);
    if (StartButtonRead != LastStartButtonState) {
      lastDebounceTime = millis();
    }
    if ((millis() - lastDebounceTime) > debounceDelay) {
      if (StartButtonRead != StartButtonState) {
        StartButtonState = StartButtonRead;
        if (StartButtonState == HIGH) {
          MachineRun = HIGH;
        }
      }
    }
  }
  if (MachineRun == HIGH) {
    // Stage 0
    if (CycleStage == 0) {
      digitalWrite (SolRelayA, LOW); // Starts the cylinder A
      // signal to solenoid valve A which extends air cylinder A
      int LimitSwitchAState = digitalRead (LimitSwitchA);
      if (LimitSwitchAState = HIGH) {
 //Read a completed circuit from switch at the end of Cylinder A travel
        digitalWrite (SolRelayB,   LOW); // Starts the cylinder B
        // signal to solenoid valve B which extends air cylinder B
        CycleTime1 = millis() + 3000;
        CycleStage = CycleStage + 1;
      }
    }
    // Stage 1
    if (CycleStage == 1) {
// Wait a set time (3 seconds) to allow cylinder B to extend
      if (CycleTime1 >= millis()) {
// signal to solenoid valve C which begins the machine cycle
        digitalWrite (SolRelayC, LOW); //Starts C
// Shut off 12 volts to solenoids A & B 
        digitalWrite (SolRelayA, HIGH);//Stops A
        digitalWrite (SolRelayB, HIGH);//Stops B
        CycleStage = CycleStage + 1;
        CycleTime2 = millis() + 5000;

      }
    }
    if (CycleStage == 3) {       //Start Cycle 3
// Wait a set time (approx. 5 seconds) then shut off 12 volts to solenoid C
     if (CycleTime2 >= millis()) {
        digitalWrite (SolRelayC, HIGH); //Stops C
// signal to solenoid valve D which extends air cylinder D
        digitalWrite (SolRelayD, LOW); //Starts D
        CycleStage = CycleStage + 1;
        CycleTime3 = millis() + 3000;

      }
    }
    if (CycleStage == 4) {       //Start Cycle 4
      if (CycleTime3 >= millis()) {
// Wait a set time (3 seconds) and then shut off  solenoid D
        digitalWrite (SolRelayD, HIGH); //Stops D
        CycleStage = CycleStage + 1;
        CycleTime4 = millis() + 3000;


      }
    }
 // Wait a set time (3 seconds) then loop back to beginning and continue.
    if (CycleStage == 5) {       //Start Cycle 5
      if (CycleTime4 >= millis()) {
        CycleStage = 0;
      }
    }
  }



  else {                  // If the stop button went LOW SHUT OFF!!
    MachineRun =               LOW;
    digitalWrite (SolRelayA,   HIGH);
    digitalWrite (SolRelayB,   HIGH);
    digitalWrite (SolRelayC,   HIGH);
    digitalWrite (SolRelayD,   HIGH);
    LastStartButtonState   =   LOW;
  }
  LastStartButtonState = StartButtonRead;
}

I would draw it up for a modest donation.

Nasa:
I would draw it up for a modest donation.

Keep that for the Gigs and Collaborations section.

...R

Thank you all sincerely for the help! Nasa I may take you up on that but as I said in my first post I just wanted to make sure I was correct that it's possible before I invested too much time in learning how to make it happen. I'm a do it yourselfer by nature and want to be able to figure this out myself although I'm sure I'll have a bunch of questions along the way. Robin2 is this the appropriate section to post in as I continue this project or would there be a more appropriate one?

Thanks!

Bill

BillMurphy:
Robin2 is this the appropriate section to post in as I continue this project or would there be a more appropriate one?

"Project guidance". Sounds as good as any.

Robin was merely commenting that there is another subject forum intended for commercial negotiations.

Paul__B:
Robin was merely commenting that there is another subject forum intended for commercial negotiations.

Yes, I got that, I just wasn't sure if there might be a more appropriate section for my questions. I do have a project and I sure do need guidance so it made sense to me. LOL Thanks!

Nasa:
The single relay is for powering the relay card of 8 due to a LOW signal makes the active. You don't want it to start moving when you power it up.

I have a question on this. Please forgive my possible butchering of terminology, I'm new at this! :slight_smile: I believe the relay card has NO & NC terminals so I'm assuming that in a low or high state one set is open and the other closed and in a high state they flip. The system I'm building will most likely need double acting air cylinders (powered in each direction) so my thinking is to have a solenoid air valve for extending and another for retracting. When the machine is not operating all cylinders would be in the retracted state. So couldn't I just hook up the relay terminals that are closed when it is getting a low signal to the retract solenoid and hook up the terminals that close when it goes high to the extend solenoid and not need to use the single, safety relay?

I recommend that people keep all the discussion about a single project in the same Thread. Most of the people with useful contributions watch several Sections of the Fourm. It is very frustrating when a project is split and some of the advice and information is "here" and other useful stuff is "there"

...R

On these relay cards, when not powered, the NC is made.

When there is Vcc applied, the High State is NC is still made.

Driving the pin LOW will energize the relay.

Internally there is an Opto Isolator tied to Vcc on the other side of the circuit.

There is a jumper on the card that can be removed that actually applies the voltage to drive the relays, not the opto isolator.

It gets confusing driving the pin LOW to energize. When powering up, assigning the pins will make the relays flash for a very brief moment and could close the contacts on the NO side.

That was my reason for an individual safety relay. I set the pins on the 8 relay card and the normally closed position driving the pins high because Vcc on both sides of the LED in the OPTO Isolater makes no light.

Using the safety relay to apply the jumper connection using the normally open set of contacts on the individual "Safety" relay.

Does this make sense?

"Does this make sense?" At this point I think I understand about 60% of what you've just explained. I'm not sure exactly how the opto isolator & jumper actually affect the circuit. But I believe I understand the rest, at least generally. I believe you are saying my idea to run without the safety relay could cause a problem because, even though no power and High are the same position, when power is switched on there may be a "glitch" where the relay briefly sees low rather than being guaranteed of a smooth power off to high signal transition? I think what I'm missing is why the safety relay doesn't suffer from the same issue? If you'll indulge me.....while the safety relay make make the most sense in the long run it does only "protect" on the powering up of the system, correct? Prior to the actual "start" signal and the program running? If I'm correct I'm thinking (because at this point I'm understanding the mechanics better than the electronics) that if the operator startup procedure was to power on the controller prior to applying air pressure to the system the power up "glitch" might (would?) flutter the relays, which would cycle the air solenoids but because there would be no air pressure present nothing would move. The the air pressure valve could be opened and the "run" button pressed to start the program.

Does THAT make any sense? lol

And one other question.....in the comments you mention "normally closed push-pull switch" for the start and stop. This is a little confusing to me as I had visualized the start and stop switches as momentary normally open switches that complete a circuit when pressed (closed). Can you explain that part?

Thanks again for your help!

Nasa:
It gets confusing driving the pin LOW to energize. When powering up, assigning the pins will make the relays flash for a very brief moment and could close the contacts on the NO side.

Only if you write the code wrongly. Clearly if you know the default state should be HIGH, you write the ports HIGH before setting them as outputs.

Dead easy! This is a software problem, not a hardware one. You can always foul things up with stupid code.

Paul Can you explain that ( or show an example code) so a newbie can understand it? I just got more confused! :o

When reset, all Arduino ports and registers are set to zero. This defines all port pins as inputs and turns off the pull-ups. The pull-ups are a clever trick - if you define a port pin as an input, but write the output register to HIGH, it switches on an internal current source that acts as a 47k (very approximately) pull-up resistor on that input pin.

OK. In your setup() function, you set your desired port pins as outputs. If that is the very first thing you do to any port pin, it will set it LOW since on reset, the output register was set to zero. But you did not want it to be LOW because that will turn on your optocoupler and its corresponding relay, so you then write the output to HIGH. If you do this, there is a quite short pulse between these two actions (depending on how you write the setup() code) which actuates the optocoupler and this - generally less than a millisecond - has been known to be enough to activate the relay briefly and cause a completely unwanted action in your machine.

You just have to make sure that if you do not want a relay to do this, you actually use digitalWrite() to set each of those active LOW port pins connected to the optocouplers as HIGH, before you use pinMode() to make them outputs.

So this code would have the problem:

pinMode (SolRelayA, OUTPUT);
digitalWrite (SolRelayA, HIGH);
pinMode (SolRelayB, OUTPUT);
digitalWrite (SolRelayB, HIGH);
pinMode (SolRelayC, OUTPUT);
digitalWrite (SolRelayC, HIGH);
pinMode (SolRelayD, OUTPUT);
digitalWrite (SolRelayD, HIGH);

But just by adjusting to this we eliminate that problem?

digitalWrite (SolRelayA, HIGH);
pinMode (SolRelayA, OUTPUT);
digitalWrite (SolRelayB, HIGH);
pinMode (SolRelayB, OUTPUT);
digitalWrite (SolRelayC, HIGH);
pinMode (SolRelayC, OUTPUT);
digitalWrite (SolRelayD, HIGH);
pinMode (SolRelayD, OUTPUT);

Have I got that right?

Yep. Somewhat worse than the first version would be:

   pinMode (SolRelayA,      OUTPUT);
  pinMode (SolRelayB,      OUTPUT);
  pinMode (SolRelayC,      OUTPUT);
  pinMode (SolRelayD,      OUTPUT);
  digitalWrite (SolRelayA,   HIGH);
  digitalWrite (SolRelayB,   HIGH);
  digitalWrite (SolRelayC,   HIGH);
  digitalWrite (SolRelayD,   HIGH);

While

  digitalWrite (SolRelayA,   HIGH);
  digitalWrite (SolRelayB,   HIGH);
  digitalWrite (SolRelayC,   HIGH);
  digitalWrite (SolRelayD,   HIGH);
  pinMode (SolRelayA,      OUTPUT);
  pinMode (SolRelayB,      OUTPUT);
  pinMode (SolRelayC,      OUTPUT);
  pinMode (SolRelayD,      OUTPUT);

would be fine.

Thank you! You anticipated my next question. :slight_smile:

I proposed my project at our production meeting yesterday and got the go ahead to try it. My controller board (Uno), relays, and solenoid valves were ordered yesterday so hopefully by this time next week I'll have the system mocked up and can begin testing the coding. Very exciting stuff!