Come posso generare un effetto fulmine?


26

Esiste un algoritmo per generare un fulmine?

Vorrei un algoritmo che genera un elenco di segmenti o oggetti punto che specifica dove atterrerà il bullone. Il metodo avrebbe bisogno di un parametro del punto iniziale, insieme a un endpoint. Il bullone dovrebbe avere rami casuali che escono da esso e zig-zag a intervalli casuali. Il risultato sarà un effetto lampo casuale che potrebbe apparire in questo modo


(fonte: wikimedia.org )

Se qualcuno fosse a conoscenza di un algoritmo per cui questo potrebbe funzionare, l'aiuto sarebbe molto apprezzato!


2
Questo articolo di Nvidia dovrebbe essere proprio quello di cui hai bisogno, anche se potrebbe essere un po 'troppo esteso. Dai un'occhiata alle diapositive da 7 a 11, hanno dei bei imadges che dovrebbero darti un'idea di cosa puntare. Se segui il secondo link, troverai il codice sorgente (C ++, Direct3D). developer.download.nvidia.com/SDK/10/direct3d/Source/Lightning/… developer.download.nvidia.com/SDK/10/direct3d/samples.html
Errore

Risposte:


32

C'è un algoritmo abbastanza semplice che puoi usare per generare bulloni di illuminazione.

Inizia con un segmento di linea tra l'origine del bullone ( O) e il punto finale ( E)

Scegli un punto su quella linea (approssimativamente o esattamente nel mezzo), chiamato Se dividi il segmento in due segmenti di linea ( O->Se S->E). Spostare Slontano dal segmento di linea originale (lungo il normale del segmento) di una piccola quantità casuale. Questo ti dà una sola "curva" di fulmini.

Dopo aver calcolato la curva, in base a una piccola possibilità casuale ti consigliamo di aggiungere un segmento di terza linea (di solito un'estensione del O->Ssegmento). Ecco come si producono le "forcelle" nel lampo. Di solito vorrai tenere traccia delle informazioni sull'intensità del bullone durante questo processo di generazione, perché vorrai che le forcelle siano più deboli o abbiano una sfocatura più sottile:

inserisci qui la descrizione dell'immagine

Quindi, ripeti il ​​procedimento sopra descritto per tutti i nuovi segmenti di linea che hai; dovrai scegliere una quantità di ripetizione che produce forme che ti piacciono:

inserisci qui la descrizione dell'immagine

C'è una spiegazione abbastanza chiara di questa tecnica sul blog del mio amico qui (è dove ho spudoratamente rubato le foto); approfondisce ulteriormente l'aggiunta dell'effetto bagliore.

Infine, c'è anche questo articolo NVIDIA che descrive lo stesso algoritmo di base (anche con maggiori dettagli).


13

Consiglierei un approccio alternativo: l'albero che esplora rapidamente (RRT) . Una cosa interessante è che puoi farla girare negli angoli o esplodere in tutte le direzioni.

L'algoritmo è davvero di base:

// Returns a random tree containing the start and the goal.
// Grows the tree for a maximum number of iterations.
Tree RRT(Node start, Node goal, int maxIters)
{
    // Initialize a tree with a root as the start node.
    Tree t = new Tree();
    t.Root = start;


    bool reachedGoal = false;
    int iter = 0;

    // Keep growing the tree until it contains the goal and we've
    // grown for the required number of iterations.
    while (!reachedGoal || iter < maxIters)
    {
         // Get a random node somewhere near the goal
         Node random = RandomSample(goal);
         // Get the closest node in the tree to the sample.
         Node closest = t.GetClosestNode(random);
         // Create a new node between the closest node and the sample.
         Node extension = ExtendToward(closest, random);
         // If we managed to create a new node, add it to the tree.
         if (extension)
         {
             closest.AddChild(extension);

             // If we haven't yet reached the goal, and the new node
             // is very near the goal, add the goal to the tree.
             if(!reachedGoal && extension.IsNear(goal))
             {
                extension.AddChild(goal);
                reachedGoal = true;
             }
         }
         iter++;
    }
    return t;
}

Modificando le funzioni RandomSamplee ExtendToward, è possibile ottenere alberi molto diversi. Se RandomSamplecampiona uniformemente ovunque, l'albero crescerà uniformemente in tutte le direzioni. Se è di parte verso l'obiettivo, l'albero tenderà a crescere verso l'obiettivo. Se campiona sempre l'obiettivo, l'albero sarà una linea retta dall'inizio alla meta.

ExtendTowardpuò permetterti di fare cose interessanti anche sull'albero. Per prima cosa, se hai ostacoli (come i muri), puoi far sì che l'albero cresca attorno a loro semplicemente rifiutando le estensioni che si scontrano con i muri.

Questo è come appare quando non distorci il campionamento verso l'obiettivo:

img
(fonte: uiuc.edu )

Ed ecco come appare con i muri

Alcune fantastiche proprietà dell'RRT al termine:

  • La RRT non si attraverserà mai da sola
  • L'RRT coprirà infine l'intero spazio con rami sempre più piccoli
  • Il percorso dall'inizio alla meta può essere completamente casuale e strano.

Ho appena usato questo algoritmo per generare un'animazione di fulmini. Devo dire che ha funzionato davvero bene! C'è un errore di battitura importante nel codice, come ad esempio non essere incrementato ad ogni ciclo. A parte questo, questo è quasi pronto per l'uso come pubblicato
applejacks01,
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.