Pasar Parámetros a Componentes
¿Cómo definir parámetros en un componente?
Cuando creas un componente personalizado extendiendo la clase `Component`, puedes definir los parámetros que recibirá utilizando tipos genéricos de TypeScript. Estos parámetros se especifican como un objeto dentro de los corchetes angulares (``).
En el siguiente ejemplo, el componente `ButtonSuccess` espera recibir un objeto con dos propiedades: `text` de tipo `string` y `onClick` de tipo `() => void` (una función que no recibe argumentos y no retorna nada).
import { Component, Context, Widget } from "@seigenta/TypesCraft/widget";
// ... otras importaciones
// Define los parámetros esperados usando genéricos
export class ButtonSuccess extends Component<{ text: string, onClick: () => void }> {
// ... resto de la implementación del componente
}
¿Cómo acceder a los parámetros dentro del componente?
Dentro de los métodos de tu componente, especialmente en el método `build`, puedes acceder a los valores pasados como parámetros a través de la propiedad `this.data`.
import { Component, Context, Widget } from "@seigenta/TypesCraft/widget";
import FloatingButton from "@seigenta/TypesCraft/widgets/buttons/floatingButton";
import Text from "@seigenta/TypesCraft/widgets/texts/text";
// ... otras importaciones y estilos
export class ButtonSuccess extends Component<{ text: string, onClick: () => void }> {
color = Color.hex("#8F87F1");
status = false;
build(_: Context): Widget<any> | null {
return new FloatingButton({
// ... estilos
child: new Text({
// Accede al parámetro 'text'
text: this.data.text,
}),
// Accede al parámetro 'onClick'
onPressed: this.data.onClick,
});
}
}
¿Cómo pasar parámetros al usar el componente?
Cuando instancias tu componente personalizado, debes pasarle un objeto que cumpla con la estructura definida en los genéricos. Las claves del objeto deben coincidir con los nombres de los parámetros definidos, y los valores deben ser del tipo esperado.
// Importa tu componente personalizado
import { ButtonSuccess } from './ruta/a/ButtonSuccess';
// ... en alguna parte de tu código donde uses el componente
new ButtonSuccess({
// Pasa el valor para 'text'
text: "Haz clic aquí",
// Pasa la función para 'onClick'
onClick: () => {
console.log("Botón presionado!");
// Llama a otra función si es necesario, por ejemplo:
// this.onSubmit();
},
})
Puedes pasar valores dinámicos o condicionales como parámetros, como se muestra en el ejemplo original:
new ButtonSuccess({
text: window.innerWidth > 500 ? "Hola mundo grande" : "Hola mundo pequeño",
onClick: () => {
this.onSubmit(); // Asumiendo que onSubmit existe en este contexto
},
})
Ejemplo Completo
A continuación se muestra el código completo de la clase `ButtonSuccess` y un ejemplo de cómo se instancia y se le pasan los parámetros:
import { Css } from "@seigenta/TypesCraft/global/style";
import { Component, Context, Widget } from "@seigenta/TypesCraft/widget";
import { ButtonStyle } from "@seigenta/TypesCraft/widgets/buttons/button";
import FloatingButton from "@seigenta/TypesCraft/widgets/buttons/floatingButton";
import Text, { TextStyle } from "@seigenta/TypesCraft/widgets/texts/text";
import BoxShadow from "@seigenta/TypesCraft/widgets/utils/boxShadow";
import Color from "@seigenta/TypesCraft/widgets/utils/color";
import Size from "@seigenta/TypesCraft/widgets/utils/size";
import Stack from '@seigenta/TypesCraft/widgets/containers/stack'; // Necesario para el ejemplo de uso
// Definición del componente con sus parámetros
export class ButtonSuccess extends Component<{ text: string, onClick: () => void }> {
color = Color.hex("#8F87F1");
status = false;
build(_: Context): Widget<any> | null {
// Simulación de cambio de estado para el ejemplo de boxShadow en styleHover
// En una aplicación real, esto se manejaría de forma más robusta.
setInterval(() => {
this.status = !this.status;
// Necesitarías un mecanismo para redibujar el componente si el estado afecta directamente el build.
// Para styleHover, el cambio se refleja al interactuar.
}, 2000);
return new FloatingButton({
style: new ButtonStyle({
backgroundColor: Color.cyan().opacity(0.5),
textStyle: new TextStyle({
color: Color.white(),
}),
borderRadius: Size.px(3),
css: Css.fromJson({
// Usa template literals correctamente para interpolar
"view-transition-name": `button-success-${this.data.text.replace(/\s+/g, '-')}`,
})
}),
styleHover: new ButtonStyle({
boxShadow: [
new BoxShadow({
color: this.color,
vOffset: Size.px(this.status ? 20 : -20),
hOffset: Size.px(this.status ? 20 : -20),
}),
new BoxShadow({
color: this.color,
vOffset: Size.px(this.status ? -30 : 30),
hOffset: Size.px(this.status ? -30 : 30),
}),
],
}),
child: new Text({
text: this.data.text,
}),
onPressed: this.data.onClick,
});
}
}
// ------ Ejemplo de uso dentro de otro Componente ------
// Definimos un Componente de ejemplo que usará ButtonSuccess
class MyExampleComponent extends Component<null> {
realizarAccion() {
console.log("Acción realizada desde MyExampleComponent!");
}
build(context: Context): Widget | null {
// Instanciamos ButtonSuccess dentro del método build
const miBoton = new ButtonSuccess({
text: "Confirmar Acción",
onClick: () => {
// Llamamos a un método de esta clase
this.realizarAccion();
},
});
// Instanciamos otro con texto dinámico
const botonDinamico = new ButtonSuccess({
text: window.innerWidth > 500 ? "Hola mundo grande" : "Hola mundo pequeño",
onClick: () => {
console.log("Click en botón dinámico!");
},
});
// Los componentes hijos usualmente se retornan dentro de un layout widget (como Stack, Column, Row)
return new Flex({
direction: FlexDirection.column,
children: [
new Text({ text: "Ejemplo de uso de ButtonSuccess:" }),
miBoton, // Usamos la instancia creada
botonDinamico // Usamos la otra instancia
]
});
}
}
// Para mostrar este componente en la página, lo instanciarías y renderizarías:
// const myApp = new MyExampleComponent({});
// document.getElementById('app').appendChild(myApp.render()); // (Ejemplo básico de renderizado)