💿🐜 Antkeeper source code https://antkeeper.com
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

449 lines
18 KiB

3 years ago
  1. /*
  2. * Copyright (C) 2021 Christopher J. Howard
  3. *
  4. * This file is part of Antkeeper source code.
  5. *
  6. * Antkeeper source code is free software: you can redistribute it and/or modify
  7. * it under the terms of the GNU General Public License as published by
  8. * the Free Software Foundation, either version 3 of the License, or
  9. * (at your option) any later version.
  10. *
  11. * Antkeeper source code is distributed in the hope that it will be useful,
  12. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  13. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  14. * GNU General Public License for more details.
  15. *
  16. * You should have received a copy of the GNU General Public License
  17. * along with Antkeeper source code. If not, see <http://www.gnu.org/licenses/>.
  18. */
  19. #include "animation/ease.hpp"
  20. #include "animation/screen-transition.hpp"
  21. #include "configuration.hpp"
  22. #include "debug/logger.hpp"
  23. #include "entity/archetype.hpp"
  24. #include "entity/components/cavity.hpp"
  25. #include "entity/components/copy-transform.hpp"
  26. #include "entity/components/copy-translation.hpp"
  27. #include "entity/components/model.hpp"
  28. #include "entity/components/snap.hpp"
  29. #include "entity/components/terrain.hpp"
  30. #include "entity/components/tool.hpp"
  31. #include "entity/components/transform.hpp"
  32. #include "entity/components/camera-follow.hpp"
  33. #include "entity/components/orbit.hpp"
  34. #include "entity/components/blackbody.hpp"
  35. #include "entity/components/celestial-body.hpp"
  36. #include "entity/components/atmosphere.hpp"
  37. #include "entity/components/light.hpp"
  38. #include "entity/components/observer.hpp"
  39. #include "entity/commands.hpp"
  40. #include "game/game-context.hpp"
  41. #include "game/states/game-states.hpp"
  42. #include "math/math.hpp"
  43. #include "nest.hpp"
  44. #include "renderer/material.hpp"
  45. #include "gl/texture-2d.hpp"
  46. #include "gl/texture-filter.hpp"
  47. #include "gl/texture-wrapping.hpp"
  48. #include "renderer/model.hpp"
  49. #include "renderer/passes/sky-pass.hpp"
  50. #include "renderer/passes/shadow-map-pass.hpp"
  51. #include "resources/resource-manager.hpp"
  52. #include "scene/model-instance.hpp"
  53. #include "scene/collection.hpp"
  54. #include "scene/camera.hpp"
  55. #include "scene/ambient-light.hpp"
  56. #include "scene/directional-light.hpp"
  57. #include "entity/systems/control.hpp"
  58. #include "entity/systems/camera.hpp"
  59. #include "entity/systems/render.hpp"
  60. #include "entity/systems/tool.hpp"
  61. #include "entity/systems/orbit.hpp"
  62. #include "entity/systems/astronomy.hpp"
  63. #include "game/biome.hpp"
  64. #include "utility/fundamental-types.hpp"
  65. #include "utility/bit-math.hpp"
  66. #include "genetics/genetics.hpp"
  67. #include "math/random.hpp"
  68. #include <iostream>
  69. #include <bitset>
  70. #include <ctime>
  71. void play_state_enter(game_context* ctx)
  72. {
  73. debug::logger* logger = ctx->logger;
  74. logger->push_task("Entering play state");
  75. resource_manager* resource_manager = ctx->resource_manager;
  76. entt::registry& entity_registry = *ctx->entity_registry;
  77. // Load biome
  78. if (ctx->option_biome.has_value())
  79. {
  80. ctx->biome = resource_manager->load<biome>(ctx->option_biome.value() + ".bio");
  81. }
  82. else
  83. {
  84. ctx->biome = resource_manager->load<biome>("forest.bio");
  85. }
  86. // Apply biome parameters to scene
  87. sky_pass* sky_pass = ctx->overworld_sky_pass;
  88. sky_pass->set_enabled(true);
  89. sky_pass->set_sky_model(ctx->resource_manager->load<model>("sky-dome.mdl"));
  90. sky_pass->set_moon_model(ctx->resource_manager->load<model>("moon.mdl"));
  91. // Create sun
  92. auto sun_entity = entity_registry.create();
  93. {
  94. entity::component::celestial_body body;
  95. body.radius = 6.957e+8;
  96. body.axial_tilt = math::radians(0.0);
  97. body.axial_rotation = math::radians(0.0);
  98. body.angular_frequency = math::radians(0.0);
  99. entity::component::orbit orbit;
  100. orbit.elements.a = 0.0;
  101. orbit.elements.e = 0.0;
  102. orbit.elements.i = math::radians(0.0);
  103. orbit.elements.raan = math::radians(0.0);
  104. orbit.elements.w = math::radians(0.0);
  105. orbit.elements.ta = math::radians(0.0);
  106. entity::component::blackbody blackbody;
  107. blackbody.temperature = 5778.0;
  108. entity::component::transform transform;
  109. transform.local = math::identity_transform<float>;
  110. transform.warp = true;
  111. entity_registry.assign<entity::component::celestial_body>(sun_entity, body);
  112. entity_registry.assign<entity::component::orbit>(sun_entity, orbit);
  113. entity_registry.assign<entity::component::blackbody>(sun_entity, blackbody);
  114. entity_registry.assign<entity::component::transform>(sun_entity, transform);
  115. }
  116. // Create Earth
  117. auto earth_entity = entity_registry.create();
  118. {
  119. entity::component::celestial_body body;
  120. body.radius = 6.3781e6;
  121. body.axial_tilt = math::radians(23.4393);
  122. body.axial_rotation = math::radians(280.46061837504);
  123. body.angular_frequency = math::radians(360.9856122880876128);
  124. entity::component::orbit orbit;
  125. orbit.elements.a = 1.496e+11;
  126. orbit.elements.e = 0.01671123;
  127. orbit.elements.i = math::radians(-0.00001531);
  128. orbit.elements.raan = math::radians(0.0);
  129. const double longitude_periapsis = math::radians(102.93768193);
  130. orbit.elements.w = longitude_periapsis - orbit.elements.raan;
  131. orbit.elements.ta = math::radians(100.46457166) - longitude_periapsis;
  132. entity::component::terrain terrain;
  133. terrain.elevation = [](double, double) -> double
  134. {
  135. //return math::random<double>(0.0, 1.0);
  136. return 0.0;
  137. };
  138. terrain.max_lod = 18;
  139. terrain.patch_material = resource_manager->load<material>("desert-terrain.mtl");
  140. entity::component::atmosphere atmosphere;
  141. atmosphere.exosphere_altitude = 65e3;
  142. atmosphere.index_of_refraction = 1.000293;
  143. atmosphere.rayleigh_density = 2.545e25;
  144. atmosphere.rayleigh_scale_height = 8000.0;
  145. atmosphere.mie_density = 14.8875;
  146. atmosphere.mie_scale_height = 1200.0;
  147. atmosphere.mie_anisotropy = 0.8;
  148. entity::component::transform transform;
  149. transform.local = math::identity_transform<float>;
  150. transform.warp = true;
  151. entity_registry.assign<entity::component::celestial_body>(earth_entity, body);
  152. entity_registry.assign<entity::component::orbit>(earth_entity, orbit);
  153. entity_registry.assign<entity::component::atmosphere>(earth_entity, atmosphere);
  154. entity_registry.assign<entity::component::terrain>(earth_entity, terrain);
  155. entity_registry.assign<entity::component::transform>(earth_entity, transform);
  156. }
  157. // Create observer
  158. auto observer_eid = entity_registry.create();
  159. {
  160. entity::component::observer observer;
  161. observer.reference_body_eid = earth_entity;
  162. observer.elevation = 0.0;
  163. observer.latitude = 0.0;
  164. observer.longitude = 0.0;
  165. observer.camera = ctx->overworld_camera;
  166. entity_registry.assign<entity::component::observer>(observer_eid, observer);
  167. }
  168. scene::ambient_light* ambient = new scene::ambient_light();
  169. ambient->set_color({1, 1, 1});
  170. ambient->set_intensity(0.0f);
  171. ambient->update_tweens();
  172. ctx->overworld_scene->add_object(ambient);
  173. scene::directional_light* sun = new scene::directional_light();
  174. //sun->set_intensity(1000.0f);
  175. //sun->set_light_texture(resource_manager->load<gl::texture_2d>("forest-gobo.tex"));
  176. //sun->set_light_texture_scale({2000, 2000});
  177. //sun->set_light_texture_opacity(0.925f);
  178. //sun->look_at({2, 1, 0}, {0, 0, 0}, {0, 0, 1});
  179. //sun->update_tweens();
  180. ctx->overworld_scene->add_object(sun);
  181. ctx->overworld_shadow_map_pass->set_light(sun);
  182. // Set universal time
  183. const double universal_time = 0.0;
  184. ctx->astronomy_system->set_universal_time(universal_time);
  185. ctx->orbit_system->set_universal_time(universal_time);
  186. // Set astronomy system observation parameters
  187. ctx->astronomy_system->set_reference_body(earth_entity);
  188. ctx->astronomy_system->set_observer_location(double3{0.0, math::radians(0.0f), math::radians(0.0f)});
  189. ctx->astronomy_system->set_sun_light(sun);
  190. ctx->astronomy_system->set_sky_pass(ctx->overworld_sky_pass);
  191. // Load entity archetypes
  192. entity::archetype* ant_hill_archetype = resource_manager->load<entity::archetype>("ant-hill.ent");
  193. entity::archetype* nest_archetype = resource_manager->load<entity::archetype>("harvester-nest.ent");
  194. entity::archetype* redwood_archetype = resource_manager->load<entity::archetype>("redwood.ent");
  195. entity::archetype* forceps_archetype = resource_manager->load<entity::archetype>("forceps.ent");
  196. entity::archetype* lens_archetype = resource_manager->load<entity::archetype>("lens.ent");
  197. entity::archetype* brush_archetype = resource_manager->load<entity::archetype>("brush.ent");
  198. entity::archetype* marker_archetype = resource_manager->load<entity::archetype>("marker.ent");
  199. entity::archetype* container_archetype = resource_manager->load<entity::archetype>("container.ent");
  200. entity::archetype* twig_archetype = resource_manager->load<entity::archetype>("twig.ent");
  201. entity::archetype* larva_archetype = resource_manager->load<entity::archetype>("ant-larva.ent");
  202. entity::archetype* flashlight_archetype = resource_manager->load<entity::archetype>("flashlight.ent");
  203. entity::archetype* flashlight_light_cone_archetype = resource_manager->load<entity::archetype>("flashlight-light-cone.ent");
  204. entity::archetype* lens_light_cone_archetype = resource_manager->load<entity::archetype>("lens-light-cone.ent");
  205. entity::archetype* cube_archetype = resource_manager->load<entity::archetype>("unit-cube.ent");
  206. entity::archetype* color_checker_archetype = resource_manager->load<entity::archetype>("color-checker.ent");
  207. // Create tools
  208. /*
  209. forceps_archetype->assign(entity_registry, ctx->forceps_entity);
  210. lens_archetype->assign(entity_registry, ctx->lens_entity);
  211. brush_archetype->assign(entity_registry, ctx->brush_entity);
  212. marker_archetype->assign(entity_registry, ctx->marker_entity);
  213. container_archetype->assign(entity_registry, ctx->container_entity);
  214. twig_archetype->assign(entity_registry, ctx->twig_entity);
  215. */
  216. // Create flashlight and light cone, set light cone parent to flashlight, and move both to underworld scene
  217. /*
  218. flashlight_archetype->assign(entity_registry, ctx->flashlight_entity);
  219. auto flashlight_light_cone = flashlight_light_cone_archetype->create(entity_registry);
  220. entity::command::parent(entity_registry, flashlight_light_cone, ctx->flashlight_entity);
  221. entity::command::assign_render_layers(entity_registry, ctx->flashlight_entity, 2);
  222. entity::command::assign_render_layers(entity_registry, flashlight_light_cone, 2);
  223. */
  224. // Make lens tool's model instance unculled, so its shadow is always visible.
  225. //scene::model_instance* lens_model_instance = ctx->render_system->get_model_instance(ctx->lens_entity);
  226. //if (lens_model_instance)
  227. //{
  228. //lens_model_instance->set_culling_mask(&ctx->no_cull);
  229. //}
  230. // Create lens light cone and set its parent to lens
  231. //auto lens_light_cone = lens_light_cone_archetype->create(entity_registry);
  232. //entity::command::bind_transform(entity_registry, lens_light_cone, ctx->lens_entity);
  233. //entity::command::parent(entity_registry, lens_light_cone, ctx->lens_entity);
  234. // Hide inactive tools
  235. /*
  236. entity::command::assign_render_layers(entity_registry, ctx->forceps_entity, 0);
  237. entity::command::assign_render_layers(entity_registry, ctx->brush_entity, 0);
  238. entity::command::assign_render_layers(entity_registry, ctx->lens_entity, 0);
  239. entity::command::assign_render_layers(entity_registry, ctx->marker_entity, 0);
  240. entity::command::assign_render_layers(entity_registry, ctx->container_entity, 0);
  241. entity::command::assign_render_layers(entity_registry, ctx->twig_entity, 0);
  242. */
  243. // Activate brush tool
  244. //ctx->tool_system->set_active_tool(ctx->brush_entity);
  245. // Create ant-hill
  246. //auto ant_hill_entity = ant_hill_archetype->create(entity_registry);
  247. //entity::command::place(entity_registry, ant_hill_entity, earth_entity, 0.0, 0.0, 0.0);
  248. // Create color checker
  249. /*
  250. auto color_checker = color_checker_archetype->create(entity_registry);
  251. entity::command::place(entity_registry, color_checker, {-10, -10});
  252. auto& cc_transform = entity_registry.get<entity::component::transform>(color_checker);
  253. cc_transform.local.scale *= 10.0f;
  254. cc_transform.local.rotation = math::angle_axis(math::radians(-90.0f), {1, 0, 0});
  255. */
  256. // Setup camera focal point
  257. entity::component::transform focal_point_transform;
  258. focal_point_transform.local = math::identity_transform<float>;
  259. //focal_point_transform.local.translation = {0, 6.3781e6, 0};
  260. focal_point_transform.warp = true;
  261. entity::component::camera_follow focal_point_follow;
  262. entity::component::snap focal_point_snap;
  263. focal_point_snap.ray = {float3{0, 10000, 0}, float3{0, -1, 0}};
  264. focal_point_snap.warp = false;
  265. focal_point_snap.relative = true;
  266. focal_point_snap.autoremove = false;
  267. entity_registry.assign_or_replace<entity::component::transform>(ctx->focal_point_entity, focal_point_transform);
  268. entity_registry.assign_or_replace<entity::component::camera_follow>(ctx->focal_point_entity, focal_point_follow);
  269. //entity_registry.assign_or_replace<entity::component::snap>(ctx->focal_point_entity, focal_point_snap);
  270. // Setup camera
  271. ctx->overworld_camera->look_at({0, 0, 1}, {0, 0, 0}, {0, 1, 0});
  272. ctx->overworld_camera->set_exposure(-14.5f);
  273. ctx->camera_system->set_camera(ctx->overworld_camera);
  274. ctx->overworld_scene->update_tweens();
  275. // Allocate a nest
  276. nest* nest = new ::nest();
  277. // Setup initial nest parameters
  278. float tunnel_radius = 1.15f;
  279. nest->set_tunnel_radius(tunnel_radius);
  280. nest::shaft* central_shaft = nest->get_central_shaft();
  281. central_shaft->chirality = 1.0f;
  282. central_shaft->rotation = math::radians(0.0f);
  283. central_shaft->depth = {0.0f, 200.0f};
  284. central_shaft->radius = {15.0f, 15.0f};
  285. central_shaft->pitch = {40.0f, 40.0f};
  286. central_shaft->translation = {{{0.0f, 0.0f}, {0.0f, 0.0f}}};
  287. central_shaft->current_depth = 0.0f;
  288. for (std::size_t i = 0; i < 4; ++i)
  289. {
  290. nest::chamber chamber;
  291. chamber.shaft = central_shaft;
  292. chamber.depth = (i + 1) * 50.0f;
  293. chamber.rotation = math::radians(0.0f);
  294. chamber.inner_radius = 4.0f;
  295. chamber.outer_radius = 10.0f;
  296. central_shaft->chambers.push_back(chamber);
  297. }
  298. // Dig nest shafts
  299. float shift = 0.1f;
  300. for (int i = 0; i < 800; ++i)
  301. {
  302. entity::component::cavity cavity;
  303. cavity.position = nest->extend_shaft(*nest->get_central_shaft());
  304. cavity.position += float3{math::random(-shift, shift), math::random(-shift, shift), math::random(-shift, shift)};
  305. cavity.radius = tunnel_radius * math::random(1.0f, 1.1f);
  306. entity_registry.assign<entity::component::cavity>(entity_registry.create(), cavity);
  307. }
  308. // Dig nest chambers
  309. /*
  310. for (int i = 0; i < central_shaft->chambers.size(); ++i)
  311. {
  312. for (int j = 0; j < 150; ++j)
  313. {
  314. entity::component::cavity cavity;
  315. cavity.position = nest->expand_chamber(central_shaft->chambers[i]);
  316. cavity.position += float3{math::random(-shift, shift), math::random(-shift, shift), math::random(-shift, shift)};
  317. cavity.radius = tunnel_radius * math::random(1.0f, 1.1f);
  318. entity_registry.assign<entity::component::cavity>(entity_registry.create(), cavity);
  319. }
  320. }
  321. */
  322. // Place larva in chamber
  323. {
  324. auto larva = larva_archetype->create(entity_registry);
  325. entity::command::assign_render_layers(entity_registry, larva, 1);
  326. entity::command::warp_to(entity_registry, larva, {50, 0.1935f, 0});
  327. //auto& transform = entity_registry.get<entity::component::transform>(larva_entity);
  328. //transform.transform = math::identity_transform<float>;
  329. //transform.transform.translation = nest->get_shaft_position(*central_shaft, central_shaft->depth[1]);
  330. //transform.transform.translation.y -= 1.0f;
  331. }
  332. entity::system::control* control_system = ctx->control_system;
  333. control_system->update(0.0, 0.0);
  334. control_system->set_nest(nest);
  335. // Start fade in
  336. ctx->fade_transition->transition(1.0f, true, ease<float>::in_quad);
  337. logger->pop_task(EXIT_SUCCESS);
  338. std::string biome_name = (*ctx->strings)[ctx->biome->name];
  339. logger->log("Entered biome \"" + biome_name + "\"");
  340. std::srand(std::time(nullptr));
  341. //auto rng = [](){ return std::rand(); };
  342. std::random_device rd;
  343. std::mt19937 rng(rd());
  344. std::string sequence_a = "CCTTGCCCTTTGGGTCGCCCCCCTAG";
  345. std::string sequence_b = "ATGTTTCCCGAAGGGTAG";
  346. std::string sequence_c = "AAATGCCCCCCCCCCCCCCCCCCCCCCCCCCCTAGAAAAAAAAA";
  347. std::string orf_a;
  348. std::string protein_a;
  349. std::string protein_b;
  350. std::string protein_c;
  351. std::cout << "sequence a: " << sequence_a << std::endl;
  352. genetics::sequence::transcribe(sequence_a.begin(), sequence_a.end(), sequence_a.begin());
  353. std::cout << "sequence a: " << sequence_a << std::endl;
  354. std::string complement;
  355. genetics::sequence::rna::complement(sequence_a.begin(), sequence_a.end(), std::back_inserter(complement));
  356. std::cout << "complement: " << complement << std::endl;
  357. auto orf = genetics::sequence::find_orf(sequence_a.begin(), sequence_a.end(), genetics::standard_code);
  358. if (orf.start != sequence_a.end())
  359. {
  360. std::copy(orf.start, orf.stop, std::back_inserter(orf_a));
  361. std::cout << "orf a: " << orf_a << std::endl;
  362. genetics::sequence::translate(orf.start, orf.stop, std::back_inserter(protein_a), genetics::standard_code);
  363. std::cout << "protein a: " << protein_a << std::endl;
  364. }
  365. protein_b = "MFFFFP";
  366. protein_c = "MFFFYP";
  367. int score;
  368. std::cout << std::endl;
  369. std::cout << "protein_b: " << protein_b << std::endl;
  370. std::cout << "protein_c: " << protein_c << std::endl;
  371. score = genetics::protein::score(protein_b.begin(), protein_b.end(), protein_c.begin(), genetics::matrix::blosum62<int>);
  372. std::cout << "score blosum62: " << score << std::endl;
  373. score = genetics::protein::score(protein_b.begin(), protein_b.end(), protein_c.begin(), genetics::matrix::blosum80<int>);
  374. std::cout << "score blosum80: " << score << std::endl;
  375. std::cout << "identity : " << genetics::protein::identity<float>(protein_b.begin(), protein_b.end(), protein_c.begin()) << std::endl;
  376. std::cout << "similarity62: " << genetics::protein::similarity<float>(protein_b.begin(), protein_b.end(), protein_c.begin(), genetics::matrix::blosum62<int>) << std::endl;
  377. std::cout << "similarity80: " << genetics::protein::similarity<float>(protein_b.begin(), protein_b.end(), protein_c.begin(), genetics::matrix::blosum80<int>) << std::endl;
  378. }
  379. void play_state_exit(game_context* ctx)
  380. {
  381. debug::logger* logger = ctx->logger;
  382. logger->push_task("Exiting play state");
  383. logger->pop_task(EXIT_SUCCESS);
  384. }