Signal Forms Parte 1: Conceptos básicos

Signal Forms Parte 1:  Conceptos   básicos
Señales

Que es y porque Signals Forms

Siguiendo el enfoque de programación reactiva, el equipo de Angular a cambiado la forma en como se realizan los formularios en Angular. Con el lanzamiento de la versión 21.0, se ha lanzado también una versión preliminar de los formularios con signals. Para angular un Signal es "un contenedor que rodea un valor y notifica a los consumidores interesados ​​cuando este cambia" (angular.dev). Esto ha facilitado la gestión de estados y datos reactivos en toda la plataforma, evitando el uso de rxjs en la mayoría del proyecto. La implementación de signal ahora a los formularios, dará como resultado un uso mas reactivo y organizado de los formularios, por lo que podemos tener un resultado mas preciso y confiable que el sistema anterior de formularios.

Concepto técnico

Signal Form en el momento que se escribe este articulo solo se deberá usar en un entorno de pruebas y desarrollo, ya que no es la versión final y puede cambiar cuando se lance en definitivo. Teniendo esto en cuenta, se puede implementar de la siguiente manera:

Definir una interface

Este es un cambio fundamental. Ahora se debe de crear primero una estructura con la cual vas a crear el formulario. Puede generar mas archivos en el desarrollo pero ayuda a estructurar la información que vamos a obtener del formulario. Para el caso que vamos a realizar seria lo siguiente:

export interface FormBlogData {
  // Datos personales
  nombre: string;
  email: string;
  telefono: string;
  fechaNacimiento: string;
  pais: string;
  // Seguridad de la cuenta
  contrasena: string;
  confirmarContrasena: string;
}

Crear modelo

En base a la estructura anterior creamos un modelo inicial con valores predeterminados. Podemos añadir cualquier valor según convenga a nuestro formulario.

formBlogModel = signal<FormBlogData>({
    // Datos personales
    nombre: '',
    email: '',
    telefono: '',
    fechaNacimiento: '',
    pais: '',

    // Gestión de direcciones
    direcciones: [],

    // Seguridad de la cuenta
    contrasena: '',
    confirmarContrasena: '',
});

Implementación en el HTML

Antes de realizar cambios en el html, es necesario importar la propiedad 'Field' para que los inputs detecten la configuración del formulario

@Component({
  selector: 'app-form-blog-1',
  imports: [Field],
  templateUrl: './form-blog-1.html',
  styleUrl: './form-blog-1.scss',
})

A continuación, demos de referenciarlo de la siguiente manera:

<form>
  <h2>Datos Personales</h2>

  <div>
    <label for="nombre">Nombre:</label>
    <input type="text" id="nombre" [field]="form.nombre" />
  </div>

  <div>
    <label for="email">Email:</label>
    <input type="email" id="email" [field]="form.email" />
  </div>

  <div>
    <label for="telefono">Teléfono:</label>
    <input type="tel" id="telefono" [field]="form.telefono" />
  </div>

  <div>
    <label for="fechaNacimiento">Fecha de Nacimiento:</label>
    <input type="date" id="fechaNacimiento" [field]="form.fechaNacimiento" />
  </div>

  <div>
    <label for="pais">País:</label>
    <select id="pais" [field]="form.pais">
      <option value="">Seleccione un país</option>
      <option value="mexico">México</option>
      <option value="colombia">Colombia</option>
      <option value="argentina">Argentina</option>
      <option value="espana">España</option>
    </select>
  </div>

  <h2>Seguridad de la Cuenta</h2>

  <div>
    <label for="contrasena">Contraseña:</label>
    <input type="password" id="contrasena" [field]="form.contrasena" />
  </div>

  <div>
    <label for="confirmarContrasena">Confirmar Contraseña:</label>
    <input type="password" id="confirmarContrasena" [field]="form.confirmarContrasena" />
  </div>

  <button type="submit">Enviar</button>
</form>

Obtener y setear datos

Luego de toda la configuración, ya llega la parte de como enviamos datos al formulario y como recuperamos datos del formulario. De manera similar como se hace con signals, se codifica de esta manera:

//Setear datos
setDataForm() {
  this.formBlogModel.set({
    nombre: 'Juan Pérez',
    email: 'juan.perez@example.com',
    telefono: '1234567890',
    fechaNacimiento: '1990-01-01',
    pais: 'mexico',
    direcciones: [],
    contrasena: 'password123',
    confirmarContrasena: 'password123',
  });
}

//Obtener datos
  save() {
    const nombre = this.form.nombre().value();
    const email = this.form.email().value();
    const telefono = this.form.telefono().value();
    const fechaNacimiento = this.form.fechaNacimiento().value();
    const pais = this.form.pais().value();
    const direcciones = this.form.direcciones().value();
    const contrasena = this.form.contrasena().value();
    const confirmarContrasena = this.form.confirmarContrasena().value();

    console.log({
      nombre,
      email,
      telefono,
      fechaNacimiento,
      pais,
      direcciones,
      contrasena,
      confirmarContrasena,
    });
  }
}

De esta manera podemos tener una configuración básica de Signal Form. Luego de esto vamos a tener varios artículos donde se explicará como funciona la parte de las validaciones y que otras formas podemos crear formularios en angular 21.

Prompt IA para Generación de Componente Angular con Signals Forms

Genera un componente standalone de Angular que implemente un formulario de registro completo utilizando la funcionalidad de Signals Forms (versión preliminar). El objetivo es demostrar la definición del modelo, el binding en el template, el seteado de datos y la obtención de valores.

El componente debe llamarse App (selector app-root) y debe ser una clase standalone (@Component con template y style inline, y sin standalone: true explícito, priorizando la estructura moderna de Angular).

Requisitos Estructurales:

  1. Interface de Datos: Define y exporta la interfaz TypeScript FormBlogData con las siguientes propiedades:

    • nombre: string

    • email: string

    • telefono: string

    • fechaNacimiento: string

    • pais: string

    • contrasena: string

    • confirmarContrasena: string

  2. Modelo del Formulario: Inicializa la variable de clase formBlogModel como un signal<FormBlogData> con valores iniciales vacíos.

  3. Importaciones: Importa las propiedades necesarias para Signals Forms. Asume que la directiva de binding es Field y que se debe importar desde la ruta simulada @angular/forms/signals. (Nota: para evitar errores de compilación, usa comentarios si la importación no es real).

  4. Template (HTML):

    • Crea una estructura de formulario estético y responsivo (usando clases de Tailwind CSS) para una "Cuenta de Usuario".

    • Incluye todos los campos de FormBlogData. Utiliza un <select> para pais con opciones de ejemplo ("México", "Colombia", "Argentina", "España").

    • Realiza el binding de los inputs/selects usando la directiva [field], enlazándolos directamente al signal (ej: [field]="formBlogModel.nombre").

  5. Métodos de Datos y Lógica:

    • Implementa setDataForm(): Un método que use this.formBlogModel.set({...}) para prellenar todos los campos del formulario con datos de ejemplo.

    • Implementa save(): Un método que se ejecute al enviar el formulario (o al hacer clic en un botón) que acceda a los valores de cada campo individualmente usando el patrón this.formBlogModel.<field>().value() y luego imprima un objeto JSON con todos los datos en la consola.

    • Añade dos botones en el UI: "Llenar con Datos de Ejemplo" (llama a setDataForm) y "Enviar Formulario" (llama a save).

Estilo (CSS): Utiliza un diseño de tarjeta (card) centrado y limpio con estilos modernos de Tailwind CSS, asegurando buena legibilidad y espaciado.

Repositorio

GitHub - Blog-jhonocampo/signal-form
Contribute to Blog-jhonocampo/signal-form development by creating an account on GitHub.