mirror of
https://github.com/ssloy/tinyraytracer.git
synced 2025-08-31 17:51:46 +02:00
Updated Home (markdown)
16
Home.md
16
Home.md
@@ -55,13 +55,13 @@ So, the goal of this step is to make sure that we can a) create an image in memo
|
||||
|
||||
<img src="https://raw.githubusercontent.com/ssloy/tinyraytracer/bd36c9857305b3cbd06f5b768bb48a92df9ae68b/out.jpg"/>
|
||||
|
||||
<h1>Этап второй, самый сложный: непосредственно трассировка лучей</h1>
|
||||
Это самый важный и сложный этап из всей цепочки. Я хочу определить в моём коде одну сферу и показать её на экране, не заморачиваясь ни материалами, ни освещением. Вот так должен выглядеть наш результат:
|
||||
<h1>Step 2, the crucial one: ray tracing</h1>
|
||||
This is the most important and difficult step of the whole chain. I want to define one sphere in my code and show it on the screen without being obsessed with materials or lighting. This is how our result should look like:
|
||||
<img src="https://raw.githubusercontent.com/ssloy/tinyraytracer/5806eb45e93dab225ab335824cbc3f537d511b28/out.jpg"/>
|
||||
|
||||
Для удобства в моём репозитории по одному коммиту на каждый этап; Github позволяет очень удобно просматривать внесённые изменения. <a href="https://github.com/ssloy/tinyraytracer/commit/5806eb45e93dab225ab335824cbc3f537d511b28">Вот, например</a>, что изменилось во втором коммите по сравнению с первым.
|
||||
For the sake of convenience, I have one commit per step in my repository; Github makes it very easy to view the changes made. <a href="https://github.com/ssloy/tinyraytracer/commit/5806eb45e93dab225ab335824cbc3f537d511b28">Here, for instance</a>, what was changed by the second commit.
|
||||
|
||||
Для начала: что нам нужно, чтобы в памяти компьютера представить сферу? Нам достаточно четырёх чисел: трёхмерный вектор с центром сферы и скаляр, описывающий радиус:
|
||||
To begin with, what do we need to represent the sphere in the computer's memory? Four numbers are enough: a three-dimensional vector for the center of the sphere and a scalar describing the radius:
|
||||
```c++
|
||||
struct Sphere {
|
||||
Vec3f center;
|
||||
@@ -84,9 +84,9 @@ struct Sphere {
|
||||
};
|
||||
```
|
||||
|
||||
Единственная нетривиальная вещь в этом коде - это функция, которая позволяет проверить, пересекается ли заданный луч (исходящий из orig в направлении dir) с нашей сферой. Детальное описание алгоритма проверки пересечения луча и сферы можно <a href="http://www.lighthouse3d.com/tutorials/maths/ray-sphere-intersection/">прочитать тут</a>, очень рекомендую это сделать и проверить мой код.
|
||||
The only non-trivial thing in this code is a function that allows you to check if a given ray (originating from orig in the direction of dir) intersects with our sphere. A detailed description of the algorithm for the ray-sphere intersection <a href="http://www.lighthouse3d.com/tutorials/maths/ray-sphere-intersection/">can be found here</a>, I highly recommend you to do this and check my code.
|
||||
|
||||
Как работает трассировка лучей? Очень просто. На первом этапе мы просто замели картинку градиентом:
|
||||
How does the ray tracing work? It is pretty simple. At the first step we just filled the picture with a gradient of colors:
|
||||
```c++
|
||||
for (size_t j = 0; j<height; j++) {
|
||||
for (size_t i = 0; i<width; i++) {
|
||||
@@ -95,10 +95,10 @@ struct Sphere {
|
||||
}
|
||||
```
|
||||
|
||||
Теперь же мы для каждого пикселя сформируем луч, идущий из центра координат, и проходящий через наш пиксель, и проверим, не пересекает ли этот луч нашу сферу.
|
||||
Now for each pixel we will form a ray coming from the origin and passing through our pixel, and then check if this ray intersects with the sphere:
|
||||
<img src="https://upload.wikimedia.org/wikipedia/commons/8/83/Ray_trace_diagram.svg"/>
|
||||
|
||||
Если пересечения со сферой нет, то мы поставим цвет1, иначе цвет2:
|
||||
If there is no intersection with sphere we draw the pixel with color1, otherwise with color2:
|
||||
```c++
|
||||
Vec3f cast_ray(const Vec3f &orig, const Vec3f &dir, const Sphere &sphere) {
|
||||
float sphere_dist = std::numeric_limits<float>::max();
|
||||
|
Reference in New Issue
Block a user