qubit_codec/transcode/encode_context.rs
1// =============================================================================
2// Copyright (c) 2026 Haixing Hu.
3//
4// SPDX-License-Identifier: Apache-2.0
5//
6// Licensed under the Apache License, Version 2.0.
7// =============================================================================
8//! Encode context for one buffered encode attempt.
9
10/// Context for one encode attempt inside a buffered encoder engine.
11///
12/// The context carries the current input value and output cursor. The hook
13/// decides whether the value can be consumed with the visible output capacity
14/// and reports that decision through [`crate::EncodeOutcome`].
15///
16/// # Type Parameters
17///
18/// - `Value`: Logical input value type.
19/// - `Unit`: Encoded output unit type.
20#[derive(Debug)]
21pub struct EncodeContext<'a, Value, Unit> {
22 input_value: &'a Value,
23 input_index: usize,
24 output: &'a mut [Unit],
25 output_index: usize,
26}
27
28impl<'a, Value, Unit> EncodeContext<'a, Value, Unit> {
29 /// Creates an encode context.
30 ///
31 /// # Parameters
32 ///
33 /// - `input_value`: Borrowed input value being encoded.
34 /// - `input_index`: Absolute input index of `input_value`.
35 /// - `output`: Complete output unit slice visible to the encoder.
36 /// - `output_index`: Start position in `output` where writing begins.
37 ///
38 /// # Returns
39 ///
40 /// Returns an encode context.
41 #[inline(always)]
42 #[must_use]
43 pub fn new(
44 input_value: &'a Value,
45 input_index: usize,
46 output: &'a mut [Unit],
47 output_index: usize,
48 ) -> Self {
49 Self {
50 input_value,
51 input_index,
52 output,
53 output_index,
54 }
55 }
56
57 /// Returns the input value being encoded.
58 ///
59 /// # Returns
60 ///
61 /// Returns a shared reference to the current input value.
62 #[inline(always)]
63 #[must_use]
64 pub fn input_value(&self) -> &Value {
65 self.input_value
66 }
67
68 /// Returns the absolute input index of the current value.
69 ///
70 /// # Returns
71 ///
72 /// Returns the absolute input index.
73 #[inline(always)]
74 #[must_use]
75 pub fn input_index(&self) -> usize {
76 self.input_index
77 }
78
79 /// Returns the complete output unit slice visible to the encoder.
80 ///
81 /// # Returns
82 ///
83 /// Returns the output slice.
84 #[inline(always)]
85 #[must_use]
86 pub fn output(&mut self) -> &mut [Unit] {
87 self.output
88 }
89
90 /// Returns the start position in the output slice where writing begins.
91 ///
92 /// # Returns
93 ///
94 /// Returns the absolute output index.
95 #[inline(always)]
96 #[must_use]
97 pub fn output_index(&self) -> usize {
98 self.output_index
99 }
100
101 /// Returns writable output units from the current output index.
102 ///
103 /// # Returns
104 ///
105 /// Returns output capacity visible to this encode attempt.
106 #[inline(always)]
107 #[must_use]
108 pub fn available_output(&self) -> usize {
109 self.output.len().saturating_sub(self.output_index)
110 }
111
112 /// Consumes the context and returns all parts.
113 ///
114 /// Use this when you need simultaneous access to the input value reference
115 /// and the mutable output slice, since Rust's borrow checker disallows
116 /// taking `&self` and `&mut self` in the same expression.
117 ///
118 /// # Returns
119 ///
120 /// Returns `(input_value, input_index, output, output_index)`.
121 #[inline(always)]
122 #[must_use]
123 pub fn into_parts(self) -> (&'a Value, usize, &'a mut [Unit], usize) {
124 (
125 self.input_value,
126 self.input_index,
127 self.output,
128 self.output_index,
129 )
130 }
131}