jontte / dmcr Goto Github PK
View Code? Open in Web Editor NEWDistributed Monte-Carlo Raytracer
License: Other
Distributed Monte-Carlo Raytracer
License: Other
Scene Description Language tarttee kätevän tavan ilmaista kappaleen / pinnan ominaisuudet.
Tällä hetkellä: JSON-koodi ja oletusarvo.
"color":[r,g,b]
"blur":1.0
"emit":0.0
"opacity":1.0
"refractive_index":1.0
Näiden tilalle pitäisi tulla seuraavat (mielellään jotenkin fiksusti jäsenneltynä, esim omaan material- tai texture- blokkiinsa:
Säteen kulkuun vaikuttavat:
"diffuse":(0-1, default esim 0.7) - kuvaa pinnan muovi/mattamaista heijastamista
"reflection": (0-1, default esim 0.0) - kuvaa pinnan pelimaista heijastamista
"emit": (0-inf, default 0.0) - kuvaa pinnan valonlähettämisominaisuutta
"opacity" : (välillä 0-1) - kuvaa materiaalin läpinäkymättömyyttä (0 täysin läpinäkyvä, 1 täysin läpinäkymätön (wat?)) TAI "transmit": (välillä 0-1) - kuvaa materiaalin läpinäkyvyyttä (0 täysin läpinäkymätön, 1 täysin läpinäkyvä)
Edellisiin vaikuttavat:
"color": [r,g,b] arvot välillä 0-1 - kuvaa pinnan väriä DIFFUSE- ja EMIT-ominaisuuksien yhteydessä (reflection-ominaisuus ei riipu väristä)
"ior": (fysikaaliset arvot välillä 1-3 tjsp), eli Index of Refraction, taitekerroin (nykyään refractive_index, mut ior on "virallinen"), vaikuttaa OPACITY/TRANSMIT:n kanssa
"blur": (arvot välillä 0-1) - kuvaa peiliheijastuksen epätäydellisyyttä (0 täydellinen peili, 1 heijastaa täysin sattumanvaraiseen suuntaan)
Cache results of float division, for more discussion see http://tavianator.com/2011/05/fast-branchless-raybounding-box-intersections/
Vector-luokka pitää laittaa dmcr-namespacen sisään.
Iteratorin tulisi valita uuden rayn:n tyypiksi YKSI seuraavista:
diffuse - uusi säde ammutaan hemispheren sisällä randomiin suuntaan ja lopputulos kerrotaan BRDF:llä ja pinnan värillä
reflection - uusi säde ammutaan heijastussuuntaan (+ randomia blur:n verran)
transmit - uusi säde ammutaan kohteen läpi (taittaen ior:n mukaan) ja lopputulos kerrotaan pinnan värillä
Valinta voidaan tehdä esim siten, että skaalataan diffuse + reflection + transmit siten, että summaksi tulee 1. Sit otetaan randomilla luku väliltä 0-1, ja jos
rand < diffuse => tehdään diffuse-ray
diffuse < rand < diffuse + reflection => tehdään reflection-ray
muuten => tehdään transmit-ray
NÄIDEN LISÄKSI osumakohdasta tulee ottaa huomioon sen kontribuutio emit-arvon mukaan, siitä huolimatta mikä ray valittiin.
Eli esim:
Color color = obj->color * obj->emit
if diffuse:
color += BRDF * color * iterator(diffuse_ray)
else if reflection:
color += iterator(reflection_ray)
else
color += color * iterator(transmit_ray)
Jokaiselle kappaleelle getRandomPointOnSurface (tjsp) -metodi, joka siis palauttaa (mielellään mahdollisimman tasaisesti jakautuneesti) sattumanvaraisen pisteen kappaleen pinnalta.
Jotta voidaan path tracettaa kahdesta suunnasta, täytyy löytää alkupiste toiselle suunnalle. Eli jokaisesta kappaleesta täytyy voida pyytää piste pinnalta. Tästä pisteestä lähdetään sitten iteroimaan.
Luokat hallinnoimaan ajossa olevia renderöintitöitä.
Backend voi kaatua jos tulee paketti jonka len-kenttä on huijattu liian isoksi. Tähän joku sanity check.
Renderer::iterator:n tulee palauttaa lista (jossain muodossa, std::list tai std::vector tai joku) joka sisältää kaikki läpikäydyt pisteet sekä oleelliset asiat niistä (esim osumapiste, normaali, tulosuunta, lähtösuunta, materiaali, väri, POLUN PAINO [tää on yllättävän kätevä ja haastava],..).
Bi-directional path tracingin toteuttaminen vaatii, että Renderer::midfunc kutsuu iterator-metodia kahdesti - kerran kamerasta (attribuuttina saatu Ray) ja kerran jostakin valonlähteestä (#23). Lisäksi kummastakin iterator-ketjusta tarvitaan suht hyvät tiedot osumapisteistä, jotta voidaan laskea muidenkin mahdollisten polkujen kontribuutiot.
Backend/src:n sisällön voisi jakaa vielä vaikka itse traceriin ja sen infraan, eli jälkimmäiseen tulisi varmaan verkkoyhteydet sekä taskien jako jne ja ekaan kaikki muu. Mielipiteitä?
Renderer::midfunc:n tehtävänä on toteuttaa bi-directionaalisuus, eli yhdistää kamerasta ja valonlähteestä lähetetyt säteet.
Kun Renderer::iterator on saatu palauttamaan kaikki osumapisteet, ::midfunc:n tulee luoda valonlähde-säteen ja kamera-säteen poluista kaikki mahdolliset kombinaatiot (yksi piste valonlähde-säteestä ja toinen kamera-säteestä) ja laskea niiden kontribuutiot.
(Tää vaatii vielä ehkä vähän lisää miettimistä toteutukseltaan..)
dmcr::Renderer::iteratoriin iterations-luvun tilalle (tai rinnalle ehkä) Color-tyyppinen paino, jota voidaan käyttää Venäläisen ruletin hyödyntämisessä.
Tällä hetkellä renderer.cpp:n dmcr::Renderer::iterator laskee tehtyjä heijastuksia, ja kun tämä iterations-luku on 20, palautetaan musta. Tehokkaampi keino on kuitenkin nk. Russian roulette: arvotaan satunnaisluku ja mikäli se on suurempi kuin tietty vertailuluku, lopetetaan.
Käytännössä tehokkuutta ruletista saadaan, kun pidetään nykyisen iterations-luvun sijaan tiedossa polun paino, "weight", eli kuinka suuri vaikutus kyseisen säteen tuloksella tulee pikselin väriin olemaan. Eli esim diff1 * bdrf(1,2) * diff2 * bdrf(2,3) * refl3 * diff4*bdrf(4,5) (ensiksi osuttu kappaleeseen 1, siitä diffuse-heijastuminen kappaleeseen 2, siitä diffuse-heijastuminen kappaleeseen 3, josta peili-heijastus kappaleeseen 4 josta diffuse-heijastuminen kappaleeseen 5. Lisäksi paino kannattaa laskea värikomponeittain (eli Color-vektorina) ja käyttää sen pituutta => jos eka kappale heijastaa vain punaista ja toka vain sinistä, ei kannata jatkaa pidemmälle.
Ratkaistuna vähintään matemaattisesti:
INPUT:
OUTPUT:
Frontend kertoo backendille resoluution, mutta backend lisää kumpaankin suuntaan yhden pikselin.
Scene
SceneObject
Renderer
Ray
oliko jotain muuta?
BRDF eli bidirectional reflectanse distribution function on funktio muotoa int BRDF(Vector3 in, Vector3 normal, Vector3 out), joka siis määrittää kappaleen pinnan diffuse-heijastuksen muotoa. BRDF:ää käytetään painottamaan eri suuntien vaikutukset DIFFUSE-heijastuksessa, ja se ottaa sisäänsä valon tulo- ja lähtövektorit sekä pinnan normaalin. Helpoin ja yksinkertaisin BRDF on Lambertian:
http://en.wikipedia.org/wiki/Lambertian
BRDF voisi olla vaikka tulevan Texture/Material -luokan ominaisuus, siten, että niitä voi jatkossa määrittää useampia. Eli dmcr::Renderer::iterator voisi käyttää sitä malliin diff_weight = obj->getTexture()->BRDF(in, rr.normal, out).
Nyt siis tuo BRDF voisi olla määritelty suoraan sinne Texture/Materialiin, mut tulevaisuudess joku funktiopointteri tai muuta hienoo siten, että sen voi SDL:llä valita (scene description language).
http://en.wikipedia.org/wiki/Bidirectional_reflectance_distribution_function
Frontend kysyy käyttäjältä mitä haluaa tehdä, vaihtoehtoina ainakin:
Käytännössä varmana helpointa tehä server.py :n Listen()-looppiin ainakin tällä hetkellä.
Lisäks tää ominaisuus vois olla niin, että se tulee käyttöön jos frontendille antaa komentoriviparametrina vaikka -ui, muuten mennään vanhan kaavan mukaan.
A declarative, efficient, and flexible JavaScript library for building user interfaces.
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google ❤️ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.