// Reserved: 0b1101_1000_0000_0000 - 0b1101_1111_1111_1111 // High surrogate: 0b1101_1000_0000_0000 - 0b1101_1011_1111_1111 // Low surrogate: 0b1101_1100_0000_0000 - 0b1101_1111_1111_1111 public bool TryReadCharacter(BlockReader blockReader, long position, out uint character, out long posFirstByte, out long posLastByte) { if (!(blockReader is BlockReader16)) { throw new ArgumentException($"Type of '{nameof(blockReader)}' should be '{typeof(BlockReader16).Name}'"); } character = 0; posFirstByte = -1; posLastByte = -1; //position -= position & 0b1; position = blockReader.PositionFirstByte(position); if (position < 0 || position + 1 >= blockReader.StreamLength) { return(false); } uint val = blockReader.ReadValue(position); if (val < 0b1101_1000_0000_0000 || val >= 0b1110_0000_0000_0000) { character = val; posFirstByte = position; posLastByte = position + 1; return(true); }
public bool TryReadCharacter(BlockReader blockReader, long position, uint valueAtPos, out uint character, out long posFirstByte, out long posLastByte) { if (!(blockReader is BlockReader32)) { throw new ArgumentException($"Type of '{nameof(blockReader)}' should be '{typeof(BlockReader32).Name}'"); } position = blockReader.PositionFirstByte(position); character = valueAtPos; posFirstByte = position; posLastByte = position + 3; return(true); }
bool IsNewLine(BlockReader blockReader, LineEndings lineEndings, ICharacterReader charReader, long position, out long begin, out long end) { begin = -1; end = -1; uint v = blockReader.ReadValue(position); if (v == LineEndings.CR) { begin = position; position += blockReader.MinCodePointSize; end = position; if (position < blockReader.StreamLength) { v = blockReader.ReadValue(position); if (v == LineEndings.LF) { end += blockReader.MinCodePointSize; } } return(true); } else if (v == LineEndings.LF) { begin = position; end = position + blockReader.MinCodePointSize; position -= blockReader.MinCodePointSize; if (position >= 0) { v = blockReader.ReadValue(position); if (v == LineEndings.CR) { begin = position; } } return(true); } else { if (charReader.TryReadCharacter(blockReader, position, v, out uint ch, out long first, out long last)) { if (lineEndings.IsLNewLine(ch)) { begin = blockReader.PositionFirstByte(first); end = blockReader.PositionFirstByte(last) + blockReader.MinCodePointSize; return(true); } } } return(false); }
public LineReader(Stream stream, Encoding encoding) { this.encoding = encoding; switch (encoding.WebName) { case "utf-8": blockReader = new BlockReader(stream); lineEndings = new UnicodeLineEndings(); charReader = new UTF8CharacterReader(); break; case "utf-16": blockReader = new BlockReader16(stream, false); lineEndings = new UnicodeLineEndings(); charReader = new UTF16CharacterReader(); break; case "utf-16BE": blockReader = new BlockReader16(stream, true); lineEndings = new UnicodeLineEndings(); charReader = new UTF16CharacterReader(); break; case "utf-32": blockReader = new BlockReader32(stream, false); lineEndings = new UnicodeLineEndings(); charReader = new UTF32CharacterReader(); break; case "utf-32BE": blockReader = new BlockReader32(stream, true); lineEndings = new UnicodeLineEndings(); charReader = new UTF32CharacterReader(); break; default: blockReader = new BlockReader(stream); lineEndings = new LineEndings(); charReader = new SimpleCharacterReader(); break; } InitNewLineMarker(); TrimCharacters = lineEndings.CodePoints .Where(c => c <= char.MaxValue && !char.IsSurrogate((char)c)) .Select(c => (char)c) .Concat(new char[] { BOM }) .ToArray(); }
public bool TryReadCharacter(BlockReader blockReader, long position, out uint character, out long posFirstByte, out long posLastByte) { if (!(blockReader is BlockReader32)) { throw new ArgumentException($"Type of '{nameof(blockReader)}' should be '{typeof(BlockReader32).Name}'"); } character = 0; posFirstByte = -1; posLastByte = -1; position = blockReader.PositionFirstByte(position); if (position < 0 || position + 3 >= blockReader.StreamLength) { return(false); } character = blockReader.ReadValue(position); posFirstByte = position; posLastByte = position + 3; return(true); }