- more work on scripting scripting

Mon, 26 Jan 2015 12:46:58 +0200

author
Teemu Piippo <crimsondusk64@gmail.com>
date
Mon, 26 Jan 2015 12:46:58 +0200
branch
scripting
changeset 922
81887a77baa0
parent 921
e2e9f594de66
child 923
e15a577a0bfe

- more work on scripting

CMakeLists.txt file | annotate | diff | comparison | revisions
src/main.cc file | annotate | diff | comparison | revisions
src/script/parser.cpp file | annotate | diff | comparison | revisions
src/script/parser.h file | annotate | diff | comparison | revisions
--- a/CMakeLists.txt	Mon Jan 26 01:16:56 2015 +0200
+++ b/CMakeLists.txt	Mon Jan 26 12:46:58 2015 +0200
@@ -71,6 +71,7 @@
 	src/editmodes/magicWandMode.cc
 	src/editmodes/rectangleMode.cc
 	src/editmodes/selectMode.cc
+	src/script/parser.cpp
 )
 
 set (LDFORGE_HEADERS
--- a/src/main.cc	Mon Jan 26 01:16:56 2015 +0200
+++ b/src/main.cc	Mon Jan 26 12:46:58 2015 +0200
@@ -33,6 +33,7 @@
 #include "configDialog.h"
 #include "dialogs.h"
 #include "crashCatcher.h"
+#include "script/parser.h"
 
 MainWindow* g_win = null;
 static QString g_versionString, g_fullVersionString;
@@ -47,6 +48,13 @@
 //
 int main (int argc, char* argv[])
 {
+	QFile fp ("script.txt", QIODevice::ReadOnly);
+	Script::Parser parser (QString::fromLocal8Bit (fp.readAll()));
+	parser.parse();
+	QFile fp2 ("script.out.txt", QIODevice::WriteOnly);
+	fp2.write (parser.preprocessedScript(), parser.preprocessedScript().length());
+	return 0;
+
 	QApplication app (argc, argv);
 	app.setOrganizationName (APPNAME);
 	app.setApplicationName (APPNAME);
--- a/src/script/parser.cpp	Mon Jan 26 01:16:56 2015 +0200
+++ b/src/script/parser.cpp	Mon Jan 26 12:46:58 2015 +0200
@@ -1,16 +1,132 @@
 #include "parser.h"
 
+static const char* TokenNames[] =
+{
+	"==",
+	"<=",
+	">=",
+	"&&",
+	"||",
+	"$",
+	":",
+	";",
+	".",
+	",",
+	"=",
+	"<",
+	">",
+	"?",
+	"{",
+	"}",
+	"[",
+	"]",
+	"(",
+	")",
+	"-",
+	"+",
+	"*",
+	"/",
+	"\\",
+	"&",
+	"^",
+	"|",
+	"!",
+	"@",
+	"#",
+	"~",
+	"`",
+	"%",
+	"<string>",
+	"<symbol>",
+	"<number>",
+	"<any>",
+};
+
 Script::Parser::Parser(QString text) :
-	m_data (text) {}
+	m_script(text) {}
 
 void Script::Parser::parse()
 {
+	bool inString = false;
+	bool inComment = false;
+	bool inBackslash = false;
+	int ln = 1;
+	int pos = 0;
+
+	// Preprocess
+	for (QChar qch : text)
+	{
+		char ch = qch.toAscii();
+
+		if (not inComment && not inString && ch == '\0')
+			scriptError ("bad character %s in script text on line %d", qch, ln);
+
+		if (ch == '\\')
+		{
+			inBackslash = true;
+			continue;
+		}
+
+		if (inBackslash)
+		{
+			if (inString)
+			{
+				switch (ch)
+				{
+				case 'n': data << '\n'; break;
+				case 't': data << '\t'; break;
+				case 'b': data << '\b'; break;
+				case '\\': data << '\\'; break;
+				default: scriptError ("misplaced backslash on line %d", ln);
+				}
+
+				++pos;
+				inBackslash == false;
+				continue;
+			}
+			else if (ch != '\n')
+			{
+				scriptError ("misplaced backslash on line %d", ln);
+			}
+		}
+
+		if (ch == '\n')
+		{
+			if (inString)
+				scriptError ("unterminated string on line %d", ln);
+
+			if (not inBackslash)
+			{
+				m_data << ';';
+				++pos;
+				inComment = false;
+				m_lineEndings << pos;
+				++ln;
+			}
+			else
+			{
+				inBackslash = false;
+			}
+			continue;
+		}
+
+		if (ch == '#' && not inString)
+		{
+			inComment = true;
+			continue;
+		}
+
+		m_data << ch;
+		++pos;
+	}
+
 	m_position.reset();
 }
 
 bool Script::Parser::next(TokenType desiredType)
 {
 	SavedPosition oldpos = position();
+	return false;
 }
 
 void Script::Parser::mustGetNext(TokenType desiredType)
@@ -20,10 +136,9 @@
 
 bool Script::Parser::peekNext(Token& tok)
 {
-
+	return false;
 }
 
-
 const Script::SavedPosition& Script::Parser::position() const
 {
 	return m_position;
--- a/src/script/parser.h	Mon Jan 26 01:16:56 2015 +0200
+++ b/src/script/parser.h	Mon Jan 26 12:46:58 2015 +0200
@@ -1,23 +1,54 @@
 #pragma once
-#include <QString>
+#include "../main.h"
 #include "ast.h"
 
 namespace Script
 {
 	enum TokenType
 	{
-		TOK_Dollar,
-		TOK_Semicolon,
-		TOK_BraceLeft,
-		TOK_BraceRight,
-		TOK_BracketLeft,
-		TOK_BracketRight,
-		TOK_ParenLeft,
-		TOK_ParenRight,
-		TOK_String,
-		TOK_Symbol,
-		TOK_Number,
-		TOK_Any
+		TOK_DoubleEquals,		// ==
+		TOK_AngleLeftEquals,	// <=
+		TOK_AngleRightEquals,	// >=
+		TOK_DoubleAmperstand,	// &&
+		TOK_DoubleBar,			// ||
+		TOK_Dollar,				// $
+		TOK_Colon,				// :
+		TOK_Semicolon,			// ;
+		TOK_Dot,				// .
+		TOK_Comma,				// ,
+		TOK_Equals,				// =
+		TOK_AngleLeft,			// <
+		TOK_AngleRight,			// >
+		TOK_QuestionMark,		// ?
+		TOK_BraceLeft,			// {
+		TOK_BraceRight,			// }
+		TOK_BracketLeft,		// [
+		TOK_BracketRight,		// ]
+		TOK_ParenLeft,			// (
+		TOK_ParenRight,			// )
+		TOK_Minus,				// -
+		TOK_Plus,				// +
+		TOK_Asterisk,			// *
+		TOK_Slash,				// /
+		TOK_Backslash,			// \.
+		TOK_Amperstand,			// &
+		TOK_Caret,				// ^
+		TOK_Bar,				// |
+		TOK_Exclamation,		// !
+		TOK_At,					// @
+		TOK_Pound,				// #
+		TOK_Tilde,				// ~
+		TOK_GraveAccent,		// `
+		TOK_Percent,			// %
+		TOK_String,				// "foo"
+		TOK_Symbol,				// bar
+		TOK_Number,				// 42
+		TOK_Any					// for next() and friends, a token never has this
+	};
+
+	enum
+	{
+		LastNamedToken = TOK_Percent
 	};
 
 	enum Type
@@ -84,9 +115,12 @@
 		bool peekNext(Token& tok);
 		const SavedPosition& position() const;
 		void setPosition(const SavedPosition& pos);
+		QString preprocessedScript() const { return QString::fromAscii (m_data); }
 
 	private:
-		QString m_data;
+		QString m_script;
+		QByteArray m_data;
+		QVector<int> m_lineEndings;
 		SavedPosition m_position;
 		Token m_token;
 		AstNode* m_astRoot;

mercurial