main.cpp 4.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133
  1. 
  2. #include <limits>
  3. #include "../../DFPSR/includeFramework.h"
  4. using namespace dsr;
  5. // Having a media folder requires keeping track of its location.
  6. // * You can start the program from its own folder and use a relative path. (Simple and works when developing)
  7. // * You can give a command line argument with the media folder's location. (Good for modifications using multiple folders)
  8. // * You can try to find the application's relative path using argv[0]. (Often works but not guaranteed by the C++ standard)
  9. // * You can use system specific API calls to find the applications location. (Increases long-term maintenance)
  10. // * You can link binary files into your application. (Hard to create modifications without access to source code)
  11. //const String mediaPath = string_combine(U"media", file_separator());
  12. //static BasicResourcePool pool(mediaPath);
  13. // Global variables
  14. bool running = true;
  15. // The window handle
  16. Window window;
  17. // Textures for 3D models must use power-of-two dimensions
  18. AlignedImageU8 darkEdge = image_fromAscii(
  19. "< .-x>"
  20. "<xxxxxxxxxxxxxxxx>"
  21. "<x--------------x>"
  22. "<x-............-x>"
  23. "<x-. .-x>"
  24. "<x-. .-x>"
  25. "<x-. .-x>"
  26. "<x-. .-x>"
  27. "<x-. .-x>"
  28. "<x-. .-x>"
  29. "<x-. .-x>"
  30. "<x-. .-x>"
  31. "<x-. .-x>"
  32. "<x-. .-x>"
  33. "<x-............-x>"
  34. "<x--------------x>"
  35. "<xxxxxxxxxxxxxxxx>"
  36. );
  37. OrderedImageRgbaU8 myTexture = image_pack(darkEdge, darkEdge, 0, 255);
  38. int createCubePart(Model model, const FVector3D &min, const FVector3D &max) {
  39. // Add positions
  40. model_addPoint(model, FVector3D(min.x, min.y, min.z)); // 0: Left-down-near
  41. model_addPoint(model, FVector3D(min.x, min.y, max.z)); // 1: Left-down-far
  42. model_addPoint(model, FVector3D(min.x, max.y, min.z)); // 2: Left-up-near
  43. model_addPoint(model, FVector3D(min.x, max.y, max.z)); // 3: Left-up-far
  44. model_addPoint(model, FVector3D(max.x, min.y, min.z)); // 4: Right-down-near
  45. model_addPoint(model, FVector3D(max.x, min.y, max.z)); // 5: Right-down-far
  46. model_addPoint(model, FVector3D(max.x, max.y, min.z)); // 6: Right-up-near
  47. model_addPoint(model, FVector3D(max.x, max.y, max.z)); // 7: Right-up-far
  48. // Create a part for the polygons
  49. int part = model_addEmptyPart(model, U"cube");
  50. // Polygons using default texture coordinates on the 4 corners of the texture
  51. model_addQuad(model, part, 3, 2, 0, 1); // Left quad
  52. model_addQuad(model, part, 6, 7, 5, 4); // Right quad
  53. model_addQuad(model, part, 2, 6, 4, 0); // Front quad
  54. model_addQuad(model, part, 7, 3, 1, 5); // Back quad
  55. model_addQuad(model, part, 3, 7, 6, 2); // Top quad
  56. model_addQuad(model, part, 0, 4, 5, 1); // Bottom quad
  57. return part;
  58. }
  59. Model createCubeModel(const FVector3D &min, const FVector3D &max) {
  60. Model result = model_create();
  61. createCubePart(result, min, max);
  62. return result;
  63. }
  64. int main(int argn, char **argv) {
  65. // Create a window
  66. window = window_create(U"Basic 3D template", 1600, 900);
  67. // Tell the application to terminate when the window is closed
  68. window_setCloseEvent(window, []() {
  69. running = false;
  70. });
  71. // Get whole window key events
  72. window_setKeyboardEvent(window, [](const KeyboardEvent& event) {
  73. if (event.keyboardEventType == KeyboardEventType::KeyDown) {
  74. DsrKey key = event.dsrKey;
  75. if (key >= DsrKey_1 && key <= DsrKey_9) {
  76. window_setPixelScale(window, key - DsrKey_0);
  77. } else if (key == DsrKey_F11) {
  78. window_setFullScreen(window, !window_isFullScreen(window));
  79. } else if (key == DsrKey_Escape) {
  80. running = false;
  81. }
  82. }
  83. });
  84. // Genrate mip-maps for the texture
  85. image_generatePyramid(myTexture);
  86. // Create a cube model
  87. Model cubeModel = createCubeModel(FVector3D(-0.5f), FVector3D(0.5f));
  88. // Assign the texture to part 0
  89. model_setDiffuseMap(cubeModel, 0, myTexture);
  90. // Create a renderer for multi-threading
  91. Renderer worker = renderer_create();
  92. while(running) {
  93. window_executeEvents(window);
  94. auto colorBuffer = window_getCanvas(window);
  95. auto depthBuffer = window_getDepthBuffer(window);
  96. int targetWidth = image_getWidth(colorBuffer);
  97. int targetHeight = image_getHeight(colorBuffer);
  98. // Paint the background color
  99. image_fill(colorBuffer, ColorRgbaI32(0, 0, 0, 0));
  100. image_fill(depthBuffer, 0.0f); // Infinite reciprocal depth using zero
  101. // Create a camera
  102. const float distance = 1.3f;
  103. const float height = 1.0f;
  104. const double speed = 0.2f;
  105. double timer = time_getSeconds() * speed;
  106. FVector3D cameraPosition = FVector3D(sin(timer) * distance, height, cos(timer) * distance);
  107. FMatrix3x3 cameraRotation = FMatrix3x3::makeAxisSystem(-cameraPosition, FVector3D(0.0f, 1.0f, 0.0f));
  108. Camera camera = Camera::createPerspective(Transform3D(cameraPosition, cameraRotation), targetWidth, targetHeight);
  109. // Render
  110. renderer_begin(worker, colorBuffer, depthBuffer);
  111. renderer_giveTask(worker, cubeModel, Transform3D(), camera);
  112. renderer_end(worker);
  113. window_showCanvas(window);
  114. }
  115. }