mirror of
https://github.com/unidoc/unipdf.git
synced 2025-05-02 22:17:06 +08:00

* Prepared skeleton and basic component implementations for the jbig2 encoding. * Added Bitset. Implemented Bitmap. * Decoder with old Arithmetic Decoder * Partly working arithmetic * Working arithmetic decoder. * MMR patched. * rebuild to apache. * Working generic * Working generic * Decoded full document * Update Jenkinsfile go version [master] (#398) * Update Jenkinsfile go version * Decoded AnnexH document * Minor issues fixed. * Update README.md * Fixed generic region errors. Added benchmark. Added bitmap unpadder. Added Bitmap toImage method. * Fixed endofpage error * Added integration test. * Decoded all test files without errors. Implemented JBIG2Global. * Merged with v3 version * Fixed the EOF in the globals issue * Fixed the JBIG2 ChocolateData Decode * JBIG2 Added license information * Minor fix in jbig2 encoding. * Applied the logging convention * Cleaned unnecessary imports * Go modules clear unused imports * checked out the README.md * Moved trace to Debug. Fixed the build integrate tag in the document_decode_test.go * Initial encoder skeleton * Applied UniPDF Developer Guide. Fixed lint issues. * Cleared documentation, fixed style issues. * Added jbig2 doc.go files. Applied unipdf guide style. * Minor code style changes. * Minor naming and style issues fixes. * Minor naming changes. Style issues fixed. * Review r11 fixes. * Added JBIG2 Encoder skeleton. * Moved Document and Page to jbig2/document package. Created decoder package responsible for decoding jbig2 stream. * Implemented raster functions. * Added raster uni low test funcitons. * Added raster low test functions * untracked files on jbig2-encoder: c869089 Added raster low test functions * index on jbig2-encoder: c869089 Added raster low test functions * Added morph files. * implemented jbig2 encoder basics * JBIG2 Encoder - Generic method * Added jbig2 image encode ttests, black/white image tests * cleaned and tested jbig2 package * unfinished jbig2 classified encoder * jbig2 minor style changes * minor jbig2 encoder changes * prepared JBIG2 Encoder * Style and lint fixes * Minor changes and lints * Fixed shift unsinged value build errors * Minor naming change * Added jbig2 encode, image gondels. Fixed jbig2 decode bug. * Provided jbig2 core.DecodeGlobals function. * Fixed JBIG2Encoder `r6` revision issues. * Removed public JBIG2Encoder document. * Minor style changes * added NewJBIG2Encoder function. * fixed JBIG2Encoder 'r9' revision issues. * Cleared 'r9' commented code. * Updated ACKNOWLEDGEMENETS. Fixed JBIG2Encoder 'r10' revision issues. Co-authored-by: Gunnsteinn Hall <gunnsteinn.hall@gmail.com>
203 lines
4.6 KiB
Go
203 lines
4.6 KiB
Go
/*
|
|
* This file is subject to the terms and conditions defined in
|
|
* file 'LICENSE.md', which is part of this source code package.
|
|
*/
|
|
|
|
package bitmap
|
|
|
|
// Blit blits the source Bitmap 'src' into Destination bitmap: 'dst' on the provided 'x' and 'y' coordinates
|
|
// with respect to the combination operator 'op'.
|
|
func Blit(src *Bitmap, dst *Bitmap, x, y int, op CombinationOperator) error {
|
|
var startLine, srcStartIdx int
|
|
srcEndIdx := src.RowStride - 1
|
|
|
|
// ignore those parts of source bitmap placed outside target bitmap.
|
|
if x < 0 {
|
|
srcStartIdx = -x
|
|
x = 0
|
|
} else if x+src.Width > dst.Width {
|
|
srcEndIdx -= src.Width + x - dst.Width
|
|
}
|
|
|
|
if y < 0 {
|
|
startLine = -y
|
|
y = 0
|
|
srcStartIdx += src.RowStride
|
|
srcEndIdx += src.RowStride
|
|
} else if y+src.Height > dst.Height {
|
|
startLine = src.Height + y - dst.Height
|
|
}
|
|
|
|
var (
|
|
lastLine int
|
|
err error
|
|
)
|
|
shiftVal1 := x & 0x07
|
|
shiftVal2 := 8 - shiftVal1
|
|
padding := src.Width & 0x07
|
|
toShift := shiftVal2 - padding
|
|
useShift := shiftVal2&0x07 != 0
|
|
specialCase := src.Width <= ((srcEndIdx-srcStartIdx)<<3)+shiftVal2
|
|
dstStartIdx := dst.GetByteIndex(x, y)
|
|
|
|
// get math.min()
|
|
temp := startLine + dst.Height
|
|
if src.Height > temp {
|
|
lastLine = temp
|
|
} else {
|
|
lastLine = src.Height
|
|
}
|
|
|
|
switch {
|
|
case !useShift:
|
|
err = blitUnshifted(src, dst, startLine, lastLine, dstStartIdx, srcStartIdx, srcEndIdx, op)
|
|
case specialCase:
|
|
err = blitSpecialShifted(src, dst, startLine, lastLine, dstStartIdx, srcStartIdx, srcEndIdx, toShift, shiftVal1, shiftVal2, op)
|
|
default:
|
|
err = blitShifted(src, dst, startLine, lastLine, dstStartIdx, srcStartIdx, srcEndIdx, toShift, shiftVal1, shiftVal2, op, padding)
|
|
}
|
|
return err
|
|
}
|
|
|
|
func blitUnshifted(
|
|
src, dst *Bitmap,
|
|
startLine, lastLine, dstStartIdx, srcStartIdx, srcEndIdx int,
|
|
op CombinationOperator,
|
|
) error {
|
|
var dstLine int
|
|
increaser := func() {
|
|
dstLine++
|
|
dstStartIdx += dst.RowStride
|
|
srcStartIdx += src.RowStride
|
|
srcEndIdx += src.RowStride
|
|
}
|
|
|
|
for dstLine = startLine; dstLine < lastLine; increaser() {
|
|
dstIdx := dstStartIdx
|
|
for srcIdx := srcStartIdx; srcIdx <= srcEndIdx; srcIdx++ {
|
|
oldByte, err := dst.GetByte(dstIdx)
|
|
if err != nil {
|
|
return err
|
|
}
|
|
|
|
newByte, err := src.GetByte(srcIdx)
|
|
if err != nil {
|
|
return err
|
|
}
|
|
|
|
if err = dst.SetByte(dstIdx, combineBytes(oldByte, newByte, op)); err != nil {
|
|
return err
|
|
}
|
|
dstIdx++
|
|
}
|
|
}
|
|
return nil
|
|
}
|
|
|
|
func blitShifted(
|
|
src, dst *Bitmap,
|
|
startLine, lastLine, dstStartIdx, srcStartIdx, srcEndIdx, toShift, shiftVal1, shiftVal2 int,
|
|
op CombinationOperator, padding int,
|
|
) error {
|
|
var dstLine int
|
|
increaser := func() {
|
|
dstLine++
|
|
dstStartIdx += dst.RowStride
|
|
srcStartIdx += src.RowStride
|
|
srcEndIdx += src.RowStride
|
|
}
|
|
|
|
for dstLine = startLine; dstLine < lastLine; increaser() {
|
|
var register uint16
|
|
dstIdx := dstStartIdx
|
|
|
|
for srcIdx := srcStartIdx; srcIdx <= srcEndIdx; srcIdx++ {
|
|
oldByte, err := dst.GetByte(dstIdx)
|
|
if err != nil {
|
|
return err
|
|
}
|
|
|
|
newByte, err := src.GetByte(srcIdx)
|
|
if err != nil {
|
|
return err
|
|
}
|
|
register = (register | (uint16(newByte) & 0xff)) << uint(shiftVal2)
|
|
|
|
newByte = byte(register >> 8)
|
|
if err = dst.SetByte(dstIdx, combineBytes(oldByte, newByte, op)); err != nil {
|
|
return err
|
|
}
|
|
dstIdx++
|
|
|
|
register <<= uint(shiftVal1)
|
|
|
|
if srcIdx == srcEndIdx {
|
|
newByte = byte(register >> (8 - uint8(shiftVal2)))
|
|
|
|
if padding != 0 {
|
|
newByte = unpad(uint(8+toShift), newByte)
|
|
}
|
|
|
|
oldByte, err = dst.GetByte(dstIdx)
|
|
if err != nil {
|
|
return err
|
|
}
|
|
|
|
if err = dst.SetByte(dstIdx, combineBytes(oldByte, newByte, op)); err != nil {
|
|
return err
|
|
}
|
|
}
|
|
}
|
|
}
|
|
return nil
|
|
}
|
|
|
|
func blitSpecialShifted(
|
|
src, dst *Bitmap,
|
|
startLine, lastLine, dstStartIdx, srcStartIdx, srcEndIdx, toShift, shiftVal1, shiftVal2 int,
|
|
op CombinationOperator,
|
|
) error {
|
|
var dstLine int
|
|
increaser := func() {
|
|
dstLine++
|
|
dstStartIdx += dst.RowStride
|
|
srcStartIdx += src.RowStride
|
|
srcEndIdx += src.RowStride
|
|
}
|
|
|
|
for dstLine = startLine; dstLine < lastLine; increaser() {
|
|
var register uint16
|
|
dstIdx := dstStartIdx
|
|
|
|
for srcIdx := srcStartIdx; srcIdx <= srcEndIdx; srcIdx++ {
|
|
oldByte, err := dst.GetByte(dstIdx)
|
|
if err != nil {
|
|
return err
|
|
}
|
|
|
|
newByte, err := src.GetByte(srcIdx)
|
|
if err != nil {
|
|
return err
|
|
}
|
|
register = (register | uint16(newByte)) << uint(shiftVal2)
|
|
newByte = byte(register >> 8)
|
|
|
|
if srcIdx == srcEndIdx {
|
|
newByte = unpad(uint(toShift), newByte)
|
|
}
|
|
|
|
if err = dst.SetByte(dstIdx, combineBytes(oldByte, newByte, op)); err != nil {
|
|
return err
|
|
}
|
|
dstIdx++
|
|
|
|
register <<= uint(shiftVal1)
|
|
}
|
|
}
|
|
return nil
|
|
}
|
|
|
|
func unpad(padding uint, b byte) byte {
|
|
return b >> padding << padding
|
|
}
|