Juego de Mago

Starter pack

En esta lección, combinaremos nuestro motor de VFX con muchas de las cosas que hemos aprendido durante este curso para crear un juego 3D simple: Un mago luchando contra viles orcos usando hechizos y magia. 🧙‍♂️

Una base sólida para tus propios proyectos de desarrollo de juegos web.

Proyecto Inicial

El proyecto inicial contiene:

Proyecto Inicial del Juego de Mago

Aquí tienes cómo se ve el proyecto inicial.

¿Listo para comenzar? 🪄

Bienvenido a Hogwarts 🏰

Antes de implementar cualquier tipo de lógica de juego, practiquemos nuestras habilidades mágicas en Hogwarts creando hechizos utilizando el motor de VFX que construimos en la lección dedicada.

Como hicimos en la lección de fuegos artificiales, podemos usar la versión publicada del motor de VFX. Vamos a añadirlo a nuestro proyecto:

yarn add wawa-vfx@^1.0.0

Al usar @^1.0.0, nos aseguramos de utilizar siempre la versión principal 1 del paquete pero incluyendo las versiones menores y de parches más recientes. De esta manera, podemos beneficiarnos de las últimas características y correcciones de errores sin cambios rompientes.

Ahora en el archivo Magic.jsx, vamos a crear un componente <VFXS /> que contendrá todos nuestros componentes <VFXParticles /> para nuestro proyecto.

import { VFXParticles } from "wawa-vfx";

export const Magic = ({ ...props }) => {
  // ...

  return (
    <group {...props}>
      <VFXS />
      {/* ... */}
    </group>
  );
};

const VFXS = () => {
  return (
    <>
      <VFXParticles
        name="sparks"
        settings={{
          nbParticles: 100000,
          renderMode: "billboard",
          intensity: 3,
          fadeSize: [0.1, 0.1],
        }}
      />
  );
};

Y junto a él, un componente Spells que contendrá la parte de renderizado de nuestros hechizos.

// ...
export const Magic = ({ ...props }) => {
  // ...

  return (
    <group {...props}>
      <VFXS />
      <Spells />
      {/* ... */}
    </group>
  );
};

const Spells = () => {
  return <></>;
};

Me gusta mezclar múltiples componentes en el mismo archivo cuando están estrechamente relacionados. Hace que sea más fácil entender la lógica del archivo. Si lo prefieres, siéntete libre de dividirlos en carpetas/archivos separados.

Vamos a preparar nuestro primer hechizo, el hechizo de Void.

Hechizo del Vacío

Vamos a crear un componente llamado Void que se renderizará en el componente Spells.

// ...
import { VFXEmitter } from "wawa-vfx";

// ...

const Spells = () => {
  return (
    <>
      <Void />
    </>
  );
};

const Void = ({ ...props }) => {
  return (
    <group {...props}>
      <VFXEmitter debug emitter="sparks" />
    </group>
  );
};

El componente VFXEmitter emitirá partículas desde el emisor sparks que creamos en el componente VFXS.

Con debug establecido en true tendremos controles visuales para dar forma al efecto que queremos lograr.

Bien, ¡vamos a crear un hechizo que hará temblar a los orcos!

Un buen efecto VFX es una combinación de los ajustes correctos y el tiempo adecuado.

Descompongamos lo que queremos lograr con el hechizo Void.

Primero, queremos una fase de carga. Esto es cuando se reúne la energía antes de lanzar el hechizo. Cuanto mejor esté hecha, más anticipación sentirá el jugador y más poderoso se verá el hechizo.

Nuestra fase de carga estará compuesta por:

  • Partículas emitidas lentamente hacia arriba
  • Una esfera en crecimiento
  • Runas escritas giratorias en el suelo como si se estuviera lanzando el hechizo

Luego, queremos la fase de explosión. Esto es cuando se lanza el hechizo y se libera la energía. Cuanto mejor esté hecha, más satisfactorio será para el jugador.

Nuestra explosión estará compuesta por:

  • La esfera explotando (haciendo que desaparezca)
  • Partículas yendo en todas las direcciones

Y para cada efecto visual, añadiremos un efecto de sonido para hacerlo más inmersivo.

Vamos a jugar con los ajustes del componente VFXEmitter para lograr el efecto deseado para las partículas de carga.

Esto es lo que se me ocurrió:

<VFXEmitter
  emitter="sparks"
  settings={{
    duration: 0.5,
    delay: 0,
    nbParticles: 20,
    spawnMode: "time",
    loop: false,
    startPositionMin: [-0.5, 0, -0.5],
    startPositionMax: [0.5, 1, 0.5],
    startRotationMin: [0, 0, 0],
    startRotationMax: [0, 0, 0],
    particlesLifetime: [0.5, 1],
    speed: [0, 1],
    directionMin: [0, 0, 0],
    directionMax: [0, 0.1, 0],
    rotationSpeedMin: [0, 0, 0],
    rotationSpeedMax: [0, 0, 0],
    colorStart: ["#4902ff"],
    colorEnd: ["#ffffff"],
    size: [0.1, 0.4],
  }}
/>

Podemos ver las partículas subiendo lentamente.

En lugar de partículas cuadradas, vamos a usar triángulos. Para hacerlo podemos usar una cone geometry con los ajustes apropiados.

// ...

const VFXS = () => {
  return (
    <>
      <VFXParticles
        name="sparks"
        geometry={<coneGeometry args={[0.5, 1, 8, 1]} />}
        settings={{
          nbParticles: 100000,
          renderMode: "billboard",
          intensity: 3,
          fadeSize: [0.1, 0.1],
        }}
      />
    </>
  );
};

// ...

Las partículas ahora tienen forma de triángulos.

Ahora añadamos la esfera en crecimiento. Para hacerlo necesitamos añadir un nuevo componente VFXParticles al componente VFXS:

const VFXS = () => {
  return (
    <>
      {/* ... */}
      <VFXParticles
        name="spheres"
        geometry={<sphereGeometry args={[1, 32, 32]} />}
        settings={{
          nbParticles: 1000,
          renderMode: "mesh",
          intensity: 5,
          fadeSize: [0.7, 0.9],
          fadeAlpha: [0, 1],
        }}
      />
    </>
  );
};

Al establecer fadeSize a [0.7, 0.9] hacemos que la esfera crezca lentamente hasta el 70% de su vida útil y luego desaparezca rápidamente durante el último 10%.

Three.js logoReact logo

React Three Fiber: The Ultimate Guide to 3D Web Development

✨ You have reached the end of the preview ✨

Go to the next level with Three.js and React Three Fiber!

Get full access to this lesson and the complete course when you enroll:

  • 🔓 Full lesson videos with no limits
  • 💻 Access to the final source code
  • 🎓 Course progress tracking & completion
  • 💬 Invite to our private Discord community
Unlock the Full Course – Just $85

One-time payment. Lifetime updates included.