Arduino SPWM generator

Continuing work on my previous project, namely the generation of pulse width modulated sinusoidal waves called SPWM, I added an important function, namely voltage feedback in this Arduino SPWM generator project.

In addition, I also added voltage, temperature, and battery protection functions. Protection is to protect against over-voltage, low voltage, over-temperature and low battery.

Now I use Arduino Nano, so the Arduino SPWM generator module is compact.

In a previous project, I focused on generating a sinusoidal signal using the PWM port on the Arduino Uno. And now I add voltage feedback and protection functions.

Arduino SPWM generator Hard Ware

Here I add a voltage divider circuit for low-batt detection, as well as a buzzer circuit (on the top left) so. the expected voltage at A0 input is at about 2.5V. Also, I add a jumper J2 and connect it when I adjust the feedback voltage trimmer potentiometer and then released it after that.

The rest of the circuit is the same as in the previous project.

arduino spwm generator circuit

Below is The Printed Circuit Board layout for this Arduino Nano SPWM module.

Full-Bridge MOSFET

If you use a Full-bridge MOSFET as in my previous post, the 12V regulator is not necessary. Just connect the input and output pins of this 12V regulator, this is because the SPWM generator card will monitor the battery voltage for low-batt detection.

Arduino SPWM Generator Code

In this section, I add code that matches the hardware above.

In the previous project, I made code only for the 50Hz frequency, here I add it also for 60Hz. To work at 60Hz use the code that I’m currently commenting as 60Hz and make the code marked as 50Hz a comment.

// <------------------ 50 Hz !!!

Voltage Feedback

The main program here performs voltage feedback processing and tries to stabilize the voltage by adjusting the output pulse width so that the voltage increases or decreases according to the error that occurs.
In addition, it also reads the temperature and battery voltage.

     feedBackTest(vMax, analogRead(tfbPin), analogRead(battPin));

After that, the program will check all the inputs by calling the function feedBackTest.

Feed Back Test

This routine is tasked with checking all feedback inputs whether exceed a predetermined limit.

Maybe you see the upper and lower limits of the voltage feedback on the program and in the comments are different, that’s because I tried to do the settings that best suit my needs.

If one of the limits is exceeded, this routine will call the alarmIndication a routine that matches the type of alarm that occurred.

This routine is bypassed when the jumper is placed on J2 so we can adjust the output with no disturbance from the under or over-voltage alarm.

void feedBackTest(float vfbIn, int tfbIn, int battIn) {
  long alrm;
  static int alrmCnt;
  
  if (digitalRead(2) == LOW) return;
  if (phs != 1) return;
  
  alrm = constrain(vfbIn, 462, 660);
  if (alrm !=vfbIn) alrmCnt++; else alrmCnt=0;
  if (alrm == 462 && alrmCnt >= 150) alarmIndication(2);        
// underVoltage @ 2.5V --> 2.75 / 5 x 1023 = 562
  if (alrm == 660 && alrmCnt >=15) alarmIndication(3);          
// overVoltage @ 3.15V --> 3.15 / 5 x 1023 = 645
  if (tfbIn >= 924) alarmIndication(4);                         
// over temp @ 80C --> 10k/(10k + 1.068k) x 1023 =924
  if (battIn <= 457) alarmIndication(5);                        
// low batt @ 10.5V --> (2k7/12.7k x 10.5) / 5 x 1023 = 457
  if (tfbIn >= 725 && digitalRead(8) == LOW)  digitalWrite(8, HIGH);  
// fan ON @45C --> 725
  if (tfbIn <= 679 && digitalRead(8) == HIGH) digitalWrite(8, LOW);   
// fan OFF @40C --> 679
}

Alarm Indication

When an alarm occurs this routine will turn off all SPWM outputs. The buzzer beeps and LEDs flash according to the alarm that occurs. The LED lights up and the buzzer sounds twice for under-voltage, three times for over-voltage and so on.

This alarm goes on continuously until it is reset because I made a continuous loop.

void alarmIndication(int alarm)
{
  TCCR1A = 0;                             // shutdown SPWM output
  TIMSK1 = 0;
  PORTB &= 0b11100001;
loopX:
  for (int i = 0; i < alarm; i++) {
    digitalWrite(7, HIGH);                // turn ON LED and Buzzer
    digitalWrite(13, HIGH);
    delay(200);
    digitalWrite(7, LOW);                 // then turn OFF
    digitalWrite(13, LOW);
    delay(200);
  }
  delay(1000);
  goto loopX;                           //never ending story... until reset
}

That’s all I can say in this post. Complete code, PCB and schematic please download from the link below…Here are the project files you can download…


This is my post this time, have a nice day.