1
0

initial parser and compiler

This commit is contained in:
2025-07-19 17:30:42 +03:00
parent 27bd44a82b
commit 58a84ade0d
9 changed files with 717 additions and 0 deletions

139
src/main.cpp Normal file
View File

@@ -0,0 +1,139 @@
#include <algorithm>
#include <array>
#include <filesystem>
#include <fstream>
#include <initializer_list>
#include <iostream>
#include <istream>
#include <limits>
#include <optional>
#include <set>
#include <tuple>
#include <variant>
#include <vector>
#include "wavefront.hpp"
#include "output.hpp"
namespace fs = std::filesystem;
void printUsage() {
std::cout
<< "Usage: parse-wavefront [options] <input.obj>" << std::endl
<< "Options:" << std::endl
<< " --filter-object / -O <name> Filter objects by name (can be used multiple times)" << std::endl
<< " --filter-group / -G <name> Filter groups by name (can be used multiple times)" << std::endl
<< " --output-float-set / -f <file> Output float set to file" << std::endl
<< " --output-position / -p <file> Output positions to file" << std::endl
<< " --output-vertex / -v <file> Output vertices to file" << std::endl
<< " --output-mesh / -m <file> Output mesh to file" << std::endl
<< " --output-normal-file / -n <file> Output normals to file" << std::endl
<< " --output-texcoord-file / -t <file> Output texture coordinates to file" << std::endl
<< " -- Stop processing flags" << std::endl
;
std::cout
<< " <input.obj> Input Wavefront OBJ file" << std::endl
<< "Examples:" << std::endl
<< " parse-wavefront --float64 --output-float-set output.fset --output-position output.pos --filter-object Car,Wheel --filter-group Metal -- model.obj" << std::endl
;
}
[[noreturn]]
void exitWithError(const std::string& message) {
std::cerr << "Error: " << message << std::endl;
std::exit(1);
}
int main(int argc, char *argv[]) {
std::vector<std::string> selected_objects, selected_groups;
bool process_flags = true;
bool has_input_file = false;
bool has_output_float_set_file = false;
bool has_output_position_file = false;
bool has_output_mesh_file = false;
bool has_output_vertex_file = false;
std::string input_file_path;
for (decltype(argc) i = 1; i < argc; ++i) {
std::string arg = argv[i];
if (!process_flags) {
if (has_input_file) {
std::cerr << "Unexpected argument after the input file: " << arg << std::endl;
printUsage();
return 1;
}
has_input_file = true;
input_file_path = arg;
continue;
}
if (arg == "--filter-object" || arg == "-O") {
if (i + 1 < argc) {
selected_groups.push_back(argv[++i]);
}
} else if (arg == "--filter-group" || arg == "-G") {
if (i + 1 < argc) {
selected_groups.push_back(argv[++i]);
}
} else if (arg == "--") {
process_flags = false;
} else if (arg.starts_with("-")) {
std::cerr << "Unknown option: " << arg << std::endl;
printUsage();
return 1;
} else {
input_file_path = arg;
has_input_file = true;
}
}
if (!has_input_file) {
std::cerr << "No input file specified." << std::endl;
printUsage();
return 1;
}
// if (!has_output_float_set_file) {
// std::cerr << "No output float set file specified." << std::endl;
// printUsage();
// return 1;
// }
// if (!has_output_vertex_file) {
// std::cerr << "No output vertex file specified." << std::endl;
// printUsage();
// return 1;
// }
// if (!has_output_mesh_file) {
// std::cerr << "No output mesh file specified." << std::endl;
// printUsage();
// return 1;
// }
// if (!has_output_position_file) {
// std::cerr << "No output position file specified." << std::endl;
// printUsage();
// return 1;
// }
WaveFront::Settings wavefront_settings(
selected_objects.empty() ? std::nullopt : std::make_optional(selected_objects),
selected_groups.empty() ? std::nullopt : std::make_optional(selected_groups)
);
WaveFront wavefront_parser(wavefront_settings);
try {
if (input_file_path == "-") {
wavefront_parser.parse(std::cin);
} else {
std::ifstream input_file(input_file_path);
if (!input_file) {
std::cerr << "Failed to open input file: " << input_file_path << std::endl;
return 1;
}
wavefront_parser.parse(input_file);
}
} catch (const WaveFront::parse_error& e) {
std::cerr << input_file_path << ":" << e.line_number() << ": " << e.what() << std::endl;
return 1;
}
Output output;
output.compile(wavefront_parser);
return 0;
}