aknlayoutcompiler/src/LayoutParse.cpp
changeset 0 f58d6ec98e88
child 1 b700e12870ca
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/aknlayoutcompiler/src/LayoutParse.cpp	Thu Dec 17 09:14:18 2009 +0200
@@ -0,0 +1,300 @@
+/*
+* Copyright (c) 2002 Nokia Corporation and/or its subsidiary(-ies).
+* All rights reserved.
+* This component and the accompanying materials are made available
+* under the terms of "Eclipse Public License v1.0"
+* which accompanies this distribution, and is available
+* at the URL "http://www.eclipse.org/legal/epl-v10.html".
+*
+* Initial Contributors:
+* Nokia Corporation - initial contribution.
+*
+* Contributors:
+*
+* Description: 
+*    
+*
+*/
+
+
+
+#include "LayoutParse.h"
+#include <sstream>
+#include <fstream>
+#include <algorithm>
+#include <iostream> // !!! for debug output only
+
+extern string whiteSpace;
+
+void SkipWhitespace(istream& aIn)
+	{
+	char ch;
+
+	while (!aIn.eof())
+		{
+		ch = aIn.get();
+		if (whiteSpace.find(ch) == string::npos)
+			{
+			aIn.putback(ch);
+			break;
+			}
+		}
+	}
+
+void TrimEnd(string& aString)
+	{
+	int len = aString.length();
+	while (whiteSpace.find(aString[len-1]) != string::npos)
+		len--;
+	aString = aString.substr(0, len);
+	}
+
+string NextToken(istream& aIn, const string& aTerminate)
+	{
+	SkipWhitespace(aIn);
+
+	string ret;
+	char ch;
+
+	while (!aIn.eof())
+		{
+		ch = aIn.get();
+		if (aTerminate.find(ch) != string::npos)
+			{
+			if (ret.length())
+				aIn.putback(ch);
+			else
+				ret += (ch);
+			break;
+			}
+		ret += ch;
+		}
+
+	TrimEnd(ret);
+
+	return ret;
+	}
+
+void FindAndSkip(istream& aIn, const string& aString)
+	{
+	string tok = NextToken(aIn, aString);
+	if (aString.find(tok) == string::npos)
+		throw LayParseErr(aIn, tok, "not found");
+	}
+
+
+TLayParseValues::TLayParseValues(TLayoutLine* aLine, string aName)
+: TValues(aLine, aName)
+	{
+	}
+
+void TLayParseValues::Parse(istream& aIn)
+	{
+	string tok = NextToken(aIn, ",{}");
+	if (tok == "," || tok == "}")
+		{
+		aIn.putback(tok[0]);
+		push_back("");
+		}
+	else if (tok == "{")
+		{
+		do	{
+			TLayParseValues v(iLine, iName);
+			v.Parse(aIn);
+			insert(end(), v.begin(), v.end());
+			tok = NextToken(aIn, ",}");
+			} while (tok != "}");
+
+		tok = NextToken(aIn, ",}[");
+		if (tok == "[")
+			{
+			tok = NextToken(aIn, "]");
+			if (tok != "]")
+				{
+				iParam = tok;
+				FindAndSkip(aIn, "]");
+				}
+			}
+		else if (tok == "," || tok == "}")
+			{
+			aIn.putback(tok[0]);
+			}
+		else
+			{
+			throw LayParseErr(aIn, tok, "expected '[' ',' or '}'");
+			}
+		}
+	else
+		{
+		push_back(tok);
+		}
+	}
+
+
+//
+//  TLayParseLayoutLine
+//
+
+TLayParseLayoutLine::TLayParseLayoutLine(TLayoutTable* aTable, int aId)
+: TLayoutLine(aTable, aId)
+	{
+	}
+
+void TLayParseLayoutLine::Parse(istream& aIn)
+	{
+	FindAndSkip(aIn, "{");
+
+	string tok;
+
+	for (vector<string>::iterator pCol = iTable->iColumnNames.begin();
+		 pCol != iTable->iColumnNames.end();
+		 ++pCol)
+		{
+		TLayParseValues values(this, *pCol);
+		values.Parse(aIn);
+		insert(make_pair(*pCol, values));
+		tok = NextToken(aIn, ",}");
+		}
+
+	if (tok != "}")
+		throw LayParseErr(aIn, tok, "expected }");
+	}
+
+
+
+// TLayParseLayoutTable
+
+
+TLayParseLayoutTable::TLayParseLayoutTable(TLayout* aTables)
+: TLayoutTable(aTables)
+	{
+	}
+
+void TLayParseLayoutTable::Parse(istream& aIn)
+	{
+	string tok = NextToken(aIn, ":{}");
+	if (string(":{}").find(tok) != string::npos)
+		throw LayParseErr(aIn, tok, "expected table name");
+	iName = tok;
+
+	tok = NextToken(aIn, ":{");
+	if (string(":{").find(tok) == string::npos)
+		throw LayParseErr(aIn, tok, "expected ':' or '{'");
+
+	if (tok == ":")
+		{
+		iParentName = NextToken(aIn, "{");
+		FindAndSkip(aIn, "{");
+		}
+
+	tok = NextToken(aIn, "{+");
+	if (string("{+").find(tok) == string::npos)
+		throw LayParseErr(aIn, tok, "expected '+' or '{'");
+	else if (tok == "+")
+		iAppend = true;
+	else
+		aIn.putback(tok[0]);
+
+	int id = 0;
+	do  {
+		TLayParseLayoutLine* line = new TLayParseLayoutLine(this, ++id);
+		push_back(line);
+		line->Parse(aIn);
+		tok = NextToken(aIn, ",}");
+		if (string(",}").find(tok) == string::npos)
+			throw LayParseErr(aIn, tok, "expected ',' or '}'");
+		} while (tok != "}");
+	}
+
+
+
+void TLayParseLayout::Parse(istream& aIn)
+	{
+	while (!aIn.eof())
+		{
+		string tok = NextToken(aIn, whiteSpace);
+		if (tok == "WindowTable" || tok == "TextTable")
+			{
+			TLayParseLayoutTable* tab = new TLayParseLayoutTable(this);
+			push_back(tab);
+			tab->iType = (tok == "WindowTable" ? TLayoutTable::EWindowTable : TLayoutTable::ETextTable);
+			tab->SetDefaultColumnNames();
+			tab->Parse(aIn);
+			}
+		else if (tok.length()==0 && aIn.eof())
+			{
+			// white space at end of file
+			break;
+			}
+		else
+			{
+			throw LayParseErr(aIn, tok, "expected a Table");
+			}
+		}
+	Compile();
+	}
+
+auto_ptr<TLayParseLayout> TLayParseLayout::Parse(const string& aLayName)
+	{
+	string layName = aLayName;
+
+	auto_ptr<TLayParseLayout> layout(new TLayParseLayout);
+	if (layName.size() >= 2 && layName.substr(0,2) == "-m")
+		{
+		layName = layName.substr(2);
+		layout->iCanBeMirror = true;
+		}
+	layout->iName = layName;
+
+	int pos=0;
+	bool first = true;
+	while (pos != string::npos)
+		{
+		int next = layName.find('+', pos);
+		string name;
+		if (next == string::npos)
+			{
+			name = layName.substr(pos);
+			pos = next;
+			}
+		else
+			{
+			name = layName.substr(pos, next-pos);
+			pos = layName.find_first_not_of('+', next);
+			}
+
+		ifstream in(name.c_str());
+		if (!in.is_open())
+			throw NotFoundErr(name);
+		cout << "reading layout " << name << endl;
+
+		if (first)
+			{
+			layout->Parse(in);
+			}
+		else
+			{
+			TLayParseLayout nextLay;
+			nextLay.Parse(in);
+			layout->Merge(TLayout::KMergeModeUnion, nextLay);
+			}
+
+		first = false;
+		in.close();
+		}
+	return layout;
+	}
+
+
+
+LayParseErr::LayParseErr(istream& aIn, const string& aTok, const string& aMsg)
+: iLoc(StreamLoc(aIn,"<<Near Here>>", 100, 100)), iTok(aTok), iMsg(aMsg) 
+	{
+	}
+
+void LayParseErr::Show(ostream& aOut) const
+	{
+	aOut << "ERROR : \"" << iTok << "\" " << iMsg << endl << iLoc << endl;
+	}
+
+// End of File