mirror of
https://github.com/ZDoom/raze-gles.git
synced 2024-12-25 03:00:46 +00:00
- hooked up the 2D drawer
compiles but not tested yet.
This commit is contained in:
parent
341ca9dd3a
commit
de829128ea
19 changed files with 676 additions and 63 deletions
|
@ -713,6 +713,8 @@ set (PCH_SOURCES
|
||||||
glbackend/glbackend.cpp
|
glbackend/glbackend.cpp
|
||||||
glbackend/gl_palmanager.cpp
|
glbackend/gl_palmanager.cpp
|
||||||
glbackend/gl_texture.cpp
|
glbackend/gl_texture.cpp
|
||||||
|
glbackend/gl_buffers.cpp
|
||||||
|
glbackend/hw_draw2d.cpp
|
||||||
|
|
||||||
mact/src/animlib.cpp
|
mact/src/animlib.cpp
|
||||||
mact/src/control.cpp
|
mact/src/control.cpp
|
||||||
|
|
|
@ -108,6 +108,8 @@ enum ERenderAlpha
|
||||||
STYLEALPHA_InvSrcCol, // Blend factor is 1.0 - color (HWR only)
|
STYLEALPHA_InvSrcCol, // Blend factor is 1.0 - color (HWR only)
|
||||||
STYLEALPHA_DstCol, // Blend factor is dest. color (HWR only)
|
STYLEALPHA_DstCol, // Blend factor is dest. color (HWR only)
|
||||||
STYLEALPHA_InvDstCol, // Blend factor is 1.0 - dest. color (HWR only)
|
STYLEALPHA_InvDstCol, // Blend factor is 1.0 - dest. color (HWR only)
|
||||||
|
STYLEALPHA_Dst, // Blend factor is dest. alpha
|
||||||
|
STYLEALPHA_InvDst, // Blend factor is 1.0 - dest. alpha
|
||||||
STYLEALPHA_MAX
|
STYLEALPHA_MAX
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
|
@ -247,7 +247,7 @@ void F2DDrawer::AddTexture(FTexture *img, DrawParms &parms)
|
||||||
dg.mVertCount = 4;
|
dg.mVertCount = 4;
|
||||||
dg.mTexture = img;
|
dg.mTexture = img;
|
||||||
|
|
||||||
dg.mTranslation = 0;
|
dg.mRemapIndex = parms.remap;
|
||||||
SetStyle(img, parms, vertexcolor, dg);
|
SetStyle(img, parms, vertexcolor, dg);
|
||||||
|
|
||||||
u1 = parms.srcx;
|
u1 = parms.srcx;
|
||||||
|
|
|
@ -67,7 +67,7 @@ public:
|
||||||
int mIndexCount;
|
int mIndexCount;
|
||||||
|
|
||||||
FTexture *mTexture;
|
FTexture *mTexture;
|
||||||
FRemapTable *mTranslation;
|
int mRemapIndex;
|
||||||
PalEntry mSpecialColormap[2];
|
PalEntry mSpecialColormap[2];
|
||||||
int mScissor[4];
|
int mScissor[4];
|
||||||
int mDesaturate;
|
int mDesaturate;
|
||||||
|
@ -86,7 +86,7 @@ public:
|
||||||
{
|
{
|
||||||
return mTexture == other.mTexture &&
|
return mTexture == other.mTexture &&
|
||||||
mType == other.mType &&
|
mType == other.mType &&
|
||||||
mTranslation == other.mTranslation &&
|
mRemapIndex == other.mRemapIndex &&
|
||||||
mSpecialColormap[0].d == other.mSpecialColormap[0].d &&
|
mSpecialColormap[0].d == other.mSpecialColormap[0].d &&
|
||||||
mSpecialColormap[1].d == other.mSpecialColormap[1].d &&
|
mSpecialColormap[1].d == other.mSpecialColormap[1].d &&
|
||||||
!memcmp(mScissor, other.mScissor, sizeof(mScissor)) &&
|
!memcmp(mScissor, other.mScissor, sizeof(mScissor)) &&
|
||||||
|
|
|
@ -265,7 +265,7 @@ bool ParseDrawTextureTags(FTexture *img, double x, double y, uint32_t tag, Va_Li
|
||||||
parms->burn = false;
|
parms->burn = false;
|
||||||
parms->monospace = EMonospacing::Off;
|
parms->monospace = EMonospacing::Off;
|
||||||
parms->spacing = 0;
|
parms->spacing = 0;
|
||||||
parms->remap = 0;
|
parms->remap = -1;
|
||||||
|
|
||||||
// Parse the tag list for attributes. (For floating point attributes,
|
// Parse the tag list for attributes. (For floating point attributes,
|
||||||
// consider that the C ABI dictates that all floats be promoted to
|
// consider that the C ABI dictates that all floats be promoted to
|
||||||
|
|
|
@ -126,7 +126,7 @@ void DrawTextCommon(F2DDrawer* drawer, FFont *font, int normalcolor, double x, d
|
||||||
double cx;
|
double cx;
|
||||||
double cy;
|
double cy;
|
||||||
int boldcolor;
|
int boldcolor;
|
||||||
FRemapTable *range;
|
int range;
|
||||||
int kerning;
|
int kerning;
|
||||||
FTexture *pic;
|
FTexture *pic;
|
||||||
|
|
||||||
|
|
|
@ -52,6 +52,7 @@
|
||||||
#include "myiswalpha.h"
|
#include "myiswalpha.h"
|
||||||
#include "fontchars.h"
|
#include "fontchars.h"
|
||||||
#include "imagehelpers.h"
|
#include "imagehelpers.h"
|
||||||
|
#include "glbackend/glbackend.h"
|
||||||
|
|
||||||
#include "fontinternals.h"
|
#include "fontinternals.h"
|
||||||
|
|
||||||
|
@ -219,7 +220,7 @@ void FFont::SetDefaultTranslation(uint32_t *othercolors)
|
||||||
SimpleTranslation(mycolors, mytranslation, myreverse, myluminosity);
|
SimpleTranslation(mycolors, mytranslation, myreverse, myluminosity);
|
||||||
SimpleTranslation(othercolors, othertranslation, otherreverse, otherluminosity);
|
SimpleTranslation(othercolors, othertranslation, otherreverse, otherluminosity);
|
||||||
|
|
||||||
FRemapTable remap(ActiveColors);
|
FRemapTable remap;
|
||||||
remap.Palette[0] = 0;
|
remap.Palette[0] = 0;
|
||||||
|
|
||||||
for (unsigned l = 1; l < myluminosity.Size(); l++)
|
for (unsigned l = 1; l < myluminosity.Size(); l++)
|
||||||
|
@ -247,7 +248,7 @@ void FFont::SetDefaultTranslation(uint32_t *othercolors)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Ranges[CR_UNTRANSLATED] = remap;
|
Ranges[CR_UNTRANSLATED] = GLInterface.GetPaletteIndex(remap.Palette);
|
||||||
forceremap = true;
|
forceremap = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -355,7 +356,7 @@ void FFont::BuildTranslations (const double *luminosity, const uint8_t *identity
|
||||||
int i, j;
|
int i, j;
|
||||||
const TranslationParm *parmstart = (const TranslationParm *)ranges;
|
const TranslationParm *parmstart = (const TranslationParm *)ranges;
|
||||||
|
|
||||||
FRemapTable remap(total_colors);
|
FRemapTable remap;
|
||||||
|
|
||||||
// Create different translations for different color ranges
|
// Create different translations for different color ranges
|
||||||
Ranges.Clear();
|
Ranges.Clear();
|
||||||
|
@ -380,15 +381,14 @@ void FFont::BuildTranslations (const double *luminosity, const uint8_t *identity
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
remap = Ranges[0];
|
|
||||||
}
|
}
|
||||||
Ranges.Push(remap);
|
Ranges.Push(GLInterface.GetPaletteIndex(remap.Palette));
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
assert(parmstart->RangeStart >= 0);
|
assert(parmstart->RangeStart >= 0);
|
||||||
|
|
||||||
remap.Palette[255] = 0;
|
remap.Palette[0] = 0;
|
||||||
|
|
||||||
for (j = 0; j < ActiveColors; j++)
|
for (j = 0; j < ActiveColors; j++)
|
||||||
{
|
{
|
||||||
|
@ -414,7 +414,8 @@ void FFont::BuildTranslations (const double *luminosity, const uint8_t *identity
|
||||||
b = clamp(b, 0, 255);
|
b = clamp(b, 0, 255);
|
||||||
remap.Palette[j] = PalEntry(255,r,g,b);
|
remap.Palette[j] = PalEntry(255,r,g,b);
|
||||||
}
|
}
|
||||||
Ranges.Push(remap);
|
|
||||||
|
Ranges.Push(GLInterface.GetPaletteIndex(remap.Palette));
|
||||||
|
|
||||||
// Advance to the next color range.
|
// Advance to the next color range.
|
||||||
while (parmstart[1].RangeStart > parmstart[0].RangeEnd)
|
while (parmstart[1].RangeStart > parmstart[0].RangeEnd)
|
||||||
|
@ -431,7 +432,7 @@ void FFont::BuildTranslations (const double *luminosity, const uint8_t *identity
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
FRemapTable *FFont::GetColorTranslation (EColorRange range, PalEntry *color) const
|
int FFont::GetColorTranslation (EColorRange range, PalEntry *color) const
|
||||||
{
|
{
|
||||||
if (noTranslate)
|
if (noTranslate)
|
||||||
{
|
{
|
||||||
|
@ -444,11 +445,11 @@ FRemapTable *FFont::GetColorTranslation (EColorRange range, PalEntry *color) con
|
||||||
if (color != nullptr) *color = retcolor;
|
if (color != nullptr) *color = retcolor;
|
||||||
}
|
}
|
||||||
if (ActiveColors == 0)
|
if (ActiveColors == 0)
|
||||||
return nullptr;
|
return -1;
|
||||||
else if (range >= NumTextColors)
|
else if (range >= NumTextColors)
|
||||||
range = CR_UNTRANSLATED;
|
range = CR_UNTRANSLATED;
|
||||||
//if (range == CR_UNTRANSLATED && !translateUntranslated) return nullptr;
|
//if (range == CR_UNTRANSLATED && !translateUntranslated) return nullptr;
|
||||||
return &Ranges[range];
|
return Ranges[range];
|
||||||
}
|
}
|
||||||
|
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
|
@ -376,8 +376,8 @@ public:
|
||||||
|
|
||||||
SimpleTranslation(colors, othertranslation, otherreverse, otherluminosity);
|
SimpleTranslation(colors, othertranslation, otherreverse, otherluminosity);
|
||||||
|
|
||||||
FRemapTable remap(ActiveColors);
|
FRemapTable remap;
|
||||||
remap.Palette[255] = 0;
|
remap.Palette[0] = 0;
|
||||||
|
|
||||||
for (unsigned l = 1; l < 18; l++)
|
for (unsigned l = 1; l < 18; l++)
|
||||||
{
|
{
|
||||||
|
|
|
@ -99,7 +99,7 @@ public:
|
||||||
|
|
||||||
virtual FTexture *GetChar (int code, int translation, int *const width, bool *redirected = nullptr) const;
|
virtual FTexture *GetChar (int code, int translation, int *const width, bool *redirected = nullptr) const;
|
||||||
virtual int GetCharWidth (int code) const;
|
virtual int GetCharWidth (int code) const;
|
||||||
FRemapTable *GetColorTranslation (EColorRange range, PalEntry *color = nullptr) const;
|
int GetColorTranslation (EColorRange range, PalEntry *color = nullptr) const;
|
||||||
int GetSpaceWidth () const { return SpaceWidth; }
|
int GetSpaceWidth () const { return SpaceWidth; }
|
||||||
int GetHeight () const { return FontHeight; }
|
int GetHeight () const { return FontHeight; }
|
||||||
int GetDefaultKerning () const { return GlobalKerning; }
|
int GetDefaultKerning () const { return GlobalKerning; }
|
||||||
|
@ -164,7 +164,7 @@ protected:
|
||||||
};
|
};
|
||||||
TArray<CharData> Chars;
|
TArray<CharData> Chars;
|
||||||
int ActiveColors;
|
int ActiveColors;
|
||||||
TArray<FRemapTable> Ranges;
|
TArray<int> Ranges;
|
||||||
uint8_t PatchRemap[256];
|
uint8_t PatchRemap[256];
|
||||||
|
|
||||||
FName FontName = NAME_None;
|
FName FontName = NAME_None;
|
||||||
|
@ -192,17 +192,7 @@ char* CleanseString(char* str);
|
||||||
|
|
||||||
struct FRemapTable
|
struct FRemapTable
|
||||||
{
|
{
|
||||||
FRemapTable(int count = 256) {}
|
PalEntry Palette[256] = { }; // The ideal palette this maps to
|
||||||
~FRemapTable() { delete Palette; }
|
|
||||||
|
|
||||||
PalEntry *Palette = nullptr; // The ideal palette this maps to
|
|
||||||
int PalIndex;
|
|
||||||
int NumEntries; // # of elements in this table (usually 256)
|
|
||||||
bool Inactive; // This table is inactive and should be treated as if it was passed as NULL
|
|
||||||
|
|
||||||
private:
|
|
||||||
void Free();
|
|
||||||
void Alloc(int count);
|
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -1,3 +1,4 @@
|
||||||
|
#pragma once
|
||||||
/*
|
/*
|
||||||
|
|
||||||
OpenGL loader generated by glad 0.1.33 on Mon Sep 16 17:51:07 2019.
|
OpenGL loader generated by glad 0.1.33 on Mon Sep 16 17:51:07 2019.
|
||||||
|
|
83
source/glbackend/buffers.h
Normal file
83
source/glbackend/buffers.h
Normal file
|
@ -0,0 +1,83 @@
|
||||||
|
#pragma once
|
||||||
|
|
||||||
|
#include <stddef.h>
|
||||||
|
#include <assert.h>
|
||||||
|
|
||||||
|
class FRenderState;
|
||||||
|
|
||||||
|
// The low level code needs to know which attributes exist.
|
||||||
|
// OpenGL needs to change the state of all of them per buffer binding.
|
||||||
|
// VAOs are mostly useless for this because they lump buffer and binding state together which the model code does not want.
|
||||||
|
enum
|
||||||
|
{
|
||||||
|
VATTR_VERTEX,
|
||||||
|
VATTR_TEXCOORD,
|
||||||
|
VATTR_COLOR,
|
||||||
|
VATTR_VERTEX2,
|
||||||
|
VATTR_NORMAL,
|
||||||
|
VATTR_NORMAL2,
|
||||||
|
|
||||||
|
VATTR_MAX
|
||||||
|
};
|
||||||
|
|
||||||
|
enum EVertexAttributeFormat
|
||||||
|
{
|
||||||
|
VFmt_Float4,
|
||||||
|
VFmt_Float3,
|
||||||
|
VFmt_Float2,
|
||||||
|
VFmt_Float,
|
||||||
|
VFmt_Byte4,
|
||||||
|
VFmt_Packed_A2R10G10B10,
|
||||||
|
};
|
||||||
|
|
||||||
|
struct FVertexBufferAttribute
|
||||||
|
{
|
||||||
|
int binding;
|
||||||
|
int location;
|
||||||
|
int format;
|
||||||
|
int offset;
|
||||||
|
};
|
||||||
|
|
||||||
|
class IBuffer
|
||||||
|
{
|
||||||
|
protected:
|
||||||
|
size_t buffersize = 0;
|
||||||
|
void *map = nullptr;
|
||||||
|
public:
|
||||||
|
IBuffer() = default;
|
||||||
|
IBuffer(const IBuffer &) = delete;
|
||||||
|
IBuffer &operator=(const IBuffer &) = delete;
|
||||||
|
virtual ~IBuffer() = default;
|
||||||
|
|
||||||
|
virtual void SetData(size_t size, const void *data, bool staticdata = true) = 0;
|
||||||
|
virtual void SetSubData(size_t offset, size_t size, const void *data) = 0;
|
||||||
|
virtual void *Lock(unsigned int size) = 0;
|
||||||
|
virtual void Unlock() = 0;
|
||||||
|
virtual void Resize(size_t newsize) = 0;
|
||||||
|
virtual void Map() {} // Only needed by old OpenGL but this needs to be in the interface.
|
||||||
|
virtual void Unmap() {}
|
||||||
|
void *Memory() { assert(map); return map; }
|
||||||
|
size_t Size() { return buffersize; }
|
||||||
|
};
|
||||||
|
|
||||||
|
class IVertexBuffer : virtual public IBuffer
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
virtual void SetFormat(int numBindingPoints, int numAttributes, size_t stride, const FVertexBufferAttribute *attrs) = 0;
|
||||||
|
};
|
||||||
|
|
||||||
|
// This merely exists to have a dedicated type for index buffers to inherit from.
|
||||||
|
class IIndexBuffer : virtual public IBuffer
|
||||||
|
{
|
||||||
|
// Element size is fixed to 4, thanks to OpenGL requiring this info to be coded into the glDrawElements call.
|
||||||
|
// This mostly prohibits a more flexible buffer setup but GZDoom doesn't use any other format anyway.
|
||||||
|
// Ob Vulkam, element size is a buffer property and of no concern to the drawing functions (as it should be.)
|
||||||
|
};
|
||||||
|
|
||||||
|
class IDataBuffer : virtual public IBuffer
|
||||||
|
{
|
||||||
|
// Can be either uniform or shader storage buffer, depending on its needs.
|
||||||
|
public:
|
||||||
|
virtual void BindRange(FRenderState *state, size_t start, size_t length) = 0;
|
||||||
|
|
||||||
|
};
|
218
source/glbackend/gl_buffers.cpp
Normal file
218
source/glbackend/gl_buffers.cpp
Normal file
|
@ -0,0 +1,218 @@
|
||||||
|
//
|
||||||
|
//---------------------------------------------------------------------------
|
||||||
|
//
|
||||||
|
// Copyright(C) 2018 Christoph Oelckers
|
||||||
|
// All rights reserved.
|
||||||
|
//
|
||||||
|
// This program is free software: you can redistribute it and/or modify
|
||||||
|
// it under the terms of the GNU Lesser General Public License as published by
|
||||||
|
// the Free Software Foundation, either version 3 of the License, or
|
||||||
|
// (at your option) any later version.
|
||||||
|
//
|
||||||
|
// This program is distributed in the hope that it will be useful,
|
||||||
|
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
// GNU Lesser General Public License for more details.
|
||||||
|
//
|
||||||
|
// You should have received a copy of the GNU Lesser General Public License
|
||||||
|
// along with this program. If not, see http://www.gnu.org/licenses/
|
||||||
|
//
|
||||||
|
//--------------------------------------------------------------------------
|
||||||
|
//
|
||||||
|
/*
|
||||||
|
** Low level vertex buffer class
|
||||||
|
**
|
||||||
|
**/
|
||||||
|
|
||||||
|
#include <algorithm>
|
||||||
|
#include "glad/glad.h"
|
||||||
|
#include "glbackend.h"
|
||||||
|
#include "gl_buffers.h"
|
||||||
|
|
||||||
|
namespace OpenGLRenderer
|
||||||
|
{
|
||||||
|
|
||||||
|
//==========================================================================
|
||||||
|
//
|
||||||
|
// basic buffer implementation
|
||||||
|
//
|
||||||
|
//==========================================================================
|
||||||
|
|
||||||
|
GLBuffer::GLBuffer(int usetype)
|
||||||
|
: mUseType(usetype)
|
||||||
|
{
|
||||||
|
glGenBuffers(1, &mBufferId);
|
||||||
|
}
|
||||||
|
|
||||||
|
GLBuffer::~GLBuffer()
|
||||||
|
{
|
||||||
|
if (mBufferId != 0)
|
||||||
|
{
|
||||||
|
glBindBuffer(mUseType, mBufferId);
|
||||||
|
glUnmapBuffer(mUseType);
|
||||||
|
glBindBuffer(mUseType, 0);
|
||||||
|
glDeleteBuffers(1, &mBufferId);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void GLBuffer::Bind()
|
||||||
|
{
|
||||||
|
glBindBuffer(mUseType, mBufferId);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void GLBuffer::SetData(size_t size, const void *data, bool staticdata)
|
||||||
|
{
|
||||||
|
Bind();
|
||||||
|
if (data != nullptr)
|
||||||
|
{
|
||||||
|
glBufferData(mUseType, size, data, staticdata? GL_STATIC_DRAW : GL_STREAM_DRAW);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
mPersistent = /*screen->BuffersArePersistent() &&*/ !staticdata;
|
||||||
|
if (mPersistent)
|
||||||
|
{
|
||||||
|
glBufferStorage(mUseType, size, nullptr, GL_MAP_WRITE_BIT | GL_MAP_PERSISTENT_BIT | GL_MAP_COHERENT_BIT);
|
||||||
|
map = glMapBufferRange(mUseType, 0, size, GL_MAP_WRITE_BIT | GL_MAP_PERSISTENT_BIT | GL_MAP_COHERENT_BIT);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
glBufferData(mUseType, size, nullptr, staticdata ? GL_STATIC_DRAW : GL_STREAM_DRAW);
|
||||||
|
map = nullptr;
|
||||||
|
}
|
||||||
|
if (!staticdata) nomap = false;
|
||||||
|
}
|
||||||
|
buffersize = size;
|
||||||
|
}
|
||||||
|
|
||||||
|
void GLBuffer::SetSubData(size_t offset, size_t size, const void *data)
|
||||||
|
{
|
||||||
|
Bind();
|
||||||
|
glBufferSubData(mUseType, offset, size, data);
|
||||||
|
}
|
||||||
|
|
||||||
|
void GLBuffer::Map()
|
||||||
|
{
|
||||||
|
assert(nomap == false); // do not allow mapping of static buffers. Vulkan cannot do that so it should be blocked in OpenGL, too.
|
||||||
|
if (!mPersistent && !nomap)
|
||||||
|
{
|
||||||
|
Bind();
|
||||||
|
map = glMapBufferRange(mUseType, 0, buffersize, GL_MAP_WRITE_BIT|GL_MAP_UNSYNCHRONIZED_BIT);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void GLBuffer::Unmap()
|
||||||
|
{
|
||||||
|
assert(nomap == false);
|
||||||
|
if (!mPersistent && map != nullptr)
|
||||||
|
{
|
||||||
|
Bind();
|
||||||
|
glUnmapBuffer(mUseType);
|
||||||
|
map = nullptr;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void *GLBuffer::Lock(unsigned int size)
|
||||||
|
{
|
||||||
|
// This initializes this buffer as a static object with no data.
|
||||||
|
SetData(size, nullptr, true);
|
||||||
|
return glMapBufferRange(mUseType, 0, size, GL_MAP_WRITE_BIT | GL_MAP_INVALIDATE_BUFFER_BIT | GL_MAP_UNSYNCHRONIZED_BIT);
|
||||||
|
}
|
||||||
|
|
||||||
|
void GLBuffer::Unlock()
|
||||||
|
{
|
||||||
|
Bind();
|
||||||
|
glUnmapBuffer(mUseType);
|
||||||
|
}
|
||||||
|
|
||||||
|
void GLBuffer::Resize(size_t newsize)
|
||||||
|
{
|
||||||
|
assert(!nomap); // only mappable buffers can be resized.
|
||||||
|
if (newsize > buffersize && !nomap)
|
||||||
|
{
|
||||||
|
// reallocate the buffer with twice the size
|
||||||
|
unsigned int oldbuffer = mBufferId;
|
||||||
|
|
||||||
|
// first unmap the old buffer
|
||||||
|
Bind();
|
||||||
|
glUnmapBuffer(mUseType);
|
||||||
|
|
||||||
|
glGenBuffers(1, &mBufferId);
|
||||||
|
SetData(newsize, nullptr, false);
|
||||||
|
glBindBuffer(GL_COPY_READ_BUFFER, oldbuffer);
|
||||||
|
|
||||||
|
// copy contents and delete the old buffer.
|
||||||
|
glCopyBufferSubData(GL_COPY_READ_BUFFER, mUseType, 0, 0, buffersize);
|
||||||
|
glBindBuffer(GL_COPY_READ_BUFFER, 0);
|
||||||
|
glDeleteBuffers(1, &oldbuffer);
|
||||||
|
buffersize = newsize;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
//===========================================================================
|
||||||
|
//
|
||||||
|
// Vertex buffer implementation
|
||||||
|
//
|
||||||
|
//===========================================================================
|
||||||
|
|
||||||
|
void GLVertexBuffer::SetFormat(int numBindingPoints, int numAttributes, size_t stride, const FVertexBufferAttribute *attrs)
|
||||||
|
{
|
||||||
|
static int VFmtToGLFmt[] = { GL_FLOAT, GL_FLOAT, GL_FLOAT, GL_FLOAT, GL_UNSIGNED_BYTE, GL_INT_2_10_10_10_REV };
|
||||||
|
static uint8_t VFmtToSize[] = {4, 3, 2, 1, 4, 4};
|
||||||
|
|
||||||
|
mStride = stride;
|
||||||
|
mNumBindingPoints = numBindingPoints;
|
||||||
|
|
||||||
|
for(int i = 0; i < numAttributes; i++)
|
||||||
|
{
|
||||||
|
if (attrs[i].location >= 0 && attrs[i].location < VATTR_MAX)
|
||||||
|
{
|
||||||
|
auto & attrinf = mAttributeInfo[attrs[i].location];
|
||||||
|
attrinf.format = VFmtToGLFmt[attrs[i].format];
|
||||||
|
attrinf.size = VFmtToSize[attrs[i].format];
|
||||||
|
attrinf.offset = attrs[i].offset;
|
||||||
|
attrinf.bindingpoint = attrs[i].binding;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void GLVertexBuffer::Bind(int *offsets)
|
||||||
|
{
|
||||||
|
int i = 0;
|
||||||
|
|
||||||
|
// This is what gets called from RenderState.Apply. It shouldn't be called anywhere else if the render state is in use
|
||||||
|
GLBuffer::Bind();
|
||||||
|
for(auto &attrinf : mAttributeInfo)
|
||||||
|
{
|
||||||
|
if (attrinf.size == 0)
|
||||||
|
{
|
||||||
|
glDisableVertexAttribArray(i);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
glEnableVertexAttribArray(i);
|
||||||
|
size_t ofs = offsets == nullptr ? attrinf.offset : attrinf.offset + mStride * offsets[attrinf.bindingpoint];
|
||||||
|
glVertexAttribPointer(i, attrinf.size, attrinf.format, attrinf.format != GL_FLOAT, (GLsizei)mStride, (void*)(intptr_t)ofs);
|
||||||
|
}
|
||||||
|
i++;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void GLDataBuffer::BindRange(FRenderState *state, size_t start, size_t length)
|
||||||
|
{
|
||||||
|
glBindBufferRange(mUseType, mBindingPoint, mBufferId, start, length);
|
||||||
|
}
|
||||||
|
|
||||||
|
void GLDataBuffer::BindBase()
|
||||||
|
{
|
||||||
|
glBindBufferBase(mUseType, mBindingPoint, mBufferId);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
GLVertexBuffer::GLVertexBuffer() : GLBuffer(GL_ARRAY_BUFFER) {}
|
||||||
|
GLIndexBuffer::GLIndexBuffer() : GLBuffer(GL_ELEMENT_ARRAY_BUFFER) {}
|
||||||
|
GLDataBuffer::GLDataBuffer(int bindingpoint, bool is_ssbo) : GLBuffer(is_ssbo ? GL_SHADER_STORAGE_BUFFER : GL_UNIFORM_BUFFER), mBindingPoint(bindingpoint) {}
|
||||||
|
|
||||||
|
}
|
73
source/glbackend/gl_buffers.h
Normal file
73
source/glbackend/gl_buffers.h
Normal file
|
@ -0,0 +1,73 @@
|
||||||
|
#pragma once
|
||||||
|
|
||||||
|
#include "buffers.h"
|
||||||
|
|
||||||
|
#ifdef _MSC_VER
|
||||||
|
// silence bogus warning C4250: 'GLVertexBuffer': inherits 'GLBuffer::GLBuffer::SetData' via dominance
|
||||||
|
// According to internet infos, the warning is erroneously emitted in this case.
|
||||||
|
#pragma warning(disable:4250)
|
||||||
|
#endif
|
||||||
|
|
||||||
|
namespace OpenGLRenderer
|
||||||
|
{
|
||||||
|
|
||||||
|
class GLBuffer : virtual public IBuffer
|
||||||
|
{
|
||||||
|
protected:
|
||||||
|
const int mUseType;
|
||||||
|
unsigned int mBufferId;
|
||||||
|
int mAllocationSize = 0;
|
||||||
|
bool mPersistent = false;
|
||||||
|
bool nomap = true;
|
||||||
|
|
||||||
|
GLBuffer(int usetype);
|
||||||
|
~GLBuffer();
|
||||||
|
void SetData(size_t size, const void *data, bool staticdata) override;
|
||||||
|
void SetSubData(size_t offset, size_t size, const void *data) override;
|
||||||
|
void Map() override;
|
||||||
|
void Unmap() override;
|
||||||
|
void Resize(size_t newsize) override;
|
||||||
|
void *Lock(unsigned int size) override;
|
||||||
|
void Unlock() override;
|
||||||
|
public:
|
||||||
|
void Bind();
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
class GLVertexBuffer : public IVertexBuffer, public GLBuffer
|
||||||
|
{
|
||||||
|
// If this could use the modern (since GL 4.3) binding system, things would be simpler... :(
|
||||||
|
struct GLVertexBufferAttribute
|
||||||
|
{
|
||||||
|
int bindingpoint;
|
||||||
|
int format;
|
||||||
|
int size;
|
||||||
|
int offset;
|
||||||
|
};
|
||||||
|
|
||||||
|
int mNumBindingPoints;
|
||||||
|
GLVertexBufferAttribute mAttributeInfo[VATTR_MAX] = {}; // Thanks to OpenGL's state system this needs to contain info about every attribute that may ever be in use throughout the entire renderer.
|
||||||
|
size_t mStride = 0;
|
||||||
|
|
||||||
|
public:
|
||||||
|
GLVertexBuffer();
|
||||||
|
void SetFormat(int numBindingPoints, int numAttributes, size_t stride, const FVertexBufferAttribute *attrs) override;
|
||||||
|
void Bind(int *offsets);
|
||||||
|
};
|
||||||
|
|
||||||
|
class GLIndexBuffer : public IIndexBuffer, public GLBuffer
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
GLIndexBuffer();
|
||||||
|
};
|
||||||
|
|
||||||
|
class GLDataBuffer : public IDataBuffer, public GLBuffer
|
||||||
|
{
|
||||||
|
int mBindingPoint;
|
||||||
|
public:
|
||||||
|
GLDataBuffer(int bindingpoint, bool is_ssbo);
|
||||||
|
void BindRange(FRenderState* state, size_t start, size_t length);
|
||||||
|
void BindBase();
|
||||||
|
};
|
||||||
|
|
||||||
|
}
|
|
@ -40,6 +40,7 @@
|
||||||
#include "baselayer.h"
|
#include "baselayer.h"
|
||||||
#include "resourcefile.h"
|
#include "resourcefile.h"
|
||||||
#include "imagehelpers.h"
|
#include "imagehelpers.h"
|
||||||
|
#include "v_font.h"
|
||||||
|
|
||||||
//===========================================================================
|
//===========================================================================
|
||||||
//
|
//
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
#include "PalEntry.h"
|
#include "PalEntry.h"
|
||||||
|
#include "gl_buffers.h"
|
||||||
class PolymostShader;
|
class PolymostShader;
|
||||||
|
|
||||||
enum PRSFlags
|
enum PRSFlags
|
||||||
|
@ -35,5 +36,9 @@ struct PolymostRenderState
|
||||||
float Brightness = 1.f;
|
float Brightness = 1.f;
|
||||||
PalEntry FogColor;
|
PalEntry FogColor;
|
||||||
|
|
||||||
|
IVertexBuffer* VertexBuffer = nullptr;
|
||||||
|
int VB_Offset[2] = {};
|
||||||
|
IIndexBuffer* IndexBuffer = nullptr;
|
||||||
|
|
||||||
void Apply(PolymostShader *shader);
|
void Apply(PolymostShader *shader);
|
||||||
};
|
};
|
||||||
|
|
|
@ -39,6 +39,7 @@
|
||||||
#include "polymost.h"
|
#include "polymost.h"
|
||||||
#include "textures.h"
|
#include "textures.h"
|
||||||
#include "bitmap.h"
|
#include "bitmap.h"
|
||||||
|
#include "v_font.h"
|
||||||
#include "../../glbackend/glbackend.h"
|
#include "../../glbackend/glbackend.h"
|
||||||
|
|
||||||
// Test CVARs.
|
// Test CVARs.
|
||||||
|
@ -155,10 +156,6 @@ FHardwareTexture* GLInstance::LoadTexture(FTexture* tex, int textype, int palid)
|
||||||
|
|
||||||
bool GLInstance::SetTextureInternal(int picnum, FTexture* tex, int palette, int method, int sampleroverride, float xpanning, float ypanning, FTexture *det, float detscale, FTexture *glow)
|
bool GLInstance::SetTextureInternal(int picnum, FTexture* tex, int palette, int method, int sampleroverride, float xpanning, float ypanning, FTexture *det, float detscale, FTexture *glow)
|
||||||
{
|
{
|
||||||
if (picnum == 3692)
|
|
||||||
{
|
|
||||||
int a = 0;
|
|
||||||
}
|
|
||||||
if (tex->GetWidth() <= 0 || tex->GetHeight() <= 0) return false;
|
if (tex->GetWidth() <= 0 || tex->GetHeight() <= 0) return false;
|
||||||
int usepalette = fixpalette >= 1 ? fixpalette - 1 : curbasepal;
|
int usepalette = fixpalette >= 1 ? fixpalette - 1 : curbasepal;
|
||||||
int usepalswap = fixpalswap >= 1 ? fixpalswap - 1 : palette;
|
int usepalswap = fixpalswap >= 1 ? fixpalswap - 1 : palette;
|
||||||
|
@ -180,7 +177,7 @@ bool GLInstance::SetTextureInternal(int picnum, FTexture* tex, int palette, int
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
// Only look up the palette if we really want to use it (i.e. when creating a true color texture of an ART tile.)
|
// Only look up the palette if we really want to use it (i.e. when creating a true color texture of an ART tile.)
|
||||||
if (!hw_useindexedcolortextures) lookuppal = palmanager.LookupPalette(usepalette, usepalswap, false);
|
if (TextureType == TT_TRUECOLOR) lookuppal = palmanager.LookupPalette(usepalette, usepalswap, false);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Load the main texture
|
// Load the main texture
|
||||||
|
@ -291,3 +288,21 @@ bool GLInstance::SetTextureInternal(int picnum, FTexture* tex, int palette, int
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
//===========================================================================
|
||||||
|
//
|
||||||
|
// Sets a named texture for 2D rendering. In this case the palette is
|
||||||
|
// a direct index into the palette map.
|
||||||
|
//
|
||||||
|
//===========================================================================
|
||||||
|
|
||||||
|
bool GLInstance::SetNamedTexture(FTexture* tex, int palette, int sampler)
|
||||||
|
{
|
||||||
|
auto mtex = LoadTexture(tex, palette>= 0? TT_TRUECOLOR : TT_HICREPLACE, palette);
|
||||||
|
if (!mtex) return false;
|
||||||
|
|
||||||
|
renderState.Flags &= ~RF_UsePalette;
|
||||||
|
BindTexture(0, mtex, sampler);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -208,7 +208,20 @@ void GLInstance::Draw(EDrawType type, size_t start, size_t count)
|
||||||
if (activeShader == polymostShader)
|
if (activeShader == polymostShader)
|
||||||
{
|
{
|
||||||
renderState.Apply(polymostShader);
|
renderState.Apply(polymostShader);
|
||||||
|
if (renderState.VertexBuffer != LastVertexBuffer || LastVB_Offset[0] != renderState.VB_Offset[0] || LastVB_Offset[1] != renderState.VB_Offset[1])
|
||||||
|
{
|
||||||
|
static_cast<OpenGLRenderer::GLVertexBuffer*>(renderState.VertexBuffer)->Bind(renderState.VB_Offset);
|
||||||
|
LastVertexBuffer = renderState.VertexBuffer;
|
||||||
|
LastVB_Offset[0] = renderState.VB_Offset[0];
|
||||||
|
LastVB_Offset[1] = renderState.VB_Offset[1];
|
||||||
}
|
}
|
||||||
|
if (renderState.IndexBuffer != LastIndexBuffer)
|
||||||
|
{
|
||||||
|
static_cast<OpenGLRenderer::GLIndexBuffer*>(renderState.IndexBuffer)->Bind();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (!LastVertexBuffer)
|
||||||
|
{
|
||||||
glBegin(primtypes[type]);
|
glBegin(primtypes[type]);
|
||||||
auto p = &Buffer[start];
|
auto p = &Buffer[start];
|
||||||
for (size_t i = 0; i < count; i++, p++)
|
for (size_t i = 0; i < count; i++, p++)
|
||||||
|
@ -217,6 +230,11 @@ void GLInstance::Draw(EDrawType type, size_t start, size_t count)
|
||||||
glVertexAttrib3f(0, p->x, p->y, p->z);
|
glVertexAttrib3f(0, p->x, p->y, p->z);
|
||||||
}
|
}
|
||||||
glEnd();
|
glEnd();
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
glDrawElements(primtypes[type], count, GL_UNSIGNED_INT, (void*)(intptr_t)(start * sizeof(uint32_t)));
|
||||||
|
}
|
||||||
if (MatrixChange) RestoreTextureProps();
|
if (MatrixChange) RestoreTextureProps();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -281,6 +299,12 @@ void GLInstance::EnableDepthTest(bool on)
|
||||||
else glDisable (GL_DEPTH_TEST);
|
else glDisable (GL_DEPTH_TEST);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void GLInstance::EnableMultisampling(bool on)
|
||||||
|
{
|
||||||
|
if (on) glEnable(GL_MULTISAMPLE);
|
||||||
|
else glDisable(GL_MULTISAMPLE);
|
||||||
|
}
|
||||||
|
|
||||||
void GLInstance::SetMatrix(int num, const VSMatrix *mat)
|
void GLInstance::SetMatrix(int num, const VSMatrix *mat)
|
||||||
{
|
{
|
||||||
matrices[num] = *mat;
|
matrices[num] = *mat;
|
||||||
|
|
|
@ -8,6 +8,7 @@
|
||||||
#include "gl_renderstate.h"
|
#include "gl_renderstate.h"
|
||||||
#include "matrix.h"
|
#include "matrix.h"
|
||||||
#include "palentry.h"
|
#include "palentry.h"
|
||||||
|
#include "renderstyle.h"
|
||||||
|
|
||||||
class FSamplerManager;
|
class FSamplerManager;
|
||||||
class FShader;
|
class FShader;
|
||||||
|
@ -64,7 +65,6 @@ class PaletteManager
|
||||||
|
|
||||||
//OpenGLRenderer::GLDataBuffer* palswapBuffer = nullptr;
|
//OpenGLRenderer::GLDataBuffer* palswapBuffer = nullptr;
|
||||||
|
|
||||||
unsigned FindPalette(const uint8_t* paldata);
|
|
||||||
unsigned FindPalswap(const uint8_t* paldata);
|
unsigned FindPalswap(const uint8_t* paldata);
|
||||||
|
|
||||||
public:
|
public:
|
||||||
|
@ -80,6 +80,8 @@ public:
|
||||||
int ActivePalswap() const { return lastsindex; }
|
int ActivePalswap() const { return lastsindex; }
|
||||||
int LookupPalette(int palette, int palswap, bool brightmap);
|
int LookupPalette(int palette, int palswap, bool brightmap);
|
||||||
const PalEntry *GetPaletteData(int palid) const { return palettes[palid].colors; }
|
const PalEntry *GetPaletteData(int palid) const { return palettes[palid].colors; }
|
||||||
|
unsigned FindPalette(const uint8_t* paldata);
|
||||||
|
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
@ -157,27 +159,6 @@ enum EDepthFunc
|
||||||
Depth_LessEqual
|
Depth_LessEqual
|
||||||
};
|
};
|
||||||
|
|
||||||
enum ERenderAlpha
|
|
||||||
{
|
|
||||||
STYLEALPHA_Zero, // Blend factor is 0.0
|
|
||||||
STYLEALPHA_One, // Blend factor is 1.0
|
|
||||||
STYLEALPHA_Src, // Blend factor is alpha
|
|
||||||
STYLEALPHA_InvSrc, // Blend factor is 1.0 - alpha
|
|
||||||
STYLEALPHA_SrcCol, // Blend factor is color (HWR only)
|
|
||||||
STYLEALPHA_InvSrcCol, // Blend factor is 1.0 - color (HWR only)
|
|
||||||
STYLEALPHA_DstCol, // Blend factor is dest. color (HWR only)
|
|
||||||
STYLEALPHA_InvDstCol, // Blend factor is 1.0 - dest. color (HWR only)
|
|
||||||
STYLEALPHA_Dst, // Blend factor is dest. alpha
|
|
||||||
STYLEALPHA_InvDst, // Blend factor is 1.0 - dest. alpha
|
|
||||||
STYLEALPHA_MAX
|
|
||||||
};
|
|
||||||
|
|
||||||
enum ERenderOp
|
|
||||||
{
|
|
||||||
STYLEOP_Add, // Add source to destination
|
|
||||||
STYLEOP_Sub, // Subtract source from destination
|
|
||||||
STYLEOP_RevSub, // Subtract destination from source
|
|
||||||
};
|
|
||||||
|
|
||||||
enum EWinding
|
enum EWinding
|
||||||
{
|
{
|
||||||
|
@ -212,6 +193,10 @@ class GLInstance
|
||||||
int TextureType;
|
int TextureType;
|
||||||
int MatrixChange = 0;
|
int MatrixChange = 0;
|
||||||
|
|
||||||
|
IVertexBuffer* LastVertexBuffer = nullptr;
|
||||||
|
int LastVB_Offset[2] = {};
|
||||||
|
IIndexBuffer* LastIndexBuffer = nullptr;
|
||||||
|
|
||||||
|
|
||||||
VSMatrix matrices[NUMMATRICES];
|
VSMatrix matrices[NUMMATRICES];
|
||||||
PolymostRenderState renderState;
|
PolymostRenderState renderState;
|
||||||
|
@ -251,6 +236,17 @@ public:
|
||||||
void EnableBlend(bool on);
|
void EnableBlend(bool on);
|
||||||
void EnableAlphaTest(bool on);
|
void EnableAlphaTest(bool on);
|
||||||
void EnableDepthTest(bool on);
|
void EnableDepthTest(bool on);
|
||||||
|
void EnableMultisampling(bool on);
|
||||||
|
void SetVertexBuffer(IVertexBuffer* vb, int offset1, int offset2)
|
||||||
|
{
|
||||||
|
renderState.VertexBuffer = vb;
|
||||||
|
renderState.VB_Offset[0] = offset1;
|
||||||
|
renderState.VB_Offset[1] = offset2;
|
||||||
|
}
|
||||||
|
void SetIndexBuffer(IIndexBuffer* vb)
|
||||||
|
{
|
||||||
|
renderState.IndexBuffer = vb;
|
||||||
|
}
|
||||||
const VSMatrix &GetMatrix(int num)
|
const VSMatrix &GetMatrix(int num)
|
||||||
{
|
{
|
||||||
return matrices[num];
|
return matrices[num];
|
||||||
|
@ -397,11 +393,17 @@ public:
|
||||||
// not yet implemented - only relevant for hires replacements.
|
// not yet implemented - only relevant for hires replacements.
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int GetPaletteIndex(PalEntry* palette)
|
||||||
|
{
|
||||||
|
return palmanager.FindPalette((uint8_t*)palette);
|
||||||
|
}
|
||||||
|
|
||||||
FHardwareTexture* CreateIndexedTexture(FTexture* tex);
|
FHardwareTexture* CreateIndexedTexture(FTexture* tex);
|
||||||
FHardwareTexture* CreateTrueColorTexture(FTexture* tex, int palid, bool checkfulltransparency = false, bool rgb8bit = false);
|
FHardwareTexture* CreateTrueColorTexture(FTexture* tex, int palid, bool checkfulltransparency = false, bool rgb8bit = false);
|
||||||
FHardwareTexture *LoadTexture(FTexture* tex, int texturetype, int palid);
|
FHardwareTexture *LoadTexture(FTexture* tex, int texturetype, int palid);
|
||||||
bool SetTextureInternal(int globalpicnum, FTexture* tex, int palette, int method, int sampleroverride, float xpanning, float ypanning, FTexture *det, float detscale, FTexture *glow);
|
bool SetTextureInternal(int globalpicnum, FTexture* tex, int palette, int method, int sampleroverride, float xpanning, float ypanning, FTexture *det, float detscale, FTexture *glow);
|
||||||
|
|
||||||
|
bool SetNamedTexture(FTexture* tex, int palette, int sampleroverride);
|
||||||
|
|
||||||
bool SetTexture(int globalpicnum, FTexture* tex, int palette, int method, int sampleroverride)
|
bool SetTexture(int globalpicnum, FTexture* tex, int palette, int method, int sampleroverride)
|
||||||
{
|
{
|
||||||
|
|
196
source/glbackend/hw_draw2d.cpp
Normal file
196
source/glbackend/hw_draw2d.cpp
Normal file
|
@ -0,0 +1,196 @@
|
||||||
|
//
|
||||||
|
//---------------------------------------------------------------------------
|
||||||
|
//
|
||||||
|
// Copyright(C) 2018 Christoph Oelckers
|
||||||
|
// All rights reserved.
|
||||||
|
//
|
||||||
|
// This program is free software: you can redistribute it and/or modify
|
||||||
|
// it under the terms of the GNU Lesser General Public License as published by
|
||||||
|
// the Free Software Foundation, either version 3 of the License, or
|
||||||
|
// (at your option) any later version.
|
||||||
|
//
|
||||||
|
// This program is distributed in the hope that it will be useful,
|
||||||
|
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
// GNU Lesser General Public License for more details.
|
||||||
|
//
|
||||||
|
// You should have received a copy of the GNU Lesser General Public License
|
||||||
|
// along with this program. If not, see http://www.gnu.org/licenses/
|
||||||
|
//
|
||||||
|
//--------------------------------------------------------------------------
|
||||||
|
//
|
||||||
|
/*
|
||||||
|
** 2d drawer
|
||||||
|
** Renderer interface
|
||||||
|
**
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include "cmdlib.h"
|
||||||
|
#include "gl_buffers.h"
|
||||||
|
#include "v_2ddrawer.h"
|
||||||
|
#include "c_cvars.h"
|
||||||
|
#include "glbackend.h"
|
||||||
|
#include "v_draw.h"
|
||||||
|
|
||||||
|
//===========================================================================
|
||||||
|
//
|
||||||
|
// Vertex buffer for 2D drawer
|
||||||
|
//
|
||||||
|
//===========================================================================
|
||||||
|
|
||||||
|
class F2DVertexBuffer
|
||||||
|
{
|
||||||
|
IVertexBuffer *mVertexBuffer;
|
||||||
|
IIndexBuffer *mIndexBuffer;
|
||||||
|
|
||||||
|
|
||||||
|
public:
|
||||||
|
|
||||||
|
F2DVertexBuffer()
|
||||||
|
{
|
||||||
|
mVertexBuffer = new OpenGLRenderer::GLVertexBuffer();
|
||||||
|
mIndexBuffer = new OpenGLRenderer::GLIndexBuffer();
|
||||||
|
|
||||||
|
static const FVertexBufferAttribute format[] = {
|
||||||
|
{ 0, VATTR_VERTEX, VFmt_Float3, (int)myoffsetof(F2DDrawer::TwoDVertex, x) },
|
||||||
|
{ 0, VATTR_TEXCOORD, VFmt_Float2, (int)myoffsetof(F2DDrawer::TwoDVertex, u) },
|
||||||
|
{ 0, VATTR_COLOR, VFmt_Byte4, (int)myoffsetof(F2DDrawer::TwoDVertex, color0) }
|
||||||
|
};
|
||||||
|
mVertexBuffer->SetFormat(1, 3, sizeof(F2DDrawer::TwoDVertex), format);
|
||||||
|
}
|
||||||
|
~F2DVertexBuffer()
|
||||||
|
{
|
||||||
|
delete mIndexBuffer;
|
||||||
|
delete mVertexBuffer;
|
||||||
|
}
|
||||||
|
|
||||||
|
void UploadData(F2DDrawer::TwoDVertex *vertices, int vertcount, int *indices, int indexcount)
|
||||||
|
{
|
||||||
|
mVertexBuffer->SetData(vertcount * sizeof(*vertices), vertices, false);
|
||||||
|
mIndexBuffer->SetData(indexcount * sizeof(unsigned int), indices, false);
|
||||||
|
}
|
||||||
|
|
||||||
|
std::pair<IVertexBuffer *, IIndexBuffer *> GetBufferObjects() const
|
||||||
|
{
|
||||||
|
return std::make_pair(mVertexBuffer, mIndexBuffer);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
//===========================================================================
|
||||||
|
//
|
||||||
|
// Draws the 2D stuff. This is the version for OpenGL 3 and later.
|
||||||
|
//
|
||||||
|
//===========================================================================
|
||||||
|
|
||||||
|
void Draw2D(F2DDrawer *drawer, FRenderState &state)
|
||||||
|
{
|
||||||
|
VSMatrix mat(0);
|
||||||
|
GLInterface.SetMatrix(Matrix_View, mat.get());
|
||||||
|
GLInterface.SetMatrix(Matrix_ModelView, mat.get());
|
||||||
|
GLInterface.SetMatrix(Matrix_Detail, mat.get());
|
||||||
|
mat.ortho(0, xdim, ydim, 0, -1, 1);
|
||||||
|
GLInterface.SetMatrix(Matrix_Projection, mat.get());
|
||||||
|
GLInterface.SetViewport(0, 0, xdim, ydim);
|
||||||
|
GLInterface.EnableDepthTest(false);
|
||||||
|
GLInterface.EnableMultisampling(false);
|
||||||
|
|
||||||
|
auto &vertices = drawer->mVertices;
|
||||||
|
auto &indices = drawer->mIndices;
|
||||||
|
auto &commands = drawer->mData;
|
||||||
|
|
||||||
|
if (commands.Size() == 0)
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (drawer->mIsFirstPass)
|
||||||
|
{
|
||||||
|
for (auto &v : vertices)
|
||||||
|
{
|
||||||
|
// Change from BGRA to RGBA
|
||||||
|
std::swap(v.color0.r, v.color0.b);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
F2DVertexBuffer vb;
|
||||||
|
vb.UploadData(&vertices[0], vertices.Size(), &indices[0], indices.Size());
|
||||||
|
GLInterface.SetVertexBuffer(vb.GetBufferObjects().first, 0, 0);
|
||||||
|
GLInterface.SetIndexBuffer(vb.GetBufferObjects().second);
|
||||||
|
GLInterface.SetFadeDisable(true);
|
||||||
|
|
||||||
|
for(auto &cmd : commands)
|
||||||
|
{
|
||||||
|
|
||||||
|
int gltrans = -1;
|
||||||
|
//state.SetRenderStyle(cmd.mRenderStyle);
|
||||||
|
//state.EnableBrightmap(!(cmd.mRenderStyle.Flags & STYLEF_ColorIsFixed));
|
||||||
|
//state.SetTextureMode(cmd.mDrawMode);
|
||||||
|
|
||||||
|
int sciX, sciY, sciW, sciH;
|
||||||
|
if (cmd.mFlags & F2DDrawer::DTF_Scissor)
|
||||||
|
{
|
||||||
|
// scissor test doesn't use the current viewport for the coordinates, so use real screen coordinates
|
||||||
|
// Note that the origin here is the lower left corner!
|
||||||
|
sciX = /*screen->ScreenToWindowX*/(cmd.mScissor[0]);
|
||||||
|
sciY = /*screen->ScreenToWindowY*/(cmd.mScissor[3]);
|
||||||
|
sciW = /*screen->ScreenToWindowX*/(cmd.mScissor[2]) - sciX;
|
||||||
|
sciH = /*screen->ScreenToWindowY*/(cmd.mScissor[1]) - sciY;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
sciX = sciY = sciW = sciH = -1;
|
||||||
|
}
|
||||||
|
//GLInterface.SetScissor(sciX, sciY, sciW, sciH);
|
||||||
|
|
||||||
|
//state.SetFog(cmd.mColor1, 0);
|
||||||
|
GLInterface.SetColor(1, 1, 1);
|
||||||
|
//state.SetColor(1, 1, 1, 1, cmd.mDesaturate);
|
||||||
|
|
||||||
|
GLInterface.SetAlphaThreshold(0.0f);
|
||||||
|
|
||||||
|
if (cmd.mTexture != nullptr)
|
||||||
|
{
|
||||||
|
auto tex = cmd.mTexture;
|
||||||
|
GLInterface.SetNamedTexture(cmd.mTexture, cmd.mRemapIndex, cmd.mFlags & F2DDrawer::DTF_Wrap ? SamplerRepeat : SamplerClampXY);
|
||||||
|
GLInterface.UseColorOnly(false);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
GLInterface.UseColorOnly(true);
|
||||||
|
}
|
||||||
|
|
||||||
|
switch (cmd.mType)
|
||||||
|
{
|
||||||
|
case F2DDrawer::DrawTypeTriangles:
|
||||||
|
GLInterface.Draw(DT_TRIANGLES, cmd.mIndexIndex, cmd.mIndexCount);
|
||||||
|
break;
|
||||||
|
|
||||||
|
case F2DDrawer::DrawTypeLines:
|
||||||
|
GLInterface.Draw(DT_LINES, cmd.mVertIndex, cmd.mVertCount);
|
||||||
|
break;
|
||||||
|
|
||||||
|
case F2DDrawer::DrawTypePoints:
|
||||||
|
//GLInterface.Draw(DT_POINTS, cmd.mVertIndex, cmd.mVertCount);
|
||||||
|
break;
|
||||||
|
|
||||||
|
}
|
||||||
|
/*
|
||||||
|
state.SetObjectColor(0xffffffff);
|
||||||
|
state.SetObjectColor2(0);
|
||||||
|
state.SetAddColor(0);
|
||||||
|
state.EnableTextureMatrix(false);
|
||||||
|
state.SetEffect(EFF_NONE);
|
||||||
|
*/
|
||||||
|
|
||||||
|
}
|
||||||
|
//state.SetScissor(-1, -1, -1, -1);
|
||||||
|
|
||||||
|
//state.SetRenderStyle(STYLE_Translucent);
|
||||||
|
GLInterface.SetVertexBuffer(nullptr, 0, 0);
|
||||||
|
GLInterface.SetIndexBuffer(nullptr);
|
||||||
|
GLInterface.UseColorOnly(false);
|
||||||
|
//state.EnableBrightmap(true);
|
||||||
|
//state.SetTextureMode(TM_NORMAL);
|
||||||
|
GLInterface.SetFadeDisable(false);
|
||||||
|
GLInterface.SetColor(1, 1, 1);
|
||||||
|
//drawer->mIsFirstPass = false;
|
||||||
|
}
|
Loading…
Reference in a new issue