Support drawing primitives included directly by a model.

This commit is contained in:
leo 2015-02-28 20:31:57 +00:00
parent a7da5aa79f
commit 635d408101
5 changed files with 56 additions and 65 deletions

View file

@ -1054,7 +1054,7 @@ bool lcPiecesLibrary::LoadTexture(lcTexture* Texture)
return true;
}
int lcPiecesLibrary::FindPrimitiveIndex(const char* Name)
int lcPiecesLibrary::FindPrimitiveIndex(const char* Name) const
{
for (int PrimitiveIndex = 0; PrimitiveIndex < mPrimitives.GetSize(); PrimitiveIndex++)
if (!strcmp(mPrimitives[PrimitiveIndex]->mName, Name))

View file

@ -137,12 +137,18 @@ public:
void GetCategoryEntries(const String& CategoryKeywords, bool GroupPieces, lcArray<PieceInfo*>& SinglePieces, lcArray<PieceInfo*>& GroupedPieces);
void GetPatternedPieces(PieceInfo* Parent, lcArray<PieceInfo*>& Pieces) const;
bool IsPrimitive(const char* Name) const
{
return FindPrimitiveIndex(Name) != -1;
}
void SetOfficialPieces()
{
if (mZipFiles[LC_ZIPFILE_OFFICIAL])
mNumOfficialPieces = mPieces.GetSize();
}
bool ReadMeshData(lcFile& File, const lcMatrix44& CurrentTransform, lcuint32 CurrentColorCode, lcArray<lcLibraryTextureMap>& TextureStack, lcLibraryMeshData& MeshData);
void CreateMesh(PieceInfo* Info, lcLibraryMeshData& MeshData);
lcArray<PieceInfo*> mPieces;
@ -163,9 +169,8 @@ protected:
bool LoadCachePiece(PieceInfo* Info);
void SaveCacheFile();
int FindPrimitiveIndex(const char* Name);
int FindPrimitiveIndex(const char* Name) const;
bool LoadPrimitive(int PrimitiveIndex);
bool ReadMeshData(lcFile& File, const lcMatrix44& CurrentTransform, lcuint32 CurrentColorCode, lcArray<lcLibraryTextureMap>& TextureStack, lcLibraryMeshData& MeshData);
char mCacheFileName[LC_MAXPATH];
lcuint64 mCacheFileModifiedTime;

View file

@ -205,7 +205,7 @@ void lcModel::DeleteModel()
mCameras.DeleteAll();
mLights.DeleteAll();
mGroups.DeleteAll();
mMeshLines.RemoveAll();
mMeshLines.clear();
}
void lcModel::CreatePieceInfo(Project* Project)
@ -382,6 +382,7 @@ void lcModel::LoadLDraw(QIODevice& Device, Project* Project)
qint64 Pos = Device.pos();
QString Line = Device.readLine().trimmed();
QTextStream LineStream(&Line, QIODevice::ReadOnly);
bool MeshLine = false;
QString Token;
LineStream >> Token;
@ -480,20 +481,27 @@ void lcModel::LoadLDraw(QIODevice& Device, Project* Project)
QString File = LineStream.readAll().trimmed().toUpper();
QString PartID = File;
PartID.replace('\\', '/');
if (PartID.endsWith(QLatin1String(".DAT")))
PartID = PartID.left(PartID.size() - 4);
lcPiecesLibrary* Library = lcGetPiecesLibrary();
if (Library->IsPrimitive(PartID.toLatin1().constData()))
MeshLine = true;
else
{
if (!Piece)
Piece = new lcPiece(NULL);
if (!CurrentGroups.IsEmpty())
Piece->SetGroup(CurrentGroups[CurrentGroups.GetSize() - 1]);
PieceInfo* Info = lcGetPiecesLibrary()->FindPiece(PartID.toLatin1().constData(), Project, false);
PieceInfo* Info = Library->FindPiece(PartID.toLatin1().constData(), Project, false);
if (!Info)
Info = lcGetPiecesLibrary()->FindPiece(File.toLatin1().constData(), Project, true);
Info = Library->FindPiece(File.toLatin1().constData(), Project, true);
float* Matrix = IncludeTransform;
lcMatrix44 Transform(lcVector4(Matrix[0], Matrix[2], -Matrix[1], 0.0f), lcVector4(Matrix[8], Matrix[10], -Matrix[9], 0.0f),
@ -505,37 +513,12 @@ void lcModel::LoadLDraw(QIODevice& Device, Project* Project)
mPieces.Add(Piece);
Piece = NULL;
}
else if (Token == QLatin1String("2"))
{
lcModelMeshLine& Line = mMeshLines.Add();
Line.LineType = 2;
LineStream >> Line.ColorCode;
for (int TokenIdx = 0; TokenIdx < 6; TokenIdx++)
LineStream >> ((float*)Line.Vertices)[TokenIdx];
}
else if (Token == QLatin1String("3"))
{
lcModelMeshLine& Line = mMeshLines.Add();
else if (Token == QLatin1String("2") || Token == QLatin1String("3") || Token == QLatin1String("4"))
MeshLine = true;
Line.LineType = 3;
LineStream >> Line.ColorCode;
for (int TokenIdx = 0; TokenIdx < 9; TokenIdx++)
LineStream >> ((float*)Line.Vertices)[TokenIdx];
}
else if (Token == QLatin1String("4"))
{
lcModelMeshLine& Line = mMeshLines.Add();
Line.LineType = 4;
LineStream >> Line.ColorCode;
for (int TokenIdx = 0; TokenIdx < 12; TokenIdx++)
LineStream >> ((float*)Line.Vertices)[TokenIdx];
}
if (MeshLine)
mMeshLines.append(Line);
}
mCurrentStep = CurrentStep;

View file

@ -113,13 +113,6 @@ struct lcModelPartsEntry
int ColorIndex;
};
struct lcModelMeshLine
{
int LineType;
int ColorCode;
lcVector3 Vertices[4];
};
class lcModel
{
public:
@ -170,7 +163,7 @@ public:
mProperties.mName = Name;
}
const lcArray<lcModelMeshLine>& GetMeshLines() const
const QStringList& GetMeshLines() const
{
return mMeshLines;
}
@ -345,7 +338,7 @@ protected:
lcArray<lcCamera*> mCameras;
lcArray<lcLight*> mLights;
lcArray<lcGroup*> mGroups;
lcArray<lcModelMeshLine> mMeshLines;
QStringList mMeshLines;
lcModelHistoryEntry* mSavedHistory;
lcArray<lcModelHistoryEntry*> mUndoHistory;

View file

@ -64,18 +64,28 @@ void PieceInfo::SetModel(lcModel* Model, bool UpdateMesh)
strncpy(m_strDescription, Model->GetProperties().mName.toLatin1().data(), sizeof(m_strDescription));
m_strDescription[sizeof(m_strDescription)-1] = 0;
const lcArray<lcModelMeshLine>& MeshLines = Model->GetMeshLines();
const QStringList& MeshLines = Model->GetMeshLines();
if (UpdateMesh && !MeshLines.IsEmpty())
if (UpdateMesh && !MeshLines.isEmpty())
{
lcLibraryMeshData MeshData;
lcMemFile PieceFile;
for (int LineIdx = 0; LineIdx < MeshLines.GetSize(); LineIdx++)
foreach (const QString& Line, MeshLines)
{
const lcModelMeshLine& Line = MeshLines[LineIdx];
MeshData.AddLine(Line.LineType, Line.ColorCode, Line.Vertices);
QByteArray Buffer = Line.toLatin1();
PieceFile.WriteBuffer(Buffer.constData(), Buffer.size());
PieceFile.WriteBuffer("\r\n", 2);
}
lcLibraryMeshData MeshData;
lcArray<lcLibraryTextureMap> TextureStack;
PieceFile.Seek(0, SEEK_SET);
const char* OldLocale = setlocale(LC_NUMERIC, "C");
bool Ret = lcGetPiecesLibrary()->ReadMeshData(PieceFile, lcMatrix44Identity(), 16, TextureStack, MeshData);
setlocale(LC_NUMERIC, OldLocale);
if (Ret)
lcGetPiecesLibrary()->CreateMesh(this, MeshData);
}
}