updated docs and code cleanup

This commit is contained in:
Florian Sundermann 2014-08-11 11:11:24 +02:00
parent bccb3d2ede
commit d0cdae0475
10 changed files with 137 additions and 106 deletions

16
README.md Normal file
View File

@ -0,0 +1,16 @@
##Introduction##
This is a package for GO which can be used to create different types of barcodes.
##Supported Barcode Types##
* Codabar
* Code 128
* Code 39
* EAN 8
* EAN 13
* Datamatrix
* QR Codes
##Documentation##
See [GoDoc](https://godoc.org/github.com/boombuler/barcode)
To create a barcode use the Encode function from one of the subpackages.

View File

@ -1,13 +1,15 @@
// Package codabar can create Codabar barcodes
package codabar
import (
"fmt"
"regexp"
"github.com/boombuler/barcode"
"github.com/boombuler/barcode/utils"
"regexp"
)
var encodingTable map[rune][]bool = map[rune][]bool{
var encodingTable = map[rune][]bool{
'0': []bool{true, false, true, false, true, false, false, true, true},
'1': []bool{true, false, true, false, true, true, false, false, true},
'2': []bool{true, false, true, false, false, true, false, true, true},
@ -30,6 +32,7 @@ var encodingTable map[rune][]bool = map[rune][]bool{
'D': []bool{true, false, true, false, false, true, true, false, false, true},
}
// Encode creates a codabar barcode for the given content
func Encode(content string) (barcode.Barcode, error) {
checkValid, _ := regexp.Compile(`[ABCD][0123456789\-\$\:/\.\+]*[ABCD]$`)
if content == "!" || checkValid.ReplaceAllString(content, "!") != "!" {
@ -40,11 +43,7 @@ func Encode(content string) (barcode.Barcode, error) {
if i > 0 {
resBits.AddBit(false)
}
bits, ok := encodingTable[r]
if !ok {
return nil, fmt.Errorf("can not encode \"%s\"", content)
}
resBits.AddBit(bits...)
resBits.AddBit(encodingTable[r]...)
}
return utils.New1DCode("Codabar", content, resBits), nil
}

View File

@ -1,11 +1,13 @@
// Package code128 can create Code128 barcodes
package code128
import (
"fmt"
"github.com/boombuler/barcode"
"github.com/boombuler/barcode/utils"
"strings"
"unicode/utf8"
"github.com/boombuler/barcode"
"github.com/boombuler/barcode/utils"
)
func strToRunes(str string) []rune {
@ -65,6 +67,7 @@ func getCodeIndexList(content []rune) *utils.BitList {
return result
}
// Encode creates a Code 128 barcode for the given content
func Encode(content string) (barcode.Barcode, error) {
contentRunes := strToRunes(content)
if len(contentRunes) < 0 || len(contentRunes) > 80 {

View File

@ -1,10 +1,12 @@
// Package code39 can create Code39 barcodes
package code39
import (
"errors"
"strings"
"github.com/boombuler/barcode"
"github.com/boombuler/barcode/utils"
"strings"
)
type encodeInfo struct {
@ -12,7 +14,7 @@ type encodeInfo struct {
data []bool
}
var encodeTable map[rune]encodeInfo = map[rune]encodeInfo{
var encodeTable = map[rune]encodeInfo{
'0': encodeInfo{0, []bool{true, false, true, false, false, true, true, false, true, true, false, true}},
'1': encodeInfo{1, []bool{true, true, false, true, false, false, true, false, true, false, true, true}},
'2': encodeInfo{2, []bool{true, false, true, true, false, false, true, false, true, false, true, true}},
@ -59,7 +61,7 @@ var encodeTable map[rune]encodeInfo = map[rune]encodeInfo{
'*': encodeInfo{-1, []bool{true, false, false, true, false, true, true, false, true, true, false, true}},
}
var extendedTable map[rune]string = map[rune]string{
var extendedTable = map[rune]string{
0: `%U`, 1: `$A`, 2: `$B`, 3: `$C`, 4: `$D`, 5: `$E`, 6: `$F`, 7: `$G`, 8: `$H`, 9: `$I`, 10: `$J`,
11: `$K`, 12: `$L`, 13: `$M`, 14: `$N`, 15: `$O`, 16: `$P`, 17: `$Q`, 18: `$R`, 19: `$S`, 20: `$T`,
21: `$U`, 22: `$V`, 23: `$W`, 24: `$X`, 25: `$Y`, 26: `$Z`, 27: `%A`, 28: `%B`, 29: `%C`, 30: `%D`,
@ -108,7 +110,7 @@ func prepare(content string) (string, error) {
return result, nil
}
// encodes the given string as a code39 barcode
// Encode returns a code39 barcode for the given content
// if includeChecksum is set to true, a checksum character is calculated and added to the content
func Encode(content string, includeChecksum bool, fullASCIIMode bool) (barcode.Barcode, error) {
if fullASCIIMode {

View File

@ -1,75 +1,77 @@
package datamatrix
import (
"errors"
"github.com/boombuler/barcode"
)
// Encodes the given content as a DataMatrix code
func Encode(content string) (barcode.Barcode, error) {
data := encodeText(content)
var size *dmCodeSize = nil
for _, s := range codeSizes {
if s.DataCodewords() >= len(data) {
size = s
break
}
}
if size == nil {
return nil, errors.New("to much data to encode")
}
data = addPadding(data, size.DataCodewords())
data = ec.calcECC(data, size)
code := render(data, size)
if code != nil {
code.content = content
return code, nil
}
return nil, errors.New("unable to render barcode")
}
func render(data []byte, size *dmCodeSize) *datamatrixCode {
cl := newCodeLayout(size)
setters := cl.IterateSetter()
for _, b := range data {
(<-setters)(b)
}
return cl.Merge()
}
func encodeText(content string) []byte {
result := make([]byte, 0)
input := []byte(content)
for i := 0; i < len(input); {
c := input[i]
i++
if c >= '0' && c <= '9' && i < len(input) && input[i] >= '0' && input[i] <= '9' {
// two numbers...
c2 := input[i]
i++
cw := byte(((c-'0')*10 + (c2 - '0')) + 130)
result = append(result, cw)
} else if c > 127 {
// not correct... needs to be redone later...
result = append(result, 235, c-127)
} else {
result = append(result, c+1)
}
}
return result
}
func addPadding(data []byte, toCount int) []byte {
if len(data) < toCount {
data = append(data, 129)
}
for len(data) < toCount {
R := ((149 * (len(data) + 1)) % 253) + 1
data = append(data, byte((129+R)%254))
}
return data
}
// Package datamatrix can create Datamatrix barcodes
package datamatrix
import (
"errors"
"github.com/boombuler/barcode"
)
// Encode returns a Datamatrix barcode for the given content
func Encode(content string) (barcode.Barcode, error) {
data := encodeText(content)
var size *dmCodeSize
for _, s := range codeSizes {
if s.DataCodewords() >= len(data) {
size = s
break
}
}
if size == nil {
return nil, errors.New("to much data to encode")
}
data = addPadding(data, size.DataCodewords())
data = ec.calcECC(data, size)
code := render(data, size)
if code != nil {
code.content = content
return code, nil
}
return nil, errors.New("unable to render barcode")
}
func render(data []byte, size *dmCodeSize) *datamatrixCode {
cl := newCodeLayout(size)
setters := cl.IterateSetter()
for _, b := range data {
(<-setters)(b)
}
return cl.Merge()
}
func encodeText(content string) []byte {
var result []byte
input := []byte(content)
for i := 0; i < len(input); {
c := input[i]
i++
if c >= '0' && c <= '9' && i < len(input) && input[i] >= '0' && input[i] <= '9' {
// two numbers...
c2 := input[i]
i++
cw := byte(((c-'0')*10 + (c2 - '0')) + 130)
result = append(result, cw)
} else if c > 127 {
// not correct... needs to be redone later...
result = append(result, 235, c-127)
} else {
result = append(result, c+1)
}
}
return result
}
func addPadding(data []byte, toCount int) []byte {
if len(data) < toCount {
data = append(data, 129)
}
for len(data) < toCount {
R := ((149 * (len(data) + 1)) % 253) + 1
data = append(data, byte((129+R)%254))
}
return data
}

View File

@ -1,8 +1,9 @@
// package for EAN barcode generation.
// Package ean can create EAN 8 and EAN 13 barcodes.
package ean
import (
"errors"
"github.com/boombuler/barcode"
"github.com/boombuler/barcode/utils"
)
@ -14,7 +15,7 @@ type encodedNumber struct {
CheckSum []bool
}
var encoderTable map[rune]encodedNumber = map[rune]encodedNumber{
var encoderTable = map[rune]encodedNumber{
'0': encodedNumber{
[]bool{false, false, false, true, true, false, true},
[]bool{false, true, false, false, true, true, true},
@ -170,7 +171,7 @@ func encodeEAN13(code string) *utils.BitList {
return result
}
// encodes the given EAN 8 or EAN 13 number to a barcode image
// Encode returns a EAN 8 or EAN 13 barcode for the given code
func Encode(code string) (barcode.Barcode, error) {
if len(code) == 7 || len(code) == 12 {
code += string(calcCheckNum(code))
@ -178,7 +179,7 @@ func Encode(code string) (barcode.Barcode, error) {
check := code[0 : len(code)-1]
check += string(calcCheckNum(check))
if check != code {
return nil, errors.New("checksum missmatch!")
return nil, errors.New("checksum missmatch")
}
}

View File

@ -36,7 +36,7 @@ func (bc *scaledBarcode) At(x, y int) color.Color {
return bc.wrapperFunc(x, y)
}
// returns a resized barcode with the given width and height.
// Scale returns a resized barcode with the given width and height.
func Scale(bc Barcode, width, height int) (Barcode, error) {
switch bc.Metadata().Dimensions {
case 1:

View File

@ -1,9 +1,11 @@
// Package utils contain some utilities which are needed to create barcodes
package utils
import (
"github.com/boombuler/barcode"
"image"
"image/color"
"github.com/boombuler/barcode"
)
type base1DCode struct {
@ -35,6 +37,7 @@ func (c *base1DCode) At(x, y int) color.Color {
return color.White
}
// New1DCode creates a new 1D barcode where the bars are represented by the bits in the bars BitList
func New1DCode(codeKind, content string, bars *BitList) barcode.Barcode {
return &base1DCode{bars, codeKind, content}
}

View File

@ -1,12 +1,12 @@
package utils
// utility class that contains bits
// BitList is a list that contains bits
type BitList struct {
count int
data []int32
}
// returns a new BitList with the given length
// NewBitList returns a new BitList with the given length
// all bits are initialize with false
func NewBitList(capacity int) *BitList {
bl := new(BitList)
@ -19,7 +19,7 @@ func NewBitList(capacity int) *BitList {
return bl
}
// returns the number of contained bits
// Len returns the number of contained bits
func (bl *BitList) Len() int {
return bl.count
}
@ -37,7 +37,7 @@ func (bl *BitList) grow() {
bl.data = nd
}
// appends the given bits to the end of the list
// AddBit appends the given bits to the end of the list
func (bl *BitList) AddBit(bits ...bool) {
for _, bit := range bits {
itmIndex := bl.count / 32
@ -49,7 +49,7 @@ func (bl *BitList) AddBit(bits ...bool) {
}
}
// sets the bit at the given index to the given value
// SetBit sets the bit at the given index to the given value
func (bl *BitList) SetBit(index int, value bool) {
itmIndex := index / 32
itmBitShift := 31 - (index % 32)
@ -60,32 +60,32 @@ func (bl *BitList) SetBit(index int, value bool) {
}
}
// returns the bit at the given index
// GetBit returns the bit at the given index
func (bl *BitList) GetBit(index int) bool {
itmIndex := index / 32
itmBitShift := 31 - (index % 32)
return ((bl.data[itmIndex] >> uint(itmBitShift)) & 1) == 1
}
// appends all 8 bits of the given byte to the end of the list
// AddByte appends all 8 bits of the given byte to the end of the list
func (bl *BitList) AddByte(b byte) {
for i := 7; i >= 0; i-- {
bl.AddBit(((b >> uint(i)) & 1) == 1)
}
}
// appends the last (LSB) 'count' bits of 'b' the the end of the list
// AddBits appends the last (LSB) 'count' bits of 'b' the the end of the list
func (bl *BitList) AddBits(b int, count byte) {
for i := int(count - 1); i >= 0; i-- {
bl.AddBit(((b >> uint(i)) & 1) == 1)
}
}
// returns all bits of the BitList as a []byte
// GetBytes returns all bits of the BitList as a []byte
func (bl *BitList) GetBytes() []byte {
len := bl.count >> 3
if (bl.count % 8) != 0 {
len += 1
len++
}
result := make([]byte, len)
for i := 0; i < len; i++ {
@ -95,7 +95,7 @@ func (bl *BitList) GetBytes() []byte {
return result
}
// iterates through all bytes contained in the BitList
// IterateBytes iterates through all bytes contained in the BitList
func (bl *BitList) IterateBytes() <-chan byte {
res := make(chan byte)
@ -108,7 +108,7 @@ func (bl *BitList) IterateBytes() <-chan byte {
shift -= 8
if shift < 0 {
shift = 24
i += 1
i++
}
c -= 8
}

View File

@ -1,10 +1,12 @@
package utils
// GaloisField encapsulates galois field arithmetics
type GaloisField struct {
ALogTbl []int
LogTbl []int
}
// NewGaloisField creates a new falois field
func NewGaloisField(pp int) *GaloisField {
result := new(GaloisField)
fldSize := 256
@ -28,10 +30,12 @@ func NewGaloisField(pp int) *GaloisField {
return result
}
// AddOrSub add or substract two numbers
func (gf *GaloisField) AddOrSub(a, b int) int {
return a ^ b
}
// Multiply multiplys two numbers
func (gf *GaloisField) Multiply(a, b int) int {
if a == 0 || b == 0 {
return 0
@ -39,6 +43,7 @@ func (gf *GaloisField) Multiply(a, b int) int {
return gf.ALogTbl[(gf.LogTbl[a]+gf.LogTbl[b])%255]
}
// Divide divides two numbers
func (gf *GaloisField) Divide(a, b int) int {
if b == 0 {
panic("divide by zero")