mirror of
https://github.com/AxioDL/metaforce.git
synced 2025-12-08 18:24:55 +00:00
extract behavior tweaks
This commit is contained in:
@@ -28,6 +28,7 @@ void InitASEngine()
|
||||
InitEntered = true;
|
||||
assert(asENGINE = AngelScript::asCreateScriptEngine(ANGELSCRIPT_VERSION));
|
||||
assert(asENGINE->SetEngineProperty(AngelScript::asEP_COPY_SCRIPT_SECTIONS, false) >= 0);
|
||||
assert(asENGINE->SetEngineProperty(AngelScript::asEP_ALLOW_MULTILINE_STRINGS, true) >= 0);
|
||||
assert(asENGINE->SetMessageCallback(AngelScript::asFUNCTION(MessageCallback), nullptr, AngelScript::asCALL_CDECL) >= 0);
|
||||
}
|
||||
|
||||
|
||||
@@ -95,7 +95,8 @@ void Project::ConfigFile::removeLine(const std::string& refLine)
|
||||
{
|
||||
if (!m_lockedFile)
|
||||
{
|
||||
LogModule.reportSource(LogVisor::FatalError, __FILE__, __LINE__, "Project::ConfigFile::lockAndRead not yet called");
|
||||
LogModule.reportSource(LogVisor::FatalError, __FILE__, __LINE__,
|
||||
"Project::ConfigFile::lockAndRead not yet called");
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -115,7 +116,8 @@ bool Project::ConfigFile::checkForLine(const std::string& refLine)
|
||||
{
|
||||
if (!m_lockedFile)
|
||||
{
|
||||
LogModule.reportSource(LogVisor::FatalError, __FILE__, __LINE__, "Project::ConfigFile::lockAndRead not yet called");
|
||||
LogModule.reportSource(LogVisor::FatalError, __FILE__, __LINE__,
|
||||
"Project::ConfigFile::lockAndRead not yet called");
|
||||
return false;
|
||||
}
|
||||
|
||||
@@ -131,7 +133,8 @@ void Project::ConfigFile::unlockAndDiscard()
|
||||
{
|
||||
if (!m_lockedFile)
|
||||
{
|
||||
LogModule.reportSource(LogVisor::FatalError, __FILE__, __LINE__, "Project::ConfigFile::lockAndRead not yet called");
|
||||
LogModule.reportSource(LogVisor::FatalError, __FILE__, __LINE__,
|
||||
"Project::ConfigFile::lockAndRead not yet called");
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -144,7 +147,8 @@ bool Project::ConfigFile::unlockAndCommit()
|
||||
{
|
||||
if (!m_lockedFile)
|
||||
{
|
||||
LogModule.reportSource(LogVisor::FatalError, __FILE__, __LINE__, "Project::ConfigFile::lockAndRead not yet called");
|
||||
LogModule.reportSource(LogVisor::FatalError, __FILE__, __LINE__,
|
||||
"Project::ConfigFile::lockAndRead not yet called");
|
||||
return false;
|
||||
}
|
||||
|
||||
@@ -186,6 +190,8 @@ bool Project::ConfigFile::unlockAndCommit()
|
||||
|
||||
Project::Project(const ProjectRootPath& rootPath)
|
||||
: m_rootPath(rootPath),
|
||||
m_dotPath(m_rootPath, _S(".hecl")),
|
||||
m_cookedRoot(m_dotPath, _S("cooked")),
|
||||
m_specs(*this, _S("specs")),
|
||||
m_paths(*this, _S("paths")),
|
||||
m_groups(*this, _S("groups"))
|
||||
@@ -200,11 +206,12 @@ Project::Project(const ProjectRootPath& rootPath)
|
||||
m_rootPath.getAbsolutePathUTF8() + "' isn't");
|
||||
|
||||
/* Create project directory structure */
|
||||
HECL::MakeDir(m_rootPath.getAbsolutePath() + _S("/.hecl"));
|
||||
HECL::MakeDir(m_rootPath.getAbsolutePath() + _S("/.hecl/cooked"));
|
||||
m_dotPath.makeDir();
|
||||
m_cookedRoot.makeDir();
|
||||
|
||||
/* Ensure beacon is valid or created */
|
||||
FILE* bf = HECL::Fopen((m_rootPath.getAbsolutePath() + _S("/.hecl/beacon")).c_str(), _S("a+b"));
|
||||
ProjectPath beaconPath(m_dotPath, _S("beacon"));
|
||||
FILE* bf = HECL::Fopen(beaconPath.getAbsolutePath().c_str(), _S("a+b"));
|
||||
struct BeaconStruct
|
||||
{
|
||||
HECL::FourCC magic;
|
||||
@@ -286,7 +293,8 @@ void Project::rescanDataSpecs()
|
||||
for (const DataSpecEntry* spec : DATA_SPEC_REGISTRY)
|
||||
{
|
||||
SystemUTF8View specUTF8(spec->m_name);
|
||||
m_compiledSpecs.push_back({*spec, m_specs.checkForLine(specUTF8.utf8_str()) ? true : false});
|
||||
m_compiledSpecs.push_back({*spec, ProjectPath(m_cookedRoot, spec->m_name + ".spec"),
|
||||
m_specs.checkForLine(specUTF8) ? true : false});
|
||||
}
|
||||
m_specs.unlockAndDiscard();
|
||||
}
|
||||
@@ -296,7 +304,9 @@ bool Project::enableDataSpecs(const std::vector<SystemString>& specs)
|
||||
m_specs.lockAndRead();
|
||||
for (const SystemString& spec : specs)
|
||||
m_specs.addLine(spec);
|
||||
return m_specs.unlockAndCommit();
|
||||
bool result = m_specs.unlockAndCommit();
|
||||
rescanDataSpecs();
|
||||
return result;
|
||||
}
|
||||
|
||||
bool Project::disableDataSpecs(const std::vector<SystemString>& specs)
|
||||
@@ -304,7 +314,9 @@ bool Project::disableDataSpecs(const std::vector<SystemString>& specs)
|
||||
m_specs.lockAndRead();
|
||||
for (const SystemString& spec : specs)
|
||||
m_specs.removeLine(spec);
|
||||
return m_specs.unlockAndCommit();
|
||||
bool result = m_specs.unlockAndCommit();
|
||||
rescanDataSpecs();
|
||||
return result;
|
||||
}
|
||||
|
||||
bool Project::cookPath(const ProjectPath& path,
|
||||
|
||||
@@ -2,79 +2,72 @@
|
||||
#include <stdexcept>
|
||||
#include <regex>
|
||||
|
||||
#if _WIN32
|
||||
char* win_realpath(const char* name, char* restrict resolved)
|
||||
{
|
||||
}
|
||||
#endif
|
||||
|
||||
namespace HECL
|
||||
{
|
||||
|
||||
static const SystemRegex regGLOB(_S("\\*"), SystemRegex::ECMAScript|SystemRegex::optimize);
|
||||
static const SystemRegex regPATHCOMP(_S("/([^/]+)"), SystemRegex::ECMAScript|SystemRegex::optimize);
|
||||
static const SystemRegex regPATHCOMP(_S("[/\\\\]*([^/\\\\]+)"), SystemRegex::ECMAScript|SystemRegex::optimize);
|
||||
static const SystemRegex regDRIVELETTER(_S("^([^/]*)/"), SystemRegex::ECMAScript|SystemRegex::optimize);
|
||||
|
||||
inline bool isAbsolute(const SystemString& path)
|
||||
static SystemString canonRelPath(const SystemString& path)
|
||||
{
|
||||
if (path.size() && path[0] == '/')
|
||||
return true;
|
||||
return false;
|
||||
}
|
||||
|
||||
bool ProjectPath::_canonAbsPath(const SystemString& path, bool& needsMake)
|
||||
{
|
||||
#if _WIN32
|
||||
#else
|
||||
SystemChar resolvedPath[PATH_MAX];
|
||||
if (!realpath(path.c_str(), resolvedPath))
|
||||
/* Absolute paths not allowed */
|
||||
if (path[0] == _S('/') || path[0] == _S('\\'))
|
||||
{
|
||||
if (errno != ENOENT)
|
||||
{
|
||||
throw std::system_error(errno, std::system_category(),
|
||||
"Unable to resolve '" + SystemUTF8View(path).utf8_str() +
|
||||
"' as a canonicalized path");
|
||||
return false;
|
||||
}
|
||||
else
|
||||
needsMake = true;
|
||||
throw std::invalid_argument("Absolute path provided; expected relative: " + path);
|
||||
return _S(".");
|
||||
}
|
||||
m_absPath = resolvedPath;
|
||||
#endif
|
||||
return true;
|
||||
|
||||
/* Tokenize Path */
|
||||
std::vector<SystemString> comps;
|
||||
HECL::SystemRegexMatch matches;
|
||||
SystemString in = path;
|
||||
while (std::regex_search(in, matches, regPATHCOMP))
|
||||
{
|
||||
in = matches.suffix();
|
||||
const SystemString& match = matches[1];
|
||||
if (!match.compare(_S(".")))
|
||||
continue;
|
||||
else if (!match.compare(_S("..")))
|
||||
{
|
||||
if (comps.empty())
|
||||
{
|
||||
/* Unable to resolve outside project */
|
||||
SystemUTF8View pathView(path);
|
||||
throw std::invalid_argument("Unable to resolve outside project root in " + pathView);
|
||||
return _S(".");
|
||||
}
|
||||
comps.pop_back();
|
||||
continue;
|
||||
}
|
||||
comps.push_back(match);
|
||||
}
|
||||
|
||||
/* Emit relative path */
|
||||
if (comps.size())
|
||||
{
|
||||
auto it = comps.begin();
|
||||
SystemString retval = *it;
|
||||
for (++it ; it != comps.end() ; ++it)
|
||||
{
|
||||
retval += _S('/');
|
||||
retval += *it;
|
||||
}
|
||||
return retval;
|
||||
}
|
||||
return ".";
|
||||
}
|
||||
|
||||
ProjectPath::ProjectPath(const ProjectPath& parentPath, const SystemString& path)
|
||||
: m_projRoot(parentPath.m_projRoot)
|
||||
{
|
||||
bool needsMake = false;
|
||||
if (!_canonAbsPath(parentPath.getRelativePath() + '/' + path, needsMake))
|
||||
return;
|
||||
if (m_absPath.size() < parentPath.m_absPath.size() ||
|
||||
m_absPath.compare(0, parentPath.m_absPath.size(),
|
||||
parentPath.m_absPath))
|
||||
{
|
||||
throw std::invalid_argument("'" + SystemUTF8View(m_absPath).utf8_str() + "' is not a subpath of '" +
|
||||
SystemUTF8View(parentPath.m_absPath).utf8_str() + "'");
|
||||
return;
|
||||
}
|
||||
if (m_absPath.size() == parentPath.m_absPath.size())
|
||||
{
|
||||
/* Copies of the project root are permitted */
|
||||
return;
|
||||
}
|
||||
SystemString::iterator beginit = m_absPath.begin() + parentPath.m_absPath.size();
|
||||
if (*beginit == _S('/'))
|
||||
++beginit;
|
||||
m_relPath = SystemString(beginit, m_absPath.end());
|
||||
m_relPath = canonRelPath(parentPath.m_relPath + '/' + path);
|
||||
m_absPath = parentPath.m_projRoot + '/' + m_relPath;
|
||||
m_hash = Hash(m_relPath);
|
||||
|
||||
#if HECL_UCS2
|
||||
m_utf8AbsPath = WideToUTF8(m_absPath);
|
||||
m_utf8RelPath = m_utf8AbsPath.c_str() + ((ProjectPath&)rootPath).m_utf8AbsPath.size();
|
||||
#endif
|
||||
|
||||
if (needsMake)
|
||||
_makeDir();
|
||||
}
|
||||
|
||||
ProjectPath::PathType ProjectPath::getPathType() const
|
||||
|
||||
Reference in New Issue
Block a user