private bool TryProcessAttributesForHeading(BlockProcessor processor, ref StringSlice line, IBlock block) { // Try to find if there is any attributes { in the info string on the first line of a FencedCodeBlock if (line.Start < line.End) { int indexOfAttributes = line.IndexOf('{'); if (indexOfAttributes >= 0) { // Work on a copy var copy = line; copy.Start = indexOfAttributes; var startOfAttributes = copy.Start; if (GenericAttributesParser.TryParse(ref copy, out HtmlAttributes? attributes)) { var htmlAttributes = block.GetAttributes(); attributes.CopyTo(htmlAttributes); // Update position for HtmlAttributes htmlAttributes.Line = processor.LineIndex; htmlAttributes.Column = startOfAttributes - processor.CurrentLineStartPosition; // This is not accurate with tabs! htmlAttributes.Span.Start = startOfAttributes; htmlAttributes.Span.End = copy.Start - 1; line.End = indexOfAttributes - 1; return(true); } } } return(false); }
static internal bool TryFindOperator <T>(StringSlice inSlice, char inSearch, T inOperator, ref int ioFoundIndex, ref T ioFoundOperator, ref int ioFoundOperatorLength) where T : struct, IConvertible { if (ioFoundIndex >= 0) { return(false); } int index = inSlice.IndexOf(inSearch); if (index >= 0) { if (CharRequiresWhitespace(inSearch)) { if (!HasWhitespaceAt(inSlice, index - 1)) { return(false); } if (!HasWhitespaceAt(inSlice, index + 1)) { return(false); } } ioFoundOperator = inOperator; ioFoundIndex = index; ioFoundOperatorLength = 1; return(true); } return(false); }
static private void SetReflectedObject(UnityEngine.Object inRoot, string inPath, object inValue) { inPath = inPath.Replace("Array.data", ""); // locate the parent object StringSlice path = inPath; int lastDot = path.LastIndexOf('.'); if (lastDot < 0) { return; } StringSlice parentPath = path.Substring(0, lastDot); StringSlice fieldName = path.Substring(lastDot + 1); object parentObject = LocateReflectedObject(inRoot, parentPath.ToString()); if (parentObject == null) { return; } Type objType = parentObject.GetType(); int arrayIdx = -1; // capture array if (fieldName.EndsWith(']')) { int elementIndexStart = fieldName.IndexOf('['); int length = fieldName.Length - elementIndexStart - 1; StringSlice elementIndexSlice = fieldName.Substring(elementIndexStart + 1, length); arrayIdx = Convert.ToInt32(elementIndexSlice.ToString()); fieldName = fieldName.Substring(0, elementIndexStart); } FieldInfo field = objType.GetField(fieldName.ToString(), InstanceBindingFlags); if (field == null) { return; } if (arrayIdx >= 0) { IList list = field.GetValue(parentObject) as IList; if (list != null) { list[arrayIdx] = inValue; } return; } field.SetValue(parentObject, inValue); }
/// <summary> /// Attempts to parse a StringSlice into a Variant Key. /// Valid formats are: /// <list type="bullet"> /// <item>variableId</item> /// <item>tableId:variableId</item> /// </list> /// </summary> static public bool TryParse(StringSlice inSource, out TableKeyPair outKey) { if (inSource.IsEmpty) { outKey = default(TableKeyPair); return(false); } inSource = inSource.Trim(); int operatorIdx = inSource.IndexOf(TableOperator); if (operatorIdx >= 0) { int variantIdx = operatorIdx + TableOperator.Length; if (variantIdx >= inSource.Length) { outKey = default(TableKeyPair); return(false); } StringSlice tableId = inSource.Substring(0, operatorIdx).TrimEnd(); StringSlice variantId = inSource.Substring(variantIdx).TrimStart(); if (!VariantUtils.IsValidIdentifier(tableId) || !VariantUtils.IsValidIdentifier(variantId)) { outKey = default(TableKeyPair); return(false); } outKey = new TableKeyPair(tableId, variantId); return(true); } if (!VariantUtils.IsValidIdentifier(inSource)) { outKey = default(TableKeyPair); return(false); } outKey = new TableKeyPair(inSource); return(true); }
static private string GetLocationFromTrace(string inTrace) { foreach (var line in StringSlice.EnumeratedSplit(inTrace, StringUtils.DefaultNewLineChars, StringSplitOptions.RemoveEmptyEntries)) { int atIndex = line.IndexOf(" (at "); if (atIndex > 0) { StringSlice method = line.Substring(0, atIndex).Trim(); StringSlice location = line.Substring(atIndex + 5); location = location.Substring(0, location.Length - 1).Trim(); // ignore locations with < or >, these are internal and not helpfuls if (location.Contains('<') || location.Contains('>')) { continue; } int param = method.IndexOf('('); if (param > 0) { method = method.Substring(0, param).Trim(); } int lineNum = 0; int colon = location.IndexOf(':'); if (colon > 0) { StringSlice lineNumStr = location.Substring(colon + 1); lineNum = StringParser.ParseInt(lineNumStr); location = location.Substring(0, colon).Trim(); } int lastSlash = location.LastIndexOf('/'); if (lastSlash >= 0) { location = location.Substring(lastSlash + 1); } return(string.Format("{0} @{1}:{2}", method, lastSlash, lineNum)); } } return(StackTraceDisabledMessage); }
static private LineResult ParseLine(ref ParseState ioState, StringSlice ioLine) { StringSlice lineContents = ioLine.TrimStart(BlockParser.TrimCharsWithSpace).TrimEnd(BlockParser.TrimCharsWithoutSpace); StringSlice lineComment = StringSlice.Empty; if (lineContents.IsEmpty) { if (ioState.CurrentState != BlockState.InData) { return(LineResult.Empty); } } int commentIdx = lineContents.IndexOf(ioState.Rules.CommentPrefix); if (commentIdx >= 0) { lineComment = lineContents.Substring(commentIdx + ioState.Rules.CommentPrefix.Length).TrimStart(BlockParser.TrimCharsWithSpace); lineContents = lineContents.Substring(0, commentIdx).TrimEnd(BlockParser.TrimCharsWithSpace); } try { bool bSuccess = true; bool bProcessedCommand = false; if (!lineContents.IsEmpty) { for (int i = 0; i < ioState.PrefixPriorities.Length && !bProcessedCommand; ++i) { PrefixType type = ioState.PrefixPriorities[i]; switch (type) { case PrefixType.BlockId: { if (lineContents.StartsWith(ioState.Rules.BlockIdPrefix)) { lineContents = lineContents.Substring(ioState.Rules.BlockIdPrefix.Length); bSuccess &= TryStartBlock(ref ioState, lineContents); bProcessedCommand = true; } break; } case PrefixType.BlockMeta: { if (ShouldCheckMeta(ref ioState) && lineContents.StartsWith(ioState.Rules.BlockMetaPrefix)) { lineContents = lineContents.Substring(ioState.Rules.BlockMetaPrefix.Length); bSuccess &= TryEvaluateMeta(ref ioState, lineContents); bProcessedCommand = true; } break; } case PrefixType.BlockHeaderEnd: { if (lineContents.StartsWith(ioState.Rules.BlockHeaderEndPrefix)) { lineContents = lineContents.Substring(ioState.Rules.BlockHeaderEndPrefix.Length); bSuccess &= TryEndHeader(ref ioState, lineContents); bProcessedCommand = true; } break; } case PrefixType.BlockContent: { if (lineContents.StartsWith(ioState.Rules.BlockContentPrefix)) { lineContents = lineContents.Substring(ioState.Rules.BlockContentPrefix.Length); bSuccess &= TryAddContent(ref ioState, lineContents); bProcessedCommand = true; } break; } case PrefixType.BlockEnd: { if (lineContents.StartsWith(ioState.Rules.BlockEndPrefix)) { lineContents = lineContents.Substring(ioState.Rules.BlockEndPrefix.Length); bSuccess &= TryEndBlock(ref ioState, lineContents); bProcessedCommand = true; } break; } case PrefixType.PackageMeta: { if (ShouldCheckPackageMeta(ref ioState) && lineContents.StartsWith(ioState.Rules.PackageMetaPrefix)) { lineContents = lineContents.Substring(ioState.Rules.PackageMetaPrefix.Length); bSuccess &= TryEvaluatePackage(ref ioState, lineContents); bProcessedCommand = true; } break; } } } } if (!bProcessedCommand) { if (ioState.CurrentState == BlockState.InData && ioState.Rules.RequireExplicitBlockContent && !string.IsNullOrEmpty(ioState.Rules.BlockContentPrefix)) { BlockParser.LogError(ioState.Position, "Cannot add content '{0}', must have content prefix '{1}'", lineContents, ioState.Rules.BlockContentPrefix); bSuccess = false; } else if (!lineContents.IsEmpty || ioState.CurrentState == BlockState.InData) { bSuccess &= TryAddContent(ref ioState, lineContents); } } if (!lineComment.IsEmpty) { bSuccess &= TryAddComment(ref ioState, lineComment); } ioState.Error |= !bSuccess; return(bSuccess ? LineResult.Error : LineResult.NoError); } catch (Exception e) { UnityEngine.Debug.LogException(e); return(LineResult.Exception); } }
public void IndexOfTest1() { var ss = new StringSlice("0123456789", 3, 4); Assert.AreEqual(1, ss.IndexOf("45", 0, StringComparison.InvariantCulture)); }
public void IndexOfTest2() { var ss = new StringSlice("01234567890123", 0, 10); Assert.AreEqual(-1, ss.IndexOf("0", 7, StringComparison.InvariantCulture)); }
/// <summary> /// Parses a tag's contents into data. /// </summary> static public void Parse(StringSlice inSlice, IDelimiterRules inDelimiters, out TagData outTagData) { if (inDelimiters == null) { throw new ArgumentNullException("inDelimiters"); } StringSlice tag = inSlice; tag = tag.Trim(MinimalWhitespaceChars); bool bRemovedTagBoundaries = false; if (tag.StartsWith(inDelimiters.TagStartDelimiter)) { tag = tag.Substring(inDelimiters.TagStartDelimiter.Length); bRemovedTagBoundaries = true; } if (tag.EndsWith(inDelimiters.TagEndDelimiter)) { tag = tag.Substring(0, tag.Length - inDelimiters.TagEndDelimiter.Length); bRemovedTagBoundaries = true; } if (bRemovedTagBoundaries) { tag = tag.Trim(MinimalWhitespaceChars); } if (inSlice.Length == 0) { outTagData = default(TagData); return; } ClosingTagState closeState = 0; char endDelim = inDelimiters.RegionCloseDelimiter; if (endDelim != 0) { if (tag.StartsWith(endDelim)) { closeState |= ClosingTagState.Start; tag = tag.Substring(1); } if (tag.EndsWith(endDelim)) { closeState |= ClosingTagState.End; tag = tag.Substring(0, tag.Length - 1); } } if (closeState != 0) { tag = tag.Trim(MinimalWhitespaceChars); } char[] dataDelims = inDelimiters.TagDataDelimiters; int dataDelimIdx = tag.Length; foreach (var delim in dataDelims) { int idx = tag.IndexOf(delim); if (idx >= 0 && idx < dataDelimIdx) { dataDelimIdx = idx; if (idx <= 0) { break; } } } if (dataDelimIdx >= tag.Length) { outTagData.Id = tag; outTagData.Data = StringSlice.Empty; } else { outTagData.Id = tag.Substring(0, dataDelimIdx).TrimEnd(MinimalWhitespaceChars); outTagData.Data = tag.Substring(dataDelimIdx).TrimStart(dataDelims).TrimStart(MinimalWhitespaceChars); } outTagData.m_CloseState = closeState; }
public static MatchedTextRange?SearchInText( this SearchState state, StringSlice text, int?startTextPosition) { IRegex re = state.re; // matched string position int matchBegin = 0; // index of the first matched char int matchEnd = 0; // index of following after the last matched one bool wholeTextMatched = false; if (!string.IsNullOrEmpty(state.options.Template)) // empty/null template means that text matching isn't required, i.e. match any input { int textPos; if (startTextPosition.HasValue) { textPos = startTextPosition.Value; } else if (state.options.ReverseSearch) { textPos = text.Length; } else { textPos = 0; } for (; ;) { if (re != null) { if (!re.Match(text, textPos, ref state.searchMatch)) { return(null); } matchBegin = state.searchMatch.Index; matchEnd = matchBegin + state.searchMatch.Length; } else { StringComparison cmp = state.options.MatchCase ? StringComparison.CurrentCulture : StringComparison.CurrentCultureIgnoreCase; int i; // todo: use running hash if (state.options.ReverseSearch) { i = text.LastIndexOf(state.options.Template, textPos, cmp); } else { i = text.IndexOf(state.options.Template, textPos, cmp); } if (i < 0) { return(null); } matchBegin = i; matchEnd = matchBegin + state.options.Template.Length; } if (state.options.WholeWord && !IsWordBoundary(text, matchBegin, matchEnd)) { textPos = state.options.ReverseSearch ? matchBegin : matchEnd; continue; } break; } } else { matchBegin = 0; matchEnd = text.Length; wholeTextMatched = true; } return(new MatchedTextRange(text, matchBegin, matchEnd, wholeTextMatched)); }