Camera and proper rendering

This commit is contained in:
Halbear 2026-06-07 21:40:21 +01:00
parent 3040800275
commit a8adf662ff
48 changed files with 65391 additions and 22367 deletions

Binary file not shown.

View file

@ -0,0 +1,15 @@
{
"ID": "CorvetteOBJ",
"Meshes": [
{
"ID": "cube_0",
"MaterialID": "CorvetteOBJ-mat-1",
"OffsetVertex": 0,
"VertexSize": 452640,
"OffsetIndex": 0,
"IndexSize": 151488
}
],
"VertexPath": "resources/models/Corvette/CorvetteOBJ.vtx",
"IndexPath": "resources/models/Corvette/CorvetteOBJ.idx"
}

View file

@ -0,0 +1,4 @@
# Made in Blockbench 5.1.4
newmtl m_64480dc7-fc68-f52d-eb18-7368900ee2a3
map_Kd corvetteclass.png
newmtl none

File diff suppressed because it is too large Load diff

Binary file not shown.

View file

@ -0,0 +1,32 @@
[
{
"ID": "CorvetteOBJ-mat-0",
"TexturePath": "",
"DiffuseColour": {
"X": 0.6,
"Y": 0.6,
"Z": 0.6,
"W": 1.0
}
},
{
"ID": "CorvetteOBJ-mat-1",
"TexturePath": "resources\\models\\Corvette\\corvetteclass.png",
"DiffuseColour": {
"X": 0.6,
"Y": 0.6,
"Z": 0.6,
"W": 1.0
}
},
{
"ID": "CorvetteOBJ-mat-2",
"TexturePath": "",
"DiffuseColour": {
"X": 0.6,
"Y": 0.6,
"Z": 0.6,
"W": 1.0
}
}
]

Binary file not shown.

After

Width:  |  Height:  |  Size: 96 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 76 KiB

Binary file not shown.

View file

@ -0,0 +1,15 @@
{
"ID": "MetroLeadCar",
"Meshes": [
{
"ID": "DoorForward_0",
"MaterialID": "MetroLeadCar-mat-1",
"OffsetVertex": 0,
"VertexSize": 186900,
"OffsetIndex": 0,
"IndexSize": 58032
}
],
"VertexPath": "resources/models/Metro/OBJ/MetroLeadCar.vtx",
"IndexPath": "resources/models/Metro/OBJ/MetroLeadCar.idx"
}

View file

@ -0,0 +1,4 @@
# Made in Blockbench 5.1.4
newmtl m_6a204395-c016-b66d-c397-a01625c2ee08
map_Kd MetroCarLeadDefault.png
newmtl none

File diff suppressed because it is too large Load diff

Binary file not shown.

View file

@ -0,0 +1,32 @@
[
{
"ID": "MetroLeadCar-mat-0",
"TexturePath": "",
"DiffuseColour": {
"X": 0.6,
"Y": 0.6,
"Z": 0.6,
"W": 1.0
}
},
{
"ID": "MetroLeadCar-mat-1",
"TexturePath": "resources\\models\\Metro\\OBJ\\MetroCarLeadDefault.png",
"DiffuseColour": {
"X": 0.6,
"Y": 0.6,
"Z": 0.6,
"W": 1.0
}
},
{
"ID": "MetroLeadCar-mat-2",
"TexturePath": "",
"DiffuseColour": {
"X": 0.6,
"Y": 0.6,
"Z": 0.6,
"W": 1.0
}
}
]

Binary file not shown.

Before

Width:  |  Height:  |  Size: 153 KiB

View file

@ -1,4 +0,0 @@
# Made in Blockbench 5.1.4
newmtl m_1306cabb-1c39-88cc-7a28-6065072778b2
map_Kd SloopBluePaintedSpruce.png
newmtl none

File diff suppressed because it is too large Load diff

Binary file not shown.

View file

@ -1,15 +0,0 @@
{
"ID": "cube",
"Meshes": [
{
"ID": "cubemtl_0",
"MaterialID": "cube-mat-1",
"OffsetVertex": 0,
"VertexSize": 480,
"OffsetIndex": 0,
"IndexSize": 144
}
],
"VertexPath": "resources/models/cube/cube.vtx",
"IndexPath": "resources/models/cube/cube.idx"
}

View file

@ -1,5 +0,0 @@
newmtl cubemtl
Kd 0.00 0.00 0.00
Ka 0.59 0.45 0.35
Ks 0.59 0.45 0.35
map_Kd cube.png

View file

@ -1,88 +0,0 @@
mtllib cube.mtl
o cube
v -0.500000 -0.500000 0.500000
v -0.500000 0.500000 0.500000
v 0.500000 0.500000 0.500000
v 0.500000 -0.500000 0.500000
v -0.500000 -0.500000 0.500000
v -0.500000 0.500000 0.500000
v -0.500000 0.500000 -0.500000
v -0.500000 -0.500000 -0.500000
v 0.500000 -0.500000 0.500000
v 0.500000 0.500000 0.500000
v 0.500000 0.500000 -0.500000
v 0.500000 -0.500000 -0.500000
v -0.500000 0.500000 0.500000
v -0.500000 0.500000 -0.500000
v 0.500000 0.500000 0.500000
v 0.500000 0.500000 -0.500000
v -0.500000 -0.500000 0.500000
v -0.500000 -0.500000 -0.500000
v 0.500000 -0.500000 0.500000
v 0.500000 -0.500000 -0.500000
v -0.500000 -0.500000 -0.500000
v -0.500000 0.500000 -0.500000
v 0.500000 0.500000 -0.500000
v 0.500000 -0.500000 -0.500000
vt 0.000000 1.000000
vt 0.250000 1.000000
vt 0.000000 0.500000
vt 0.250000 0.500000
vt 0.250000 1.000000
vt 0.500000 1.000000
vt 0.250000 0.500000
vt 0.500000 0.500000
vt 0.500000 1.000000
vt 0.750000 1.000000
vt 0.500000 0.500000
vt 0.750000 0.500000
vt 0.750000 1.000000
vt 1.000000 1.000000
vt 0.750000 0.500000
vt 1.000000 0.500000
vt 0.000000 0.000000
vt 0.250000 0.000000
vt 0.000000 0.500000
vt 0.250000 0.500000
vt 0.250000 0.500000
vt 0.500000 0.500000
vt 0.250000 0.000000
vt 0.500000 0.000000
vn 0.000000 0.000000 1.000000
vn -1.000000 0.000000 0.000000
vn 1.000000 0.000000 0.000000
vn 0.000000 1.000000 0.000000
vn 0.000000 -1.000000 0.000000
vn 0.000000 0.000000 -1.000000
g cubemtl
usemtl cubemtl
f 1/3/1 2/1/1 4/4/1
f 2/1/1 3/2/1 4/4/1
f 5/8/2 6/6/2 8/7/2
f 6/6/2 7/5/2 8/7/2
f 9/11/3 10/9/3 12/12/3
f 10/9/3 12/12/3 11/10/3
f 13/15/4 14/13/4 15/16/4
f 14/13/4 16/14/4 15/16/4
f 17/19/5 18/17/5 19/20/5
f 18/17/5 20/18/5 19/20/5
f 21/24/6 22/22/6 24/23/6
f 22/22/6 23/21/6 24/23/6

Binary file not shown.

Before

Width:  |  Height:  |  Size: 7.4 KiB

Binary file not shown.

View file

@ -1,22 +0,0 @@
[
{
"ID": "cube-mat-0",
"TexturePath": "",
"DiffuseColour": {
"X": 0.6,
"Y": 0.6,
"Z": 0.6,
"W": 1.0
}
},
{
"ID": "cube-mat-1",
"TexturePath": "resources/models/cube/cube.png",
"DiffuseColour": {
"x": 0.0,
"y": 0.0,
"z": 0.0,
"w": 1.0
}
}
]

View file

@ -12,11 +12,11 @@ struct Material{
uint padding[2]; uint padding[2];
}; };
layout(set = 1, binding = 0) readonly buffer MaterialUniform{ layout(set = 2, binding = 0) readonly buffer MaterialUniform{
Material materials[]; Material materials[];
} matUniform; } matUniform;
layout(set = 2, binding = 0) uniform sampler2D textSampler[MAX_TEXTURES]; layout(set = 3, binding = 0) uniform sampler2D textSampler[MAX_TEXTURES];
layout(push_constant) uniform pc{ layout(push_constant) uniform pc{
layout(offset = 64) uint materialIdx; layout(offset = 64) uint materialIdx;

View file

@ -2,6 +2,7 @@
layout(location = 0) in vec3 inPos; layout(location = 0) in vec3 inPos;
layout(location = 1) in vec2 inTextCoords; layout(location = 1) in vec2 inTextCoords;
layout(location = 0) out vec2 outTextCoords; layout(location = 0) out vec2 outTextCoords;
@ -9,12 +10,16 @@ layout(set = 0, binding = 0) uniform ProjUniform{
mat4 matrix; mat4 matrix;
} projUniform; } projUniform;
layout(set = 1, binding = 0) uniform ViewUniform{
mat4 matrix;
} viewUniform;
layout(push_constant) uniform pc{ layout(push_constant) uniform pc{
mat4 modelMatrix; mat4 modelMatrix;
} push_constants; } push_constants;
void main() void main()
{ {
gl_Position = projUniform.matrix * push_constants.modelMatrix * vec4(inPos,1); gl_Position = projUniform.matrix * viewUniform.matrix * push_constants.modelMatrix * vec4(inPos,1);
outTextCoords = inTextCoords; outTextCoords = inTextCoords;
} }

View file

@ -133,7 +133,7 @@ public class Render {
resize(engineInstance); resize(engineInstance);
return; return;
} }
sceneRender.Render(engineInstance,RendererContext,CommandBuffer, modelsCache,materialsCache,ImageIndex); sceneRender.Render(engineInstance,RendererContext,CommandBuffer, modelsCache,materialsCache,ImageIndex,CurrentFrame);
RecordingStop(CommandBuffer); RecordingStop(CommandBuffer);
Submit(CommandBuffer, CurrentFrame, ImageIndex); Submit(CommandBuffer, CurrentFrame, ImageIndex);
Resize = swapChain.PresentImage(PresentQueue, RenderCompleteSemaphores[ImageIndex],ImageIndex); Resize = swapChain.PresentImage(PresentQueue, RenderCompleteSemaphores[ImageIndex],ImageIndex);

View file

@ -4,6 +4,7 @@ public interface GameLogic {
void cleanup(); void cleanup();
InitData Initialise(EngineInstance engineInstance); InitData Initialise(EngineInstance engineInstance);
void Input(EngineInstance engineInstance, long FrameDiffNanoSeconds); void Input(EngineInstance engineInstance, long FrameDiffNanoSeconds);
void CameraInput(EngineInstance engineInstance, long FrameDiffNanoSeconds);
void Update(EngineInstance engineInstance, long FrameDiffNanoSeconds); void Update(EngineInstance engineInstance, long FrameDiffNanoSeconds);
void UpdateFastThread(EngineInstance engineInstance, long FrameDiffNanoSeconds); void UpdateFastThread(EngineInstance engineInstance, long FrameDiffNanoSeconds);
} }

View file

@ -35,7 +35,7 @@ public class ModelCompiler {
| aiProcess_Triangulate | aiProcess_FixInfacingNormals | aiProcess_CalcTangentSpace | aiProcess_Triangulate | aiProcess_FixInfacingNormals | aiProcess_CalcTangentSpace
| aiProcess_PreTransformVertices; | aiProcess_PreTransformVertices;
@Parameter(names = "-m", description = "Model Path", required = true) @Parameter(names = "-model", description = "Model Path", required = true)
private String ModelPath; private String ModelPath;
public static void main(String[] args){ public static void main(String[] args){
@ -50,8 +50,7 @@ public class ModelCompiler {
Logger.error("Error Compiling model",exception); Logger.error("Error Compiling model",exception);
} }
} }
public static void Process(String ModelPath) throws IOException{
private void Process() throws IOException{
Logger.debug("Loading 3D Model Data from [{}]", ModelPath); Logger.debug("Loading 3D Model Data from [{}]", ModelPath);
var ModelSourceFile = new File(ModelPath); var ModelSourceFile = new File(ModelPath);
if (!ModelSourceFile.exists()) throw new RuntimeException("Model path does not exist->["+ModelPath+"]"); if (!ModelSourceFile.exists()) throw new RuntimeException("Model path does not exist->["+ModelPath+"]");
@ -86,7 +85,7 @@ public class ModelCompiler {
String CreateModelFile = ModelPath.substring(0,ModelPath.lastIndexOf('.')) + ".json"; String CreateModelFile = ModelPath.substring(0,ModelPath.lastIndexOf('.')) + ".json";
Writer writer = new FileWriter(CreateModelFile); Writer writer = new FileWriter(CreateModelFile);
var gson = new GsonBuilder().setFieldNamingPolicy(FieldNamingPolicy.LOWER_CASE_WITH_UNDERSCORES).setPrettyPrinting().create(); var gson = new GsonBuilder().setFieldNamingPolicy(FieldNamingPolicy.UPPER_CAMEL_CASE).setPrettyPrinting().create();
gson.toJson(model, writer); gson.toJson(model, writer);
writer.flush(); writer.flush();
writer.close(); writer.close();
@ -102,7 +101,11 @@ public class ModelCompiler {
Logger.info("Generated Vertex File [{}] and Index File [{}]",BinaryData.GetVertexFilePath(),BinaryData.GetIndexFilePath()); Logger.info("Generated Vertex File [{}] and Index File [{}]",BinaryData.GetVertexFilePath(),BinaryData.GetIndexFilePath());
} }
private MaterialData ProcessMaterial(AIScene aiScene, AIMaterial aiMaterial, String ModelName, String BaseDirectory, int Position) throws IOException{ private void Process() throws IOException{
Process(ModelPath);
}
public static MaterialData ProcessMaterial(AIScene aiScene, AIMaterial aiMaterial, String ModelName, String BaseDirectory, int Position) throws IOException{
Vector4f diffuse = new Vector4f(); Vector4f diffuse = new Vector4f();
AIColor4D colour = AIColor4D.create(); AIColor4D colour = AIColor4D.create();
@ -114,7 +117,7 @@ public class ModelCompiler {
return new MaterialData(ModelName + "-mat-" + Position,DiffuseTexture,diffuse); return new MaterialData(ModelName + "-mat-" + Position,DiffuseTexture,diffuse);
} }
private MeshData ProcessMesh(AIMesh aiMesh, List<MaterialData> MaterialList, int MeshPosition, ModelBinaryData BinaryData) throws IOException { public static MeshData ProcessMesh(AIMesh aiMesh, List<MaterialData> MaterialList, int MeshPosition, ModelBinaryData BinaryData) throws IOException {
List<Float> vertices = ProcessVertices(aiMesh); List<Float> vertices = ProcessVertices(aiMesh);
List<Float> textureCoordinates = ProcessTextureCoords(aiMesh); List<Float> textureCoordinates = ProcessTextureCoords(aiMesh);
List<Integer> indices = ProcessIndices(aiMesh); List<Integer> indices = ProcessIndices(aiMesh);
@ -155,7 +158,7 @@ public class ModelCompiler {
return meshData; return meshData;
} }
private static List<Float> ProcessTextureCoords(AIMesh aiMesh){ public static List<Float> ProcessTextureCoords(AIMesh aiMesh){
List<Float> TextureCoords = new ArrayList<>(); List<Float> TextureCoords = new ArrayList<>();
AIVector3D.Buffer aiTextureCoords = aiMesh.mTextureCoords(0); AIVector3D.Buffer aiTextureCoords = aiMesh.mTextureCoords(0);
int CoordinateCount = aiTextureCoords != null ? aiTextureCoords.remaining() : 0; int CoordinateCount = aiTextureCoords != null ? aiTextureCoords.remaining() : 0;
@ -167,7 +170,7 @@ public class ModelCompiler {
return TextureCoords; return TextureCoords;
} }
private List<Integer> ProcessIndices(AIMesh aiMesh){ public static List<Integer> ProcessIndices(AIMesh aiMesh){
List<Integer> Indices = new ArrayList<>(); List<Integer> Indices = new ArrayList<>();
int FaceCount = aiMesh.mNumFaces(); int FaceCount = aiMesh.mNumFaces();
AIFace.Buffer aiFaces = aiMesh.mFaces(); AIFace.Buffer aiFaces = aiMesh.mFaces();
@ -181,7 +184,7 @@ public class ModelCompiler {
return Indices; return Indices;
} }
private List<Float> ProcessVertices(AIMesh aiMesh){ public static List<Float> ProcessVertices(AIMesh aiMesh){
List<Float> vertices = new ArrayList<>(); List<Float> vertices = new ArrayList<>();
AIVector3D.Buffer aiVertices = aiMesh.mVertices(); AIVector3D.Buffer aiVertices = aiMesh.mVertices();
while(aiVertices.remaining() > 0){ while(aiVertices.remaining() > 0){
@ -193,7 +196,7 @@ public class ModelCompiler {
return vertices; return vertices;
} }
private String ProcessTexture(AIScene aiScene, AIMaterial aiMaterial, String BaseDirectory,int TextType ) throws IOException{ public static String ProcessTexture(AIScene aiScene, AIMaterial aiMaterial, String BaseDirectory,int TextType ) throws IOException{
String TexturePath; String TexturePath;
try(var MemStack = MemoryStack.stackPush()){ try(var MemStack = MemoryStack.stackPush()){
int EmbeddedTextureCount = aiScene.mNumTextures(); int EmbeddedTextureCount = aiScene.mNumTextures();

View file

@ -17,6 +17,21 @@ public class ModelLoader { // Model Utility class kinda like a model version of
} }
public static List<MaterialData> LoadMaterials(String[] Path){
var Result = new ArrayList<MaterialData>();
for(int i = 0; i < Path.length; i++) {
Logger.debug("Material loading step [{}], Loading Materials From [{}]", i, Path[i]);
try {
String content = new String(Files.readAllBytes(Paths.get(Path[i])));
var gson = new GsonBuilder().setFieldNamingPolicy(FieldNamingPolicy.UPPER_CAMEL_CASE).create();
Result.addAll(Arrays.asList(gson.fromJson(content, MaterialData[].class)));
} catch (Exception e) {
throw new RuntimeException(e);
}
Logger.debug("Loaded Material Data: [{}]", Result.toString());
}
return Result;
}
public static List<MaterialData> LoadMaterials(String Path){ public static List<MaterialData> LoadMaterials(String Path){
Logger.debug("Loading Materials From [{}]",Path); Logger.debug("Loading Materials From [{}]",Path);
var Result = new ArrayList<MaterialData>(); var Result = new ArrayList<MaterialData>();

View file

@ -1,25 +1,35 @@
package net.halbear.Terrain4J.EngineCore.Main; package net.halbear.Terrain4J.EngineCore.Main;
import net.halbear.Terrain4J.EngineCore.Display.Window;
import net.halbear.Terrain4J.EngineCore.Input.KeyboardInput;
import net.halbear.Terrain4J.EngineCore.Input.MouseListener;
import net.halbear.Terrain4J.EngineCore.Logic.EngineConfig; import net.halbear.Terrain4J.EngineCore.Logic.EngineConfig;
import net.halbear.Terrain4J.EngineCore.Logic.EngineInstance; import net.halbear.Terrain4J.EngineCore.Logic.EngineInstance;
import net.halbear.Terrain4J.EngineCore.Logic.GameLogic; import net.halbear.Terrain4J.EngineCore.Logic.GameLogic;
import net.halbear.Terrain4J.EngineCore.Logic.InitData; import net.halbear.Terrain4J.EngineCore.Logic.InitData;
import net.halbear.Terrain4J.EngineCore.Logic.Rendering.ModelLoader; import net.halbear.Terrain4J.EngineCore.Logic.Rendering.ModelLoader;
import net.halbear.Terrain4J.EngineCore.Main.Scene.Actor; import net.halbear.Terrain4J.EngineCore.Main.Scene.Actor;
import net.halbear.Terrain4J.EngineCore.Main.Scene.Camera;
import net.halbear.Terrain4J.EngineCore.Main.Scene.Scene; import net.halbear.Terrain4J.EngineCore.Main.Scene.Scene;
import net.halbear.Terrain4J.EngineCore.Vulkan.Rendering.VkModel.MaterialData; import net.halbear.Terrain4J.EngineCore.Vulkan.Rendering.VkModel.MaterialData;
import net.halbear.Terrain4J.EngineCore.Vulkan.Rendering.VkModel.ModelData; import net.halbear.Terrain4J.EngineCore.Vulkan.Rendering.VkModel.ModelData;
import org.joml.Vector2f;
import org.joml.Vector3f; import org.joml.Vector3f;
import org.tinylog.Logger; import org.tinylog.Logger;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.List; import java.util.List;
import static org.lwjgl.glfw.GLFW.*;
public class GameCore implements GameLogic { public class GameCore implements GameLogic {
private final Vector3f rotatingAngle = new Vector3f(1, 1, 1); private static final float MOUSE_SENSITIVITY = 0.1f;
private float angle = 0; private static final float MOVEMENT_SPEED = 0.01f;
private final Vector3f rotatingAngle = new Vector3f(0, 1, 0);
private float angle = 180;
private List<Float> angles = new ArrayList<>(); private List<Float> angles = new ArrayList<>();
private List<Vector3f> rotatingAngles = new ArrayList<>();
private List<Vector3f> Velocities = new ArrayList<>(); private List<Vector3f> Velocities = new ArrayList<>();
private Actor CubeActor; private Actor CubeActor;
private List<Actor> CubeActors = new ArrayList<>(); private List<Actor> CubeActors = new ArrayList<>();
@ -34,31 +44,81 @@ public class GameCore implements GameLogic {
Scene scene = engineInstance.scene(); Scene scene = engineInstance.scene();
List<ModelData> models = new ArrayList<>(); List<ModelData> models = new ArrayList<>();
ModelData SloopModel = ModelLoader.LoadModel("resources/Models/Cube/cube.json"); models.add(ModelLoader.LoadModel("resources/models/Metro/OBJ/MetroLeadCar.json"));
models.add(SloopModel); models.add(ModelLoader.LoadModel("resources/models/Corvette/CorvetteOBJ.json"));
Logger.trace(SloopModel.ID()); //models.add(ModelLoader.LoadModel("resources/models/Sloop/SloopOBJ.json"));
Actor SloopActor = new Actor("CubeEntity",SloopModel.ID(),new Vector3f(0.0f,0.0f,-10.0f)); models.add(ModelLoader.LoadModel("resources/models/melona/melona.json"));
angles.add(34F); models.add(ModelLoader.LoadModel("resources/models/Alice/Welsh040Alice.json"));
Velocities.add(new Vector3f(0,0,0)); for(int i = 0; i < 50000; i++) {
CubeActors.add(SloopActor); CubeActors.add(new Actor("CubeEntity" + i, models.get((int)Math.round(Math.min(Math.max((Math.random() * models.size() - 1),0),models.size() - 1))).ID(), new Vector3f((float)(-200 + Math.random() * 400), (float)(-50 + Math.random() * 100), (float)(250 + Math.random() * -500))));
scene.AddActor(SloopActor); angles.add((float)(Math.random() * 360));
rotatingAngles.add(new Vector3f((float)(Math.random()*2), (float)(Math.random()*2), (float)(Math.random()*2)));
Velocities.add(new Vector3f((float)(Math.random()*2), (float)(Math.random()*2), (float)(Math.random()*2)));
}
CubeActors.forEach(scene::AddActor);
List<MaterialData> materials = new ArrayList<>(ModelLoader.LoadMaterials("resources/Models/Cube/cube_mat.json")); List<MaterialData> materials = new ArrayList<>();
materials.addAll(ModelLoader.LoadMaterials("resources/models/Metro/OBJ/MetroLeadCar_mat.json"));
materials.addAll(ModelLoader.LoadMaterials("resources/models/Corvette/CorvetteOBJ_mat.json"));
materials.addAll(ModelLoader.LoadMaterials("resources/models/Sloop/SloopOBJ_mat.json"));
materials.addAll(ModelLoader.LoadMaterials("resources/models/melona/melona_mat.json"));
materials.addAll(ModelLoader.LoadMaterials("resources/models/Alice/Welsh040Alice_mat.json"));
Camera camera = scene.GetCamera();
camera.SetPosition(0.0f, 0.0f, 0.0f);
camera.SetRotation((float) Math.toRadians(0.0f), (float) Math.toRadians(0.0f),0);
return new InitData(models,materials); return new InitData(models,materials);
} }
@Override @Override
public void Input(EngineInstance engineInstance, long FrameDiffNanoSeconds) { public void CameraInput(EngineInstance engineInstance, long FrameDiffNanoSeconds) {
Scene scene = engineInstance.scene();
Window window = engineInstance.window();
Camera camera = scene.GetCamera();
MouseListener MouseInput = window.getMouseInput();
if(MouseInput.isRightButtonPressed()){
Vector2f deltaPos = MouseInput.getDeltaPos();
camera.AddRotation((float)Math.toRadians(-deltaPos.y * MOUSE_SENSITIVITY),(float)Math.toRadians(-deltaPos.x * MOUSE_SENSITIVITY),0);
}
}
@Override
public void Input(EngineInstance engineInstance, long FrameDiffNanoSeconds) {
Scene scene = engineInstance.scene();
Window window = engineInstance.window();
KeyboardInput input = window.getKeyboardInput();
float MovementDist = (float)(FrameDiffNanoSeconds / 1000000L) * MOVEMENT_SPEED;
Camera camera = scene.GetCamera();
if(input.keyPressed(GLFW_KEY_W)){
camera.MoveForward(MovementDist);
}
if(input.keyPressed(GLFW_KEY_S)){
camera.MoveBackward(MovementDist);
}
if(input.keyPressed(GLFW_KEY_A)){
camera.MoveLeft(MovementDist);
}
if(input.keyPressed(GLFW_KEY_D)){
camera.MoveRight(MovementDist);
}
if(input.keyPressed(GLFW_KEY_SPACE)){
camera.MoveUp(MovementDist);
}
if(input.keyPressed(GLFW_KEY_LEFT_SHIFT)){
camera.MoveDown(MovementDist);
}
} }
@Override @Override
public void Update(EngineInstance engineInstance, long FrameDiffNanoSeconds) { public void Update(EngineInstance engineInstance, long FrameDiffNanoSeconds) {
float DeltaTime = (float)(FrameDiffNanoSeconds/16000000.0); float DeltaTime = (float)(FrameDiffNanoSeconds/16000000.0);
for(int i = 0; i < angles.size()/2; i++) { for(int i = 0; i < angles.size()/2; i++) {
angles.set(i, (angles.get(i) + 1.0f* DeltaTime) % 360); angles.set(i, (angles.get(i) + 0.1f* DeltaTime) % 360);
CubeActors.get(i).GetRotation().identity().rotateAxis((float) EngineConfig.DegToRad * angles.get(i), rotatingAngle); Camera camera = engineInstance.scene().GetCamera();
CubeActors.get(i).GetPosition().add((Velocities.get(i).x/100.0f) * DeltaTime,(Velocities.get(i).y/100.0f) * DeltaTime,(Velocities.get(i).z/100.0f) * DeltaTime); CubeActors.get(i).GetRotation().identity().rotateAxis((float) EngineConfig.DegToRad * angles.get(i), rotatingAngles.get(i));
//CubeActors.get(i).GetPosition().add((Velocities.get(i).x/100.0f) * DeltaTime,(Velocities.get(i).y/100.0f) * DeltaTime,(Velocities.get(i).z/100.0f) * DeltaTime);
CubeActors.get(i).UpdateModelMatrix(); CubeActors.get(i).UpdateModelMatrix();
} }
} }
@ -68,9 +128,9 @@ public class GameCore implements GameLogic {
float DeltaTime = (float)(FrameDiffNanoSeconds/16000000.0); float DeltaTime = (float)(FrameDiffNanoSeconds/16000000.0);
for(int i = angles.size()/2; i < angles.size(); i++) { for(int i = angles.size()/2; i < angles.size(); i++) {
angles.set(i, (angles.get(i) + 1.0f* DeltaTime) % 360); angles.set(i, (angles.get(i) + 1.0f* DeltaTime) % 360);
CubeActors.get(i).GetRotation().identity().rotateAxis((float) EngineConfig.DegToRad * angles.get(i), rotatingAngle); CubeActors.get(i).GetRotation().identity().rotateAxis((float) EngineConfig.DegToRad * angles.get(i), rotatingAngles.get(i));
CubeActors.get(i).GetPosition().add((Velocities.get(i).x/100.0f) * DeltaTime,(Velocities.get(i).y/100.0f) * DeltaTime,(Velocities.get(i).z/100.0f) * DeltaTime); // CubeActors.get(i).GetPosition().add((Velocities.get(i).x/100.0f) * DeltaTime,(Velocities.get(i).y/100.0f) * DeltaTime,(Velocities.get(i).z/100.0f) * DeltaTime);
CubeActors.get(i).UpdateModelMatrix(); CubeActors.get(i).UpdateModelMatrix();
} }
} }
} }

View file

@ -27,9 +27,11 @@ public class PrimaryRuntime {
private static long OriginalFrameAccuracy; private static long OriginalFrameAccuracy;
private static boolean CappedToTickRate = false; private static boolean CappedToTickRate = false;
public final CPUMonitor cpuProfiler; public final CPUMonitor cpuProfiler;
private static GameLogic gameLogic;
public PrimaryRuntime(String windowTitle, GameLogic appLogic) { public PrimaryRuntime(String windowTitle, GameLogic appLogic) {
window = new Window(windowTitle); window = new Window(windowTitle);
gameLogic = appLogic;
engineInstance = new EngineInstance(window, new Scene(window)); engineInstance = new EngineInstance(window, new Scene(window));
InitData initData = appLogic.Initialise(engineInstance); InitData initData = appLogic.Initialise(engineInstance);
PrimaryThread = new MainThread(engineInstance, appLogic); PrimaryThread = new MainThread(engineInstance, appLogic);
@ -59,6 +61,10 @@ public class PrimaryRuntime {
} }
} }
public void PrimaryRuntimeInputUpdate(long nsTimeDiff){
gameLogic.CameraInput(PrimaryRuntime.GetEngineInstance(), (nsTimeDiff));
}
public void run(){ public void run(){
UpdateTickRateThreshold(); UpdateTickRateThreshold();
long InitialTime = System.nanoTime(); long InitialTime = System.nanoTime();
@ -85,6 +91,7 @@ public class PrimaryRuntime {
if (TickDiff >= TickRate) { if (TickDiff >= TickRate) {
TickFrames++; TickFrames++;
long nsTimeDiff = now - updateTime; long nsTimeDiff = now - updateTime;
PrimaryRuntimeInputUpdate(nsTimeDiff);
updateTime = now; updateTime = now;
TickDiff = 0; TickDiff = 0;
} }

View file

@ -0,0 +1,80 @@
package net.halbear.Terrain4J.EngineCore.Main.Scene;
import org.joml.Matrix4f;
import org.joml.Vector3f;
public class Camera {
private final Vector3f Direction;
private final Vector3f Position;
private final Vector3f Right;
private final Vector3f Rotation;
private final Vector3f Up;
private final Matrix4f ViewMatrix;
public Camera(){
Direction = new Vector3f();
Position = new Vector3f();
Right = new Vector3f();
Rotation = new Vector3f();
Up = new Vector3f();
ViewMatrix = new Matrix4f();
}
public void SetRotation(float x, float y, float z){Rotation.set(x,y,z); Recalculate();}
public void AddRotation(float x, float y, float z){Rotation.add(x,y,z); Recalculate();}
public void AddRotX(float x){Rotation.x += x; Recalculate();}
public void AddRotY(float y){Rotation.y += y; Recalculate();}
public void AddRotZ(float z){Rotation.z += z; Recalculate();}
public Vector3f GetRotation(){return Rotation;}
public void SetPosition(float x, float y, float z){Position.set(x,y,z); Recalculate();}
public void AddPosition(float x, float y, float z){Position.add(x,y,z);Recalculate(); }
public void AddPosX(float x){Position.x += x;Recalculate();}
public void AddPosY(float y){Position.y += y;Recalculate();}
public void AddPosZ(float z){Position.z += z;Recalculate();}
public Vector3f GetPosition(){return Position;}
public Matrix4f GetViewMatrix(){
return ViewMatrix;
}
public void MoveForward(float Distance){
ViewMatrix.positiveZ(Direction).negate().mul(Distance);
Position.add(Direction);
Recalculate();
}
public void MoveBackward(float Distance){
ViewMatrix.positiveZ(Direction).negate().mul(Distance);
Position.sub(Direction);
Recalculate();
}
public void MoveUp(float Distance){
ViewMatrix.positiveY(Up).negate().mul(Distance);
Position.sub(Up);
Recalculate();
}
public void MoveDown(float Distance){
ViewMatrix.positiveY(Up).negate().mul(Distance);
Position.add(Up);
Recalculate();
}
public void MoveLeft(float Distance){
ViewMatrix.positiveX(Right).negate().mul(Distance);
Position.add(Right);
Recalculate();
}
public void MoveRight(float Distance){
ViewMatrix.positiveX(Right).negate().mul(Distance);
Position.sub(Right);
Recalculate();
}
public void Recalculate(){
ViewMatrix.identity()
.rotateX(Rotation.x)
.rotateY(Rotation.y)
//.rotateZ(Rotation.z)
.translate(-Position.x, -Position.y, -Position.z);
}
}

View file

@ -11,14 +11,16 @@ public class Scene {
private final List<Actor> Actors; private final List<Actor> Actors;
private final Project3D Projection; private final Project3D Projection;
private final Camera camera;
public Scene(Window window) { public Scene(Window window) {
Actors = new ArrayList<>(); Actors = new ArrayList<>();
var EngConfig = EngineConfig.getInstance(); var EngConfig = EngineConfig.getInstance();
Projection = new Project3D(EngConfig.GetFOV(),EngConfig.GetZNearPlane(), EngConfig.GetZFarPlane(), Projection = new Project3D(EngConfig.GetFOV(),EngConfig.GetZNearPlane(), EngConfig.GetZFarPlane(),
window.getWidth(), window.getHeight()); window.getWidth(), window.getHeight());
camera = new Camera();
} }
public Camera GetCamera(){return camera;}
public void AddActor(Actor NewActor){Actors.add(NewActor);} public void AddActor(Actor NewActor){Actors.add(NewActor);}
public List<Actor> GetActors(){return Actors;} public List<Actor> GetActors(){return Actors;}
public Project3D GetProjection(){return Projection;} public Project3D GetProjection(){return Projection;}

View file

@ -0,0 +1,7 @@
package net.halbear.Terrain4J.EngineCore.Main.Util.Maths;
public class T4Math {
public static double Log2(int n){
return Math.log(n) / Math.log(n);
}
}

View file

@ -14,7 +14,6 @@ public class MainThread extends EngineThread {
} }
@Override @Override
public void FrameEvent(long now, long InitialTime){ public void FrameEvent(long now, long InitialTime){
gameLogic.Input(PrimaryRuntime.GetEngineInstance(), (now - InitialTime));
} }
@Override @Override
public void CycleEvent(){ public void CycleEvent(){

View file

@ -24,6 +24,7 @@ public class RenderThread extends EngineThread {
} }
@Override @Override
public void FrameEvent(long now, long InitialTime){ public void FrameEvent(long now, long InitialTime){
gameLogic.Input(PrimaryRuntime.GetEngineInstance(), (now - InitialTime));
render.render(PrimaryRuntime.GetEngineInstance()); render.render(PrimaryRuntime.GetEngineInstance());
} }
@Override @Override

View file

@ -1,18 +1,20 @@
package net.halbear.Terrain4J.EngineCore.Vulkan.Rendering.Pipeline.Images; package net.halbear.Terrain4J.EngineCore.Vulkan.Rendering.Pipeline.Images;
import net.halbear.Terrain4J.EngineCore.Logic.Rendering.VulkanContext; import net.halbear.Terrain4J.EngineCore.Logic.Rendering.VulkanContext;
import net.halbear.Terrain4J.EngineCore.Main.Util.Maths.T4Math;
import net.halbear.Terrain4J.EngineCore.Vulkan.Structure.DeviceLayers.CommandBuffer; import net.halbear.Terrain4J.EngineCore.Vulkan.Structure.DeviceLayers.CommandBuffer;
import net.halbear.Terrain4J.EngineCore.Vulkan.Structure.DisplayToScreen.ImageView; import net.halbear.Terrain4J.EngineCore.Vulkan.Structure.DisplayToScreen.ImageView;
import net.halbear.Terrain4J.EngineCore.Vulkan.Util.VulkanBuffer; import net.halbear.Terrain4J.EngineCore.Vulkan.Util.VulkanBuffer;
import net.halbear.Terrain4J.EngineCore.Vulkan.Util.VulkanUtils; import net.halbear.Terrain4J.EngineCore.Vulkan.Util.VulkanUtils;
import org.lwjgl.system.MemoryStack; import org.lwjgl.system.MemoryStack;
import org.lwjgl.system.MemoryUtil; import org.lwjgl.system.MemoryUtil;
import org.lwjgl.vulkan.VkBufferImageCopy; import org.lwjgl.vulkan.*;
import java.nio.ByteBuffer; import java.nio.ByteBuffer;
import static org.lwjgl.vulkan.VK10.*; import static org.lwjgl.vulkan.VK10.*;
import static org.lwjgl.vulkan.VK13.VK_ACCESS_2_NONE; import static org.lwjgl.vulkan.VK13.VK_ACCESS_2_NONE;
import static org.lwjgl.vulkan.VK13.vkCmdPipelineBarrier2;
public class Texture { public class Texture {
@ -22,6 +24,7 @@ public class Texture {
private final Image image; private final Image image;
private final ImageView imageView; private final ImageView imageView;
private boolean RecordedTransition; private boolean RecordedTransition;
private boolean Transparent;
private VulkanBuffer stgBuffer; private VulkanBuffer stgBuffer;
public Texture(VulkanContext VkCtx, String ID, ImageSrc imageSrc, int ImageFormat){ public Texture(VulkanContext VkCtx, String ID, ImageSrc imageSrc, int ImageFormat){
@ -29,17 +32,30 @@ public class Texture {
RecordedTransition = false; RecordedTransition = false;
Width = imageSrc.Width(); Width = imageSrc.Width();
Height = imageSrc.Height(); Height = imageSrc.Height();
SetTransparency(imageSrc.data());
int MipMapLevels = (int) Math.floor(T4Math.Log2(Math.min(Width, Height))) + 1;
CreateStgBuffer(VkCtx, imageSrc.data()); CreateStgBuffer(VkCtx, imageSrc.data());
var ImageData = new Image.ImageData().Width(Width).Height(Height) var ImageData = new Image.ImageData().Width(Width).Height(Height)
.Usage(VK_IMAGE_USAGE_TRANSFER_SRC_BIT | VK_IMAGE_USAGE_TRANSFER_DST_BIT | VK_IMAGE_USAGE_SAMPLED_BIT) .Usage(VK_IMAGE_USAGE_TRANSFER_SRC_BIT | VK_IMAGE_USAGE_TRANSFER_DST_BIT | VK_IMAGE_USAGE_SAMPLED_BIT)
.Format(ImageFormat); .Format(ImageFormat).MipMapLevels(MipMapLevels);
image = new Image(VkCtx, ImageData); image = new Image(VkCtx, ImageData);
var ImageViewData = new ImageView.ImageViewData().Format(image.GetFormat()) var ImageViewData = new ImageView.ImageViewData().Format(image.GetFormat())
.AspectMask(VK_IMAGE_ASPECT_COLOR_BIT); .AspectMask(VK_IMAGE_ASPECT_COLOR_BIT).MipLevels(MipMapLevels);
imageView = new ImageView(VkCtx.GetDevice(), image.getVulkanImage(), ImageViewData, false); imageView = new ImageView(VkCtx.GetDevice(), image.getVulkanImage(), ImageViewData, false);
} }
public boolean HasTransparency(){return Transparent;}
public void SetTransparency(ByteBuffer data){
int PixelCount = data.capacity()/4;
int Offset = 0;
Transparent = false;
for(int i = 0; i < PixelCount; i++){
int alpha = (0xFF & data.get(Offset + 3));
if( alpha < 255){
Transparent = true;
}
Offset += 4;
}
}
public void CreateStgBuffer(VulkanContext VkCtx, ByteBuffer data){ public void CreateStgBuffer(VulkanContext VkCtx, ByteBuffer data){
int Size = data.remaining(); int Size = data.remaining();
stgBuffer = new VulkanBuffer(VkCtx, Size, VK_BUFFER_USAGE_TRANSFER_SRC_BIT, VK_MEMORY_PROPERTY_HOST_VISIBLE_BIT | VK_MEMORY_PROPERTY_HOST_COHERENT_BIT); stgBuffer = new VulkanBuffer(VkCtx, Size, VK_BUFFER_USAGE_TRANSFER_SRC_BIT, VK_MEMORY_PROPERTY_HOST_VISIBLE_BIT | VK_MEMORY_PROPERTY_HOST_COHERENT_BIT);
@ -58,13 +74,84 @@ public class Texture {
VK_IMAGE_LAYOUT_UNDEFINED, VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, VK_PIPELINE_STAGE_TOP_OF_PIPE_BIT, VK_IMAGE_LAYOUT_UNDEFINED, VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, VK_PIPELINE_STAGE_TOP_OF_PIPE_BIT,
VK_PIPELINE_STAGE_TRANSFER_BIT, VK_ACCESS_2_NONE, VK_ACCESS_TRANSFER_WRITE_BIT, VK_IMAGE_ASPECT_COLOR_BIT); VK_PIPELINE_STAGE_TRANSFER_BIT, VK_ACCESS_2_NONE, VK_ACCESS_TRANSFER_WRITE_BIT, VK_IMAGE_ASPECT_COLOR_BIT);
RecordCopyBuffer(MemStack, commandBuffer, stgBuffer); RecordCopyBuffer(MemStack, commandBuffer, stgBuffer);
VulkanUtils.ImageBarrier(MemStack, commandBuffer.GetVulkanCommandBuffer(), image.getVulkanImage(), RecordGenerateMipMaps(MemStack, commandBuffer);
VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL,VK_PIPELINE_STAGE_TRANSFER_BIT,
VK_PIPELINE_STAGE_FRAGMENT_SHADER_BIT, VK_ACCESS_TRANSFER_WRITE_BIT, VK_ACCESS_SHADER_READ_BIT,VK_IMAGE_ASPECT_COLOR_BIT);
} }
} }
} }
private void RecordGenerateMipMaps(MemoryStack MemStack, CommandBuffer commandBuffer){
VkImageSubresourceRange SubResourceRange = VkImageSubresourceRange.calloc(MemStack)
.aspectMask(VK_IMAGE_ASPECT_COLOR_BIT)
.baseArrayLayer(0)
.levelCount(1)
.layerCount(1);
VkImageMemoryBarrier2.Buffer ImageMemoryBarrierBuffer = VkImageMemoryBarrier2.calloc(1,MemStack)
.sType$Default()
.image(image.getVulkanImage())
.srcQueueFamilyIndex(VK_QUEUE_FAMILY_IGNORED)
.dstQueueFamilyIndex(VK_QUEUE_FAMILY_IGNORED)
.subresourceRange(SubResourceRange);
VkDependencyInfo dependencyInfo = VkDependencyInfo.calloc(MemStack)
.sType$Default()
.pImageMemoryBarriers(ImageMemoryBarrierBuffer);
int MipMapWidth = Width;
int MipMapHeight = Height;
int MipMapLevels = image.GetMipLevels();
for(int i = 1; i < MipMapLevels; i++){
SubResourceRange.baseMipLevel(i - 1);
ImageMemoryBarrierBuffer.subresourceRange(SubResourceRange)
.oldLayout(VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL)
.newLayout(VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL)
.srcStageMask(VK_PIPELINE_STAGE_TRANSFER_BIT)
.dstStageMask(VK_PIPELINE_STAGE_TRANSFER_BIT)
.srcAccessMask(VK_ACCESS_TRANSFER_WRITE_BIT)
.dstAccessMask(VK_ACCESS_TRANSFER_READ_BIT);
vkCmdPipelineBarrier2(commandBuffer.GetVulkanCommandBuffer(),dependencyInfo);
int auxi = i;
VkOffset3D srcOffset0 = VkOffset3D.calloc(MemStack).x(0).y(0).z(0);
VkOffset3D srcOffset1 = VkOffset3D.calloc(MemStack).x(MipMapWidth).y(MipMapHeight).z(1);
VkOffset3D dstOffset0 = VkOffset3D.calloc(MemStack).x(0).y(0).z(0);
VkOffset3D dstOffset1 = VkOffset3D.calloc(MemStack)
.x(MipMapWidth > 1 ? MipMapWidth/2 : 1).y(MipMapHeight > 1 ? MipMapHeight/2 : 1).z(1);
VkImageBlit.Buffer BlitBuffer = VkImageBlit.calloc(1,MemStack)
.srcOffsets(0,srcOffset0)
.srcOffsets(1,srcOffset1)
.srcSubresource(it -> it.aspectMask(VK_IMAGE_ASPECT_COLOR_BIT)
.mipLevel(auxi - 1)
.baseArrayLayer(0)
.layerCount(1))
.dstOffsets(0,dstOffset0)
.dstOffsets(1,dstOffset1)
.dstSubresource(it -> it.aspectMask(VK_IMAGE_ASPECT_COLOR_BIT)
.mipLevel(auxi)
.baseArrayLayer(0)
.layerCount(1));
vkCmdBlitImage(commandBuffer.GetVulkanCommandBuffer(),image.getVulkanImage(),VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL,
image.getVulkanImage(),VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL,BlitBuffer,VK_FILTER_LINEAR);
ImageMemoryBarrierBuffer.oldLayout(VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL).newLayout(VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL)
.srcAccessMask(VK_ACCESS_TRANSFER_READ_BIT).dstAccessMask(VK_ACCESS_SHADER_READ_BIT);
ImageMemoryBarrierBuffer.srcStageMask(VK_PIPELINE_STAGE_TRANSFER_BIT).dstAccessMask(VK_PIPELINE_STAGE_FRAGMENT_SHADER_BIT);
vkCmdPipelineBarrier2(commandBuffer.GetVulkanCommandBuffer(),dependencyInfo);
if(MipMapWidth > 1) MipMapWidth/=2;
if(MipMapHeight > 1) MipMapHeight/=2;
}
ImageMemoryBarrierBuffer.subresourceRange(it -> it.baseMipLevel(MipMapLevels - 1))
.oldLayout(VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL)
.newLayout(VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL)
.srcStageMask(VK_PIPELINE_STAGE_TRANSFER_BIT)
.dstAccessMask(VK_PIPELINE_STAGE_FRAGMENT_SHADER_BIT)
.srcAccessMask(VK_ACCESS_TRANSFER_WRITE_BIT)
.dstAccessMask(VK_ACCESS_SHADER_READ_BIT);
vkCmdPipelineBarrier2(commandBuffer.GetVulkanCommandBuffer(), dependencyInfo);
}
private void RecordCopyBuffer(MemoryStack MemStack, CommandBuffer commandBuffer, VulkanBuffer bufferData){ private void RecordCopyBuffer(MemoryStack MemStack, CommandBuffer commandBuffer, VulkanBuffer bufferData){
VkBufferImageCopy.Buffer Region = VkBufferImageCopy.calloc(1, MemStack) VkBufferImageCopy.Buffer Region = VkBufferImageCopy.calloc(1, MemStack)
.bufferOffset(0) .bufferOffset(0)
@ -77,6 +164,9 @@ public class Texture {
.layerCount(1) .layerCount(1)
).imageOffset(it->it.x(0).y(0).z(0)) ).imageOffset(it->it.x(0).y(0).z(0))
.imageExtent(it->it.width(Width).height(Height).depth(1)); .imageExtent(it->it.width(Width).height(Height).depth(1));
vkCmdCopyBufferToImage(commandBuffer.GetVulkanCommandBuffer(), bufferData.GetBuffer(), image.getVulkanImage(),
VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, Region);
} }
public void CleanUp(VulkanContext VkCtx){ public void CleanUp(VulkanContext VkCtx){

View file

@ -54,20 +54,6 @@ public class Pipeline {
var MultisampleStateCreateInfo = VkPipelineMultisampleStateCreateInfo.calloc(MemStack) var MultisampleStateCreateInfo = VkPipelineMultisampleStateCreateInfo.calloc(MemStack)
.sType$Default() .sType$Default()
.rasterizationSamples(VK_SAMPLE_COUNT_1_BIT); .rasterizationSamples(VK_SAMPLE_COUNT_1_BIT);
VkPipelineDynamicStateCreateInfo VulkanPipelineDynamicStateCreateInfo = VkPipelineDynamicStateCreateInfo.calloc(MemStack)
.sType(VK_STRUCTURE_TYPE_PIPELINE_DYNAMIC_STATE_CREATE_INFO)
.pDynamicStates(MemStack.ints(
VK_DYNAMIC_STATE_VIEWPORT,
VK_DYNAMIC_STATE_SCISSOR
));
var BlendAttributeState = VkPipelineColorBlendAttachmentState.calloc(1,MemStack)
.colorWriteMask(VK_COLOR_COMPONENT_R_BIT | VK_COLOR_COMPONENT_G_BIT | VK_COLOR_COMPONENT_B_BIT | VK_COLOR_COMPONENT_A_BIT)
.blendEnable(false);
var ColourBlendState = VkPipelineColorBlendStateCreateInfo.calloc(MemStack)
.sType$Default()
.pAttachments(BlendAttributeState);
IntBuffer ColourFormats = MemStack.mallocInt(1);
ColourFormats.put(0,BuildInfo.GetColourFormat());
VkPipelineDepthStencilStateCreateInfo DepthStencil = null; VkPipelineDepthStencilStateCreateInfo DepthStencil = null;
if(BuildInfo.GetDepthFormat() != VK_FORMAT_UNDEFINED){ if(BuildInfo.GetDepthFormat() != VK_FORMAT_UNDEFINED){
@ -80,12 +66,14 @@ public class Pipeline {
.stencilTestEnable(false); .stencilTestEnable(false);
} }
var RendererCreateInfo = VkPipelineRenderingCreateInfo.calloc(MemStack)
.sType$Default()
.colorAttachmentCount(1)
.pColorAttachmentFormats(ColourFormats);
if(DepthStencil != null){RendererCreateInfo.depthAttachmentFormat(BuildInfo.GetDepthFormat());} VkPipelineDynamicStateCreateInfo VulkanPipelineDynamicStateCreateInfo = VkPipelineDynamicStateCreateInfo.calloc(MemStack)
.sType$Default()
.pDynamicStates(MemStack.ints(
VK_DYNAMIC_STATE_VIEWPORT,
VK_DYNAMIC_STATE_SCISSOR
));
VkPushConstantRange.Buffer VkPushConstRangeBuffer = null; VkPushConstantRange.Buffer VkPushConstRangeBuffer = null;
PushConstantsRange[] PushConstRanges = BuildInfo.GetPushConstantRanges(); PushConstantsRange[] PushConstRanges = BuildInfo.GetPushConstantRanges();
@ -100,13 +88,37 @@ public class Pipeline {
.size(pushConstantsRange.Size()); .size(pushConstantsRange.Size());
} }
} }
DescriptorSetLayout[] descriptorSetLayouts = BuildInfo.GetDescriptorSetLayouts(); DescriptorSetLayout[] descriptorSetLayouts = BuildInfo.GetDescriptorSetLayouts();
int LayoutCount = descriptorSetLayouts != null ? descriptorSetLayouts.length : 0; int LayoutCount = descriptorSetLayouts != null ? descriptorSetLayouts.length : 0;
LongBuffer ppLayout = MemStack.mallocLong(LayoutCount); LongBuffer ppLayout = MemStack.mallocLong(LayoutCount);
for(int i = 0; i < LayoutCount; i++){ for(int i = 0; i < LayoutCount; i++){
ppLayout.put(i, descriptorSetLayouts[i].GetVkDescriptorLayout()); ppLayout.put(i, descriptorSetLayouts[i].GetVkDescriptorLayout());
} }
var BlendAttributeState = VkPipelineColorBlendAttachmentState.calloc(1,MemStack)
.colorWriteMask(VK_COLOR_COMPONENT_R_BIT | VK_COLOR_COMPONENT_G_BIT | VK_COLOR_COMPONENT_B_BIT | VK_COLOR_COMPONENT_A_BIT)
.blendEnable(BuildInfo.BlendingUsed());
if(BuildInfo.BlendingUsed()){
BlendAttributeState.get(0).colorBlendOp(VK_BLEND_OP_ADD)
.alphaBlendOp(VK_BLEND_OP_ADD)
.srcColorBlendFactor(VK_BLEND_FACTOR_SRC_ALPHA)
.dstColorBlendFactor(VK_BLEND_FACTOR_ONE_MINUS_SRC_ALPHA)
.srcAlphaBlendFactor(VK_BLEND_FACTOR_SRC_ALPHA)
.dstAlphaBlendFactor(VK_BLEND_FACTOR_ZERO);
}
var ColourBlendState = VkPipelineColorBlendStateCreateInfo.calloc(MemStack)
.sType$Default()
.pAttachments(BlendAttributeState);
IntBuffer ColourFormats = MemStack.mallocInt(1);
ColourFormats.put(0,BuildInfo.GetColourFormat());
var RendererCreateInfo = VkPipelineRenderingCreateInfo.calloc(MemStack)
.sType$Default()
.colorAttachmentCount(1)
.pColorAttachmentFormats(ColourFormats);
if(DepthStencil != null){RendererCreateInfo.depthAttachmentFormat(BuildInfo.GetDepthFormat());}
var PipelineLayoutCreateInfoPtr = VkPipelineLayoutCreateInfo.calloc(MemStack) var PipelineLayoutCreateInfoPtr = VkPipelineLayoutCreateInfo.calloc(MemStack)
.sType$Default() .sType$Default()

View file

@ -14,12 +14,14 @@ public class PipelineBuildInfo {
private int DepthFormat; private int DepthFormat;
private PushConstantsRange[] PushConstRanges; private PushConstantsRange[] PushConstRanges;
private DescriptorSetLayout[] DescriptorSetLayouts; private DescriptorSetLayout[] DescriptorSetLayouts;
private boolean useBlend;
public PipelineBuildInfo(ShaderModule[] shaderModules, VkPipelineVertexInputStateCreateInfo VertexInput, int ColourFormat){ public PipelineBuildInfo(ShaderModule[] shaderModules, VkPipelineVertexInputStateCreateInfo VertexInput, int ColourFormat){
this.ColourFormat = ColourFormat; this.ColourFormat = ColourFormat;
this.ShaderModules = shaderModules; this.ShaderModules = shaderModules;
this.VertexInput = VertexInput; this.VertexInput = VertexInput;
DepthFormat = VK_FORMAT_UNDEFINED; DepthFormat = VK_FORMAT_UNDEFINED;
useBlend = true;
} }
public DescriptorSetLayout[] GetDescriptorSetLayouts(){return DescriptorSetLayouts;} public DescriptorSetLayout[] GetDescriptorSetLayouts(){return DescriptorSetLayouts;}
@ -29,6 +31,14 @@ public class PipelineBuildInfo {
return this; return this;
} }
public boolean BlendingUsed(){
return useBlend;
}
public PipelineBuildInfo BlendingIsUsed(boolean useBlend) {
this.useBlend = useBlend;
return this;
}
public PipelineBuildInfo SetDepthFormat(int DepthFormat){ public PipelineBuildInfo SetDepthFormat(int DepthFormat){
this.DepthFormat = DepthFormat; this.DepthFormat = DepthFormat;
return this; return this;

View file

@ -10,6 +10,7 @@ import org.lwjgl.vulkan.VkDescriptorSetAllocateInfo;
import org.lwjgl.vulkan.VkWriteDescriptorSet; import org.lwjgl.vulkan.VkWriteDescriptorSet;
import java.nio.LongBuffer; import java.nio.LongBuffer;
import java.util.ArrayList;
import java.util.List; import java.util.List;
import static net.halbear.Terrain4J.EngineCore.Vulkan.Util.VulkanUtils.vkCheck; import static net.halbear.Terrain4J.EngineCore.Vulkan.Util.VulkanUtils.vkCheck;
@ -51,7 +52,12 @@ public class DescriptorSet {
} }
} }
public void SetImage(Device device, List<ImageView> imageViews, TextureSampler textureSampler, int BaseBinding){ public void SetImage(Device device, ImageView imageView, TextureSampler textureSampler, int BaseBinding){
List<ImageView> imageViews = new ArrayList<>();
imageViews.add(imageView);
SetImages(device, imageViews, textureSampler, BaseBinding);
}
public void SetImages(Device device, List<ImageView> imageViews, TextureSampler textureSampler, int BaseBinding){
try(var MemStack = MemoryStack.stackPush()){ try(var MemStack = MemoryStack.stackPush()){
int ImageCount = imageViews.size(); int ImageCount = imageViews.size();
var DescriptorBuffer = VkWriteDescriptorSet.calloc(ImageCount,MemStack); var DescriptorBuffer = VkWriteDescriptorSet.calloc(ImageCount,MemStack);

View file

@ -1,6 +1,7 @@
package net.halbear.Terrain4J.EngineCore.Vulkan.Rendering.VkModel; package net.halbear.Terrain4J.EngineCore.Vulkan.Rendering.VkModel;
import net.halbear.Terrain4J.EngineCore.Logic.Rendering.VulkanContext; import net.halbear.Terrain4J.EngineCore.Logic.Rendering.VulkanContext;
import net.halbear.Terrain4J.EngineCore.Vulkan.Rendering.Pipeline.Images.Texture;
import net.halbear.Terrain4J.EngineCore.Vulkan.Rendering.Pipeline.Images.TextureCache; import net.halbear.Terrain4J.EngineCore.Vulkan.Rendering.Pipeline.Images.TextureCache;
import net.halbear.Terrain4J.EngineCore.Vulkan.Rendering.Pipeline.IndexedLinkedHashMap; import net.halbear.Terrain4J.EngineCore.Vulkan.Rendering.Pipeline.IndexedLinkedHashMap;
import net.halbear.Terrain4J.EngineCore.Vulkan.Structure.DeviceLayers.CommandBuffer; import net.halbear.Terrain4J.EngineCore.Vulkan.Structure.DeviceLayers.CommandBuffer;
@ -49,14 +50,19 @@ public class MaterialsCache {
var Material = Materials.get(i); var Material = Materials.get(i);
String TexturePath = Material.TexturePath(); String TexturePath = Material.TexturePath();
boolean ValidTexture = TexturePath != null && !TexturePath.isEmpty(); boolean ValidTexture = TexturePath != null && !TexturePath.isEmpty();
boolean TransparentTexture;
if(ValidTexture){ if(ValidTexture){
Logger.debug("Loading Texture [{}]",TexturePath); Logger.debug("Loading Texture [{}]",TexturePath);
textureCache.AddTexture(VkCtx, TexturePath, TexturePath, VK_FORMAT_R8G8B8A8_SRGB); Texture newTexture = textureCache.AddTexture(VkCtx, TexturePath, TexturePath, VK_FORMAT_R8G8B8A8_SRGB);
TransparentTexture = newTexture.HasTransparency();
} else{
TransparentTexture = Material.DiffuseColour().w < 1.0f;
} }
VulkanMaterial newMaterial = new VulkanMaterial(Material.ID()); VulkanMaterial newMaterial = new VulkanMaterial(Material.ID(),TransparentTexture);
MaterialsMap.put(newMaterial.ID(), newMaterial); MaterialsMap.put(newMaterial.ID(), newMaterial);
Logger.trace(Material.toString()); Logger.trace(Material.toString());
Material.DiffuseColour().get(Offset, data); data.position(Offset);
Material.DiffuseColour().get(data);
Logger.debug("Set Diffuse Colour -> [{}]",Material.DiffuseColour()); Logger.debug("Set Diffuse Colour -> [{}]",Material.DiffuseColour());
data.putInt(Offset + VulkanUtils.VEC4_SIZE, ValidTexture ? 1 : 0); data.putInt(Offset + VulkanUtils.VEC4_SIZE, ValidTexture ? 1 : 0);
data.putInt(Offset + VulkanUtils.VEC4_SIZE + VulkanUtils.INT_SIZE, textureCache.GetPosition(TexturePath)); data.putInt(Offset + VulkanUtils.VEC4_SIZE + VulkanUtils.INT_SIZE, textureCache.GetPosition(TexturePath));
@ -66,6 +72,8 @@ public class MaterialsCache {
data.putInt(Offset + VulkanUtils.VEC4_SIZE + VulkanUtils.INT_SIZE * 3,0); data.putInt(Offset + VulkanUtils.VEC4_SIZE + VulkanUtils.INT_SIZE * 3,0);
Offset += MATERIAL_SIZE; Offset += MATERIAL_SIZE;
} }
data.position(0);
SrcBuffer.UnMapMemory(VkCtx); SrcBuffer.UnMapMemory(VkCtx);
transferBuffer.RecordTransferCommand(CmdBuffer); transferBuffer.RecordTransferCommand(CmdBuffer);
CmdBuffer.EndRecording(); CmdBuffer.EndRecording();

View file

@ -0,0 +1,4 @@
package net.halbear.Terrain4J.EngineCore.Vulkan.Rendering.VkModel;
public class ProceduralMesh {
}

View file

@ -1,4 +1,4 @@
package net.halbear.Terrain4J.EngineCore.Vulkan.Rendering.VkModel; package net.halbear.Terrain4J.EngineCore.Vulkan.Rendering.VkModel;
public record VulkanMaterial(String ID) { public record VulkanMaterial(String ID, boolean HasTransparency) {
} }

View file

@ -41,6 +41,7 @@ public class SceneRender {//dynamic rendering
private static final String DESCRIPTOR_ID_MAT = "SCN_DESC_ID_MAT"; private static final String DESCRIPTOR_ID_MAT = "SCN_DESC_ID_MAT";
private static final String DESCRIPTOR_ID_PRJ = "SCN_DESC_ID_PRJ"; private static final String DESCRIPTOR_ID_PRJ = "SCN_DESC_ID_PRJ";
private static final String DESCRIPTOR_ID_TEXT = "SCN_DESC_ID_TEXT"; private static final String DESCRIPTOR_ID_TEXT = "SCN_DESC_ID_TEXT";
private static final String DESCRIPTOR_ID_VIEW = "SCN_DESC_ID_VIEW";
private static final int PUSH_CONSTANTS_SIZE = VulkanUtils.MATRIX4X4_SIZE + VulkanUtils.INT_SIZE; private static final int PUSH_CONSTANTS_SIZE = VulkanUtils.MATRIX4X4_SIZE + VulkanUtils.INT_SIZE;
private final VulkanBuffer BufferProjectionMatrix; private final VulkanBuffer BufferProjectionMatrix;
private final DescriptorSetLayout descriptorLayoutFragStorage; private final DescriptorSetLayout descriptorLayoutFragStorage;
@ -69,15 +70,20 @@ public class SceneRender {//dynamic rendering
private static final String FRAGMENT_SHADER_FILE_SPV = FRAGMENT_SHADER_FILE_GLSL + ".spv"; private static final String FRAGMENT_SHADER_FILE_SPV = FRAGMENT_SHADER_FILE_GLSL + ".spv";
private static final String VERTEX_SHADER_FILE_GLSL = "resources/shaders/scene_vertex.glsl"; private static final String VERTEX_SHADER_FILE_GLSL = "resources/shaders/scene_vertex.glsl";
private static final String VERTEX_SHADER_FILE_SPV = VERTEX_SHADER_FILE_GLSL + ".spv"; private static final String VERTEX_SHADER_FILE_SPV = VERTEX_SHADER_FILE_GLSL + ".spv";
private final VulkanBuffer[] BufferViewMatrices;
private final Pipeline VkPipeline; private final Pipeline VkPipeline;
public SceneRender(VulkanContext vulkanContext){ public SceneRender(VulkanContext vulkanContext){
ClearValueDepth = VkClearValue.calloc().color(c->c.float32(0,1.0f)); ClearValueColour = VkClearValue.calloc().color(
c -> c.float32(0, 0.0f).float32(1, 0.0f).float32(2, 0.0f).float32(3, 0.0f));
//ClearValueDepth = VkClearValue.calloc().color(c -> c.float32(0, 1.0f));
ClearValueDepth = VkClearValue.calloc().depthStencil(c -> c.depth(1.0f).stencil());
AttDepth = createDepthAttachments(vulkanContext); AttDepth = createDepthAttachments(vulkanContext);
AttInfoDepth = createDepthAttachmentsInfo(vulkanContext, AttDepth, ClearValueDepth); AttInfoDepth = createDepthAttachmentsInfo(vulkanContext, AttDepth, ClearValueDepth);
ClearValueColour = VkClearValue.calloc().color(c->c.float32(0,R).float32(1,G).float32(2,B).float32(3,1.0f)); ClearValueColour = VkClearValue.calloc().color(c->c.float32(0,R).float32(1,G).float32(2,B).float32(3,1.0f));
AttachmentInfoColour = CreateColourAttachmentsInfo(vulkanContext,ClearValueColour); AttachmentInfoColour = CreateColourAttachmentsInfo(vulkanContext,ClearValueColour);
RenderInfo = CreateRenderInfo(vulkanContext, AttachmentInfoColour, AttInfoDepth); RenderInfo = CreateRenderInfo(vulkanContext, AttachmentInfoColour, AttInfoDepth);
ShaderModule[] shaderModules = SceneRender.CreateShaderModules(vulkanContext);
PushConstBuffer = (MemoryUtil.memAlloc(PUSH_CONSTANTS_SIZE)); PushConstBuffer = (MemoryUtil.memAlloc(PUSH_CONSTANTS_SIZE));
descriptorLayoutVertexUniform = new DescriptorSetLayout(vulkanContext, new DescriptorSetLayout.LayoutInformation(VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER, descriptorLayoutVertexUniform = new DescriptorSetLayout(vulkanContext, new DescriptorSetLayout.LayoutInformation(VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER,
@ -93,12 +99,16 @@ public class SceneRender {//dynamic rendering
descriptorLayoutTexture = new DescriptorSetLayout(vulkanContext, new DescriptorSetLayout.LayoutInformation( descriptorLayoutTexture = new DescriptorSetLayout(vulkanContext, new DescriptorSetLayout.LayoutInformation(
VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER, 0, TextureCache.MAX_TEXTURES, VK_SHADER_STAGE_FRAGMENT_BIT VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER, 0, TextureCache.MAX_TEXTURES, VK_SHADER_STAGE_FRAGMENT_BIT
)); ));
DescriptorSetLayout[] layouts = new DescriptorSetLayout[]{
descriptorLayoutVertexUniform,
descriptorLayoutVertexUniform,
descriptorLayoutFragStorage,
descriptorLayoutTexture
};
ShaderModule[] shaderModules = SceneRender.CreateShaderModules(vulkanContext); BufferViewMatrices = VulkanUtils.CreateHostVisibleBuffers(vulkanContext, VulkanUtils.MATRIX4X4_SIZE, VulkanUtils.MAX_IN_FLIGHT, VK_BUFFER_USAGE_UNIFORM_BUFFER_BIT, DESCRIPTOR_ID_VIEW, descriptorLayoutVertexUniform);
VkPipeline = CreatePipeline(vulkanContext, shaderModules, new DescriptorSetLayout[]{
descriptorLayoutVertexUniform, descriptorLayoutFragStorage, descriptorLayoutFragStorage VkPipeline = CreatePipeline(vulkanContext, shaderModules, layouts);
});
//Continue Here
Arrays.asList(shaderModules).forEach(shaderModule -> shaderModule.CleanUp(vulkanContext)); Arrays.asList(shaderModules).forEach(shaderModule -> shaderModule.CleanUp(vulkanContext));
} }
@ -122,7 +132,7 @@ public class SceneRender {//dynamic rendering
var Attachments = VkRenderingAttachmentInfo.calloc() var Attachments = VkRenderingAttachmentInfo.calloc()
.sType$Default() .sType$Default()
.imageView(DepthAttachments[i].GetVkImageView().GetVulkanImageView()) .imageView(DepthAttachments[i].GetVkImageView().GetVulkanImageView())
.imageLayout(VK_IMAGE_LAYOUT_STENCIL_ATTACHMENT_OPTIMAL) .imageLayout(VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL)
.loadOp(VK_ATTACHMENT_LOAD_OP_CLEAR) .loadOp(VK_ATTACHMENT_LOAD_OP_CLEAR)
.storeOp(VK_ATTACHMENT_STORE_OP_DONT_CARE) .storeOp(VK_ATTACHMENT_STORE_OP_DONT_CARE)
.clearValue(clearValue); .clearValue(clearValue);
@ -134,7 +144,7 @@ public class SceneRender {//dynamic rendering
private static ShaderModule[] CreateShaderModules(VulkanContext VkCtx){ private static ShaderModule[] CreateShaderModules(VulkanContext VkCtx){
if(EngineConfig.getInstance().RecompileShaders()){ if(EngineConfig.getInstance().RecompileShaders()){
ShaderCompiler.CompileGLSLShaderOnChange(VERTEX_SHADER_FILE_GLSL, Shaderc.shaderc_glsl_vertex_shader); ShaderCompiler.CompileGLSLShaderOnChange(VERTEX_SHADER_FILE_GLSL, Shaderc.shaderc_glsl_vertex_shader);
ShaderCompiler.CompileGLSLShaderOnChange(FRAGMENT_SHADER_FILE_GLSL, Shaderc.shaderc_fragment_shader); ShaderCompiler.CompileGLSLShaderOnChange(FRAGMENT_SHADER_FILE_GLSL, Shaderc.shaderc_glsl_fragment_shader);
} }
return new ShaderModule[]{ return new ShaderModule[]{
new ShaderModule(VkCtx, VK_SHADER_STAGE_VERTEX_BIT, VERTEX_SHADER_FILE_SPV), new ShaderModule(VkCtx, VK_SHADER_STAGE_VERTEX_BIT, VERTEX_SHADER_FILE_SPV),
@ -148,11 +158,12 @@ public class SceneRender {//dynamic rendering
VkCtx.GetSurface().GetSurfaceFormat().ImageFormat()) VkCtx.GetSurface().GetSurfaceFormat().ImageFormat())
.SetDepthFormat(DEPTH_FORMAT) .SetDepthFormat(DEPTH_FORMAT)
.SetPushConstantRanges( .SetPushConstantRanges(
new PushConstantsRange[]{ new PushConstantsRange[]{
new PushConstantsRange(VK_SHADER_STAGE_VERTEX_BIT,0,VulkanUtils.MATRIX4X4_SIZE * 2), new PushConstantsRange(VK_SHADER_STAGE_VERTEX_BIT,0,VulkanUtils.MATRIX4X4_SIZE),
new PushConstantsRange(VK_SHADER_STAGE_FRAGMENT_BIT,VulkanUtils.MATRIX4X4_SIZE,VulkanUtils.INT_SIZE) new PushConstantsRange(VK_SHADER_STAGE_FRAGMENT_BIT,VulkanUtils.MATRIX4X4_SIZE,VulkanUtils.INT_SIZE)
}) })
.SetDescriptorSetLayouts(DescriptorSetLayouts); .SetDescriptorSetLayouts(DescriptorSetLayouts)
.BlendingIsUsed(true);
var pipeline = new Pipeline(VkCtx, BuildInfo); var pipeline = new Pipeline(VkCtx, BuildInfo);
vertexBufferStructure.cleanup(); vertexBufferStructure.cleanup();
return pipeline; return pipeline;
@ -180,12 +191,12 @@ public class SceneRender {//dynamic rendering
if (B >0.0f&& Math.random() <0.7) B-=0.0005f; if (B >0.0f&& Math.random() <0.7) B-=0.0005f;
else if (B <= 0.0f) Bb = true; else if (B <= 0.0f) Bb = true;
} }
ClearValueColour = VkClearValue.calloc().color(c->c.float32(0,R).float32(1,G).float32(2,B).float32(3,1.0f)); //ClearValueColour = VkClearValue.calloc().color(c->c.float32(0,R).float32(1,G).float32(2,B).float32(3,1.0f));
AttachmentInfoColour = CreateColourAttachmentsInfo(vulkanContext,ClearValueColour); //AttachmentInfoColour = CreateColourAttachmentsInfo(vulkanContext,ClearValueColour);
RenderInfo = CreateRenderInfo(vulkanContext, AttachmentInfoColour, AttInfoDepth); //RenderInfo = CreateRenderInfo(vulkanContext, AttachmentInfoColour, AttInfoDepth);
} }
public void Render(EngineInstance engineInstance,VulkanContext vulkanContext, CommandBuffer commandBuffer, ModelsCache modelsCache,MaterialsCache materialsCache, int ImageIndex){ public void Render(EngineInstance engineInstance,VulkanContext vulkanContext, CommandBuffer commandBuffer, ModelsCache modelsCache,MaterialsCache materialsCache, int ImageIndex, int CurrentFrame){
UpdateColours(vulkanContext); UpdateColours(vulkanContext);
try(var MemStack = MemoryStack.stackPush()){ try(var MemStack = MemoryStack.stackPush()){
SwapChain swapChain = vulkanContext.GetSwapChain(); SwapChain swapChain = vulkanContext.GetSwapChain();
@ -219,22 +230,38 @@ public class SceneRender {//dynamic rendering
vkCmdSetViewport(CommandHandle, 0, Viewport); vkCmdSetViewport(CommandHandle, 0, Viewport);
var Scissor = VkRect2D.calloc(1,MemStack) var Scissor = VkRect2D.calloc(1,MemStack)
.extent(it -> it.width(width).height(height)) .extent(it -> it.width(width).height(height))
.offset(it->it.x(0).y(0)); .offset(it->it.x(0).y(0));
vkCmdSetScissor(CommandHandle, 0, Scissor); vkCmdSetScissor(CommandHandle, 0, Scissor);
LongBuffer offsets = MemStack.mallocLong(1).put(0,0L); VulkanUtils.CopyMatrixToBuffer(vulkanContext, BufferViewMatrices[CurrentFrame],engineInstance.scene().GetCamera().GetViewMatrix(), 0);
LongBuffer vertexBuffer = MemStack.mallocLong(1);
Scene scene = engineInstance.scene();
List<Actor> Actors = scene.GetActors();
int ActorCount = Actors.size();
DescriptorAllocator descriptorAllocator = vulkanContext.GetDescriptorAllocator(); DescriptorAllocator descriptorAllocator = vulkanContext.GetDescriptorAllocator();
LongBuffer DescriptorSets = MemStack.mallocLong(3) LongBuffer DescriptorSets = MemStack.mallocLong(4)
.put(0,descriptorAllocator.GetDescriptorSet(DESCRIPTOR_ID_PRJ).GetVkDescriptorSet()) .put(0,descriptorAllocator.GetDescriptorSet(DESCRIPTOR_ID_PRJ).GetVkDescriptorSet())
.put(1,descriptorAllocator.GetDescriptorSet(DESCRIPTOR_ID_MAT).GetVkDescriptorSet()) .put(1,descriptorAllocator.GetDescriptorSet(DESCRIPTOR_ID_VIEW).GetVkDescriptorSet())
.put(2,descriptorAllocator.GetDescriptorSet(DESCRIPTOR_ID_TEXT).GetVkDescriptorSet()); .put(2,descriptorAllocator.GetDescriptorSet(DESCRIPTOR_ID_MAT).GetVkDescriptorSet())
.put(3,descriptorAllocator.GetDescriptorSet(DESCRIPTOR_ID_TEXT).GetVkDescriptorSet());
vkCmdBindDescriptorSets(CommandHandle, VK_PIPELINE_BIND_POINT_GRAPHICS, VkPipeline.GetVulkanPipelineLayout(),0,DescriptorSets,null); vkCmdBindDescriptorSets(CommandHandle, VK_PIPELINE_BIND_POINT_GRAPHICS, VkPipeline.GetVulkanPipelineLayout(),0,DescriptorSets,null);
RenderActors(engineInstance, CommandHandle, modelsCache, materialsCache, false);
RenderActors(engineInstance, CommandHandle, modelsCache, materialsCache, true);
vkCmdEndRendering(CommandHandle);
VulkanUtils.ImageBarrier(MemStack, CommandHandle, SwapChainImage,
VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL, VK_IMAGE_LAYOUT_PRESENT_SRC_KHR,
VK_PIPELINE_STAGE_2_COLOR_ATTACHMENT_OUTPUT_BIT, VK_PIPELINE_STAGE_2_BOTTOM_OF_PIPE_BIT,
VK_ACCESS_2_COLOR_ATTACHMENT_READ_BIT | VK_ACCESS_2_COLOR_ATTACHMENT_WRITE_BIT, VK_PIPELINE_STAGE_2_NONE,
VK_IMAGE_ASPECT_COLOR_BIT);
}
}
private void RenderActors(EngineInstance instance, VkCommandBuffer CommandHandle, ModelsCache modelsCache, MaterialsCache materialsCache, boolean Transparent){
try(var MemStack = MemoryStack.stackPush()){
LongBuffer offsets = MemStack.mallocLong(1).put(0,0L);
LongBuffer vertexBuffer = MemStack.mallocLong(1);
Scene scene = instance.scene();
List<Actor> Actors = scene.GetActors();
int ActorCount = Actors.size();
for(int i = 0; i < ActorCount; i++){ for(int i = 0; i < ActorCount; i++){
var Actor = Actors.get(i); var Actor = Actors.get(i);
@ -250,22 +277,18 @@ public class SceneRender {//dynamic rendering
Logger.warn("Mesh [{}] in model [{}] does not have material",j,model.GetID()); Logger.warn("Mesh [{}] in model [{}] does not have material",j,model.GetID());
continue; continue;
} }
SetPushConstants(CommandHandle, Actor.GetModelMatrix(),MaterialIndex); if(vulkanMaterial.HasTransparency() == Transparent) {
vertexBuffer.put(0,VkMesh.VerticesBuffer().GetBuffer()); SetPushConstants(CommandHandle, Actor.GetModelMatrix(), MaterialIndex);
vkCmdBindVertexBuffers(CommandHandle,0,vertexBuffer,offsets); vertexBuffer.put(0, VkMesh.VerticesBuffer().GetBuffer());
vkCmdBindIndexBuffer(CommandHandle,VkMesh.IndicesBuffer().GetBuffer(),0,VK_INDEX_TYPE_UINT32); vkCmdBindVertexBuffers(CommandHandle, 0, vertexBuffer, offsets);
vkCmdDrawIndexed(CommandHandle,VkMesh.IndicesCount(),1,0,0,0); vkCmdBindIndexBuffer(CommandHandle, VkMesh.IndicesBuffer().GetBuffer(), 0, VK_INDEX_TYPE_UINT32);
vkCmdDrawIndexed(CommandHandle, VkMesh.IndicesCount(), 1, 0, 0, 0);
}
} }
} }
vkCmdEndRendering(CommandHandle);
VulkanUtils.ImageBarrier(MemStack, CommandHandle, SwapChainImage,
VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL, VK_IMAGE_LAYOUT_PRESENT_SRC_KHR,
VK_PIPELINE_STAGE_2_COLOR_ATTACHMENT_OUTPUT_BIT, VK_PIPELINE_STAGE_2_BOTTOM_OF_PIPE_BIT,
VK_ACCESS_2_COLOR_ATTACHMENT_READ_BIT | VK_ACCESS_2_COLOR_ATTACHMENT_WRITE_BIT, VK_PIPELINE_STAGE_2_NONE,
VK_IMAGE_ASPECT_COLOR_BIT);
} }
} }
private void SetPushConstants(VkCommandBuffer CmdHandle, Matrix4f ModelMatrix, int MaterialIndex){ private void SetPushConstants(VkCommandBuffer CmdHandle, Matrix4f ModelMatrix, int MaterialIndex){
ModelMatrix.get(0,PushConstBuffer); ModelMatrix.get(0,PushConstBuffer);
PushConstBuffer.putInt(VulkanUtils.MATRIX4X4_SIZE, MaterialIndex); PushConstBuffer.putInt(VulkanUtils.MATRIX4X4_SIZE, MaterialIndex);
@ -328,6 +351,7 @@ public class SceneRender {//dynamic rendering
.imageView(swapChain.GetVulkanImageView(i).GetVulkanImageView()) .imageView(swapChain.GetVulkanImageView(i).GetVulkanImageView())
.imageLayout(VK_IMAGE_LAYOUT_ATTACHMENT_OPTIMAL_KHR) .imageLayout(VK_IMAGE_LAYOUT_ATTACHMENT_OPTIMAL_KHR)
.loadOp(VK_ATTACHMENT_LOAD_OP_CLEAR) .loadOp(VK_ATTACHMENT_LOAD_OP_CLEAR)
.storeOp(VK_ATTACHMENT_STORE_OP_STORE)
.clearValue(CLearValue); .clearValue(CLearValue);
result[i] = Attachments; result[i] = Attachments;
} }
@ -336,6 +360,7 @@ public class SceneRender {//dynamic rendering
public void cleanup(VulkanContext VkCtx){ public void cleanup(VulkanContext VkCtx){
VkPipeline.CleanUp(VkCtx); VkPipeline.CleanUp(VkCtx);
Arrays.asList(RenderInfo).forEach(VkRenderingInfo::free); Arrays.asList(RenderInfo).forEach(VkRenderingInfo::free);
Arrays.asList(BufferViewMatrices).forEach(buffer -> buffer.cleanup(VkCtx));
Arrays.asList(AttachmentInfoColour).forEach(VkRenderingAttachmentInfo.Buffer::free); Arrays.asList(AttachmentInfoColour).forEach(VkRenderingAttachmentInfo.Buffer::free);
Arrays.asList(AttInfoDepth).forEach(VkRenderingAttachmentInfo::free); Arrays.asList(AttInfoDepth).forEach(VkRenderingAttachmentInfo::free);
Arrays.asList(AttachmentInfoColour).forEach(VkRenderingAttachmentInfo.Buffer::free); Arrays.asList(AttachmentInfoColour).forEach(VkRenderingAttachmentInfo.Buffer::free);

View file

@ -1,6 +1,7 @@
package net.halbear.Terrain4J.EngineCore.Vulkan.Util; package net.halbear.Terrain4J.EngineCore.Vulkan.Util;
import net.halbear.Terrain4J.EngineCore.Logic.Rendering.VulkanContext; import net.halbear.Terrain4J.EngineCore.Logic.Rendering.VulkanContext;
import net.halbear.Terrain4J.EngineCore.Vulkan.Rendering.Shader.DescriptorAllocator;
import net.halbear.Terrain4J.EngineCore.Vulkan.Rendering.Shader.DescriptorSet; import net.halbear.Terrain4J.EngineCore.Vulkan.Rendering.Shader.DescriptorSet;
import net.halbear.Terrain4J.EngineCore.Vulkan.Rendering.Shader.DescriptorSetLayout; import net.halbear.Terrain4J.EngineCore.Vulkan.Rendering.Shader.DescriptorSetLayout;
import net.halbear.Terrain4J.EngineCore.Vulkan.Structure.DeviceLayers.Device; import net.halbear.Terrain4J.EngineCore.Vulkan.Structure.DeviceLayers.Device;
@ -29,6 +30,21 @@ public class VulkanUtils {
matrix.get(Offset, matrixBuffer); matrix.get(Offset, matrixBuffer);
VkBuffer.UnMapMemory(VkCtx); VkBuffer.UnMapMemory(VkCtx);
} }
public static VulkanBuffer[] CreateHostVisibleBuffers(VulkanContext VkCtx, long BufferSize, int BufferCount, int Usage, String ID, DescriptorSetLayout layout){
DescriptorAllocator descriptorAllocator = VkCtx.GetDescriptorAllocator();
Device device = VkCtx.GetDevice();
VulkanBuffer[] Result = new VulkanBuffer[BufferCount];
descriptorAllocator.AddDescriptorSets(device, ID, BufferCount, layout);
DescriptorSetLayout.LayoutInformation LayoutInfo = layout.GetLayoutInfo();
for(int i = 0; i < BufferCount; i++){
Result[i] = new VulkanBuffer(VkCtx, BufferSize, Usage, VK_MEMORY_PROPERTY_HOST_VISIBLE_BIT | VK_MEMORY_PROPERTY_HOST_COHERENT_BIT);
DescriptorSet descriptorSet = descriptorAllocator.GetDescriptorSet(ID, i);
descriptorSet.SetBuffer(device, Result[i], Result[i].GetRequestedSize(), layout.GetLayoutInfo().Binding(),layout.GetLayoutInfo().DescriptorType());
}
return Result;
}
public static VulkanBuffer CreateHostVisibleBuffer(VulkanContext VkCtx, long BufferSize, int Usage, String ID, DescriptorSetLayout layout){ public static VulkanBuffer CreateHostVisibleBuffer(VulkanContext VkCtx, long BufferSize, int Usage, String ID, DescriptorSetLayout layout){
var Buffer = new VulkanBuffer(VkCtx, BufferSize, Usage, VK_MEMORY_PROPERTY_HOST_VISIBLE_BIT | VK_MEMORY_PROPERTY_HOST_COHERENT_BIT); var Buffer = new VulkanBuffer(VkCtx, BufferSize, Usage, VK_MEMORY_PROPERTY_HOST_VISIBLE_BIT | VK_MEMORY_PROPERTY_HOST_COHERENT_BIT);
Device device = VkCtx.GetDevice(); Device device = VkCtx.GetDevice();