FileParserRegistry

FileParserRegistry is the process-wide singleton that owns every FileParser instance Blackchirp knows about. The registry is populated during application startup — main() calls FileParserRegistry::registerParser() once for each shipped parser (SPCATParser, XIAMParser, and GenericXYParser) — and then services every “given this file, find a parser that understands it” request from the rest of the application. The overlay-import dialogs (CatalogOverlayWidget, GenericXYOverlayWidget) and the overlay-replay code path (OverlayOperation) all consume the registry directly; nothing in Blackchirp constructs a parser instance outside of this class.

Two lookup methods cover the dispatch surface. FileParserRegistry::findParser() returns the first registered parser whose FileParser::canParse() returns true for the candidate file; FileParserRegistry::findParserOfType() is a templated variant that filters on a specific parser family — for instance, the catalog-import dialog only wants a CatalogParser, even if a generic parser would also accept the file. A registered parser keeps its position in the registry’s internal vector, so registration order determines lookup priority when two parsers would both claim a file.

The registry is also the source of truth for QFileDialog filter strings: FileParserRegistry::fileDialogFilter() joins each parser’s FileParser::fileExtensions() into a ;;-separated filter string suitable for QFileDialog::getOpenFileName, with one entry per format, an “All Catalog Files” entry combining every supported extension, and a final “All Files” wildcard. The FileParserRegistry::parserRegistered() signal fires once per FileParserRegistry::registerParser() call and is intended for UI surfaces that want to refresh their format lists when a new parser is added at runtime.

The user-facing import workflow that consumes the registry is described in Overlays.

API Reference

class FileParserRegistry : public QObject

Singleton catalog of registered :cpp:class:FileParser instances.

Public Functions

void registerParser(std::unique_ptr<FileParser> parser)

Take ownership of parser and add it to the registry.

Emits :cpp:func:parserRegistered with the new parser’s format name. A null pointer is rejected with a qWarning and no signal is emitted.

FileParser *findParser(const QString &filePath) const

Find the first registered parser whose canParse returns true for filePath.

Returns:

Borrowed pointer (registry retains ownership) or nullptr if no parser claims the file.

template<typename T>
inline T *findParserOfType(const QString &filePath) const

Find the first parser of type T (or a subclass) that claims filePath.

Used by callers that need a specific parser family — e.g., CatalogOverlayWidget only wants a :cpp:class:CatalogParser, even if a generic parser would also accept the file.

Template Parameters:

T – Parser class to filter on.

Returns:

Borrowed T* or nullptr.

std::vector<FileParser*> getAllParsers() const

Return borrowed pointers to every registered parser, in registration order.

QStringList supportedFormats() const

Return the format names of every registered parser.

QStringList supportedExtensions() const

Return the union of every parser’s :cpp:func:FileParser::fileExtensions with duplicates removed.

QString fileDialogFilter() const

Build a QFileDialog filter string covering every registered parser.

The filter string includes one entry per format, an “All Catalog

Files” entry combining every supported extension, and a final “All Files” wildcard.

bool canParseFile(const QString &filePath) const

Convenience predicate equivalent to findParser(filePath) != nullptr.

Signals

void parserRegistered(const QString &formatName)

Emitted from :cpp:func:registerParser after the new parser is added.

Parameters:

formatName – The :cpp:func:FileParser::formatName of the registered parser.

Public Static Functions

static FileParserRegistry *instance()

Return the process-wide singleton, constructing it on first call.

static void cleanup()

Destroy the singleton.

Called from application shutdown so all owned parsers are torn down before Qt’s global cleanup runs.

Private Functions

explicit FileParserRegistry(QObject *parent = nullptr)
~FileParserRegistry()
FileParserRegistry(const FileParserRegistry&) = delete
FileParserRegistry &operator=(const FileParserRegistry&) = delete

Private Members

std::vector<std::unique_ptr<FileParser>> d_parsers

Private Static Attributes

static FileParserRegistry *s_instance = nullptr