Maison >interface Web >tutoriel CSS >Une toile de fond étoilée interactive pour le contenu

Une toile de fond étoilée interactive pour le contenu

William Shakespeare
William Shakespeareoriginal
2025-03-13 11:22:10870parcourir

Une toile de fond étoilée interactive pour le contenu

L'année dernière, j'ai eu l'occasion de collaborer avec Shawn Wang (Swyx) sur un projet de temporal. L'objectif était d'améliorer leur site Web avec des éléments créatifs. C'était un défi fascinant, car je suis plus un développeur qu'un concepteur, mais j'ai saisi la chance d'élargir mes compétences en conception.

Une de mes contributions a été une toile de fond étoilée interactive. Vous pouvez le voir en action ici:

Concept de Blockquote utilisant la perspective et les propriétés personnalisées CSS. Profiter de la liberté de création à @temporalio. Ajouter une touche de fantaisie! ⚒️ @reactjs && @tailwindcss (le site est NextJS)? Lien vers Codepen via @codepen pic.twitter.com/s9xp2trrox

- Jhey ?? ✨ (@ jh3yy) 2 juillet 2021

La force de cette conception réside dans son implémentation en tant que composant réutilisable REACT, offrant une configurabilité élevée. Besoin de formes différentes au lieu des étoiles? Vous voulez contrôler précisément le placement des particules? Vous êtes en contrôle total.

Construisons ce composant! Nous utiliserons React, Greensock et le HTML<canvas></canvas> élément. React est facultatif, mais l'utiliser crée un composant réutilisable pour les projets futurs.

Construire l'application de base

 Importer React à partir de 'https://cdn.skypack.dev/react';
Importez Reactdom depuis 'https://cdn.skypack.dev/rect-dom';
Importer GSAP à partir de 'https://cdn.skypack.dev/gsap';

const root_node = document.QuerySelector ('# app');

const starscape = () =><h1> Cool Thingzzz!</h1> ;

const app = () =><starscape></starscape> ;

Reactdom.render (<app></app> , Root_node);

Tout d'abord, nous rendons un<canvas></canvas> élément et saisissez une référence à utiliser dans le crochet useEffect de React. Si vous n'utilisez pas React, stockez la référence directement dans une variable.

 const starscape = () => {
  const canvasref = react.UseRef (null);
  retour<canvas ref="{canvasRef}"></canvas> ;
};

Nous allons styliser le<canvas></canvas> Pour remplir la fenêtre et asseoir derrière le contenu:

 toile {
  Position: fixe;
  Encart: 0;
  Contexte: # 262626;
  Z-Index: -1;
  Hauteur: 100VH;
  Largeur: 100 VW;
}

Ajout d'étoiles

Nous simplifierons le rendu d'étoile en utilisant des cercles avec des opacités et des tailles variables. Dessinant un cercle sur un<canvas></canvas> implique d'obtenir le contexte et d'utiliser la fonction arc . Rendons un cercle (notre étoile) au centre à l'aide d'un crochet useEffect :

 const starscape = () => {
  const canvasref = react.UseRef (null);
  const ContexTref = react.UseRef (null);
  React.Useeffect (() => {
    canvasref.current.width = window.innerwidth;
    canvasref.current.height = window.innerHeight;
    contextref.current = canvasref.current.getContext ('2d');
    contextref.current.fillstyle = 'jaune';
    contextref.current.beginPath ();
    contextref.current.arc (
      window.innerwidth / 2, // x
      window.innerheight / 2, // y
      100, // rayon
      0, // Angle de démarrage (radians)
      Math.pi * 2 // Angle de fin (radians)
    ));
    contextref.current.fill ();
  }, []);
  retour<canvas ref="{canvasRef}"></canvas> ;
};

Cela crée un cercle jaune. Le code restant sera dans cette useEffect . C'est pourquoi la pièce de réact est facultative; Vous pouvez adapter ce code pour d'autres cadres.

Nous devons générer et rendre plusieurs étoiles. Créons une fonction LOAD pour gérer la génération d'étoiles et la configuration du canevas, y compris le dimensionnement du canevas:

 const charge = () => {
  const vmin = math.min (window.innerheight, window.innerwidth);
  const star_count = math.floor (vmin * densityratio);
  canvasref.current.width = window.innerwidth;
  canvasref.current.height = window.innerHeight;
  starsRef.current = new Array (star_count) .fill (). map (() => ({
    x: gsap.utils.random (0, window.innerwidth, 1),
    y: gsap.utils.random (0, window.innerheight, 1),
    Taille: gsap.utils.random (1, sizelimit, 1),
    Échelle: 1,
    alpha: gsap.utils.random (0,1, defaultalpha, 0,1),
  }));
};

Chaque étoile est un objet avec des propriétés définissant ses caractéristiques (x, position y, taille, échelle, alpha). sizeLimit , defaultAlpha et densityRatio sont des accessoires transmis au composant Starscape avec des valeurs par défaut.

Un exemple d'objet étoile:

 {
  "x": 1252,
  "Y": 29,
  "taille": 4,
  "échelle": 1,
  "Alpha": 0,5
}

Pour rendre ces étoiles, nous créons une fonction RENDER qui itère sur le tableau stars et rend chaque étoile en utilisant la fonction arc :

 const Render = () => {
  contextref.current.clearrect (
    0,
    0,
    canvasref.current.width,
    canvasref.current.height
  ));
  StarsRef.current.ForEach ((Star) => {
    contextref.current.fillStyle = `Hsla (0, 100%, 100%, $ {star.alpha})`;
    contextref.current.beginPath ();
    contextref.current.arc (star.x, star.y, star.size / 2, 0, math.pi * 2);
    contextref.current.fill ();
  });
};

La fonction clearRect efface la toile avant le rendu, ce qui est crucial pour l'animation.

Le composant Starscape complet (sans interactivité) est illustré ci-dessous:

Composant Starscape complet (sans interactivité)

 const starScape = ({densityRatio = 0,5, sizelimit = 5, defaultalpha = 0,5}) => {
  const canvasref = react.UseRef (null);
  const ContexTref = react.UseRef (null);
  const starsRef = react.UseRef (null);
  React.Useeffect (() => {
    contextref.current = canvasref.current.getContext ('2d');
    const charge = () => {
      const vmin = math.min (window.innerheight, window.innerwidth);
      const star_count = math.floor (vmin * densityratio);
      canvasref.current.width = window.innerwidth;
      canvasref.current.height = window.innerHeight;
      starsRef.current = new Array (star_count) .fill (). map (() => ({
        x: gsap.utils.random (0, window.innerwidth, 1),
        y: gsap.utils.random (0, window.innerheight, 1),
        Taille: gsap.utils.random (1, sizelimit, 1),
        Échelle: 1,
        alpha: gsap.utils.random (0,1, defaultalpha, 0,1),
      }));
    };
    const Render = () => {
      contextref.current.clearrect (0, 0, canvasref.current.width, canvasref.current.height);
      StarsRef.current.ForEach ((Star) => {
        contextref.current.fillStyle = `Hsla (0, 100%, 100%, $ {star.alpha})`;
        contextref.current.beginPath ();
        contextref.current.arc (star.x, star.y, star.size / 2, 0, math.pi * 2);
        contextref.current.fill ();
      });
    };
    const run = () => {
      CHARGER();
      RENDRE();
    };
    COURIR();
    window.addeventListener («redimensi», exécuter);
    return () => {
      window.reMoveEventListener («redimensi», exécuter);
    };
  }, []);
  retour<canvas ref="{canvasRef}"></canvas> ;
};

Expérimentez les accessoires dans une démo pour voir leurs effets. Pour gérer le redimensionnement de la fenêtre, nous appelons LOAD et RENDER sur redimensionnement (avec le débouchement pour l'optimisation, qui est omis pour la concision ici).

Ajout d'interactivité

Maintenant, rendons la toile de fond interactive. Lorsque le pointeur se déplace, les étoiles près du curseur s'éclaiment et se montent.

Nous ajouterons une fonction UPDATE pour calculer la distance entre le pointeur et chaque étoile, puis entre l'échelle de l'étoile et l'alpha à l'aide de l'utilitaire mapRange de Greensock. Nous ajouterons également des accessoires scaleLimit et proximityRatio pour contrôler le comportement de mise à l'échelle.

 const update = ({x, y}) => {
  StarsRef.current.ForEach ((Star) => {
    const Distance = math.sqrt (math.pow (star.x - x, 2) math.pow (star.y - y, 2));
    gsap.to (étoile, {
      Échelle: scalemapperref.current (math.min (distance, vMinref.current * proximityratio)),
      alpha: alphamapperref.current (math.min (distance, vMinref.current * proximityratio)),
    });
  });
};

Pour rendre les mises à jour, nous utilisons gsap.ticker (une bonne alternative à requestAnimationFrame ), ajoutant RENDER au ticker et le supprimant dans le nettoyage. Nous définissons les cadres par seconde (FPS) sur 24. La fonction RENDER utilise désormais la valeur star.scale lors du dessin de l'arc.

 CHARGER();
gsap.ticker.add (rendu);
gsap.ticker.fps (24);
window.addeventListener («redimensi», charge);
document.addeventListener ('PointerMove', Update);
return () => {
  window.reMoveEventListener («redimensi», charge);
  Document.RemoveEventListener («PointerMove», mise à jour);
  GSAP.Ticker.Remove (rendu);
};

Maintenant, lorsque vous déplacez votre souris, les étoiles réagissent!

Pour gérer le cas où la souris quitte la toile, nous ajoutons un auditeur d'événements pointerleave qui revient les étoiles à leur état d'origine:

 const exit = () => {
  gsap.to (starsRef.current, {scale: 1, alpha: defaultalpha});
};

// ... Écouteurs d'événements ...
document.addeventListener ('PointerLeave', exit);
return () => {
  // ... nettoyage ...
  Document.RemoveEventListener («PointerLeave», exit);
  GSAP.Ticker.Remove (rendu);
};

Bonus: Oeuf de Pâques de code konami

Ajoutons un oeuf de Pâques de code konami. Nous écouterons les événements du clavier et déclencherons une animation si le code est entré.

 const konami_code = 'arrowup, arrowup, arrowdown, arrowdown, arrowleft, arrowright, arrowleft, arrowright, keyb, keya';
const CodeRef = react.UseRef ([]);
React.Useeffect (() => {
  const handlecode = (e) => {
    CodeRef.Current = [... CodeRef.Current, E.Code] .Slice (CodeRef.Current.Length> 9? CodeRef.Current.Length - 9: 0);
    if (CodeRef.Current.Join (','). TolowerCase () === Konami_Code.tolowerCase ()) {
      // déclenche une animation d'oeuf de Pâques
    }
  };
  window.addeventListener ('keyup', handlecode);
  return () => {
    window.reMoveEventListener ('KeyUp', handlecode);
  };
}, []);

Le composant Starscape complet et interactif avec l'œuf de Pâques du code Konami est assez long et omis ici pour la concision. Cependant, les principes décrits ci-dessus montrent comment créer une toile de fond étoilée interactive entièrement fonctionnelle et personnalisable à l'aide de React, Greensock et HTML<canvas></canvas> . L'animation des œufs de Pâques impliquerait de créer un gsap.timeline pour animer les propriétés des étoiles.

Cet exemple montre les techniques nécessaires pour créer vos propres fonds personnalisés. N'oubliez pas de considérer comment la toile de fond interagit avec le contenu de votre site. Expérimentez avec différentes formes, couleurs et animations pour créer des visuels uniques et engageants.

Ce qui précède est le contenu détaillé de. pour plus d'informations, suivez d'autres articles connexes sur le site Web de PHP en chinois!

Déclaration:
Le contenu de cet article est volontairement contribué par les internautes et les droits d'auteur appartiennent à l'auteur original. Ce site n'assume aucune responsabilité légale correspondante. Si vous trouvez un contenu suspecté de plagiat ou de contrefaçon, veuillez contacter admin@php.cn