improved performance using my own tga load function always instead of QImage

improved Profiler
This commit is contained in:
Anakin 2017-01-30 16:00:14 +01:00
parent d1c68e8ba6
commit 4342260e6d
4 changed files with 125 additions and 119 deletions

View File

@ -2,9 +2,10 @@
#ifdef _DEBUG #ifdef _DEBUG
#include <QElapsedTimer.h> #include <QElapsedTimer.h>
#include <QString>
#include <iostream> #include <iostream>
#define TIC Profiler::getInstance().startTimer(); #define TIC(val) Profiler::getInstance().startTimer(val);
#define TOC Profiler::getInstance().takeTime(); #define TOC(val) Profiler::getInstance().takeTime(val);
class Profiler class Profiler
{ {
@ -21,16 +22,17 @@
return instance; return instance;
} }
void startTimer() { void startTimer(QString position = "") {
std::cout << "from: " << position.toStdString() << std::endl;
timer.restart(); timer.restart();
}; };
void takeTime() { void takeTime(QString position = "") {
std::cout << "time elapsed: " << timer.elapsed() << std::endl; std::cout << "to: "<< position.toStdString() << " time elapsed: " << timer.elapsed() << std::endl;
}; };
}; };
#else #else
#define TIC #define TIC(val)
#define TOC #define TOC(val)
#endif #endif

View File

@ -3,137 +3,136 @@
#include <QImage> #include <QImage>
#include <QColor> #include <QColor>
#include "..\Header\Profiler.h"
QImage loadTga(QString filePath, bool &success) QImage loadTga(QString filePath, bool &success)
{ {
QImage img; QImage img;
if (!img.load(filePath))
// open the file
std::fstream fsPicture(filePath.toStdString().c_str(), std::ios::in | std::ios::binary);
if (!fsPicture.is_open())
{ {
img = QImage(1, 1, QImage::Format_RGB32);
img.fill(Qt::red);
success = false;
return img;
}
// open the file // read in the header
std::fstream fsPicture(filePath.toStdString().c_str(), std::ios::in | std::ios::binary); std::uint8_t ui8x18Header[19] = { 0 };
fsPicture.read(reinterpret_cast<char*>(&ui8x18Header), sizeof(ui8x18Header) - 1);
if (!fsPicture.is_open()) //get variables
std::uint32_t ui32BpP;
std::uint32_t ui32Width;
std::uint32_t ui32Height;
std::uint32_t ui32IDLength;
std::uint32_t ui32PicType;
std::uint32_t ui32PaletteLength;
std::uint32_t ui32Size;
// extract all information from header
ui32IDLength = ui8x18Header[0];
ui32PicType = ui8x18Header[2];
ui32PaletteLength = ui8x18Header[6] * 0x100 + ui8x18Header[5];
ui32Width = ui8x18Header[13] * 0x100 + ui8x18Header[12];
ui32Height = ui8x18Header[15] * 0x100 + ui8x18Header[14];
ui32BpP = ui8x18Header[16];
// calculate some more information
ui32Size = ui32Width * ui32Height * ui32BpP / 8;
// jump to the data block
fsPicture.seekg(ui32IDLength + ui32PaletteLength, std::ios_base::cur);
img = QImage(ui32Width, ui32Height, ui32BpP == 32? QImage::Format_RGBA8888 : QImage::Format_RGB888);
// uncompressed
if (ui32PicType == 2 && (ui32BpP == 24 || ui32BpP == 32))
{
std::vector<std::uint8_t> vui8Pixels;
vui8Pixels.resize(ui32Size);
fsPicture.read(reinterpret_cast<char*>(vui8Pixels.data()), ui32Size);
for (unsigned int y = 0; y < ui32Height; y++)
{ {
img = QImage(1, 1, QImage::Format_RGB32); for (unsigned int x = 0; x < ui32Width; x++)
img.fill(Qt::red);
success = false;
return img;
}
// read in the header
std::uint8_t ui8x18Header[19] = { 0 };
fsPicture.read(reinterpret_cast<char*>(&ui8x18Header), sizeof(ui8x18Header) - 1);
//get variables
std::uint32_t ui32BpP;
std::uint32_t ui32Width;
std::uint32_t ui32Height;
std::uint32_t ui32IDLength;
std::uint32_t ui32PicType;
std::uint32_t ui32PaletteLength;
std::uint32_t ui32Size;
// extract all information from header
ui32IDLength = ui8x18Header[0];
ui32PicType = ui8x18Header[2];
ui32PaletteLength = ui8x18Header[6] * 0x100 + ui8x18Header[5];
ui32Width = ui8x18Header[13] * 0x100 + ui8x18Header[12];
ui32Height = ui8x18Header[15] * 0x100 + ui8x18Header[14];
ui32BpP = ui8x18Header[16];
// calculate some more information
ui32Size = ui32Width * ui32Height * ui32BpP / 8;
// jump to the data block
fsPicture.seekg(ui32IDLength + ui32PaletteLength, std::ios_base::cur);
img = QImage(ui32Width, ui32Height, ui32BpP == 32? QImage::Format_RGBA8888 : QImage::Format_RGB888);
// uncompressed
if (ui32PicType == 2 && (ui32BpP == 24 || ui32BpP == 32))
{
std::vector<std::uint8_t> vui8Pixels;
vui8Pixels.resize(ui32Size);
fsPicture.read(reinterpret_cast<char*>(vui8Pixels.data()), ui32Size);
for (unsigned int y = 0; y < ui32Height; y++)
{ {
for (unsigned int x = 0; x < ui32Width; x++) int valr = vui8Pixels.at(y * ui32Width * ui32BpP / 8 + x * ui32BpP / 8 + 2);
{ int valg = vui8Pixels.at(y * ui32Width * ui32BpP / 8 + x * ui32BpP / 8 + 1);
int valr = vui8Pixels.at(y * ui32Width * ui32BpP / 8 + x * ui32BpP / 8 + 2); int valb = vui8Pixels.at(y * ui32Width * ui32BpP / 8 + x * ui32BpP / 8);
int valg = vui8Pixels.at(y * ui32Width * ui32BpP / 8 + x * ui32BpP / 8 + 1);
int valb = vui8Pixels.at(y * ui32Width * ui32BpP / 8 + x * ui32BpP / 8);
QColor value(valr, valg, valb); QColor value(valr, valg, valb);
img.setPixel(x, ui32Width - 1 - y, value.rgba()); img.setPixel(x, ui32Width - 1 - y, value.rgba());
}
} }
} }
// else if compressed 24 or 32 bit }
else if (ui32PicType == 10 && (ui32BpP == 24 || ui32BpP == 32)) // compressed // else if compressed 24 or 32 bit
{ else if (ui32PicType == 10 && (ui32BpP == 24 || ui32BpP == 32)) // compressed
std::uint8_t tempChunkHeader; {
std::uint8_t tempData[5]; std::uint8_t tempChunkHeader;
unsigned int tmp_pixelIndex = 0; std::uint8_t tempData[5];
unsigned int tmp_pixelIndex = 0;
do { do {
fsPicture.read(reinterpret_cast<char*>(&tempChunkHeader), sizeof(tempChunkHeader)); fsPicture.read(reinterpret_cast<char*>(&tempChunkHeader), sizeof(tempChunkHeader));
if (tempChunkHeader >> 7) // repeat count if (tempChunkHeader >> 7) // repeat count
{
// just use the first 7 bits
tempChunkHeader = (uint8_t(tempChunkHeader << 1) >> 1);
fsPicture.read(reinterpret_cast<char*>(&tempData), ui32BpP / 8);
for (int i = 0; i <= tempChunkHeader; i++)
{ {
// just use the first 7 bits QColor color;
tempChunkHeader = (uint8_t(tempChunkHeader << 1) >> 1);
if (ui32BpP == 32)
color.setRgba(qRgba(tempData[2], tempData[1], tempData[0], tempData[3]));
else
color.setRgb(qRgb(tempData[2], tempData[1], tempData[0]));
img.setPixel(tmp_pixelIndex % ui32Width, ui32Height - 1 - (tmp_pixelIndex / ui32Width), color.rgba());
tmp_pixelIndex++;
}
}
else // data count
{
// just use the first 7 bits
tempChunkHeader = (uint8_t(tempChunkHeader << 1) >> 1);
for (int i = 0; i <= tempChunkHeader; i++)
{
fsPicture.read(reinterpret_cast<char*>(&tempData), ui32BpP / 8); fsPicture.read(reinterpret_cast<char*>(&tempData), ui32BpP / 8);
for (int i = 0; i <= tempChunkHeader; i++) QColor color;
{
QColor color;
if (ui32BpP == 32) if (ui32BpP == 32)
color.setRgba(qRgba(tempData[2], tempData[1], tempData[0], tempData[3])); color.setRgba(qRgba(tempData[2], tempData[1], tempData[0], tempData[3]));
else else
color.setRgb(qRgb(tempData[2], tempData[1], tempData[0])); color.setRgb(qRgb(tempData[2], tempData[1], tempData[0]));
img.setPixel(tmp_pixelIndex % ui32Width, ui32Height - 1 - (tmp_pixelIndex / ui32Width), color.rgba()); img.setPixel(tmp_pixelIndex % ui32Width, ui32Height - 1 - (tmp_pixelIndex / ui32Width), color.rgba());
tmp_pixelIndex++; tmp_pixelIndex++;
}
} }
else // data count }
{ } while (tmp_pixelIndex < (ui32Width * ui32Height));
// just use the first 7 bits
tempChunkHeader = (uint8_t(tempChunkHeader << 1) >> 1);
for (int i = 0; i <= tempChunkHeader; i++)
{
fsPicture.read(reinterpret_cast<char*>(&tempData), ui32BpP / 8);
QColor color;
if (ui32BpP == 32)
color.setRgba(qRgba(tempData[2], tempData[1], tempData[0], tempData[3]));
else
color.setRgb(qRgb(tempData[2], tempData[1], tempData[0]));
img.setPixel(tmp_pixelIndex % ui32Width, ui32Height - 1 - (tmp_pixelIndex / ui32Width), color.rgba());
tmp_pixelIndex++;
}
}
} while (tmp_pixelIndex < (ui32Width * ui32Height));
}
// not useable format
else
{
fsPicture.close();
img = QImage(1, 1, QImage::Format_RGB32);
img.fill(Qt::red);
success = false;
return img;
}
fsPicture.close();
} }
// not useable format
else
{
fsPicture.close();
img = QImage(1, 1, QImage::Format_RGB32);
img.fill(Qt::red);
success = false;
return img;
}
fsPicture.close();
success = true; success = true;
return img; return img;
} }

View File

@ -3,6 +3,8 @@
#include "..\Header\OutputDevice.h" #include "..\Header\OutputDevice.h"
#include <QColor> #include <QColor>
#include "..\Header\Profiler.h"
// helper function to save data from file to any variable type // helper function to save data from file to any variable type
#define F2V(variableName) reinterpret_cast<char*>(&variableName) #define F2V(variableName) reinterpret_cast<char*>(&variableName)
@ -278,7 +280,6 @@ void MshFile::analyseMatdChunks(std::list<ChunkHeader*>& chunkList)
curMat->flags[i] = (std::uint8_t)(flag << (7 - i)) >> 7; curMat->flags[i] = (std::uint8_t)(flag << (7 - i)) >> 7;
curMat->transparent = curMat->flags[2] || curMat->flags[3] || curMat->flags[4] || curMat->flags[6] || curMat->rendertype == 4; curMat->transparent = curMat->flags[2] || curMat->flags[3] || curMat->flags[4] || curMat->flags[6] || curMat->rendertype == 4;
} }
// texture 0 // texture 0
@ -310,7 +311,6 @@ void MshFile::analyseMatdChunks(std::list<ChunkHeader*>& chunkList)
if (!m_materials->back().tx1d.isEmpty()) if (!m_materials->back().tx1d.isEmpty())
loadTexture(m_materials->back().texture1, m_filepath, m_materials->back().tx1d); loadTexture(m_materials->back().texture1, m_filepath, m_materials->back().tx1d);
} }
// texture 2 // texture 2
@ -719,6 +719,7 @@ void MshFile::readUV(Segment * dataDestination, std::streampos position)
void MshFile::loadTexture(QOpenGLTexture *& destination, QString filepath, QString& filename) void MshFile::loadTexture(QOpenGLTexture *& destination, QString filepath, QString& filename)
{ {
bool loadSuccess(false); bool loadSuccess(false);
QImage img = loadTga(filepath + "/" + filename, loadSuccess); QImage img = loadTga(filepath + "/" + filename, loadSuccess);
if (!loadSuccess) if (!loadSuccess)

View File

@ -428,8 +428,12 @@ void OglViewerWidget::setAmbCoef(double value)
void OglViewerWidget::setHeadlight(bool value) void OglViewerWidget::setHeadlight(bool value)
{ {
m_light.headlight = value; m_light.headlight = value;
if (m_lightOn)
if (m_lightOn && value)
{
updateLightPosition();
update(); update();
}
} }
void OglViewerWidget::setBackfaceCulling(bool value) void OglViewerWidget::setBackfaceCulling(bool value)