Browse Source

Add altitude as sky pass parameter

master
C. J. Howard 4 years ago
parent
commit
6e273279d9
7 changed files with 71 additions and 26 deletions
  1. +3
    -1
      src/game/biome.hpp
  2. +1
    -1
      src/game/states/play-state.cpp
  3. +13
    -7
      src/game/systems/weather-system.cpp
  4. +8
    -2
      src/game/systems/weather-system.hpp
  5. +30
    -9
      src/renderer/passes/sky-pass.cpp
  6. +13
    -3
      src/renderer/passes/sky-pass.hpp
  7. +3
    -3
      src/resources/biome-loader.cpp

+ 3
- 1
src/game/biome.hpp View File

@ -28,7 +28,9 @@ class image;
struct biome struct biome
{ {
std::string name; std::string name;
float2 coordinates; // Latitude and longitude, in radians
/// Latitude (radians), longitude (radians), altitude (meters)
float3 location;
// Terrain // Terrain
material* terrain_material; material* terrain_material;

+ 1
- 1
src/game/states/play-state.cpp View File

@ -91,7 +91,7 @@ void play_state_enter(game_context* ctx)
sky_pass->set_sky_model(ctx->resource_manager->load<model>("sky-dome.mdl")); sky_pass->set_sky_model(ctx->resource_manager->load<model>("sky-dome.mdl"));
sky_pass->set_moon_model(ctx->resource_manager->load<model>("moon.mdl")); sky_pass->set_moon_model(ctx->resource_manager->load<model>("moon.mdl"));
ctx->weather_system->set_coordinates(ctx->biome->coordinates);
ctx->weather_system->set_location(ctx->biome->location[0], ctx->biome->location[1], ctx->biome->location[2]);
ctx->weather_system->set_time(2020, 6, 1, 5, 0, 0, -7.0); ctx->weather_system->set_time(2020, 6, 1, 5, 0, 0, -7.0);
ctx->weather_system->set_sky_palette(ctx->biome->sky_palette); ctx->weather_system->set_sky_palette(ctx->biome->sky_palette);
ctx->weather_system->set_sun_palette(ctx->biome->sun_palette); ctx->weather_system->set_sun_palette(ctx->biome->sun_palette);

+ 13
- 7
src/game/systems/weather-system.cpp View File

@ -178,7 +178,7 @@ weather_system::weather_system(entt::registry& registry):
sky_palette(nullptr), sky_palette(nullptr),
shadow_palette(nullptr), shadow_palette(nullptr),
sun_direction{0.0f, -1.0f, 0.0f}, sun_direction{0.0f, -1.0f, 0.0f},
coordinates{0.0f, 0.0f},
location{0.0f, 0.0f, 0.0f},
jd(0.0) jd(0.0)
{} {}
@ -186,8 +186,8 @@ void weather_system::update(double t, double dt)
{ {
jd += (dt * time_scale) / seconds_per_day; jd += (dt * time_scale) / seconds_per_day;
const float latitude = coordinates[0];
const float longitude = coordinates[1];
const float latitude = location[0];
const float longitude = location[1];
// Time correction // Time correction
double tc = longitude / (math::two_pi<double> / 24.0); double tc = longitude / (math::two_pi<double> / 24.0);
@ -323,7 +323,7 @@ void weather_system::update(double t, double dt)
sky_pass->set_sky_gradient(sky_gradient); sky_pass->set_sky_gradient(sky_gradient);
sky_pass->set_time_of_day(static_cast<float>(hour * 60.0 * 60.0)); sky_pass->set_time_of_day(static_cast<float>(hour * 60.0 * 60.0));
sky_pass->set_observer_coordinates(coordinates);
sky_pass->set_observer_location(location[0], location[1], location[2]);
sky_pass->set_sun_coordinates(sun_position, sun_az_el); sky_pass->set_sun_coordinates(sun_position, sun_az_el);
sky_pass->set_moon_coordinates(moon_position, moon_az_el); sky_pass->set_moon_coordinates(moon_position, moon_az_el);
sky_pass->set_julian_day(static_cast<float>(jd)); sky_pass->set_julian_day(static_cast<float>(jd));
@ -349,14 +349,14 @@ void weather_system::update(double t, double dt)
} }
} }
void weather_system::set_coordinates(const float2& coordinates)
void weather_system::set_location(float latitude, float longitude, float altitude)
{ {
this->coordinates = coordinates;
location = {latitude, longitude, altitude};
} }
void weather_system::set_ambient_light(::ambient_light* light) void weather_system::set_ambient_light(::ambient_light* light)
{ {
this->ambient_light = light;
ambient_light = light;
} }
void weather_system::set_sun_light(directional_light* light) void weather_system::set_sun_light(directional_light* light)
@ -372,6 +372,12 @@ void weather_system::set_moon_light(directional_light* light)
void weather_system::set_sky_pass(::sky_pass* pass) void weather_system::set_sky_pass(::sky_pass* pass)
{ {
sky_pass = pass; sky_pass = pass;
if (sky_pass)
{
sky_pass->set_moon_angular_radius(math::radians(1.0f));
sky_pass->set_sun_angular_radius(math::radians(1.1f));
}
} }
void weather_system::set_shadow_map_pass(::shadow_map_pass* pass) void weather_system::set_shadow_map_pass(::shadow_map_pass* pass)

+ 8
- 2
src/game/systems/weather-system.hpp View File

@ -37,7 +37,13 @@ public:
weather_system(entt::registry& registry); weather_system(entt::registry& registry);
virtual void update(double t, double dt); virtual void update(double t, double dt);
void set_coordinates(const float2& coordinates);
/**
*
* @param latitude Latitude, in radians.
* @param longitude Longitude, in radians.
* @param altitude Altitude, in radians.
*/
void set_location(float latitude, float longitude, float altitude);
void set_ambient_light(ambient_light* light); void set_ambient_light(ambient_light* light);
void set_sun_light(directional_light* light); void set_sun_light(directional_light* light);
@ -61,7 +67,7 @@ private:
static T interpolate_gradient(const std::vector<T>& gradient, float position); static T interpolate_gradient(const std::vector<T>& gradient, float position);
double jd; double jd;
float2 coordinates;
float3 location;
float time_scale; float time_scale;
float3 sun_direction; float3 sun_direction;
ambient_light* ambient_light; ambient_light* ambient_light;

+ 30
- 9
src/renderer/passes/sky-pass.cpp View File

@ -46,12 +46,14 @@ sky_pass::sky_pass(::rasterizer* rasterizer, const ::framebuffer* framebuffer, r
render_pass(rasterizer, framebuffer), render_pass(rasterizer, framebuffer),
mouse_position({0.0f, 0.0f}), mouse_position({0.0f, 0.0f}),
sky_model(nullptr), sky_model(nullptr),
sky_material(nullptr),
sky_model_vao(nullptr), sky_model_vao(nullptr),
moon_model(nullptr), moon_model(nullptr),
moon_material(nullptr),
moon_model_vao(nullptr), moon_model_vao(nullptr),
moon_shader_program(nullptr), moon_shader_program(nullptr),
blue_noise_map(nullptr), blue_noise_map(nullptr),
observer_coordinates{0.0f, 0.0f}
observer_location{0.0f, 0.0f, 0.0f}
{ {
shader_program = resource_manager->load<::shader_program>("sky.glsl"); shader_program = resource_manager->load<::shader_program>("sky.glsl");
model_view_projection_input = shader_program->get_input("model_view_projection"); model_view_projection_input = shader_program->get_input("model_view_projection");
@ -61,12 +63,14 @@ sky_pass::sky_pass(::rasterizer* rasterizer, const ::framebuffer* framebuffer, r
time_input = shader_program->get_input("time"); time_input = shader_program->get_input("time");
time_of_day_input = shader_program->get_input("time_of_day"); time_of_day_input = shader_program->get_input("time_of_day");
blue_noise_map_input = shader_program->get_input("blue_noise_map"); blue_noise_map_input = shader_program->get_input("blue_noise_map");
observer_coordinates_input = shader_program->get_input("observer_coordinates");
observer_location_input = shader_program->get_input("observer_location");
sun_position_input = shader_program->get_input("sun_position"); sun_position_input = shader_program->get_input("sun_position");
sun_az_el_input = shader_program->get_input("sun_az_el"); sun_az_el_input = shader_program->get_input("sun_az_el");
moon_position_input = shader_program->get_input("moon_position"); moon_position_input = shader_program->get_input("moon_position");
moon_az_el_input = shader_program->get_input("moon_az_el"); moon_az_el_input = shader_program->get_input("moon_az_el");
julian_day_input = shader_program->get_input("julian_day"); julian_day_input = shader_program->get_input("julian_day");
cos_moon_angular_radius_input = shader_program->get_input("cos_moon_angular_radius");
cos_sun_angular_radius_input = shader_program->get_input("cos_sun_angular_radius");
sky_gradient[0] = {1.0, 0.0f, 0.0f, 0.0f}; sky_gradient[0] = {1.0, 0.0f, 0.0f, 0.0f};
sky_gradient[1] = {0.0, 1.0f, 0.0f, 0.333f}; sky_gradient[1] = {0.0, 1.0f, 0.0f, 0.333f};
@ -106,7 +110,6 @@ void sky_pass::render(render_context* context) const
float4x4 projection = camera.get_projection_tween().interpolate(context->alpha); float4x4 projection = camera.get_projection_tween().interpolate(context->alpha);
float4x4 model_view_projection = projection * model_view; float4x4 model_view_projection = projection * model_view;
float time_of_day = time_of_day_tween.interpolate(context->alpha); float time_of_day = time_of_day_tween.interpolate(context->alpha);
float julian_day = julian_day_tween.interpolate(context->alpha); float julian_day = julian_day_tween.interpolate(context->alpha);
float3 sun_position = sun_position_tween.interpolate(context->alpha); float3 sun_position = sun_position_tween.interpolate(context->alpha);
@ -133,9 +136,8 @@ void sky_pass::render(render_context* context) const
time_of_day_input->upload(time_of_day); time_of_day_input->upload(time_of_day);
if (blue_noise_map_input) if (blue_noise_map_input)
blue_noise_map_input->upload(blue_noise_map); blue_noise_map_input->upload(blue_noise_map);
if (observer_coordinates_input)
observer_coordinates_input->upload(observer_coordinates);
if (observer_location_input)
observer_location_input->upload(observer_location);
if (sun_position_input) if (sun_position_input)
sun_position_input->upload(sun_position); sun_position_input->upload(sun_position);
if (sun_az_el_input) if (sun_az_el_input)
@ -146,16 +148,22 @@ void sky_pass::render(render_context* context) const
moon_az_el_input->upload(moon_az_el); moon_az_el_input->upload(moon_az_el);
if (julian_day_input) if (julian_day_input)
julian_day_input->upload(julian_day); julian_day_input->upload(julian_day);
if (cos_moon_angular_radius_input)
cos_moon_angular_radius_input->upload(cos_moon_angular_radius);
if (cos_sun_angular_radius_input)
cos_sun_angular_radius_input->upload(cos_sun_angular_radius);
sky_material->upload(context->alpha);
rasterizer->draw_arrays(*sky_model_vao, sky_model_drawing_mode, sky_model_start_index, sky_model_index_count); rasterizer->draw_arrays(*sky_model_vao, sky_model_drawing_mode, sky_model_start_index, sky_model_index_count);
} }
// Draw moon model // Draw moon model
if (moon_az_el[1] >= -moon_angular_radius)
{ {
glEnable(GL_BLEND); glEnable(GL_BLEND);
glBlendFunc(GL_SRC_ALPHA, GL_ONE); glBlendFunc(GL_SRC_ALPHA, GL_ONE);
float moon_angular_radius = math::radians(1.0f);
float moon_distance = (clip_near + clip_far) * 0.5f; float moon_distance = (clip_near + clip_far) * 0.5f;
float moon_radius = moon_angular_radius * moon_distance; float moon_radius = moon_angular_radius * moon_distance;
@ -189,6 +197,7 @@ void sky_pass::set_sky_model(const model* model)
const std::vector<model_group*>& groups = *model->get_groups(); const std::vector<model_group*>& groups = *model->get_groups();
for (model_group* group: groups) for (model_group* group: groups)
{ {
sky_material = group->get_material();
sky_model_drawing_mode = group->get_drawing_mode(); sky_model_drawing_mode = group->get_drawing_mode();
sky_model_start_index = group->get_start_index(); sky_model_start_index = group->get_start_index();
sky_model_index_count = group->get_index_count(); sky_model_index_count = group->get_index_count();
@ -271,9 +280,9 @@ void sky_pass::set_julian_day(float jd)
julian_day_tween[1] = jd; julian_day_tween[1] = jd;
} }
void sky_pass::set_observer_coordinates(const float2& coordinates)
void sky_pass::set_observer_location(float latitude, float longitude, float altitude)
{ {
observer_coordinates = coordinates;
observer_location = {latitude, longitude, altitude};
} }
void sky_pass::set_sun_coordinates(const float3& position, const float2& az_el) void sky_pass::set_sun_coordinates(const float3& position, const float2& az_el)
@ -288,6 +297,18 @@ void sky_pass::set_moon_coordinates(const float3& position, const float2& az_el)
moon_az_el_tween[1] = az_el; moon_az_el_tween[1] = az_el;
} }
void sky_pass::set_moon_angular_radius(float radius)
{
moon_angular_radius = radius;
cos_moon_angular_radius = std::cos(moon_angular_radius);
}
void sky_pass::set_sun_angular_radius(float radius)
{
sun_angular_radius = radius;
cos_sun_angular_radius = std::cos(sun_angular_radius);
}
void sky_pass::handle_event(const mouse_moved_event& event) void sky_pass::handle_event(const mouse_moved_event& event)
{ {
mouse_position = {static_cast<float>(event.x), static_cast<float>(event.y)}; mouse_position = {static_cast<float>(event.x), static_cast<float>(event.y)};

+ 13
- 3
src/renderer/passes/sky-pass.hpp View File

@ -57,9 +57,12 @@ public:
void set_moon_model(const model* model); void set_moon_model(const model* model);
void set_julian_day(float jd); void set_julian_day(float jd);
void set_observer_coordinates(const float2& coordinates);
void set_observer_location(float latitude, float longitude, float altitude);
void set_sun_coordinates(const float3& position, const float2& az_el); void set_sun_coordinates(const float3& position, const float2& az_el);
void set_moon_coordinates(const float3& position, const float2& az_el); void set_moon_coordinates(const float3& position, const float2& az_el);
void set_moon_angular_radius(float radius);
void set_sun_angular_radius(float radius);
private: private:
virtual void handle_event(const mouse_moved_event& event); virtual void handle_event(const mouse_moved_event& event);
@ -71,13 +74,15 @@ private:
const shader_input* resolution_input; const shader_input* resolution_input;
const shader_input* time_input; const shader_input* time_input;
const shader_input* time_of_day_input; const shader_input* time_of_day_input;
const shader_input* observer_coordinates_input;
const shader_input* observer_location_input;
const shader_input* sun_position_input; const shader_input* sun_position_input;
const shader_input* sun_az_el_input; const shader_input* sun_az_el_input;
const shader_input* moon_position_input; const shader_input* moon_position_input;
const shader_input* moon_az_el_input; const shader_input* moon_az_el_input;
const shader_input* blue_noise_map_input; const shader_input* blue_noise_map_input;
const shader_input* julian_day_input; const shader_input* julian_day_input;
const shader_input* cos_sun_angular_radius_input;
const shader_input* cos_moon_angular_radius_input;
::shader_program* moon_shader_program; ::shader_program* moon_shader_program;
const shader_input* moon_model_view_projection_input; const shader_input* moon_model_view_projection_input;
@ -86,6 +91,7 @@ private:
const shader_input* moon_sun_position_input; const shader_input* moon_sun_position_input;
const model* sky_model; const model* sky_model;
const material* sky_material;
const vertex_array* sky_model_vao; const vertex_array* sky_model_vao;
drawing_mode sky_model_drawing_mode; drawing_mode sky_model_drawing_mode;
std::size_t sky_model_start_index; std::size_t sky_model_start_index;
@ -102,7 +108,7 @@ private:
float2 mouse_position; float2 mouse_position;
std::array<float4, 4> sky_gradient; std::array<float4, 4> sky_gradient;
const tween<double>* time_tween; const tween<double>* time_tween;
float2 observer_coordinates;
float3 observer_location;
tween<float> time_of_day_tween; tween<float> time_of_day_tween;
tween<float> julian_day_tween; tween<float> julian_day_tween;
@ -110,6 +116,10 @@ private:
tween<float2> sun_az_el_tween; tween<float2> sun_az_el_tween;
tween<float3> moon_position_tween; tween<float3> moon_position_tween;
tween<float2> moon_az_el_tween; tween<float2> moon_az_el_tween;
float moon_angular_radius;
float cos_moon_angular_radius;
float sun_angular_radius;
float cos_sun_angular_radius;
}; };
#endif // ANTKEEPER_SKY_PASS_HPP #endif // ANTKEEPER_SKY_PASS_HPP

+ 3
- 3
src/resources/biome-loader.cpp View File

@ -70,10 +70,10 @@ biome* resource_loader::load(resource_manager* resource_manager, PHYSFS_F
load_value(&biome->name, json, "name"); load_value(&biome->name, json, "name");
float2 coordinates;
if (load_array(&coordinates.x, 2, json, "coordinates"))
float3 location;
if (load_array(&location.x, 3, json, "location"))
{ {
biome->coordinates = {math::radians(coordinates.x), math::radians(coordinates.y)};
biome->location = {math::radians(location.x), math::radians(location.y), location.z};
} }
if (auto terrain = json.find("terrain"); terrain != json.end()) if (auto terrain = json.find("terrain"); terrain != json.end())

Loading…
Cancel
Save