Interruptor de interfaz y led con cualquier controlador [duplicado]

Estoy tratando de conectar el interruptor y el led. Quiero escribir un programa en el que, si presiono y suelto, el LED del interruptor debe encenderse y, si lo presiono nuevamente, el LED del interruptor debe apagarse. No puedo escribir lógica para él, ya que soy un novato en el sistema integrado. ¿Alguien puede ayudarme a escribir la lógica para ello? Gracias.

Este es mi código para encender y apagar el led usando el interruptor CÓDIGO

int main(void)
 {
    DDRC |= (1<<PC0); //Makes first pin of PORTC as Output
    DDRD &= ~(1<<PD0);//Makes firs pin of PORTD as Input

    while(1) //infinite loop
    {
        if(PIND & (1<<PD0) == 1) //If switch is pressed
        {
            PORTC |= (1<<PC0); //Turns ON LED
            _delay_ms(3000); //3 second delay
            PORTC &= ~(1<<PC0); //Turns OFF LED
        }
    }
}
¿Qué has intentado hasta ahora? No vamos a sentarnos y hacer su proyecto por usted; si lo hiciéramos, no aprendería nada en absoluto.
@NickJohnson He incluido el código del interruptor y el led pero en este código el led se apaga al soltar el interruptor
Un buen comienzo: ¿entiendes por qué actúa de la forma en que lo hace actualmente? ¿Qué necesita saber específicamente para modificarlo para que funcione de la manera que desea?
no se como modificarlo
¿Qué sucede cuando ejecutas este código?

Respuestas (5)

No soy programador, pero después de leer su pregunta sobre la solución, me vino a la mente y la explicaré a continuación.

Para la lógica a continuación, su LED e interruptor deben controlarse con un pin de E / S diferente del controlador. El primer controlador debe detectar la lógica del interruptor presionado y, en función de la lógica del interruptor, el controlador debe detectar primero la lógica del pin de E/S del LED para la condición previa de lógica BAJA o ALTA. Si la lógica del LED Pin es ALTA, cámbiela a BAJA y viceversa. Tenga en cuenta que la E/S del pin del LED debe invertirse solo después de presionar el interruptor.

A continuación se puede seguir la lógica

Switched pressed (Y/N)
{

If Y
    {
      changed the logic of LED port pin // If HIGH, change it to LOW if LOW, change it to HIGH

        else N
              { Do nothing}
        }
}

El único cambio a realizar podría ser de esto a

if(PIND & (1<<PD0) == 1) //If switch is pressed
        {
            PORTC |= (1<<PC0); //Turns ON LED
            _delay_ms(3000); //3 second delay
            PORTC &= ~(1<<PC0); //Turns OFF LED
        }

este:

if(PIND & (1<<PD0) == 1) //If switch is pressed
        {
            //Toggle PC0
            // a few 10s of mili-second delay
        }

Puede considerar usar Switch como interrupción, PD0 puede configurarse como interrupción, de modo que pueda hacer un trabajo útil hasta que el usuario presione el interruptor. El código de alternancia de LED puede ser parte de ISR (rutina de servicio de interrupción). Además, busque Switch De-bouncing...

Sugerencia #1) Realice una búsqueda en Internet usando c program operator precedencey luego estudie la expresión lógica de su sentencia if(). Específicamente, considere el orden de evaluación de las subexpresiones en una expresión cuya forma es

a & b == c

Sugerencia n.° 2) La expresión lógica de la declaración if() debe reescribirse para probar un resultado cero (=falso) o distinto de cero (=verdadero), en lugar de probar un valor de resultado de exactamente '1' (uno). ¿Por qué una prueba de cero/distinto de cero es una práctica preferible cuando se prueban valores de bit como este?

el problema con el código publicado es con esta línea:

if(PIND & (1<<PD0) == 1)

Dado: si se estuviera probando el bit 0 de PIND, el resultado sería 0 o 1

Sin embargo, si 'PD0' no se define como 0, entonces

entonces el valor resultante de 'PIND & (1<

Sugerir:

if( (PIND & (1<<PD0)) == 1<<PD0 )

Tenga en cuenta el uso de paréntesis para que no tenga que preocuparse por el orden de evaluación y la precedencia del operador.

Al usar la declaración de código sugerida, ambos lados de '==' se comparan con el mismo valor.

Además, la pregunta no menciona qué chip se está programando.

Algunos chips requieren más de una instrucción para cambiar el estado de un pin GPIO.

Sugiera agregar una declaración dando el chip de destino.

El problema con su código es que está apagando el LED después de un retraso. Que no es el requisito. En su lugar, debe alternar el LED cada vez que se presiona el botón. Compruebe el siguiente código:

int main(void)
 {
    int flag=0;
    DDRC |= (1<<PC0); //Makes first pin of PORTC as Output
    DDRD &= ~(1<<PD0);//Makes firs pin of PORTD as Input

    while(1) //infinite loop
    {
        if(PIND & (1<<PD0) == 1) //If switch is pressed
        {
            flag=~flag;
        }
        PORTC = (1<<PC0) | flag  ; //Toggle the LED
    }
}