01 · Punto de partida
Siete LED que saben contar
Un dígito de display de 7 segmentos son siete barras luminosas (a, b, c, d, e, f, g) más un punto decimal. Cada dígito del 0 al 9 enciende una combinación distinta. El camino de la información es siempre el mismo: un número en BCD (cuatro bits) entra a un decodificador BCD a 7 segmentos, que genera siete señales; cada señal alimenta un segmento a través de una resistencia.
Una escena típica. Armás un contador de 0 a 9 y querés ver el número. Conectás un 74LS47 a un display, ponés una sola resistencia para todos los segmentos «para ahorrar», y el 8 se ve opaco mientras el 1 brilla de más. Cambiás de display y no enciende nada: era de cátodo común y el 7447 solo maneja ánodo común. Un tercer problema aparece cuando querés mostrar cuatro dígitos: el montaje se llena de cables y te quedás sin pines.
Los tres problemas (la resistencia por segmento, el tipo de común y el multiplexado) tienen explicación y solución en este tema. Además, los siete segmentos son siete funciones de cuatro variables con seis condiciones «no importa», así que hay un ejercicio de Karnaugh escondido.
- ¿Qué segmentos enciende cada dígito, y qué byte corresponde a cada uno?
- ¿Qué diferencia hay entre ánodo común y cátodo común, y cuál decodificador va con cuál?
- ¿Cuánta corriente consume un dígito y qué resistencia lleva cada segmento?
- ¿Qué pasa con los códigos 10 a 15?
- ¿Cómo se muestran varios dígitos con pocos pines?
02 · Segmentos
El mapa a–g y los códigos
Los segmentos se nombran con letras en un orden fijo: a arriba, luego b y c a la derecha (de arriba abajo), d abajo, e y f a la izquierda (de abajo arriba) y g en el medio. El punto decimal es el octavo elemento (dp).
| Símbolo | Segmentos | Cantidad | Byte para cátodo común (1 enciende) | Byte para ánodo común (0 enciende) |
|---|---|---|---|---|
| 0 | a b c d e f | 6 | 0x3F | 0xC0 |
| 1 | b c | 2 | 0x06 | 0xF9 |
| 2 | a b d e g | 5 | 0x5B | 0xA4 |
| 3 | a b c d g | 5 | 0x4F | 0xB0 |
| 4 | b c f g | 4 | 0x66 | 0x99 |
| 5 | a c d f g | 5 | 0x6D | 0x92 |
| 6 | a c d e f g | 6 | 0x7D | 0x82 |
| 7 | a b c | 3 | 0x07 | 0xF8 |
| 8 | a b c d e f g | 7 | 0x7F | 0x80 |
| 9 | a b c d f g | 6 | 0x6F | 0x90 |
| A | a b c e f g | 6 | 0x77 | 0x88 |
| b | c d e f g | 5 | 0x7C | 0x83 |
| C | a d e f | 4 | 0x39 | 0xC6 |
| d | b c d e g | 5 | 0x5E | 0xA1 |
| E | a d e f g | 5 | 0x79 | 0x86 |
| F | a e f g | 4 | 0x71 | 0x8E |
- Un byte por símbolo
- Con un microcontrolador, la tabla anterior es un arreglo de 16 bytes:
const uint8_t SEG[16]. El byte de ánodo común es el complemento (XOR con 0xFF) del de cátodo común. El bit 7 es el punto decimal. - Variantes de dibujo
- Según el fabricante, el 6 puede omitir el segmento a, el 9 el d y el 7 sumar el f. Son diferencias de estilo; verificá el aspecto antes de armar una tabla propia.
- Siete funciones de cuatro variables
- Cada segmento es una función de las cuatro entradas BCD, con los códigos 10 a 15 como «no importa». Por ejemplo, el segmento a vale 1 en los dígitos 0, 2, 3, 5, 6, 7, 8 y 9, y minimizando con las X queda a = A + C + B·D + ~B·~D (con A como bit más significativo). Se pueden obtener los otros seis de la misma manera con el Tema 16 (el Paso 2 de Python los calcula todos).
03 · Común
Ánodo común, cátodo común y sus decodificadores
Los siete LED de un dígito comparten un terminal, para ahorrar patas. Si comparten el ánodo, ese terminal va a VCC y cada segmento se enciende llevando su cátodo a un nivel bajo (el driver «hunde» corriente). Si comparten el cátodo, ese terminal va a masa y cada segmento se enciende con un nivel alto (el driver «entrega» corriente).
Ánodo común (CA)
Común a VCC, segmento a 0
Cada salida del decodificador es activa en bajo y debe soportar la corriente del segmento hacia masa. Driver clásico: 7447 (colector abierto, aguanta decenas de mA).
Cátodo común (CC)
Común a masa, segmento a 1
Cada salida es activa en alto y entrega la corriente. Drivers: 7448 (poca corriente) y CD4511/74HC4511 (con memoria).
| Chip | Display | Salidas | Códigos 10 a 15 | Entradas especiales |
|---|---|---|---|---|
| 74LS47 (7447) | Ánodo común | Activas en bajo, colector abierto (hunden decenas de mA) | Símbolos raros (no son letras) | ~LT (prueba de lámpara), ~RBI y ~RBO (supresión de ceros), ~BI |
| 74LS48 (7448) | Cátodo común | Activas en alto, con resistencias internas (poca corriente) | Símbolos raros | Las mismas que el 47 |
| CD4511 / 74HC4511 | Cátodo común | Activas en alto, con corriente moderada | Apagado (blanking) | LE (retiene el dígito), ~BI (apagar), ~LT (prueba) |
| Microcontrolador + tabla | El que quieras | Pines de E/S | Lo que decidas: hexadecimal, guiones, letras | Software |
- Códigos 10 a 15
- Los decodificadores BCD no están pensados para ellos (son «no importa» del Tema 6) y cada chip hace algo distinto. El 4511 apaga todo; los 7447 y 7448 dibujan símbolos extraños que no son las letras hexadecimales. Para ver A a F hace falta una tabla propia, normalmente en un microcontrolador.
- Prueba de lámpara (~LT)
- Con ~LT en 0 se encienden todos los segmentos sin importar la entrada: sirve para detectar segmentos quemados o mal soldados. Es una prueba que un programador reconoce: un «self-test» al arrancar.
- Apagado (~BI)
- Con ~BI en 0 el display se apaga completamente. Se usa para regular el brillo (con PWM) o para el multiplexado.
- Latch del 4511
- Con LE = 0 las salidas siguen a las entradas BCD; con LE = 1 el chip retiene el último dígito aunque las entradas cambien. Permite compartir el bus de datos entre varios 4511 (uno por dígito) y actualizarlos por turnos.
- El punto decimal
- No lo maneja el decodificador: es un LED aparte con su propia resistencia. No hay que olvidarlo al contar pines.
04 · Corriente
Resistencia por segmento y presupuesto de corriente
Un LED no limita su propia corriente: cualquier voltaje por encima de su caída directa (Vf) la dispara y lo quema. Cada segmento necesita una resistencia en serie que fije la corriente:
| Color | Vf típica | R exacta | Valor E12 (por arriba) | Corriente real |
|---|---|---|---|---|
| Rojo | 1,8 V | 270 Ω | 270 Ω | 10,0 mA |
| Amarillo | 2,0 V | 250 Ω | 270 Ω | 9,3 mA |
| Verde | 2,1 V | 240 Ω | 270 Ω | 8,9 mA |
| Azul / blanco | 3,1 V | 140 Ω | 150 Ω | 9,3 mA |
Una resistencia por segmento, no una común
Cada dígito enciende una cantidad distinta de segmentos, así que la corriente total cambia:
| Dígito | Segmentos | Corriente total |
|---|---|---|
| 1 | 2 | 20 mA |
| 7 | 3 | 30 mA |
| 4 | 4 | 40 mA |
| 2, 3, 5 | 5 | 50 mA |
| 0, 6, 9 | 6 | 60 mA |
| 8 | 7 | 70 mA |
Con una sola resistencia común (en el terminal común) la corriente total estaría fijada por esa resistencia y se repartiría entre los segmentos encendidos: el 1 (dos segmentos) brillaría el triple que cada segmento del 8 (siete). Con una resistencia por segmento, cada uno recibe la misma corriente sin importar cuántos más estén encendidos.
- Los límites del driver
- Un 74LS47 hunde 40 mA por salida: sobra. Los CMOS tienen un tope por salida (típicamente 25 mA como máximo absoluto) y otro por patita de alimentación (50 mA en la familia HC). Con 70 mA para un 8 a 10 mA por segmento, un 74HC4511 se pasaría del tope total: hay que bajar la corriente por segmento (menos de unos 7 mA con los siete encendidos) o usar transistores.
- ¿Cuánta corriente hace falta?
- Los LED rojos de alta eficiencia modernos se ven bien con 2 a 5 mA. Los 10 mA de los textos clásicos eran para LED antiguos. Bajar la corriente ahorra energía, calor y problemas con el driver. Probá con una resistencia mayor antes de aceptar 10 mA.
- Segmentos con distinta eficiencia
- Un LED azul o blanco necesita más de 3 V: a 5 V con un driver que cae 0,5 V quedan 1,5 V para la resistencia. Con alimentación de 3,3 V directamente no encienden.
05 · Varios dígitos
El multiplexado: encender de a uno, rápido
Un display de cuatro dígitos con un decodificador por dígito necesita cuatro decodificadores y 28 resistencias. El multiplexado lo resuelve con un solo decodificador y siete resistencias: los segmentos de los cuatro dígitos están unidos en paralelo y cada dígito tiene su propio común. En cada instante se enciende un solo dígito, con sus datos, y se pasa al siguiente tan rápido que el ojo ve los cuatro encendidos a la vez (persistencia de la visión).
| Dígitos (N) | Ciclo de trabajo | Frecuencia de barrido (N × 100 Hz) | Corriente pico para 5 mA promedio |
|---|---|---|---|
| 1 | 100 % | — | 5 mA |
| 2 | 50 % | 200 Hz | 10 mA |
| 4 | 25 % | 400 Hz | 20 mA |
| 8 | 12,5 % | 800 Hz | 40 mA |
- Compensar el brillo
- Con N dígitos, cada uno está encendido 1/N del tiempo. Para el mismo brillo promedio hay que multiplicar la corriente pico por N. Eso exige que el driver soporte el pico (por eso en displays de 8 dígitos se usan transistores o drivers dedicados).
- Selección de dígito
- Un decodificador (74HC138 o 139, Tema 20) maneja transistores que conectan el común de cada dígito: PNP a VCC para ánodo común, NPN a masa para cátodo común. El común de un dígito lleva la suma de la corriente de todos sus segmentos.
- Los datos
- Un multiplexor (Tema 18) por cada bit del nibble elige el dígito BCD del que toca mostrar, y un contador sincroniza el selector de dígito con el selector del multiplexor. Con un microcontrolador, simplemente se escribe el byte del dígito en cada turno.
- Parpadeo
- Por debajo de unos 60 Hz de refresco completo se percibe parpadeo; más de 100 Hz es cómodo. Si el microcontrolador hace otras cosas, el barrido se programa en una interrupción de temporizador.
- Fantasmas (ghosting)
- Si se cambian los datos de los segmentos antes de apagar el dígito anterior, por un instante los segmentos del dígito nuevo se ven en el viejo: una tenue imagen fantasma. La regla es la de los buses (Tema 7): primero apagar, después cambiar, por último encender.
06 · Vida real
Ceros a la izquierda, binario a BCD y drivers integrados
- Supresión de ceros a la izquierda
- Un contador de 4 dígitos que vale 7 mostraría «0007». Los 7447 y 7448 tienen las entradas ~RBI y ~RBO (ripple blanking) para apagar los ceros del principio: el dígito más significativo recibe ~RBI = 0, y si vale 0 se apaga y emite ~RBO = 0 hacia el siguiente. El último dígito nunca se apaga (su ~RBI se ata a VCC), así que el cero solitario sigue viéndose.
- El problema binario a BCD
- Los contadores y los microcontroladores trabajan en binario; el decodificador espera BCD. 42 en binario es 101010; el decodificador de unidades recibiría 1010 (el código inválido A). Hay que convertir. El algoritmo clásico es el doble dabble (shift-and-add-3): por cada bit del número, de izquierda a derecha, se suma 3 a cada dígito BCD que valga 5 o más y se desplaza todo un lugar. En 8 iteraciones, el número binario queda en BCD.
- Los contadores BCD
- Si el contador ya cuenta en BCD (74HC160, 74HC4518), se evita la conversión: cada dígito cuenta de 0 a 9 y avisa al siguiente con un acarreo. Es la solución natural para contadores y relojes.
- Drivers integrados
- Para displays de varios dígitos, hoy es más cómodo un integrado que haga todo: el MAX7219 maneja hasta 8 dígitos por SPI (multiplexado, decodificación BCD, brillo y prueba de lámpara incluidos) y el TM1637 hace lo mismo para 4 dígitos con dos cables. Es el mismo principio que viste, empaquetado en un chip y una interfaz serie.
| Número | Dígitos | Sin supresión | Con supresión |
|---|---|---|---|
| 7 | 0 0 0 7 | 0007 | ···7 |
| 42 | 0 0 4 2 | 0042 | ··42 |
| 100 | 0 1 0 0 | 0100 | ·100 |
| 0 | 0 0 0 0 | 0000 | ···0 |
| 1005 | 1 0 0 5 | 1005 | 1005 (los ceros del medio se ven) |
07 · Simulador
Laboratorio: probador de dígitos
El simulador dibuja un display de 7 segmentos y lo maneja desde un código de 4 bits (0 a 15). Elegís el decodificador (74LS47 para ánodo común, 74HC4511 para cátodo común, o un microcontrolador con tabla propia), el color del LED y la corriente por segmento, y ves qué segmentos se encienden, el nivel de cada salida, la resistencia comercial, la corriente total y el efecto de multiplexar N dígitos.
- Display: los segmentos encendidos en amarillo, los apagados en gris. Con 74LS47 y códigos 10 a 15 se dibuja un «?» (los símbolos raros dependen del chip); con 74HC4511 el display se apaga; con la tabla propia se ve el hexadecimal.
- Tabla de salidas: el nivel de cada salida del chip. En ánodo común un segmento encendido tiene su salida en 0 (el chip «hunde»); en cátodo común, en 1.
- Corrientes: la resistencia exacta y la comercial para esa corriente, la corriente real y el total del dígito, con un aviso si se superan los límites del driver.
Probador de dígitos
5 → a c d f g
5: segmentos a c d f g.
Recorrido guiado (8 minutos)
- 1Mirá el 5 con el 74LS47.
Cinco segmentos (a, c, d, f, g) encendidos. La tabla muestra que en ánodo común esas salidas valen 0 (el chip las lleva a nivel bajo para que fluya corriente), y las otras dos valen 1. El byte de ánodo común es 0x92 (el complemento de 0x6D).
- 2Apretá «Dígito 8» y después «Dígito 1».
El 8 enciende siete segmentos (70 mA con 10 mA cada uno); el 1 solo dos (20 mA). El consumo del dígito depende de lo que se muestra. Por eso la resistencia va en cada segmento y no en el común.
- 3Cambiá a 74HC4511 con el dígito 8 a 10 mA.
Aparece un aviso: 70 mA superan el límite total de 50 mA por alimentación del CMOS. Bajá la corriente por segmento hasta que el aviso desaparezca (con el control en 8 mA o menos: la resistencia comercial, un poco mayor que la exacta, deja la corriente real en unos 7 mA).
- 4Probá los códigos 10 a 15 con cada decodificador.
Con el 74LS47 se dibuja un «?»: símbolos extraños, no estándar. Con el 74HC4511 el display se apaga (blanking). Con la tabla de un microcontrolador ves A, b, C, d, E, F: tenés que dibujarlas vos.
- 5Cambiá el color a azul.
La caída directa sube de 1,8 V a 3,1 V y la resistencia necesaria baja de 270 Ω a 150 Ω para la misma corriente: quedan 1,4 V para la resistencia.
- 6Subí la corriente a 20 mA con el 4511 o el micro.
Aparece el aviso de límite por salida (25 mA para CMOS, 20 mA para un pin de microcontrolador). Los LED modernos se ven bien con mucho menos.
- 7Elegí 4 dígitos y después 8.
El ciclo de trabajo baja a 25 % y 12,5 %, y la corriente pico necesaria para el mismo brillo sube de 10 mA a 40 y 80 mA. La frecuencia de barrido mínima sube a 400 y 800 Hz para mantener 100 Hz de refresco por dígito. A 8 dígitos, el pico excede lo que un driver CMOS soporta: hacen falta transistores o un MAX7219.
- 8Recorré el código con «Siguiente».
Del 0 al 9 pasan los diez dígitos; después, lo que corresponda a cada decodificador. Compará el byte con la tabla de la sección 02.
Preguntas para pensar
- ¿Cuántos segmentos y qué corriente total tienen el 8 y el 1 con 10 mA por segmento?
- ¿Qué hace cada decodificador con los códigos 10 a 15?
- ¿Por qué cambia la resistencia al pasar de un LED rojo a uno azul?
- Con 4 dígitos multiplexados y 5 mA de brillo promedio, ¿qué corriente pico hace falta?
Ver respuestas sugeridas
- El 8 tiene 7 segmentos (70 mA) y el 1 tiene 2 (20 mA): el consumo depende del dígito.
- El 4511 apaga todo; los 7447 y 7448 dibujan símbolos raros; un microcontrolador con tabla puede mostrar A a F. Ninguno muestra «solo» las letras sin ayuda.
- El azul cae unos 3,1 V (contra 1,8 V del rojo): queda menos voltaje para la resistencia, y R = V/I resulta menor para la misma corriente.
- Cada dígito está encendido un cuarto del tiempo: el pico debe ser 4 × 5 = 20 mA.
08 · Dígitos en código
Dibujar, minimizar, calcular y convertir
Los bloques dibujan los 16 símbolos en texto con sus bytes, minimizan los siete segmentos del decodificador (con las X de 10 a 15), calculan resistencias y presupuestos de corriente, simulan el multiplexado con y sin apagado previo (fantasmas), reproducen la supresión de ceros con RBI/RBO y convierten binario a BCD con doble dabble.
Python en tu navegador. Los bloques son editables: cambiá los valores y presioná «Ejecutar Python». La primera vez tarda unos segundos en cargar.
Paso 1: los 16 símbolos y sus bytes
SEG = {"0": "abcdef", "1": "bc", "2": "abdeg", "3": "abcdg", "4": "bcfg", "5": "acdfg",
"6": "acdefg", "7": "abc", "8": "abcdefg", "9": "abcdfg",
"A": "abcefg", "b": "cdefg", "C": "adef", "d": "bcdeg", "E": "adefg", "F": "aefg"}
def byte_cc(c):
return sum(1 << "abcdefg".index(x) for x in SEG[c])
def tres_lineas(c):
s = SEG[c]
return [" " + ("_" if "a" in s else " ") + " ",
("|" if "f" in s else " ") + ("_" if "g" in s else " ") + ("|" if "b" in s else " "),
("|" if "e" in s else " ") + ("_" if "d" in s else " ") + ("|" if "c" in s else " ")]
def mostrar(texto):
cols = [tres_lineas(c) for c in texto]
for fila in range(3):
print(" ".join(col[fila] for col in cols))
mostrar("0123456789")
mostrar("ABCDEF")
print()
print("símbolo segmentos cátodo común ánodo común")
for c in "0123456789AbCdEF":
cc = byte_cc(c)
print(f" {c} {len(SEG[c])} 0x{cc:02X} 0x{cc ^ 0xFF:02X}")
Los bytes coinciden con la tabla de la sección 02: 0x3F para el 0, 0x06 para el 1, 0x7F para el 8, y el de ánodo común es el complemento de cada uno. Con un micro, esto es literalmente el arreglo SEG[16].
Paso 2: los siete segmentos minimizados (con las X)
from itertools import combinations
SEG = {"0": "abcdef", "1": "bc", "2": "abdeg", "3": "abcdg", "4": "bcfg", "5": "acdfg",
"6": "acdefg", "7": "abc", "8": "abcdefg", "9": "abcdfg"}
def primos(unos, dcs, n):
actual = {format(m, f"0{n}b") for m in set(unos) | set(dcs)}
res = set()
while actual:
sig, usados = set(), set()
for a, b in combinations(sorted(actual), 2):
d = [i for i in range(n) if a[i] != b[i]]
if len(d) == 1 and "-" not in (a[d[0]], b[d[0]]):
i = d[0]
sig.add(a[:i] + "-" + a[i + 1:])
usados.update((a, b))
res |= actual - usados
actual = sig
return sorted(res)
def cubre(p, m, n):
b = format(m, f"0{n}b")
return all(x in ("-", y) for x, y in zip(p, b))
def minima(unos, dcs, n):
ps = primos(unos, dcs, n)
esc = set()
for m in unos:
c = [p for p in ps if cubre(p, m, n)]
if len(c) == 1:
esc.add(c[0])
resto = [m for m in unos if not any(cubre(p, m, n) for p in esc)]
libres = [p for p in ps if p not in esc]
for k in range(len(libres) + 1):
sol = [c for c in combinations(libres, k) if all(any(cubre(p, m, n) for p in c) for m in resto)]
if sol:
return sorted(esc | set(min(sol, key=lambda c: sum(x != "-" for p in c for x in p))))
return sorted(esc)
def termino(p):
return "·".join(v if x == "1" else "~" + v for v, x in zip("ABCD", p) if x != "-") or "1"
dcs = list(range(10, 16))
todos = set()
for s in "abcdefg":
unos = [d for d in range(10) if s in SEG[str(d)]]
ps = minima(unos, dcs, 4)
todos.update(ps)
ok = all(any(cubre(p, d, 4) for p in ps) == (s in SEG[str(d)]) for d in range(10))
print(f"{s} = {' + '.join(termino(p) for p in ps):<28} {'ok' if ok else 'FALLA'}")
print(f"términos de producto distintos entre los siete segmentos: {len(todos)}")
print("alternativa: una ROM de 16 x 7 bits =", 16 * 7, "bits")
Cada segmento queda con entre 2 y 5 términos. El segmento a sale A + C + B·D + ~B·~D, como en la sección 02. Hay términos que se repiten entre segmentos y se pueden compartir, como en un diseño multisalida (Tema 17).
Paso 3: resistencias, E12 y el presupuesto de corriente
E12 = (1.0, 1.2, 1.5, 1.8, 2.2, 2.7, 3.3, 3.9, 4.7, 5.6, 6.8, 8.2)
def e12_mayor(r):
dec = 1
while True:
for v in E12:
if v * dec >= r - 1e-9:
return v * dec
dec *= 10
def resistencia(vcc, vf, vdrop, i_ma):
r = (vcc - vf - vdrop) / (i_ma / 1000)
rc = e12_mayor(r)
return r, rc, (vcc - vf - vdrop) / rc * 1000
print("color Vf R exacta E12 corriente real")
for color, vf in (("rojo", 1.8), ("amarillo", 2.0), ("verde", 2.1), ("azul/blanco", 3.1)):
r, rc, i = resistencia(5.0, vf, 0.5, 10)
print(f"{color:<11} {vf:>4} {r:>6.0f} Ω {rc:>4.0f} Ω {i:>5.1f} mA")
SEGS = {"0": 6, "1": 2, "2": 5, "3": 5, "4": 4, "5": 5, "6": 6, "7": 3, "8": 7, "9": 6}
print()
print("corriente por dígito con 10 mA por segmento:", {d: n * 10 for d, n in SEGS.items()})
LIMITE_TOTAL = 50 # mA por patita de alimentación en un CMOS de la familia HC
print(f"con un 74HC4511 el dígito 8 admite como máximo {LIMITE_TOTAL / 7:.1f} mA por segmento")
r, rc, i = resistencia(5.0, 1.8, 0.5, 7)
print(f"para 7 mA: R exacta {r:.0f} Ω -> {rc:.0f} Ω -> {i:.1f} mA, el 8 consume {7 * i:.0f} mA")
Rojo: 270 Ω y 10 mA; verde y amarillo: 270 Ω y unos 9 mA; azul: 150 Ω. Con un CMOS limitado a 50 mA totales, un dígito 8 admite unos 7 mA por segmento (resistencia de 390 Ω).
Paso 4: multiplexado y fantasmas
print(" N ciclo barrido pico para 5 mA promedio")
for N in (1, 2, 4, 8):
print(f"{N:>2} {100 / N:>5.1f} % {100 * N:>5} Hz {5 * N:>5} mA")
DATOS = {0: "1", 1: "2"} # qué debe mostrar cada dígito
def secuencia(apagar_primero):
pasos, activo, segs = [], None, None
for d in (0, 1):
if apagar_primero:
activo = None
pasos.append((activo, segs)) # primero apago el dígito
segs = DATOS[d]
pasos.append((activo, segs)) # cambio los segmentos con todo apagado
activo = d
pasos.append((activo, segs)) # recién ahora enciendo el dígito
else:
segs = DATOS[d]
pasos.append((activo, segs)) # cambio los segmentos con el dígito anterior encendido
activo = d
pasos.append((activo, segs))
return pasos
for apagar in (False, True):
print()
print("con apagado previo:" if apagar else "sin apagado previo:")
fantasmas = 0
for activo, segs in secuencia(apagar):
fantasma = activo is not None and DATOS[activo] != segs
fantasmas += fantasma
print(f" dígito encendido={activo} segmentos={segs} {'FANTASMA' if fantasma else ''}")
print(f" instantes con fantasma: {fantasmas}")
El pico de corriente crece con N (5, 10, 20, 40 mA para el mismo brillo). Cambiar los segmentos antes de apagar el dígito anterior muestra un instante del símbolo equivocado en el dígito viejo (fantasma). Con la regla «apagar, cambiar, encender» no hay ningún instante así.
Paso 5: supresión de ceros con RBI y RBO
def con_rbi(n, k=4):
digs = [int(c) for c in str(n).zfill(k)]
rbi = True # el dígito más significativo recibe ~RBI activo
salida = []
for i, d in enumerate(digs):
ultimo = i == k - 1 # el último dígito nunca se apaga (su ~RBI va a VCC)
if d == 0 and rbi and not ultimo:
salida.append("·") # apagado; su ~RBO activo pasa al siguiente
else:
salida.append(str(d))
rbi = False # un dígito visible corta la cadena
return "".join(salida)
for n in (7, 42, 100, 0, 1005, 5000, 9999):
print(f"{n:>5} sin supresión: {str(n).zfill(4)} con supresión: {con_rbi(n)}")
Los ceros del principio se apagan, pero un cero entre dígitos visibles (1005) o al final (100) se ve, y el número 0 muestra un cero en la última posición. La cadena RBI → RBO funciona de izquierda a derecha, igual que este bucle.
Paso 6: de binario a BCD con doble dabble
def doble_dabble(n, bits=8):
bcd = 0
digitos = (bits + 2) // 3
for i in range(bits - 1, -1, -1):
for d in range(digitos):
nib = (bcd >> (4 * d)) & 0xF
if nib >= 5:
bcd += 3 << (4 * d) # si un dígito es 5 o más, sumarle 3...
bcd = (bcd << 1) | ((n >> i) & 1) # ...y desplazar todo una posición
return bcd
for n in (7, 42, 99, 100, 255):
b = doble_dabble(n)
print(f"{n:>3} = {n:08b} -> BCD {b >> 8 & 0xF}{b >> 4 & 0xF}{b & 0xF} (0x{b:03X})")
print("verificado para 0 a 255:", all(doble_dabble(n) == int(str(n), 16) for n in range(256)))
print("42 sin convertir: nibble bajo =", format(42 & 0xF, "04b"), "= 0x%X (código inválido)" % (42 & 0xF))
El doble dabble convierte 0 a 255 en tres nibbles BCD (42 pasa a 0x042, es decir, 0, 4, 2). Es la razón por la que no se puede alimentar un decodificador directamente con la salida de un contador binario: el 42 binario tiene el nibble bajo en 0xA, un código inválido.
09 · Analogía de programador
Una fuente de 7 píxeles
| En software | En el display de 7 segmentos |
|---|---|
| Una fuente bitmap: un mapa de bits por carácter | El byte de segmentos de cada símbolo |
Un arreglo de consulta const uint8_t SEG[16] | El decodificador 7447/4511 hecho en silicio |
| Validar el rango de una entrada antes de usarla | El blanking del 4511 con los códigos 10 a 15 |
| Limitar el consumo de recursos por hilo (rate limit) | Una resistencia por segmento: corriente pareja en cada canal |
| Refrescar una pantalla a N cuadros por segundo | El multiplexado: cada dígito se redibuja en cada ciclo |
| Doble búfer: no mostrar un cuadro a medio escribir | Apagar antes de cambiar los segmentos (sin fantasmas) |
itoa: pasar un número a dígitos decimales | La conversión binario a BCD (doble dabble) |
| Un self-test al arrancar | La prueba de lámpara ~LT |
| Delegar el trabajo a un periférico por SPI | El MAX7219 o el TM1637 |
- 1Segmentos = bitmap.
Cada dígito son siete bits: una fuente de siete píxeles con decodificador incluido.
- 2Blanking = validación.
Entrada fuera de rango, sin salida: mejor que dibujar basura.
- 3Resistencia por segmento = límite por canal.
Un único limitador global castiga a los canales que menos usan; un limitador por canal da un comportamiento uniforme.
Una diferencia con el software: el «píxel» consume corriente real, y la suma de todos los píxeles encendidos pasa por una sola patita de alimentación. Dibujar un 8 en lugar de un 1 puede superar el límite de un chip, algo que en una pantalla de software nunca pasa.
10 · Comprensión
Confusiones frecuentes
«Una resistencia común para todos los segmentos»
El brillo cambiaría con el dígito: el 1 (dos segmentos) se vería mucho más brillante por segmento que el 8 (siete). Cada segmento lleva su propia resistencia.
«Ánodo o cátodo da igual»
Define el decodificador (74LS47 para ánodo, 74LS48 y 4511 para cátodo) y el cableado del común. Equivocarse da un display apagado o al revés.
«Los códigos 10 a 15 muestran A a F»
El 4511 los apaga y el 7447/7448 dibuja símbolos raros. Para mostrar hexadecimal hace falta una tabla propia (un microcontrolador).
«Sin resistencia hay más brillo»
Hay un LED o un driver quemado. El brillo se diseña con la corriente, y la corriente la fija una resistencia.
«Un 74HC puede manejar 70 mA de un dígito 8»
Cada salida tiene su límite y la patita de alimentación tiene otro (unos 50 mA en la familia HC). Hay que bajar la corriente por segmento, usar transistores o un driver dedicado.
«Con 30 Hz de refresco alcanza»
Por debajo de unos 60 Hz de refresco completo se ve parpadeo. Conviene 100 Hz o más para todo el display, es decir, N × 100 Hz de barrido para N dígitos.
«Puedo conectar la salida de un contador binario al decodificador BCD»
Solo si el contador cuenta en BCD. Un contador binario llega al 10 como 1010, un código inválido. Se convierte (doble dabble) o se usa un contador de décadas.
11 · Práctica guiada
Ejercicios de display
Ejercicio 1: la resistencia exacta
Un display rojo (Vf = 1,8 V) a 5 V con un driver que cae 0,5 V, para 12 mA por segmento. ¿Qué resistencia exacta y cuál comercial (E12)? ¿Qué corriente real da?
Ver solución razonada
R = (5 − 1,8 − 0,5) V / 12 mA = 225 Ω. El valor E12 inmediato por arriba es 270 Ω, que da 2,7 / 270 = 10 mA (por debajo del objetivo, más seguro). El 220 Ω da 12,3 mA, ligeramente por encima de 12 mA; solo conviene si ese es el valor máximo tolerado. Con el 8 encendido (siete segmentos) el consumo es 70 mA con 270 Ω.
Ejercicio 2: dos dígitos con latch
Un contador de 00 a 99 usa dos 74HC4511. ¿Qué ventaja da el latch y cómo se carga el «42»?
Ver solución razonada
Con LE = 0 el 4511 sigue las entradas; con LE = 1 retiene el último dígito aunque las entradas cambien. Permite compartir un único bus de datos de 4 bits entre los dos chips: se pone 4 en el bus y se pulsa LE del primero a 1 para fijarlo; se pone 2 y se fija el segundo. Los dos dígitos quedan mostrando «42» aunque el bus siga cambiando.
Ejercicio 3: montar un dígito
Un 74HC4511 con un display de cátodo común y siete resistencias de 270 Ω. ¿A qué se atan ~LT, ~BI y LE para que funcione? ¿Qué se ve con los códigos 10 a 15?
Ver solución razonada
~LT y ~BI (activas en bajo) a VCC (desactivadas); LE a GND (transparente). Con 0 a 9, el dígito correcto; con 10 a 15, el display apagado (blanking). Si un segmento no enciende nunca, revisar su resistencia, su pin y que el común del display esté a masa.
Ejercicio 4: el límite del CMOS
Un 74HC4511 limita la corriente total de VCC a 50 mA. ¿Cuál es la máxima corriente por segmento para que el dígito 8 sea seguro? ¿Qué resistencia usarías para un LED rojo?
Ver solución razonada
50 mA / 7 segmentos ≈ 7,1 mA por segmento como máximo. Con una caída del driver de 0,5 V y un LED rojo: R = (5 − 1,8 − 0,5) / 0,007 ≈ 386 Ω → 390 Ω (E12), que da unos 6,9 mA y 48 mA con el 8. Bajo, pero con LED modernos se ve bien.
Ejercicio 5: multiplexar cuatro dígitos
Querés 5 mA promedio por segmento con 4 dígitos y 100 Hz de refresco por dígito. ¿Qué frecuencia de barrido, qué ciclo de trabajo y qué corriente pico necesita el driver?
Ver solución razonada
Ciclo de trabajo 25 %, barrido de 4 × 100 = 400 Hz (cada dígito está encendido 2,5 ms cada 10 ms) y corriente pico de 5 × 4 = 20 mA. Dentro de lo que soporta un driver CMOS por salida, pero hay que tener en cuenta el total de los siete segmentos encendidos de un mismo dígito: 140 mA en el común (hace falta un transistor).
Ejercicio 6: binario a BCD
El número binario 101010 (42) debe mostrarse en dos displays. ¿Qué recibiría el decodificador de las unidades si se le conectara directamente el nibble bajo? ¿Qué debería recibir? ¿Cómo lo resuelve el doble dabble?
Ver solución razonada
El nibble bajo de 101010 es 1010 = 0xA: un código inválido (en el 4511 apagaría el display). Debería recibir 0010 (unidades) y 0100 (decenas), es decir, BCD 0100 0010 = 0x42. El doble dabble lo hace en 6 pasos sumando 3 a los nibbles que valgan 5 o más y desplazando un bit por vez. Verificalo con el Paso 6.
12 · Síntesis
Ideas para recordar
- Un dígito son 7 segmentos (a a g) y un punto; cada símbolo es un byte (0x3F para el 0, 0x7F para el 8). El de ánodo común es el complemento del de cátodo común.
- 74LS47: ánodo común (salidas activas en bajo, colector abierto). 74LS48 y 74HC4511: cátodo común (activas en alto). El 4511 tiene latch y apaga los códigos 10 a 15.
- Cada segmento es una función de 4 variables con 6 X: a = A + C + B·D + ~B·~D.
- Una resistencia por segmento: R = (VCC − Vf − Vdriver) / I. 270 Ω para un LED rojo a 10 mA y 5 V.
- La corriente depende del dígito: el 8 enciende siete segmentos, el 1 solo dos. Los CMOS tienen un límite por salida y otro total (unos 50 mA).
- Multiplexado: un dígito a la vez, ciclo de trabajo 1/N, barrido de N × 100 Hz, corriente pico N veces mayor. Apagar, cambiar y encender para evitar fantasmas.
- Ceros a la izquierda: ~RBI/~RBO apagan los ceros del principio. Un contador binario necesita conversión a BCD (doble dabble) antes del decodificador.
- Para varios dígitos, un MAX7219 o un TM1637 encapsula todo esto en un chip.
¿Listo para el Tema 22?
Podés avanzar si sos capaz de responder esto sin mirar:
- Decir qué segmentos enciende el 5 y qué byte le corresponde en cátodo común.
- Elegir el decodificador para un display de ánodo común y para uno de cátodo común.
- Calcular la resistencia para un LED verde a 8 mA con un driver que cae 0,5 V.
- Explicar por qué la resistencia va en cada segmento y no en el común.
- Describir qué hace el multiplexado con la corriente y la frecuencia.
- Convertir 42 a BCD y explicar por qué no se pasa directamente a un 4511.
Ya mostrás números a una persona. Falta el camino de entrada: convertir lo que hace una persona (pulsar una tecla entre muchas) en un número binario. En el próximo tema, codificadores.