diff --git a/CMakeLists.txt b/CMakeLists.txt
index 76d31905..be8b71c4 100644
--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -49,9 +49,9 @@ elseif(TARGET_TYPE STREQUAL game)
     ${ASSETS_SOURCE_DIR}/shared/shaders/textured.vert shaders/textured.vert
     ${ASSETS_SOURCE_DIR}/shared/shaders/textured.frag shaders/textured.frag
   )
-  tool_copy(shader_test
-    ${ASSETS_SOURCE_DIR}/shared/shaders/test.vert shaders/test.vert
-    ${ASSETS_SOURCE_DIR}/shared/shaders/test.frag shaders/test.frag
+  tool_copy(shader_singlerenderlist
+    ${ASSETS_SOURCE_DIR}/shared/shaders/singlerenderlist.vert shaders/singlerenderlist.vert
+    ${ASSETS_SOURCE_DIR}/shared/shaders/singlerenderlist.frag shaders/singlerenderlist.frag
   )
 
   # Fonts
@@ -86,20 +86,20 @@ elseif(TARGET_TYPE STREQUAL game)
     # Characters
     set(DIR_CHARS "${ASSETS_SOURCE_DIR}/poker/characters")
     tool_vn_character(vn_penny
-      ${DIR_CHARS}/penny/character.xml ${DIR_CHARS}/penny.png
-    )
-    tool_vn_character(vn_lucy
-      ${DIR_CHARS}/lucy/character.xml ${DIR_CHARS}/lucy.png
-    )
-    tool_vn_character(vn_julie
-      ${DIR_CHARS}/julie/character.xml ${DIR_CHARS}/julie.png
-    )
-    tool_vn_character(vn_sammy
-      ${DIR_CHARS}/sammy/character.xml ${DIR_CHARS}/sammy.png
-    )
-    tool_vn_character(vn_jenny
-      ${DIR_CHARS}/jenny/character.xml ${DIR_CHARS}/jenny.png
+      ${DIR_CHARS}/penny/character.xml poker/characters/penny/sprite
     )
+    # tool_vn_character(vn_lucy
+    #   ${DIR_CHARS}/lucy/character.xml poker/characters/lucy/sprite
+    # )
+    # tool_vn_character(vn_julie
+    #   ${DIR_CHARS}/julie/character.xml poker/characters/julie/sprite
+    # )
+    # tool_vn_character(vn_sammy
+    #   ${DIR_CHARS}/sammy/character.xml poker/characters/sammy/sprite
+    # )
+    # tool_vn_character(vn_jenny
+    #   ${DIR_CHARS}/jenny/character.xml poker/characters/jenny/sprite
+    # )
 
     # World
     tool_copy(texture_pub
@@ -111,16 +111,17 @@ elseif(TARGET_TYPE STREQUAL game)
 
     tool_assets(
       shader_textured
+      shader_singlerenderlist
+
       font_opensans
+
       texture_test
 
       vn_penny
-      vn_lucy
-      vn_julie
-      vn_sammy
-      
-      texture_pub
-      texture_cards
+      # vn_lucy
+      # vn_julie
+      # vn_sammy
+      # vn_jenny
 
       locale_en
     )
@@ -145,9 +146,7 @@ elseif(TARGET_TYPE STREQUAL game)
     tool_assets(
       vn_penny
       vn_sammy
-
       shader_textured
-      shader_test
       font_opensans
       texture_test
     )
diff --git a/assets/shared/shaders/singlerenderlist.frag b/assets/shared/shaders/singlerenderlist.frag
new file mode 100644
index 00000000..4be0b4e0
--- /dev/null
+++ b/assets/shared/shaders/singlerenderlist.frag
@@ -0,0 +1,10 @@
+#version 330 core
+
+in vec2 TexCoord;
+uniform sampler2D u_Text;
+out vec4 FragColor;
+
+void main() {
+  vec4 color1 = texture(u_Text, TexCoord);
+  FragColor = color1;
+}
\ No newline at end of file
diff --git a/assets/shared/shaders/test.vert b/assets/shared/shaders/singlerenderlist.vert
similarity index 78%
rename from assets/shared/shaders/test.vert
rename to assets/shared/shaders/singlerenderlist.vert
index 0aee5e96..77c4c2e7 100644
--- a/assets/shared/shaders/test.vert
+++ b/assets/shared/shaders/singlerenderlist.vert
@@ -10,11 +10,11 @@ layout (location = 1) in vec2 aTexCoord;
 
 uniform mat4 u_Proj;
 uniform mat4 u_View;
-uniform mat4 u_Modl;
+uniform mat4 u_Model;
 
 out vec2 TexCoord;
 
 void main() {
-  gl_Position = u_Proj * u_View * u_Modl * vec4(aPos, 1.0);
+  gl_Position = u_Proj * u_View * u_Model * vec4(aPos, 1.0);
   TexCoord = vec2(aTexCoord.x, aTexCoord.y);
 }
\ No newline at end of file
diff --git a/assets/shared/shaders/test.frag b/assets/shared/shaders/test.frag
deleted file mode 100644
index a99055dd..00000000
--- a/assets/shared/shaders/test.frag
+++ /dev/null
@@ -1,12 +0,0 @@
-#version 330 core
-
-in vec2 TexCoord;
-uniform sampler2D u_Text0;
-uniform sampler2D u_Text1;
-out vec4 FragColor;
-
-void main() {
-  vec4 color1 = texture(u_Text0, TexCoord);
-  vec4 color2 = texture(u_Text1, TexCoord);
-  FragColor = color1 + color2;
-}
\ No newline at end of file
diff --git a/assets/shared/shaders/textured.frag b/assets/shared/shaders/textured.frag
index 78bcd501..3bfc62b7 100644
--- a/assets/shared/shaders/textured.frag
+++ b/assets/shared/shaders/textured.frag
@@ -2,10 +2,9 @@
 
 in vec2 TexCoord;
 uniform sampler2D u_Text;
-uniform vec4 u_Colr;
 out vec4 FragColor;
 
 void main() {
   vec4 color = texture(u_Text, TexCoord);
-  FragColor = color * u_Colr;
+  FragColor = color;
 }
\ No newline at end of file
diff --git a/assets/shared/shaders/textured.vert b/assets/shared/shaders/textured.vert
index 0aee5e96..77c4c2e7 100644
--- a/assets/shared/shaders/textured.vert
+++ b/assets/shared/shaders/textured.vert
@@ -10,11 +10,11 @@ layout (location = 1) in vec2 aTexCoord;
 
 uniform mat4 u_Proj;
 uniform mat4 u_View;
-uniform mat4 u_Modl;
+uniform mat4 u_Model;
 
 out vec2 TexCoord;
 
 void main() {
-  gl_Position = u_Proj * u_View * u_Modl * vec4(aPos, 1.0);
+  gl_Position = u_Proj * u_View * u_Model * vec4(aPos, 1.0);
   TexCoord = vec2(aTexCoord.x, aTexCoord.y);
 }
\ No newline at end of file
diff --git a/assets/shared/textures/test_texture.png b/assets/shared/textures/test_texture.png
index b2835b2d..8b197fdc 100644
Binary files a/assets/shared/textures/test_texture.png and b/assets/shared/textures/test_texture.png differ
diff --git a/src/display/renderlist.c b/src/display/renderlist.c
index 5ac91852..c52e09d6 100644
--- a/src/display/renderlist.c
+++ b/src/display/renderlist.c
@@ -47,9 +47,7 @@ renderpass_t * renderListRenderPass(
 }
 
 void renderListRender(
-  renderlist_t *list, shader_t *shader,
-  shaderuniform_t uniformView, shaderuniform_t uniformProjection,
-  shaderuniform_t uniformModel, shaderuniform_t uniformTextures[]
+  renderlist_t *list, shader_t *shader, shaderuniform_t *uniforms
 ) {
   camera_t camera;
   int32_t i;
@@ -64,21 +62,20 @@ void renderListRender(
 
   // Set the shader
   shaderUse(shader);
-  shaderUsePosition(shader, uniformModel, 0,0,0, 0,0,0);
-  shaderUseCamera(shader, uniformView, uniformProjection, &camera);
+  shaderUseCamera(shader, uniforms[0], uniforms[1], &camera);
+  shaderUsePosition(shader, uniforms[2], 0,0,0, 0,0,0);
 
   // Render each pass.
   for(i = 0; i < list->passCount; i++) {
     pass = renderListGetPass(list, i);
-    shaderUseTexture(shader, uniformTextures[i], &pass->frame.texture);
+    shaderUseTexture(shader, uniforms[3+i], &pass->frame.texture);
     primitiveDraw(&list->quad, 0, -1);
   }
 }
 
 void renderListAsBackbuffer(
   renderlist_t *list, engine_t *engine, shader_t *shader,
-  shaderuniform_t uniformView, shaderuniform_t uniformProjection,
-  shaderuniform_t uniformModel, shaderuniform_t uniformTexture
+  shaderuniform_t *uniforms
 ) {
   camera_t camera;
 
@@ -91,9 +88,9 @@ void renderListAsBackbuffer(
 
   // Set up the shader.
   shaderUse(shader); 
-  shaderUseTexture(shader, uniformTexture, &list->frame.texture);
-  shaderUseCamera(shader, uniformView, uniformProjection, &camera);
-  shaderUsePosition(shader, uniformModel, 0,0,0, 0,0,0);
+  shaderUseCamera(shader, uniforms[0], uniforms[1], &camera);
+  shaderUsePosition(shader, uniforms[2], 0,0,0, 0,0,0);
+  shaderUseTexture(shader, uniforms[3], &list->frame.texture);
 
   // Render the quad to the back buffer.
   primitiveDraw(&list->quad, 0, -1);
diff --git a/src/display/renderlist.h b/src/display/renderlist.h
index 6833866d..3a79e241 100644
--- a/src/display/renderlist.h
+++ b/src/display/renderlist.h
@@ -86,15 +86,10 @@ renderpass_t * renderListRenderPass(
  * 
  * @param list List to render.
  * @param shader Shader to use while rendering.
- * @param uniformView Shader uniform to receive the view matrix.
- * @param uniformProjection Shader uniform to receive the projection matirx.
- * @param uniformModel Shader uniform to receive the model matrix.
- * @param uniformTextures Array of uniforms for each rendered pass as textures.
+ * @param uniforms Uniforms for the render list. [ view, proj, model, ...text ]
  */
 void renderListRender(
-  renderlist_t *list, shader_t *shader,
-  shaderuniform_t uniformView, shaderuniform_t uniformProjection,
-  shaderuniform_t uniformModel, shaderuniform_t uniformTextures[]
+  renderlist_t *list, shader_t *shader, shaderuniform_t *uniforms
 );
 
 /**
@@ -105,15 +100,11 @@ void renderListRender(
  * @param list Render list to render to the backbuffer
  * @param engine Engine to use when rendering.
  * @param shader Shader to use to render to the backbuffer.
- * @param uniformView Shader uniform to receive the view matrix.
- * @param uniformProjection Shader uniform to receive the projection matirx.
- * @param uniformModel Shader uniform to receive the model matrix.
- * @param uniformTexture Shader uniform to receive the texture.
+ * @param uniforms Uniforms for the back buffer. [ view, proj, model, text ]
  */
 void renderListAsBackbuffer(
   renderlist_t *list, engine_t *engine, shader_t *shader,
-  shaderuniform_t uniformView, shaderuniform_t uniformProjection,
-  shaderuniform_t uniformModel, shaderuniform_t uniformTexture
+  shaderuniform_t *uniforms
 );
 
 /**
diff --git a/src/display/shader/shader.c b/src/display/shader/shader.c
index 9949a9f5..e40ed043 100644
--- a/src/display/shader/shader.c
+++ b/src/display/shader/shader.c
@@ -100,7 +100,17 @@ shaderuniform_t shaderGetUniform(shader_t *shader, char *name) {
   for(i = 0; i < shader->uniformCount; i++) {
     if(strcmp(shader->uniformNames[i], name) == 0) return i;
   }
-  return (shaderuniform_t)-1;
+  return (shaderuniform_t)0xFFFFFFFF;
+}
+
+void shaderGetUniformArray(
+  shader_t *shader, shaderuniform_t *uniformSet,
+  char **uniforms, int32_t uniformCount
+) {
+  int32_t i;
+  for(i = 0; i < uniformCount; i++) {
+    uniformSet[i] = shaderGetUniform(shader, uniforms[i]);
+  }
 }
 
 void shaderDispose(shader_t *shader) {
@@ -183,4 +193,4 @@ void shaderUseCamera(
 ) {
   shaderUseMatrix(shader, uniformView, &camera->view);
   shaderUseMatrix(shader, uniformProjection, &camera->projection);
-}
\ No newline at end of file
+}
diff --git a/src/display/shader/shader.h b/src/display/shader/shader.h
index 04b1a655..5c8638ad 100644
--- a/src/display/shader/shader.h
+++ b/src/display/shader/shader.h
@@ -24,7 +24,7 @@ typedef GLuint shaderuniform_t;
  */
 typedef struct {
   /** Pointer to an uploaded vertex shader program */
-  shaderuniform_t shaderVertex;
+  GLuint shaderVertex;
 
   /** Pointer to an uploaded fragment shader program */
   GLuint shaderFrag;
@@ -65,6 +65,19 @@ void shaderInit(shader_t *shader,
  */
 shaderuniform_t shaderGetUniform(shader_t *shader, char *name);
 
+/**
+ * Return an array of shaderuniform_t's into an array for a given string array.
+ * 
+ * @param shader Shader to get the uniforms from.
+ * @param uniformSet Uniform array to get.
+ * @param uniforms Uniform strings to get.
+ * @param uniformCount Count of uniforms you're getting.
+ */
+void shaderGetUniformArray(
+  shader_t *shader, shaderuniform_t *uniformSet,
+  char **uniforms, int32_t uniformCount
+);
+
 /**
  * Cleanup and unload a previously loaded shader.
  * @param shader The shader to unload
@@ -77,8 +90,6 @@ void shaderDispose(shader_t *shader);
  */
 void shaderUse(shader_t *shader);
 
-
-
 /**
  * Attaches a texture to the shader.
  * 
diff --git a/src/display/scaledtexture.h b/src/display/texturescale.h
similarity index 81%
rename from src/display/scaledtexture.h
rename to src/display/texturescale.h
index dd0224e3..c92d3d45 100644
--- a/src/display/scaledtexture.h
+++ b/src/display/texturescale.h
@@ -15,7 +15,7 @@ typedef struct {
   int16_t width;
   int16_t height;
   uint8_t scale;
-} scaledtexturescale_t;
+} texturescalescale_t;
 
 typedef struct {
   uint8_t channels;
@@ -24,6 +24,6 @@ typedef struct {
   int16_t baseWidth;
   int16_t baseHeight;
 
-  scaledtexturescale_t scales[MANAGED_TEXTURE_SCALE_MAX];
+  texturescalescale_t scales[MANAGED_TEXTURE_SCALE_MAX];
   uint8_t scaleCount;
-} scaledtexture_t;
\ No newline at end of file
+} texturescale_t;
\ No newline at end of file
diff --git a/src/engine/thread.c b/src/engine/thread.c
index d9fc41c6..7dc0a79c 100644
--- a/src/engine/thread.c
+++ b/src/engine/thread.c
@@ -27,7 +27,7 @@ void threadCancel(thread_t *thread) {
 }
 
 void threadSleep(float time) {
-  sleep((time * 1000.0f));
+  sleep((unsigned long)(time * 1000.0f));
 }
 
 int32_t _threadWrappedCallback(thread_t *thread) {
diff --git a/src/file/assetmanager.c b/src/file/assetmanager.c
index e2cd2293..45d393df 100644
--- a/src/file/assetmanager.c
+++ b/src/file/assetmanager.c
@@ -25,13 +25,8 @@ assetmanagerloaderdefinition_t ASSET_MANAGER_LOADERS[] = {
   },
   {
     &_assetManagerLoaderScaledTextureAsync,
-    NULL,
-    NULL
-  },
-  {
-    &_assetManagerLoaderTextureScaleAsync,
-    &_assetManagerLoaderTextureScaleSync,
-    &_assetManagerLoaderTextureScaleDispose
+    &_assetManagerLoaderScaledTextureSync,
+    &_assetManagerLoaderScaledTextureDispose
   }
 };
 
@@ -48,15 +43,42 @@ void assetManagerInit(assetmanager_t *manager) {
 float assetManagerProgressGet(assetmanager_t *manager) {
   float done;
   uint8_t i;
+  assetmanageritem_t *item;
 
   done = 0.0f;
-
   for(i = 0; i < manager->itemCount; i++) {
-    if(!assetManagerItemIsFinished(manager->items + i)) continue;
-    done++;
+    item = manager->items + i;
+    done += assetManagerItemIsFinished(
+      item, ASSET_MANAGER_LOADERS + item->type
+    ) ? 1 : 0;
   }
+  return done / ((float)manager->itemCount);
+}
 
-  return done / ((float) manager->itemCount);
+float assetManagerProgressGetForHolder(
+  assetmanager_t *manager, assetmanagerowner_t hold
+) {
+  float done;
+  uint8_t i, j, c;
+  assetmanageritem_t *item;
+  done = 0.0f;
+  c = 0x00;
+  for(i = 0; i < manager->itemCount; i++) {
+    //Is this held by this holder?
+    item = manager->items + i;
+
+    for(j = 0; j < item->holderCount; j++) {
+      if(item->holders[j] != hold) continue;
+      c++;
+      done += assetManagerItemIsFinished(
+        item, ASSET_MANAGER_LOADERS + item->type
+      ) ? 1 : 0;
+      break;
+    }
+  }
+  // Is this thing even holding any assets to begin with?
+  if(c == 0x00) return 1.0f;
+  return done / (float)c;
 }
 
 assetmanagerowner_t assetManagerHolderCreate(assetmanager_t *man) {
@@ -215,328 +237,4 @@ void assetManagerUpdate(assetmanager_t *manager) {
   }
 
   manager->finished = assetManagerProgressGet(manager) >= 1.0f;
-}
-
-assetmanageritem_t * assetManagerItemGet(assetmanager_t *man, char *key) {
-  uint8_t i;
-  assetmanageritem_t *item;
-
-  for(i = 0; i < man->itemCount; i++) {
-    item = man->items + i;
-    if(strcmp(item->key, key) == 0) return item;
-  }
-
-  return NULL;
-}
-
-assetmanageritem_t * assetManagerItemAdd(assetmanager_t *manager, char *key) {
-  // Check if key already exists.
-  assetmanageritem_t *item = manager->items + manager->itemCount++;
-  item->state = ASSET_MANAGER_STATE_NOT_READY;
-  memcpy(item->key, key, strlen(key) + 1);
-  item->holderCount = 0x00;
-  return item;
-}
-
-uint8_t assetManagerItemGetOrAddHolder(
-  assetmanageritem_t *item, assetmanagerowner_t owner
-) {
-  uint8_t i, firstEmpty;
-  firstEmpty = 0xFF;
-
-  for(i = 0; i < item->holderCount; i++) {
-    if(item->holders[i] == owner) return i;
-    if(firstEmpty == 0xFF && item->holders[i] == 0xFF) {
-      firstEmpty = i;
-    }
-  }
-
-  if(firstEmpty == 0xFF) firstEmpty = item->holderCount++;
-  item->holders[firstEmpty] = owner;
-  return firstEmpty;
-}
-
-bool assetManagerItemIsFinished(assetmanageritem_t *item) {
-  // Sync done is always done
-  if(item->state == ASSET_MANAGER_STATE_SYNC_DONE) return true;
-  // Only check if ASYNC is done.
-  if(item->state != ASSET_MANAGER_STATE_ASYNC_DONE) return false;
-  // Does it need to still sync load?
-  if(ASSET_MANAGER_LOADERS[item->type].loadSync == NULL) return true;
-  return false;
-}
-
-// Font
-assetmanageritem_t * assetManagerLoadFont(
-  assetmanager_t *manager, assetmanagerowner_t owner, char *fileName
-) {
-  assetmanageritem_t *item; 
-  item = assetManagerItemGet(manager, fileName);
-  if(item == NULL) {
-    item = assetManagerItemAdd(manager, fileName);
-    item->type = ASSET_MANAGER_TYPE_FONT;
-    item->data.font.fileName = fileName;
-  }
-  assetManagerItemGetOrAddHolder(item, owner);
-
-  return item;
-}
-
-bool _assetManagerLoaderFontAsync(assetmanageritem_t *item) {
-  item->data.font.data = assetStringLoad(item->data.font.fileName);
-  return item->data.font.data != NULL;
-}
-
-bool _assetManagerLoaderFontSync(assetmanageritem_t *item) {
-  fontInit(&item->data.font.font, item->data.font.data);
-  free(item->data.font.data);
-  return true;
-}
-
-bool _assetManagerLoaderFontDispose(assetmanageritem_t *item) {
-  fontDispose(&item->data.font.font);
-  return true;
-}
-
-// Texture
-assetmanageritem_t * assetManagerLoadTexture(
-  assetmanager_t *manager, assetmanagerowner_t owner, char *fileName
-) {
-  assetmanageritem_t *item;
-  item = assetManagerItemGet(manager, fileName);
-  if(item == NULL) {
-    item = assetManagerItemAdd(manager, fileName);
-    item->type = ASSET_MANAGER_TYPE_TEXTURE;
-    item->data.texture.fileName = fileName;
-  }
-  assetManagerItemGetOrAddHolder(item, owner);
-  
-  return item;
-}
-
-bool _assetManagerLoaderTextureAsync(assetmanageritem_t *item) {
-  assetbuffer_t *buffer;
-  int channels;
-  stbi_io_callbacks OPENGL_STBI_CALLBACKS;
-
-  buffer = assetBufferOpen(item->data.texture.fileName);
-  if(buffer == NULL) return false;
-
-  // Setup the interface for STBI
-  OPENGL_STBI_CALLBACKS.read = &assetBufferRead;
-  OPENGL_STBI_CALLBACKS.skip = &assetBufferSkip;
-  OPENGL_STBI_CALLBACKS.eof = &assetBufferEnd; 
-
-  // Buffer the image
-  channels = 0;
-  item->data.texture.data = (pixel_t *)stbi_load_from_callbacks(
-    &OPENGL_STBI_CALLBACKS, buffer,
-    &item->data.texture.width, &item->data.texture.height,
-    &channels, STBI_rgb_alpha
-  );
-
-  // Close the buffer
-  assetBufferClose(buffer);
-  if(item->data.texture.data == NULL) return false;
-  return true;
-}
-
-bool _assetManagerLoaderTextureSync(assetmanageritem_t *item) {
-  // Turn into a texture.
-  textureInit(
-    &item->data.texture.texture,
-    item->data.texture.width,
-    item->data.texture.height,
-    item->data.texture.data
-  );
-
-  // Cleanup
-  stbi_image_free(item->data.texture.data);
-  return true;
-}
-
-bool _assetManagerLoaderTextureDispose(assetmanageritem_t *item) {
-  textureDispose(&item->data.texture.texture);
-  return true;
-}
-
-// Scaled Texture
-assetmanageritem_t * assetManagerLoadScaledTexture(
-  assetmanager_t *manager, assetmanagerowner_t owner, char *path, char *file
-) {
-  assetmanageritem_t *item;
-  scaledtexture_t *st;
-  char buffer[ASSET_MANAGER_ITEM_NAME_MAX];
-  sprintf(buffer, "%s/%s", path, file);
-  item = assetManagerItemGet(manager, buffer);
-  if(item == NULL) {
-    item = assetManagerItemAdd(manager, buffer);
-
-    item->type = ASSET_MANAGER_TYPE_SCALED_TEXTURE;
-    st = &item->data.scaledTexture.scaledTexture;
-    st->scaleCount = 0;
-    st->baseWidth = 0;
-    st->baseHeight = 0;
-    st->path = path;
-    st->file = file;
-  }
-  assetManagerItemGetOrAddHolder(item, owner);
-
-  return item;
-}
-
-bool _assetManagerLoaderScaledTextureAsync(assetmanageritem_t *item) {
-  char buffer[128];
-  char *xmlData;
-  xml_t xml;
-  xml_t *child;
-  int16_t i, j;
-  scaledtexture_t *st;
-  st = &item->data.scaledTexture.scaledTexture;
-
-  // Begin loading texture XML
-  sprintf(buffer, "%s/%s.xml", st->path, st->file);
-
-  xmlData = assetStringLoad(buffer);
-  if(xmlData == NULL) return false;
-  xmlLoad(&xml, xmlData);
-  free(xmlData);
-
-  // Parse root texture info
-  i = xmlGetAttributeByName(&xml, "channels");
-  st->channels = (uint8_t)atoi(xml.attributeDatas[i]);
-  i = xmlGetAttributeByName(&xml, "width");
-  st->baseWidth = (int16_t)atoi(xml.attributeDatas[i]);
-  i = xmlGetAttributeByName(&xml, "height");
-  st->baseHeight = (int16_t)atoi(xml.attributeDatas[i]);
-
-  for(j = 0; j < xml.childrenCount; j++) {
-    child = xml.children + j;
-    i = xmlGetAttributeByName(child, "scale");
-    st->scales[st->scaleCount].scale = (uint8_t)atoi(child->attributeDatas[i]);
-    i = xmlGetAttributeByName(child, "width");
-    st->scales[st->scaleCount].width = (int16_t)atoi(child->attributeDatas[i]);
-    i = xmlGetAttributeByName(child, "height");
-    st->scales[st->scaleCount].height = (int16_t)atoi(child->attributeDatas[i]);
-    st->scaleCount++;
-  }
-
-  // Cleanup XML
-  xmlDispose(&xml);
-  return true;
-}
-
-// Texture Scale
-assetmanageritem_t * assetManagerLoadTextureScale(
-  assetmanager_t *manager, assetmanagerowner_t owner, 
-  scaledtexture_t *st, uint8_t scale
-) {
-  assetmanageritem_t *item;
-  char buffer[ASSET_MANAGER_ITEM_NAME_MAX];
-  sprintf(buffer, "%s/%s_%u", st->path, st->file, scale);
-  item = assetManagerItemGet(manager, buffer);
-  if(item == NULL) {
-    item = assetManagerItemAdd(manager, buffer);
-    item->type = ASSET_MANAGER_TYPE_SCALE_TEXTURE;
-    item->data.scaleTexture.scale = scale;
-    item->data.scaleTexture.scaledTexture = st;
-  }
-  assetManagerItemGetOrAddHolder(item, owner);
-  return item;
-}
-
-bool _assetManagerLoaderTextureScaleAsync(assetmanageritem_t *item) {
-  char buffer[128];
-  scaledtexture_t *st;
-  scaledtexturescale_t *sts;
-  size_t length;
-
-  st = item->data.scaleTexture.scaledTexture;
-  sts = st->scales + item->data.scaleTexture.scale;
-
-  // Get filename
-  sprintf(buffer, "%s/%s_%i.texture", st->path, st->file, sts->scale);
-
-  // Create some space
-  length = assetRawLoad(buffer, NULL);
-  if(length == 0) return false;
-  item->data.scaleTexture.data = malloc(sizeof(pixel_t) * length);
-
-  // Load
-  length = assetRawLoad(buffer, (uint8_t *)item->data.scaleTexture.data);
-  if(length == 0) {
-    free(item->data.scaleTexture.data);
-    return false;
-  }
-  
-  return true;
-}
-
-bool _assetManagerLoaderTextureScaleSync(assetmanageritem_t *item) {
-  scaledtexture_t *st;
-  scaledtexturescale_t *sts;
-  st = item->data.scaleTexture.scaledTexture;
-  sts = st->scales + item->data.scaleTexture.scale;
-
-  textureInit(
-    &item->data.scaleTexture.texture,
-    sts->width, sts->height,
-    item->data.scaleTexture.data
-  );
-
-  free(item->data.scaleTexture.data);
-  return true;
-}
-
-bool _assetManagerLoaderTextureScaleDispose(assetmanageritem_t *item) {
-  textureDispose(&item->data.scaleTexture.texture);
-  return true;
-}
-
-// Shader
-assetmanageritem_t * assetManagerLoadShader(
-  assetmanager_t *manager, assetmanagerowner_t owner,
-  char *fileVert, char *fileFrag
-) {
-  assetmanageritem_t *item;
-  char buffer[ASSET_MANAGER_ITEM_NAME_MAX];
-  sprintf(buffer, "%s/%s", fileVert, fileFrag);
-  item = assetManagerItemGet(manager, buffer);
-  if(item == NULL) {
-    item = assetManagerItemAdd(manager, buffer);
-    item->type = ASSET_MANAGER_TYPE_SHADER;
-    item->data.shader.fileVert = fileVert;
-    item->data.shader.fileFrag = fileFrag;
-  }
-  assetManagerItemGetOrAddHolder(item, owner);
-  return item;
-}
-
-bool _assetManagerLoaderShaderAsync(assetmanageritem_t *item) {
-  item->data.shader.dataVert = assetStringLoad(item->data.shader.fileVert);
-  if(item->data.shader.dataVert == NULL) return false;
-
-  item->data.shader.dataFrag = assetStringLoad(item->data.shader.fileFrag);
-  if(item->data.shader.dataFrag == NULL) {
-    free(item->data.shader.fileVert);
-    return false;
-  }
-  
-  return true;
-}
-
-bool _assetManagerLoaderShaderSync(assetmanageritem_t *item) {
-  shaderInit(
-    &item->data.shader.shader,
-    item->data.shader.dataVert,
-    item->data.shader.dataFrag
-  );
-  free(item->data.shader.dataFrag);
-  free(item->data.shader.dataVert);
-  return true;
-}
-
-bool _assetManagerLoaderShaderDispose(assetmanageritem_t *item) {
-  shaderDispose(&item->data.shader.shader);
-  return true;
 }
\ No newline at end of file
diff --git a/src/file/assetmanager.h b/src/file/assetmanager.h
index 0168dae1..d7dbcf85 100644
--- a/src/file/assetmanager.h
+++ b/src/file/assetmanager.h
@@ -7,107 +7,12 @@
 
 #pragma once
 #include "../libs.h"
-#include "../display/font.h"
-#include "../display/texture.h"
-#include "../display/scaledtexture.h"
-#include "../display/shader/shader.h"
-#include "../engine/thread.h"
-#include "../util/array.h"
+#include "types/common.h"
+#include "loaders/font.h"
+#include "loaders/scaledtexture.h"
+#include "loaders/shader.h"
+#include "loaders/texture.h"
 #include "asset.h"
-#include "xml.h"
-
-#define ASSET_MANAGER_ITEMS_MAX 64
-#define ASSET_MANAGER_ITEM_NAME_MAX 96
-
-#define ASSET_MANAGER_HOLDERS_MAX 8
-
-#define ASSET_MANAGER_STATE_NOT_READY 0x00
-#define ASSET_MANAGER_STATE_PENDING 0x01
-#define ASSET_MANAGER_STATE_ASYNC_LOADING 0x02
-#define ASSET_MANAGER_STATE_ASYNC_ERROR 0x03
-#define ASSET_MANAGER_STATE_ASYNC_DONE 0x04
-#define ASSET_MANAGER_STATE_SYNC_LOADING 0x05
-#define ASSET_MANAGER_STATE_SYNC_ERROR 0x06
-#define ASSET_MANAGER_STATE_SYNC_DONE 0x07
-
-#define ASSET_MANAGER_TYPE_TEXTURE 0x00
-#define ASSET_MANAGER_TYPE_FONT 0x01
-#define ASSET_MANAGER_TYPE_SHADER 0x02
-#define ASSET_MANAGER_TYPE_SCALED_TEXTURE 0x03
-#define ASSET_MANAGER_TYPE_SCALE_TEXTURE 0x04
-
-// Loader Types
-typedef struct {
-  font_t font;
-  char *fileName;
-  char *data;
-} assetmanagerfont_t;
-
-typedef struct {
-  texture_t texture;
-  char *fileName;
-  int32_t width, height;
-  pixel_t *data;
-} assetmanagertexture_t;
-
-typedef struct {
-  scaledtexture_t scaledTexture;
-} assetmanagerscaledtexture_t;
-
-typedef struct {
-  scaledtexture_t *scaledTexture;
-  texture_t texture;
-  uint8_t scale;
-  pixel_t *data;
-} assetmanagerscaletexture_t;
-
-typedef struct {
-  shader_t shader;
-  char *fileVert;
-  char *fileFrag;
-  char *dataVert;
-  char *dataFrag;
-} assetmanagershader_t;
-
-// Item
-typedef uint8_t assetmanagerowner_t;
-
-typedef union {
-  assetmanagertexture_t texture;
-  assetmanagershader_t shader;
-  assetmanagerfont_t font;
-  assetmanagerscaledtexture_t scaledTexture;
-  assetmanagerscaletexture_t scaleTexture;
-} assetmanagerassetdata_t;
-
-typedef struct {
-  uint8_t type;
-  uint8_t state;
-  char key[ASSET_MANAGER_ITEM_NAME_MAX];
-  assetmanagerassetdata_t data;
-  assetmanagerowner_t holders[ASSET_MANAGER_HOLDERS_MAX];
-  uint8_t holderCount;
-} assetmanageritem_t;
-
-// Loader
-typedef bool assetmanagerloader_t(assetmanageritem_t *item);
-
-typedef struct {
-  assetmanagerloader_t *loadAsync;
-  assetmanagerloader_t *loadSync;
-  assetmanagerloader_t *dispose;
-} assetmanagerloaderdefinition_t;
-
-// Manager
-typedef struct {
-  thread_t thread;
-  bool finished;
-  assetmanageritem_t items[ASSET_MANAGER_ITEMS_MAX];
-  uint8_t itemCount;
-  assetmanagerowner_t holders[ASSET_MANAGER_HOLDERS_MAX];
-  uint8_t holderCount;
-  bool running;
-} assetmanager_t;
 
 // Constants
 extern assetmanagerloaderdefinition_t ASSET_MANAGER_LOADERS[];
@@ -128,12 +33,52 @@ void assetManagerInit(assetmanager_t *manager);
  */
 float assetManagerProgressGet(assetmanager_t *manager);
 
-assetmanagerowner_t assetManagerHolderCreate(assetmanager_t *man);
-void assetManagerHolderRelease(assetmanager_t *man, uint8_t hold);
-void assetManagerDisposeReleased(assetmanager_t *man);
-void assetManagerDispose(assetmanager_t *man);
+/**
+ * Gets the progress of the assets for only those held by a specific holder.
+ * 
+ * @param manager Manager to get the progress from
+ * @param hold Holder to get the items progress from.
+ * @return The percentage (0-1) of the loaded assets.
+ */
+float assetManagerProgressGetForHolder(
+  assetmanager_t *manager, assetmanagerowner_t hold
+);
 
-////////////////////////////////////////////////////////////////////////////////
+/**
+ * Creates a holder for a given asset manager. Asset holders are kept track of
+ * so that those who requests assets are responsible for those who free them. It
+ * also ensures only the assets that are actually necessary are kept loaded in 
+ * memory at all times.
+ * 
+ * @param man Asset manager in question
+ * @return An asset manager owner ID.
+ */
+assetmanagerowner_t assetManagerHolderCreate(assetmanager_t *man);
+
+/**
+ * Release a previously reserved asset manager holder. This will (in turn) cause
+ * all of the assets that manager was holding to also be released.
+ * 
+ * @param man Asset manager holder to release for.
+ * @param hold Holder to release.
+ */
+void assetManagerHolderRelease(assetmanager_t *man, assetmanagerowner_t hold);
+
+/**
+ * Disposes all assets that are not currently held (released assets). This can
+ * only happen from the main thread due to synchronous assets such as Textures.
+ * 
+ * @param man Manager to dispose.
+ */
+void assetManagerDisposeReleased(assetmanager_t *man);
+
+/**
+ * Completely dispose an asset manager. This will also completely dispose all
+ * of the assets that this asset manager is holding.
+ * 
+ * @param man Asset manager to dispose
+ */
+void assetManagerDispose(assetmanager_t *man);
 
 /**
  * Begin asynchronously loading all of the assets
@@ -153,132 +98,3 @@ int32_t _assetManagerThread(thread_t *thread);
  * @param manager Manager to synchronously tick.
  */
 void assetManagerUpdate(assetmanager_t *manager);
-
-////////////////////////////////////////////////////////////////////////////////
-
-/**
- * Retreive an exisitng asset manager item by its key.
- * 
- * @param man Manager to get from
- * @param key Key to search for.
- * @return The matching asset manager item, or NULL if not found.
- */
-assetmanageritem_t * assetManagerItemGet(assetmanager_t *man, char *key);
-
-/**
- * Private method, simply adds an item to the manager and resets the state.
- * 
- * @param manager Manager to add to.
- * @param key Key to use when adding.
- * @return The added and reset item.
- */
-assetmanageritem_t * assetManagerItemAdd(assetmanager_t *manager, char *key);
-
-/**
- * Add or get the index that a given holder has as a manager item.
- * 
- * @param i Asset Item to check.
- * @param o Owner to get/add.
- * @return The index within the item that the owner is at.
- */
-uint8_t assetManagerItemGetOrAddHolder(
-  assetmanageritem_t *i, assetmanagerowner_t o
-);
-
-/**
- * Checks if a given asset item is finished or not.
- * 
- * @param item Item to check.
- * @return True if finished, otherwise false.
- */
-bool assetManagerItemIsFinished(assetmanageritem_t *item);
-
-////////////////////////////////////////////////////////////////////////////////
-
-/**
- * Queue a font load onto the asset manager buffer.
- * 
- * @param manager Manager to queue on to.
- * @param owner Owner ID requesting to load this resource.
- * @param font Font to push the result in to.
- * @param fileName Filename of the asset to load.
- * @return A pointer to the asset manager item for tracking.
- */
-assetmanageritem_t * assetManagerLoadFont(
-  assetmanager_t *manager, assetmanagerowner_t owner, char *fileName
-);
-
-bool _assetManagerLoaderFontAsync(assetmanageritem_t *item);
-bool _assetManagerLoaderFontSync(assetmanageritem_t *item);
-bool _assetManagerLoaderFontDispose(assetmanageritem_t *item);
-
-/**
- * Queue a texture load onto the asset manager buffer.
- * 
- * @param manager Manager to queue on to.
- * @param owner Owner ID requesting to load this resource.
- * @param texture Texture to push the result in to.
- * @param fileName Texture filename to load.
- * @return A pointer to the asset manager item for tracking.
- */
-assetmanageritem_t * assetManagerLoadTexture(
-  assetmanager_t *manager, assetmanagerowner_t owner, char *fileName
-);
-
-bool _assetManagerLoaderTextureAsync(assetmanageritem_t *item);
-bool _assetManagerLoaderTextureSync(assetmanageritem_t *item);
-bool _assetManagerLoaderTextureDispose(assetmanageritem_t *item);
-
-/**
- * Queue a scaled texture load asset to the asset manager buffer. This will not
- * actually load the texture, just the scaled texture information.
- * 
- * @param manager Manager to queue on to.
- * @param owner Owner ID requesting to load this resource.
- * @param path Path of the texture files
- * @param file File name of the texture sets.
- * @return A pointer to the asset manager item for tracking.
- */
-assetmanageritem_t * assetManagerLoadScaledTexture(
-  assetmanager_t *manager, assetmanagerowner_t owner, char *path, char *file
-);
-
-bool _assetManagerLoaderScaledTextureAsync(assetmanageritem_t *item);
-
-/**
- * Load the given texture scale for a scaled texture.
- * 
- * @param manager Manager to queue on to.
- * @param owner Owner ID requesting to load this resource.
- * @param st Scaled Texture to load in to.
- * @param text Texture to load the scale in to.
- * @param scale Scale to load.
- * @return A pointer to the asset manager item for tracking.
- */
-assetmanageritem_t * assetManagerLoadTextureScale(
-  assetmanager_t *manager, assetmanagerowner_t owner, 
-  scaledtexture_t *st, uint8_t scale
-);
-
-bool _assetManagerLoaderTextureScaleAsync(assetmanageritem_t *item);
-bool _assetManagerLoaderTextureScaleSync(assetmanageritem_t *item);
-bool _assetManagerLoaderTextureScaleDispose(assetmanageritem_t *item);
-
-/**
- * Queues a shader load onto the asset manager buffer.
- * 
- * @param manager Manager to queue on to.
- * @param owner Owner ID requesting to load this resource.
- * @param shader Shader to push the result in to.
- * @param fileVert Vertex file in question to load.
- * @param fileFrag Fragment file in question to load.
- * @return A pointer to the asset manager item for tracking.
- */
-assetmanageritem_t * assetManagerLoadShader(
-  assetmanager_t *manager, assetmanagerowner_t owner,
-  char *fileVert, char *fileFrag
-);
-
-bool _assetManagerLoaderShaderAsync(assetmanageritem_t *item);
-bool _assetManagerLoaderShaderSync(assetmanageritem_t *item);
-bool _assetManagerLoaderShaderDispose(assetmanageritem_t *item);
\ No newline at end of file
diff --git a/src/file/loaders/font.c b/src/file/loaders/font.c
new file mode 100644
index 00000000..4e6ceb63
--- /dev/null
+++ b/src/file/loaders/font.c
@@ -0,0 +1,39 @@
+/**
+ * Copyright (c) 2021 Dominic Masters
+ * 
+ * This software is released under the MIT License.
+ * https://opensource.org/licenses/MIT
+ */
+
+#include "font.h"
+
+assetmanageritem_t * assetManagerLoadFont(
+  assetmanager_t *manager, assetmanagerowner_t owner, char *fileName
+) {
+  assetmanageritem_t *item; 
+  item = assetManagerItemGet(manager, fileName);
+  if(item == NULL) {
+    item = assetManagerItemAdd(manager, fileName);
+    item->type = ASSET_MANAGER_TYPE_FONT;
+    item->data.font.fileName = fileName;
+  }
+  assetManagerItemGetOrAddHolder(item, owner);
+
+  return item;
+}
+
+bool _assetManagerLoaderFontAsync(assetmanageritem_t *item) {
+  item->data.font.data = assetStringLoad(item->data.font.fileName);
+  return item->data.font.data != NULL;
+}
+
+bool _assetManagerLoaderFontSync(assetmanageritem_t *item) {
+  fontInit(&item->data.font.font, item->data.font.data);
+  free(item->data.font.data);
+  return true;
+}
+
+bool _assetManagerLoaderFontDispose(assetmanageritem_t *item) {
+  fontDispose(&item->data.font.font);
+  return true;
+}
\ No newline at end of file
diff --git a/src/file/loaders/font.h b/src/file/loaders/font.h
new file mode 100644
index 00000000..51f79dd8
--- /dev/null
+++ b/src/file/loaders/font.h
@@ -0,0 +1,27 @@
+/**
+ * Copyright (c) 2021 Dominic Masters
+ * 
+ * This software is released under the MIT License.
+ * https://opensource.org/licenses/MIT
+ */
+
+#pragma once
+#include "item.h"
+#include "../asset.h"
+
+/**
+ * Queue a font load onto the asset manager buffer.
+ * 
+ * @param manager Manager to queue on to.
+ * @param owner Owner ID requesting to load this resource.
+ * @param font Font to push the result in to.
+ * @param fileName Filename of the asset to load.
+ * @return A pointer to the asset manager item for tracking.
+ */
+assetmanageritem_t * assetManagerLoadFont(
+  assetmanager_t *manager, assetmanagerowner_t owner, char *fileName
+);
+
+bool _assetManagerLoaderFontAsync(assetmanageritem_t *item);
+bool _assetManagerLoaderFontSync(assetmanageritem_t *item);
+bool _assetManagerLoaderFontDispose(assetmanageritem_t *item);
\ No newline at end of file
diff --git a/src/file/loaders/item.c b/src/file/loaders/item.c
new file mode 100644
index 00000000..d8ba68bb
--- /dev/null
+++ b/src/file/loaders/item.c
@@ -0,0 +1,57 @@
+/**
+ * Copyright (c) 2021 Dominic Masters
+ * 
+ * This software is released under the MIT License.
+ * https://opensource.org/licenses/MIT
+ */
+
+#include "item.h"
+
+assetmanageritem_t * assetManagerItemGet(assetmanager_t *man, char *key) {
+  uint8_t i;
+  assetmanageritem_t *item;
+
+  for(i = 0; i < man->itemCount; i++) {
+    item = man->items + i;
+    if(strcmp(item->key, key) == 0) return item;
+  }
+
+  return NULL;
+}
+
+assetmanageritem_t * assetManagerItemAdd(assetmanager_t *manager, char *key) {
+  // Check if key already exists.
+  assetmanageritem_t *item = manager->items + manager->itemCount++;
+  item->state = ASSET_MANAGER_STATE_NOT_READY;
+  memcpy(item->key, key, strlen(key) + 1);
+  item->holderCount = 0x00;
+  return item;
+}
+
+uint8_t assetManagerItemGetOrAddHolder(
+  assetmanageritem_t *item, assetmanagerowner_t owner
+) {
+  uint8_t i, firstEmpty;
+  firstEmpty = 0xFF;
+
+  for(i = 0; i < item->holderCount; i++) {
+    if(item->holders[i] == owner) return i;
+    if(firstEmpty == 0xFF && item->holders[i] == 0xFF) {
+      firstEmpty = i;
+    }
+  }
+
+  if(firstEmpty == 0xFF) firstEmpty = item->holderCount++;
+  item->holders[firstEmpty] = owner;
+  return firstEmpty;
+}
+
+bool assetManagerItemIsFinished(assetmanageritem_t *item, assetmanagerloaderdefinition_t *def) {
+  // Sync done is always done
+  if(item->state == ASSET_MANAGER_STATE_SYNC_DONE) return true;
+  // Only check if ASYNC is done.
+  if(item->state != ASSET_MANAGER_STATE_ASYNC_DONE) return false;
+  // Does it need to still sync load?
+  if(def->loadSync == NULL) return true;
+  return false;
+}
\ No newline at end of file
diff --git a/src/file/loaders/item.h b/src/file/loaders/item.h
new file mode 100644
index 00000000..5327cfb4
--- /dev/null
+++ b/src/file/loaders/item.h
@@ -0,0 +1,49 @@
+/**
+ * Copyright (c) 2021 Dominic Masters
+ * 
+ * This software is released under the MIT License.
+ * https://opensource.org/licenses/MIT
+ */
+
+#pragma once
+#include "../types/common.h"
+
+/**
+ * Retreive an exisitng asset manager item by its key.
+ * 
+ * @param man Manager to get from
+ * @param key Key to search for.
+ * @return The matching asset manager item, or NULL if not found.
+ */
+assetmanageritem_t * assetManagerItemGet(assetmanager_t *man, char *key);
+
+/**
+ * Private method, simply adds an item to the manager and resets the state.
+ * 
+ * @param manager Manager to add to.
+ * @param key Key to use when adding.
+ * @return The added and reset item.
+ */
+assetmanageritem_t * assetManagerItemAdd(assetmanager_t *manager, char *key);
+
+/**
+ * Add or get the index that a given holder has as a manager item.
+ * 
+ * @param i Asset Item to check.
+ * @param o Owner to get/add.
+ * @return The index within the item that the owner is at.
+ */
+uint8_t assetManagerItemGetOrAddHolder(
+  assetmanageritem_t *i, assetmanagerowner_t o
+);
+
+/**
+ * Checks if a given asset item is finished or not.
+ * 
+ * @param item Item to check.
+ * @param def Item type definition used for loading.
+ * @return True if finished, otherwise false.
+ */
+bool assetManagerItemIsFinished(
+  assetmanageritem_t *item, assetmanagerloaderdefinition_t *def
+);
\ No newline at end of file
diff --git a/src/file/loaders/scaledtexture.c b/src/file/loaders/scaledtexture.c
new file mode 100644
index 00000000..206bb760
--- /dev/null
+++ b/src/file/loaders/scaledtexture.c
@@ -0,0 +1,123 @@
+/**
+ * Copyright (c) 2021 Dominic Masters
+ * 
+ * This software is released under the MIT License.
+ * https://opensource.org/licenses/MIT
+ */
+
+#include "scaledtexture.h"
+
+assetmanageritem_t * assetManagerLoadScaledTexture(
+  assetmanager_t *manager, assetmanagerowner_t owner,
+  char *path, char *file, uint8_t scale
+) {
+  assetmanageritem_t *item;
+  texturescale_t *st;
+  char buffer[ASSET_MANAGER_ITEM_NAME_MAX];
+  
+  sprintf(buffer, "%s/%s_%u", path, file, scale);
+  item = assetManagerItemGet(manager, buffer);
+  
+  if(item == NULL) {
+    item = assetManagerItemAdd(manager, buffer);
+    item->type = ASSET_MANAGER_TYPE_SCALED_TEXTURE;
+    item->data.scaledTexture.scale = scale;
+
+    st = &item->data.scaledTexture.textureScale;
+    st->scaleCount = 0;
+    st->baseWidth = 0;
+    st->baseHeight = 0;
+    st->path = path;
+    st->file = file;
+  }
+
+  assetManagerItemGetOrAddHolder(item, owner);
+  return item;
+}
+
+bool _assetManagerLoaderScaledTextureAsync(assetmanageritem_t *item) {
+  char buffer[128];
+  char *xmlData;
+  xml_t xml;
+  xml_t *child;
+  int16_t i, j;
+  texturescale_t *st;
+  texturescalescale_t *sts;
+  size_t length;
+
+  // TODO: This can be improved if we allow both asset dependencies and 
+  // dependency sibling adding
+
+  st = &item->data.scaledTexture.textureScale;
+
+  // Begin loading texture XML
+  sprintf(buffer, "%s/%s.xml", st->path, st->file);
+
+  xmlData = assetStringLoad(buffer);
+  if(xmlData == NULL) return false;
+  xmlLoad(&xml, xmlData);
+  free(xmlData);
+
+  // Parse root texture info
+  i = xmlGetAttributeByName(&xml, "channels");
+  st->channels = (uint8_t)atoi(xml.attributeDatas[i]);
+  i = xmlGetAttributeByName(&xml, "width");
+  st->baseWidth = (int16_t)atoi(xml.attributeDatas[i]);
+  i = xmlGetAttributeByName(&xml, "height");
+  st->baseHeight = (int16_t)atoi(xml.attributeDatas[i]);
+
+  for(j = 0; j < xml.childrenCount; j++) {
+    child = xml.children + j;
+    i = xmlGetAttributeByName(child, "scale");
+    st->scales[st->scaleCount].scale = (uint8_t)atoi(child->attributeDatas[i]);
+    i = xmlGetAttributeByName(child, "width");
+    st->scales[st->scaleCount].width = (int16_t)atoi(child->attributeDatas[i]);
+    i = xmlGetAttributeByName(child, "height");
+    st->scales[st->scaleCount].height = (int16_t)atoi(child->attributeDatas[i]);
+    st->scaleCount++;
+  }
+
+  // Cleanup XML
+  xmlDispose(&xml);
+
+  // Get the scale
+  sts = st->scales + item->data.scaledTexture.scale;
+
+  // Get filename
+  sprintf(buffer, "%s/%s_%i.texture", st->path, st->file, sts->scale);
+
+  // Create some space
+  length = assetRawLoad(buffer, NULL);
+  if(length == 0) return false;
+  item->data.scaledTexture.data = malloc(sizeof(pixel_t) * length);
+
+  // Load
+  length = assetRawLoad(buffer, (uint8_t *)item->data.scaledTexture.data);
+  if(length == 0) {
+    free(item->data.scaledTexture.data);
+    return false;
+  }
+  
+  return true;
+}
+
+bool _assetManagerLoaderScaledTextureSync(assetmanageritem_t *item) {
+  texturescale_t *st;
+  texturescalescale_t *sts;
+  st = &item->data.scaledTexture.textureScale;
+  sts = st->scales + item->data.scaledTexture.scale;
+
+  textureInit(
+    &item->data.scaledTexture.texture,
+    sts->width, sts->height,
+    item->data.scaledTexture.data
+  );
+
+  free(item->data.scaledTexture.data);
+  return true;
+}
+
+bool _assetManagerLoaderScaledTextureDispose(assetmanageritem_t *item) {
+  textureDispose(&item->data.scaledTexture.texture);
+  return true;
+}
diff --git a/src/file/loaders/scaledtexture.h b/src/file/loaders/scaledtexture.h
new file mode 100644
index 00000000..a23c41f9
--- /dev/null
+++ b/src/file/loaders/scaledtexture.h
@@ -0,0 +1,30 @@
+/**
+ * Copyright (c) 2021 Dominic Masters
+ * 
+ * This software is released under the MIT License.
+ * https://opensource.org/licenses/MIT
+ */
+
+#pragma once
+#include "item.h"
+#include "../xml.h"
+#include "../asset.h"
+
+/**
+ * Load the given texture scale for a scaled texture.
+ * 
+ * @param manager Manager to queue on to.
+ * @param owner Owner ID requesting to load this resource.
+ * @param path Path of the texture size sets
+ * @param file Name of the texture that was generated.
+ * @param scale Scale to load.
+ * @return A pointer to the asset manager item for tracking.
+ */
+assetmanageritem_t * assetManagerLoadScaledTexture(
+  assetmanager_t *manager, assetmanagerowner_t owner,
+  char *path, char *file, uint8_t scale
+);
+
+bool _assetManagerLoaderScaledTextureAsync(assetmanageritem_t *item);
+bool _assetManagerLoaderScaledTextureSync(assetmanageritem_t *item);
+bool _assetManagerLoaderScaledTextureDispose(assetmanageritem_t *item);
\ No newline at end of file
diff --git a/src/file/loaders/shader.c b/src/file/loaders/shader.c
new file mode 100644
index 00000000..5398c16e
--- /dev/null
+++ b/src/file/loaders/shader.c
@@ -0,0 +1,55 @@
+/**
+ * Copyright (c) 2021 Dominic Masters
+ * 
+ * This software is released under the MIT License.
+ * https://opensource.org/licenses/MIT
+ */
+
+#include "shader.h"
+
+assetmanageritem_t * assetManagerLoadShader(
+  assetmanager_t *manager, assetmanagerowner_t owner,
+  char *fileVert, char *fileFrag
+) {
+  assetmanageritem_t *item;
+  char buffer[ASSET_MANAGER_ITEM_NAME_MAX];
+  sprintf(buffer, "%s/%s", fileVert, fileFrag);
+  item = assetManagerItemGet(manager, buffer);
+  if(item == NULL) {
+    item = assetManagerItemAdd(manager, buffer);
+    item->type = ASSET_MANAGER_TYPE_SHADER;
+    item->data.shader.fileVert = fileVert;
+    item->data.shader.fileFrag = fileFrag;
+  }
+  assetManagerItemGetOrAddHolder(item, owner);
+  return item;
+}
+
+bool _assetManagerLoaderShaderAsync(assetmanageritem_t *item) {
+  item->data.shader.dataVert = assetStringLoad(item->data.shader.fileVert);
+  if(item->data.shader.dataVert == NULL) return false;
+
+  item->data.shader.dataFrag = assetStringLoad(item->data.shader.fileFrag);
+  if(item->data.shader.dataFrag == NULL) {
+    free(item->data.shader.fileVert);
+    return false;
+  }
+  
+  return true;
+}
+
+bool _assetManagerLoaderShaderSync(assetmanageritem_t *item) {
+  shaderInit(
+    &item->data.shader.shader,
+    item->data.shader.dataVert,
+    item->data.shader.dataFrag
+  );
+  free(item->data.shader.dataFrag);
+  free(item->data.shader.dataVert);
+  return true;
+}
+
+bool _assetManagerLoaderShaderDispose(assetmanageritem_t *item) {
+  shaderDispose(&item->data.shader.shader);
+  return true;
+}
\ No newline at end of file
diff --git a/src/file/loaders/shader.h b/src/file/loaders/shader.h
new file mode 100644
index 00000000..970948e9
--- /dev/null
+++ b/src/file/loaders/shader.h
@@ -0,0 +1,29 @@
+/**
+ * Copyright (c) 2021 Dominic Masters
+ * 
+ * This software is released under the MIT License.
+ * https://opensource.org/licenses/MIT
+ */
+
+#pragma once
+#include "item.h"
+#include "../asset.h"
+
+/**
+ * Queues a shader load onto the asset manager buffer.
+ * 
+ * @param manager Manager to queue on to.
+ * @param owner Owner ID requesting to load this resource.
+ * @param shader Shader to push the result in to.
+ * @param fileVert Vertex file in question to load.
+ * @param fileFrag Fragment file in question to load.
+ * @return A pointer to the asset manager item for tracking.
+ */
+assetmanageritem_t * assetManagerLoadShader(
+  assetmanager_t *manager, assetmanagerowner_t owner,
+  char *fileVert, char *fileFrag
+);
+
+bool _assetManagerLoaderShaderAsync(assetmanageritem_t *item);
+bool _assetManagerLoaderShaderSync(assetmanageritem_t *item);
+bool _assetManagerLoaderShaderDispose(assetmanageritem_t *item);
\ No newline at end of file
diff --git a/src/file/loaders/texture.c b/src/file/loaders/texture.c
new file mode 100644
index 00000000..3eea99b5
--- /dev/null
+++ b/src/file/loaders/texture.c
@@ -0,0 +1,69 @@
+/**
+ * Copyright (c) 2021 Dominic Masters
+ * 
+ * This software is released under the MIT License.
+ * https://opensource.org/licenses/MIT
+ */
+
+#include "texture.h"
+
+assetmanageritem_t * assetManagerLoadTexture(
+  assetmanager_t *manager, assetmanagerowner_t owner, char *fileName
+) {
+  assetmanageritem_t *item;
+  item = assetManagerItemGet(manager, fileName);
+  if(item == NULL) {
+    item = assetManagerItemAdd(manager, fileName);
+    item->type = ASSET_MANAGER_TYPE_TEXTURE;
+    item->data.texture.fileName = fileName;
+  }
+  assetManagerItemGetOrAddHolder(item, owner);
+  
+  return item;
+}
+
+bool _assetManagerLoaderTextureAsync(assetmanageritem_t *item) {
+  assetbuffer_t *buffer;
+  int channels;
+  stbi_io_callbacks OPENGL_STBI_CALLBACKS;
+
+  buffer = assetBufferOpen(item->data.texture.fileName);
+  if(buffer == NULL) return false;
+
+  // Setup the interface for STBI
+  OPENGL_STBI_CALLBACKS.read = &assetBufferRead;
+  OPENGL_STBI_CALLBACKS.skip = &assetBufferSkip;
+  OPENGL_STBI_CALLBACKS.eof = &assetBufferEnd; 
+
+  // Buffer the image
+  channels = 0;
+  item->data.texture.data = (pixel_t *)stbi_load_from_callbacks(
+    &OPENGL_STBI_CALLBACKS, buffer,
+    &item->data.texture.width, &item->data.texture.height,
+    &channels, STBI_rgb_alpha
+  );
+
+  // Close the buffer
+  assetBufferClose(buffer);
+  if(item->data.texture.data == NULL) return false;
+  return true;
+}
+
+bool _assetManagerLoaderTextureSync(assetmanageritem_t *item) {
+  // Turn into a texture.
+  textureInit(
+    &item->data.texture.texture,
+    item->data.texture.width,
+    item->data.texture.height,
+    item->data.texture.data
+  );
+
+  // Cleanup
+  stbi_image_free(item->data.texture.data);
+  return true;
+}
+
+bool _assetManagerLoaderTextureDispose(assetmanageritem_t *item) {
+  textureDispose(&item->data.texture.texture);
+  return true;
+}
\ No newline at end of file
diff --git a/src/file/loaders/texture.h b/src/file/loaders/texture.h
new file mode 100644
index 00000000..19ffa98d
--- /dev/null
+++ b/src/file/loaders/texture.h
@@ -0,0 +1,27 @@
+/**
+ * Copyright (c) 2021 Dominic Masters
+ * 
+ * This software is released under the MIT License.
+ * https://opensource.org/licenses/MIT
+ */
+
+#pragma once
+#include "item.h"
+#include "../asset.h"
+
+/**
+ * Queue a texture load onto the asset manager buffer.
+ * 
+ * @param manager Manager to queue on to.
+ * @param owner Owner ID requesting to load this resource.
+ * @param texture Texture to push the result in to.
+ * @param fileName Texture filename to load.
+ * @return A pointer to the asset manager item for tracking.
+ */
+assetmanageritem_t * assetManagerLoadTexture(
+  assetmanager_t *manager, assetmanagerowner_t owner, char *fileName
+);
+
+bool _assetManagerLoaderTextureAsync(assetmanageritem_t *item);
+bool _assetManagerLoaderTextureSync(assetmanageritem_t *item);
+bool _assetManagerLoaderTextureDispose(assetmanageritem_t *item);
\ No newline at end of file
diff --git a/src/file/types/common.h b/src/file/types/common.h
new file mode 100644
index 00000000..32a70b79
--- /dev/null
+++ b/src/file/types/common.h
@@ -0,0 +1,80 @@
+/**
+ * Copyright (c) 2021 Dominic Masters
+ * 
+ * This software is released under the MIT License.
+ * https://opensource.org/licenses/MIT
+ */
+
+#pragma once
+#include "../../libs.h"
+#include "../engine/thread.h"
+#include "texture.h"
+#include "font.h"
+#include "shader.h"
+#include "scaledtexture.h"
+
+#define ASSET_MANAGER_ITEMS_MAX 64
+#define ASSET_MANAGER_ITEM_NAME_MAX 96
+#define ASSET_MANAGER_HOLDERS_MAX 8
+
+/** States */
+#define ASSET_MANAGER_STATE_NOT_READY 0x00
+#define ASSET_MANAGER_STATE_PENDING 0x01
+#define ASSET_MANAGER_STATE_ASYNC_LOADING 0x02
+#define ASSET_MANAGER_STATE_ASYNC_ERROR 0x03
+#define ASSET_MANAGER_STATE_ASYNC_DONE 0x04
+#define ASSET_MANAGER_STATE_SYNC_LOADING 0x05
+#define ASSET_MANAGER_STATE_SYNC_ERROR 0x06
+#define ASSET_MANAGER_STATE_SYNC_DONE 0x07
+
+/** Type IDs */
+#define ASSET_MANAGER_TYPE_TEXTURE 0x00
+#define ASSET_MANAGER_TYPE_FONT 0x01
+#define ASSET_MANAGER_TYPE_SHADER 0x02
+#define ASSET_MANAGER_TYPE_SCALED_TEXTURE 0x03
+
+// Owner
+typedef uint8_t assetmanagerowner_t;
+
+// Union of all the manager types
+typedef union {
+  assetmanagertexture_t texture;
+  assetmanagershader_t shader;
+  assetmanagerfont_t font;
+  assetmanagerscaledtexture_t scaledTexture;
+} assetmanagerassetdata_t;
+
+// Item Type
+typedef struct {
+  uint8_t type;
+  uint8_t state;
+  char key[ASSET_MANAGER_ITEM_NAME_MAX];
+  assetmanagerassetdata_t data;
+  assetmanagerowner_t holders[ASSET_MANAGER_HOLDERS_MAX];
+  uint8_t holderCount;
+} assetmanageritem_t;
+
+// Loader
+typedef bool assetmanagerloader_t(assetmanageritem_t *item);
+
+// Loader Definition
+typedef struct {
+  assetmanagerloader_t *loadAsync;
+  assetmanagerloader_t *loadSync;
+  assetmanagerloader_t *dispose;
+} assetmanagerloaderdefinition_t;
+
+
+
+// Manager
+typedef struct {
+  thread_t thread;
+  bool finished;
+  bool running;
+
+  assetmanageritem_t items[ASSET_MANAGER_ITEMS_MAX];
+  uint8_t itemCount;
+
+  assetmanagerowner_t holders[ASSET_MANAGER_HOLDERS_MAX];
+  uint8_t holderCount;
+} assetmanager_t;
\ No newline at end of file
diff --git a/src/file/types/font.h b/src/file/types/font.h
new file mode 100644
index 00000000..7f7d2203
--- /dev/null
+++ b/src/file/types/font.h
@@ -0,0 +1,15 @@
+/**
+ * Copyright (c) 2021 Dominic Masters
+ * 
+ * This software is released under the MIT License.
+ * https://opensource.org/licenses/MIT
+ */
+
+#pragma once
+#include "../../display/font.h"
+
+typedef struct {
+  font_t font;
+  char *fileName;
+  char *data;
+} assetmanagerfont_t;
\ No newline at end of file
diff --git a/src/file/types/scaledtexture.h b/src/file/types/scaledtexture.h
new file mode 100644
index 00000000..21058778
--- /dev/null
+++ b/src/file/types/scaledtexture.h
@@ -0,0 +1,18 @@
+/**
+ * Copyright (c) 2021 Dominic Masters
+ * 
+ * This software is released under the MIT License.
+ * https://opensource.org/licenses/MIT
+ */
+
+#pragma once
+#include "../../libs.h"
+#include "../../display/texture.h"
+#include "../../display/texturescale.h"
+
+typedef struct {
+  texturescale_t textureScale;
+  texture_t texture;
+  uint8_t scale;
+  pixel_t *data;
+} assetmanagerscaledtexture_t;
\ No newline at end of file
diff --git a/src/file/types/shader.h b/src/file/types/shader.h
new file mode 100644
index 00000000..839b4f91
--- /dev/null
+++ b/src/file/types/shader.h
@@ -0,0 +1,16 @@
+// Copyright (c) 2021 Dominic Masters
+// 
+// This software is released under the MIT License.
+// https://opensource.org/licenses/MIT
+
+#pragma once
+#include "../../libs.h"
+#include "../../display/shader/shader.h"
+
+typedef struct {
+  shader_t shader;
+  char *fileVert;
+  char *fileFrag;
+  char *dataVert;
+  char *dataFrag;
+} assetmanagershader_t;
\ No newline at end of file
diff --git a/src/file/types/texture.h b/src/file/types/texture.h
new file mode 100644
index 00000000..443bc482
--- /dev/null
+++ b/src/file/types/texture.h
@@ -0,0 +1,15 @@
+// Copyright (c) 2021 Dominic Masters
+// 
+// This software is released under the MIT License.
+// https://opensource.org/licenses/MIT
+
+#pragma once
+#include "../../libs.h"
+#include "../../display/texture.h"
+
+typedef struct {
+  texture_t texture;
+  char *fileName;
+  int32_t width, height;
+  pixel_t *data;
+} assetmanagertexture_t;
\ No newline at end of file
diff --git a/src/game/poker/game.c b/src/game/poker/game.c
index b5f8ac0c..66d4cfe4 100644
--- a/src/game/poker/game.c
+++ b/src/game/poker/game.c
@@ -8,76 +8,14 @@
 #include "game.h"
 
 bool pokerGameInit(pokergame_t *game) {
-  // Begin to load the assets.
-  pokerGameAssetsInit(&game->assets);
-  loadingSceneInit(&game->loadingScene, &game->assets.manager);
-  loadingSceneStart(&game->loadingScene);
-
+  pokerGameSceneInit(&game->gameScene, &game->engine);
   return true;
 } 
 
 void pokerGameUpdate(pokergame_t *game) {
-  bool t;
-  if(!game->loadingScene.manager->finished) {
-    t = loadingSceneUpdate(&game->loadingScene);
-    if(t) {
-      // Initialize the Visual Novel Engine.
-      vnSceneInit(&game->scene,
-        &game->assets.font,
-        &game->assets.testTexture
-      );
-
-      // Initialize the world
-      pokerWorldInit(&game->world, &game->scene, &game->assets);
-
-      // Initialize the UI.
-      pokerUiInit(&game->ui);
-
-      // Add the first action, the game action, and then start the action queue.
-      pokerGameActionStartAdd(game);
-      queueNext(&game->scene.conversation.actionQueue);
-    } else {
-      loadingSceneRender(&game->loadingScene);
-      return;
-    }
-  }
-
-  // Update the VN Engine.
-  vnSceneUpdate(&game->scene, &game->engine);
-
-  // Update the UI
-  pokerUiUpdate(
-    &game->ui,
-    &game->engine,
-    &game->assets.shader,
-    game->scene.characters,
-    game->poker.players
-  );
-
-  // Bind the shader.
-  shaderUse(&game->assets.shader);
-
-  // Render the visual novel scene.
-  vnSceneRenderWorld(&game->scene, &game->engine, &game->assets.shader);
-
-  pokerWorldRender(&game->world, &game->assets);
-  vnSceneRenderCharacters(&game->scene, &game->assets.shader);
-
-  // Render the UI
-  vnSceneRenderGui(&game->scene, &game->engine, &game->assets.shader);
-  pokerUiRender(&game->ui, &game->engine, &game->assets, &game->poker);
+  pokerGameSceneUpdate(&game->gameScene);
 }
 
 void pokerGameDispose(pokergame_t *game) {
-  //Cleanup the UI
-  pokerUiDispose(&game->ui);
-
-  // Cleanup the world
-  pokerWorldDispose(&game->world);
-
-  // Destroy the Visual Novel engine.
-  vnSceneDispose(&game->scene);
-
-  // Unload all assets
-  pokerGameAssetsDispose(&game->assets);
+  pokerGameSceneDispose(&game->gameScene);
 }
diff --git a/src/game/poker/game.h b/src/game/poker/game.h
index 0e33de10..70732203 100644
--- a/src/game/poker/game.h
+++ b/src/game/poker/game.h
@@ -7,18 +7,17 @@
 
 #pragma once
 #include "../../libs.h"
-#include "../../poker/poker.h"
-#include "../../vn/conversation/talk.h"
-#include "../../vn/vnscene.h"
-#include "../../util/array.h"
-#include "../../engine/thread.h"
-#include "../../scene/loadingscene.h"
-#include "pokergame.h"
-#include "pokergameassets.h"
-#include "pokerui.h"
-#include "pokerworld.h"
-#include "pokergameaction.h"
-#include "actions/start.h"
+#include "../../scene/scene.h"
+#include "../file/assetmanager.h"
+#include "scenes/gamescene.h"
+
+typedef struct {
+  /** Game Engine Instance */
+  engine_t engine;
+
+  /** Main game scene */
+  pokergamescene_t gameScene;
+} pokergame_t;
 
 /**
  * Initializes the game state for the poker game.
diff --git a/src/game/poker/scenes/gamescene.c b/src/game/poker/scenes/gamescene.c
new file mode 100644
index 00000000..fe1f6243
--- /dev/null
+++ b/src/game/poker/scenes/gamescene.c
@@ -0,0 +1,103 @@
+/**
+ * Copyright (c) 2021 Dominic Masters
+ * 
+ * This software is released under the MIT License.
+ * https://opensource.org/licenses/MIT
+ */
+
+#include "gamescene.h"
+
+void _pokerGameSceneLoaded(scene_t *scene) {
+  pokergamescene_t *gameScene;
+  char *uniforms[4] = { "u_View", "u_Proj", "u_Model", "u_Text" };
+
+  gameScene = (pokergamescene_t *)scene->user;
+
+
+  shaderGetUniformArray(
+    &gameScene->shaderWorld->data.shader.shader, gameScene->uniformsWorld,
+    uniforms, 4
+  );
+  shaderGetUniformArray(
+    &gameScene->shaderList->data.shader.shader, gameScene->uniformsList,
+    uniforms, 4
+  );
+  
+  gameScene->passOnly = renderPassAdd(
+    &scene->renderList, &gameScene->shaderWorld->data.shader.shader
+  );
+}
+
+void _pokerGameSceneRender(scene_t *scene) {
+  camera_t camera;
+  pokergamescene_t *gameScene;
+  renderpass_t *pass;
+
+  gameScene = (pokergamescene_t *)scene->user;
+  pass = sceneUsePass(scene, gameScene->passOnly);
+  
+  cameraPerspective(&camera, 75,
+    (float)pass->frame.texture.width / (float)pass->frame.texture.height,
+    0.01f, 1000.0f
+  );
+  cameraLookAt(&camera, 3,3,3, 0,0,0);
+
+  shaderUseCamera(pass->shader,
+    gameScene->uniformsWorld[0], gameScene->uniformsWorld[1], &camera
+  );
+  shaderUsePosition(pass->shader, gameScene->uniformsWorld[2], 
+    0,0,0, scene->engine->time.current,scene->engine->time.current,0
+  );
+  shaderUseTexture(pass->shader, gameScene->uniformsWorld[3],
+    &gameScene->textureTest->data.scaledTexture.texture
+  );
+  primitiveDraw(&gameScene->cube, 0, -1);
+}
+
+void pokerGameSceneInit(pokergamescene_t *gameScene, engine_t *engine) {
+  sceneInit(&gameScene->scene, engine, (void *)gameScene);
+  gameScene->scene.onLoaded = &_pokerGameSceneLoaded;
+  gameScene->scene.onRender = &_pokerGameSceneRender;
+
+  // Fonts
+  gameScene->font = assetManagerLoadFont(
+    &engine->assetManager, gameScene->scene.assetOwner,
+    "fonts/opensans/OpenSans-Bold.ttf"
+  );
+
+  // Shaders
+  gameScene->shaderWorld = assetManagerLoadShader(
+    &engine->assetManager, gameScene->scene.assetOwner,
+    "shaders/textured.vert", "shaders/textured.frag"
+  );
+
+  gameScene->shaderList = assetManagerLoadShader(
+    &engine->assetManager, gameScene->scene.assetOwner,
+    "shaders/singlerenderlist.vert", "shaders/singlerenderlist.frag"
+  );
+
+  // Textures
+  gameScene->textureTest = assetManagerLoadScaledTexture(
+    &engine->assetManager, gameScene->scene.assetOwner,
+    "textures", "test_texture", 0
+  );
+  // gameScene->textureTest = assetManagerLoadTexture(
+  //   &engine->assetManager, gameScene->scene.assetOwner, "textures/test_texture.png"
+  // );
+
+
+  // Cube
+  cubeInit(&gameScene->cube, 1, 1, 1);
+}
+
+void pokerGameSceneUpdate(pokergamescene_t *gameScene) {
+  int i = 3;
+  sceneUpdateToBackbuffer(&gameScene->scene,
+    &gameScene->shaderList->data.shader.shader, gameScene->uniformsList,
+    &gameScene->shaderWorld->data.shader.shader, gameScene->uniformsWorld
+  );
+}
+
+void pokerGameSceneDispose(pokergamescene_t *gameScene) {
+
+}
\ No newline at end of file
diff --git a/src/game/poker/scenes/gamescene.h b/src/game/poker/scenes/gamescene.h
new file mode 100644
index 00000000..477da091
--- /dev/null
+++ b/src/game/poker/scenes/gamescene.h
@@ -0,0 +1,37 @@
+/**
+ * Copyright (c) 2021 Dominic Masters
+ * 
+ * This software is released under the MIT License.
+ * https://opensource.org/licenses/MIT
+ */
+
+#pragma once
+#include "../../../libs.h"
+#include "../../../scene/scene.h"
+#include "../../../display/primitive/primitive.h"
+#include "../../../display/primitive/cube.h"
+#include "../../../file/assetmanager.h"
+
+typedef struct {
+  scene_t scene;
+
+  assetmanageritem_t *font;
+
+  uint8_t passOnly;
+  
+  assetmanageritem_t *shaderWorld;
+  shaderuniform_t uniformsWorld[4];
+
+  assetmanageritem_t *shaderList;
+  shaderuniform_t uniformsList[4];
+
+  assetmanageritem_t *textureTest;
+
+  primitive_t cube;
+} pokergamescene_t;
+
+void pokerGameSceneInit(pokergamescene_t *gameScene, engine_t *engine);
+
+void pokerGameSceneUpdate(pokergamescene_t *gameScene);
+
+void pokerGameSceneDispose(pokergamescene_t *gameScene);
\ No newline at end of file
diff --git a/src/game/poker/actions/action.c b/src/game/pokerbackup/actions/action.c
similarity index 100%
rename from src/game/poker/actions/action.c
rename to src/game/pokerbackup/actions/action.c
diff --git a/src/game/poker/actions/action.h b/src/game/pokerbackup/actions/action.h
similarity index 100%
rename from src/game/poker/actions/action.h
rename to src/game/pokerbackup/actions/action.h
diff --git a/src/game/poker/actions/bet.c b/src/game/pokerbackup/actions/bet.c
similarity index 100%
rename from src/game/poker/actions/bet.c
rename to src/game/pokerbackup/actions/bet.c
diff --git a/src/game/poker/actions/bet.h b/src/game/pokerbackup/actions/bet.h
similarity index 100%
rename from src/game/poker/actions/bet.h
rename to src/game/pokerbackup/actions/bet.h
diff --git a/src/game/poker/actions/flop.c b/src/game/pokerbackup/actions/flop.c
similarity index 100%
rename from src/game/poker/actions/flop.c
rename to src/game/pokerbackup/actions/flop.c
diff --git a/src/game/poker/actions/flop.h b/src/game/pokerbackup/actions/flop.h
similarity index 100%
rename from src/game/poker/actions/flop.h
rename to src/game/pokerbackup/actions/flop.h
diff --git a/src/game/poker/actions/look.c b/src/game/pokerbackup/actions/look.c
similarity index 100%
rename from src/game/poker/actions/look.c
rename to src/game/pokerbackup/actions/look.c
diff --git a/src/game/poker/actions/look.h b/src/game/pokerbackup/actions/look.h
similarity index 100%
rename from src/game/poker/actions/look.h
rename to src/game/pokerbackup/actions/look.h
diff --git a/src/game/poker/actions/restack.c b/src/game/pokerbackup/actions/restack.c
similarity index 100%
rename from src/game/poker/actions/restack.c
rename to src/game/pokerbackup/actions/restack.c
diff --git a/src/game/poker/actions/restack.h b/src/game/pokerbackup/actions/restack.h
similarity index 100%
rename from src/game/poker/actions/restack.h
rename to src/game/pokerbackup/actions/restack.h
diff --git a/src/game/poker/actions/round.c b/src/game/pokerbackup/actions/round.c
similarity index 100%
rename from src/game/poker/actions/round.c
rename to src/game/pokerbackup/actions/round.c
diff --git a/src/game/poker/actions/round.h b/src/game/pokerbackup/actions/round.h
similarity index 100%
rename from src/game/poker/actions/round.h
rename to src/game/pokerbackup/actions/round.h
diff --git a/src/game/poker/actions/start.c b/src/game/pokerbackup/actions/start.c
similarity index 100%
rename from src/game/poker/actions/start.c
rename to src/game/pokerbackup/actions/start.c
diff --git a/src/game/poker/actions/start.h b/src/game/pokerbackup/actions/start.h
similarity index 100%
rename from src/game/poker/actions/start.h
rename to src/game/pokerbackup/actions/start.h
diff --git a/src/game/poker/actions/winner.c b/src/game/pokerbackup/actions/winner.c
similarity index 100%
rename from src/game/poker/actions/winner.c
rename to src/game/pokerbackup/actions/winner.c
diff --git a/src/game/poker/actions/winner.h b/src/game/pokerbackup/actions/winner.h
similarity index 100%
rename from src/game/poker/actions/winner.h
rename to src/game/pokerbackup/actions/winner.h
diff --git a/src/game/poker/characters/characters.c b/src/game/pokerbackup/characters/characters.c
similarity index 100%
rename from src/game/poker/characters/characters.c
rename to src/game/pokerbackup/characters/characters.c
diff --git a/src/game/poker/characters/characters.h b/src/game/pokerbackup/characters/characters.h
similarity index 100%
rename from src/game/poker/characters/characters.h
rename to src/game/pokerbackup/characters/characters.h
diff --git a/src/game/poker/characters/jenny.c b/src/game/pokerbackup/characters/jenny.c
similarity index 100%
rename from src/game/poker/characters/jenny.c
rename to src/game/pokerbackup/characters/jenny.c
diff --git a/src/game/poker/characters/jenny.h b/src/game/pokerbackup/characters/jenny.h
similarity index 100%
rename from src/game/poker/characters/jenny.h
rename to src/game/pokerbackup/characters/jenny.h
diff --git a/src/game/poker/characters/julie.c b/src/game/pokerbackup/characters/julie.c
similarity index 100%
rename from src/game/poker/characters/julie.c
rename to src/game/pokerbackup/characters/julie.c
diff --git a/src/game/poker/characters/julie.h b/src/game/pokerbackup/characters/julie.h
similarity index 100%
rename from src/game/poker/characters/julie.h
rename to src/game/pokerbackup/characters/julie.h
diff --git a/src/game/poker/characters/lucy.c b/src/game/pokerbackup/characters/lucy.c
similarity index 100%
rename from src/game/poker/characters/lucy.c
rename to src/game/pokerbackup/characters/lucy.c
diff --git a/src/game/poker/characters/lucy.h b/src/game/pokerbackup/characters/lucy.h
similarity index 100%
rename from src/game/poker/characters/lucy.h
rename to src/game/pokerbackup/characters/lucy.h
diff --git a/src/game/poker/characters/penny.c b/src/game/pokerbackup/characters/penny.c
similarity index 100%
rename from src/game/poker/characters/penny.c
rename to src/game/pokerbackup/characters/penny.c
diff --git a/src/game/poker/characters/penny.h b/src/game/pokerbackup/characters/penny.h
similarity index 100%
rename from src/game/poker/characters/penny.h
rename to src/game/pokerbackup/characters/penny.h
diff --git a/src/game/poker/characters/sammy.c b/src/game/pokerbackup/characters/sammy.c
similarity index 100%
rename from src/game/poker/characters/sammy.c
rename to src/game/pokerbackup/characters/sammy.c
diff --git a/src/game/poker/characters/sammy.h b/src/game/pokerbackup/characters/sammy.h
similarity index 100%
rename from src/game/poker/characters/sammy.h
rename to src/game/pokerbackup/characters/sammy.h
diff --git a/src/game/pokerbackup/game.c b/src/game/pokerbackup/game.c
new file mode 100644
index 00000000..b5f8ac0c
--- /dev/null
+++ b/src/game/pokerbackup/game.c
@@ -0,0 +1,83 @@
+/**
+ * Copyright (c) 2021 Dominic Masters
+ * 
+ * This software is released under the MIT License.
+ * https://opensource.org/licenses/MIT
+ */
+
+#include "game.h"
+
+bool pokerGameInit(pokergame_t *game) {
+  // Begin to load the assets.
+  pokerGameAssetsInit(&game->assets);
+  loadingSceneInit(&game->loadingScene, &game->assets.manager);
+  loadingSceneStart(&game->loadingScene);
+
+  return true;
+} 
+
+void pokerGameUpdate(pokergame_t *game) {
+  bool t;
+  if(!game->loadingScene.manager->finished) {
+    t = loadingSceneUpdate(&game->loadingScene);
+    if(t) {
+      // Initialize the Visual Novel Engine.
+      vnSceneInit(&game->scene,
+        &game->assets.font,
+        &game->assets.testTexture
+      );
+
+      // Initialize the world
+      pokerWorldInit(&game->world, &game->scene, &game->assets);
+
+      // Initialize the UI.
+      pokerUiInit(&game->ui);
+
+      // Add the first action, the game action, and then start the action queue.
+      pokerGameActionStartAdd(game);
+      queueNext(&game->scene.conversation.actionQueue);
+    } else {
+      loadingSceneRender(&game->loadingScene);
+      return;
+    }
+  }
+
+  // Update the VN Engine.
+  vnSceneUpdate(&game->scene, &game->engine);
+
+  // Update the UI
+  pokerUiUpdate(
+    &game->ui,
+    &game->engine,
+    &game->assets.shader,
+    game->scene.characters,
+    game->poker.players
+  );
+
+  // Bind the shader.
+  shaderUse(&game->assets.shader);
+
+  // Render the visual novel scene.
+  vnSceneRenderWorld(&game->scene, &game->engine, &game->assets.shader);
+
+  pokerWorldRender(&game->world, &game->assets);
+  vnSceneRenderCharacters(&game->scene, &game->assets.shader);
+
+  // Render the UI
+  vnSceneRenderGui(&game->scene, &game->engine, &game->assets.shader);
+  pokerUiRender(&game->ui, &game->engine, &game->assets, &game->poker);
+}
+
+void pokerGameDispose(pokergame_t *game) {
+  //Cleanup the UI
+  pokerUiDispose(&game->ui);
+
+  // Cleanup the world
+  pokerWorldDispose(&game->world);
+
+  // Destroy the Visual Novel engine.
+  vnSceneDispose(&game->scene);
+
+  // Unload all assets
+  pokerGameAssetsDispose(&game->assets);
+}
diff --git a/src/game/pokerbackup/game.h b/src/game/pokerbackup/game.h
new file mode 100644
index 00000000..0e33de10
--- /dev/null
+++ b/src/game/pokerbackup/game.h
@@ -0,0 +1,41 @@
+/**
+ * Copyright (c) 2021 Dominic Masters
+ * 
+ * This software is released under the MIT License.
+ * https://opensource.org/licenses/MIT
+ */
+
+#pragma once
+#include "../../libs.h"
+#include "../../poker/poker.h"
+#include "../../vn/conversation/talk.h"
+#include "../../vn/vnscene.h"
+#include "../../util/array.h"
+#include "../../engine/thread.h"
+#include "../../scene/loadingscene.h"
+#include "pokergame.h"
+#include "pokergameassets.h"
+#include "pokerui.h"
+#include "pokerworld.h"
+#include "pokergameaction.h"
+#include "actions/start.h"
+
+/**
+ * Initializes the game state for the poker game.
+ * 
+ * @param game Game to initialize.
+ * @returns True if successful, otherwise false.
+ */
+bool pokerGameInit(pokergame_t *game);
+
+/**
+ * Updates the poker game instance.
+ * @param game Poker game to update for.
+ */
+void pokerGameUpdate(pokergame_t *game);
+
+/**
+ * Disposes a previously initialized poker game instance.
+ * @param game Game to dispose.
+ */
+void pokerGameDispose(pokergame_t *game);
\ No newline at end of file
diff --git a/src/game/poker/pokerdiscussion.c b/src/game/pokerbackup/pokerdiscussion.c
similarity index 100%
rename from src/game/poker/pokerdiscussion.c
rename to src/game/pokerbackup/pokerdiscussion.c
diff --git a/src/game/poker/pokerdiscussion.h b/src/game/pokerbackup/pokerdiscussion.h
similarity index 100%
rename from src/game/poker/pokerdiscussion.h
rename to src/game/pokerbackup/pokerdiscussion.h
diff --git a/src/game/poker/pokergame.c b/src/game/pokerbackup/pokergame.c
similarity index 100%
rename from src/game/poker/pokergame.c
rename to src/game/pokerbackup/pokergame.c
diff --git a/src/game/poker/pokergame.h b/src/game/pokerbackup/pokergame.h
similarity index 100%
rename from src/game/poker/pokergame.h
rename to src/game/pokerbackup/pokergame.h
diff --git a/src/game/poker/pokergameaction.h b/src/game/pokerbackup/pokergameaction.h
similarity index 100%
rename from src/game/poker/pokergameaction.h
rename to src/game/pokerbackup/pokergameaction.h
diff --git a/src/game/poker/pokergameassets.c b/src/game/pokerbackup/pokergameassets.c
similarity index 100%
rename from src/game/poker/pokergameassets.c
rename to src/game/pokerbackup/pokergameassets.c
diff --git a/src/game/poker/pokergameassets.h b/src/game/pokerbackup/pokergameassets.h
similarity index 100%
rename from src/game/poker/pokergameassets.h
rename to src/game/pokerbackup/pokergameassets.h
diff --git a/src/game/poker/pokerui.c b/src/game/pokerbackup/pokerui.c
similarity index 100%
rename from src/game/poker/pokerui.c
rename to src/game/pokerbackup/pokerui.c
diff --git a/src/game/poker/pokerui.h b/src/game/pokerbackup/pokerui.h
similarity index 100%
rename from src/game/poker/pokerui.h
rename to src/game/pokerbackup/pokerui.h
diff --git a/src/game/poker/pokerworld.c b/src/game/pokerbackup/pokerworld.c
similarity index 100%
rename from src/game/poker/pokerworld.c
rename to src/game/pokerbackup/pokerworld.c
diff --git a/src/game/poker/pokerworld.h b/src/game/pokerbackup/pokerworld.h
similarity index 100%
rename from src/game/poker/pokerworld.h
rename to src/game/pokerbackup/pokerworld.h
diff --git a/src/scene/scene.c b/src/scene/scene.c
index 6c1a458f..1f9fc450 100644
--- a/src/scene/scene.c
+++ b/src/scene/scene.c
@@ -7,39 +7,66 @@
 
 #include "scene.h"
 
-void sceneInit(scene_t *scene, engine_t *engine) {
+void sceneInit(scene_t *scene, engine_t *engine, void *user) {
   scene->engine = engine;
   scene->assetOwner = assetManagerHolderCreate(&engine->assetManager);
-  renderListInit(&scene->renderList,
-    (int32_t)engine->render.width, (int32_t)engine->render.height
-  );
+  scene->user = user;
+  scene->onLoaded = NULL;
+  scene->onRender = NULL;
+  scene->loaded = false;
+  renderListInit(&scene->renderList, (int32_t)1, (int32_t)1);
 }
 
-void sceneRenderStart(scene_t *scene) {
-  renderListResize(&scene->renderList,
-    (int32_t)scene->engine->render.width, (int32_t)scene->engine->render.height
-  );
-}
-
-void sceneRenderEnd(
-  scene_t *scene,
-  shader_t *shaderRenderList,
-  shaderuniform_t listUniformView, shaderuniform_t listUniformProjection,
-  shaderuniform_t listUniformModel, shaderuniform_t listUniformTextures[],
-  shader_t *shaderBackBuffer,
-  shaderuniform_t backUniformView, shaderuniform_t backUniformProjection,
-  shaderuniform_t backUniformModel, shaderuniform_t backUniformTexture
+float sceneUpdate(
+  scene_t *scene, int32_t width, int32_t height, shader_t *shader,
+  shaderuniform_t *uniforms
 ) {
-  if(shaderRenderList == NULL || shaderBackBuffer == NULL) return;
-  renderListRender(&scene->renderList, shaderRenderList,
-    listUniformView, listUniformProjection,listUniformModel, listUniformTextures
+  // First, lets check how loading has been going
+  float n = assetManagerProgressGetForHolder(
+    &scene->engine->assetManager, scene->assetOwner
   );
+
+  // TODO: Loading screen
+  if(n < 1.0f) return n;
+
+  // Fire event
+  if(!scene->loaded) {
+    scene->loaded = true;
+    if(scene->onLoaded != NULL) scene->onLoaded(scene);
+  }
+
+  // Resize the render list
+  renderListResize(&scene->renderList, width, height);
+
+  // Fire callback
+  if(scene->onRender != NULL) scene->onRender(scene);
+
+  // Render the render list itself.
+  renderListRender(&scene->renderList, shader, uniforms);
+
+  return n;
+}
+
+void sceneUpdateToBackbuffer(scene_t *scene,
+  shader_t *shaderRenderList, shaderuniform_t *listUniforms,
+  shader_t *shaderBackBuffer, shaderuniform_t *backUniforms
+) {
+  float n = sceneUpdate(scene,
+    (int32_t)scene->engine->render.width, (int32_t)scene->engine->render.height,
+    shaderRenderList, listUniforms
+  );
+  if(n < 1.0f) return;
+
   renderListAsBackbuffer(&scene->renderList, scene->engine, shaderBackBuffer,
-    backUniformView, backUniformProjection, backUniformModel, backUniformTexture
+    backUniforms
   );
 }
 
 void sceneDispose(scene_t *scene) {
   assetManagerHolderRelease(&scene->engine->assetManager, scene->assetOwner);
   renderListDispose(&scene->renderList);
+}
+
+renderpass_t * sceneUsePass(scene_t *scene, uint8_t i) {
+  return renderListRenderPass(&scene->renderList, scene->engine, i);
 }
\ No newline at end of file
diff --git a/src/scene/scene.h b/src/scene/scene.h
index b6ca6167..635efc93 100644
--- a/src/scene/scene.h
+++ b/src/scene/scene.h
@@ -12,21 +12,39 @@
 #include "../display/renderlist.h"
 #include "../display/shader/shader.h"
 
-typedef struct {
+// Forwarder for scene_t
+typedef struct _scene_t scene_t;
+
+// Callbacks
+typedef void scenecallback_t(scene_t *scene);
+
+// Scene Definition
+typedef struct _scene_t {
   engine_t *engine;
   assetmanagerowner_t assetOwner;
   renderlist_t renderList;
+  void *user;
+
+  bool loaded;
+
+  /** Scene Callbacks */
+  scenecallback_t *onLoaded;
+  scenecallback_t *onRender;
 } scene_t;
 
-void sceneInit(scene_t *scene, engine_t *engine);
-void sceneRenderStart(scene_t *scene);
-void sceneRenderEnd(
-  scene_t *scene,
-  shader_t *shaderRenderList,
-  shaderuniform_t listUniformView, shaderuniform_t listUniformProjection,
-  shaderuniform_t listUniformModel, shaderuniform_t listUniformTextures[],
-  shader_t *shaderBackBuffer,
-  shaderuniform_t backUniformView, shaderuniform_t backUniformProjection,
-  shaderuniform_t backUniformModel, shaderuniform_t backUniformTexture
+void sceneInit(scene_t *scene, engine_t *engine, void *user);
+
+
+float sceneUpdate(
+  scene_t *scene, int32_t width, int32_t height, shader_t *shader,
+  shaderuniform_t *uniforms
 );
-void sceneDispose(scene_t *scene);
\ No newline at end of file
+
+void sceneUpdateToBackbuffer(scene_t *scene,
+  shader_t *shaderRenderList, shaderuniform_t *listUniforms,
+  shader_t *shaderBackBuffer, shaderuniform_t *backUniforms
+);
+
+void sceneDispose(scene_t *scene);
+
+renderpass_t * sceneUsePass(scene_t *scene, uint8_t i);
\ No newline at end of file
diff --git a/tools/display/CMakeLists.txt b/tools/display/CMakeLists.txt
index ec60d1e1..40cb95b2 100644
--- a/tools/display/CMakeLists.txt
+++ b/tools/display/CMakeLists.txt
@@ -7,7 +7,7 @@ cmake_minimum_required(VERSION 3.13)
 set(CMAKE_C_STANDARD 99)
 set(CMAKE_C_STANDARD_REQUIRED ON)
 
-# Build Tool
+# Texture Build Tool
 project(texture_generation VERSION 1.0)
 add_executable(texture_generation)
 target_sources(texture_generation
@@ -16,7 +16,7 @@ target_sources(texture_generation
     ../utils/file.c
     ../utils/image.c
 )
-target_include_directories(${PROJECT_NAME}
+target_include_directories(texture_generation
   PUBLIC
     ${CMAKE_CURRENT_LIST_DIR}/../
 )
diff --git a/tools/utils/common.h b/tools/utils/common.h
index 4eb59e30..28c9a9f9 100644
--- a/tools/utils/common.h
+++ b/tools/utils/common.h
@@ -11,8 +11,4 @@
 #include <stdlib.h>
 #include <stdint.h>
 #include <stdbool.h>
-#include <string.h>
-
-#include <stb_image.h>
-#include <stb_image_resize.h>
-#include <stb_image_write.h>
+#include <string.h>
\ No newline at end of file
diff --git a/tools/utils/image.h b/tools/utils/image.h
index 35e48bdf..040d5189 100644
--- a/tools/utils/image.h
+++ b/tools/utils/image.h
@@ -9,6 +9,10 @@
 #include "common.h"
 #include "file.h"
 
+#include <stb_image.h>
+#include <stb_image_resize.h>
+#include <stb_image_write.h>
+
 void imageCopy(
   uint8_t *source, int32_t sourceWidth, int32_t sourceHeight,
   uint8_t *dest, int32_t destWidth, int32_t destHeight,