Automatização de cortina

Boa tarde, há uns 2 anos atrás automatizei a cortina do meu quarto usando um motor de vidro elétrico para carros (12V/5A), porém tal automatização foi completamente analógica, passei um chicote por cima do forro de gesso, e na ponta dele coloquei uma chave de 3 posições para a inversão de polaridade do motor. Como irei fazer uma reforma em meu quarto, estava querendo automatizar a cortina, só que agora digitalmente com o auxilio de um arduíno, ontem fiz um código onde ao pressionar um botão uma vez, o motor gira para um sentido durante 6 segundos (tempo necessário para que a cortina abra ou feixe totalmente)(irei deixar o código abaixo), porem encontrei um problema, a saída do arduíno não é 12V/5A e o motor não tem força para levantar a cortina, queria saber como posso controlar o motor pelo o arduíno, porem alimentar o motor de forma independente com uma fonte externa.

CÓDIGO DO PROJETO

#define porta1motor 2

#define porta2motor 3

#define botao A0

int rotacao = 0;

boolean executar = false;

void setup() {

pinMode( porta1motor, OUTPUT );

pinMode( porta2motor, OUTPUT );

pinMode( A0, INPUT_PULLUP );

}

void loop() {

int leitura = digitalRead( botao );

if (leitura == LOW ) {

delay(30);

if ( digitalRead( botao ) == leitura ) {

  executar = true;

}

}

if ( executar){

executar = false;

if ( rotacao == 0 ) {

  digitalWrite( porta1motor, HIGH );

  digitalWrite( porta2motor,  LOW );

  delay(6000);

  digitalWrite( porta1motor,  LOW);

  rotacao = 1;

} else{ //1

  digitalWrite( porta1motor,  LOW );

  digitalWrite( porta2motor, HIGH );

  delay(6000);

  digitalWrite( porta1motor, HIGH ); 

  rotacao = 0;

}

}

}
(os fios do motor serão ligados nas portas digitais 2 e 3, e o botão para acionamento será ligado na porta analógica 0 e no GND da placa).

achei uma forma de controlar a duração de rotação e o sentido de rotação do motor, pelo arduíno com uma alimentação externa, para quem estiver interessado, lá vai.

 usei um módulo relé 5v 4 canais, dois serão alimentados pelo positivo da fonte, e os outros dois pelo negativo, no código antigo eu usaria 2 portas digitais, agora usei 4 para fazer o controle dos relés, a ligação do motor é simples, fiz uma sangria no fio do motor, assim ficando 2 positivos e 2 negativos, uma das duplas de positivos e negativos foram ligados em suas respectivas polaridades nos relés, já a outra dupla foi ligada ao inverso(para que a direção de rotação do motor mude).

NOVO CÓDIGO

#define porta1motor 2

#define porta2motor 3

#define porta3motor 4

#define porta4motor 5

#define botao A0

int rotacao = 0;

boolean executar = false;

void setup() {

pinMode( porta1motor, OUTPUT );

pinMode( porta2motor, OUTPUT );

pinMode( porta3motor, OUTPUT );

pinMode( porta4motor, OUTPUT );

pinMode( A0, INPUT_PULLUP );

}

void loop() {

int leitura = digitalRead( botao );

if (leitura == LOW ) {

delay(30);

if ( digitalRead( botao ) == leitura ) {

  executar = true;

}

}

if ( executar){

executar = false;

if ( rotacao == 0 ) {

  digitalWrite( porta1motor, HIGH );

  digitalWrite( porta2motor, HIGH );

  delay(6000);

  digitalWrite( porta1motor,  LOW );

  digitalWrite( porta2motor,  LOW );

  rotacao = 1;

} else{ //1

  digitalWrite( porta3motor, HIGH );

  digitalWrite( porta4motor, HIGH );

  delay(6000);

  digitalWrite( porta3motor, LOW );

  digitalWrite( porta4motor, LOW ); 

  rotacao = 0;

  

}

}

}
De novidade nesse código foi somente a adição de mais duas portas digitais
(porta3motor, porta4motor), e agora os dois pares de portas digitais mandam inicialmente um sinal HIGH para acionamento dos relés, logo após os 6 segundos, o sinal LOW para a parada do motor.

Não sei quanto de grana vc quer gastar, mas a maneira que eu faria seria usar um motor de passo e uma CNC shield… iria gastar uns R$100 com tudo. O motor é aliemntado por até 24v independente do arduino. E no código vc simplesmente comanda quantos pulso quer dar ou seja pode comandar o quanto vai abrir e fechar a cortina e não simplesmente aberto/fechado. Ja tem a biblioteca stepper e é muito facil de usar… mais mesmo que o que vc fez sendo muito preciso

o motor de passo com a CNC shield seria uma boa, eu usei o motor de vidro elétrico pois ja tinha aqui na minha casa e a foça dele ja supria minha necessidade, usei ele por 2 anos e nunca deu problema. O módulo relé 5v 4 canais, achei por um preço baixo no aliexpress, em torno de 14 reais, caso alguém se interesse, aqui vai o link: Wavgato módulo de relé 5v 12v, módulo de relé de 1 2 4 8 16 canal placa escudo de interface para imagem avr dsp braço mcu arduino|Circuitos integrados| - AliExpress

bom… fiz mais uma modificação no projeto, quando eu tinha dito que estava buscando uma automatização totalmente digital, tinha esquecido do fato de ter que passar dois fios por todo o quarto para o acionamento das portas digitais, então adicionei um sensor infravermelho ao invés de um push boton.

NOVO CÓDIGO

#include <IRremote.h>

#define RECV_PIN 8

#define TECLA_SUBIR_DESCER 14025

#define pino_rele1 2

#define pino_rele2 3

#define pino_rele3 4

#define pino_rele4 5

IRrecv irrecv(RECV_PIN);

decode_results results;

int rotacao = 0;

boolean executar = false;

void setup()

{

pinMode (pino_rele1, OUTPUT);

pinMode (pino_rele2, OUTPUT);

pinMode (pino_rele3, OUTPUT);

pinMode (pino_rele4, OUTPUT);

Serial.begin(9600);

irrecv.enableIRIn(); // Start the receiver

}

void loop()

{

if(irrecv.decode(&results)){

unsigned int codigoRecebido = results.value;



Serial.print( "Codigo binario =");

Serial.print(codigoRecebido);

Serial.print("     /     ");

Serial.print( "Codigo Hexadecimal = ");

Serial.print(codigoRecebido, HEX);    



irrecv.resume(); // Receive the next value



if(codigoRecebido != 0xFFFF)

{

  switch(codigoRecebido)

   case TECLA_SUBIR_DESCER:

    if ( rotacao == 0 ) {

    digitalWrite( pino_rele1, HIGH );

    digitalWrite( pino_rele2, HIGH );

    delay(5000);(TEMPO QUE A MINHA CORTINA SOBE E DESCE)

    digitalWrite( pino_rele1,  LOW );

    digitalWrite( pino_rele2,  LOW );

    rotacao = 1;

  } else{ //1

    digitalWrite( pino_rele3, HIGH );

    digitalWrite( pino_rele4, HIGH );

    delay(5000); (TEMPO QUE A MINHA CORTINA SOBE E DESCE)

    digitalWrite( pino_rele3,  LOW );

    digitalWrite( pino_rele4,  LOW ); 

    rotacao = 0;

   }

 }

}

}

mais uma atualização, meu arduíno e as placas reles queimaram, o sistema ficava exposto e algo metálico pode ter geraco um curto, queimando os dois. Porém, recentemente tive a ideia de usar um ESP32, para controlar a cortina, tanto pelo wifi, quanto pelo infra-vermelho. sendo assim, tive que fazer um novo código, lá vai ele:

#include <WiFi.h>                         
#include <IRremote.h>                     

// ============================================================================

#define   pino_rele1   21                    
#define   pino_rele2   22                    
#define   RECV_PIN 8                         
#define   TECLA_SUBIR_DESCER 41055           

//=============================================================================

IRrecv irrecv(RECV_PIN);
decode_results results;

int rotacao = 0;
boolean executar = false;

//=============================================================================

void loop() 
{
  if(irrecv.decode(&results)){
    unsigned int codigoRecebido = results.value;
    
    Serial.print( "Codigo binario =");
    Serial.print(codigoRecebido);
    Serial.print("     /     ");
    Serial.print( "Codigo Hexadecimal = ");
    Serial.print(codigoRecebido, HEX);    
    
    irrecv.resume(); 
    
    if(codigoRecebido != 0xFFFFF)
    {
      switch(codigoRecebido)
       case TECLA_SUBIR_DESCER:
        if ( rotacao == 0 ) {
        digitalWrite( pino_rele1, HIGH );
        delay(4950);
        digitalWrite( pino_rele1,  LOW );
        rotacao = 1;
      } else{ //1
        digitalWrite( pino_rele2, HIGH );
        delay(5100);
        digitalWrite( pino_rele2,  LOW ); 
        rotacao = 0;
       }
     }
  }
}
                    
// ============================================================================
// 
const char *ssid     = "ID DA REDE";  
const char *password = "SENHA DA REDE"; 


// ============================================================================
//
WiFiServer server(80);                    
                                          

// ============================================================================
//
void relay_wifi();                       
                                

// ============================================================================
// 
void setup() 
{
  Serial.begin(115200);                  
  pinMode(pino_rele1, OUTPUT);               
  pinMode(pino_rele2, OUTPUT);              

  Serial.println();                      
  Serial.print("Conectando-se a ");      
  Serial.println(ssid);                  
  WiFi.begin(ssid, password);           

  while(WiFi.status() != WL_CONNECTED)   
  {
    delay(741);                          
    Serial.print(".");                   
  }

  Serial.println("");                   
  Serial.println("WiFi conectada");      
  Serial.println("Endereço de IP: ");    
  Serial.println(WiFi.localIP());        

  server.begin();                       

}


// ============================================================================
// 
void loop() 
{


  while(WiFi.status() != WL_CONNECTED)  
  {
    WiFi.begin(ssid, password);          
    Serial.print(".");                   

    delay(741);                         
  }
  
  relay_wifi();                                


  
} 


// ============================================================================

void relay_wifi()
{

  WiFiClient client = server.available();      
  
  if(client)                                   
  {                                            
    Serial.println("Novo Cliente Definido");   
    String currentLine = "";                   
    
    while(client.connected())                  
    {
      
      if(client.available())                   
      {                                       
        char c=client.read();                  
        Serial.write(c);                      
        
        if(c=='\n')                            
        {                                      
          if(currentLine.length()==0)          
          {                                    
            
            client.println("HTTP/1.1 200 OK");
            client.println("Content-type:text/html");
            client.println();
            client.println("<html>");
            client.println("<head><meta content=\"width=device-width, inicial scale=1\">");
            client.println("<style>html { background-color: #363636; margin:0px auto; text-align: center;}");
            client.println(".botão_sobe { background-color: #4682B4; color white; padding: 15px 40px; border-radius: 25px;}");
            client.println(".botão_desce { background-color: #4682B4; color white; padding: 15px 40px; border-radius: 25px;}</style></head>");
            client.println("<body><hl>CORTINA DO QUARTO</hl>");
            
            client.println("<p><a href=\"/H\"><button class=\"botão_sobe\">SUBIR</button></a></p>");
            client.println("<p><a href=\"/L\"><button class=\"botão_desce\">DESCER</button></a></p>");
            client.println("</body></html>");
            client.println();
            break;                             
            
          }
          
          else currentLine="";                 
        
        } 
                  
        else if(c != '\r') currentLine += c;  

       
          if(currentLine.endsWith("GET /H")) digitalWrite(pino_rele1, HIGH);
            delay(5000)
              digitalWrite(pino_rele1,  LOW);
          if(currentLine.endsWith("GET /L")) digitalWrite(pino_rele2, HIGH);
            delay(5000)
              digitalWrite(pino_rele2,  LOW);
          
       
      } 
      
    } 

    client.stop();                           
    Serial.println("Client Disconnected.");
    
  }  
  
  
}
}