सरल कण प्रभाव बनाने का सबसे तेज़ तरीका


12

मैं वास्तव में सरल कण प्रभाव बनाने के लिए सबसे तेज़ तरीका ढूंढ रहा हूं जो खेल पर नरक की तरह स्पैम हो जाएगा ...

मूल रूप से, मेरा गेम एक वेक्ट्रेक्स गेम जैसा दिखता है, जो ज्यादातर लाइनों से बना है ... मैं कुछ छोटे विस्फोट करना चाहता हूं जो वास्तव में सामान्य होंगे।

कुछ बिंदुओं पर घूमने और GL_Point के साथ रेंडर करने की तुलना में कुछ तेज़ हैं?


+1 केवल वेक्ट्रेक्स संदर्भ के लिए। मैंने शुरुआती 80 के दशक में एक बच्चे के रूप में स्क्रैम्बल और टेम्पेस्ट पर कुछ मजेदार घंटे बिताए। इसके बिना मैं शायद आज गेम डेवलपर के रूप में समाप्त नहीं होता।
काइलोटन

हां, टेंपेस्ट कमाल का है: D
स्पीड

मैं कैसे कहूं कि कोई भी सही नहीं है?
स्पीड जूल

जवाबों:


13

प्रत्येक कण के लिए स्मृति को स्टोर करने और प्रत्येक कण को ​​अलग से चेतन करने की वास्तव में कोई आवश्यकता नहीं है। आप इसे क्लासिक भौतिकी समीकरण का उपयोग करके ड्राइंग के दौरान कण की स्थिति का पुनर्निर्माण करके प्रक्रियात्मक रूप से कर सकते हैं। s = ut + 1 / 2.at ^ 2

एक सरल उदाहरण (कणों के निरंतर त्वरण के बिना):


void drawExplosion(ExplosionParameters& s)
{
  Random rng;
  rng.seed(s.startSeed);
  glBegin(GL_POINTS);
  for (int i = 0; i < s.numParticles; i++)
  {
    vec3 vel = rng.getRandomVector(-1.0f, 1.0f) * s.explosionSpeed;
    float timeBias = rng.getRandom(0, s.particleTimeBias);
    vec3 pos = s.explosionCentre + (vel * (s.timeElapsed + timeBias));
    glPoint3fv(&pos);
  }
  glEnd();
}

तो आप बस अपने अद्यतन लूप के हर पुनरावृत्ति पर s.timeElapsed बढ़ाएँ।

यह भी पूरी तरह से GPU पर लागू किया जा रहा है इस प्रकार अपने CPU किसी भी काम करने से मुक्त किया जा रहा है। एक gpu कार्यान्वयन इस तरह लग सकता है:

void drawExplosion(ExplosionParameters& s)
{
    //bind Vertex Shader If Not Already Bound();
    ...
    // bindVertexBuffer of Zeroes If Not AlreadyBound();
    glVertexPointer(...)
    //uploadShaderUniformsForExplosion(s);
    glUniform3f(...)
    ...
    glDrawArrays(GL_POINTS, 0, s.numParticles);
} 

GPU वर्टेक्स shader फिर भौतिकी समीकरण और इसके माध्यम से वर्दी / स्थिरांक के माध्यम से कण स्थिति को फिर से संगठित करेगा - जैसा कि सीपीयू संस्करण ने किया था।

कुछ भिन्नताएँ जोड़ने के लिए, आप भिन्न भिन्न मापदंडों के साथ अधिक समकालिक विस्फोटों का उपयोग कर सकते हैं, रंग / अल्फा को अलग कर सकते हैं, भिन्न आरंभिक पदों को चुन सकते हैं। आदि।


इसके अलावा, आप सभी कणों के प्रारंभिक वैक्टर को उत्पन्न करने के लिए छद्म यादृच्छिक संख्याओं की भविष्यवाणी का उपयोग कर सकते हैं, जिससे कुछ अंतर डेटा के सैकड़ों कण बन सकते हैं। क्वैड बनाने के लिए GPU का उपयोग करना सरल कणों के लिए वास्तव में अच्छा विचार है।
स्किज़ जूल

वर्षों से मैं कण प्रणालियों को पारंपरिक तरीकों से बना रहा हूं जो कक्षाओं के सरणियों के साथ कणों को अर्ध-बुद्धिमान संस्थाओं के रूप में मानते हैं और यह हमेशा बेकार और फूला हुआ लगता था। यह तरीका बुनियादी कणों के लिए बहुत बेहतर है जो कि स्क्रीन के ऊपर स्प्यू से ज्यादा कुछ नहीं करते हैं।
पीकू

7

मैंने कई परीक्षण किए, और सबसे तेज़ तरीका (कोड के लिए सबसे तेज़ नहीं) कण थे जो GL_LINE से बने थे जो उनकी स्थिति और गति को जानते थे, और इसका उपयोग तब किया जाता था जब रेंडरिंग के दौरान अंक (इसलिए, जितनी तेज़ी से कण जाते हैं, सबसे "लाइन" यह हो जाता है, धीमा, यह एक बिंदु बन जाता है)।

प्रभाव वास्तव में अच्छा है (इसे देखने के लिए किसी भी ज्यामिति युद्धों वीडियो को देखें), और वास्तव में तेजी से भी। बकवास को क्वाड्स से बाहर निकालें (विशेषकर क्योंकि क्वैड्स मुझे वर्टेक्स की दोहरी मात्रा की गणना करने की आवश्यकता होगी)

इसके अलावा, यह पहले से ही किए गए कण प्रणाली का उपयोग करने से बेहतर है, क्योंकि मैं एक विशिष्ट और तेज़ प्रभाव चाहता था, कण प्रणाली आमतौर पर ओवरहेड की आनुपातिक मात्रा के साथ बहुत सारी सुविधाओं का समर्थन करती है।


2
+1 यह समझाने के लिए कि आपने क्या किया, हालाँकि मैं आपके परीक्षणों के बारे में अधिक जानकारी सुनने के लिए उत्सुक हूँ। =)
leander

Btw: वह सब तत्काल मोड में था (कि केवल एक चीज है जो मुझे पता है कि कोड कैसे करना है, और मैंने कल नाम सीखा ...)
स्पीड सेपर

6

आम तौर पर मुझे लगता है कि आप बनावट-मैप किए गए quads के रूप में कणों को करेंगे। उन्हें मूल रूप से 2 डी स्प्राइट के रूप में व्यवहार करें, और अदृश्य होने पर उन्हें नष्ट करते हुए, समय के साथ उन्हें फीका कर दें। बेहतर तब भी, जब आप नए बनाते हैं तो पुराने का पुन: उपयोग करें ताकि आप इन चीजों के लिए स्मृति को नहीं बढ़ा रहे हैं।

यदि आप कला पर प्रीमैलिप्लीड अल्फ़ा का उपयोग करते हैं तो आप आसानी से एक प्रकार के ब्लोइंग ऑपरेशन के अलावा लाइट्स, फायर, स्मोक और बहुत कुछ का समर्थन कर सकते हैं।


हम ... अंक बनावट की तुलना में तेज नहीं हैं?
स्पीड जूल

2
ग्राफिक्स हार्डवेयर को विशेष रूप से फ़्रेमबफ़र को रेखापुंज बनावट के लिए अनुकूलित किया गया है। यदि अंक अधिक तेज़ हैं, तो यह एक नगण्य राशि से होने की संभावना है, और आप उन सभी संभावनाओं को खो देते हैं जो आपको बनावट के साथ मिलती हैं।
काइलोटन

जैसे क्या? ध्यान रहे मैं एक पूर्ण रूप से चित्रित कण प्रणाली नहीं बना रहा हूं, यह केवल एक विशिष्ट प्रभाव (छोटे विस्फोट, ज्यादातर गेमबैक फीडबैक के लिए है कि आप कुछ हिट करते हैं)
स्पीड जूल

यदि आप केवल अंक या रेखाओं का उपयोग करना चाहते हैं, तो यह ठीक है। मैं केवल इस बात पर टिप्पणी कर सकता हूं कि अधिकांश लोग कणों के लिए क्या करते हैं। शायद एक अधूरा त्रिकोण एक अच्छा कण बना देगा।
काइलोटन

4

OpenGL ES 2.0, ES 1.X एक एक्सटेंशन के साथ और OpenGL => 2.1 के साथ, आप GL_POINT_SPRITES का उपयोग कर सकते हैं। GL_POINT_SPRITES हमेशा कैमरे के सामने एक क्वाड की तरह होता है।

टुकड़े टुकड़े में, आप कर सकते हैं:

  • वर्टीकल शेडर में gl_PointSize के साथ स्प्राइट के आकार को परिभाषित करें
  • टुकड़ा shader में gl_PointCoord (uv निर्देशांक) का उपयोग करें

आप गेंद स्प्राइट को आकर्षित करने के लिए अल्फा के साथ बनावट का उपयोग कर सकते हैं ...

प्वाइंट स्प्राइट्स के लिए एक ट्यूटोरियल


मैं विस्तार से बच रहा हूं, मूर्ख लोग जो इंजन (जो मैंने नहीं बनाया है) पहले से उपयोग करते हैं, कई लोगों के लिए पर्याप्त रूप से पर्याप्त हैं जो शिकायत करते हैं कि खेल नहीं चलता है ...
तेज जूल

1

अधिकांश कण प्रभाव प्रणाली मैंने देखी है, बड़ी संख्या में बिंदुओं को खींचने के बजाय , बिलबोर्ड बनावट की अपेक्षाकृत कम संख्या आकर्षित करें जहां प्रत्येक बनावट विस्फोट की तरह दिखती है। जब तक आपकी कला शैली वास्तव में रोकती है, तब तक आप संभवतः उस मार्ग से नीचे जाने में अधिक खुश होंगे। यह उन कणों की मात्रा को कम कर देगा जिन्हें आपको व्यक्तिगत रूप से चेतन करने और रेंडर करने की आवश्यकता है जबकि अभी भी एक बड़ा दृश्य प्रभाव देता है।


1
सच है, लेकिन वह वेक्ट्रेक्स शैली के लिए लक्ष्य बना रहा है, यह वहां कम अच्छी तरह से काम करेगा।
काज

1
वास्तव में काज ने जो कहा ... वह व्यर्थ होगा, और डाउनलोड आकार में वृद्धि होगी (मैं सबसे अधिक ग्राफिक्स स्विच कर रहा हूं जो मुझे सच्चे वैक्टर से फैल सकता है, इसलिए मैं फ़ाइलों को कम कर सकता हूं)
तेज तर्रार

1

कणों के स्पाविंग / विलोपन / अद्यतन को संभालने के लिए एक छोटे से तरीके के लिए, यह मानते हुए कि आपके पास कणों का एक सरल सरणी है - कण [MAX_PARTICLES]:

सक्रिय कणों पर नज़र रखें (NumActiveParticles = 0 से शुरू)

नए कण हमेशा सरणी के अंत में जोड़े जाते हैं:

pNewParticle = &Particles[NumActiveParticles++];

चतुर बिट - जब एक 'मृत' कण को ​​हटाते हैं - इसे अंतिम सक्रिय कण के साथ स्वैप करते हैं, और न्यूमेरिकटार्टर को घटाते हैं:

if ( DeadParticle < NumActiveParticles-1 )
{
  Particles[ DeadParticle ] = Particles[ NumActiveParticles-1 ];
}
NumActiveParticles--;

यह स्पॉनिंग के दौरान 'अप्रयुक्त कणों' के लिए किसी भी खोज से बचा जाता है, और अगर कोई भी उपयोग में नहीं है, तो MAX_PARTICLES की एक सरणी के माध्यम से किसी भी स्कैनिंग से बचा जाता है।

ध्यान दें कि यह केवल तभी काम करता है जब अपडेट / रेंडर ऑर्डर महत्वहीन हो (जैसा कि कई कण प्रभावों के लिए मामला है, जो कि additive सम्मिश्रण का उपयोग करता है) - के रूप में एक कण को ​​हटाने का यह तरीका फिर से आदेश देता है


-1

सबसे तेज़ तरीका मुझे लगता है कि एक कण इंजन को ढूंढना है और अपने प्रभावों के लिए इसका उपयोग करना है। यहाँ कुछ है:

हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.