AYUDA: ruido eléctrico en entradas digitales? (SOLUCIONADO)

  • 16 Respuestas
  • 691 Vistas

guille

  • Aprendiz
  • **
  • Mensajes: 20
Hola gente del foro!

Estoy automatizando una seleccionadora de granos con un STX8091, placa de expansión STX570 y HMI Array SH300.

Debo manejar 5 actuadores lineales con motor de CC, que mueven 5 compuertas. Dichos actuadores me proporcionan salida potenciométrica y al final de su recorrido tienen instalados finales de carrera inductivos. Además, debo comandar 2 variadores que manejan motores trifásicos de 1 y 20HP.

Cuando la máquina inicia en frio, posiciona las compuertas y configura y activa los variadores. El programa permite modificar todos los parámetros sobre la marcha. Es aquí cuando se repite más el problema, cuando están ambos motores andando.

Mi problema es el siguiente:

Cuando inicio la rutina de posicionar los actuadores, el soft erráticamente se saltea pasos, ya que detecta que el final de carrera esta activado (cuando no lo esta!). El código en cuestión es el siguiente (sólo esa parte):

Código: (Pawn) [Seleccionar]

   for(new i=1;i<=5;i++)
{
POTENCIOMETRO=VinRead(i+3)

LedOff()

/////////////////////////DEBUG/////////////////////////////////////
debug_point:
        if(!DinValue(DIN13)) goto debug_point
///////////////////////////////////////////////////////////////////

BitSet(Salida,i-1)

if(POTENCIOMETRO<=SetPoint_Compuertas[i]) OpenClose=0
else OpenClose=1

if(!OpenClose)
{
//Abrir
while(POTENCIOMETRO<=SetPoint_Compuertas[i])
{

if(DinReadFiltered(i))
{
LedOn()
break //Final de carrera?
}

POTENCIOMETRO=VinRead(i+3)
DelayMS(60)
DoutSetOn(Salida)
}
DoutSetOff(Salida)
}
else
{
//Cerrar
while(POTENCIOMETRO>=SetPoint_Compuertas[i])
{

if(EXT_DinReadFiltered(i))
{
LedOn()
break//Final de carrera?
}

POTENCIOMETRO=VinRead(i+3)
DelayMS(60)
Stx570_DoutSet(0, Salida)

}
Stx570_DoutClr(0, Salida)
}

BitClr(Salida,i-1)

  /////////////////////////DEBUG/////////////////////////////////////
debug_point2:
   if(!DinValue(DIN13)) goto debug_point2
          ///////////////////////////////////////////////////////////////////


}

La funciones DinReadFiltered y EXT_DinReadFiltered son códigos de antirrebote que saqué de acá, escritos por Boris. Llego a probar con tiempos de hasta 600mS para evitar el ruido, pero igual se mete. Los inductivos usados son IFM7100, que indican una frecuencia de operación de 800HZ, por lo cual con un tiempo de "antirrebote" mayor a 1.25mS estaría cubierto... (?). Las compuertas se mueven a 1mm/seg, por lo cual no tendría problemas de velocidades excesivas.

Los debug point los utilizo como puntos de debug de hardware, para detener el programa y observar como se modificaron las variables en el HMI, actuador por actuador. La placa de expansión tiene LEDs que indican si se activo o no una entrada: sucede que a veces este LED está apagado y el programa sale por el "break"....

Cumplí todas las siguientes recomendaciones con respecto al ruido, obtenidas también de este foro:

1. Conectar a tierra la bornera GND del PLC y placa de expansión.
2. La tierra tiene que ser mediante jabalina y muy cerca de la instalación.
3. Poner a tierra también gabinetes, partes metálicas, mallados, etc.
4. Utilizar cables mallados para las conexiones, con su malla conectada a tierra.
5. No pasar cerca del PLC o lógica (por arriba o abajo) los cables de potencia u otros del tablero.
6. Utilizar contactores o reles secundarios (desmontables) en lo posible para comandar las válvulas.
7. Colocar un circuito-serie RC con un valor de capacitor (0.1uF cerámico) y resistencia (220 ohms), en paralelo a la parte de potencia de las válvulas, donde conmuta o en su defecto, cerca del la bobina del contactor o rele secundario utilizado.
8. No pasar cerca del cable de control de la STX570A señales de potencia.

3.---> El tablero trifásico al cual se conecta la máquina esta debidamente puesto a tierra, pero la jabalina no esta "muy cerca".
4.--->El cableado de los sensores se lleva por un caño metálico corrugado con recubrimiento plástico, el cual está conectado a GND.
7.---> coloqué ese circuito RC en la entrada de todos los finales de carrera.

Espero que puedan ayudarme porque ya llevo más de dos semanas con el mismo problema y estoy agotando las posibles soluciones!

Muchas gracias! Saludos!


« Última Modificación: agosto 11, 2017, 16:32:20 pm por Soporte »

Soporte

  • Global Moderator
  • Experto
  • *****
  • Mensajes: 1848
  • Soporte Técnico
Re:AYUDA: ruido eléctrico en entradas digitales?
« Respuesta #1 : mayo 16, 2017, 20:44:55 pm »
Buenas tardes Guillermo,

Te hago algunas consultas debajo de tus comentarios, para entender mejor y ver como solucionar el ruido.

Debo manejar 5 actuadores lineales con motor de CC, que mueven 5 compuertas. Dichos actuadores me proporcionan salida potenciométrica y al final de su recorrido tienen instalados finales de carrera inductivos. Además, debo comandar 2 variadores que manejan motores trifásicos de 1 y 20HP.

¿ Como conectas los actuadores de CC ?.

¿ Es decir, los activas usando un rele de interface o directamente conectado al PLC ? ¿ Que tensión de control ?.

¿ Los activas con el PLC o con las salidas de expansión ?.

Cuando la máquina inicia en frio, posiciona las compuertas y configura y activa los variadores. El programa permite modificar todos los parámetros sobre la marcha. Es aquí cuando se repite más el problema, cuando están ambos motores andando.

¿Los variadores los manejas con la salidas analogicas 0-10V?.

¿Crees que los variadores generan el ruido o que son los actuadores de CC cuando los prendes/apagas?.

¿A que velocidad en tiempo se prenden apagan los actuadores de CC normalmente (mas o menos, cada 1 segundos, cada cientos de mS ...) ?

Mi problema es el siguiente: Cuando inicio la rutina de posicionar los actuadores, el soft erráticamente se saltea pasos, ya que detecta que el final de carrera esta activado (cuando no lo esta!).

Creo que es porque esta introduciéndose como bien decís un ruido, por ello lee una entrada erraticamente.
Aunque luego analizaré mejor el código según tu respuesta.

La funciones DinReadFiltered y EXT_DinReadFiltered son códigos de antirrebote que saqué de acá, escritos por Boris. Llego a probar con tiempos de hasta 600mS para evitar el ruido, pero igual se mete. Los inductivos usados son IFM7100, que indican una frecuencia de operación de 800HZ, por lo cual con un tiempo de "antirrebote" mayor a 1.25mS estaría cubierto... (?). Las compuertas se mueven a 1mm/seg, por lo cual no tendría problemas de velocidades excesivas.

Esta parte no me queda clara.

¿ Los fines de carrera te entregan una salida estatica "1" o "0" fija, o es una señal cuadrada con una frecuencia de 800 Hz ?


Los debug point los utilizo como puntos de debug de hardware, para detener el programa y observar como se modificaron las variables en el HMI, actuador por actuador. La placa de expansión tiene LEDs que indican si se activo o no una entrada: sucede que a veces este LED está apagado y el programa sale por el "break"....

No descarto ruido, pero si la entrada es pulsante, puede ser leída más rápida de lo que el led tarda en prenderse y apagarse.

7.---> coloqué ese circuito RC en la entrada de todos los finales de carrera.

Si es baja tensión (12 o 24V) podrías utilizar solo un capacitor más grande, sin la resistencia, de 100 uF / 50V (electrolítico) para hacer más lenta su respuesta.

Espero tus comentarios para analizar mejor.
« Última Modificación: mayo 16, 2017, 20:52:01 pm por Soporte »
SOPORTE TÉCNICO

Slicetex Electronics
www.slicetex.com

guille

  • Aprendiz
  • **
  • Mensajes: 20
AYUDA: ruido eléctrico en entradas digitales?
« Respuesta #2 : mayo 17, 2017, 14:03:38 pm »
Hola Boris!

En respuesta a tus preguntas:

¿ Como conectas los actuadores de CC ?.
¿ Es decir, los activas usando un rele de interface o directamente conectado al PLC ? ¿ Que tensión de control ?.
¿ Los activas con el PLC o con las salidas de expansión ?.

Los motores se activan manejando un puente H con dos relés en 12V, según se active uno o el otro, cambiará el sentido de la corriente. Cada actuador es manejado por 2 salidas, para abrir (de DO1 a DO5) o cerrar(de EDO1 a EDO5).

¿Los variadores los manejas con la salidas analogicas 0-10V?.
El variador se maneja con 2 salidas digitales para subir o bajar velocidad y una entrada analógica 4..20mA que retroalimenta la velocidad actual.
*MOTOR 1 (1HP) : +DOUT8,-EDOUT8, VIN2
*MOTOR 2 (20HP) : +DOUT9,-DOUT10,VIN3

¿Crees que los variadores generan el ruido o que son los actuadores de CC cuando los prendes/apagas?.
Creo que es cuando enciendo los motores que me aparece con mas frecuencia este bug, pero a veces me lo hace en frio y realmente me desconcierta!!

¿A que velocidad en tiempo se prenden apagan los actuadores de CC normalmente (mas o menos, cada 1 segundos, cada cientos de mS ...) ?
En el código existe un DelayMS(60), que es debido al tiempo de espera para que se actualice el conversor AD y lea la entrada del pote y detenga el actuador. También hay que sumarle el tiempo de la función antirrebote que está actualmente en 350mS.

¿ Los fines de carrera te entregan una salida estatica "1" o "0" fija, o es una señal cuadrada con una frecuencia de 800 Hz ?
Si, me exprese mal! La salida de los inductivos es NA, entrega 0 o 1, claro. Hay un dato de "frecuencia de conmutación" en la hoja de datos que yo interpreté que esa era la ventana en la que el inductivo puede "ver" un ruido.... (?) .. Entonces en base a ese dato, 800Mhz, establecí un filtro "antirrebote" varias veces mas grande... Llegue hasta los 600mS!! Pero el problema persiste.. Igualmente esta interpretación de la hoja de datos puede ser un bolazo... jajaja..

Gracias por tu ayuda!
« Última Modificación: mayo 17, 2017, 14:07:00 pm por guille »

Soporte

  • Global Moderator
  • Experto
  • *****
  • Mensajes: 1848
  • Soporte Técnico
Re:AYUDA: ruido eléctrico en entradas digitales?
« Respuesta #3 : mayo 17, 2017, 21:34:02 pm »
Buenas Guillermo,

Los motores se activan manejando un puente H con dos relés en 12V, según se active uno o el otro, cambiará el sentido de la corriente. Cada actuador es manejado por 2 salidas, para abrir (de DO1 a DO5) o cerrar(de EDO1 a EDO5).

¿Los puentes H los controlas con algun rele similar a este (ver foto abajo) desde el PLC ?:




Estos reles tienen en general un diodo volante (es decir un diodo que va opuesto a la bobina) para minimizar el ruido.
Se los puede poner externamente, pero son más practicos y confiables si lo tienen adentro.

La siguiente imagen muestra por dentro este rele:




El diodo en ese tipo de reles, va conectado por dentro como el siguiente diagrama a modo ejemplo (eliminando picos de tensión):



¿Los variadores los manejas con la salidas analogicas 0-10V?.
El variador se maneja con 2 salidas digitales para subir o bajar velocidad y una entrada analógica 4..20mA que retroalimenta la velocidad actual.
*MOTOR 1 (1HP) : +DOUT8,-EDOUT8, VIN2
*MOTOR 2 (20HP) : +DOUT9,-DOUT10,VIN3

¿Aca tambien usas reles de interface para el control entre el PLC y el control del motor?

Creo que es cuando enciendo los motores que me aparece con mas frecuencia este bug, pero a veces me lo hace en frio y realmente me desconcierta!!

En el código existe un DelayMS(60), que es debido al tiempo de espera para que se actualice el conversor AD y lea la entrada del pote y detenga el actuador. También hay que sumarle el tiempo de la función antirrebote que está actualmente en 350mS.

Pienso que son ambas cosas, de alguna forma se induce el ruido a la placa cuando conmutas los motores de CC y los trifasicos.

Para solucionar de forma permanente, veo las siguientes medidas:

  • En primer lugar colocar reles de interfase como te mostré en la foto (te puedo enviar algunos para que pruebes, luego arreglamos) para controlar las salidas, asi minimizas ruido.
  • Poner alguna fuente de mejor calidad para el PLC, con filtros de línea, tambien te puedo enviar la fuente STX612 para que pruebes (a menos que ya estes usando alguna de buena calidad).
  • Por último, si estos pasos no mejoran, aislar salidas mediante optoacopladores, de esta forma quedan bien separadas electricamente del PLC, y el ruido no se induce. Aca podria ser alguna solución comercial con reles de estado solido o mediante alguna plaquetita, aca tambien te podemos ayudar.

Decime que te parece, asi vemos de dar los siguientes pasos.

Saludos
« Última Modificación: mayo 19, 2017, 21:13:56 pm por Soporte »
SOPORTE TÉCNICO

Slicetex Electronics
www.slicetex.com

guille

  • Aprendiz
  • **
  • Mensajes: 20
Re:AYUDA: ruido eléctrico en entradas digitales?
« Respuesta #4 : mayo 29, 2017, 11:34:43 am »
Hola Boris,

te comento que los relays instalados son marca IDEC,  los siguientes modelos:

Variadores:  base + rele = SV1H-07L-1 + RV1H-G-12
Actuadores: RJ1S-C-D12

Ninguno tienen diodo de protección, según indican sus hojas de datos:

https://www.kele.com/Catalog/20%20Relays_Contactors/PDFs/RV8H%20Data%20Sheet.pdf
https://www.idec.com/language/english/catalog/Relays/RJSeries.pdf

Por el momento voy a probar con agregar protecciones externas a los relays. Ambas hojas de datos indican circuitos de protección en su penúltima página. Vos recomendás alguno de esos? Coloco un diodo o un RC?

Después de esta modificación, veré si hace falta una fuente de mejor calidad. La instalada es marca "X", voy a probar con un Siemens.

Gracias por tu asistencia!

Saludos!

Soporte

  • Global Moderator
  • Experto
  • *****
  • Mensajes: 1848
  • Soporte Técnico
Re:AYUDA: ruido eléctrico en entradas digitales?
« Respuesta #5 : mayo 29, 2017, 18:56:15 pm »
Buenas tardes Guillermo,

te comento que los relays instalados son marca IDEC,  los siguientes modelos:
Variadores:  base + rele = SV1H-07L-1 + RV1H-G-12
Actuadores: RJ1S-C-D12

Ese rele RJ1S-C-D12 parece de ruidoso por la bobina de gran tamaño que tiene, suelen funcionar como una antena.
¿No podés utilizar los reles que tenes para el variador?.

Por el momento voy a probar con agregar protecciones externas a los relays. Ambas hojas de datos indican circuitos de protección en su penúltima página. Vos recomendás alguno de esos? Coloco un diodo o un RC?



El RC se coloca del lado del contacto o carga del rele. Podes probar los valores que te recomienda la documentación que me pasaste (adjunto imagen arriba).
Por ej. en serie: 100 ohms + 100nF, 1uF, 10uF.
La segunda opción del RC en la imagen es la más recomendada, es decir en paralelo con la carga.

El diodo, puede ir de lado de la carga (si es corriente continua) o del lado de la bobina/PLC, o de ambos lados al mismo tiempo.
Puede ser un diodo 1N4006 o 1N4007 por ejemplo.

Los relay que tengo son Zoloda P/N 221.017, te puedo enviar por transporte para que pruebes de forma rápida algunos, sino conseguís en algún local cercano.

Quedo a disposición. Saludos.
« Última Modificación: mayo 29, 2017, 19:02:47 pm por Soporte »
SOPORTE TÉCNICO

Slicetex Electronics
www.slicetex.com

guille

  • Aprendiz
  • **
  • Mensajes: 20
Re:AYUDA: ruido eléctrico en entradas digitales?
« Respuesta #6 : junio 28, 2017, 17:45:43 pm »
Hola Boris,

después de probar las siguientes configuraciones:

1-RC 100ohm 10uF entre relays y actuadores - Diodo 1N4007 entre PLC y relays

2-RC 100ohm 10uf en entrada de finales de carrera inductivos - Diodo 1N4007 entre PLC y relays.

3-Tengo 3 fuentes de DC; vinculé todos los GND y los conecte al chasis y a la puesta a tierra del tablero.

4-Los variadores tienen una conexión del chasis a GND, pero creo que es en AC. (Se entiende?) Es conveniente unir las tierras/masas AC y DC??

No logro dar con el problema de "ruido" y empiezo a pensar si no habrá un problema de formatos o "representación" numéricos en la comparación del valor analógico leído y el set point...

Inicialmente se calibran los actuadores: se los hace recorrer a todos desde el final de carrera 0% hasta el final de carrera 100%, se toman los valores de potenciómetro "inicial" y "final", se restan y se dividen por 10, obteniéndose un valor de "escalón" para cada actuador.

....PORCIÓN RUTINA CALIBRADO....

for(new i=1;i<=5;i++) STEPS=Float:(POT_Fin-POT_Inicio)/10

         EepromWriteCells(52,6,STEPS)
         EepromWriteCells(76,6,POT_Inicio)

....PORCIÓN RUTINA CALIBRADO....

El usuario puede elegir entre estos 11 escalones (0 incluido!) mediante el HMI para determinar la posición del actuador. La siguiente linea de codigo calcula el setpoint

for(new i=1;i<=5;i++) SetPoint_Compuertas=FloatToInt(X[i+1]*STEPS) + POT_Inicio // + Offset!

El vector X contiene los numeros del 0 al 10.

Cuando se da arranque al programa, y remitiéndome al codigo anterior,
Citar

      for(new i=1;i<=5;i++)
      {
         POTENCIOMETRO=VinRead(i+3)
      
         LedOff()
         
         /////////////////////////DEBUG/////////////////////////////////////
         debug_point:
              if(!DinValue(DIN13)) goto debug_point
         ///////////////////////////////////////////////////////////////////

         BitSet(Salida,i-1)
            
         if(POTENCIOMETRO<=SetPoint_Compuertas) OpenClose=0
         else OpenClose=1
      
         if(!OpenClose)
            {
            //Abrir
            while(POTENCIOMETRO<=SetPoint_Compuertas)
             {
               
               if(DinReadFiltered(i))
               {
                  LedOn()
                  break    //Final de carrera?
               }
               
               POTENCIOMETRO=VinRead(i+3)
               DelayMS(60)
               DoutSetOn(Salida)
             }
            DoutSetOff(Salida)
            }   
         else
            {
            //Cerrar
            while(POTENCIOMETRO>=SetPoint_Compuertas)
             {
               
               if(EXT_DinReadFiltered(i))
               {
                  LedOn()
                  break//Final de carrera?
               }
               
               POTENCIOMETRO=VinRead(i+3)
               DelayMS(60)
                Stx570_DoutSet(0, Salida)
               
             }
             Stx570_DoutClr(0, Salida)
         }
         
         BitClr(Salida,i-1)
         
        /////////////////////////DEBUG/////////////////////////////////////
         debug_point2:
         if(!DinValue(DIN13)) goto debug_point2
             ///////////////////////////////////////////////////////////////////
         

      }

La conversión AD devuelve un SIGNED de 12 bits, que puede ser complemento a 0. El valor de Setpoint se almacena en una variable cell de 32bits. Y los datos de la EEPROM son de tipo cell, 32bits. Es posible que exista algun error de truncado, conversión, formato, y que esto lleve a una comparación errónea en el programa??

Agradezco tu ayuda ya que realmente no logro encontrar cual es el problema.

Saludos!

Guillermo.

Soporte

  • Global Moderator
  • Experto
  • *****
  • Mensajes: 1848
  • Soporte Técnico
Re:AYUDA: ruido eléctrico en entradas digitales?
« Respuesta #7 : junio 29, 2017, 13:53:00 pm »
Buenos días Guillermo,

3-Tengo 3 fuentes de DC; vinculé todos los GND y los conecte al chasis y a la puesta a tierra del tablero.

Si la fuente con que alimentas los reles externos o entradas digitales, es diferente a la del PLC, no compartas la masa. Ya que no es utilizada entre ambos y esto mejora la aislación.

4-Los variadores tienen una conexión del chasis a GND, pero creo que es en AC. (Se entiende?) Es conveniente unir las tierras/masas AC y DC??

No, la masa de AC no debe compartirse con la de DC, ya que las perturbaciones en la linea de AC estaran disponibles en la linea de DC.

No logro dar con el problema de "ruido" y empiezo a pensar si no habrá un problema de formatos o "representación" numéricos en la comparación del valor analógico leído y el set point...

Si, me pone en duda, de si es un tema de soft o externo.

Algo a considerar es como guardas los datos en EEPROM, es conveniente que si llamas varias veces seguido a las funciones de escritura, entre cada llamado exista un pequeño delay, ya que la EEPROM suele ser más lenta que el Microporcesador para guardar un dato, por lo tanto mientras intentas guardas el siguiente dato con una llamada write, el dato anterior todavía esta en proceso de guardarse e interrumpa el proceso. Esto es muy rápido, pero puede ser una posibilidad, ya que esta en el orden de los mili-segundos.

Entonces, entre cada escritura podrías agregar un pequeño delay de seguridad:

DelayMS(50)
EepromWriteCells()
DelayMS(50)
EepromWriteCells()


Inicialmente se calibran los actuadores: se los hace recorrer a todos desde el final de carrera 0% hasta el final de carrera 100%, se toman los valores de potenciómetro "inicial" y "final", se restan y se dividen por 10, obteniéndose un valor de "escalón" para cada actuador.

....PORCIÓN RUTINA CALIBRADO....

for(new i=1;i<=5;i++) STEPS=Float:(POT_Fin-POT_Inicio)/10

         EepromWriteCells(52,6,STEPS)
         EepromWriteCells(76,6,POT_Inicio)

¿ Usas valores Float para guardar en EEPROM ? Entonces dos notas:

1)

Para guardar en EEPROM, podes guardar el float normalmente, por ejemplo:

Código: (Pawn) [Seleccionar]
EepromWriteCells(Address, Len, FloatValues[])
Para recuperar los valores floats:

Código: (Pawn) [Seleccionar]
EepromReadCells(Address, Len, ValuesTemp)
Y luego convertís a Float:

Código: (Pawn) [Seleccionar]
FloatValue[x] = Float: ValuesTemp[x]
2) Conviene usar constantes como direcciones para guardar en memoria EEPROM, ya que evita que luego te confundas con los números o que estés sobre-escribiendo alguna dirección.

Código: (Pawn) [Seleccionar]
#define EEPROM_STEPS_INDEX_ADDRESS       (52)
EepromWriteCells(EEPROM_STEPS_INDEX_ADDRESS,6,STEPS)

....PORCIÓN RUTINA CALIBRADO....

El usuario puede elegir entre estos 11 escalones (0 incluido!) mediante el HMI para determinar la posición del actuador. La siguiente linea de codigo calcula el setpoint

for(new i=1;i<=5;i++) SetPoint_Compuertas=FloatToInt(X[i+1]*STEPS) + POT_Inicio // + Offset!

El vector X contiene los numeros del 0 al 10.

Esta bien el indice X[i+1] ?. No deberia ser X ?. Solamente comento, ya que probablemente tenga que ver con otro código y sea correcto.

      
         if(POTENCIOMETRO<=SetPoint_Compuertas) OpenClose=0
         else OpenClose=1
      
         if(!OpenClose)
            {
            //Abrir
            while(POTENCIOMETRO<=SetPoint_Compuertas)
             {
               
               if(DinReadFiltered(i))
               {
                  LedOn()
                  break    //Final de carrera?
               }
               
               POTENCIOMETRO=VinRead(i+3)
               DelayMS(60)
               DoutSetOn(Salida)
             }
            DoutSetOff(Salida)
            }   
         else
            {
            //Cerrar
            while(POTENCIOMETRO>=SetPoint_Compuertas)
             {
               
               if(EXT_DinReadFiltered(i))
               {
                  LedOn()
                  break//Final de carrera?
               }
               
               POTENCIOMETRO=VinRead(i+3)
               DelayMS(60)
                Stx570_DoutSet(0, Salida)
               
             }
             Stx570_DoutClr(0, Salida)
         }
         

Otro posibilidad es que se induzca alguna tensión al momento de leer el canal analógico en el cable y te de una lectura falsa, invalidandote la lógica.
Esto suponiendo que en laboratorio te anduviera bien.

Un capacitor de 100 nF o mas, entre VIN y AGND, puede hacer mas lenta la entrada analógica respecto a cambios bruscos de tensión.

La conversión AD devuelve un SIGNED de 12 bits, que puede ser complemento a 0. El valor de Setpoint se almacena en una variable cell de 32bits. Y los datos de la EEPROM son de tipo cell, 32bits. Es posible que exista algun error de truncado, conversión, formato, y que esto lleve a una comparación errónea en el programa??

Si usas el rango 0 a 10V o 0 a 5V de las entradas, no hay complemento a dos en la conversión, ya que no lees valores de tensión negativos. Así mismo toda la lectura es en 12 bits, que cabe en los 32-bits. Pero si debes prestar atención si guardas en EEPROM tipo float, para recuperarlo correctamente como te expliqué.

Bueno, si ves que seguís sin dar con mejora, avísame y tengo reles des estado solido para que conectes en los actuadores, estos aíslan el PLC de los motores de CC.

Saludos
SOPORTE TÉCNICO

Slicetex Electronics
www.slicetex.com

Soporte

  • Global Moderator
  • Experto
  • *****
  • Mensajes: 1848
  • Soporte Técnico
Re:AYUDA: ruido eléctrico en entradas digitales?
« Respuesta #8 : junio 29, 2017, 16:40:44 pm »
Una forma optima de evitar que la EEPROM este ocupada con la escritura previa, seria haciendo uso de la función EepromBusy().

Ejemplo:

Código: (Pawn) [Seleccionar]
// ********************************************************************************
// Funcion     : EepromWriteCheck()
// Descripcion : Escribe en memoria EEPROM comprobando si esta ocupada previamente.
//
// ENTRADA     :
//
//    - Address = Direccion de variable en memoria EEPROM.
//    - Len = Cantidad de elementos a escribir.
//    - Data[] = Array con datos a escribir.
//
// SALIDA      :
//
//    - (  0   ) = Operacion exitosa.
//      ( <0   ) = Error de escritura.
//
// ********************************************************************************

EepromWriteCheck(Address, Len, Data[])
{
   // Esperar que memoria este lista para escribir.
   for(new i=0; i < 10; i++)
   {
      if(EepromBusy())
      {
         PauseMS(10)
      }
      else
      {
         break
      }
   }
   
   // Escribir Data[] a partir de la dirección Address de la EEPROM.
   return EepromWriteCells(Address, Len, Data)
}
SOPORTE TÉCNICO

Slicetex Electronics
www.slicetex.com

guille

  • Aprendiz
  • **
  • Mensajes: 20
Re:AYUDA: ruido eléctrico en entradas digitales?
« Respuesta #9 : julio 10, 2017, 21:31:31 pm »
Hola Boris!

Ya corregi algunas cosas q me sugeriste: agregue un delay de 50mS despues de la lectura de EEPROM y la variable STEPS la hice entera, total no necesito los valores decimales.

Estuve probando la rutina, quitando la siguiente porción de código:

if(DinReadFiltered(i))
               {
                  LedOn()
                  break    //Final de carrera?
               }

 y

if(EXT_DinReadFiltered(i))
               {
                  LedOn()
                  break//Final de carrera?
               }


O sea, no tuve en cuenta los finales de carrera, pero sólo posicioné los actuadores en posiciones intermedias, evitando llegar a los extremos asi no me pasaba del tope mecánico.

El programa anduvo perfecto, sin errores. Descarto que el ruido ingrese por los relays de interfase o por las entradas analógicas de los potenciómetros. Tampoco observo un bug en la programación.

Luego volví a agregar el mencionado código y el bug apareció enseguida. Trate de filtrar la entrada de los finales de carrera con un RC, pero esto solo empeoró la cuestión. Entonces llego a la conclusión de que el ruido ingresa por acá.

Los FC utilizados son los siguientes:

https://www.ifm.com/products/ar/ds/IF7100.htm

Inductivos, M12, cuerpo metálico.

Me preguntaba, es posible que al estar en contacto con el chasis de la maquina el ruido ingrese por alli? Sera mejor aislar estos componentes? Como son NA, hay una interfaz de transistores que los cambia a NC, cuestión de comodidad. Podrá ingresar por aqui el ruido?

Segun tengo entendido IFM es una marca "respetable" (?). No encontré ni un solo foro en que alguien se quejara de algo como ruido....ni una queja! jajaa

Otro opcion seria optoaislar las entradas? (No es que el PLC tiene su circuiteria interna asi?)

Gracias por tu ayuda Boris!

Soporte

  • Global Moderator
  • Experto
  • *****
  • Mensajes: 1848
  • Soporte Técnico
Re:AYUDA: ruido eléctrico en entradas digitales?
« Respuesta #10 : julio 11, 2017, 12:28:46 pm »
Buenos días Guillermo,

Estuve probando la rutina, quitando la siguiente porción de código:

if(DinReadFiltered(i))
               {
                  LedOn()
                  break    //Final de carrera?
               }

 y

if(EXT_DinReadFiltered(i))
               {
                  LedOn()
                  break//Final de carrera?
               }


O sea, no tuve en cuenta los finales de carrera, pero sólo posicioné los actuadores en posiciones intermedias, evitando llegar a los extremos asi no me pasaba del tope mecánico.

El programa anduvo perfecto, sin errores. Descarto que el ruido ingrese por los relays de interfase o por las entradas analógicas de los potenciómetros. Tampoco observo un bug en la programación.

Luego volví a agregar el mencionado código y el bug apareció enseguida. Trate de filtrar la entrada de los finales de carrera con un RC, pero esto solo empeoró la cuestión. Entonces llego a la conclusión de que el ruido ingresa por acá.

¿Podrías pasarme el código que usas para las funciones DinReadFiltered(i) y EXT_DinReadFiltered(i)?

¿Es posible que solo uses el PLC para leer los fines de carrera y no el módulo de expansión?.

Quizás el ruido pueda estar relacionado a la expansión.

Los FC utilizados son los siguientes:

https://www.ifm.com/products/ar/ds/IF7100.htm

Inductivos, M12, cuerpo metálico.

Es muy raro que venga relacionado en "forma de ruido" el problema por las entradas discretas, ya que están opto-acopladas.

Este es el diagrama de conexión de los detectores-inductivos, ¿como lo conectas el PLC y con que tensión alimentas?:



Por ahí pienso que no estén generando un "0" o "1" correctamente en el PLC, es decir, que la tensión resultante aplicada quede dentro del margen de tensión (5-9V) donde para el PLC puede ser 0 o 1. Entonces la lectura sea indeterminada o variable. Porque fíjate, según hoja de datos dice "2.5V" de caída de tensión, si alimentas con +12, le resta y queda en 9.5V desde el vamos, pero depende de como lo conectes a las entradas.

¿El fin de carrera es estático de tensión, no?. ¿Es decir te pone un valor fijo cuando llega sin que variar hasta que sale de esa condición?.

Me preguntaba, es posible que al estar en contacto con el chasis de la maquina el ruido ingrese por alli? Sera mejor aislar estos componentes? Como son NA, hay una interfaz de transistores que los cambia a NC, cuestión de comodidad. Podrá ingresar por aqui el ruido?

Si mal no entiendo ¿Le pones otro transistor al sensor? . Pregunto, por lo que te mencioné antes, que no sea el caso que este cerrando/abriendo incorrectamente el circuito.

Si el chasis de la maquina hace contacto en alguna conexion electrica del sensor, como GND o alimentacion, entonces si es posible que entre ruido o tensiones inducidas en el chasis a la parte de DC (corriente continua) del sistema. Deberia estar aislado.

Otro opcion seria optoaislar las entradas? (No es que el PLC tiene su circuiteria interna asi?)

Claro, están opto-aisladas las entradas. Por eso suponía que si es tema de ruido, debería entrar el ruido cuando los motores o cargas inductivas entran en funcionamiento.

Espero tus comentarios.

Saludos
« Última Modificación: julio 11, 2017, 12:31:14 pm por Soporte »
SOPORTE TÉCNICO

Slicetex Electronics
www.slicetex.com

guille

  • Aprendiz
  • **
  • Mensajes: 20
Re:AYUDA: ruido eléctrico en entradas digitales?
« Respuesta #11 : julio 12, 2017, 20:11:08 pm »
Hola Boris!

Te pego el código antirrebote que saque de este foro:

//anti-rebote
DinReadFiltered(Din)
{
   new timeOut = 25
   new lastLevel = 0

   lastLevel = DinValue(Din)

   while(timeOut > 0) 
   {
      if(DinValue(Din) == lastLevel)
      {
          // Retardo de 500 mS.
          DelayMS(20)
          timeOut--
      }
      else
      {
          // Valor difiere al ultimo leído, reiniciar timeout.
          lastLevel = DinValue(Din)
          timeOut = 25
      }
   }

   return lastLevel
}

//anti-rebotes placa expansión
EXT_DinReadFiltered(Din)
{
   new timeOut = 25
   new lastLevel = 0

   lastLevel = Stx570_DinGetValue(0, Din)

   while(timeOut > 0) 
   {
      if(Stx570_DinGetValue(0, Din) == lastLevel)
      {
          // Retardo de 500 mS.
          DelayMS(20)
          timeOut--
      }
      else
      {
          // Valor difiere al ultimo leído, reiniciar timeout.
          lastLevel = Stx570_DinGetValue(0, Din)
          timeOut = 25
      }
   }

   return lastLevel
}


Existen en total 10 finales de carrera (5 actuadores) por el momento. Hay 5 conectados al PLC y 5 al módulo de expansión.

Con respecto al circuito, al tablero lo armaron otros contratistas y no hay planos completos todavía. Según lo que pude apreciar, parece que el modo de conexión es de 3 hilos: +,GND y Señal, que va la entrada del PLC y modulo de expansión. La tensión de alimentación es 12V y cuando conmuta he medido valores de 11V y pico. La interfaz "extra" de transistores creo que se utiliza sólo para la placa de expansión. (tengo que fijarme bien y en todo caso pedir planimetria precisa). En ningún lugar IFM dice que el cuerpo esta unido a algún contacto eléctrico ni tampoco advierte de su aislación de otros elementos metálicos "no sometidos a tension".

Gracias por tu ayuda!

Estamos en contacto,

Guille.

Soporte

  • Global Moderator
  • Experto
  • *****
  • Mensajes: 1848
  • Soporte Técnico
Re:AYUDA: ruido eléctrico en entradas digitales?
« Respuesta #12 : julio 13, 2017, 13:28:53 pm »
Buenos días Guillermo,

Hola Boris!

Te pego el código antirrebote que saque de este foro:

Ok, le voy a dar una revisada, especialmente la parte del módulo de expansión y te aviso.

Existen en total 10 finales de carrera (5 actuadores) por el momento. Hay 5 conectados al PLC y 5 al módulo de expansión.

Estaría bueno descartar problema de lectura del módulo y solo leer con el PLC.

Voy a ver si puedo modificarte la rutina del filtro para que compruebe antes errores de conexión entre PLC y módulo (cambiando la función Stx570_DinGetValue() por otra), ya que quizás retorna error la conexión al producirse el ruido y por lo tanto el valor devuelto es "0" como valor de entrada, cuando en realidad es "1".

Con respecto al circuito, al tablero lo armaron otros contratistas y no hay planos completos todavía. Según lo que pude apreciar, parece que el modo de conexión es de 3 hilos: +,GND y Señal, que va la entrada del PLC y modulo de expansión. La tensión de alimentación es 12V y cuando conmuta he medido valores de 11V y pico. La interfaz "extra" de transistores creo que se utiliza sólo para la placa de expansión. (tengo que fijarme bien y en todo caso pedir planimetria precisa). En ningún lugar IFM dice que el cuerpo esta unido a algún contacto eléctrico ni tampoco advierte de su aislación de otros elementos metálicos "no sometidos a tension".

El sensor IFM es transistor tipo PNP, es decir, un switch que va del lado de la fuente (arriba) en la conexión, y si lo conectas al PLC te quedaría mal, como te muestro en la imagen:



Quizás para el PLC usan los transistores, que habría que ver como los emplean al final.

Para conectarlo al modulo, seria posible por el tipo de interfaz que tiene el módulo internamente para las entradas, como te adjunto en la segunda imagen:



En el último caso, te pongo en el gráfico de "verificar caída de tensión", ya que si es muy grande le queda poco margen a la entrada del modulo.

Esto para que quede más claro, ya que con esquemas es mas fácil interpretar.

Te estoy pasando lo que te comenté de la función.

Saludos.
« Última Modificación: julio 13, 2017, 13:34:23 pm por Soporte »
SOPORTE TÉCNICO

Slicetex Electronics
www.slicetex.com

Soporte

  • Global Moderator
  • Experto
  • *****
  • Mensajes: 1848
  • Soporte Técnico
Re:AYUDA: ruido eléctrico en entradas digitales?
« Respuesta #13 : julio 15, 2017, 20:52:13 pm »
Buenas Guillermo,

Después de revisar más detenidamente tu código, me parece que el error esta en como seleccionas la entrada a leer, es decir un error numérico en el parámetro de la función, por ejemplo, yendo a tu código (ver partes señaladas en rojo):


      for(new i=1;i<=5;i++)
      {
         POTENCIOMETRO=VinRead(i+3)
      
         LedOff()
         
         /////////////////////////DEBUG/////////////////////////////////////
         debug_point:
              if(!DinValue(DIN13)) goto debug_point
         ///////////////////////////////////////////////////////////////////

         BitSet(Salida,i-1)
            
         if(POTENCIOMETRO<=SetPoint_Compuertas) OpenClose=0
         else OpenClose=1
      
         if(!OpenClose)
            {
            //Abrir
            while(POTENCIOMETRO<=SetPoint_Compuertas)
             {
               
               if(DinReadFiltered(i))
               {
                  LedOn()
                  break    //Final de carrera?
               }
               
               POTENCIOMETRO=VinRead(i+3)
               DelayMS(60)
               DoutSetOn(Salida)
             }
            DoutSetOff(Salida)
            }   
         else
            {
            //Cerrar
            while(POTENCIOMETRO>=SetPoint_Compuertas)
             {
               
               if(EXT_DinReadFiltered(i))
               {
                  LedOn()
                  break//Final de carrera?
               }
               
               POTENCIOMETRO=VinRead(i+3)
               DelayMS(60)
                Stx570_DoutSet(0, Salida)
               
             }
             Stx570_DoutClr(0, Salida)
         }
         
         BitClr(Salida,i-1)
         
        /////////////////////////DEBUG/////////////////////////////////////
         debug_point2:
         if(!DinValue(DIN13)) goto debug_point2
             ///////////////////////////////////////////////////////////////////
         

      }

Si te fijas, intentas usar la variable "i" que tiene el valor 1, 2, 3, 4 o 5, según se incrementa. Pero las funciones para leer entradas discretas, necesitan el "bit" a leer.

Por ejemplo:


 DIN1 = 00000001
 DIN2 = 00000010
 DIN3 = 00000100
 ...
 DIN8 = 10000000

 EDIN1 = 00000001
 EDIN2 = 00000010
 EDIN3 = 00000100
 ...
 EDIN8 = 10000000


Pero como les estas pasando un valor entre 1 y 5, te queda:

1 = 00000001 (selecciona para leer DIN1, bien)
2 = 00000010 (selecciona DIN2, bien)
3 = 00000011 (selecciona para leer DIN1 y DIN2 al mismo tiempo, mal)
4 = 00000100 (selecciona para leer DIN3, mal)
5 = 00000101 (selecciona para leer DIN3 y DIN1 al mismo tiempo, mal)

Creo que ese es el error que cometes.

No asi para activar las salidas, que usas BitXxx(Salida,i-1).

Para corregir rápido, podrías emplear:

DinReadFiltered(BIT(i-1))

EXT_DinReadFiltered(BIT(i-1))

La función BIT(x), es lo mismo que hacer (1 << x), es decir mueve "x" veces un bit a la izquierda.

Probalo y fíjate si ahora lees bien las entradas.
Como seguridad podrías verificar con un código separado, sin el resto de la lógica.

Saludos

PD: Para VinRead() se puede usar el número puro, no el "bit", por lo que no necesita modificación esa parte.


« Última Modificación: julio 15, 2017, 21:00:06 pm por Soporte »
SOPORTE TÉCNICO

Slicetex Electronics
www.slicetex.com

Soporte

  • Global Moderator
  • Experto
  • *****
  • Mensajes: 1848
  • Soporte Técnico
Re:AYUDA: ruido eléctrico en entradas digitales?
« Respuesta #14 : julio 15, 2017, 20:59:08 pm »
Independiente del mensaje anterior, en el que te indico el error de parámetro en funciones DinReadFiltered(), te paso una versión para leer las entradas DIN de la placa STX570 filtrando y comprobando errores de comunicación, que hace más robusta la lectura.

Esto úsalo luego de aplicar los cambios anteriores:

Código: (Pawn) [Seleccionar]
// ********************************************************************************
// Funcion     : EXT_DinReadFiltered()
// Descripcion : Filtro anti-rebotes para STX570 con comprobación de errores en
//               comunicación.
//
// ENTRADAS:
//
//     - Din = Entrada discreta a leer.
//       Ejemplo EDIN1 para entrada Numero 1.
//       Recordar constantes EDIN tiene un valor "mascara" es decir:
//       EDIN1 = 00000001
//       EDIN2 = 00000010
//       EDIN3 = 00000100
//       EDIN8 = 10000000
//
// SALIDAS :
//
//     - Estado lógico de la entrada.
//
// ********************************************************************************


EXT_DinReadFiltered(Din)
{
   new dinState = 0
   new timeOut = 25
   new lastLevel = 0
   new currentLevel = 0
   
   do
   {     
      // Obtener estado de todas las entradas discretas del módulo.
      // Comprobar error de comunicación con módulo.
      if(Stx570_DinReadAll(0, dinState) < 0)
      {
         // Error de lectura entre PLC y módulo.
         
         // Esperar 20 mS para próximo intento.
         DelayMS(20)
         
         // Reiniciar timeout.
         timeOut = 25
         
         // Recomenzar ciclo (forzar).
         continue         
      }
     
      // Obtener nivel lógico de entrada.
      lastLevel = Stx570_DinRead(dinState, Din) == 1 ? 1: 0
     
      // Esperar 20 mS para próxima lectura.
      DelayMS(20)
     
      // Obtener estado de todas las entradas discretas del módulo.
      // Comprobar error de comunicación con módulo.
      if(Stx570_DinReadAll(0, dinState) < 0)
      {
         // Error de lectura.
         
         // Esperar 20 mS para próximo intento.
         DelayMS(20)
         
         // Reiniciar timeout.
         timeOut = 25
         
         // Recomenzar ciclo (forzar).
         continue
      }
     
      // Obtener nivel lógico de entrada.
      currentLevel = Stx570_DinRead(dinState, Din) == 1 ? 1: 0
     
      // Comprobar si estado actual difiere del último estado leído.
      if(currentLevel != lastLevel)
      {
         // Difiere, reiniciar timeout.
         timeOut = 25
      }
      else
      {
         // Iguales, decrementar timeout.
         timeOut--
      }   
   }   
   while(timeOut > 0)

   // Retornar último estado de entrada estable.
   return lastLevel
}

« Última Modificación: julio 15, 2017, 21:02:19 pm por Soporte »
SOPORTE TÉCNICO

Slicetex Electronics
www.slicetex.com