Come posso far brillare le particelle e proiettare luce sull'ambiente circostante?


22

Al momento sto provando a fare un effetto lucciola su una foresta oscura. Il livello ha una luce molto bassa e il giocatore è una delle poche fonti di luce. Per consentire al giocatore di vedere meglio il livello, sto tentando di far apparire casualmente lucciole luccicanti sulla mappa. Un modo è usare un sistema di particelle. Ma non posso far illuminare le particelle nei dintorni. C'è un modo per fare questo?


3
Il vero problema qui è che "la luce è costosa". Potrebbe essere meglio posizionare alcune luci a punto fisso che illuminano sufficientemente l'area, cuocere le luci in una mappa luminosa, quindi utilizzare le particelle per spiegare da dove proviene la sorgente luminosa, piuttosto che usare dozzine di luci dinamiche orribilmente costose.
Draco18s

@ Draco18s Non ci saranno dozzine di lucciole. Appariranno solo nella vista del giocatore. È dall'alto verso il basso e come tale facile da controllare. E in qualsiasi momento ci dovrebbero essere solo meno di 10 lucciole. Non suppongo che 10 punti luce dinamici siano costosi?
DarkDestry,

Per impostazione predefinita, Unity consente solo a due luci dinamiche attive di illuminare la geometria alla volta (sebbene possa essere diversa per una configurazione 2D). Puoi aumentare questo, ovviamente, ma tieni presente che +1 luce ha un impatto x2 sulle chiamate di disegno.
Draco18s

2
@ Draco18s questo può essere vero per il percorso di rendering in avanti, ma come indicato nei documenti "Quando si utilizza Deferred Shading, non vi è alcun limite al numero di luci che possono influenzare un oggetto" - Molte piccole luci che interessano solo una piccola parte di lo schermo è esattamente il tipo di percorsi di rendering differiti del caso d'uso che eccellono nella gestione efficiente. (Ad un costo tipico di una chiamata di disegno per luce unica, piuttosto che un moltiplicatore come con il rendering in avanti)
DMGregory

È un buon punto. Mi dimentico dei diversi percorsi di rendering per la maggior parte del tempo.
Draco18s,

Risposte:


7

Le particelle che emettono luce sono ora integrate in Unity in 5.5.

Abilita semplicemente le luci nell'ispettore di particelle, inserisci un riferimento a un prefabbricato leggero (funzionano sia le luci puntiformi che quelle spot) e modifica il rapporto su 1.

inserisci qui la descrizione dell'immagine

E voilà, particelle che emettono luci: ! [inserisci la descrizione dell'immagine qui

A quanto pare, si tratta di una configurazione piuttosto ottimizzata, che funziona a 1500 + fps sul mio impianto di perforazione anche con le massime luci a centinaia.

Modifica: dopo alcune osservazioni, mi sembra che le luci delle particelle si alternino tra l'illuminazione per frammento e l'illuminazione del vertice (presumibilmente per l'ottimizzazione?). Ciò potrebbe produrre piccole quantità di artefatti visivi se le luci massime sono impostate su un valore troppo alto.

Edit2: come sottolineato da DMGregory, i manufatti sono un sottoprodotto delle ottimizzazioni del rendering in avanti. L'illuminazione differita risolve il problema. Aggiunto gif più bello


1
Questa è una buona notizia! :) Questa risposta sarebbe ancora migliore se includesse alcune istruzioni dettagliate su come configurarlo con le nuove funzionalità del sistema particellare.
DMGregory

1
Il comportamento dell'illuminazione dei vertici che stai vedendo suona un po 'come alcune delle ottimizzazioni che Unity applica nel rendering in avanti. Vedi lo stesso comportamento quando usi il percorso differito?
DMGregory

Hai ragione! Gli artefatti non sono più presenti quando si utilizza il percorso di rendering differito.
eclmist

31

Dritta:

Questa risposta è obsoleta. L'unità ora supporta le particelle di luce puntiforme in modo nativo. Si prega di consultare questa risposta per tutti i dettagli.

Lascerò questo post qui per chiunque sia curioso, o utilizzi vecchie versioni di Unity o necessiti di un maggiore controllo manuale rispetto al metodo nativo, basta notare che il supporto nativo sarà probabilmente molto più efficiente e scalabile rispetto all'approccio presentato di seguito.


Non sono sicuro del motivo per cui così tante risposte affermano che questo è difficile o impossibile. Gestire alcune dozzine di luci dinamiche a punti è piuttosto convenzionale per una moderna pipeline di rendering differita in esecuzione su PC.

Ecco un breve esempio che ho preparato: Esempio di lucciole con luci

Uso questo script per generare dinamicamente abbastanza luci per le mie particelle massime (assicurati di regolare le impostazioni del tuo sistema particellare in modo che il massimo sia ragionevole - il valore predefinito di 1000 non renderà molto felice la tua scheda grafica), e quindi le aggiorna per seguire l'attivo particelle:

[RequireComponent(typeof(ParticleSystem))]
public class ParticleLights : MonoBehaviour {

    public Light lightPrefab;

    ParticleSystem _system;
    ParticleSystem.Particle[] _particles;
    Light[] _lights;


    void Start () {
        _system = GetComponent<ParticleSystem>();
        _particles = new ParticleSystem.Particle[_system.maxParticles];

        _lights = new Light[_system.maxParticles];
        for(int i = 0; i < _lights.Length; i++)
        {
            _lights[i] = (Light)Instantiate(lightPrefab);
            _lights[i].transform.parent = transform;
        }
    }

    void Update () {

        int count = _system.GetParticles(_particles);
        for(int i = 0; i < count; i++)
        {
            _lights[i].gameObject.SetActive(true);
            _lights[i].transform.localPosition = _particles[i].position;

            // Looks like the GetCurrentColor function was added in 5.3.
            // You can use other methods in earlier Unity versions.
            _lights[i].color = _particles[i].GetCurrentColor(_system);
        }

        for (int i = count; i < _particles.Length; i++)
        {
            _lights[i].gameObject.SetActive(false);
        }
    }
}

Modifica: puoi creare un prefabbricato creando prima un oggetto di gioco (in questo caso, Crea -> Luce -> Punto luce), impostandolo con il nome / parametri / script / figli che desideri, quindi trascinandolo dalla tua Gerarchia in il tuo esploratore di progetti. Ciò consente di salvare l'oggetto come risorsa che è possibile riutilizzare su più scene e script, con un certo grado di eredità. È possibile eliminare la copia nella scena e la risorsa rimarrà nella cartella Risorse a cui fare riferimento quando necessario.

Assicurati che lightPrefab abbia una gamma relativamente piccola e non offra ombre, per darti il ​​massimo spazio per le prestazioni per tutto ciò che accade nella tua scena. Non è necessario rendere LightPrefab stesso verde (o il colore delle tue lucciole): lo raccoglierà dal colore delle particelle.

Potresti scoprire che hai un migliore controllo sul volo delle lucciole se fai di ognuno il suo GameObject, con un quadrante cartellone e una luce attaccata con uno script di movimento / blinkig personalizzato, poiché ottenere un vagare convincente richiede più abilità nel sistema particellare che Lo so. ;)


In realtà ... anche se ho detto di non usare l'ombreggiatura per le lucciole, ho solo provato ad accenderlo nella mia scena di esempio e non ha causato problemi. Il modo in cui le ombre oscillano mentre le lucciole passano davanti agli oggetti è davvero fantastico e potrebbe aggiungere un'atmosfera spettrale. Il tuo chilometraggio può variare in base alla complessità della scena e dell'hardware di destinazione, quindi il profilo è sicuro, ma questo potrebbe essere un caso di ottimizzazione prematura da parte mia. :)
DMGregory

Come si crea un prefabbricato leggero?
DarkDestry,

Inoltre, per qualche motivo, ParticleSystem.Particle si riferisce alla particella legacy. Non esiste un metodo GetCurrentColor o GetCurrentSize per questo.
DarkDestry,

@DarkDestry Ho aggiunto una nota alla risposta sulla creazione di prefabbricati. Per quanto riguarda le funzioni mancanti, questo potrebbe essere un problema di versione: sto lavorando in 5.3, nelle versioni precedenti di Unity potresti farlo in un modo diverso. Discutiamo i dettagli dell'implementazione in chat , usando la stanza creata da Hamza Hasan.
DMGregory

Quindi un prefabbricato leggero è lo stesso di un normale prefabbricato. È stato confuso quando è menzionato come un prefabbricato leggero.
DarkDestry,

3

Anni fa, prima che le luci dinamiche fossero accessibili, avremmo semplicemente usato un effetto particellare in cartellone 2D con miscelazione additiva. Illuminerebbe la scena verso il bianco. Disegnandolo con la profondità corretta della lucciola, si ottiene un ordinamento quasi corretto. L'alfa additiva non ha bisogno di essere ordinata quando si sovrascrive se stessa rispetto alla miscelazione alfa. Non illuminerà TUTTA la scena, ma illuminerà l'area circostante la lucciola. Potresti quindi prendere una luce dinamica e scegliere una delle lucciole ogni pochi secondi per illuminare effettivamente la scena, se ne hai bisogno.

C'è già una domanda e risposta sugli effetti di bagliore Come ottenere un'illuminazione simile in Unity per i giochi 2D?


0

Sfortunatamente, non ho avuto molta esperienza con Unity nella sua forma attuale (ci ho giocato molti anni fa), quindi non so esattamente con quali set di funzionalità devi lavorare nel motore.

In ogni caso, indipendentemente dal motore con cui lavori, le luci dinamiche sono qualcosa da evitare ogni volta che puoi. Sono molto costosi dal punto di vista computazionale e tendono ad aggiungere complessità della scena in modo esponenziale. Tuttavia, come è l'ordine del giorno per la maggior parte del rendering 3D, ci sono molti modi per ottenere effetti simili ingannando;

Un modo possibile per ottenere un effetto simile è mappare una trama di bagliore premade sul terreno sotto le lucciole, (assumendo un sistema di coordinate Y = su / giù) con posizioni X e Z che controllano la posizione del bagliore sul terreno e l'offset Y dal terreno che controlla l'alfa della trama (più luminoso = più vicino al terreno)

Ci sono ovviamente diversi svantaggi di questo metodo. Non proietti ombre poiché non viene utilizzata la luce e non influenzerai nessun'altra geometria del mondo (oggetti di scena, fogliame, ecc.)


-2

Usa Lightl'origine del fuoco e gioca con le sue dimensioni nello script in modo da dare l'effetto di bruciare. E usa il tuo sistema di particelle :)


Non c'è fuoco nella scena. Sto avendo scarse particelle apparire dentro e fuori dall'esistenza. Non esiste alcuna posizione fissa per le particelle. Si prega di leggere la domanda.
DarkDestry,

Allora, qual è il problema? puoi attaccare la luce al tuo prefabbricato in particelle piuttosto che in posizioni predefinite
Hamza Hasan,

La domanda è come farlo. Sto usando il sistema di particelle di unità. E non vedo un prefabbricato lì. A meno che tu non mi stia chiedendo di creare un prefabbricato che abbia una luce e generi una base sulla sceneggiatura
DarkDestry,

Quindi hai un gioco di particelle Oggetto nella scena. Attacca una luce allo stesso oggetto di gioco e creane uno prefabbricato trascinando quel giocoObject in Unity File Explorer.
Hamza Hasan,

Ho un gioco Particle SystemObject nella scena. Non una particella.
DarkDestry,
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.