Rendering a Sphere Using Ray Tracing! // Ray Tracing Series

  Рет қаралды 77,941

The Cherno

The Cherno

Күн бұрын

Пікірлер: 121
@TheCherno
@TheCherno 2 жыл бұрын
Hope you all enjoyed the video! Don't forget we have a Discord channel for this series (#raytracing-series), and a discussion thread there for each episode - go ahead and post your spheres there! discord.com/channels/349857236656324608/990217821021679636/990217929972924416 If you need to brush up on your math, visit brilliant.org/TheCherno to get started learning STEM for free, and the first 200 people will get 20% off their annual premium subscription.
@oamioxmocliox8082
@oamioxmocliox8082 2 жыл бұрын
;)
@lazyemperor5182
@lazyemperor5182 2 жыл бұрын
Great series Cherno, always wanted to do my own rendering Please make a series where u completely code a renderer basically render the current hazel Would love that
@gantz7386
@gantz7386 2 жыл бұрын
Hope you are doing fine. Currently doing your C++ tutorial Series. You are the champ man!
@zch7491
@zch7491 2 жыл бұрын
I definitely earned more money at work by watching and learning that series. It's really good
@user-dh8oi2mk4f
@user-dh8oi2mk4f 2 жыл бұрын
@@zch7491 You do ray tracing at work?
@emmanaikins
@emmanaikins 2 жыл бұрын
I never thought i would understrand this in-depth👏👏👏
@zxuiji
@zxuiji 2 жыл бұрын
17:44, would've used local copies of the width height, pre-converted to floats, 2 less conversions the cpu has to make every call, then also a pre-converted y value in it's loop so when entering the x loop the x value is the only one that need to be converted frequently
@SirRebonack
@SirRebonack 2 жыл бұрын
Not only that. You can predivide 1 by width and height to save on having to do division each loop iteration. Just the fact that all variables are local to the function will encourage the compiler to put them in registers which can increase performance. I know the often repeated "premature optimization... blah blah" quote. But in my opinion there's gotta be some middle ground. Sure, micro-optimizations that mess up the readability of the code is one thing but small things like these shouldn't be frowned upon.
@Legendarior
@Legendarior 2 жыл бұрын
On a release build, invariants are optimised out of the loop by compilers, and expressions that can be executed at compile time will most likely be executed. Ofc one need to confirm this by checking the output assembly.
@zxuiji
@zxuiji 2 жыл бұрын
@@Legendarior As long as you already as them converted in local variables you won't need to check the asm since you've made sure there will be some time savings with the local variables alone, the only way to guarantee more at that point would be to craft the asm yourself which is not worth it for modern computers, maybe for PS1 etc but that's it.
@Legendarior
@Legendarior 2 жыл бұрын
@@zxuiji yeah I agree, there is always this tradeoff between readability and handmade optimisations (because you can't really trust 100% the compiler)
@achtsekundenfurz7876
@achtsekundenfurz7876 2 жыл бұрын
Many of these optimizations will be made by the compiler, some will be aded at a later stage by Cherno, but for now the focus is on features rather than best possible performance. For newcomers, the formulas are complicated enough as they are now. BTW, you save FAR more time computing one sphere/plane intersection per line; that allows you to eliminate spheres from X pixels as a time rather than one, and even if you can't eliminate a sphere, you can reduce the math from the 3d case to a simpler 2d case. That can save far more time than the optimizations a good compiler can do. You might spend 2% of the time eliminating ~75% of the spheres in a typical scene and saving 40% of the calculations for those which remain, which would save 83% of CPU time.
@yabot5496
@yabot5496 2 жыл бұрын
You can press CTRL twice to enable / disable inline hints (those parameter things)
@CoolBurnz
@CoolBurnz 2 жыл бұрын
I love you
@williamchurch8401
@williamchurch8401 10 ай бұрын
I love that you are walking us through it step by step! I feel a blind man gifted sight. ❤
@aaronh248
@aaronh248 2 жыл бұрын
Awesome series so far. From the comments I can see programmers seem to think their idea is the better idea lol. Are you planning on tackling BVHs during this series? Since RT became popular due to the new consoles/PC GPUs being able to handle RT and begin implementation it would be cool to see what BVHs are, how they work, etc seeing as how, for now, everything gaming related is using BVHs.
@bratprica6383
@bratprica6383 2 жыл бұрын
As a beginner programmer the comments are actually giving me confidence. When someone like him will still be given advice on how to improve his code, it makes me feel better about my code lol
@achtsekundenfurz7876
@achtsekundenfurz7876 2 жыл бұрын
Many of "their ideas" are in fact better, but Cherno tries to go for early results and will probably introduce those changes later, insead of throwing everything at the viewers at the same time. Checking if the intersections are in front (t1 and t2 positive) is something you have to do if objects can be behind the camera. If you forget it, you get weird results each time some happen to be inside the "reversed" view cone. Really weird, like spheres moving "backwards" when animated, an where the lighting looks inverted. (Yes, I forgot that check, too.) Normalizing the light direction to length one is something you should definitely consider if there are spheres. If there are only planes and polygons, it's less useful, but it's a cheap operation, so little harm done if you always do it.
@steveafanador6441
@steveafanador6441 2 жыл бұрын
I've never heard you say it but I think your a genius 😮😮
@bishboria
@bishboria 2 жыл бұрын
Really enjoying this series. Looking forward to the next video!
@CROXoDyLE
@CROXoDyLE 2 жыл бұрын
Wow this was very cool. Also didn’t know about shadertoy. I’m going to have to try that out
2 жыл бұрын
i just spent my last week to study for my computer graphics final exam. i got an A, but what's better is i kinda understand now what you are talking about :D
@SBH618
@SBH618 2 жыл бұрын
Loving this style, keep it up!
@bogdanflorescu8338
@bogdanflorescu8338 2 жыл бұрын
Shouldn't we check for t1 and t2 if they are positive? If t is negative it means the ray is not hitting the sphere. It means that the ray would have hit the sphere if it was pointing in the opposite direction (ray = origin + t * direction). Wouldn't this mean that the sphere will be rendered if it is in the back of the camera as well? Also, that z from the ray direction vector shouldn't be calculated in order to get the FOV that we want instead of setting it to -1? I tried to go alone through the mats of the previous video and I got this formula: z = -1 / tan(fov / 2).
@alfredholmes9899
@alfredholmes9899 2 жыл бұрын
It would be quite cool to replace the straight line math with null geodesics in some non euclidean spaces (might be a bit slow), could do gravitational lensing simulations etc
@paulosantana9607
@paulosantana9607 Жыл бұрын
holly fuck, thank you for that
@stevenfrench3644
@stevenfrench3644 2 жыл бұрын
You should make an ep on triangle intersection and rendering and maybe even bring in lighting using multiple lights? OP series though +1
@achtsekundenfurz7876
@achtsekundenfurz7876 2 жыл бұрын
That's one of the next few lessons. For now, he tried to keep it as simple as possible and merely generate a hit/miss map of a sphere. The next lesson will probably be a single light source, then reflection and refraction, then infinite planes and possibly triangles. Light sources will almost surely be the next topic, since they will make the sphere look like an actual sphere rather than a circle.
@Basel-ll8fj
@Basel-ll8fj 2 жыл бұрын
amazing work 3>
@nikudyshko
@nikudyshko 2 жыл бұрын
It's a good idea to normalize RayDirection. This way the term 'a' (which is glm::dot(RayDirection, RayDirection) will always be == 1.0
@TheCherno
@TheCherno 2 жыл бұрын
True, however a dot product is much faster than normalizing, so the code I wrote will actually be (significantly) faster.
@nikudyshko
@nikudyshko 2 жыл бұрын
Yeah, just checked on current version of series' repo. With normalization render takes ~2ms longer (10ms vs 8ms without norm)
@francis_the_cat9549
@francis_the_cat9549 2 жыл бұрын
I have never felt as smart as when I was able to render a warped circle on to my screen a few seconds earlier than the cherno
@CSharp1991
@CSharp1991 2 жыл бұрын
I love your videos man, thanks
@stephenelliott7071
@stephenelliott7071 2 жыл бұрын
Very cool series.
@mobslicer1529
@mobslicer1529 2 жыл бұрын
you can press control twice to toggle the parameters
@anonymoussloth6687
@anonymoussloth6687 2 жыл бұрын
Will u do this using a compute shader later on?
@spectrm6014
@spectrm6014 2 жыл бұрын
Aye, early! :D Good and concise explanation, Cherno!
@zxuiji
@zxuiji 2 жыл бұрын
6:41, rather than a jump statement I would use function pointers and initiatlise Resize something like m_createCB and then have m_createCB change the pointer to m_resizeCB after it first succeeds, likewise m_resizeCB could change it back if it removes the allocation/s etc
@rastaarmando7058
@rastaarmando7058 2 жыл бұрын
That's what we call premature optimization.
@homelikebrick42
@homelikebrick42 2 жыл бұрын
A function pointer is alot more expensive than a single if statement
@zxuiji
@zxuiji 2 жыл бұрын
@@homelikebrick42 Not when to get to that if statement you have to use a function pointer anyways, rather you have to lookup the symbol, load the address, load the bytes, whereas a direct function pointer skips symbol lookup since it already has the address and it skips the if statement as the pointer only changes during initialisation
@ciekce
@ciekce Жыл бұрын
@@zxuiji "symbol lookup" happens during linking, as previously mentioned this is just premature optimization
@zxuiji
@zxuiji Жыл бұрын
@@ciekce No, not with function pointers as the linker can only record the addresses where it's told, function pointers start as NULL typically because they're set during runtime, not link time, if you think I'm on about the functions themselves then you need to change concept, here's an example of what I mean in C: typedef struct memory mem_t; typedef void* (*resize_cb)( mem_t *mem, size_t size ); struct memory { size_t cap; void* ptr; resize_cb resizeCB; }; extern mem_t const mem_t_defaults; ... void* create_memory( mem_t *mem, size_t cap ) { (void)ptr; ... mem->resizeCB = resize_memory; return mem->ptr; } void *resize_memory( mem_t *mem, size_t cap ) { ... mem->resizeCB = create_memory; return NULL; } mem_t const mem_t_defaults = { 0, NULL, create_memory };
@allesbanane2329
@allesbanane2329 2 жыл бұрын
Hey the cherno, great tutorial series 👍. I was wondering though / i cant remember if you said so in your introduction video, if you will just do the basic stuff like simple shadows and reflections (the stuff that everybody does and stops after that) or if you will include more complicated stuff like 3D models, global illumination and so on...
2 жыл бұрын
32:00 these "a"s and "b"s are a bit confusing
@goshisanniichi
@goshisanniichi 2 жыл бұрын
It would be cool to fully model the camera lens instead of just this basic approach. But, that's something for the [far] future.
@astitva5002
@astitva5002 2 жыл бұрын
cherno is referring a bit from Raytracing in a weekend series and in it they do explore depth of field and focal distances so yes im excited to see it as well
@shriram5494
@shriram5494 2 жыл бұрын
17:45 I was wondering if the GetWidth() method call will have any overhead because it is called many times per pixel. would it be better if we store it as a local variable?
@astitva5002
@astitva5002 2 жыл бұрын
i think GetWidth() is getting called at each iteration for dynamic resizing of the render
@foomoo1088
@foomoo1088 2 жыл бұрын
Might be easier to just start with vectors and arrive at results in the quadratic coefficients that come from dot products
@xenopheliac7202
@xenopheliac7202 Жыл бұрын
The problem is not the Ray origin, but you subbed in 4.0f as radius in the quadradic, instead of r (0.5).
@steveafanador6441
@steveafanador6441 2 жыл бұрын
I'm way way to stupid to comprehend this stuff. It's unreal how you do this stuff
@peezieforestem5078
@peezieforestem5078 2 жыл бұрын
not true. It might take more time for you, but there's nothing incomprehensible about it that an average human cannot do. Just go very slowly over what The Cherno says, pausing if necessary, looking up unfamiliar terms, slowly familiarizing yourself with concepts if necessary. It might take a lot of time, but you will understand it if you put the honest hours in.
@shriram5494
@shriram5494 2 жыл бұрын
Each ray is perpendicular to a pixel right? do we not account for rays which land on the pixel obliquely?
@vertexforger
@vertexforger 2 жыл бұрын
What theme do you use for Visual Studio?
@oni5571
@oni5571 2 жыл бұрын
Nice tutorial, however I am really new to Github , and in my project I can't use the Image->Resize() because the Walnut app in my template isn't up to date because I set it up a few weeks ago. I was wondering how I would go about getting the Walnut app up to date, I have done some searching but am struggling to find an answer. If anyone could help with this I would really appreciate it, forgive me if the way I worded the question is weird.
@卖女孩的小火柴-g9g
@卖女孩的小火柴-g9g 2 жыл бұрын
just chang to the Walnut directory git checkout master git pull
@aliang8373
@aliang8373 2 жыл бұрын
i have the same issue too. It seems the Walnut submodule is in "detached head" status. So i went to the RayTracing/Walnut folder and use "git checkout master" command. And it works for me
@robrucki6695
@robrucki6695 2 жыл бұрын
Would love to see raytracing on the GPU. There aren't many tutorials out there on that
@jlmonolith
@jlmonolith 2 жыл бұрын
When implementing this, I realized that the new Image::Resize function removes the need for the Image object to be dynamically allocated. Changing the Image object (m_FinalImage) into a regular member object helps to simplify the code by removing multiple nullptr checks. GetFinalImage can simply return a const reference to the member. Also, implementing m_ImageData as a std::vector can additionally simplify the OnResize function without adding any overhead.
@b4ttlemast0r
@b4ttlemast0r 2 жыл бұрын
is there a particular reason behind the m_ prefix you're using, does it stand for anything?
@MirrorsEdgeGamer01
@MirrorsEdgeGamer01 2 жыл бұрын
*m_* stands for member.
@FullGardenStudent
@FullGardenStudent 2 жыл бұрын
this felt to me like he was programming in ue5 for a moment lol
@Yadobler
@Yadobler 2 жыл бұрын
Normalising the Ray Direction will allow you to skip calculating "a" because the dot-product of a line to itself is, well, 1.0f
@TheCherno
@TheCherno 2 жыл бұрын
Normalizing is (significantly) slower than a dot product.
@Yadobler
@Yadobler 2 жыл бұрын
@@TheCherno ooo I didn't know that, thanks!
@zxuiji
@zxuiji 2 жыл бұрын
10:53, I would just have swappable pointers, something like: Image::SwapImages() { m_swapping = true; LockMutex( &(m_mutex) ); ImageCfg *tmp = m_showImage; m_showImage = m_editImage; m_edit_Image = tmp; m_swapping = false; FreeMutex( &m_mutex ); } That way can keep the memory that already have if it's big enough.
@fuhoo5836
@fuhoo5836 2 жыл бұрын
wonder if that is an apartment or an office?
@EyeNeo
@EyeNeo 2 жыл бұрын
How to enable this new feature which shows variable types in small box ?
@ricardosaraviaarmaulia3009
@ricardosaraviaarmaulia3009 10 ай бұрын
Hi, someone know why in my pc the render time is so bad? I have an RTX 4090 and intel i9 i think i should get a nice render time(i get doing the first part of the video 200 ms ). Thank you.
@davidcfrogley
@davidcfrogley 2 жыл бұрын
Can't upload screenshots here, unfortunately, but here's my stab at the "homework": float discriminant = b * b - 4.0f * a * c; if (discriminant < 0.0f) { return 0xff000000; } float time1 = (-b - sqrtf(discriminant)) / (2.0f * a); float time2 = (-b + sqrtf(discriminant)) / (2.0f * a); float t = std::min(time1, time2); // Get the closer time, so the ray hitting the "front" of the sphere glm::vec3 hitPoint(rayOrigin + rayDirection * t); // origin + direction * time glm::vec3 normal(hitPoint - glm::vec3(0.0f, 0.0f, 0.0f)); // Will be more interesting once the sphere moves... normal = glm::normalize(normal); auto scalar = glm::dot(rayDirection, normal) * -1.0f; // Simple shading based on the dot product of the normal and the direction: gets brighter closer to parallel if (scalar < 0.0f) { scalar = 0.0f; } if (scalar > 1.0f) { scalar = 1.0f; } auto brightness = static_cast(scalar * 255.0f); return 0xff000000 | (brightness
@m96fa40
@m96fa40 8 ай бұрын
I'm gonna save somebody's time here: Guys NEVER EVER write *`coord *= 2.0f - 1.0f;`* just trust me and don't, it will make the circle look stretched, if you did the same problem as I did and struggled to fix, just change it to *`coord = coord * 2.0f - 1.0f;`*
@pushqrdx
@pushqrdx 2 жыл бұрын
Goodness, What colorscheme is this?
@banzeirao
@banzeirao 2 жыл бұрын
Hi from brazil, actually worth use std::string in an Engine that use for indie games our need own string types like QString etc, or is bad to production and cross platform? sorry for english
@mr.mirror1213
@mr.mirror1213 2 жыл бұрын
LESS GOOO
@xxdeadmonkxx
@xxdeadmonkxx 2 жыл бұрын
Finally we have use for a discriminant after school :)
@SXpitbull
@SXpitbull 2 жыл бұрын
Can I do this using opengl?
@mwaeb1828
@mwaeb1828 2 жыл бұрын
clicked
@Jkauppa
@Jkauppa 2 жыл бұрын
2d/3d-dda on grid/quad/oct-tree is the most useful individual ray tracing algorithm (most robust), assuming all worst cases, all rays individually accelerated in the grid, think a very dense voxel fog or tree leaves
@Jkauppa
@Jkauppa 2 жыл бұрын
you could multisample per pixel, or 4x screen size render the whole displayed image, resize resample down to the 1x image size
@Jkauppa
@Jkauppa 2 жыл бұрын
you should have a separate render buffer, whatever dynamic resolution, then fit that to the final screen pixels
@Jkauppa
@Jkauppa 2 жыл бұрын
set a value of supersampling (oversampling) resolution, like 1.25, 2, or 4, assume its same for x and y, compared to the window or screen image size
@Jkauppa
@Jkauppa 2 жыл бұрын
0.5 render scaling would mean undersampling then fitting to screen
@Jkauppa
@Jkauppa 2 жыл бұрын
ie, render 1080p then fit to 4K
@Mr.Dirkelz
@Mr.Dirkelz 2 жыл бұрын
Will you ever use the rust programming language, it fixes a lot of C/C++ mistakes, and I would like a rust series with , because I am struggling translating c libraries like raylib to the raylib-bindings for rust, because of the borrowing system, otherwise I will just be switching to C, but I do not like it as much as rust and I have to relearn it because of the borrowing system, otherwise I will just be switching to C, but I do not like it as much as rust and I have to relearn it
@banlukas_
@banlukas_ 2 жыл бұрын
What mistakes
@张向乐
@张向乐 2 жыл бұрын
cool
@oamioxmocliox8082
@oamioxmocliox8082 2 жыл бұрын
;)
@jaysleezy2234
@jaysleezy2234 2 жыл бұрын
please make a game engine code in java.
@TheYosi277
@TheYosi277 2 жыл бұрын
we must have an RTX card for this series? :(
@oamioxmocliox8082
@oamioxmocliox8082 2 жыл бұрын
;)
@tejasmaloor2507
@tejasmaloor2507 2 жыл бұрын
No, rtx cards is to use nvidia's ray tracing application but here we are creating our own application so we don't need it and it can be done on any card.( Please correct me if I am wrong)
@roxxel8167
@roxxel8167 2 жыл бұрын
@@tejasmaloor2507 You're right, Ray Tracing isn't something invented by nVidia, nVidia just made that their videocards do calculation really fast
@DaminGamerMC
@DaminGamerMC 2 жыл бұрын
not really this can even be done in CPU, obviously speed will be affected by what device you are using
@TheYosi277
@TheYosi277 2 жыл бұрын
@@roxxel8167 i understand, its really interesting to know why big company doesn't do those things in there engine's if this youTuber show it so easily, i only heard about crytech that implemented ray tracing in there engie and lumen in unreal engie but its no really a ray tracing, its just a fake and smart ray calculations that are really great 😅
@Illuxel
@Illuxel 2 жыл бұрын
You can turn off this thing by double clicking CTRL
I made a better Ray-Tracing engine
17:38
NamePointer
Рет қаралды 257 М.
Cheerleader Transformation That Left Everyone Speechless! #shorts
00:27
Fabiosa Best Lifehacks
Рет қаралды 16 МЛН
Rays and Spheres: The MATH! // Ray Tracing series
37:55
The Cherno
Рет қаралды 99 М.
Materials and Physically Based Rendering // Ray Tracing series
27:18
How Ray Tracing (Modern CGI) Works And How To Do It 600x Faster
32:06
Josh's Channel
Рет қаралды 584 М.
FASTER Ray Tracing with Multithreading // Ray Tracing series
22:23
2 Years Of Learning C | Prime Reacts
22:24
ThePrimeTime
Рет қаралды 321 М.
Coding Adventure: Ray Tracing
37:58
Sebastian Lague
Рет қаралды 1,2 МЛН
2024's Biggest Breakthroughs in Math
15:13
Quanta Magazine
Рет қаралды 520 М.
FAST Random in 3 LINES OF CODE // Ray Tracing series
18:53
The Cherno
Рет қаралды 45 М.
LIGHTING AND SHADING // Ray Tracing series
32:38
The Cherno
Рет қаралды 47 М.
Vulkan is HARD
8:26
lolzdev
Рет қаралды 69 М.
Cheerleader Transformation That Left Everyone Speechless! #shorts
00:27
Fabiosa Best Lifehacks
Рет қаралды 16 МЛН