RigsofRods
Soft-body Physics Simulation
All Data Structures Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Modules Pages
GenericFileFormat.h
Go to the documentation of this file.
1 /*
2  This source file is part of Rigs of Rods
3  Copyright 2022 Petr Ohlidal
4 
5  For more information, see http://www.rigsofrods.org/
6 
7  Rigs of Rods is free software: you can redistribute it and/or modify
8  it under the terms of the GNU General Public License version 3, as
9  published by the Free Software Foundation.
10 
11  Rigs of Rods is distributed in the hope that it will be useful,
12  but WITHOUT ANY WARRANTY; without even the implied warranty of
13  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14  GNU General Public License for more details.
15 
16  You should have received a copy of the GNU General Public License
17  along with Rigs of Rods. If not, see <http://www.gnu.org/licenses/>.
18 */
19 
33 
34 #pragma once
35 
36 #include "RefCountingObject.h"
37 #include "RefCountingObjectPtr.h"
38 #include "BitFlags.h"
39 #include "Application.h"
40 
41 #include <vector>
42 #include <string>
43 
44 #include <Ogre.h>
45 
46 namespace RoR {
47 
48 enum class TokenType
49 {
50  NONE,
51  LINEBREAK, // Input: LF (CR is ignored); Output: platform-specific.
52  COMMENT, // Line starting with ; (skipping whitespace). Data: offset in string pool.
53  STRING, // Quoted string. Data: offset in string pool.
54  FLOAT,
55  INT,
56  BOOL, // Lowercase 'true'/'false'. Data: 1.0 for true, 0.0 for false.
57  KEYWORD, // Unquoted string at start of line (skipping whitespace). Data: offset in string pool.
58 };
59 
60 struct Token
61 {
63  float data;
64 };
65 
66 struct GenericDocument: public RefCountingObject<GenericDocument>
67 {
77 
78  virtual ~GenericDocument() {};
79 
80  std::vector<char> string_pool; // Data of COMMENT/KEYWORD/STRING tokens; NUL-terminated strings.
81  std::vector<Token> tokens;
82 
83  virtual void loadFromDataStream(Ogre::DataStreamPtr datastream, BitMask_t options = 0);
84  virtual void saveToDataStream(Ogre::DataStreamPtr datastream);
85 
86  virtual bool loadFromResource(std::string resource_name, std::string resource_group_name, BitMask_t options = 0);
87  virtual bool saveToResource(std::string resource_name, std::string resource_group_name);
88 };
89 
90 struct GenericDocContext: public RefCountingObject<GenericDocContext>
91 {
93  {
94  ROR_ASSERT(doc != nullptr);
95  if (doc == nullptr && AngelScript::asGetActiveContext() != nullptr)
96  {
97  AngelScript::asGetActiveContext()->SetException("Cannot create GenericDocContextClass from null GenericDocument!");
98  }
99  }
100  virtual ~GenericDocContext() {};
101 
103  uint32_t token_pos = 0;
104 
105  // PLEASE maintain the same order as in 'bindings/GenericFileFormatAngelscript.cpp' and 'doc/*/GenericDocContextClass.h'
106 
107  bool moveNext() { token_pos++; return endOfFile(); }
108  uint32_t getPos() const { return token_pos; }
109  bool seekNextLine();
110  int countLineArgs();
111  bool endOfFile(int offset = 0) const { return token_pos + offset >= doc->tokens.size(); }
112  TokenType tokenType(int offset = 0) const { return !endOfFile(offset) ? doc->tokens[token_pos + offset].type : TokenType::NONE; }
113 
114  std::string getTokString(int offset = 0) const { ROR_ASSERT(isTokString(offset)); return getStringData(offset); }
115  float getTokFloat(int offset = 0) const { ROR_ASSERT(isTokFloat(offset)); return getFloatData(offset); }
116  int getTokInt(int offset = 0) const { ROR_ASSERT(isTokInt(offset)); return (int)getFloatData(offset); }
117  float getTokNumeric(int offset = 0) const { ROR_ASSERT(isTokNumeric(offset)); return getFloatData(offset); }
118  bool getTokBool(int offset = 0) const { ROR_ASSERT(isTokBool(offset)); return getFloatData(offset) == 1.f; }
119  std::string getTokKeyword(int offset = 0) const { ROR_ASSERT(isTokKeyword(offset)); return getStringData(offset); }
120  std::string getTokComment(int offset = 0) const { ROR_ASSERT(isTokComment(offset)); return getStringData(offset); }
121 
122  bool isTokString(int offset = 0) const { return tokenType(offset) == TokenType::STRING; }
123  bool isTokFloat(int offset = 0) const { return tokenType(offset) == TokenType::FLOAT; }
124  bool isTokInt(int offset = 0) const { return tokenType(offset) == TokenType::INT; }
125  bool isTokBool(int offset = 0) const { return tokenType(offset) == TokenType::BOOL; }
126  bool isTokKeyword(int offset = 0) const { return tokenType(offset) == TokenType::KEYWORD; }
127  bool isTokComment(int offset = 0) const { return tokenType(offset) == TokenType::COMMENT; }
128  bool isTokLineBreak(int offset = 0) const { return tokenType(offset) == TokenType::LINEBREAK; }
129  bool isTokNumeric(int offset = 0) const { return isTokInt(offset) || isTokFloat(offset); }
130 
131  // Editing functions:
132 
133  void appendTokens(int count);
134  bool insertToken(int offset = 0);
135  bool eraseToken(int offset = 0);
136 
137  void appendTokString(const std::string& str) { appendTokens(1); setTokString(0, str); }
138  void appendTokFloat(float val) { appendTokens(1); setTokFloat(0, val); }
139  void appendTokInt(int val) { appendTokens(1); setTokInt(0, val); }
140  void appendTokBool(bool val) { appendTokens(1); setTokBool(0, val); }
141  void appendTokKeyword(const std::string& str) { appendTokens(1); setTokKeyword(0, str); }
142  void appendTokComment(const std::string& str) { appendTokens(1); setTokComment(0, str); }
144 
145  bool setTokString(int offset, const std::string& str) { return setStringData(offset, TokenType::STRING, str); }
146  bool setTokFloat(int offset, float val) { return setFloatData(offset, TokenType::FLOAT, val); }
147  bool setTokInt(int offset, int val) { return setFloatData(offset, TokenType::INT, val); }
148  bool setTokBool(int offset, bool val) { return setFloatData(offset, TokenType::BOOL, val); }
149  bool setTokKeyword(int offset, const std::string& str) { return setStringData(offset, TokenType::KEYWORD, str); }
150  bool setTokComment(int offset, const std::string& str) { return setStringData(offset, TokenType::COMMENT, str); }
151  bool setTokLineBreak(int offset) { return setFloatData(offset, TokenType::LINEBREAK, 0.f); }
152 
153  // Not exported to script:
154 
155  const char* getStringData(int offset = 0) const { return !endOfFile(offset) ? (doc->string_pool.data() + (uint32_t)doc->tokens[token_pos + offset].data) : ""; }
156  float getFloatData(int offset = 0) const { return !endOfFile(offset) ? doc->tokens[token_pos + offset].data : 0.f; }
157  bool setStringData(int offset, TokenType type, const std::string& data);
158  bool setFloatData(int offset, TokenType type, float data);
159 };
160 
161 } // namespace RoR
ROR_ASSERT
#define ROR_ASSERT(_EXPR)
Definition: Application.h:40
RoR::GenericDocContext::setFloatData
bool setFloatData(int offset, TokenType type, float data)
Definition: GenericFileFormat.cpp:1216
RoR::GenericDocContext::appendTokBool
void appendTokBool(bool val)
Definition: GenericFileFormat.h:140
RoR::GenericDocContext::isTokInt
bool isTokInt(int offset=0) const
Definition: GenericFileFormat.h:124
RoR::GenericDocContext::insertToken
bool insertToken(int offset=0)
Inserts TokenType::NONE;.
Definition: GenericFileFormat.cpp:1181
RoR::GenericDocContext::setTokKeyword
bool setTokKeyword(int offset, const std::string &str)
Definition: GenericFileFormat.h:149
RoR::GenericDocContext::appendTokComment
void appendTokComment(const std::string &str)
Definition: GenericFileFormat.h:142
RoR::GenericDocContext::getTokNumeric
float getTokNumeric(int offset=0) const
Definition: GenericFileFormat.h:117
RoR::GenericDocContext::isTokKeyword
bool isTokKeyword(int offset=0) const
Definition: GenericFileFormat.h:126
RoR::GenericDocContext::appendTokKeyword
void appendTokKeyword(const std::string &str)
Definition: GenericFileFormat.h:141
RoR::TokenType::INT
@ INT
RoR::GenericDocument::OPTION_ALLOW_SEPARATOR_COLON
static const BitMask_t OPTION_ALLOW_SEPARATOR_COLON
Allow ':' as separator between tokens.
Definition: GenericFileFormat.h:71
RoR::Token::data
float data
Definition: GenericFileFormat.h:63
RoR::GenericDocContext::getTokBool
bool getTokBool(int offset=0) const
Definition: GenericFileFormat.h:118
RoR::GenericDocument::OPTION_ALLOW_SLASH_COMMENTS
static const BitMask_t OPTION_ALLOW_SLASH_COMMENTS
Allow comments starting with //.
Definition: GenericFileFormat.h:69
RoR::GenericDocContext::isTokLineBreak
bool isTokLineBreak(int offset=0) const
Definition: GenericFileFormat.h:128
RoR::GenericDocContext::appendTokInt
void appendTokInt(int val)
Definition: GenericFileFormat.h:139
RoR::GenericDocContext::getTokString
std::string getTokString(int offset=0) const
Definition: GenericFileFormat.h:114
RoR::GenericDocContext::setTokComment
bool setTokComment(int offset, const std::string &str)
Definition: GenericFileFormat.h:150
RoR::GenericDocContext::tokenType
TokenType tokenType(int offset=0) const
Definition: GenericFileFormat.h:112
RoR::GenericDocContext::isTokFloat
bool isTokFloat(int offset=0) const
Definition: GenericFileFormat.h:123
RoR::GenericDocContext::seekNextLine
bool seekNextLine()
Definition: GenericFileFormat.cpp:1140
RoR::GenericDocument::loadFromResource
virtual bool loadFromResource(std::string resource_name, std::string resource_group_name, BitMask_t options=0)
Definition: GenericFileFormat.cpp:1108
RoR::GenericDocContext::setTokString
bool setTokString(int offset, const std::string &str)
Definition: GenericFileFormat.h:145
RoR::GenericDocContext::getTokFloat
float getTokFloat(int offset=0) const
Definition: GenericFileFormat.h:115
BITMASK
#define BITMASK(OFFSET)
Definition: BitFlags.h:10
RefCountingObjectPtr< GenericDocument >
RoR::GenericDocument::saveToResource
virtual bool saveToResource(std::string resource_name, std::string resource_group_name)
Definition: GenericFileFormat.cpp:1124
RoR::GenericDocument::saveToDataStream
virtual void saveToDataStream(Ogre::DataStreamPtr datastream)
Definition: GenericFileFormat.cpp:1049
RoR::GenericDocContext::isTokString
bool isTokString(int offset=0) const
Definition: GenericFileFormat.h:122
RoR::GenericDocContext::setTokInt
bool setTokInt(int offset, int val)
Definition: GenericFileFormat.h:147
RoR::GenericDocContext::countLineArgs
int countLineArgs()
Definition: GenericFileFormat.cpp:1158
RoR::TokenType::KEYWORD
@ KEYWORD
RoR::Token::type
TokenType type
Definition: GenericFileFormat.h:62
BitFlags.h
Bit operations.
RoR::GenericDocContext::appendTokString
void appendTokString(const std::string &str)
Definition: GenericFileFormat.h:137
RoR::TokenType::COMMENT
@ COMMENT
RoR::GenericDocContext::isTokNumeric
bool isTokNumeric(int offset=0) const
Definition: GenericFileFormat.h:129
RoR::GenericDocContext::getTokComment
std::string getTokComment(int offset=0) const
Definition: GenericFileFormat.h:120
RoR::GenericDocContext::appendTokens
void appendTokens(int count)
Appends a series of TokenType::NONE and sets Pos at the first one added; use setTok* functions to fil...
Definition: GenericFileFormat.cpp:1169
RoR::GenericDocument::tokens
std::vector< Token > tokens
Definition: GenericFileFormat.h:81
RoR::GenericDocContext::doc
GenericDocumentPtr doc
Definition: GenericFileFormat.h:100
RefCountingObject.h
RoR::GenericDocContext::moveNext
bool moveNext()
Definition: GenericFileFormat.h:107
RoR::GenericDocument::OPTION_ALLOW_BRACED_KEYWORDS
static const BitMask_t OPTION_ALLOW_BRACED_KEYWORDS
Allow INI-like '[keyword]' tokens.
Definition: GenericFileFormat.h:73
Application.h
Central state/object manager and communications hub.
RoR::Token
Definition: GenericFileFormat.h:60
RoR::GenericDocument::OPTION_FIRST_LINE_IS_TITLE
static const BitMask_t OPTION_FIRST_LINE_IS_TITLE
First non-empty & non-comment line is a naked string with spaces.
Definition: GenericFileFormat.h:70
RoR::GenericDocument::string_pool
std::vector< char > string_pool
Definition: GenericFileFormat.h:78
RoR::TokenType::NONE
@ NONE
RoR::GenericDocContext::setStringData
bool setStringData(int offset, TokenType type, const std::string &data)
Definition: GenericFileFormat.cpp:1202
RoR::GenericDocument::OPTION_ALLOW_SEPARATOR_EQUALS
static const BitMask_t OPTION_ALLOW_SEPARATOR_EQUALS
Allow '=' as separator between tokens.
Definition: GenericFileFormat.h:74
RoR::GenericDocContext::getStringData
const char * getStringData(int offset=0) const
Definition: GenericFileFormat.h:155
RoR::GenericDocContext::endOfFile
bool endOfFile(int offset=0) const
Definition: GenericFileFormat.h:111
RoR::GenericDocContext::isTokBool
bool isTokBool(int offset=0) const
Definition: GenericFileFormat.h:125
RoR::GenericDocContext::getFloatData
float getFloatData(int offset=0) const
Definition: GenericFileFormat.h:156
RoR::GenericDocument::OPTION_NAKEDSTR_USCORES_TO_SPACES
static const BitMask_t OPTION_NAKEDSTR_USCORES_TO_SPACES
Only for OPTION_ALLOW_NAKED_STRINGS: Replace underscores with spaces in naked strings (classic behavi...
Definition: GenericFileFormat.h:76
RoR::GenericDocContext::eraseToken
bool eraseToken(int offset=0)
Definition: GenericFileFormat.cpp:1190
RoR::TokenType
TokenType
Definition: GenericFileFormat.h:48
RoR::GenericDocument
Definition: GenericFileFormat.h:66
RefCountingObjectPtr.h
RoR::TokenType::STRING
@ STRING
RoR::GenericDocContext::getTokKeyword
std::string getTokKeyword(int offset=0) const
Definition: GenericFileFormat.h:119
BitMask_t
uint32_t BitMask_t
Definition: BitFlags.h:7
RoR::GenericDocContext
Definition: GenericFileFormat.h:90
RoR::GenericDocContext::GenericDocContext
GenericDocContext(GenericDocumentPtr d)
Definition: GenericFileFormat.h:92
RoR::GenericDocument::~GenericDocument
virtual ~GenericDocument()
Definition: GenericFileFormat.h:78
RoR::GenericDocument::loadFromDataStream
virtual void loadFromDataStream(Ogre::DataStreamPtr datastream, BitMask_t options=0)
Definition: GenericFileFormat.cpp:1018
RoR::GenericDocContext::setTokBool
bool setTokBool(int offset, bool val)
Definition: GenericFileFormat.h:148
RoR::GenericDocContext::~GenericDocContext
virtual ~GenericDocContext()
Definition: GenericFileFormat.h:100
RefCountingObject
Self reference-counting objects, as requred by AngelScript garbage collector.
Definition: RefCountingObject.h:26
RoR::GenericDocContext::setTokFloat
bool setTokFloat(int offset, float val)
Definition: GenericFileFormat.h:146
RoR::GenericDocContext::isTokComment
bool isTokComment(int offset=0) const
Definition: GenericFileFormat.h:127
RoR::GenericDocContext::token_pos
uint32_t token_pos
Definition: GenericFileFormat.h:103
RoR::TokenType::LINEBREAK
@ LINEBREAK
RoR::GenericDocContext::appendTokFloat
void appendTokFloat(float val)
Definition: GenericFileFormat.h:138
RoR::GenericDocument::OPTION_ALLOW_NAKED_STRINGS
static const BitMask_t OPTION_ALLOW_NAKED_STRINGS
Allow strings without quotes, for backwards compatibility.
Definition: GenericFileFormat.h:68
RoR
Definition: AppContext.h:36
RoR::GenericDocument::OPTION_ALLOW_HASH_COMMENTS
static const BitMask_t OPTION_ALLOW_HASH_COMMENTS
Allow comments starting with #.
Definition: GenericFileFormat.h:75
RoR::TokenType::FLOAT
@ FLOAT
RoR::GenericDocument::OPTION_PARENTHESES_CAPTURE_SPACES
static const BitMask_t OPTION_PARENTHESES_CAPTURE_SPACES
If non-empty NAKED string encounters '(', following spaces will be captured until matching ')' is fou...
Definition: GenericFileFormat.h:72
RoR::GenericDocContext::getPos
uint32_t getPos() const
Definition: GenericFileFormat.h:108
RoR::GenericDocContext::appendTokLineBreak
void appendTokLineBreak()
Definition: GenericFileFormat.h:143
RoR::GenericDocContext::setTokLineBreak
bool setTokLineBreak(int offset)
Definition: GenericFileFormat.h:151
RoR::GenericDocContext::getTokInt
int getTokInt(int offset=0) const
Definition: GenericFileFormat.h:116
RoR::TokenType::BOOL
@ BOOL