447832dd81
* Updated the GameApplication to mount the engine.pak This allows loading the autoexec.cfg and bootstrap.game.<config>.<platform>.setreg from the engine.pak files The engine.pak is searched for in the following order: <ExecutableDirectory>/engine.pak, followed by <ProjectCacheRoot>/engine.pak Removed a lot of unused APIs from the AZ::IO::Archive feature suite Updated many of the AZ::IO::Archive classes to use AZ::IO::Path internally. The logic to search for files within an Archive has been updated to use AZ::IO::Path and to remove case-insensitve string comparisons Somehow removed the CryFile dependency on anything Cry Updated the Settings Registry to support reading from the FileIOBase and therefore Archive files in the GameLauncher via the `SetUseFileIO` function Removed AzFramework Dependency on md5 3rdParty library Signed-off-by: lumberyard-employee-dm <56135373+lumberyard-employee-dm@users.noreply.github.com> * Linux build fix Added an include of <stdio.h> before the <rapidxml/rapidxml.h> include as it usesnprintf. Added `static` to the constexpr constants in ExtractFileDescription in SettingsRegistryImpl.cpp to fix clang compile issue Signed-off-by: lumberyard-employee-dm <56135373+lumberyard-employee-dm@users.noreply.github.com> * Updated the case used to mount the Engine PAK file in the GameApplication to be Engine.pak to match the other locations where it is mounted Signed-off-by: lumberyard-employee-dm <56135373+lumberyard-employee-dm@users.noreply.github.com> * Updated the proper FFont call to FileIOBase::Size to supply the correct integer type of AZ::u64 instead of size_t This fixes building on platforms where size_t is type defined to be unsigned long Signed-off-by: lumberyard-employee-dm <56135373+lumberyard-employee-dm@users.noreply.github.com> * Fixed segmentation fault in Archive::Unregister when outputing the filename of the Archive file being closed Signed-off-by: lumberyard-employee-dm <56135373+lumberyard-employee-dm@users.noreply.github.com> * Fix calls to OpenPack in the Legacy LevelSystem The LevelSystem was calling the incorrect overload of OpenPack that accepts BindRoot for the mounted level.pak instead of the overload that that passes a memory block object. This was causing the level pak files to be mounted using an invalid directory, causing file accesses inside the level pak to fail. Signed-off-by: lumberyard-employee-dm <56135373+lumberyard-employee-dm@users.noreply.github.com> * Updated the error messages in the ZipDir CacheFactory class to use AZ_Warning directly Signed-off-by: lumberyard-employee-dm <56135373+lumberyard-employee-dm@users.noreply.github.com> * Updated the ArchiveFileIO m_trackedFiles container to store mapped type as an AZ::IO::Path Signed-off-by: lumberyard-employee-dm <56135373+lumberyard-employee-dm@users.noreply.github.com>
1139 lines
43 KiB
C++
1139 lines
43 KiB
C++
/*
|
|
* Copyright (c) Contributors to the Open 3D Engine Project.
|
|
* For complete copyright and license terms please see the LICENSE at the root of this distribution.
|
|
*
|
|
* SPDX-License-Identifier: Apache-2.0 OR MIT
|
|
*
|
|
*/
|
|
|
|
|
|
#include "EditorDefs.h"
|
|
|
|
#include "PythonEditorFuncs.h"
|
|
|
|
// Qt
|
|
#include <QMessageBox>
|
|
#include <QFileDialog>
|
|
|
|
#include <AzCore/Utils/Utils.h>
|
|
|
|
// AzToolsFramework
|
|
#include <AzToolsFramework/API/EditorPythonRunnerRequestsBus.h>
|
|
#include <AzToolsFramework/UI/UICore/WidgetHelpers.h>
|
|
|
|
// Editor
|
|
#include "CryEdit.h"
|
|
#include "GameEngine.h"
|
|
#include "ViewManager.h"
|
|
#include "StringDlg.h"
|
|
#include "GenericSelectItemDialog.h"
|
|
#include "Objects/BaseObject.h"
|
|
#include "Commands/CommandManager.h"
|
|
|
|
|
|
namespace
|
|
{
|
|
//////////////////////////////////////////////////////////////////////////
|
|
const char* PyGetCVarAsString(const char* pName)
|
|
{
|
|
ICVar* pCVar = GetIEditor()->GetSystem()->GetIConsole()->GetCVar(pName);
|
|
if (!pCVar)
|
|
{
|
|
AZ_Warning("editor", false, "PyGetCVar: Attempt to access non-existent CVar '%s'", pName ? pName : "(null)");
|
|
return "(missing)";
|
|
}
|
|
return pCVar->GetString();
|
|
}
|
|
|
|
//////////////////////////////////////////////////////////////////////////
|
|
// forward declarations
|
|
void PySetCVarFromInt(const char* pName, int pValue);
|
|
void PySetCVarFromFloat(const char* pName, float pValue);
|
|
|
|
//////////////////////////////////////////////////////////////////////////
|
|
void PySetCVarFromString(const char* pName, const char* pValue)
|
|
{
|
|
ICVar* pCVar = GetIEditor()->GetSystem()->GetIConsole()->GetCVar(pName);
|
|
if (!pCVar)
|
|
{
|
|
AZ_Warning("editor", false, "Attempt to set non-existent string CVar '%s'", pName ? pName : "(null)");
|
|
}
|
|
else if (pCVar->GetType() == CVAR_INT)
|
|
{
|
|
PySetCVarFromInt(pName, std::stol(pValue));
|
|
}
|
|
else if (pCVar->GetType() == CVAR_FLOAT)
|
|
{
|
|
PySetCVarFromFloat(pName, static_cast<float>(std::stod(pValue)));
|
|
}
|
|
else if (pCVar->GetType() != CVAR_STRING)
|
|
{
|
|
AZ_Warning("editor", false, "Type mismatch while assigning CVar '%s' as a string.", pName ? pName : "(null)");
|
|
}
|
|
else
|
|
{
|
|
pCVar->Set(pValue);
|
|
}
|
|
}
|
|
|
|
//////////////////////////////////////////////////////////////////////////
|
|
void PySetCVarFromInt(const char* pName, int pValue)
|
|
{
|
|
ICVar* pCVar = GetIEditor()->GetSystem()->GetIConsole()->GetCVar(pName);
|
|
if (!pCVar)
|
|
{
|
|
AZ_Warning("editor", false, "Attempt to set non-existent integer CVar '%s'", pName ? pName : "(null)");
|
|
}
|
|
else if (pCVar->GetType() == CVAR_FLOAT)
|
|
{
|
|
PySetCVarFromFloat(pName, float(pValue));
|
|
}
|
|
else if (pCVar->GetType() == CVAR_STRING)
|
|
{
|
|
auto stringValue = AZStd::to_string(pValue);
|
|
PySetCVarFromString(pName, stringValue.c_str());
|
|
}
|
|
else if (pCVar->GetType() != CVAR_INT)
|
|
{
|
|
AZ_Warning("editor", false, "Type mismatch while assigning CVar '%s' as an integer.", pName ? pName : "(null)");
|
|
}
|
|
else
|
|
{
|
|
pCVar->Set(pValue);
|
|
}
|
|
}
|
|
|
|
//////////////////////////////////////////////////////////////////////////
|
|
void PySetCVarFromFloat(const char* pName, float pValue)
|
|
{
|
|
ICVar* pCVar = GetIEditor()->GetSystem()->GetIConsole()->GetCVar(pName);
|
|
if (!pCVar)
|
|
{
|
|
AZ_Warning("editor", false, "Attempt to set non-existent float CVar '%s'", pName ? pName : "(null)");
|
|
}
|
|
else if (pCVar->GetType() == CVAR_INT)
|
|
{
|
|
PySetCVarFromInt(pName, static_cast<int>(pValue));
|
|
}
|
|
else if (pCVar->GetType() == CVAR_STRING)
|
|
{
|
|
auto stringValue = AZStd::to_string(pValue);
|
|
PySetCVarFromString(pName, stringValue.c_str());
|
|
}
|
|
else if (pCVar->GetType() != CVAR_FLOAT)
|
|
{
|
|
AZ_Warning("editor", false, "Type mismatch while assigning CVar '%s' as a float.", pName ? pName : "(null)");
|
|
}
|
|
else
|
|
{
|
|
pCVar->Set(pValue);
|
|
}
|
|
}
|
|
|
|
//////////////////////////////////////////////////////////////////////////
|
|
void PySetCVarFromAny(const char* pName, const AZStd::any& value)
|
|
{
|
|
ICVar* pCVar = GetIEditor()->GetSystem()->GetIConsole()->GetCVar(pName);
|
|
if (!pCVar)
|
|
{
|
|
AZ_Warning("editor", false, "Attempt to set non-existent float CVar '%s'", pName ? pName : "(null)");
|
|
}
|
|
else if (pCVar->GetType() == CVAR_INT)
|
|
{
|
|
PySetCVarFromInt(pName, static_cast<int>(AZStd::any_cast<AZ::s64>(value)));
|
|
}
|
|
else if (pCVar->GetType() == CVAR_FLOAT)
|
|
{
|
|
PySetCVarFromFloat(pName, static_cast<float>(AZStd::any_cast<double>(value)));
|
|
}
|
|
else if (pCVar->GetType() == CVAR_STRING)
|
|
{
|
|
PySetCVarFromString(pName, AZStd::any_cast<AZStd::string_view>(value).data());
|
|
}
|
|
else
|
|
{
|
|
AZ_Warning("editor", false, "Type mismatch while assigning CVar '%s' as a float.", pName ? pName : "(null)");
|
|
}
|
|
}
|
|
|
|
//////////////////////////////////////////////////////////////////////////
|
|
void PyEnterGameMode()
|
|
{
|
|
if (GetIEditor()->GetGameEngine())
|
|
{
|
|
GetIEditor()->GetGameEngine()->RequestSetGameMode(true);
|
|
}
|
|
}
|
|
|
|
void PyExitGameMode()
|
|
{
|
|
if (GetIEditor()->GetGameEngine())
|
|
{
|
|
GetIEditor()->GetGameEngine()->RequestSetGameMode(false);
|
|
}
|
|
}
|
|
|
|
bool PyIsInGameMode()
|
|
{
|
|
return GetIEditor()->IsInGameMode();
|
|
}
|
|
|
|
//////////////////////////////////////////////////////////////////////////
|
|
void PyEnterSimulationMode()
|
|
{
|
|
if (!GetIEditor()->IsInSimulationMode())
|
|
{
|
|
CCryEditApp::instance()->OnSwitchPhysics();
|
|
}
|
|
}
|
|
|
|
void PyExitSimulationMode()
|
|
{
|
|
if (GetIEditor()->IsInSimulationMode())
|
|
{
|
|
CCryEditApp::instance()->OnSwitchPhysics();
|
|
}
|
|
}
|
|
|
|
bool PyIsInSimulationMode()
|
|
{
|
|
return GetIEditor()->IsInSimulationMode();
|
|
}
|
|
|
|
//////////////////////////////////////////////////////////////////////////
|
|
void PyRunConsole(const char* text)
|
|
{
|
|
GetIEditor()->GetSystem()->GetIConsole()->ExecuteString(text);
|
|
}
|
|
|
|
//////////////////////////////////////////////////////////////////////////
|
|
bool GetPythonScriptPath(const char* pFile, QString& path)
|
|
{
|
|
bool bRelativePath = true;
|
|
char drive[_MAX_DRIVE];
|
|
char fdir[_MAX_DIR];
|
|
char fname[_MAX_FNAME];
|
|
char fext[_MAX_EXT];
|
|
drive[0] = '\0';
|
|
|
|
_splitpath_s(pFile, drive, fdir, fname, fext);
|
|
if (strlen(drive) != 0)
|
|
{
|
|
bRelativePath = false;
|
|
}
|
|
|
|
if (bRelativePath)
|
|
{
|
|
// Try to open from user folder
|
|
QString userSandboxFolder = Path::GetResolvedUserSandboxFolder();
|
|
Path::ConvertBackSlashToSlash(userSandboxFolder);
|
|
path = userSandboxFolder + pFile;
|
|
|
|
// If not found try editor folder
|
|
if (!CFileUtil::FileExists(path))
|
|
{
|
|
AZ::IO::FixedMaxPathString engineRoot = AZ::Utils::GetEnginePath();
|
|
QDir engineDir = !engineRoot.empty() ? QDir(QString(engineRoot.c_str())) : QDir::current();
|
|
|
|
QString scriptFolder = engineDir.absoluteFilePath("Assets/Editor/Scripts/");
|
|
Path::ConvertBackSlashToSlash(scriptFolder);
|
|
path = scriptFolder + pFile;
|
|
|
|
if (!CFileUtil::FileExists(path))
|
|
{
|
|
QString error = QString("Could not find '%1'\n in '%2'\n or '%3'\n").arg(pFile).arg(userSandboxFolder).arg(scriptFolder);
|
|
AZ_Warning("python", false, error.toUtf8().data());
|
|
return false;
|
|
}
|
|
}
|
|
}
|
|
else
|
|
{
|
|
path = pFile;
|
|
if (!CFileUtil::FileExists(path))
|
|
{
|
|
QString error = QString("Could not find '") + pFile + "'\n";
|
|
AZ_Warning("python", false, error.toUtf8().data());
|
|
return false;
|
|
}
|
|
}
|
|
|
|
Path::ConvertBackSlashToSlash(path);
|
|
return true;
|
|
}
|
|
|
|
//////////////////////////////////////////////////////////////////////////
|
|
void GetPythonArgumentsVector(const char* pArguments, QStringList& inputArguments)
|
|
{
|
|
if (pArguments == nullptr)
|
|
{
|
|
return;
|
|
}
|
|
|
|
inputArguments = QString(pArguments).split(" ", Qt::SkipEmptyParts);
|
|
}
|
|
|
|
//////////////////////////////////////////////////////////////////////////
|
|
void PyRunFileWithParameters(const char* pFile, const char* pArguments)
|
|
{
|
|
QString path;
|
|
QStringList inputArguments;
|
|
GetPythonArgumentsVector(pArguments, inputArguments);
|
|
if (GetPythonScriptPath(pFile, path))
|
|
{
|
|
AZStd::vector<AZStd::string_view> argList;
|
|
argList.reserve(inputArguments.size() + 1);
|
|
QByteArray p = path.toUtf8();
|
|
|
|
QVector<QByteArray> argData;
|
|
argData.reserve(inputArguments.count());
|
|
for (auto iter = inputArguments.begin(); iter != inputArguments.end(); ++iter)
|
|
{
|
|
argData.push_back(iter->toLatin1());
|
|
argList.push_back(argData.last().data());
|
|
}
|
|
using namespace AzToolsFramework;
|
|
EditorPythonRunnerRequestBus::Broadcast(&AzToolsFramework::EditorPythonRunnerRequestBus::Events::ExecuteByFilenameWithArgs, p.data(), argList);
|
|
}
|
|
}
|
|
|
|
void PyRunFile(const char* pFile)
|
|
{
|
|
PyRunFileWithParameters(pFile, nullptr);
|
|
}
|
|
|
|
//////////////////////////////////////////////////////////////////////////
|
|
void PyExecuteCommand(const char* cmdline)
|
|
{
|
|
GetIEditor()->GetCommandManager()->Execute(cmdline);
|
|
}
|
|
|
|
//////////////////////////////////////////////////////////////////////////
|
|
void PyLog(const char* pMessage)
|
|
{
|
|
if (strcmp(pMessage, "") != 0)
|
|
{
|
|
CryLogAlways("%s", pMessage);
|
|
}
|
|
}
|
|
|
|
//////////////////////////////////////////////////////////////////////////
|
|
bool PyMessageBox(const char* pMessage)
|
|
{
|
|
return QMessageBox::information(QApplication::activeWindow(), QString(), pMessage, QMessageBox::Ok | QMessageBox::Cancel) == QMessageBox::Ok;
|
|
}
|
|
|
|
bool PyMessageBoxYesNo(const char* pMessage)
|
|
{
|
|
return QMessageBox::question(QApplication::activeWindow(), QString(), pMessage) == QMessageBox::Yes;
|
|
}
|
|
|
|
bool PyMessageBoxOK(const char* pMessage)
|
|
{
|
|
return QMessageBox::information(QApplication::activeWindow(), QString(), pMessage) == QMessageBox::Ok;
|
|
}
|
|
|
|
AZStd::string PyEditBox(AZStd::string_view pTitle)
|
|
{
|
|
StringDlg stringDialog(pTitle.data());
|
|
if (stringDialog.exec() == QDialog::Accepted)
|
|
{
|
|
return stringDialog.GetString().toUtf8().constData();
|
|
}
|
|
return "";
|
|
}
|
|
|
|
AZStd::any PyEditBoxAndCheckProperty(const char* pTitle)
|
|
{
|
|
StringDlg stringDialog(pTitle);
|
|
stringDialog.SetString(QStringLiteral(""));
|
|
if (stringDialog.exec() == QDialog::Accepted)
|
|
{
|
|
const QString stringValue = stringDialog.GetString();
|
|
|
|
// detect data type
|
|
QString tempString = stringValue;
|
|
int countComa = 0;
|
|
int countOpenRoundBraket = 0;
|
|
int countCloseRoundBraket = 0;
|
|
int countDots = 0;
|
|
|
|
int posDots = 0;
|
|
int posComa = 0;
|
|
int posOpenRoundBraket = 0;
|
|
int posCloseRoundBraket = 0;
|
|
|
|
for (int i = 0; i < 3; i++)
|
|
{
|
|
if (tempString.indexOf(".", posDots) > -1)
|
|
{
|
|
posDots = tempString.indexOf(".", posDots) + 1;
|
|
countDots++;
|
|
}
|
|
if (tempString.indexOf(",", posComa) > -1)
|
|
{
|
|
posComa = tempString.indexOf(",", posComa) + 1;
|
|
countComa++;
|
|
}
|
|
if (tempString.indexOf("(", posOpenRoundBraket) > -1)
|
|
{
|
|
posOpenRoundBraket = tempString.indexOf("(", posOpenRoundBraket) + 1;
|
|
countOpenRoundBraket++;
|
|
}
|
|
if (tempString.indexOf(")", posCloseRoundBraket) > -1)
|
|
{
|
|
posCloseRoundBraket = tempString.indexOf(")", posCloseRoundBraket) + 1;
|
|
countCloseRoundBraket++;
|
|
}
|
|
}
|
|
|
|
if (countDots == 3 && countComa == 2 && countOpenRoundBraket == 1 && countCloseRoundBraket == 1)
|
|
{
|
|
// for example: (1.95, 2.75, 3.36)
|
|
QString valueRed = stringValue;
|
|
int iStart = valueRed.indexOf("(");
|
|
valueRed.remove(0, iStart + 1);
|
|
int iEnd = valueRed.indexOf(",");
|
|
valueRed.remove(iEnd, valueRed.length());
|
|
float fValueRed = valueRed.toFloat();
|
|
|
|
QString valueGreen = stringValue;
|
|
iStart = valueGreen.indexOf(",");
|
|
valueGreen.remove(0, iStart + 1);
|
|
iEnd = valueGreen.indexOf(",");
|
|
valueGreen.remove(iEnd, valueGreen.length());
|
|
float fValueGreen = valueGreen.toFloat();
|
|
|
|
QString valueBlue = stringValue;
|
|
valueBlue.remove(0, valueBlue.indexOf(",") + 1);
|
|
valueBlue.remove(0, valueBlue.indexOf(",") + 1);
|
|
valueBlue.remove(valueBlue.indexOf(")"), valueBlue.length());
|
|
float fValueBlue = valueBlue.toFloat();
|
|
|
|
return AZStd::make_any<AZ::Vector3>(fValueRed, fValueGreen, fValueBlue);
|
|
}
|
|
else if (countDots == 0 && countComa == 2 && countOpenRoundBraket == 1 && countCloseRoundBraket == 1)
|
|
{
|
|
// for example: (128, 32, 240)
|
|
const AZ::u8 lowColorValue { 0 };
|
|
const AZ::u8 highColorValue { 255 };
|
|
QString valueRed = stringValue;
|
|
int iStart = valueRed.indexOf("(");
|
|
valueRed.remove(0, iStart + 1);
|
|
int iEnd = valueRed.indexOf(",");
|
|
valueRed.remove(iEnd, valueRed.length());
|
|
AZ::u8 iValueRed = AZStd::clamp(aznumeric_cast<AZ::u8>(valueRed.toInt()), lowColorValue, highColorValue);
|
|
|
|
QString valueGreen = stringValue;
|
|
iStart = valueGreen.indexOf(",");
|
|
valueGreen.remove(0, iStart + 1);
|
|
iEnd = valueGreen.indexOf(",");
|
|
valueGreen.remove(iEnd, valueGreen.length());
|
|
AZ::u8 iValueGreen = AZStd::clamp(aznumeric_cast<AZ::u8>(valueGreen.toInt()), lowColorValue, highColorValue);
|
|
|
|
QString valueBlue = stringValue;
|
|
valueBlue.remove(0, valueBlue.indexOf(",") + 1);
|
|
valueBlue.remove(0, valueBlue.indexOf(",") + 1);
|
|
valueBlue.remove(valueBlue.indexOf(")"), valueBlue.length());
|
|
AZ::u8 iValueBlue = AZStd::clamp(aznumeric_cast<AZ::u8>(valueBlue.toInt()), lowColorValue, highColorValue);
|
|
|
|
return AZStd::make_any<AZ::Color>(iValueRed, iValueGreen, iValueBlue, highColorValue);
|
|
}
|
|
else if (countDots == 1 && countComa == 0 && countOpenRoundBraket == 0 && countCloseRoundBraket == 0)
|
|
{
|
|
// for example: 2.56
|
|
return AZStd::make_any<double>(stringValue.toDouble());
|
|
}
|
|
else if (countDots == 0 && countComa == 0 && countOpenRoundBraket == 0 && countCloseRoundBraket == 0)
|
|
{
|
|
if (stringValue == "False" || stringValue == "True")
|
|
{
|
|
// for example: True
|
|
return AZStd::make_any<bool>(stringValue == "True");
|
|
}
|
|
else
|
|
{
|
|
const bool anyNotDigits = AZStd::any_of(stringValue.begin(), stringValue.end(), [](const QChar& ch) { return !ch.isDigit(); });
|
|
|
|
// looks like a string value?
|
|
if (stringValue.isEmpty() || anyNotDigits)
|
|
{
|
|
// for example: Hello
|
|
return AZStd::make_any<AZStd::string>(stringValue.toUtf8().data());
|
|
}
|
|
else // then it looks like an integer
|
|
{
|
|
// for example: 456
|
|
return AZStd::make_any<AZ::s64>(stringValue.toInt());
|
|
}
|
|
}
|
|
}
|
|
}
|
|
QMessageBox::critical(AzToolsFramework::GetActiveWindow(), QObject::tr("Invalid Data"), QObject::tr("Invalid data type."));
|
|
return {};
|
|
}
|
|
|
|
AZStd::string PyOpenFileBox()
|
|
{
|
|
QString path = QFileDialog::getOpenFileName();
|
|
if (!path.isEmpty())
|
|
{
|
|
Path::ConvertBackSlashToSlash(path);
|
|
}
|
|
return path.toUtf8().constData();
|
|
}
|
|
|
|
AZStd::string PyComboBox(AZStd::string title, AZStd::vector<AZStd::string> values, int selectedIdx = 0)
|
|
{
|
|
AZStd::string result;
|
|
|
|
if (title.empty())
|
|
{
|
|
throw std::runtime_error("Incorrect title argument passed in. ");
|
|
}
|
|
|
|
if (values.size() == 0)
|
|
{
|
|
throw std::runtime_error("Empty value list passed in. ");
|
|
}
|
|
|
|
QStringList list;
|
|
|
|
for (const AZStd::string& str : values)
|
|
{
|
|
list.push_back(str.c_str());
|
|
}
|
|
|
|
CGenericSelectItemDialog pyDlg;
|
|
pyDlg.setWindowTitle(title.c_str());
|
|
pyDlg.SetMode(CGenericSelectItemDialog::eMODE_LIST);
|
|
pyDlg.SetItems(list);
|
|
pyDlg.PreSelectItem(list[selectedIdx]);
|
|
|
|
if (pyDlg.exec() == QDialog::Accepted)
|
|
{
|
|
result = pyDlg.GetSelectedItem().toUtf8().constData();
|
|
}
|
|
|
|
return result;
|
|
}
|
|
|
|
void PyCrash()
|
|
{
|
|
AZ_Crash();
|
|
}
|
|
|
|
static void PyDrawLabel(int x, int y, float size, float r, float g, float b, float a, const char* pLabel)
|
|
{
|
|
if (!pLabel)
|
|
{
|
|
throw std::logic_error("No label given.");
|
|
return;
|
|
}
|
|
|
|
if (!r || !g || !b || !a)
|
|
{
|
|
throw std::logic_error("Invalid color parameters given.");
|
|
return;
|
|
}
|
|
|
|
if (!x || !y || !size)
|
|
{
|
|
throw std::logic_error("Invalid position or size parameters given.");
|
|
}
|
|
else
|
|
{
|
|
// ToDo: Remove function or update to work with Atom? LYN-3672
|
|
// float color[] = {r, g, b, a};
|
|
// ???->Draw2dLabel(x, y, size, color, false, pLabel);
|
|
}
|
|
}
|
|
|
|
//////////////////////////////////////////////////////////////////////////
|
|
// Constrain
|
|
//////////////////////////////////////////////////////////////////////////
|
|
const char* PyGetAxisConstraint()
|
|
{
|
|
AxisConstrains actualConstrain = GetIEditor()->GetAxisConstrains();
|
|
switch (actualConstrain)
|
|
{
|
|
case AXIS_X:
|
|
return "X";
|
|
case AXIS_Y:
|
|
return "Y";
|
|
case AXIS_Z:
|
|
return "Z";
|
|
case AXIS_XY:
|
|
return "XY";
|
|
case AXIS_XZ:
|
|
return "XZ";
|
|
case AXIS_YZ:
|
|
return "YZ";
|
|
case AXIS_XYZ:
|
|
return "XYZ";
|
|
case AXIS_TERRAIN:
|
|
return (GetIEditor()->IsTerrainAxisIgnoreObjects()) ? "TERRAIN" : "TERRAINSNAP";
|
|
default:
|
|
throw std::logic_error("Invalid axes.");
|
|
}
|
|
}
|
|
|
|
void PySetAxisConstraint(AZStd::string_view pConstrain)
|
|
{
|
|
if (pConstrain == "X")
|
|
{
|
|
GetIEditor()->SetAxisConstraints(AXIS_X);
|
|
}
|
|
else if (pConstrain == "Y")
|
|
{
|
|
GetIEditor()->SetAxisConstraints(AXIS_Y);
|
|
}
|
|
else if (pConstrain == "Z")
|
|
{
|
|
GetIEditor()->SetAxisConstraints(AXIS_Z);
|
|
}
|
|
else if (pConstrain == "XY")
|
|
{
|
|
GetIEditor()->SetAxisConstraints(AXIS_XY);
|
|
}
|
|
else if (pConstrain == "YZ")
|
|
{
|
|
GetIEditor()->SetAxisConstraints(AXIS_YZ);
|
|
}
|
|
else if (pConstrain == "XZ")
|
|
{
|
|
GetIEditor()->SetAxisConstraints(AXIS_XZ);
|
|
}
|
|
else if (pConstrain == "XYZ")
|
|
{
|
|
GetIEditor()->SetAxisConstraints(AXIS_XYZ);
|
|
}
|
|
else if (pConstrain == "TERRAIN")
|
|
{
|
|
GetIEditor()->SetAxisConstraints(AXIS_TERRAIN);
|
|
GetIEditor()->SetTerrainAxisIgnoreObjects(true);
|
|
}
|
|
else if (pConstrain == "TERRAINSNAP")
|
|
{
|
|
GetIEditor()->SetAxisConstraints(AXIS_TERRAIN);
|
|
GetIEditor()->SetTerrainAxisIgnoreObjects(false);
|
|
}
|
|
else
|
|
{
|
|
throw std::logic_error("Invalid axes.");
|
|
}
|
|
}
|
|
|
|
//////////////////////////////////////////////////////////////////////////
|
|
AZ::IO::Path PyGetPakFromFile(const char* filename)
|
|
{
|
|
auto pIPak = GetIEditor()->GetSystem()->GetIPak();
|
|
AZ::IO::HandleType fileHandle = pIPak->FOpen(filename, "rb");
|
|
if (fileHandle == AZ::IO::InvalidHandle)
|
|
{
|
|
throw std::logic_error("Invalid file name.");
|
|
}
|
|
AZ::IO::Path pArchPath = pIPak->GetFileArchivePath(fileHandle);
|
|
pIPak->FClose(fileHandle);
|
|
|
|
return pArchPath;
|
|
}
|
|
|
|
//////////////////////////////////////////////////////////////////////////
|
|
void PyUndo()
|
|
{
|
|
GetIEditor()->Undo();
|
|
}
|
|
|
|
//////////////////////////////////////////////////////////////////////////
|
|
void PyRedo()
|
|
{
|
|
GetIEditor()->Redo();
|
|
}
|
|
}
|
|
|
|
//////////////////////////////////////////////////////////////////////////
|
|
// Temporal, to be removed by LY-101149
|
|
AZ::EntityId PyFindEditorEntity(const char* name)
|
|
{
|
|
AZ::EntityId foundEntityId;
|
|
|
|
auto searchFunc = [name, &foundEntityId](AZ::Entity* e)
|
|
{
|
|
if (!foundEntityId.IsValid() && e->GetName() == name)
|
|
{
|
|
bool isEditorEntity = false;
|
|
AzToolsFramework::EditorEntityContextRequestBus::BroadcastResult(isEditorEntity, &AzToolsFramework::EditorEntityContextRequests::IsEditorEntity, e->GetId());
|
|
if (isEditorEntity)
|
|
{
|
|
foundEntityId = e->GetId();
|
|
}
|
|
}
|
|
};
|
|
|
|
AZ::ComponentApplicationBus::Broadcast(&AZ::ComponentApplicationRequests::EnumerateEntities, searchFunc);
|
|
return foundEntityId;
|
|
}
|
|
|
|
AZ::EntityId PyFindGameEntity(const char* name)
|
|
{
|
|
AZ::EntityId foundEntityId;
|
|
|
|
auto searchFunc = [name, &foundEntityId](AZ::Entity* e)
|
|
{
|
|
if (!foundEntityId.IsValid() && e->GetName() == name)
|
|
{
|
|
bool isEditorEntity = true;
|
|
AzToolsFramework::EditorEntityContextRequestBus::BroadcastResult(isEditorEntity, &AzToolsFramework::EditorEntityContextRequests::IsEditorEntity, e->GetId());
|
|
if (!isEditorEntity)
|
|
{
|
|
foundEntityId = e->GetId();
|
|
}
|
|
}
|
|
};
|
|
|
|
AZ::ComponentApplicationBus::Broadcast(&AZ::ComponentApplicationRequests::EnumerateEntities, searchFunc);
|
|
return foundEntityId;
|
|
}
|
|
|
|
|
|
struct PyDumpBindings
|
|
{
|
|
static AZ_INLINE bool IsBehaviorFlaggedForEditor(const AZ::AttributeArray& attributes)
|
|
{
|
|
// defaults to Launcher
|
|
AZ::Script::Attributes::ScopeFlags scopeType = AZ::Script::Attributes::ScopeFlags::Launcher;
|
|
AZ::Attribute* scopeAttribute = AZ::FindAttribute(AZ::Script::Attributes::Scope, attributes);
|
|
if (scopeAttribute)
|
|
{
|
|
AZ::AttributeReader scopeAttributeReader(nullptr, scopeAttribute);
|
|
scopeAttributeReader.Read<AZ::Script::Attributes::ScopeFlags>(scopeType);
|
|
}
|
|
return (scopeType == AZ::Script::Attributes::ScopeFlags::Automation || scopeType == AZ::Script::Attributes::ScopeFlags::Common);
|
|
}
|
|
|
|
static AZ_INLINE AZStd::string GetModuleName(const AZ::AttributeArray& attributes)
|
|
{
|
|
AZStd::string moduleName;
|
|
AZ::Attribute* moduleAttribute = AZ::FindAttribute(AZ::Script::Attributes::Module, attributes);
|
|
if (moduleAttribute)
|
|
{
|
|
AZ::AttributeReader scopeAttributeReader(nullptr, moduleAttribute);
|
|
scopeAttributeReader.Read<AZStd::string>(moduleName);
|
|
}
|
|
if (!moduleName.empty())
|
|
{
|
|
moduleName = "azlmbr." + moduleName;
|
|
}
|
|
else
|
|
{
|
|
moduleName = "azlmbr";
|
|
}
|
|
|
|
return moduleName;
|
|
}
|
|
|
|
|
|
static AZStd::string ParameterToString(const AZ::BehaviorMethod* method, size_t index)
|
|
{
|
|
const AZStd::string* argNameStr = method->GetArgumentName(index);
|
|
const char* argName = (argNameStr && !argNameStr->empty()) ? argNameStr->c_str() : nullptr;
|
|
if (argName)
|
|
{
|
|
return AZStd::string::format("%s %s", method->GetArgument(index)->m_name, argName);
|
|
}
|
|
else
|
|
{
|
|
return method->GetArgument(index)->m_name;
|
|
}
|
|
}
|
|
|
|
static AZStd::string MethodArgumentsToString(const AZ::BehaviorMethod* method)
|
|
{
|
|
AZStd::string ret;
|
|
AZStd::string argumentStr;
|
|
for (size_t i = 0; i < method->GetNumArguments(); ++i)
|
|
{
|
|
argumentStr = ParameterToString(method, i);
|
|
ret += argumentStr;
|
|
if (i < method->GetNumArguments() - 1)
|
|
{
|
|
ret += ", ";
|
|
}
|
|
}
|
|
return ret;
|
|
}
|
|
|
|
static AZStd::string MethodToString(const AZStd::string& methodName, const AZ::BehaviorMethod* method)
|
|
{
|
|
AZStd::string methodNameStrip = methodName.data() + methodName.rfind(':') + 1; // remove ClassName:: part as it is redundant
|
|
return AZStd::string::format("%s %s(%s)%s", method->GetResult()->m_name, methodNameStrip.c_str(), MethodArgumentsToString(method).c_str(), method->m_isConst ? " const" : "");
|
|
}
|
|
|
|
static AZStd::string GetExposedPythonClasses()
|
|
{
|
|
AZ::BehaviorContext* behaviorContext(nullptr);
|
|
AZ::ComponentApplicationBus::BroadcastResult(behaviorContext, &AZ::ComponentApplicationRequests::GetBehaviorContext);
|
|
|
|
AZStd::string output = "";
|
|
output += "// Classes\n\n";
|
|
|
|
for (auto elem : behaviorContext->m_classes)
|
|
{
|
|
AZ::BehaviorClass* cls = elem.second;
|
|
|
|
bool exposedToPython = IsBehaviorFlaggedForEditor(cls->m_attributes);
|
|
if (!exposedToPython)
|
|
continue;
|
|
|
|
output += AZStd::string::format("// Module: %s\n", GetModuleName(cls->m_attributes).c_str());
|
|
output += AZStd::string::format("class %s\n", cls->m_name.c_str());
|
|
output += "{\n";
|
|
|
|
if (cls->m_methods.size() > 0)
|
|
{
|
|
output += " // Methods\n";
|
|
for (auto method_elem : cls->m_methods)
|
|
{
|
|
output += AZStd::string::format(" %s;\n", MethodToString(method_elem.first, method_elem.second).c_str());
|
|
}
|
|
}
|
|
if (cls->m_properties.size() > 0)
|
|
{
|
|
output += " // Properties\n";
|
|
for (auto property_elem : cls->m_properties)
|
|
{
|
|
AZ::BehaviorProperty* bproperty = property_elem.second;
|
|
output += AZStd::string::format(" %s %s;\n", bproperty->m_getter->GetResult()->m_name, bproperty->m_name.c_str());
|
|
}
|
|
}
|
|
|
|
output += "}\n";
|
|
}
|
|
output += "\n\n// Ebuses\n\n";
|
|
for (auto elem : behaviorContext->m_ebuses)
|
|
{
|
|
AZ::BehaviorEBus* ebus = elem.second;
|
|
|
|
bool exposedToPython = IsBehaviorFlaggedForEditor(ebus->m_attributes);
|
|
if (!exposedToPython)
|
|
continue;
|
|
|
|
output += AZStd::string::format("// Module: %s\n", GetModuleName(ebus->m_attributes).c_str());
|
|
output += AZStd::string::format("ebus %s\n", ebus->m_name.c_str());
|
|
output += "{\n";
|
|
for (auto event_elem : ebus->m_events)
|
|
{
|
|
auto method = event_elem.second.m_event ? event_elem.second.m_event : event_elem.second.m_broadcast;
|
|
if (method)
|
|
{
|
|
const char* comment = event_elem.second.m_event ? "/* event */" : "/* broadcast */";
|
|
output += AZStd::string::format(" %s %s\n", comment, MethodToString(event_elem.first, method).c_str());
|
|
}
|
|
else
|
|
{
|
|
output += AZStd::string::format(" %s %s\n", "/* unknown */", event_elem.first.c_str());
|
|
}
|
|
}
|
|
|
|
if (ebus->m_createHandler)
|
|
{
|
|
AZ::BehaviorEBusHandler* handler = nullptr;
|
|
ebus->m_createHandler->InvokeResult(handler);
|
|
if (handler)
|
|
{
|
|
const auto& notifications = handler->GetEvents();
|
|
for (const auto& notification : notifications)
|
|
{
|
|
AZStd::string argsStr;
|
|
const size_t paramCount = notification.m_parameters.size();
|
|
for (size_t i = 0; i < notification.m_parameters.size(); ++i)
|
|
{
|
|
AZStd::string argName = notification.m_parameters[i].m_name;
|
|
argsStr += argName;
|
|
if (i != paramCount - 1)
|
|
{
|
|
argsStr += ", ";
|
|
}
|
|
}
|
|
|
|
AZStd::string funcName = notification.m_name;
|
|
output += AZStd::string::format(" /* notification */ %s(%s);\n", funcName.c_str(), argsStr.c_str());
|
|
}
|
|
ebus->m_destroyHandler->Invoke(handler);
|
|
}
|
|
}
|
|
|
|
output += "}\n";
|
|
|
|
}
|
|
AzFramework::StringFunc::Replace(output, "AZStd::basic_string<char, AZStd::char_traits<char>, allocator>", "AZStd::string");
|
|
return output;
|
|
}
|
|
};
|
|
|
|
//////////////////////////////////////////////////////////////////////////
|
|
|
|
namespace AzToolsFramework
|
|
{
|
|
void PythonEditorComponent::Reflect(AZ::ReflectContext* context)
|
|
{
|
|
if (AZ::BehaviorContext* behaviorContext = azrtti_cast<AZ::BehaviorContext*>(context))
|
|
{
|
|
behaviorContext->EBus<EditorLayerPythonRequestBus>("PythonEditorBus")
|
|
->Attribute(AZ::Script::Attributes::Scope, AZ::Script::Attributes::ScopeFlags::Automation)
|
|
->Attribute(AZ::Script::Attributes::Module, "python_editor_funcs")
|
|
->Event("GetCVar", &EditorLayerPythonRequestBus::Events::GetCVar)
|
|
->Event("SetCVar", &EditorLayerPythonRequestBus::Events::SetCVar)
|
|
->Event("SetCVarFromString", &EditorLayerPythonRequestBus::Events::SetCVarFromString)
|
|
->Event("SetCVarFromInteger", &EditorLayerPythonRequestBus::Events::SetCVarFromInteger)
|
|
->Event("SetCVarFromFloat", &EditorLayerPythonRequestBus::Events::SetCVarFromFloat)
|
|
->Event("RunConsole", &EditorLayerPythonRequestBus::Events::PyRunConsole)
|
|
->Event("EnterGameMode", &EditorLayerPythonRequestBus::Events::EnterGameMode)
|
|
->Event("IsInGameMode", &EditorLayerPythonRequestBus::Events::IsInGameMode)
|
|
->Event("ExitGameMode", &EditorLayerPythonRequestBus::Events::ExitGameMode)
|
|
->Event("EnterSimulationMode", &EditorLayerPythonRequestBus::Events::EnterSimulationMode)
|
|
->Event("IsInSimulationMode", &EditorLayerPythonRequestBus::Events::IsInSimulationMode)
|
|
->Event("ExitSimulationMode", &EditorLayerPythonRequestBus::Events::ExitSimulationMode)
|
|
->Event("RunFile", &EditorLayerPythonRequestBus::Events::RunFile)
|
|
->Event("RunFileParameters", &EditorLayerPythonRequestBus::Events::RunFileParameters)
|
|
->Event("ExecuteCommand", &EditorLayerPythonRequestBus::Events::ExecuteCommand)
|
|
->Event("MessageBoxOkCancel", &EditorLayerPythonRequestBus::Events::MessageBoxOkCancel)
|
|
->Event("MessageBoxYesNo", &EditorLayerPythonRequestBus::Events::MessageBoxYesNo)
|
|
->Event("MessageBoxOk", &EditorLayerPythonRequestBus::Events::MessageBoxOk)
|
|
->Event("EditBox", &EditorLayerPythonRequestBus::Events::EditBox)
|
|
->Event("EditBoxCheckDataType", &EditorLayerPythonRequestBus::Events::EditBoxCheckDataType)
|
|
->Event("OpenFileBox", &EditorLayerPythonRequestBus::Events::OpenFileBox)
|
|
->Event("GetAxisConstraint", &EditorLayerPythonRequestBus::Events::GetAxisConstraint)
|
|
->Event("SetAxisConstraint", &EditorLayerPythonRequestBus::Events::SetAxisConstraint)
|
|
->Event("GetPakFromFile", &EditorLayerPythonRequestBus::Events::GetPakFromFile)
|
|
->Event("Log", &EditorLayerPythonRequestBus::Events::Log)
|
|
->Event("Undo", &EditorLayerPythonRequestBus::Events::Undo)
|
|
->Event("Redo", &EditorLayerPythonRequestBus::Events::Redo)
|
|
->Event("DrawLabel", &EditorLayerPythonRequestBus::Events::DrawLabel)
|
|
->Event("ComboBox", &EditorLayerPythonRequestBus::Events::ComboBox)
|
|
;
|
|
}
|
|
}
|
|
|
|
void PythonEditorComponent::Activate()
|
|
{
|
|
EditorLayerPythonRequestBus::Handler::BusConnect(GetEntityId());
|
|
}
|
|
|
|
void PythonEditorComponent::Deactivate()
|
|
{
|
|
EditorLayerPythonRequestBus::Handler::BusDisconnect();
|
|
}
|
|
|
|
const char* PythonEditorComponent::GetCVar(const char* pName)
|
|
{
|
|
return PyGetCVarAsString(pName);
|
|
}
|
|
|
|
void PythonEditorComponent::SetCVar(const char* pName, const AZStd::any& value)
|
|
{
|
|
return PySetCVarFromAny(pName, value);
|
|
}
|
|
|
|
void PythonEditorComponent::SetCVarFromString(const char* pName, const char* pValue)
|
|
{
|
|
return PySetCVarFromString(pName, pValue);
|
|
}
|
|
|
|
void PythonEditorComponent::SetCVarFromInteger(const char* pName, int pValue)
|
|
{
|
|
return PySetCVarFromInt(pName, pValue);
|
|
}
|
|
|
|
void PythonEditorComponent::SetCVarFromFloat(const char* pName, float pValue)
|
|
{
|
|
return PySetCVarFromFloat(pName, pValue);
|
|
}
|
|
|
|
void PythonEditorComponent::PyRunConsole(const char* text)
|
|
{
|
|
return ::PyRunConsole(text);
|
|
}
|
|
|
|
void PythonEditorComponent::EnterGameMode()
|
|
{
|
|
return PyEnterGameMode();
|
|
}
|
|
|
|
bool PythonEditorComponent::IsInGameMode()
|
|
{
|
|
return PyIsInGameMode();
|
|
}
|
|
|
|
void PythonEditorComponent::ExitGameMode()
|
|
{
|
|
return PyExitGameMode();
|
|
}
|
|
|
|
void PythonEditorComponent::EnterSimulationMode()
|
|
{
|
|
return PyEnterSimulationMode();
|
|
}
|
|
|
|
bool PythonEditorComponent::IsInSimulationMode()
|
|
{
|
|
return PyIsInSimulationMode();
|
|
}
|
|
|
|
void PythonEditorComponent::ExitSimulationMode()
|
|
{
|
|
return PyExitSimulationMode();
|
|
}
|
|
|
|
void PythonEditorComponent::RunFile(const char *pFile)
|
|
{
|
|
return PyRunFile(pFile);
|
|
}
|
|
|
|
void PythonEditorComponent::RunFileParameters(const char* pFile, const char* pArguments)
|
|
{
|
|
return PyRunFileWithParameters(pFile, pArguments);
|
|
}
|
|
|
|
void PythonEditorComponent::ExecuteCommand(const char* cmdline)
|
|
{
|
|
return PyExecuteCommand(cmdline);
|
|
}
|
|
|
|
bool PythonEditorComponent::MessageBoxOkCancel(const char* pMessage)
|
|
{
|
|
return PyMessageBox(pMessage);
|
|
}
|
|
|
|
bool PythonEditorComponent::MessageBoxYesNo(const char* pMessage)
|
|
{
|
|
return PyMessageBoxYesNo(pMessage);
|
|
}
|
|
|
|
bool PythonEditorComponent::MessageBoxOk(const char* pMessage)
|
|
{
|
|
return PyMessageBoxOK(pMessage);
|
|
}
|
|
|
|
AZStd::string PythonEditorComponent::EditBox(AZStd::string_view pTitle)
|
|
{
|
|
return PyEditBox(pTitle);
|
|
}
|
|
|
|
AZStd::any PythonEditorComponent::EditBoxCheckDataType(const char* pTitle)
|
|
{
|
|
return PyEditBoxAndCheckProperty(pTitle);
|
|
}
|
|
|
|
AZStd::string PythonEditorComponent::OpenFileBox()
|
|
{
|
|
return PyOpenFileBox();
|
|
}
|
|
|
|
const char* PythonEditorComponent::GetAxisConstraint()
|
|
{
|
|
return PyGetAxisConstraint();
|
|
}
|
|
|
|
void PythonEditorComponent::SetAxisConstraint(AZStd::string_view pConstrain)
|
|
{
|
|
return PySetAxisConstraint(pConstrain);
|
|
}
|
|
|
|
AZ::IO::Path PythonEditorComponent::GetPakFromFile(const char* filename)
|
|
{
|
|
return PyGetPakFromFile(filename);
|
|
}
|
|
|
|
void PythonEditorComponent::Log(const char* pMessage)
|
|
{
|
|
return PyLog(pMessage);
|
|
}
|
|
|
|
void PythonEditorComponent::Undo()
|
|
{
|
|
return PyUndo();
|
|
}
|
|
|
|
void PythonEditorComponent::Redo()
|
|
{
|
|
return PyRedo();
|
|
}
|
|
|
|
void PythonEditorComponent::DrawLabel(int x, int y, float size, float r, float g, float b, float a, const char* pLabel)
|
|
{
|
|
return PyDrawLabel(x, y, size, r, g, b, a, pLabel);
|
|
}
|
|
|
|
AZStd::string PythonEditorComponent::ComboBox(AZStd::string title, AZStd::vector<AZStd::string> values, int selectedIdx)
|
|
{
|
|
return PyComboBox(title, values, selectedIdx);
|
|
}
|
|
}
|
|
|
|
namespace AzToolsFramework
|
|
{
|
|
void PythonEditorFuncsHandler::Reflect(AZ::ReflectContext* context)
|
|
{
|
|
if (auto behaviorContext = azrtti_cast<AZ::BehaviorContext*>(context))
|
|
{
|
|
// this will put these methods into the 'azlmbr.legacy.general' module
|
|
auto addLegacyGeneral = [](AZ::BehaviorContext::GlobalMethodBuilder methodBuilder)
|
|
{
|
|
methodBuilder->Attribute(AZ::Script::Attributes::Scope, AZ::Script::Attributes::ScopeFlags::Automation)
|
|
->Attribute(AZ::Script::Attributes::Category, "Legacy/General")
|
|
->Attribute(AZ::Script::Attributes::Module, "legacy.general");
|
|
};
|
|
addLegacyGeneral(behaviorContext->Method("get_cvar", PyGetCVarAsString, nullptr, "Gets a CVar value as a string."));
|
|
addLegacyGeneral(behaviorContext->Method("set_cvar", PySetCVarFromAny, nullptr, "Sets a CVar value from any simple value."));
|
|
addLegacyGeneral(behaviorContext->Method("set_cvar_string", PySetCVarFromString, nullptr, "Sets a CVar value from a string."));
|
|
addLegacyGeneral(behaviorContext->Method("set_cvar_integer", PySetCVarFromInt, nullptr, "Sets a CVar value from an integer."));
|
|
addLegacyGeneral(behaviorContext->Method("set_cvar_float", PySetCVarFromFloat, nullptr, "Sets a CVar value from a float."));
|
|
addLegacyGeneral(behaviorContext->Method("run_console", PyRunConsole, nullptr, "Runs a console command."));
|
|
|
|
addLegacyGeneral(behaviorContext->Method("enter_game_mode", PyEnterGameMode, nullptr, "Enters the editor game mode."));
|
|
addLegacyGeneral(behaviorContext->Method("is_in_game_mode", PyIsInGameMode, nullptr, "Queries if it's in the game mode or not."));
|
|
addLegacyGeneral(behaviorContext->Method("exit_game_mode", PyExitGameMode, nullptr, "Exits the editor game mode."));
|
|
|
|
addLegacyGeneral(behaviorContext->Method("enter_simulation_mode", PyEnterSimulationMode, nullptr, "Enters the editor AI/Physics simulation mode."));
|
|
addLegacyGeneral(behaviorContext->Method("is_in_simulation_mode", PyIsInSimulationMode, nullptr, "Queries if the editor is currently in the AI/Physics simulation mode or not."));
|
|
addLegacyGeneral(behaviorContext->Method("exit_simulation_mode", PyExitSimulationMode, nullptr, "Exits the editor AI/Physics simulation mode."));
|
|
addLegacyGeneral(behaviorContext->Method("run_file", PyRunFile, nullptr, "Runs a script file. A relative path from the editor user folder or an absolute path should be given as an argument."));
|
|
addLegacyGeneral(behaviorContext->Method("run_file_parameters", PyRunFileWithParameters, nullptr, "Runs a script file with parameters. A relative path from the editor user folder or an absolute path should be given as an argument. The arguments should be separated by whitespace."));
|
|
addLegacyGeneral(behaviorContext->Method("execute_command", PyExecuteCommand, nullptr, "Executes a given string as an editor command."));
|
|
|
|
addLegacyGeneral(behaviorContext->Method("message_box", PyMessageBox, nullptr, "Shows a confirmation message box with ok|cancel and shows a custom message."));
|
|
addLegacyGeneral(behaviorContext->Method("message_box_yes_no", PyMessageBoxYesNo, nullptr, "Shows a confirmation message box with yes|no and shows a custom message."));
|
|
addLegacyGeneral(behaviorContext->Method("message_box_ok", PyMessageBoxOK, nullptr, "Shows a confirmation message box with only ok and shows a custom message."));
|
|
addLegacyGeneral(behaviorContext->Method("edit_box", PyEditBox, nullptr, "Shows an edit box and returns the value as string."));
|
|
|
|
addLegacyGeneral(behaviorContext->Method("edit_box_check_data_type", PyEditBoxAndCheckProperty, nullptr, "Shows an edit box and checks the custom value to use the return value with other functions correctly."));
|
|
|
|
addLegacyGeneral(behaviorContext->Method("open_file_box", PyOpenFileBox, nullptr, "Shows an open file box and returns the selected file path and name."));
|
|
|
|
addLegacyGeneral(behaviorContext->Method("get_axis_constraint", PyGetAxisConstraint, nullptr, "Gets axis."));
|
|
addLegacyGeneral(behaviorContext->Method("set_axis_constraint", PySetAxisConstraint, nullptr, "Sets axis."));
|
|
|
|
addLegacyGeneral(behaviorContext->Method("get_pak_from_file", [](const char* filename) -> AZStd::string { return PyGetPakFromFile(filename).Native(); }, nullptr, "Finds a pak file name for a given file."));
|
|
|
|
addLegacyGeneral(behaviorContext->Method("log", PyLog, nullptr, "Prints the message to the editor console window."));
|
|
|
|
addLegacyGeneral(behaviorContext->Method("undo", PyUndo, nullptr, "Undoes the last operation."));
|
|
addLegacyGeneral(behaviorContext->Method("redo", PyRedo, nullptr, "Redoes the last undone operation."));
|
|
|
|
addLegacyGeneral(behaviorContext->Method("draw_label", PyDrawLabel, nullptr, "Shows a 2d label on the screen at the given position and given color."));
|
|
addLegacyGeneral(behaviorContext->Method("combo_box", PyComboBox, nullptr, "Shows a combo box listing each value passed in, returns string value selected by the user."));
|
|
|
|
addLegacyGeneral(behaviorContext->Method("crash", PyCrash, nullptr, "Crashes the application, useful for testing crash reporting and other automation tools."));
|
|
|
|
/////////////////////////////////////////////////////////////////////////
|
|
// Temporal, to be removed by LY-101149
|
|
addLegacyGeneral(behaviorContext->Method("find_editor_entity", PyFindEditorEntity, nullptr, "Retrieves a editor entity id by name"));
|
|
addLegacyGeneral(behaviorContext->Method("find_game_entity", PyFindGameEntity, nullptr, "Retrieves a game entity id by name"));
|
|
//////////////////////////////////////////////////////////////////////////
|
|
addLegacyGeneral(behaviorContext->Method("dump_exposed_classes", PyDumpBindings::GetExposedPythonClasses, nullptr, "Retrieves exposed classes"));
|
|
}
|
|
}
|
|
}
|