8 votos

Las diferencias entre las Interrupciones y muestreo de botón de hardware?

Tengo un botón de hardware me he conectado a una interrupción, pero mi problema es que rebota un poco, haciendo que el botón pulse poco fiables. Creo que una buena parte de estos problemas podrían ser resueltos por muestreo en el bucle principal, pero que sólo se siente técnicamente incorrecto.

Se interrumpe el más apropiado para el comercio intra-circuito de comunicación o se interrumpe también es adecuado para conmutadores de hardware? Si es así lo que de rebote técnicas puedo utilizar?

He tratado de mantener un contador de tiempo variable y la comprobación contra la corriente del tiempo, los retrasos, y otras técnicas. Parece como si los rebotes son tan rápidos que no importa.

8voto

AitorTheRed Puntos 241

Eliminación de rebotes es un FAQ. Usted debe ser capaz de encontrar... casi un número ilimitado de páginas web sobre el tema. Smith comentó acerca de Jack Ganssle ampliamente leer PDF sobre el tema, así. Y con todas estas respuestas tienes tanto de hardware como de software métodos.

Voy a añadir a esta "literatura" sólo un poco por sobre todo hablando de ideas que no son ya bien cubierto. Pero, antes de hacerlo, un punto o dos:

  1. Eliminación de rebotes en hardware analógico puede lograr resultados que no se puede lograr por medio de un interruptor "observado" sólo digitalmente sobre una base periódica, mediante el sondeo o incluso por el pin de hardware-cambio de eventos. Pero se puede hacer "lo suficientemente bien", para todos los intentos y propósitos, digitalmente. Casi nadie en estos días los usos analógicos externos eliminación de rebotes de soluciones. Pero yo he usado de todo, desde el pulso de estiramiento mediante one-shot (74121) a las técnicas mencionadas por Jack Ganssle aquí.
  2. Para aquellos que hacen de programación incrustados y no sólo a todos los interesados en aprender acerca de la electrónica, eliminación de rebotes de los conmutadores es, probablemente, uno de los dos conjuntos de habilidades necesarias. Funcionamiento de los LEDs es probablemente el otro. Y por esto, no me refiero a tener sólo una habilidad en estas. Me refiero a ser capaz de hacerlo en un número de maneras. Así que usted realmente hacer necesaria para aprehender lo que Jack Ganssle escribe acerca de, y más aún, con respecto a los interruptores.

Ya he mencionado el pulso de estiramiento mediante un 74121 y desde Jack Ganssle ¿ no lo mencionan, y tampoco nadie aquí todavía, me puede proporcionar este enlace adicional de lectura sugerida sobre el uso de la 74121 o 555 como un one-shot temporizador de eliminación de rebotes de los interruptores.


Ahora, a hacer esto a través de la observación con un microcontrolador.

Yo normalmente uso una máquina de estado para manejar eliminación de rebotes. Esto es casi siempre impulsados por un "latido" timer I a \$8\:\textrm{ms}\$, donde sea posible. (Yo generalmente NO utilizar edge-triggered eventos de interrupción por varias razones.)

El estado de la máquina se parece a esto:

schematic

simular este circuito – Esquema creado mediante CircuitLab

El valor de REBOTADA por el interruptor, puede tomar en "inactivo", "activo", y "desconocido" de los valores. De esta manera, usted puede asegurarse de que su software de espera hasta que el interruptor de valor se sitúa después de la inicialización. Pero por lo general, no me molestes con eso. Puedo reemplazar el "desconocido" valor con algún valor por defecto, y sólo tiene que utilizar un valor binario del sistema, en lugar.

El estado de la máquina se introduce por primera configuración de la rebotada valor predeterminado y, a continuación, entrar en el "CAMBIO" estado de la máquina de estado. En cada intervalo de tiempo (normalmente \$8\:\textrm{ms}\$ si me puede conseguir lejos con él), voy a leer el interruptor de corriente de valor y realizar una actualización de la situación actual y, posiblemente, el rebotada valor. A continuación, me acaba de salir. El alto nivel de código, a continuación, sólo tiene acceso a rebotada del estado.

Si a mí me importa, yo podría también mantener un antes rebotada del estado. En estos casos, cuando la actualización de la rebotada propio estado, en primer lugar se copia ese estado a un 'antes de rebotada del estado". Puedo utilizar el par de valores para determinar si ha habido una rebotada de transición. A veces, no me importa acerca de las transiciones. A veces, lo hago yo. Así que depende. Pero en todos los casos, solo quiero saber acerca de las transiciones que han sido rebotada. Yo nunca la atención sobre el runt transiciones. Tan alto nivel de código no utiliza ninguno de los internos que el estado de la máquina se utiliza para su propio trabajo.

Una de las cosas buenas acerca de este método es que puedo rebote todo un puerto de interruptores a la vez. Y yo no puedo hacer esto sin una sola rama en el código de interrupción, demasiado. Esto significa que es muy rápido y corto depuración de código hasta el puerto de ancho del microcontrolador (generalmente de 8 bits de ancho.) Un ejemplo de Atmel AT90 muestra cómo se logra esto mediante un evento de interrupción Timer0:

.equ    SWPORTPINS  =   PINB
.def    SwRawCurr   =   r4
.def    SwRawPrev   =   r5
.def    SwState     =   r6
.def    SwDebCurr   =   r7
.def    SwDebPrev   =   r8

            ; Debounce the input switches.

                mov     SwRawPrev, SwRawCurr
                in      SwRawCurr, SWPORTPINS
                mov     Timer0Tmp1, SwRawCurr
                eor     Timer0Tmp1, SwRawPrev
                mov     Timer0Tmp0, Timer0Tmp1
                or      Timer0Tmp1, SwState
                mov     SwState, Timer0Tmp0
                mov     Timer0Tmp0, Timer0Tmp1
                com     Timer0Tmp0
                and     Timer0Tmp1, SwDebCurr
                and     Timer0Tmp0, SwRawCurr
                or      Timer0Tmp1, Timer0Tmp0
                mov     SwDebPrev, SwDebCurr
                mov     SwDebCurr, Timer0Tmp1

Ahora, en este ejemplo se muestra toda la oferta, incluyendo la anterior y la actual rebotada interruptor de valores. Y realiza todas las transiciones de estado. No muestro la inicialización de este código. Pero el de arriba se pone el punto sobre lo fácil de la máquina de estado es operar y cómo poco código es necesario para hacerlo. Es muy rápido y sencillo y no requiere de ramificación (que a veces implica ciclos adicionales así como código adicional de espacio.)


Yo prefiero usar \$8\:\textrm{ms}\$ temporización porque, mucho, mucho tiempo de pruebas con una variedad de personas diferentes, utilizando equipos que yo he trabajado en el pasado me ha llevado allí. He tratado de períodos más largos y cuando lo hago, empiezo a tener la gente me dice que la "capacidad de respuesta" no "enérgico" suficiente. (En estos días, con los niños que crecen de trabajo en tiempo real "shoot 'em up" de juego, que incluso podría acortar aún más. Ellos se quejan amargamente de incluso pequeños retrasos causados por los modernos Televisores digitales en la creación y visualización de un marco.)

Algunas personas tienen muy claro los sentimientos acerca de cómo crujiente y sensible de un sistema. Crujiente y sensible significa que la muestra más a menudo, no menos. Pero yo, personalmente, encontrar \$20\:\textrm{ms}\$ periodos de observación aceptable. (Yo no encontrar más veces lo suficientemente bueno para mí, sin embargo.)

Por favor, tenga en cuenta que el estado de la máquina que he mencionado, debe introducir primero el estado estable y, a continuación, permanecer ahí durante un tiempo de la muestra antes de que el valor de REBOTADA se actualiza. Así que presionar un botón y se mantiene, incluso en las mejores circunstancias, se requieren estas transiciones:

  1. cambio de reiterada a CAMBIAR
  2. cambio de CAMBIO para el arreglo de
  3. estancia en ASENTARON, la actualización de REBOTADA

Por tanto, un nuevo rebotada estado requiere un mínimo de 3 muestras períodos de tiempo para lograr.

Un botón pulsador se requieren al menos 6 veces la muestra para ir de inactivo a activo y, a continuación, volver a inactivo.


He mencionado los datos mencionados, por lo que es absolutamente claro que una muestra del tiempo de \$8\:\textrm{ms}\$ significa que en algún lugar entre \$16\:\textrm{ms} \lt t \le 24\:\textrm{ms}\$ ir de inactivo a un reconocido activo rebotada resultado. Y otros \$24\:\textrm{ms}\$ antes de que el estado puede volver a inactivo. Que un mínimo de \$40\:\textrm{ms} \lt t \le 48\:\textrm{ms}\$ a ir a través de todo un pulsador ciclo.

El uso más veces la muestra tendrá correspondientemente largos periodos de tiempo. El uso de la \$20\:\textrm{ms}\$ mencioné como "aceptable" para mí ya significa, entonces, en algún lugar alrededor de \$100\:\textrm{ms} \lt t \le 120\:\textrm{ms}\$ durante todo un pulsador ciclo. Y que está recibiendo de lleno en la zona donde las personas hacen tienden a notar. Yo ciertamente no como el "sentir" si se pone un poco más que eso.

Si usted va esta ruta, no desdeñes sobre el uso más veces la muestra. Si usted debe, entonces creo que usted también debe hacer un montón de pruebas con los usuarios/consumidores.

Y si eres de desarrollo de código para escribir un teclado, a continuación, utilizar tiempos más cortos. El registro de un mecanógrafo fue establecido hace décadas en el 217 wpm. Esto se traduce en alrededor de una clave de cada \$45\:\textrm{ms}\$. Mecanógrafos como que están golpeando a varias claves de forma controlada en un pedido. Para obtener un buen rendimiento muy rápido mecanógrafos el uso de mercurio en contacto relé reed sistema de conmutación, me encontré con que \$2\:\textrm{ms}\$ funcionado bien.

5voto

ozmank Puntos 127

De rebote puede ser hecho en el software mediante el enmascaramiento de IRQ para el tiempo de rebote o en hardware mediante la adición de un holding de condensadores con su RC =T > tiempo de rebote que van desde 1 a 15 ms, dependiendo del tamaño del interruptor.

  • por ejemplo, 100k pullup y 0.1 µF a través del interruptor = 10ms @63% o ~8ms al 50%Vdd o si el uso de Disparador de Schmitt puerta @1.33 V=Vil de 5V o ~73% V+ ~12ms

4voto

Bart Roozendaal Puntos 370

Para hacer un SW de rebote, el registro de la marca de tiempo de evento actual y verificación de demora desde el último evento válido:

#define DELAY_DEBOUNCE       150

uint32_t    __ts_lastpress = 0;

ISR(some_vector)
{
    uint32_t    now = millis(); // some timer tick counter

    if ( now - __ts_lastpress < DELAY_DEBOUNCE )
        return; // ignore it

    __ts_lastpress = now;
    // do the job here
}

UPD: con pequeña modificación puede registrar doble clic:

#define DELAY_DEBOUNCE       150
#define DELAY_DOUBLE_CLICK   600

uint32_t    __ts_lastpress = 0;

ISR(some_vector)
{
    uint32_t    now = millis(); // some timer tick counter

    if ( now - __ts_lastpress < DELAY_DEBOUNCE )
        return; // ignore it

    // do the job here
    if ( now - __ts_lastpress < DELAY_DOUBLE_CLICK )
    {
        // it is double click
    }
    else
    {
        // it is single click
    }

    __ts_lastpress = now;
}

2voto

Pedro Mantovani Puntos 29

Las interrupciones son definitivamente ideal para conmutadores de hardware también. Mediante el uso de interrupciones, de evitar un gran desperdicio de recursos y, posiblemente, de la energía, especialmente si se trata de la batería de dispositivos alimentados.

También, como su código se hace más grande y más grande, verás que es aún más fácil de implementar las interrupciones para los botones de votación en el ciclo principal.

Como para su depuración, es probable que sea un problema de codificación. Yo por lo general uso un ~temporizador de 10 ms para la eliminación de rebotes, mientras que la comprobación de la liberación del botón. Asegúrese también de desactivar temporalmente el botón de interrupción, mientras que de rebote, por lo que la rutina de interrupción no se ejecuta varias veces.

Si usted todavía tiene problemas, a publicar el código aquí, para que podamos ayudar.

1voto

Vijay C Puntos 111

Esto es bastante similar a la de Tony Stewart Respuesta, pero creo que podría ser ampliado.

La parte superior esquemático es para una interrupción en el bajo o en flanco de bajada. La parte inferior esquemático es una interrupción en alta o un flanco de subida.

schematic

simular este circuito – Esquema creado mediante CircuitLab

personalmente, dado el costo de un condensador, es pena para mí, simplemente, el uso, en lugar de tener que preocuparse por si mi software de rebote es el buggy.

Tenga en cuenta que como Tony Stewart dijo, la constante de tiempo en este circuito es de 10ms \$(R * C\$ o \$10k\Omega * 1 \mu F) \$. Va a tomar algún lugar de tres a cinco constantes de tiempo (dependiendo de la sensibilidad de su microcontrolador para el botón para restablecer a sí mismo, así que si el microcontrolador tiene problemas con la repetición de la función de la interrupción, que puede ser la causa, y usted puede necesitar ajustar la tapa/resistencia para hacer que la interrupción no suceder varias veces (es decir, sólo si la interrupción se puso a trabajar en una señal alta o baja, y no el flanco ascendente o descendente.

Relacionados con el Hardware eliminación de rebotes

i-Ciencias.com

I-Ciencias es una comunidad de estudiantes y amantes de la ciencia en la que puedes resolver tus problemas y dudas.
Puedes consultar las preguntas de otros usuarios, hacer tus propias preguntas o resolver las de los demás.

Powered by:

X