public bool IsAutoCompletionAllowedHere(TextLocation location)
        {
            var app = ProbeNppPlugin.Instance;
            var currentLine = app.CurrentLine;
            var lineText = app.GetLineText(currentLine);
            var state = currentLine > 1 ? app.GetLineState(currentLine - 1) : 0;

            var startPos = 0;
            if ((state & ProbeLexer.State_InsideComment) != 0)
            {
                var index = lineText.IndexOf("*/");
                if (index < 0) return false;
                startPos = index + 2;
            }

            if (startPos + 1 > location.CharPosition) return false;

            var parser = new TokenParser.Parser(app.GetLineText(currentLine));
            parser.ReturnComments = true;
            parser.ReturnWhiteSpace = true;
            if (startPos > 0) parser.SetOffset(startPos);

            while (parser.Read())
            {
                if (parser.Position.LinePos > location.CharPosition || parser.EndOfFile)
                {
                    if (parser.TokenType == TokenParser.TokenType.Comment || parser.TokenType == TokenParser.TokenType.StringLiteral)
                    {
                        return false;
                    }
                    return true;
                }
            }

            if (parser.TokenType == TokenParser.TokenType.Comment || parser.TokenType == TokenParser.TokenType.StringLiteral)
            {
                return false;
            }
            return true;
        }
        private ParseState ParseFunctionSigFromSource()
        {
            var startPos = _source.Length;
            var parser = new TokenParser.Parser(_source.ToString());
            var retVal = ParseState.NotEnoughSource;

            // Find the last token before startPos.
            while (startPos > 0)
            {
                var newStartPos = 0;
                parser.ResetPosition();
                while (parser.Position.Offset < startPos)
                {
                    newStartPos = parser.Position.Offset;
                    if (!parser.Read()) break;
                }

                startPos = newStartPos;
                if ((retVal = ParseFunctionSigFromSource(startPos)) == ParseState.Found) return retVal;
            }

            return retVal;
        }
		private bool IndentNextLine(string lineText)
		{
			var parser = new TokenParser.Parser(lineText);
			var first = true;
			var startsWithCase = false;
			TokenParser.TokenType type = TokenParser.TokenType.Unknown;
			string text = "";

			while (parser.Read())
			{
				type = parser.TokenType;
				text = parser.TokenText;

				if (first && type == TokenParser.TokenType.Word && text == "case") startsWithCase = true;
				if (first) first = false;
			}

			if (type == TokenParser.TokenType.Operator && text == "{") return true;
			if (startsWithCase && type == TokenParser.TokenType.Operator && text == ":") return true;
			return false;
		}
		private bool TryFindOpeningBrace(TextLocation closeBraceLoc, out TextLocation openBraceLoc)
		{
			var app = ProbeNppPlugin.Instance;
			var source = app.GetText(app.Start, app.CurrentLocation);
			var sourceLength = source.Length;
			var found = false;
			var openLoc = closeBraceLoc;

			var parser = new TokenParser.Parser(source);
			while (parser.ReadNestable())
			{
				if (parser.TokenType == TokenParser.TokenType.Nested &&
					parser.TokenText.EndsWith("}") &&
					parser.Position.Offset == sourceLength)
				{
					openLoc = parser.TokenStartPostion.ToNppSharpTextLocation();
					found = true;
				}
			}

			if (found)
			{
				openBraceLoc = openLoc;
				return true;
			}
			else
			{
				openBraceLoc = closeBraceLoc;
				return false;
			}
		}
        private ParseState ParseFunctionSigFromSource(int startPos)
        {
            var parser = new TokenParser.Parser(_source.ToString().Substring(startPos));
            var lastTokenText = "";
            TokenParser.TokenType lastTokenType = TokenParser.TokenType.Unknown;

            _funcName = "";
            _commaCount = 0;

            while (parser.Read())
            {
                if (parser.TokenText == "(")
                {
                    if (!ParseNestable(parser, ")", true))
                    {
                        if (lastTokenType == TokenParser.TokenType.Word)
                        {
                            _funcName = lastTokenText;
                            return ParseState.Found;
                        }
                        return ParseState.BadSyntax;
                    }
                }
                else if (parser.TokenText == ";")
                {
                    return ParseState.BadSyntax;
                }
                else if (parser.TokenText == ",")
                {
                    _commaCount++;
                }

                lastTokenText = parser.TokenText;
                lastTokenType = parser.TokenType;
            }

            return ParseState.NotEnoughSource;
        }
        private bool GetFunctionSignatureHighlightRange(string sig, int argToHighlight, out int startIndex, out int length)
        {
            // Get the last set of closed brackets
            var parser = new TokenParser.Parser(sig);
            int argsStart = -1;
            int argsStartUnclosed = -1;
            int argsEnd = -1;
            while (parser.ReadNestable())
            {
                if (parser.TokenType == TokenParser.TokenType.Nested && parser.TokenText.StartsWith("("))
                {
                    argsStart = parser.TokenStartPostion.Offset + 1;
                    argsEnd = parser.Position.Offset - 1;
                }
                else if (parser.TokenType == TokenParser.TokenType.Operator && parser.TokenText == "(")
                {
                    argsStartUnclosed = parser.TokenStartPostion.Offset;
                }
            }

            if (argsStart == -1)
            {
                argsStart = argsStartUnclosed;
                argsEnd = sig.Length;
            }
            if (argsStart == -1)
            {
                startIndex = length = 0;
                return false;
            }

            // Parse the argument text to get the parameters
            var args = parser.GetText(argsStart, argsEnd - argsStart);
            parser.SetSource(args);

            int argCount = 0;
            int argStart = 0;
            while (parser.ReadNestable())
            {
                if (parser.TokenType == TokenParser.TokenType.Operator && parser.TokenText == ",")
                {
                    if (argCount == argToHighlight)
                    {
                        startIndex = argStart + argsStart;
                        length = parser.TokenStartPostion.Offset - argStart;
                        return true;
                    }
                    else
                    {
                        argCount++;
                        argStart = parser.Position.Offset;
                    }
                }
            }

            startIndex = argStart + argsStart;
            length = parser.Position.Offset - argStart;
            return true;
        }