private OperationType HandleOpenBrace(ParseContext context, out ParseErrorType errorType) { TokenStream<RToken> tokens = context.Tokens; errorType = ParseErrorType.None; // Separate expression from function call. In case of // function call previous token is either closing indexer // brace or closing function brace. Identifier with brace // is handled up above. // Indentifier followed by a brace needs to be analyzed // so we can tell between previous expression that ended // with identifier and identifier that is a function name: // // a <- 2*b // (expression) // // in this case b is not a function name. Similarly, // // a <- 2*b[1] // (expression) // // is not a function call operator over b[1]. if (_operators.Count > 1 || _operands.Count > 0) { // We are not in the beginning of the expression if (tokens.PreviousToken.TokenType == RTokenType.CloseBrace || tokens.PreviousToken.TokenType == RTokenType.CloseSquareBracket || tokens.PreviousToken.TokenType == RTokenType.CloseDoubleSquareBracket || tokens.PreviousToken.IsVariableKind()) { FunctionCall functionCall = new FunctionCall(); functionCall.Parse(context, null); errorType = HandleFunctionOrIndexer(functionCall); return OperationType.Function; } } Group group = new Group(); group.Parse(context, null); _operands.Push(group); return OperationType.Operand; }
private static ISignatureInfo ParseSignature(string functionName, ParseContext context, IReadOnlyDictionary<string, string> argumentsDescriptions = null) { SignatureInfo info = new SignatureInfo(functionName); List<IArgumentInfo> signatureArguments = new List<IArgumentInfo>(); // RD data may contain function name(s) without braces if (context.Tokens.CurrentToken.TokenType == RTokenType.OpenBrace) { FunctionCall functionCall = new FunctionCall(); functionCall.Parse(context, context.AstRoot); for (int i = 0; i < functionCall.Arguments.Count; i++) { IAstNode arg = functionCall.Arguments[i]; string argName = null; string argDefaultValue = null; bool isEllipsis = false; bool isOptional = false; ExpressionArgument expArg = arg as ExpressionArgument; if (expArg != null) { argName = context.TextProvider.GetText(expArg.ArgumentValue); } else { NamedArgument nameArg = arg as NamedArgument; if (nameArg != null) { argName = context.TextProvider.GetText(nameArg.NameRange); argDefaultValue = RdText.CleanRawRdText(context.TextProvider.GetText(nameArg.DefaultValue)); } else { MissingArgument missingArg = arg as MissingArgument; if (missingArg != null) { argName = string.Empty; } else { EllipsisArgument ellipsisArg = arg as EllipsisArgument; if (ellipsisArg != null) { argName = "..."; isEllipsis = true; } } } } ArgumentInfo argInfo = new ArgumentInfo(argName); argInfo.DefaultValue = argDefaultValue; argInfo.IsEllipsis = isEllipsis; argInfo.IsOptional = isOptional; // TODO: actually parse if (argumentsDescriptions != null) { string description; if (argumentsDescriptions.TryGetValue(argName, out description)) { argInfo.Description = description; } } signatureArguments.Add(argInfo); } } info.Arguments = signatureArguments; return info; }