Laid groundwork for library collection support.

Thu, 09 Mar 2017 12:50:14 +0200

author
Teemu Piippo <teemu@hecknology.net>
date
Thu, 09 Mar 2017 12:50:14 +0200
changeset 1209
c2723022b173
parent 1208
8d4b8a9df724
child 1210
0b3b35f560f2

Laid groundwork for library collection support.

CMakeLists.txt file | annotate | diff | comparison | revisions
src/librarycollection.cpp file | annotate | diff | comparison | revisions
src/librarycollection.h file | annotate | diff | comparison | revisions
--- a/CMakeLists.txt	Thu Mar 09 00:54:45 2017 +0200
+++ b/CMakeLists.txt	Thu Mar 09 12:50:14 2017 +0200
@@ -44,6 +44,7 @@
 	src/hierarchyelement.cpp
 	src/lddocument.cpp
 	src/ldpaths.cpp
+	src/librarycollection.cpp
 	src/main.cpp
 	src/mainwindow.cpp
 	src/mathfunctions.cpp
@@ -111,6 +112,7 @@
 	src/lddocument.h
 	src/ldobjectiterator.h
 	src/ldpaths.h
+	src/librarycollection.h
 	src/macros.h
 	src/main.h
 	src/mainwindow.h
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/librarycollection.cpp	Thu Mar 09 12:50:14 2017 +0200
@@ -0,0 +1,94 @@
+#include "librarycollection.h"
+
+const QStringList LibraryCollection::directoryNames = {"parts", "p"};
+
+/*
+ * Searches the libraries for a file by relative path.
+ */
+QString LibraryCollection::find(QString relativePath) const
+{
+	// LDraw uses backslashes for directory separators. We need to convert them to forward
+	// slashes so that Qt understands them on all platforms.
+	relativePath.replace('\\', '/');
+
+	for (const Library& library : m_libraries)
+	{
+		for (const QString& directoryName : directoryNames)
+		{
+			QDir dir = library.path;
+
+			if (dir.exists() and dir.cd(directoryName) and dir.exists(relativePath))
+				return QDir::cleanPath(dir.absoluteFilePath(relativePath));
+		}
+	}
+
+	return "";
+}
+
+/*
+ * Searches the libraries for a file. This overload takes the parameters of a FileSpec and
+ * calls another overload with a ready spec.
+ */
+QString LibraryCollection::find(const QString &name, FileType type) const
+{
+	return find(FileSpec {name, type});
+}
+
+/*
+ * Searches the libraries for a file by the given file specification. The type attribute
+ * specifies what kind of file we are looking for.
+ */
+QString LibraryCollection::find(const FileSpec& spec) const
+{
+	for (const Library& library : m_libraries)
+	{
+		try
+		{
+			QDir subdirectory = library.subdirectory(spec.type);
+			if (subdirectory.exists(spec.name))
+				return QDir::cleanPath(subdirectory.absoluteFilePath(spec.name));
+		}
+		catch (SubdirectoryNotFoundError&) {}
+	}
+
+	return "";
+}
+
+/*
+ * Returns the appropriate subdirectory for the given file type.
+ */
+QDir LibraryCollection::Library::subdirectory(FileType type) const
+{
+	QString subdirectory = subdirectoryName(type);
+
+	if (path.exists(subdirectory))
+		return path.absolutePath() + "/" + subdirectory;
+	else
+		throw SubdirectoryNotFoundError {};
+}
+
+/*
+ * Returns the appropriate subdirectory name for the given file type.
+ */
+QString LibraryCollection::Library::subdirectoryName(FileType type)
+{
+	switch (type)
+	{
+	case Part:
+		return "/parts/";
+
+	case Subpart:
+		return "/parts/s/";
+
+	case Primitive:
+		return "/p/";
+
+	case HighResolutionPrimitive:
+		return "/p/48/";
+
+	case LowResolutionPrimitive:
+		return "/p/8/";
+	}
+
+	return "";
+}
\ No newline at end of file
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/librarycollection.h	Thu Mar 09 12:50:14 2017 +0200
@@ -0,0 +1,46 @@
+#pragma once
+#include <QDir>
+#include "main.h"
+
+/*
+ * Models a collection of libraries. A library is a folder containing directories named "p" and
+ * "parts" that contains part and subpart files.
+ */
+class LibraryCollection
+{
+public:
+	enum FileType
+	{
+		Part,
+		Subpart,
+		Primitive,
+		HighResolutionPrimitive,
+		LowResolutionPrimitive,
+	};
+
+	struct FileSpec
+	{
+		QString name;
+		FileType type;
+	};
+
+	QString find(QString relativePath) const;
+	QString find(const QString& name, FileType type) const;
+	QString find(const FileSpec& spec) const;
+
+	static const QStringList directoryNames;
+
+private:
+	class SubdirectoryNotFoundError : public std::exception {};
+
+	struct Library
+	{
+		QDir path;
+		QString name;
+
+		QDir subdirectory(FileType type) const;
+		static QString subdirectoryName(FileType type);
+	};
+
+	QVector<Library> m_libraries;
+};

mercurial