package bits type Writer struct { buf []byte // total buf byte *byte // pointer to current byte bits byte // bits left in byte } func NewWriter(buf []byte) *Writer { return &Writer{buf: buf} } //goland:noinspection GoStandardMethods func (w *Writer) WriteByte(b byte) { if w.bits != 0 { w.WriteBits8(b, 8) } w.buf = append(w.buf, b) } func (w *Writer) WriteBit(b byte) { if w.bits == 0 { w.buf = append(w.buf, 0) w.byte = &w.buf[len(w.buf)-1] w.bits = 7 } else { w.bits-- } *w.byte |= (b & 1) << w.bits } func (w *Writer) WriteBits(v uint32, n byte) { for i := n - 1; i != 255; i-- { w.WriteBit(byte(v>>i) & 0b1) } } func (w *Writer) WriteBits16(v uint16, n byte) { for i := n - 1; i != 255; i-- { w.WriteBit(byte(v>>i) & 0b1) } } func (w *Writer) WriteBits8(v, n byte) { for i := n - 1; i != 255; i-- { w.WriteBit((v >> i) & 0b1) } } func (w *Writer) WriteAllBits(bit, n byte) { for i := byte(0); i < n; i++ { w.WriteBit(bit) } } func (w *Writer) WriteBool(b bool) { if b { w.WriteBit(1) } else { w.WriteBit(0) } } func (w *Writer) WriteUint16(v uint16) { if w.bits != 0 { w.WriteBits16(v, 16) } w.buf = append(w.buf, byte(v>>8), byte(v)) } func (w *Writer) WriteBytes(bytes ...byte) { if w.bits != 0 { for _, b := range bytes { w.WriteByte(b) } } w.buf = append(w.buf, bytes...) } func (w *Writer) Bytes() []byte { return w.buf } func (w *Writer) Len() int { return len(w.buf) } func (w *Writer) Reset() { w.buf = w.buf[:0] w.bits = 0 }