20 Commits

Author SHA1 Message Date
Redacted
1f4913ae7d Update .gitea/workflows/buildtest.yml
All checks were successful
Run ReCI Build Test / Explore-Gitea-Actions (push) Successful in 1m47s
2024-10-04 23:36:34 -04:00
Redacted
1adaff6362 Update .gitea/workflows/buildtest.yml
All checks were successful
Run ReCI Build Test / Explore-Gitea-Actions (push) Successful in 1m56s
2024-10-04 23:23:33 -04:00
f1017eb1da fixed cmake_minimum_required using rebitch
All checks were successful
Run ReCI Build Test / Explore-Gitea-Actions (push) Successful in 1m48s
2024-08-26 19:53:47 -04:00
Redacted
b334095aaa Update README.md
All checks were successful
Run ReCI Build Test / Explore-Gitea-Actions (push) Successful in 2m0s
2024-08-06 00:49:21 -04:00
Redacted
8ec95df86c Update README.md
All checks were successful
Run ReCI Build Test / Explore-Gitea-Actions (push) Successful in 1m43s
2024-08-04 17:37:55 -04:00
f746d395b3 reci
All checks were successful
Run ReCI Build Test / Explore-Gitea-Actions (push) Successful in 5m33s
2024-07-30 10:28:50 -04:00
6dbe1c4616 Merge branch 'testing' 2024-07-17 16:04:44 -04:00
f5ab983176 Cleanup 2024-07-17 13:52:24 -04:00
7f65fee891 More accurate lighting.
Sacrificed one texture unit to make it such that point lights on things that are multi-textured look the same as on regular things.
2024-07-16 20:09:49 -04:00
30ff52a3f8 Updated README to include libfreetype6-dev dependency for Ubuntu. Added an Additional Notes section thanking contributors and describing Re3D working on non-x86 architectures. 2024-07-15 15:53:09 -04:00
e550dea76e Update JGL 2024-07-07 20:24:56 -04:00
8ee3cec460 Test 2??? 2024-07-07 00:20:29 -04:00
c2077481c3 2D Text Context!!! 2024-07-06 23:50:30 -04:00
463895a44f 1 2024-07-06 23:10:48 -04:00
4091b1281f merge 2024-07-05 22:48:51 -04:00
37301b1dc4 Merge branch 'main' into testing 2024-07-05 22:48:35 -04:00
5196401dd3 JGL Render Pass 2024-07-05 22:32:42 -04:00
d9928dde76 Initial Windows Support 2024-06-30 20:48:54 -04:00
7c0b91d8cc Update repositories to latest. 2024-06-30 19:43:19 -04:00
c82663fdc2 Update 2024-06-24 13:07:14 -04:00
29 changed files with 369 additions and 258 deletions

View File

@@ -0,0 +1,22 @@
name: Run ReCI Build Test
run-name: Run ReCI Build Test For ${{ gitea.repository }}.
on: [push]
jobs:
Explore-Gitea-Actions:
runs-on: ubuntu-22.04
env:
RECI_GIT: https://git.redacted.cc/maxine/ReCI
RECI: /RECI
steps:
- run: echo "The job was automatically triggered by a ${{ gitea.event_name }} event."
- run: echo "This job is now running on a ${{ runner.os }} server hosted by Gitea!"
- run: echo "The name of your branch is ${{ gitea.ref }} and your repository is ${{ gitea.repository }}."
- name: Check out repository code
uses: actions/checkout@v3
- run: echo "The ${{ gitea.repository }} repository has been cloned to the runner."
- run: echo "The workflow is now ready to run your tests on the runner."
- run: echo "Install toolchain and run ReCI build test"
- run: apt-get update && apt-get install -y lua5.3 git libxrandr-dev && git clone $RECI_GIT $RECI
- run: lua $RECI/reci.lua -f $RECI/scripts/buildtools.reci -f reci/scripts/builddeps.reci -f $RECI/scripts/buildtest.reci
- run: echo "This job's status is ${{ job.status }}."

View File

@@ -1,4 +1,4 @@
cmake_minimum_required(VERSION 3.18)
cmake_minimum_required(VERSION 3.18..3.27)
project(Re3D
VERSION 1.0
LANGUAGES CXX C
@@ -20,7 +20,6 @@ file(GLOB_RECURSE HEADERS "include/*")
file(GLOB_RECURSE SOURCES "src/*")
file(GLOB_RECURSE ASSETS "assets/*")
#Move all libraries to lib after building.
SET(CMAKE_LIBRARY_OUTPUT_DIRECTORY "${PROJECT_BINARY_DIR}/lib")
SET(CMAKE_ARCHIVE_OUTPUT_DIRECTORY "${PROJECT_BINARY_DIR}/lib")
@@ -30,7 +29,7 @@ SET(CMAKE_ARCHIVE_OUTPUT_DIRECTORY "${PROJECT_BINARY_DIR}/lib")
CPMAddPackage(
NAME ReWindow
URL https://git.redacted.cc/Redacted/ReWindow/archive/Prerelease-2.zip
URL https://git.redacted.cc/Redacted/ReWindow/archive/Prerelease-3.zip
)
CPMAddPackage(
@@ -38,30 +37,29 @@ CPMAddPackage(
URL https://git.redacted.cc/josh/Event/archive/Release-6.zip
)
#Temporarily removed due to SystemD requirement.
#CPMAddPackage(
# NAME ReHardwareID
# URL https://git.redacted.cc/Redacted/ReHardwareID/archive/v1.1.zip
# URL https://git.redacted.cc/Redacted/ReHardwareID/archive/Prerelease-1.zip
#)
CPMAddPackage(
NAME J3ML
URL https://git.redacted.cc/josh/j3ml/archive/Release-2.1.zip
URL https://git.redacted.cc/josh/j3ml/archive/Release-2.2.zip
)
CPMAddPackage(
NAME JGL
URL https://git.redacted.cc/josh/JGL/archive/Prerelease-14.zip
URL https://git.redacted.cc/josh/JGL/archive/Prerelease-20.zip
)
CPMAddPackage(
NAME ReTexture
URL https://git.redacted.cc/Redacted/ReTexture/archive/Prerelease-1.zip
URL https://git.redacted.cc/Redacted/ReTexture/archive/Prerelease-2.zip
)
CPMAddPackage(
NAME UUID
URL https://git.redacted.cc/Redacted/uuid/archive/v1.zip
URL https://git.redacted.cc/Redacted/uuid/archive/Release-1.zip
)
CPMAddPackage(
@@ -69,22 +67,28 @@ CPMAddPackage(
URL https://git.redacted.cc/Redacted/glad/archive/v2.1ext_mt.zip
)
CPMAddPackage(
NAME archive
URL https://git.redacted.cc/Redacted/archive/archive/v1.0.zip
)
#CPMAddPackage(
# NAME archive
# URL https://git.redacted.cc/Redacted/archive/archive/v1.0.zip
#)
CPMAddPackage(
NAME Collage
URL https://git.redacted.cc/Redacted/Collage/archive/v0.4.zip
URL https://git.redacted.cc/Redacted/Collage/archive/v0.5.zip
)
CPMAddPackage(
NAME jlog
URL https://git.redacted.cc/josh/jlog/archive/Prerelease-8.zip
URL https://git.redacted.cc/josh/jlog/archive/Prerelease-12.zip
)
add_library(Re3D SHARED ${SOURCES})
if (UNIX AND NOT APPLE)
add_library(Re3D SHARED ${SOURCES})
endif()
if (WIN32)
add_library(Re3D STATIC ${SOURCES})
endif()
target_include_directories(Re3D PUBLIC
${PROJECT_SOURCE_DIR}/include
@@ -96,7 +100,7 @@ target_include_directories(Re3D PUBLIC
${ReTexture_SOURCE_DIR}/include
${glad_SOURCE_DIR}/include
${UUID_SOURCE_DIR}/include
${archive_SOURCE_DIR}/include
#${archive_SOURCE_DIR}/include
${Collage_SOURCE_DIR}/include
${Event_SOURCE_DIR}/include
)
@@ -104,9 +108,14 @@ target_include_directories(Re3D PUBLIC
# Why god???
set_target_properties(Re3D PROPERTIES LINKER_LANGUAGE CXX)
find_package(OpenGL REQUIRED)
if (UNIX AND NOT APPLE)
find_package(OpenGL REQUIRED)
target_link_libraries(Re3D PUBLIC Event ReWindowLibrary ReTexture J3ML GL glad Collage JGL jlog)
endif()
target_link_libraries(Re3D PUBLIC Event ReWindowLibrary ReTexture J3ML GL glad Collage JGL archive jlog)
if (WIN32)
target_link_libraries(Re3D PUBLIC Event ReWindowLibrary ReTexture J3ML glad Collage JGL jlog)
endif()
include(src/demo/RuntimeTest/CMakeLists.txt)

View File

@@ -7,7 +7,7 @@ A classic 3D game-engine for Linux & Windows.
### Installing Dependencies
- Fedora ```sudo dnf install git cmake make gcc-g++ mesa-libGL-devel systemd-devel```
<br><br>
- Ubuntu ```sudo apt install git cmake make gcc g++ pkg-config libgl-dev libudev-dev```
- Ubuntu ```sudo apt install git cmake make gcc g++ pkg-config libgl-dev libudev-dev libfreetype6-dev```
<br><br>
- Archᵇᵗʷ ```sudo pacman -S git cmake make gcc libgl```
@@ -15,6 +15,22 @@ A classic 3D game-engine for Linux & Windows.
```bash
git clone https://git.redacted.cc/Redacted/Re3D.git && cd Re3D && mkdir build && cd build && cmake .. && make -j8
```
### What's The Goal?
The game development industry has lost sight of what made games fun. A massive amount of the development time will be focused on graphics instead, The result being a pretty game that's not fun to play. Or worse, A game that's released unfinished.
Open Source game engines or engine components are commonly under copyleft licenses. If you were to make use of it then the entire game would also have to be under the same license. In terms of making a game to sell they're useless.
So then, A simple game-engine with the goal of **all** of the code being public domain.
### Additional Notes
It is possible to run Re3D on ARM. Re3D is known to run on the X13s using Ubuntu 24.04 at a reported 500 FPS (Software Renderer) as of writing. Thank you to Richard Neale for this discovery!
It is also possible to run Re3D on the VisionFive2 (RISC-V). We've tested this not long ago and have made appropriate fixes since. If I remember correctly we were running Debian on the board. (FPS not documented, but we remember it being quite low - Maxine)
Richard Neale has also discovered Re3D can run on a Banana Pi F3 (RISC-V) running Armbian 24.5 at a reported 5 FPS. For armbian the Ubuntu instructions should apply and the package name for libfreetype is libfreetype-dev.
Testing of Re3D on a variety of CPU architectures is encouraged and greatly appreciated. Although we may not support every architecture at this current time we definitely appreciate any work put toward testing and porting to various architectures.
<div style="text-align: left; line-height: 0">
<h5>Donation</h5>
<h76><a href="monero:89P8iW1Ly6wbypAYegceveUKe36nGYSsAfQhwCu3JJDHGso3XdXwuYpEGRM14QhXo63idEyWu5xYRMRoiJYekGE34z8SDtu">Monero</a></h76>

View File

@@ -53,6 +53,7 @@ public:
void initGL() const;
void loadConfig();
static void init();
void jglRenderPass();
void preRender();
void render();
static void postRender();

View File

@@ -2,5 +2,6 @@
#include <Redacted3D/types/entity/camera.h>
namespace Occlusion {
//TODO
bool frustumCull(Camera* camera, Entity* entity);
}

View File

@@ -49,7 +49,7 @@ private:
Vector3 globalLightColor = {0, 0, 0};
Vector4 globalFogColor = {0, 0, 0, 0};
Vector2 globalFogRange = {0, 0};
GLenum globalFogMode = NULL; ///There's Linear, GL_EXP, GL_EXP2.
GLenum globalFogMode = 0; ///There's Linear, GL_EXP, GL_EXP2.
GLfloat globalFogDensity = 0.0f;
public:
@@ -68,6 +68,7 @@ public:
[[nodiscard]] GLfloat getGlobalFogDensity() const;
Camera* getActiveCamera();
Vector3 upVector = {0, 1, 0};
std::string name;
std::vector<VertexArray*> geometryList;
std::vector<Texture*> textureList;

View File

@@ -5,7 +5,7 @@
#include <J3ML/LinearAlgebra/Matrix4x4.h>
#include <J3ML/LinearAlgebra/Vector3.h>
#include <Redacted3D/engine/collision.h>
#include <archive.h>
//#include <archive.h>
using J3ML::LinearAlgebra::Matrix4x4;
using J3ML::LinearAlgebra::Vector3;
@@ -18,24 +18,26 @@ private:
///Pitch Yaw Roll, The orientation of the entity in the world,
Vector3 angle = {0,0,0};
///Loads the texture for the entity.
virtual void loadTexture();
///Loads the geometry for it.
void loadGeometry();
///The scale it should be rendered at.
GLfloat scale = 1.0f;
Vector3 scale = {1.0f, 1.0f, 1.0f};
protected:
std::string modelPath;
std::string texturePath;
///If the entity has a parent entity, It's here.
Entity* parent;
///Entity list of child entities.
std::vector<Entity*> children;
///Loads the geometry for it.
void loadGeometry(const std::string& file);
void loadTexture(const std::string& file);
void loadMultiTexture(const std::vector<std::string>& files);
void loadMotionTexture(const std::vector<std::string>& files, u16 frameDelta, bool doAnim = true);
public:
std::string name; //Entity name. TODO remove this.
bool alive;
virtual std::vector<std::string> GetEntityUUIDList() const {}
virtual std::vector<std::string> GetEntityUUIDList() const { return std::vector<std::string> { "" }; }
template <class T>
void SerializeMemberData(T& archive)
@@ -75,7 +77,7 @@ public:
[[nodiscard]] Entity* GetFamilyTreeRoot() const;
Entity *Add(Entity *newChild);
void setScale(const float& multiplier);
[[nodiscard]] GLfloat getScale() const;
[[nodiscard]] Vector3 getScale() const;
// TODO: Constrain to DerivedEntityType
template <typename T>
@@ -110,7 +112,6 @@ public:
Vector3 getAngle();
void setAngle(const Vector3& a);
void setAngle(float pitch, float yaw, float roll);
///Removes an entity from the list, Checks if the assets are being used by any other entity. Removes them from their lists & deletes. Then deletes the entity.
void erase();
bool draw = true;
@@ -118,6 +119,7 @@ public:
bool isCollidingWith(Entity* entity);
virtual void pre_render() {}
virtual void post_render() {}
virtual void jglRenderPass() {}
///The default rendering routine. Works for 99% of cases.
virtual void render();
virtual void update(float elapsed) {}

View File

@@ -10,8 +10,7 @@ private:
///Speed.
float velocity;
public:
Vector3 upVector = {0.0f,1.0f,0.0f};
Moby(): Entity(), upVector(0, 1, 0){}
Moby(): Entity(){}
///Move
void move(Direction a, float speed);

View File

@@ -8,11 +8,11 @@ public:
std::string name;
///The shader program
GLuint id = NULL;
GLuint id = 0;
///The individual shaders
GLuint vertex = NULL;
GLuint fragment = NULL;
GLuint vertex = 0;
GLuint fragment = 0;
Shader(const char* name, const std::string& vertexPath, const std::string& fragmentPath);
Shader(const char* name, const std::string& filePath, const GLenum& type);

View File

@@ -33,22 +33,24 @@ public:
void erase() override;
///Every texture other than the base texture.
std::vector<Texture> multi;
///Loads a multi-texture from a given directory. One must be called "default.png"
MultiTexture(Entity* entity, const char* pathContainingTextures, bool storeOnTextureList);
///Loads a list of Textures into a MultiTexture.
MultiTexture(Entity* entity, const std::vector<std::string>& textures, bool storeOnTextureList);
MultiTexture() = default;
//TODO load multi-texture from array of std::string of file names.
};
///A list of textures where the one actually displayed depends on how much time has elapsed.
class MotionTexture : public Texture {
private:
std::chrono::high_resolution_clock::time_point lastUpdate;
int lastDisplayedIndex;
u16 msDelay;
public:
int lastDisplayedIndex = 0;
u16 msDelay = 0;
bool doAnim = true;
public:
std::vector<Texture> motion;
Texture* current();
MotionTexture(Entity* entity, const std::vector<std::string>& textures,u16 msBetweenFrames, bool storeOnTextureList);
Texture* base();
void advance();
void toggleAnim();
MotionTexture(Entity* entity, const std::vector<std::string>& textures,u16 msBetweenFrames, bool storeOnTextureList, bool doAnim = true);
MotionTexture() = default;
};

View File

@@ -1,9 +1,8 @@
#pragma once
#include <vector>
#include <iostream>
#include <fstream>
#include <Collage/types/animation.h>
#include <Collage/types/model.h>
#include <J3ML/LinearAlgebra/Vector3.h>
#include <J3ML/LinearAlgebra/Vector2.h>
#include <J3ML/Geometry/OBB.h>
@@ -12,6 +11,7 @@
///Forward declaration of entity.
class Entity;
typedef Vector2 TextureCoordinate;
using J3ML::LinearAlgebra::Vector3;
using J3ML::LinearAlgebra::Vector2;
using J3ML::Geometry::OBB;
@@ -19,7 +19,6 @@ using J3ML::Geometry::OBB;
///A point which makes up a model in 3D space.
typedef Vector3 Vertex;
///Determines how your texture is wrapped around the model.
typedef Vector2 TextureCoordinate;
///Drawable type. Models are stored in these.
class VertexArray {

View File

@@ -0,0 +1 @@
Main:new("Install build dependencies", "apt-get install -yq pkg-config libgl-dev libudev-dev libfreetype6-dev")

View File

@@ -2,7 +2,10 @@ include_directories("src/demo/RuntimeTest/include")
add_executable(Re3D-RuntimeTest "src/demo/RuntimeTest/main.cpp")
#Link based on the relative path *so you can copy the game around*
set_target_properties(Re3D-RuntimeTest PROPERTIES LINK_FLAGS "-Wl,-rpath,./lib")
if (UNIX AND NOT APPLE)
set_target_properties(Re3D-RuntimeTest PROPERTIES LINK_FLAGS "-Wl,-rpath,./lib")
endif()
#Copy the assets to the build directory.
file(COPY "assets" DESTINATION "${PROJECT_BINARY_DIR}")

View File

@@ -17,8 +17,7 @@ public:
//The "camera point" is the position the camera will want to be while following the player.
//We will probably end up having a different camera point class controlled by the "world".
void update(float elapsed) override;
//void update(float elapsed) override;
void pre_render() override;
void loadTexture() override;
Cube();
};

View File

@@ -0,0 +1,13 @@
#pragma once
#include <JGL/JGL.h>
#include <JGL/Colors.h>
namespace Fonts {
inline int Jupiteroid = -1;
inline int ModeSeven = -1;
inline void initFonts() {
Jupiteroid = JGL::LoadFont("assets/fonts/Jupiteroid/JupiteroidRegular.ttf");
ModeSeven = JGL::LoadFont("assets/fonts/modeseven.ttf");
}
}

View File

@@ -1,7 +1,9 @@
#pragma once
#include <Redacted3D/types/entity/camera.h>
#include <fonts.h>
class FreeCam : public Camera {
public:
void pre_render() override;
void jglRenderPass() override;
};

View File

@@ -4,14 +4,14 @@
#include <ball.h>
#include <freeCam.h>
#include <demoSky.h>
//#include <JGL/JGL.h>
//#include <JGL/Colors.h>
int main()
{
engine->window = new ReWindow::RWindow("Re3D Test Application", 1152, 864, RenderingAPI::OPENGL);
engine->world = new(World);
Engine::init();
JGL::Update(engine->window->getSize());
Fonts::initFonts();
engine->window->setVsyncEnabled(false);
engine->window->setResizable(false);
engine->world->setAmbientLightColor(1.0f, 1.0f, 1.0f);

View File

@@ -10,7 +10,7 @@ void Ball::update(float elapsed) {
Ball::Ball() {
name = "ball";
modelPath = "assets/models/sphere_lo.obj";
texturePath = "assets/textures/missing.png";
loadGeometry("assets/models/sphere_lo.obj");
loadTexture("assets/textures/missing.png");
setScale(1.0f);
}
}

View File

@@ -1,31 +1,27 @@
#include <cube.h>
#include <Redacted3D/engine/engine.h>
#include <ball.h>
void Cube::pre_render() {
getGeometry();
setAngle(getAngle().Add(24 * engine->frameDelta));
}
void Cube::update(float elapsed) {
}
Cube::Cube() {
name = "cube";
modelPath = "assets/models/cube.obj";
texturePath = "assets/textures/multi/";
setScale(0.5f);
}
void Cube::loadTexture() {
//MultiTexture texture(this, texturePath.c_str(), true);
std::vector<std::string> textures;
textures.emplace_back("assets/textures/motion/default.png");
textures.emplace_back("assets/textures/motion/1.png");
textures.emplace_back("assets/textures/motion/2.png");
textures.emplace_back("assets/textures/motion/3.png");
textures.emplace_back("assets/textures/motion/4.png");
textures.emplace_back("assets/textures/motion/5.png");
textures.emplace_back("assets/textures/motion/6.png");
MotionTexture texture(this, textures, 250, true);
loadGeometry("assets/models/cube.obj");
std::vector<std::string> motionTextures = {
"assets/textures/motion/default.png", "assets/textures/motion/1.png", "assets/textures/motion/2.png",
"assets/textures/motion/3.png", "assets/textures/motion/4.png", "assets/textures/motion/5.png",
"assets/textures/motion/6.png"
};
std::vector<std::string> multiTextures = {
"assets/textures/multi/default.png", "assets/textures/multi/1.png", "assets/textures/multi/2.png", "assets/textures/multi/3.png",
"assets/textures/multi/4.png", "assets/textures/multi/5.png", "assets/textures/multi/6.png"
};
loadMultiTexture(multiTextures);
//loadMotionTexture(motionTextures, 250, true);
}

View File

@@ -3,7 +3,7 @@
DemoSkybox::DemoSkybox() {
name = "skybox";
modelPath = engine->workingDir + "/assets/models/sphere_vlo.obj";
texturePath = engine->workingDir + "/assets/textures/skybox.png";
loadGeometry("assets/models/sphere_vlo.obj");
loadTexture("assets/textures/skybox.png");
setScale(engine->farPlane);
}

View File

@@ -1,4 +1,5 @@
#include <freeCam.h>
#include <JGL/Colors.h>
void FreeCam::pre_render() {
if (engine->window->isKeyDown(Keys::W))
@@ -16,7 +17,7 @@ void FreeCam::pre_render() {
if (engine->window->isKeyDown(Keys::Space))
vMove(4);
if (engine->window->isKeyDown(Keys::LShift))
if (engine->window->isKeyDown(Keys::LeftShift))
vMove(-4);
if (engine->window->isKeyDown(Keys::LeftArrow))
@@ -36,5 +37,23 @@ void FreeCam::pre_render() {
if (engine->window->isKeyDown(Keys::E))
setAngle(getAngle().x, getAngle().y, getAngle().z + 75.0f * engine->frameDelta);
}
Vector3 textAngle = {0,0,0};
void FreeCam::jglRenderPass() {
textAngle.x = textAngle.x - (96.f * engine->frameDelta);
using namespace JGL;
J3D::Begin();
J3D::DrawString(JGL::Colors::Red, "Text", {0, -2, 0}, textAngle, 4.f, 32, Fonts::Jupiteroid);
J3D::End();
J2D::Begin();
J2D::FillRect({255,0,0,128}, {0, 72}, {100, 100});
J2D::FillCircle(JGL::Colors::White, {16, 128}, 12, 16);
J2D::DrawString(JGL::Colors::White, "Framerate: " + std::to_string((int) engine->framerate()), 0, -16, 1, 16, Fonts::Jupiteroid);
J2D::DrawString(JGL::Colors::White, "Framecount: " + std::to_string(engine->frameCount), 0, -33, 1,16, Fonts::Jupiteroid);
J2D::DrawString(JGL::Colors::White, "Position: " + std::to_string(position.x) + " " + std::to_string(position.y) + " " + std::to_string(position.z), 0, -50, 1,16, Fonts::Jupiteroid);
J2D::DrawString(JGL::Colors::White, "ViewAngle: " + std::to_string(getAngle().x) + " " + std::to_string(getAngle().y) + " " + std::to_string(getAngle().z), 0, -67, 1,16, Fonts::Jupiteroid);
J2D::End();
}

View File

@@ -1,15 +1,14 @@
#include <sstream>
#include <thread>
#include <Redacted3D/engine/engine.h>
#include <Redacted3D/engine/utils/instanceOf.h>
#include <Redacted3D/types/entity/camera.h>
#include <JGL/JGL.h>
#include <JGL/Colors.h>
#include <Redacted3D/engine/engine.h>
#include <Redacted3D/types/entity/camera.h>
#include <jlog/jlog.hpp>
using namespace J3ML;
std::array<float, 16> perspective(float fov, float aspect, float nearPlane, float farPlane) {
std::array<float, 16> result{};
std::vector<float> perspective(float fov, float aspect, float nearPlane, float farPlane) {
std::vector<float> result(16);
float f = 1.0f / tan(fov * 0.5f * M_PI / 180.0f);
result[0] = f / aspect;
result[5] = f;
@@ -20,7 +19,7 @@ std::array<float, 16> perspective(float fov, float aspect, float nearPlane, floa
}
void Engine::quit() const {
window->destroyWindow();
//window->destroyWindow();
exit(0);
}
@@ -83,68 +82,72 @@ void Engine::initGL() const {
glDepthMask(GL_TRUE);
glEnable(GL_CULL_FACE);
glHint(GL_PERSPECTIVE_CORRECTION_HINT, GL_NICEST);
glEnable(GL_LIGHT0);
}
void Engine::init()
{
engine->window->Open();
engine->initGL();
engine->loadConfig();
glPixelStorei(GL_UNPACK_ALIGNMENT, 1);
JGL::InitTextEngine();
void Engine::init() {
engine->window->Open();
engine->initGL();
engine->loadConfig();
glPixelStorei(GL_UNPACK_ALIGNMENT, 1);
}
void Engine::preRender() {
engine->window->pollEvents();
engine->frameCount++;
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
for (auto& e : world->GetChildren())
e->pre_render();
}
void Engine::render() {
glMatrixMode(GL_MODELVIEW);
glLoadIdentity();
if(world->getActiveCamera() != nullptr)
world->getActiveCamera()->render();
for (auto& e : world->GetChildren())
if (e->draw)
if (auto* c = dynamic_cast<Camera*>(e); c == nullptr) //If it's not a camera.
e->render();
int glError = glGetError();
if (glError != GL_NO_ERROR) {
FATAL("GL Error: " + std::to_string(glError))
exit(0);
}
}
void Engine::preRender()
{
engine->window->pollEvents();
engine->frameCount++;
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
void Engine::jglRenderPass() {
JGL::Update(engine->window->getSize());
glDisable(GL_LIGHTING);
///If elements are attached to a camera that's not the active one then they shouldn't be drawn.
if(world->getActiveCamera() != nullptr)
world->getActiveCamera()->jglRenderPass();
for (auto& e : world->GetChildren())
e->pre_render();
}
for (auto& e : world->GetChildren())
if (e->draw)
if (auto* c = dynamic_cast<Camera*>(e); c == nullptr) //If it's not a camera.
e->jglRenderPass();
glEnable(GL_LIGHTING);
}
void Engine::postRender() {
for (auto& e : engine->world->GetChildren())
e->post_render();
ReWindow::RWindow::glSwapBuffers();
}
void Engine::renderPass() {
preRender();
render();
jglRenderPass();
postRender();
}
void Engine::render()
{
glMatrixMode(GL_MODELVIEW);
glLoadIdentity();
if(world->getActiveCamera() != nullptr)
world->getActiveCamera()->render();
for (auto& e : world->GetChildren())
if (e->draw)
if (auto* c = dynamic_cast<Camera*>(e); c == nullptr) //If it's not a camera.
e->render();
if (glGetError() != GL_NO_ERROR)
exit(0);
//TODO JGL rendering pass.
glDisable(GL_LIGHTING);
JGL::J3D::DrawString3D(JGL::Colors::White, std::to_string((int) framerate()), {0.5f, 0, 0.5f}, 0.0125f);
glEnable(GL_LIGHTING);
}
void Engine::postRender()
{
for (auto& e : engine->world->GetChildren())
e->post_render();
ReWindow::RWindow::glSwapBuffers();
}
void Engine::renderPass()
{
preRender();
render();
postRender();
}
[[noreturn]] void Engine::renderLoop()
{
[[noreturn]] void Engine::renderLoop() {
while (true) {
auto start = std::chrono::high_resolution_clock::now();
renderPass();
@@ -225,7 +228,7 @@ EngineError Engine::getError() {
}
void Engine::quit(ENGINE_ERROR_CODE code) const {
window->destroyWindow();
//window->destroyWindow();
exit((int) code);
}

View File

@@ -2,6 +2,4 @@
#include <Redacted3D/types/entity/entity.h>
bool Occlusion::frustumCull(Camera* camera, Entity* entity) {
}
bool Occlusion::frustumCull(Camera* camera, Entity* entity) { return false; }

View File

@@ -21,15 +21,16 @@ void Camera::render() {
glRotatef(getAngle().y,0.0f, 1.0f, 0.0f);
glRotatef(getAngle().z,0.0f, 0.0f, 1.0f);
glMultMatrixf(lookAt({position.x, position.y, position.z}, {position.x, position.y, engine->farPlane+position.z}, upVector).data());
glMultMatrixf(lookAt({position.x, position.y, position.z}, {position.x, position.y, engine->farPlane+position.z}, engine->world->upVector).data());
}
void Camera::post_render() {
ticksAlive++;
}
/*
bool Camera::raycast(Entity *entity) {
Vector3 rayOrigin = position;
Vector3 rayAngle = getAngle();
}
*/

View File

@@ -42,7 +42,7 @@ Entity::Entity() {
ticksAlive = 0;
children = std::vector<Entity*> ();
parent = nullptr;
scale = 1.0f;
scale = {1.0f, 1.0f, 1.0f};
//UUIDv4::UUIDGenerator<std::mt19937_64> uuidGenerator;
//UUIDv4::UUID id = uuidGenerator.getUUID();
@@ -50,24 +50,43 @@ Entity::Entity() {
}
void Entity::setScale(const float &multiplier) {
scale = multiplier;
scale.Set(multiplier, multiplier, multiplier);
}
GLfloat Entity::getScale() const {
Vector3 Entity::getScale() const {
return scale;
}
void Entity::loadTexture() {
Texture texture(this, texturePath.c_str(), true);
void Entity::loadTexture(const std::string& file) {
for (const auto* e : engine->world->GetChildren())
if (instanceOf(this, e))
return;
Texture texture(this, file.c_str(), true);
}
void Entity::loadGeometry() {
VertexArray vArray(this, modelPath, true);
void Entity::loadMultiTexture(const std::vector<std::string>& files) {
for (const auto* e : engine->world->GetChildren())
if (instanceOf(this, e))
return;
MultiTexture texture(this, files, true);
}
void Entity::loadMotionTexture(const std::vector<std::string>& files, u16 frameDelta, bool doAnim) {
for (const auto* e : engine->world->GetChildren())
if (instanceOf(this, e))
return;
MotionTexture(this, files, frameDelta, true, doAnim);
}
void Entity::loadGeometry(const std::string& file) {
for (const auto& vA : engine->world->geometryList)
for (const auto& reference : vA->usedBy)
if (instanceOf(this, reference))
return;
VertexArray vArray(this, file, true);
}
VertexArray* Entity::getGeometry() {
if (engine->world->geometryList.empty())
loadGeometry();
for (auto& vArray : engine->world->geometryList)
for (auto& entity : vArray->usedBy)
if (instanceOf(this, entity)) {
@@ -75,28 +94,60 @@ VertexArray* Entity::getGeometry() {
vArray->usedBy.push_back(this);
return vArray;
}
loadGeometry();
return getGeometry();
return nullptr;
}
Texture* Entity::getTexture() {
for (auto& texture : engine->world->textureList)
for (auto& entity : texture->usedBy)
if (instanceOf(this, entity)) {
if (std::find(texture->usedBy.begin(), texture->usedBy.end(), this) == texture->usedBy.end()) //If this is the first time the entity is using it.
texture->usedBy.push_back(this);
return texture;
}
return nullptr;
}
inline Texture* baseTexture = new Texture;
void Entity::render() {
bool multiTexture = false;
bool motionTexture = false;
if (!baseTexture) {
Texture t;
glGenTextures(1, &t.id);
glBindTexture(GL_TEXTURE_2D, t.id);
if (auto* t = dynamic_cast<MultiTexture*>(getTexture()))
multiTexture = true;
unsigned char whitePixel[4] = { 255, 255, 255, 255};
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, 1, 1, 0, GL_RGBA, GL_UNSIGNED_BYTE, whitePixel);
if (!multiTexture)
if (auto* t = dynamic_cast<MotionTexture*>(getTexture()))
motionTexture = true;
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
glActiveTexture(0);
baseTexture = new Texture(t);
}
MultiTexture texture;
texture.id = baseTexture->id;
if (auto* t = dynamic_cast<MultiTexture*>(getTexture())) {
texture.multi.emplace_back(*t);
for (const auto &item: t->multi)
texture.multi.push_back(item);
}
else if (auto* j = dynamic_cast<MotionTexture*>(getTexture()))
texture.multi.push_back(*j->current());
else if (auto* k = dynamic_cast<Texture*>(getTexture()))
texture.multi.push_back(*k);
glPushMatrix();
glTranslatef(position.x, position.y, position.z);
glRotatef(angle.x, 1.0f, 0.0f, 0.0f);
glRotatef(angle.y, 0.0f, 1.0f, 0.0f);
glRotatef(angle.z, 0.0f, 0.0f, 1.0f);
if (getScale() != 1.0f)
glScalef(getScale(), getScale(), getScale());
if (getScale().x != 1.0f || getScale().y != 1.0f || getScale().z != 1.0f)
glScalef(getScale().x, getScale().y, getScale().z);
//Set up texture.
glActiveTexture(GL_TEXTURE0);
@@ -104,7 +155,9 @@ void Entity::render() {
glEnable(GL_TEXTURE_2D);
glEnableClientState(GL_VERTEX_ARRAY);
glEnableClientState(GL_TEXTURE_COORD_ARRAY);
glBindTexture(GL_TEXTURE_2D, motionTexture ? ((MotionTexture*)getTexture())->current()->id : getTexture()->id);
glBindTexture(GL_TEXTURE_2D, texture.id);
//Texture unit mode.
glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE);
if (!engine->useVBO)
glVertexPointer(3, GL_FLOAT, sizeof(Vertex), &getGeometry()->vertices[0].x),
@@ -114,41 +167,32 @@ void Entity::render() {
glBindBuffer(GL_ARRAY_BUFFER, getGeometry()->tbo),
glTexCoordPointer(2, GL_FLOAT, 0, nullptr);
if (!multiTexture)
getGeometry()->draw();
if (multiTexture) {
auto* multi = (MultiTexture*) getTexture();
int i = 0;
for(auto& t : texture.multi) {
glActiveTexture(GL_TEXTURE1 + i);
glClientActiveTexture(GL_TEXTURE1 + i);
glEnable(GL_TEXTURE_2D);
glEnableClientState(GL_VERTEX_ARRAY);
glEnableClientState(GL_TEXTURE_COORD_ARRAY);
int i = 0;
GLfloat blendingFactor[3] = {engine->world->getAmbientLightColor().x * 0.2f, engine->world->getAmbientLightColor().y * 0.2f, engine->world->getAmbientLightColor().z * 0.2f};
for(auto& texture : multi->multi) {
glActiveTexture(GL_TEXTURE1 + i);
glClientActiveTexture(GL_TEXTURE1 + i);
glEnable(GL_TEXTURE_2D);
glEnableClientState(GL_VERTEX_ARRAY);
glEnableClientState(GL_TEXTURE_COORD_ARRAY);
if (!engine->useVBO)
glVertexPointer(3, GL_FLOAT, sizeof(Vertex), &getGeometry()->vertices[0].x),
glTexCoordPointer(2, GL_FLOAT, sizeof(TextureCoordinate), &getGeometry()->texCoords[0].x);
if (!engine->useVBO)
glVertexPointer(3, GL_FLOAT, sizeof(Vertex), &getGeometry()->vertices[0].x),
glTexCoordPointer(2, GL_FLOAT, sizeof(TextureCoordinate), &getGeometry()->texCoords[0].x);
if (engine->useVBO)
glBindBuffer(GL_ARRAY_BUFFER, getGeometry()->tbo),
glTexCoordPointer(2, GL_FLOAT, 0, nullptr);
if (engine->useVBO)
glBindBuffer(GL_ARRAY_BUFFER, getGeometry()->tbo),
glTexCoordPointer(2, GL_FLOAT, 0, nullptr);
//Texture unit mode.
glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_BLEND);
//Makes the lighting work the way you'd think it would.
glTexEnvfv(GL_TEXTURE_ENV, GL_TEXTURE_ENV_COLOR, blendingFactor);
glBindTexture(GL_TEXTURE_2D, texture.id);
glBindTexture(GL_TEXTURE_2D, t.id);
i++;
}
getGeometry()->draw();
//Reset the multi-texture units.
for (int j = 0; j <= i; j++) {
for (int j = 0; j < i; j++) {
glActiveTexture(GL_TEXTURE1 + j);
glClientActiveTexture(GL_TEXTURE1 + j);
glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE);
@@ -156,7 +200,6 @@ void Entity::render() {
glDisableClientState(GL_VERTEX_ARRAY);
glDisableClientState(GL_TEXTURE_COORD_ARRAY);
}
}
//Reset texture unit 0.
glActiveTexture(GL_TEXTURE0);
@@ -178,23 +221,7 @@ void Entity::render() {
}
}
bool Entity::isCollidingWith(Entity *entity) {
}
Texture* Entity::getTexture() {
if (engine->world->textureList.empty())
loadTexture();
for (auto& texture : engine->world->textureList)
for (auto& entity : texture->usedBy)
if (instanceOf(this, entity)) {
if (std::find(texture->usedBy.begin(), texture->usedBy.end(), this) == texture->usedBy.end()) //If this is the first time the entity is using it.
texture->usedBy.push_back(this);
return texture;
}
loadTexture();
return getTexture();
}
//bool Entity::isCollidingWith(Entity *entity) {}
void Entity::erase() {
Texture* t = getTexture();
@@ -222,9 +249,10 @@ void Entity::erase() {
AABB Entity::getAABB() {
AABB aabb = Collision::genMinimallyEnclosingAABB(getGeometry());
if (getScale() != 1)
aabb.minPoint *= scale,
aabb.maxPoint *= scale;
//TODO this won't look right.
if (getScale().x != 1)
aabb.minPoint *= scale.x,
aabb.maxPoint *= scale.x;
aabb.minPoint += position;
aabb.maxPoint += position;
@@ -233,7 +261,8 @@ AABB Entity::getAABB() {
Sphere Entity::getSphere() {
Sphere sphere = Collision::genMinimallyEnclosingSphere(getGeometry());
sphere.Radius *= scale;
//TODO this won't look right.
sphere.Radius *= scale.x;
sphere.Position = position;
return sphere;
}
@@ -243,7 +272,7 @@ OBB Entity::getOBB() {
}
Vector3 Entity::getAngle() {
return angle;
return {Math::Degrees(Math::Radians(angle.x)), Math::Degrees(Math::Radians(angle.y)), Math::Degrees(Math::Radians(angle.z))};
}
void Entity::setAngle(const Vector3 &a) {
@@ -255,7 +284,7 @@ void Entity::setAngle(float pitch, float yaw, float roll) {
}
Direction Entity::getAngleDirection() {
Direction a = Vector3::Direction(angle);
Direction a = Vector3::Direction(getAngle());
//These two are reversed when moving things in the Re3D scene.
//-Z is forward.
a.x = -a.x;

View File

@@ -37,7 +37,7 @@ void Moby::vAngleMove(float speed) {
}
//Returns the position we'd be at *if* we did a movement.
Direction Moby::projectedHorizontalMove(Vector3 a, float vel) {
Position Moby::projectedHorizontalMove(Vector3 a, float vel) {
Position p;
p.z -= (vel*engine->frameDelta) * a.x;
p.x += (vel*engine->frameDelta) * a.z;
@@ -48,13 +48,8 @@ Position Moby::projectedVerticalMove(float speed) {
return {position.x, position.y += (speed*engine->frameDelta), position.z};
}
Direction Moby::fAngle()
{
Direction a;
a.x = -(cos(Math::Radians(getAngle().y)) * cos(Math::Radians(getAngle().x)));
a.y = -sin(Math::Radians(getAngle().x));
a.z = -(sin(Math::Radians(getAngle().y)) * cos(Math::Radians(getAngle().x)));
return a;
Direction Moby::fAngle() {
return getAngleDirection();
}
Direction Moby::bAngle() {
@@ -62,21 +57,11 @@ Direction Moby::bAngle() {
}
Direction Moby::rAngle() {
Direction f = fAngle();
Direction a;
a.x = f.x * upVector.z - f.z * upVector.y;
a.y = f.z * upVector.x - f.x * upVector.z;
a.z = f.x * upVector.y - f.y * upVector.x;
return a;
return Vector3::Cross(fAngle(), engine->world->upVector);
}
Direction Moby::lAngle() {
Direction f = fAngle();
Direction a;
a.x = -(f.y * upVector.z - f.z * upVector.y);
a.y = (f.z * upVector.x - f.x * upVector.z);
a.z = -(f.x * upVector.y - f.y * upVector.x);
return a;
return -rAngle();
}
float Moby::getVelocity() {
@@ -105,4 +90,4 @@ void Moby::setVelocityAngle(const Vector3 &a) {
void Moby::setVelocityAngle(float pitch, float yaw, float roll) {
velAngle = {pitch, yaw, roll};
}
}

View File

@@ -12,7 +12,7 @@ void Skybox::render() {
glTranslatef(position.x ,position.y, position.z);
glBindTexture(GL_TEXTURE_2D, getTexture()->id);
glCullFace(GL_FRONT);
glScalef(getScale(), getScale(), getScale());
glScalef(getScale().x, getScale().y, getScale().z);
getGeometry()->draw();
glCullFace(GL_BACK);
glBindTexture(GL_TEXTURE_2D,0);
@@ -21,7 +21,5 @@ void Skybox::render() {
Skybox::Skybox() {
name = "skybox";
modelPath = engine->workingDir + "/assets/models/sphere_vlo.obj";
texturePath = engine->workingDir + "/assets/textures/missing.png";
setScale(engine->farPlane);
}

View File

@@ -1,9 +1,10 @@
#include <Redacted3D/types/texture.h>
#include <ReTexture/rTexture.h>
#include <Redacted3D/types/texture.h>
#include <Redacted3D/engine/engine.h>
void Texture::load(Entity* entity, const std::string& file, bool storeOnTextureList) {
auto* texture = new RTexture(file, {RTextureFlag::INVERT_Y});
glGenTextures(1, &id);
glBindTexture(GL_TEXTURE_2D, id);
if (texture->format == RTextureFormat::RGBA)
@@ -11,6 +12,7 @@ void Texture::load(Entity* entity, const std::string& file, bool storeOnTextureL
if (texture->format == RTextureFormat::RGB)
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, texture->width, texture->height, 0, GL_RGB, GL_UNSIGNED_BYTE, texture->pixelData.data());
delete texture;
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
@@ -55,35 +57,31 @@ void Texture::erase(Texture* texture) const {
engine->world->textureList.erase(engine->world->textureList.begin() + i);
}
MultiTexture::MultiTexture(Entity* entity, const char* pathContainingTextures, bool storeOnTextureList) {
for (const auto& entry : std::filesystem::directory_iterator(pathContainingTextures))
if (entry.is_regular_file() && entry.path().extension() == ".png") {
Texture texture(entity, entry.path().c_str(), false);
//The base texture *must* go in the first slot.
if (entry.path().filename() == "default.png")
this->id = texture.id,
this->usedBy = texture.usedBy;
else multi.push_back(texture);
}
MultiTexture::MultiTexture(Entity* entity, const std::vector<std::string>& textures, bool storeOnTextureList) {
Texture base;
for (const auto& t : textures) {
if (id != 0)
multi.emplace_back(entity, t.c_str(), false);
else
base = Texture(entity, t.c_str(), false),
id = base.id,
usedBy = base.usedBy;
}
if (storeOnTextureList)
engine->world->textureList.push_back(new MultiTexture(*this));
//You cannot have more than 8 total textures rendered in one pass.
//In Fixed-Function OpenGL you only have 8 TMUs available.
//TODO: multi-pass multi-texturing (will be slower).
if (multi.size() > 7)
engine->setError(ENGINE_ERROR_CODE::MULTI_TEXTURE_SIZE_EXCEEDS, true);
if (multi.size() > 6)
engine->setError(ENGINE_ERROR_CODE::MULTI_TEXTURE_SIZE_EXCEEDS, false);
}
void MultiTexture::erase() {
Texture::erase(this);
}
MotionTexture::MotionTexture(Entity* entity, const std::vector<std::string>& textures, u16 msBetweenFrames, bool storeOnTextureList) {
MotionTexture::MotionTexture(Entity* entity, const std::vector<std::string>& textures, u16 msBetweenFrames, bool storeOnTextureList, bool doAnim) {
msDelay = msBetweenFrames;
this->doAnim = doAnim;
Texture base(entity, textures[0].c_str(), false);
std::vector<std::string> extra(textures.begin()+1, textures.end());
@@ -124,4 +122,18 @@ Texture* MotionTexture::current() {
return this;
return &motion[lastDisplayedIndex - 1];
}
}
void MotionTexture::advance() {
lastDisplayedIndex++;
if (lastDisplayedIndex > motion.size())
lastDisplayedIndex = 0;
}
void MotionTexture::toggleAnim() {
doAnim = !doAnim;
}
Texture* MotionTexture::base() {
return this;
}

View File

@@ -33,7 +33,7 @@ void VertexArray::load (const std::string& filename) {
}
//Cached OBB.
this->cachedOBB = Collision::genMinimallyEnclosingOBB(this, (Vector3) {0, 0, 0});
this->cachedOBB = Collision::genMinimallyEnclosingOBB(this, {0, 0, 0});
}
void VertexArray::draw() {