Browse Source

Added Triangle Rasterizer.

angel 7 years ago
parent
commit
90b96631b8
6 changed files with 67 additions and 16 deletions
  1. 3 3
      CMakeLists.txt
  2. 4 2
      include/rasterizer.h
  3. 4 0
      include/texture.h
  4. 41 2
      src/rasterizer.cpp
  5. 4 7
      src/renderManager.cpp
  6. 11 2
      src/texture.cpp

+ 3 - 3
CMakeLists.txt

@@ -10,9 +10,9 @@ include_directories(${SDL2_INCLUDE_DIR} include)
 file(GLOB source_files "*.h" "*.cpp" "src/*.cpp" "include/*.h")
 file(GLOB source_files "*.h" "*.cpp" "src/*.cpp" "include/*.h")
 
 
 add_executable(softwareRenderer ${source_files})
 add_executable(softwareRenderer ${source_files})
-#set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -pg")
-#set(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} -pg")
-#set(CMAKE_SHARED_LINKER_FLAGS "${CMAKE_SHARED_LINKER_FLAGS} -pg")
+#set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -g")
+#set(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} -g")
+#set(CMAKE_SHARED_LINKER_FLAGS "${CMAKE_SHARED_LINKER_FLAGS} -g")
 target_link_libraries(softwareRenderer ${SDL2_LIBRARY})
 target_link_libraries(softwareRenderer ${SDL2_LIBRARY})
 
 
 if(WIN32)
 if(WIN32)

+ 4 - 2
include/rasterizer.h

@@ -10,7 +10,9 @@ class Rasterizer{
     public:
     public:
         Rasterizer(Canvas *canvas) :mCanvas(canvas){}
         Rasterizer(Canvas *canvas) :mCanvas(canvas){}
 
 
-        void drawModels(Vector3 &v1, Vector3 &v2, Vector3 &v3);
+        void drawTriangles(Vector3 &v1, Vector3 &v2, Vector3 &v3);
+
+        void drawWireFrame(Vector3 &v1, Vector3 &v2, Vector3 &v3);
 
 
         void testPattern();
         void testPattern();
 
 
@@ -23,7 +25,7 @@ class Rasterizer{
 
 
         Uint32 getPixelColor(int x, int y);
         Uint32 getPixelColor(int x, int y);
 
 
-        void drawLine(Vector3 vertex1, Vector3 vertex2, Uint32 color);
+        void drawLine(Vector3 &vertex1, Vector3 &vertex2, Uint32 &color);
 
 
         void setPixelColor(Uint32 color, int x, int y);
         void setPixelColor(Uint32 color, int x, int y);
 
 

+ 4 - 0
include/texture.h

@@ -26,6 +26,10 @@ class Texture{
         int mWidth;
         int mWidth;
         int mHeight;
         int mHeight;
 
 
+        //Only used to lock and unlock pixels, not  the actual pixel
+         //values
+        void* mPixels;
+
 };
 };
 
 
 #endif
 #endif

+ 41 - 2
src/rasterizer.cpp

@@ -1,5 +1,7 @@
 #include "rasterizer.h"
 #include "rasterizer.h"
 #include "vector"
 #include "vector"
+#include "array"
+#include <algorithm>
 
 
 const SDL_PixelFormat* Rasterizer::mappingFormat( SDL_AllocFormat(PIXEL_FORMAT));
 const SDL_PixelFormat* Rasterizer::mappingFormat( SDL_AllocFormat(PIXEL_FORMAT));
 
 
@@ -30,13 +32,50 @@ void Rasterizer::testPattern(){
 }
 }
 
 
 //Should probably do something fancier in the future
 //Should probably do something fancier in the future
-void Rasterizer::drawModels(Vector3 &v1, Vector3 &v2, Vector3 &v3 ){
+void Rasterizer::drawTriangles(Vector3 &v0, Vector3 &v1, Vector3 &v2 ){
+    std::array<int, 3> xVerts;
+    std::array<int, 3> yVerts;
+    xVerts[0] = (v0.x + 1 ) * mCanvas->mWidth * 0.5;
+    yVerts[0] = (-v0.y + 1 ) * mCanvas->mHeight * 0.5;
+
+    xVerts[1] = (v1.x +1 ) * mCanvas->mWidth  * 0.5;
+    yVerts[1] = (-v1.y +1 ) * mCanvas->mHeight * 0.5;
+
+    xVerts[2] = (v2.x +1 ) * mCanvas->mWidth  * 0.5;
+    yVerts[2] = (-v2.y +1 ) * mCanvas->mHeight * 0.5;
+
+    int xMax = *std::max_element(xVerts.begin(),xVerts.end());
+    int yMax = *std::max_element(yVerts.begin(),yVerts.end());
+
+    int xMin = *std::min_element(xVerts.begin(),xVerts.end());
+    int yMin = *std::min_element(yVerts.begin(),yVerts.end());
+
+
+    for(int y = yMin; y < yMax; ++y){
+        for(int x = xMin; x < xMax; ++x){
+            float edge1 = (x-xVerts[0])*(yVerts[1]-yVerts[0]) 
+                            - (xVerts[1]-xVerts[0])*(y-yVerts[0]);
+            float edge2 = (x-xVerts[1])*(yVerts[2]-yVerts[1]) 
+                            - (xVerts[2]-xVerts[1])*(y-yVerts[1]);
+            float edge3 = (x-xVerts[2])*(yVerts[0]-yVerts[2]) 
+                            - (xVerts[0]-xVerts[2])*(y-yVerts[2]);
+
+            if(edge1 >= 0 && edge2 >= 0 && edge3 >= 0){
+                setPixelColor(white, x, y);
+            } 
+        
+        }
+    }
+    
+}   
+
+void Rasterizer::drawWireFrame(Vector3 &v1, Vector3 &v2, Vector3 &v3 ){
     drawLine(v1, v2, red);
     drawLine(v1, v2, red);
     drawLine(v2, v3, green);
     drawLine(v2, v3, green);
     drawLine(v1, v3, blue);
     drawLine(v1, v3, blue);
 }   
 }   
 
 
-void Rasterizer::drawLine(Vector3 vertex1, Vector3 vertex2, Uint32 color){
+void Rasterizer::drawLine(Vector3 &vertex1, Vector3 &vertex2, Uint32 &color){
 
 
         int x1 = (vertex1.x + 1 ) * mCanvas->mWidth * 0.5;
         int x1 = (vertex1.x + 1 ) * mCanvas->mWidth * 0.5;
         int y1 = (-vertex1.y + 1 ) * mCanvas->mHeight * 0.5;
         int y1 = (-vertex1.y + 1 ) * mCanvas->mHeight * 0.5;

+ 4 - 7
src/renderManager.cpp

@@ -89,6 +89,7 @@ void RenderManager::render(Model *models, Matrix4 &viewMatrix){
     std::vector<Vector3> * faces = &modelMesh->faces;
     std::vector<Vector3> * faces = &modelMesh->faces;
     std::vector<Vector3> * vertices = &modelMesh->vertices;
     std::vector<Vector3> * vertices = &modelMesh->vertices;
 
 
+    //Kind of a vertex shader I guess?
     for (Vector3 f : *faces ){
     for (Vector3 f : *faces ){
         Vector3 v1 = viewProjectionMatrix.matMultVec((*vertices)[f.x-1]); //-1 because .obj file starts face count
         Vector3 v1 = viewProjectionMatrix.matMultVec((*vertices)[f.x-1]); //-1 because .obj file starts face count
         Vector3 v2 = viewProjectionMatrix.matMultVec((*vertices)[f.y-1]); // from 1. Should probably fix this 
         Vector3 v2 = viewProjectionMatrix.matMultVec((*vertices)[f.y-1]); // from 1. Should probably fix this 
@@ -96,14 +97,10 @@ void RenderManager::render(Model *models, Matrix4 &viewMatrix){
         if(v1.x < -1 || v1.x > 1 || v1.y < -1 || v1.y > 1 || v1.z > 1 || v1.z < -1) continue;
         if(v1.x < -1 || v1.x > 1 || v1.y < -1 || v1.y > 1 || v1.z > 1 || v1.z < -1) continue;
         if(v2.x < -1 || v2.x > 1 || v2.y < -1 || v2.y > 1 || v2.z > 1 || v2.z < -1) continue;
         if(v2.x < -1 || v2.x > 1 || v2.y < -1 || v2.y > 1 || v2.z > 1 || v2.z < -1) continue;
         if(v3.x < -1 || v3.x > 1 || v3.y < -1 || v3.y > 1 || v3.z > 1 || v3.z < -1) continue;
         if(v3.x < -1 || v3.x > 1 || v3.y < -1 || v3.y > 1 || v3.z > 1 || v3.z < -1) continue;
-
-        raster->drawModels(v1,v2,v3);
+       
+        //Rasterizing
+        raster->drawTriangles(v1,v2,v3);
     }
     }
-
-
-    //Rasterizing
-    
-
     //Apply the pixel changes and redraw
     //Apply the pixel changes and redraw
     updateScreen();
     updateScreen();
 }
 }

+ 11 - 2
src/texture.cpp

@@ -26,13 +26,22 @@ bool Texture::createBlank(SDL_Renderer  *renderer, int width, int height ){
     mHeight = height;
     mHeight = height;
     mPitch  = width * sizeof(Uint32);
     mPitch  = width * sizeof(Uint32);
     mTexture = SDL_CreateTexture(renderer, SDL_PIXELFORMAT_RGBA8888,
     mTexture = SDL_CreateTexture(renderer, SDL_PIXELFORMAT_RGBA8888,
-        SDL_TEXTUREACCESS_STATIC, mWidth, mHeight);
+        SDL_TEXTUREACCESS_STREAMING, mWidth, mHeight);
 
 
     return mTexture != NULL;
     return mTexture != NULL;
 }
 }
 
 
 void Texture::updateTexture(Uint32 * pixels){
 void Texture::updateTexture(Uint32 * pixels){
-    SDL_UpdateTexture(mTexture, NULL, pixels, mPitch);
+
+    //Lock texture for manipulation
+    SDL_LockTexture(mTexture, NULL, &mPixels, &mPitch );
+    //Copy pixels to texture
+    memcpy(mPixels, pixels, mHeight*mPitch);
+
+    //Update texture
+    SDL_UnlockTexture(mTexture);
+    mPixels = nullptr;
+    //SDL_UpdateTexture(mTexture, NULL, pixels, mPitch);
 }
 }
 
 
 void Texture::renderToScreen(SDL_Renderer * renderer){
 void Texture::renderToScreen(SDL_Renderer * renderer){