///|
fn pdf_cursor_name_output_capacity(cursor : @core.ByteCursor) -> Int {
let mut index = cursor.absolute_position()
let mut capacity = 1
let mut done = false
while index < cursor.length() && !done {
let value = cursor.byte_int_at_absolute(index)
if @core.pdf_is_whitespace_or_delimiter_byte(value) {
done = true
} else {
index += 1
capacity += 1
if value == 35 {
if index < cursor.length() {
index += 1
}
if index < cursor.length() {
index += 1
}
}
}
}
capacity
}
///|
/// Lex a PDF name object.
///
/// Names start with `/` and keep the slash in the stored bytes. `#xx` hex
/// escapes are decoded into raw bytes. Invalid escapes raise `@core.PdfError::InvalidHexEscape`;
/// non-name input returns `LexNone` without consuming it.
pub fn pdf_cursor_lex_name(
cursor : @core.ByteCursor,
) -> PdfLexeme raise @core.PdfError {
if cursor.peek_byte() != 47 {
LexNone
} else {
cursor.nudge()
let bytes = Array::make(pdf_cursor_name_output_capacity(cursor), b'\x00')
let mut position = pdf_lexeme_write_byte_at(bytes, 0, (47).to_byte())
let mut done = false
while !done {
let value = cursor.peek_byte()
if value == @core.pdf_no_more ||
@core.pdf_is_whitespace_or_delimiter_byte(value) {
done = true
} else {
cursor.nudge()
if value == 35 {
let high = cursor.input_byte()
let low = cursor.input_byte()
match (pdf_hex_value(high), pdf_hex_value(low)) {
(Some(high), Some(low)) =>
position = pdf_lexeme_write_byte_at(
bytes,
position,
(high * 16 + low).to_byte(),
)
_ => raise InvalidHexEscape
}
} else {
position = pdf_lexeme_write_byte_at(bytes, position, value.to_byte())
}
}
}
LexName(@core.pdf_name_of_bytes(Bytes::from_array(bytes[:position])))
}
}
///|
/// Lex and skip a PDF comment.
///
/// A comment starts with `%` and runs up to but not including the next newline.
/// The comment text is intentionally not retained; this returns an empty
/// `LexComment` payload. Non-comment input returns `LexNone`.
pub fn pdf_cursor_lex_comment(cursor : @core.ByteCursor) -> PdfLexeme {
if cursor.peek_byte() != 37 {
LexNone
} else {
let empty : Array[Byte] = []
let mut done = false
while !done {
let value = cursor.peek_byte()
if value == @core.pdf_no_more || @core.pdf_is_newline_byte(value) {
done = true
} else {
cursor.nudge()
}
}
LexComment(Bytes::from_array(empty))
}
}