O que é PWM? Guia de analogWrite, ciclo de trabalho e frequência no Arduino
O que é PWM (modulação por largura de pulso) e como funciona? Ciclo de trabalho e frequência, pinos PWM do Arduino, brilho de LED e velocidade de motor com analogWrite, a diferença dos servos, LEDC do ESP32 e PWM no Raspberry Pi Pico.
Os pinos digitais do Arduino só conhecem duas coisas: 0 V ou 5 V. Então, como deixar um LED com metade do brilho ou fazer um motor girar devagar? A resposta é o PWM (Pulse Width Modulation, modulação por largura de pulso). O pino é ligado e desligado muito rápido e, mudando a proporção do tempo em que ele fica ligado, você define a potência média entregue à carga. Controle de brilho de LEDs, controle de velocidade de motores, acionamento de servos, geração de som e até carregadores de celular usam essa técnica.

Como funciona o PWM?
Um sinal PWM é uma onda quadrada: ele fica em HIGH por um tempo, depois em LOW, e o ciclo se repete sem parar. A duração de um ciclo liga-desliga é o período, e a proporção do período em que o sinal fica em HIGH é o ciclo de trabalho (duty cycle). Com um ciclo de trabalho de 25%, o sinal fica ligado um quarto do tempo, então um pino de 5 V se comporta, em média, como 1,25 V. O LED pisca cerca de 490 vezes por segundo; seu olho não acompanha isso e só vê o brilho médio. Um motor, graças à inércia, suaviza os pulsos e gira na velocidade média.
| Ciclo de trabalho | Valor no analogWrite | Tensão média (5 V) | LED |
|---|---|---|---|
| 0% | 0 | 0 V | Apagado |
| 25% | 64 | 1,25 V | Fraco |
| 50% | 127 | 2,5 V | Meio brilho |
| 75% | 191 | 3,75 V | Forte |
| 100% | 255 | 5 V | Brilho máximo |
Nossos olhos não respondem à luz de forma linear: eles percebem muito bem as mudanças em níveis baixos e bem menos as mudanças em níveis altos. Por isso um LED com ciclo de trabalho de 50% parece muito mais forte do que a metade. Para um controle de brilho que pareça natural, usa-se a correção gama mostrada abaixo.
Frequência: quão rápido é o PWM?
A frequência é quantas vezes por segundo o sinal liga e desliga. No Arduino Uno, os pinos 5 e 6 funcionam em cerca de 980 Hz e os pinos 3, 9, 10 e 11 em cerca de 490 Hz. Para LEDs, essas frequências são mais do que suficientes. Com motores, porém, 490 Hz fica na faixa que você consegue ouvir, e o motor pode chiar um pouco; no ESP32 e no Pico você pode subir a frequência para 20 kHz para acabar com o ruído. Subir a frequência muito além do necessário, no entanto, faz transistores e MOSFETs esquentarem.
| Placa | Pinos PWM | Frequência padrão | Resolução |
|---|---|---|---|
| Arduino Uno / Nano | 3, 5, 6, 9, 10, 11 | 490 Hz (5 e 6: 980 Hz) | 8 bits (0–255) |
| Arduino Mega | 2–13, 44–46 | 490 Hz (4 e 13: 980 Hz) | 8 bits (0–255) |
| ESP32 | Quase todos os pinos de saída | Ajustável (analogWrite: 1 kHz) | 1–16 bits |
| Raspberry Pi Pico | Todos os pinos GPIO | Ajustável | 16 bits (0–65535) |
Brilho de LED com analogWrite
No Arduino, você gera PWM com analogWrite(pin, value), em que o valor fica entre 0 e 255. Apesar do nome enganoso, esse comando não produz uma tensão analógica de verdade; ele produz PWM. Ele só funciona nos pinos marcados com ~. O código abaixo aumenta e diminui o brilho de um LED devagar, para um efeito de "respiração":
1const int LED_PIN = 9; // ~ işaretli PWM pini / PWM pin marked with ~
2
3void setup() {
4 pinMode(LED_PIN, OUTPUT);
5}
6
7void loop() {
8 for (int v = 0; v <= 255; v++) { // yavaşça yan / fade in
9 analogWrite(LED_PIN, v);
10 delay(8);
11 }
12 for (int v = 255; v >= 0; v--) { // yavaşça sön / fade out
13 analogWrite(LED_PIN, v);
14 delay(8);
15 }
16}Controle de brilho com um potenciômetro
Se você ligar um potenciômetro no A0, pode ajustar o brilho do LED à mão. analogRead() devolve um valor de 0 a 1023; dividir por 4 dá a faixa de 0–255 que o analogWrite espera. A ligação do potenciômetro é explicada em O que é potenciômetro?
1void loop() {
2 int pot = analogRead(A0); // 0–1023
3 analogWrite(9, pot / 4); // 0–255
4}Velocidade de motor CC com PWM
Até um motor CC pequeno puxa centenas de miliampères, enquanto um pino do Arduino só fornece com segurança cerca de 20 mA. Por isso o motor é acionado através de um transistor, MOSFET ou um driver de motor como o L298N, e o sinal PWM vai para a entrada de velocidade do driver. No L298N, essa entrada é o pino ENA (e o ENB para o segundo motor); para usar PWM, você precisa tirar o jumper que fica nele. Os pinos IN1 e IN2 definem o sentido de giro.

1const int ENA = 9; // hız (PWM) / speed (PWM)
2const int IN1 = 8; // yön / direction
3const int IN2 = 7;
4
5void setup() {
6 pinMode(ENA, OUTPUT);
7 pinMode(IN1, OUTPUT);
8 pinMode(IN2, OUTPUT);
9 digitalWrite(IN1, HIGH); // ileri / forward
10 digitalWrite(IN2, LOW);
11}
12
13void loop() {
14 analogWrite(ENA, 255); delay(2000); // tam hız / full speed
15 analogWrite(ENA, 150); delay(2000); // orta hız / medium speed
16 analogWrite(ENA, 0); delay(2000); // dur / stop
17}Servo motor e PWM são a mesma coisa?
Os servo motores também são controlados com pulsos, mas a lógica é diferente: a posição é definida pela largura do pulso, e não pelo ciclo de trabalho. Um servo espera 50 pulsos por segundo (50 Hz); um pulso de 1 milissegundo significa cerca de 0°, 1,5 ms significa 90° e 2 ms significa 180°. O analogWrite não consegue gerar essa temporização, e é por isso que os servos usam a biblioteca Servo. Os detalhes estão em O que é servo motor?
Uma tensão analógica de verdade a partir do PWM: o filtro RC
Às vezes você precisa mesmo de uma tensão estável, por exemplo para dar uma referência a um amplificador operacional ou para ter uma saída de áudio. Nesse caso, você passa o PWM por um filtro passa-baixa feito com um resistor e um capacitor. Com 10 kΩ e 10 µF, a constante de tempo é de 0,1 segundo; a saída fica bem lisa, mas reage devagar às mudanças. Você pode testar valores diferentes com a calculadora de constante de tempo RC. O ESP32 clássico também tem dois DACs, no GPIO 25 e no 26, que dão uma saída analógica de verdade.
PWM no ESP32: LEDC
No ESP32, o PWM é gerado por um hardware chamado LEDC, e você escolhe a frequência e a resolução. No core Arduino 3.x, você usa ledcAttach(pin, frequency, resolution) e ledcWrite(pin, value); as versões antigas 2.x tinham os comandos ledcSetup e ledcAttachPin, baseados em canais. O exemplo abaixo varia o brilho de um LED a 5 kHz com resolução de 8 bits:
1const int LED_PIN = 2;
2
3void setup() {
4 ledcAttach(LED_PIN, 5000, 8); // 5 kHz, 8 bit (0–255) — ESP32 Arduino core 3.x
5}
6
7void loop() {
8 for (int d = 0; d <= 255; d++) { ledcWrite(LED_PIN, d); delay(5); }
9 for (int d = 255; d >= 0; d--) { ledcWrite(LED_PIN, d); delay(5); }
10}PWM no Raspberry Pi Pico (MicroPython)
Todos os pinos GPIO do Pico podem gerar PWM. No MicroPython, você usa a classe PWM, definindo a frequência com freq() e o ciclo de trabalho com duty_u16(), que recebe valores de 0 a 65535:
1from machine import Pin, PWM
2import time
3
4led = PWM(Pin(15))
5led.freq(1000) # 1 kHz
6
7while True:
8 for d in range(0, 65536, 512): # yavaşça yan / fade in
9 led.duty_u16(d)
10 time.sleep_ms(5)
11 for d in range(65535, -1, -512): # yavaşça sön / fade out
12 led.duty_u16(d)
13 time.sleep_ms(5)Ideias de projetos com PWM
- LED que respira: uma luz de status que acende e apaga devagar, como em aparelhos em modo de espera.
- Luminária de mesa com dimmer: uma luminária de LED com o brilho ajustado por um potenciômetro.
- Ventilador controlado pela temperatura: acelere um ventilador conforme a temperatura medida por um DHT11 sobe.
- Mistura de cores: crie milhões de cores em um LED RGB com três canais PWM.
- Carrinho robô: deixe as curvas mais suaves definindo a velocidade de cada motor separadamente.
- Luminária do amanhecer: aumente aos poucos o brilho de uma luz durante 15 minutos antes do despertador da manhã.
Erros comuns e como resolvê-los
- analogWrite em um pino sem PWM: no Uno, os pinos sem ~ só ficam ligados ou desligados; 128 ou mais conta como ligado e qualquer valor menor como desligado.
- Pinos 9 e 10 com a biblioteca Servo: no Uno, a biblioteca Servo usa o Timer1 e desativa o PWM nesses dois pinos; passe o LED ou o motor para outro pino PWM.
- Pinos 3 e 11 com tone(): tone() usa o Timer2 e atrapalha o PWM nesses pinos.
- Ligar um motor direto em um pino: use sempre um transistor, MOSFET ou driver de motor.
- Estouro no cálculo da correção gama: v * v passa do limite do int; acrescente a conversão (long).
- Tratar o PWM como analógico de verdade: o multímetro mostra a média, mas o sinal continua oscilando entre 0 e 5 V; use um filtro RC ou um DAC em circuitos sensíveis.
O PWM é uma das ideias mais úteis que você vai aprender no Arduino: LEDs, motores, ventiladores e alto-falantes são todos controlados com esse truque simples. Para o básico, dê uma olhada em O que é LED?; no app BlueGrays você encontra projetos de LED com PWM, brilho com potenciômetro e transição de cores com LED RGB passo a passo, com código.
Perguntas frequentes
O que é PWM, resumindo?
PWM é uma forma de definir a potência média entregue a uma carga ligando e desligando um pino muito rápido e mudando a proporção do tempo em que ele fica ligado (o ciclo de trabalho). Ele permite que um pino digital, que só fornece 0 ou 5 V, diminua o brilho de um LED ou desacelere um motor.
Quais pinos têm PWM no Arduino Uno?
No Uno e no Nano, os pinos 3, 5, 6, 9, 10 e 11 têm PWM; eles estão marcados com ~ na placa. No Mega, os pinos 2–13 e 44–46 podem gerar PWM.
O analogWrite dá uma saída analógica de verdade?
Não. O analogWrite produz PWM; o pino alterna rapidamente entre 0 e 5 V. Ele define a tensão média, mas, para ter uma tensão realmente estável, você precisa passar o PWM por um filtro RC ou usar um DAC, como o do ESP32.
Como se calcula o ciclo de trabalho?
O ciclo de trabalho é o tempo em que o sinal fica em HIGH dividido pelo período inteiro: (tempo em HIGH / período) × 100. No Arduino, você o encontra dividindo o valor do analogWrite por 255 e multiplicando por 100; por exemplo, 64 dá cerca de 25%.
Como mudo a frequência do PWM no Arduino?
O analogWrite não muda a frequência. No Uno, você pode ajustá-la mudando os registradores dos timers (por exemplo, o TCCR1B para os pinos 9 e 10), mas isso pode afetar o millis e algumas bibliotecas. No ESP32, você define a frequência direto com ledcAttach, e no Pico com freq().
O PWM pode danificar um LED?
Não. O LED acende com a corrente total durante cada pulso, mas essa corrente já é limitada pelo resistor em série, e a corrente média cai na proporção do ciclo de trabalho. Desde que você use o resistor certo, o PWM não encurta a vida do LED.
Projetos para montar depois desta leitura
Ver todos os projetos
Variação gradual do brilho do LED com PWM no ESP32
Varie suavemente o brilho do LED de 0 ao máximo e do máximo a 0. Controlamos o PWM com analogWrite(), como no Arduino. A mesma sintaxe funciona sem problemas com ESP32 Arduino Core 3.0+. Basta definir o pino e usar pinMode e analogWrite.

Raspberry Pi Pico: variação de brilho do LED com PWM (efeito de respiração)
O LED não só pisca — ele respira! Com o PWM (modulação por largura de pulso) do Raspberry Pi Pico, o brilho do LED aumenta e diminui lentamente, como a luz de um MacBook em repouso. Aprenda a usar a classe machine.PWM, duty_u16() (brilho de 16 bits, de 0–65535), frequência PWM (freq(1000) — 1.000 ciclos de ligar/desligar por segundo, sem cintilação visível), laços com passos usando range() (crescentes e decrescentes) e saída semelhante à analógica em um pino digital.

Brilho do LED com potenciômetro no ESP32 (analógico → PWM)
Neste projeto, controlamos o brilho de um LED de forma analógica com um potenciômetro. O pino ADC do ESP32 lê a tensão de 0-3,3V do potenciômetro e converte esse valor em um sinal PWM (modulação por largura de pulso), enviado ao LED. Assim, ao girar o potenciômetro, o brilho do LED aumenta e diminui gradualmente. Com Arduino Core 3.0+, você pode usar analogWrite() diretamente; no ESP32-S2/S3, a resolução do ADC é fixada em 12 bits.

Transição suave de cores com LED RGB
Um único LED RGB muda lentamente do vermelho para o verde, do verde para o azul e de volta para o vermelho, repetindo esse ciclo de arco-íris sem parar. Cada transição leva cerca de dois segundos e me

Controle de LED RGB com ESP32
Gere inúmeras cores com um único LED RGB em vez de 3 LEDs separados. Como no Arduino, ajustamos os valores R/G/B com analogWrite() para criar uma transição de arco-íris. Você vê a teoria das cores na prática, como vermelho + verde = amarelo.

Ciclo de cores com LED RGB no Raspberry Pi Pico (PWM de 3 canais)
Um LED, milhões de cores! Um LED RGB contém, na verdade, 3 LEDs: vermelho, verde e azul. Controlar cada um com seu próprio canal PWM do Pico mistura as cores: vermelho + verde = amarelo, verde + azul = ciano, os três = branco. Aqui, o LED alterna entre 8 cores. Aprenda sobre múltiplos canais PWM, definição de funções (def set_color(...)), mistura de cores RGB (como funcionam telas e lâmpadas inteligentes), conversão de 8 bits → 16 bits (x257 converte 0–255 em…

Servo motor com ESP32 (controle por potenciômetro)
Neste projeto, controlamos um servo motor SG90 com um potenciômetro. Ajustamos o ângulo do servo mapeando o valor analógico lido do potenciômetro para a faixa de 0 a 180 graus. A biblioteca ESP32Servo gera sinais para o servo nos GPIOs do ESP32 adequados e capazes de operar como saída; este projeto usa o GPIO 18. Esse é um método básico de controle para braços robóticos, estabilizadores de câmera e mecanismos de portas automáticas.

Luminária com mistura de cores e ESP32 (3 potenciômetros + LED RGB + OLED)
Uma luminária inteligente que permite misturar a cor que você quiser girando três potenciômetros com o ESP32! Ao girar os potenciômetros de vermelho, verde e azul, o LED RGB de cátodo comum muda de cor em tempo real. O display OLED SSD1306 mostra os valores de cada cor na faixa de 0–255, barras de preenchimento e o código HEX da cor para a web, como #FF8040.
Mais artigos
App BlueGrays
Monte este circuito passo a passo pelo celular
Esquema do circuito, código e lista de componentes em uma só tela. Mais de 200 projetos com Arduino, ESP32 e Pico prontos para montar.
Escaneie com seu celular
Aponte a câmera para o código para abrir a loja de aplicativos do seu celular.
ou abrir a loja

