Files
GDevelop/Core/GDCore/Events/Instruction.h

201 lines
6.4 KiB
C++

/*
* GDevelop Core
* Copyright 2008-2016 Florian Rival (Florian.Rival@gmail.com). All rights
* reserved. This project is released under the MIT License.
*/
#ifndef INSTRUCTION_H
#define INSTRUCTION_H
#include <memory>
#include <vector>
#include "GDCore/Events/Expression.h"
#include "GDCore/Events/InstructionsList.h"
#include "GDCore/String.h"
namespace gd {
/**
* \brief An instruction is a member of an event: It can be a condition or an
* action.
*
* An instruction has a type, which define what it does, and some parameters. It
* can also be set as inverted (when the instruction is a condition) and it
* can have sub instructions. This class does nothing particular except storing
* these data.
*
* \see gd::BaseEvent
*
* \ingroup Events
*/
class GD_CORE_API Instruction {
public:
/**
* \brief Default constructor
* \param type The type of the instruction
*/
Instruction(gd::String type_ = "");
/**
* \brief Constructor
* \param type The type of the instruction
* \param parameters A vector containing the parameters of the instruction
* \param inverted true to set the instruction as inverted (used for condition
* instructions).
*/
Instruction(gd::String type_,
const std::vector<gd::Expression>& parameters_,
bool inverted = false);
virtual ~Instruction(){};
/**
* \brief Return the type of the instruction.
* \return The type of the instruction
*/
const gd::String& GetType() const { return type; }
/**
* \brief Change the instruction type
* \param val The new type of the instruction
*/
void SetType(const gd::String& newType) { type = newType; }
/**
* \brief Return true if the condition is inverted
* \return true if the condition is inverted
*/
bool IsInverted() const { return inverted; }
/**
* \brief Set if the instruction is inverted or not.
* \param inverted true if the condition must be set as inverted
*/
void SetInverted(bool inverted_) { inverted = inverted_; }
/**
* \brief Return true if the async instruction should be awaited.
* This is not relevant if the instruction is not optionally asynchronous.
*
* \return true if the instruction is to be awaited
*/
bool IsAwaited() const { return awaitAsync; }
/**
* \brief Set if the async instruction is to be awaited or not.
* This is not relevant if the instruction is not optionally asynchronous.
*
* \param inverted true if the instruction must be awaited
*/
void SetAwaited(bool awaited) { awaitAsync = awaited; }
/**
* \brief Return the number of parameters of the instruction.
*/
std::size_t GetParametersCount() const { return parameters.size(); }
/**
* \brief Change the number of parameter of the instruction.
*
* If the new size if larger than the previous, new blank parameters are
* added.
*/
void SetParametersCount(std::size_t size);
/**
* \brief Get the value of a parameter.
*
* Return an empty expression if the parameter requested does not exists.
* \return The current value of the parameter.
*/
const gd::Expression& GetParameter(std::size_t index) const;
/**
* \brief Get the value of a parameter.
*
* Return an empty expression if the parameter requested does not exists.
* \return The current value of the parameter.
*/
gd::Expression& GetParameter(std::size_t index);
/** Change the specified parameter
* \param nb The parameter number
* \param val The new value of the parameter
*/
void SetParameter(std::size_t nb, const gd::Expression& val);
/** Add a parameter at the end
* \param val The new value of the parameter
*/
void AddParameter(const gd::Expression& val);
/** \brief Get a reference to the std::vector containing the parameters.
* \return A std::vector containing the parameters
*/
inline const std::vector<gd::Expression>& GetParameters() const {
return parameters;
}
/** \brief Replace all the parameters by new ones.
* \param val A vector containing the new parameters.
*/
inline void SetParameters(const std::vector<gd::Expression>& val) {
parameters = val;
}
/**
* \brief Return a reference to the vector containing sub instructions
*/
inline const gd::InstructionsList& GetSubInstructions() const {
return subInstructions;
};
/**
* \brief Return a reference to the vector containing sub instructions
*/
inline gd::InstructionsList& GetSubInstructions() { return subInstructions; };
/**
* \brief Return the original instruction this instruction was copied from.
*
* Useful to get reference to the original instruction in memory during code
* generation, to ensure stable unique identifiers.
*/
std::weak_ptr<Instruction> GetOriginalInstruction() {
return originalInstruction;
};
friend std::shared_ptr<Instruction> CloneRememberingOriginalElement(
std::shared_ptr<Instruction> instruction);
private:
gd::String type; ///< Instruction type
bool inverted; ///< True if the instruction if inverted. Only applicable for
///< instruction used as conditions by events
bool awaitAsync =
false; ///< Tells the code generator whether the optionally asynchronous
///< instruction should be generated as asynchronous (awaited) or not.
mutable std::vector<gd::Expression>
parameters; ///< Vector containing the parameters
gd::InstructionsList subInstructions; ///< Sub instructions, if applicable.
std::weak_ptr<Instruction>
originalInstruction; ///< Pointer used to remember which gd::Instruction
///< this instruction was copied from. Useful to
///< ensure the stability of code generation (as
///< some part of code generation uses the pointer
///< to the instruction as a unique identifier).
static gd::Expression badExpression;
};
/**
* Clone the given instruction, returning an instruction for which
* `GetOriginalInstruction()` returns the originally copied instruction.
*/
std::shared_ptr<Instruction> GD_CORE_API
CloneRememberingOriginalElement(std::shared_ptr<Instruction> instruction);
} // namespace gd
#endif // INSTRUCTION_H