Looking for PWM IC

Can anyone suggest an IC that can output a PWM signal like the one that comes from the Arduino but will operate at 10Khz or more.

Must have 0-100% duty cycle, be able to be driven by the Arduino pins and it would be nice if there is control over the frequency.

Thank you
Alan

I bet if you combined a 555 timer with a couple of digital pots that Arduino can control, you could get there easily.

I wondered about this route and can see getting 0-100% seems a challenge but I was looking for a chip that did all the work for me.

By programming a timer, the Arduino can output PWM at just about any frequency you want, from essentially 0 to 100% duty cycle.

Done that but the resolution of the duty cycle drops off to unusably large steps

Even with timer1?

I'm sure I tried all the options

acboother:
Done that but the resolution of the duty cycle drops off to unusably large steps

No it doesn't if you pick the right frequencies.

If you want a chip then there is the TLC5940 or I think the better one is the PCA9685.

Read the 16-bit timer section of ATMEGA datasheet.

If you want 10khz, here is the general idea.

divide the CPU clock by 8 to get a frequency of 2mhz. This means each increment of the timer counter is 0.5us.

To get 10khz, that is a period of 100us. Which means you need to increment 200x to for 100us to elapse. remember, each increment takes 0.5us.

The resolution of this is 200, which means the pwm can go from high to low anywhere between 0 and 200.

To get the above on PWM pin D5 on the AtMega using the following code

DDRE |= _BV(PE3);
PORTE &= ~(_BV(PE3);
TCCR3A=TCCR3B=0;
TCCR3A |= _BV(WGM31) | _BV(COM3A1);
TCCR3B |= _BV(WGM33) | _BV(CS31);
ICR3=200;
OCR3A=0; //set this to duty cycle

to change the duty cycle you would simply do

uint8_t saveSREG = SREG;
cli();
OCR3A=100;
SREG = saveSREG;

to set 50% duty cycle (100/200).

you can play around with resolution and clock divide to get your desired frequency and resolution.

I use this code to control multiple pwm devices. pwm fan for instance using 20khz pwm frequency.

using divide by 8 to get 0.5us makes it easy to calculate the value to set ICR3.
So if say you want a 12khz pwm, all you need to do is set ICR3=167.

you should get an idea on what you can do with timers to generate pwm given the above info.

LTC6992

Use PWM out with an 10 k ohm/4.7uF RC LPF on the output of the PWM pin to convert the arduino PWM to true analog which the LTC6992 requires in order to output PWM up to 1 Mhz.

OP is asking for PWM IC only because he could not get the desired output with arduino pwm, despite saying he tried all options, which apparently there are options he did not try yet.

@doughboy,

I don't think the code you posted in Reply#8 is going to be much help to the OP, being as it doesn't compile. If you are going to post code for newbies it make more sense to post working code and not "snippets" of code that are not going to compile and probably just frustrate the OP. I would suggest
posting an actual working , sketch that will compile. If the OP knew how to use what you posted, he would wouldn't be posting because as you yourself pointed out, the reason he was posting is that he doesn't know how to write the code your "snippet" (that doesn't compile) represents.

The code posted above would compile for a mega I think, and for an uno if you change the 3s in the registers to 1s. It looks okay to me

Ok , I tried but I must have missed something. It still doesn't compile.

void setup() {
  // put your setup code here, to run once:
DDRB |= _BV(PE1);
PORTE &= ~(_BV(PE1);
TCCR1A=TCCR1B=0;
TCCR1A |= _BV(WGM11) | _BV(COM1A1);
TCCR1B |= _BV(WGM33) | _BV(CS31);
ICR1=200;
OCR1A=0; //set this to duty cycle

}

void loop() {
  // put your main code here, to run repeatedly:

}

I changed the DDRE to DDRB. (is that right ?)

I found this sketch online:

I got it from a Youtube video. It does 10 kHz PWM.

 #include <PWM.h>
int32_t frequency = 10000; // frequency (in Hz)
 int sensorValue =0;

void setup() 
{
  // put your setup code here, to run once:
  InitTimersSafe();
  bool success = SetPinFrequencySafe(9, frequency);
  if(success) {
    pinMode(13,OUTPUT);
    digitalWrite(13,HIGH);
   }
 }

void loop()
   {
    // put your main code here, to run repeatedly:
    int sensorValue = analogRead(A0);
    pwmWrite(9,sensorValue/4);
    delay(30);
    }

Oh, yeah, he used direct port manipulation. You can just lose the DDRx and PORTx lines, and call pinMode() on the pin to make it output. I see those and know what they do at a glance.

What pin is used for that timer ? Is it pin 9?

raschemmel:
LTC6992

Use PWM out with an 10 k ohm/4.7uF RC LPF on the output of the PWM pin to convert the arduino PWM to true analog which the LTC6992 requires in order to output PWM up to 1 Mhz.

That looks interesting. Very tune'able as well

Did you see the 10 kHz PWM sketch I posted in Reply#13 ?

And did you see the chips I suggested in reply #7?

raschemmel:
Did you see the 10 kHz PWM sketch I posted in Reply#13 ?

Yes and I've fiddled with this approach a little time back and was now looking at the possibility of an IC.