| Line | Hits | Source |
|---|---|---|
| 1 | 1 | (function(){ |
| 2 | ||
| 3 | // Main function, calls drawCanvas(...) in the right way | |
| 4 | 1 | var JsBarcode = function(image, content, options){ |
| 5 | // If the image is a string, query select call again | |
| 6 | 21 | if(typeof image === "string"){ |
| 7 | 1 | image = document.querySelector(image); |
| 8 | 0 | JsBarcode(image, content, options); |
| 9 | } | |
| 10 | // If image, draw on canvas and set the uri as src | |
| 11 | 20 | else if(typeof HTMLCanvasElement !== 'undefined' && image instanceof HTMLImageElement){ |
| 12 | 0 | canvas = document.createElement('canvas'); |
| 13 | 0 | drawCanvas(canvas, content, options); |
| 14 | 0 | image.setAttribute("src", canvas.toDataURL()); |
| 15 | } | |
| 16 | // If canvas, just draw | |
| 17 | 20 | else if(image.getContext){ |
| 18 | 19 | drawCanvas(image, content, options); |
| 19 | } | |
| 20 | else{ | |
| 21 | 1 | throw new Error("Not supported type to draw on."); |
| 22 | } | |
| 23 | } | |
| 24 | ||
| 25 | // The main function, handles everything with the modules and draws the image | |
| 26 | 1 | var drawCanvas = function(canvas, content, options) { |
| 27 | // Merge the user options with the default | |
| 28 | 19 | options = merge(JsBarcode.defaults, options); |
| 29 | ||
| 30 | // Fix the margins | |
| 31 | 19 | options.marginTop = options.marginTop | options.margin; |
| 32 | 19 | options.marginBottom = options.marginBottom | options.margin; |
| 33 | 19 | options.marginRight = options.marginRight | options.margin; |
| 34 | 19 | options.marginLeft = options.marginLeft | options.margin; |
| 35 | ||
| 36 | //Abort if the browser does not support HTML5 canvas | |
| 37 | 19 | if (!canvas.getContext) { |
| 38 | 0 | throw new Error('The browser does not support canvas.'); |
| 39 | } | |
| 40 | ||
| 41 | // Automatically choose barcode if format set to "auto"... | |
| 42 | 19 | if(options.format == "auto"){ |
| 43 | 3 | var encoder = new (JsBarcode.autoSelectEncoder(content))(content); |
| 44 | } | |
| 45 | // ...or else, get by name | |
| 46 | else{ | |
| 47 | 16 | var encoder = new (JsBarcode.getModule(options.format))(content); |
| 48 | } | |
| 49 | ||
| 50 | //Abort if the barcode format does not support the content | |
| 51 | 18 | if(!encoder.valid()){ |
| 52 | 2 | options.valid(false); |
| 53 | 2 | if(options.valid == JsBarcode.defaults.valid){ |
| 54 | 1 | throw new Error('The data is not valid for the type of barcode.'); |
| 55 | } | |
| 56 | 1 | return; |
| 57 | } | |
| 58 | ||
| 59 | // Set the binary to a cached version if possible | |
| 60 | 16 | var cachedBinary = JsBarcode.getCache(options.format, content); |
| 61 | 16 | if(cachedBinary){ |
| 62 | 9 | var binary = cachedBinary; |
| 63 | } | |
| 64 | else{ | |
| 65 | // Encode the content | |
| 66 | 7 | var binary = encoder.encoded(); |
| 67 | // Cache the encoding if it will be used again later | |
| 68 | 7 | JsBarcode.cache(options.format, content, binary); |
| 69 | } | |
| 70 | ||
| 71 | // Get the canvas context | |
| 72 | 16 | var ctx = canvas.getContext("2d"); |
| 73 | ||
| 74 | // Set font | |
| 75 | 16 | var font = options.fontOptions + " " + options.fontSize + "px "+options.font; |
| 76 | 16 | ctx.font = font; |
| 77 | ||
| 78 | // Set the width and height of the barcode | |
| 79 | 16 | var width = binary.length*options.width; |
| 80 | // Replace with width of the text if it is wider then the barcode | |
| 81 | 16 | var textWidth = ctx.measureText(encoder.getText()).width; |
| 82 | 16 | if(options.displayValue && width < textWidth){ |
| 83 | 0 | if(options.textAlign == "center"){ |
| 84 | 0 | var barcodePadding = Math.floor((textWidth - width)/2); |
| 85 | } | |
| 86 | 0 | else if(options.textAlign == "left"){ |
| 87 | 0 | var barcodePadding = 0; |
| 88 | } | |
| 89 | 0 | else if(options.textAlign == "right"){ |
| 90 | 0 | var barcodePadding = Math.floor(textWidth - width); |
| 91 | } | |
| 92 | ||
| 93 | 0 | width = textWidth; |
| 94 | } | |
| 95 | // Make sure barcodePadding is not undefined | |
| 96 | 16 | var barcodePadding = barcodePadding || 0; |
| 97 | ||
| 98 | 16 | canvas.width = width + options.marginLeft + options.marginRight; |
| 99 | ||
| 100 | // Set extra height if the value is displayed under the barcode. Multiplication with 1.3 t0 ensure that some | |
| 101 | //characters are not cut in half | |
| 102 | 16 | canvas.height = options.height |
| 103 | + (options.displayValue ? options.fontSize : 0) | |
| 104 | + options.textMargin | |
| 105 | + options.marginTop | |
| 106 | + options.marginBottom; | |
| 107 | ||
| 108 | // Paint the canvas | |
| 109 | 16 | ctx.clearRect(0,0,canvas.width,canvas.height); |
| 110 | 16 | if(options.background){ |
| 111 | 16 | ctx.fillStyle = options.background; |
| 112 | 16 | ctx.fillRect(0,0,canvas.width, canvas.height); |
| 113 | } | |
| 114 | ||
| 115 | // Creates the barcode out of the encoded binary | |
| 116 | 16 | ctx.fillStyle = options.lineColor; |
| 117 | 16 | for(var i=0;i<binary.length;i++){ |
| 118 | 1538 | var x = i*options.width + options.marginLeft + barcodePadding; |
| 119 | 1538 | if(binary[i] == "1"){ |
| 120 | 730 | ctx.fillRect(x, options.marginTop, options.width, options.height); |
| 121 | } | |
| 122 | } | |
| 123 | ||
| 124 | // Draw the text if displayValue is set | |
| 125 | 16 | if(options.displayValue){ |
| 126 | 15 | var x, y; |
| 127 | ||
| 128 | 15 | y = options.height + options.textMargin + options.marginTop; |
| 129 | ||
| 130 | 15 | ctx.font = font; |
| 131 | 15 | ctx.textBaseline = "bottom"; |
| 132 | 15 | ctx.textBaseline = 'top'; |
| 133 | ||
| 134 | // Draw the text in the correct X depending on the textAlign option | |
| 135 | 15 | if(options.textAlign == "left" || barcodePadding > 0){ |
| 136 | 1 | x = options.marginLeft; |
| 137 | 1 | ctx.textAlign = 'left'; |
| 138 | } | |
| 139 | 14 | else if(options.textAlign == "right"){ |
| 140 | 1 | x = canvas.width - options.marginRight; |
| 141 | 1 | ctx.textAlign = 'right'; |
| 142 | } | |
| 143 | //In all other cases, center the text | |
| 144 | else{ | |
| 145 | 13 | x = canvas.width / 2; |
| 146 | 13 | ctx.textAlign = 'center'; |
| 147 | } | |
| 148 | ||
| 149 | 15 | ctx.fillText(encoder.getText(), x, y); |
| 150 | } | |
| 151 | ||
| 152 | // Send a confirmation that the generation was successful to the valid function if it does exist | |
| 153 | 16 | options.valid(true); |
| 154 | }; | |
| 155 | ||
| 156 | 1 | JsBarcode._modules = []; |
| 157 | ||
| 158 | // Add a new module sorted in the array | |
| 159 | 1 | JsBarcode.register = function(module, regex, priority){ |
| 160 | 17 | var position = 0; |
| 161 | 17 | if(typeof priority === "undefined"){ |
| 162 | 4 | position = JsBarcode._modules.length - 1; |
| 163 | } | |
| 164 | else{ | |
| 165 | 13 | for(var i=0;i<JsBarcode._modules.length;i++){ |
| 166 | 38 | position = i; |
| 167 | 38 | if(!(priority < JsBarcode._modules[i].priority)){ |
| 168 | 10 | break; |
| 169 | } | |
| 170 | } | |
| 171 | } | |
| 172 | ||
| 173 | // Add the module in position position | |
| 174 | 17 | JsBarcode._modules.splice(position, 0, { |
| 175 | "regex": regex, | |
| 176 | "module": module, | |
| 177 | "priority": priority | |
| 178 | }); | |
| 179 | }; | |
| 180 | ||
| 181 | // Get module by name | |
| 182 | 1 | JsBarcode.getModule = function(name){ |
| 183 | 33 | for(var i in JsBarcode._modules){ |
| 184 | 368 | if(name.search(JsBarcode._modules[i].regex) !== -1){ |
| 185 | 32 | return JsBarcode._modules[i].module; |
| 186 | } | |
| 187 | } | |
| 188 | 1 | throw new Error('Module ' + name + ' does not exist or is not loaded.'); |
| 189 | }; | |
| 190 | ||
| 191 | // If any format is valid with the content, return the format with highest priority | |
| 192 | 1 | JsBarcode.autoSelectEncoder = function(content){ |
| 193 | 3 | for(var i in JsBarcode._modules){ |
| 194 | 17 | var barcode = new (JsBarcode._modules[i].module)(content); |
| 195 | 17 | if(barcode.valid(content)){ |
| 196 | 3 | return JsBarcode._modules[i].module; |
| 197 | } | |
| 198 | } | |
| 199 | 0 | throw new Error("Can't automatically find a barcode format matching the string '" + content + "'"); |
| 200 | }; | |
| 201 | ||
| 202 | // Defining the cache dictionary | |
| 203 | 1 | JsBarcode._cache = {}; |
| 204 | ||
| 205 | // Cache a regerated barcode | |
| 206 | 1 | JsBarcode.cache = function(format, input, output){ |
| 207 | 7 | if(!JsBarcode._cache[format]){ |
| 208 | 4 | JsBarcode._cache[format] = {}; |
| 209 | } | |
| 210 | 7 | JsBarcode._cache[format][input] = output; |
| 211 | }; | |
| 212 | ||
| 213 | // Get a chached barcode | |
| 214 | 1 | JsBarcode.getCache = function(format, input){ |
| 215 | 16 | if(JsBarcode._cache[format]){ |
| 216 | 12 | if(JsBarcode._cache[format][input]){ |
| 217 | 9 | return JsBarcode._cache[format][input]; |
| 218 | } | |
| 219 | } | |
| 220 | 7 | return ""; |
| 221 | }; | |
| 222 | ||
| 223 | // Detect if the code is running under nodejs | |
| 224 | 1 | JsBarcode._isNode = false; |
| 225 | 1 | if (typeof module !== 'undefined' && module.exports) { |
| 226 | 1 | module.exports = JsBarcode; // Export to nodejs |
| 227 | 1 | JsBarcode._isNode = true; |
| 228 | ||
| 229 | //Register all modules in ./barcodes/ | |
| 230 | 1 | var path = require("path"); |
| 231 | 1 | var dir = path.join(__dirname, "barcodes"); |
| 232 | 1 | var files = require("fs").readdirSync(dir); |
| 233 | 1 | for(var i in files){ |
| 234 | 8 | var barcode = require(path.join(dir, files[i])); |
| 235 | 8 | barcode.register(JsBarcode); |
| 236 | } | |
| 237 | } | |
| 238 | ||
| 239 | //Regsiter JsBarcode for the browser | |
| 240 | 1 | if(typeof window !== 'undefined'){ |
| 241 | 0 | window.JsBarcode = JsBarcode; |
| 242 | } | |
| 243 | ||
| 244 | // Register JsBarcode as an jQuery plugin if jQuery exist | |
| 245 | 1 | if (typeof jQuery !== 'undefined') { |
| 246 | 0 | jQuery.fn.JsBarcode = function(content, options, validFunction){ |
| 247 | 0 | JsBarcode(this.get(0), content, options, validFunction); |
| 248 | 0 | return this; |
| 249 | }; | |
| 250 | } | |
| 251 | ||
| 252 | // All the default options. If one is not set. | |
| 253 | 1 | JsBarcode.defaults = { |
| 254 | width: 2, | |
| 255 | height: 100, | |
| 256 | format: "auto", | |
| 257 | displayValue: true, | |
| 258 | fontOptions: "", | |
| 259 | font: "monospace", | |
| 260 | textAlign: "center", | |
| 261 | textMargin: 2, | |
| 262 | fontSize: 20, | |
| 263 | background: "#ffffff", | |
| 264 | lineColor: "#000000", | |
| 265 | margin: 10, | |
| 266 | marginTop: undefined, | |
| 267 | marginBottom: undefined, | |
| 268 | marginLeft: undefined, | |
| 269 | marginRight: undefined, | |
| 270 | valid: function(valid){} | |
| 271 | }; | |
| 272 | ||
| 273 | // Function to merge the default options with the default ones | |
| 274 | 1 | var merge = function(m1, m2) { |
| 275 | 19 | var newMerge = {}; |
| 276 | 19 | for (var k in m1) { |
| 277 | 323 | newMerge[k] = m1[k]; |
| 278 | } | |
| 279 | 19 | for (var k in m2) { |
| 280 | 26 | if(typeof m2[k] !== "undefined"){ |
| 281 | 26 | newMerge[k] = m2[k]; |
| 282 | } | |
| 283 | } | |
| 284 | 19 | return newMerge; |
| 285 | }; | |
| 286 | })(); | |
| 287 |
| Line | Hits | Source |
|---|---|---|
| 1 | // ASCII value ranges 0-127, 200-211 | |
| 2 | 1 | var validCODE128 = /^[\x00-\x7F\xC8-\xD3]+$/; |
| 3 | ||
| 4 | // This is the master class, it does require the start code to be | |
| 5 | //included in the string | |
| 6 | 1 | function CODE128(string) { |
| 7 | // Fill the bytes variable with the ascii codes of string | |
| 8 | 29 | this.bytes = []; |
| 9 | 29 | for (var i = 0; i < string.length; ++i) { |
| 10 | 232 | this.bytes.push(string.charCodeAt(i)); |
| 11 | } | |
| 12 | ||
| 13 | // First element should be startcode, remove that | |
| 14 | 29 | this.string = string.substring(1); |
| 15 | ||
| 16 | 29 | this.getText = function() { |
| 17 | 19 | var string = this.string; |
| 18 | ||
| 19 | 19 | string = string.replace(String.fromCharCode(201), "[FNC3]"); |
| 20 | 19 | string = string.replace(String.fromCharCode(202), "[FNC2]"); |
| 21 | 19 | string = string.replace(String.fromCharCode(203), "[SHIFT]"); |
| 22 | 19 | string = string.replace(String.fromCharCode(207), "[FNC1]"); |
| 23 | ||
| 24 | 19 | return string.replace(/[^\x20-\x7E]/g, ""); |
| 25 | }; | |
| 26 | ||
| 27 | // The public encoding function | |
| 28 | 29 | this.encoded = function() { |
| 29 | 11 | var encodingResult; |
| 30 | 11 | var bytes = this.bytes; |
| 31 | // Remove the startcode from the bytes and set its index | |
| 32 | 11 | var startIndex = bytes.shift() - 105; |
| 33 | ||
| 34 | // Start encode with the right type | |
| 35 | 11 | if(startIndex === 103){ |
| 36 | 4 | encodingResult = nextA(bytes, 1); |
| 37 | } | |
| 38 | 7 | else if(startIndex === 104){ |
| 39 | 4 | encodingResult = nextB(bytes, 1); |
| 40 | } | |
| 41 | 3 | else if(startIndex === 105){ |
| 42 | 3 | encodingResult = nextC(bytes, 1); |
| 43 | } | |
| 44 | ||
| 45 | 11 | return ( |
| 46 | //Add the start bits | |
| 47 | getEncoding(startIndex) + | |
| 48 | //Add the encoded bits | |
| 49 | encodingResult.result + | |
| 50 | //Add the checksum | |
| 51 | getEncoding((encodingResult.checksum + startIndex) % 103) + | |
| 52 | //Add the end bits | |
| 53 | getEncoding(106) | |
| 54 | ); | |
| 55 | } | |
| 56 | ||
| 57 | //Data for each character, the last characters will not be encoded but are used for error correction | |
| 58 | //Numbers encode to (n + 1000) -> binary; 740 -> (740 + 1000).toString(2) -> "11011001100" | |
| 59 | 29 | var code128b = [ // + 1000 |
| 60 | 740, 644, 638, 176, 164, 100, 224, 220, 124, 608, 604, | |
| 61 | 572, 436, 244, 230, 484, 260, 254, 650, 628, 614, 764, | |
| 62 | 652, 902, 868, 836, 830, 892, 844, 842, 752, 734, 590, | |
| 63 | 304, 112, 94, 416, 128, 122, 672, 576, 570, 464, 422, | |
| 64 | 134, 496, 478, 142, 910, 678, 582, 768, 762, 774, 880, | |
| 65 | 862, 814, 896, 890, 818, 914, 602, 930, 328, 292, 200, | |
| 66 | 158, 68, 62, 424, 412, 232, 218, 76, 74, 554, 616, | |
| 67 | 978, 556, 146, 340, 212, 182, 508, 268, 266, 956, 940, | |
| 68 | 938, 758, 782, 974, 400, 310, 118, 512, 506, 960, 954, | |
| 69 | 502, 518, 886, 966, /* Start codes */ 668, 680, 692, | |
| 70 | 5379 | |
| 71 | ]; | |
| 72 | 29 | var getEncoding = function(n) { |
| 73 | 122 | return (code128b[n] ? (code128b[n] + 1000).toString(2) : ''); |
| 74 | }; | |
| 75 | ||
| 76 | // Use the regexp variable for validation | |
| 77 | 29 | this.valid = function() { |
| 78 | 12 | return !(this.string.search(validCODE128) === -1); |
| 79 | } | |
| 80 | ||
| 81 | 29 | function nextA(bytes, depth){ |
| 82 | 32 | if(bytes.length <= 0){ |
| 83 | 4 | return {"result": "", "checksum": 0}; |
| 84 | } | |
| 85 | ||
| 86 | 28 | var next, index; |
| 87 | ||
| 88 | // Special characters | |
| 89 | 28 | if(bytes[0] >= 200){ |
| 90 | 5 | index = bytes[0] - 105; |
| 91 | ||
| 92 | //Remove first element | |
| 93 | 5 | bytes.shift(); |
| 94 | ||
| 95 | // Swap to CODE128C | |
| 96 | 5 | if(index === 99){ |
| 97 | 1 | next = nextC(bytes, depth + 1); |
| 98 | } | |
| 99 | // Swap to CODE128B | |
| 100 | 4 | else if(index === 100){ |
| 101 | 2 | next = nextB(bytes, depth + 1); |
| 102 | } | |
| 103 | // Shift | |
| 104 | 2 | else if(index === 98){ |
| 105 | // Convert the next character so that is encoded correctly | |
| 106 | 1 | bytes[0] = bytes[0] > 95 ? bytes[0] - 96 : bytes[0]; |
| 107 | 1 | next = nextA(bytes, depth + 1); |
| 108 | } | |
| 109 | // Continue on CODE128A but encode a special character | |
| 110 | else{ | |
| 111 | 1 | next = nextA(bytes, depth + 1); |
| 112 | } | |
| 113 | } | |
| 114 | // Continue encoding of CODE128A | |
| 115 | else{ | |
| 116 | 23 | var charCode = bytes[0]; |
| 117 | 23 | index = charCode < 32 ? charCode + 64 : charCode - 32; |
| 118 | ||
| 119 | // Remove first element | |
| 120 | 23 | bytes.shift(); |
| 121 | ||
| 122 | 23 | next = nextA(bytes, depth + 1); |
| 123 | } | |
| 124 | ||
| 125 | // Get the correct binary encoding and calculate the weight | |
| 126 | 28 | var enc = getEncoding(index); |
| 127 | 28 | var weight = index * depth; |
| 128 | ||
| 129 | 28 | return {"result": enc + next.result, "checksum": weight + next.checksum} |
| 130 | } | |
| 131 | ||
| 132 | 29 | function nextB(bytes, depth){ |
| 133 | 42 | if(bytes.length <= 0){ |
| 134 | 4 | return {"result": "", "checksum": 0}; |
| 135 | } | |
| 136 | ||
| 137 | 38 | var next, index; |
| 138 | ||
| 139 | // Special characters | |
| 140 | 38 | if(bytes[0] >= 200){ |
| 141 | 5 | index = bytes[0] - 105; |
| 142 | ||
| 143 | //Remove first element | |
| 144 | 5 | bytes.shift(); |
| 145 | ||
| 146 | // Swap to CODE128C | |
| 147 | 5 | if(index === 99){ |
| 148 | 2 | next = nextC(bytes, depth + 1); |
| 149 | } | |
| 150 | // Swap to CODE128A | |
| 151 | 3 | else if(index === 101){ |
| 152 | 1 | next = nextA(bytes, depth + 1); |
| 153 | } | |
| 154 | // Shift | |
| 155 | 2 | else if(index === 98){ |
| 156 | // Convert the next character so that is encoded correctly | |
| 157 | 1 | bytes[0] = bytes[0] < 32 ? bytes[0] + 96 : bytes[0]; |
| 158 | 1 | next = nextB(bytes, depth + 1); |
| 159 | } | |
| 160 | // Continue on CODE128B but encode a special character | |
| 161 | else{ | |
| 162 | 1 | next = nextB(bytes, depth + 1); |
| 163 | } | |
| 164 | } | |
| 165 | // Continue encoding of CODE128B | |
| 166 | else { | |
| 167 | 33 | index = bytes[0] - 32; |
| 168 | 33 | bytes.shift(); |
| 169 | 33 | next = nextB(bytes, depth + 1); |
| 170 | } | |
| 171 | ||
| 172 | // Get the correct binary encoding and calculate the weight | |
| 173 | 38 | var enc = getEncoding(index); |
| 174 | 38 | var weight = index * depth; |
| 175 | ||
| 176 | 38 | return {"result": enc + next.result, "checksum": weight + next.checksum}; |
| 177 | } | |
| 178 | ||
| 179 | 29 | function nextC(bytes, depth){ |
| 180 | 26 | if(bytes.length <= 0){ |
| 181 | 3 | return {"result": "", "checksum": 0}; |
| 182 | } | |
| 183 | ||
| 184 | 23 | var next, index; |
| 185 | ||
| 186 | // Special characters | |
| 187 | 23 | if(bytes[0] >= 200){ |
| 188 | 5 | index = bytes[0] - 105; |
| 189 | ||
| 190 | // Remove first element | |
| 191 | 5 | bytes.shift(); |
| 192 | ||
| 193 | // Swap to CODE128B | |
| 194 | 5 | if(index === 100){ |
| 195 | 1 | next = nextB(bytes, depth + 1); |
| 196 | } | |
| 197 | // Swap to CODE128A | |
| 198 | 4 | else if(index === 101){ |
| 199 | 2 | next = nextA(bytes, depth + 1); |
| 200 | } | |
| 201 | // Continue on CODE128C but encode a special character | |
| 202 | else{ | |
| 203 | 2 | next = nextC(bytes, depth + 1); |
| 204 | } | |
| 205 | } | |
| 206 | // Continue encoding of CODE128C | |
| 207 | else{ | |
| 208 | 18 | index = (bytes[0]-48) * 10 + bytes[1]-48; |
| 209 | 18 | bytes.shift(); |
| 210 | 18 | bytes.shift(); |
| 211 | 18 | next = nextC(bytes, depth + 1); |
| 212 | } | |
| 213 | ||
| 214 | // Get the correct binary encoding and calculate the weight | |
| 215 | 23 | var enc = getEncoding(index); |
| 216 | 23 | var weight = index * depth; |
| 217 | ||
| 218 | 23 | return {"result": enc + next.result, "checksum": weight + next.checksum}; |
| 219 | } | |
| 220 | } | |
| 221 | ||
| 222 | 1 | function autoSelectModes(string){ |
| 223 | // ASCII ranges 0-98 and 200-207 (FUNCs and SHIFTs) | |
| 224 | 18 | var aLength = string.match(/^[\x00-\x5F\xC8-\xCF]*/)[0].length; |
| 225 | // ASCII ranges 32-127 and 200-207 (FUNCs and SHIFTs) | |
| 226 | 18 | var bLength = string.match(/^[\x20-\x7F\xC8-\xCF]*/)[0].length; |
| 227 | // Number pairs or [FNC1] | |
| 228 | 18 | var cLength = string.match(/^(\xCF*[0-9]{2}\xCF*)*/)[0].length; |
| 229 | ||
| 230 | 18 | var newString; |
| 231 | // Select CODE128C if the string start with enough digits | |
| 232 | 18 | if(cLength >= 2){ |
| 233 | 2 | newString = String.fromCharCode(210) + autoSelectFromC(string); |
| 234 | } | |
| 235 | // Select A/C depending on the longest match | |
| 236 | 16 | else if(aLength > bLength){ |
| 237 | 3 | newString = String.fromCharCode(208) + autoSelectFromA(string); |
| 238 | } | |
| 239 | else{ | |
| 240 | 13 | newString = String.fromCharCode(209) + autoSelectFromB(string); |
| 241 | } | |
| 242 | ||
| 243 | 18 | newString = newString.replace(/[\xCD\xCE]([^])[\xCD\xCE]/, function(match, char){ |
| 244 | 2 | return String.fromCharCode(203) + char; |
| 245 | }); | |
| 246 | ||
| 247 | 18 | return newString; |
| 248 | } | |
| 249 | ||
| 250 | 1 | function autoSelectFromA(string){ |
| 251 | 8 | var untilC = string.match(/^([\x00-\x5F\xC8-\xCF]+?)(([0-9]{2}){2,})([^0-9]|$)/); |
| 252 | ||
| 253 | 8 | if(untilC){ |
| 254 | 1 | return untilC[1] + String.fromCharCode(204) + autoSelectFromC(string.substring(untilC[1].length)); |
| 255 | } | |
| 256 | ||
| 257 | 7 | var aChars = string.match(/^[\x00-\x5F\xC8-\xCF]+/); |
| 258 | 7 | if(aChars[0].length === string.length){ |
| 259 | 3 | return string; |
| 260 | } | |
| 261 | ||
| 262 | 4 | return aChars[0] + String.fromCharCode(205) + autoSelectFromB(string.substring(aChars[0].length)); |
| 263 | } | |
| 264 | ||
| 265 | 1 | function autoSelectFromB(string){ |
| 266 | 18 | var untilC = string.match(/^([\x20-\x7F\xC8-\xCF]+?)(([0-9]{2}){2,})([^0-9]|$)/); |
| 267 | ||
| 268 | 18 | if(untilC){ |
| 269 | 2 | return untilC[1] + String.fromCharCode(204) + autoSelectFromC(string.substring(untilC[1].length)); |
| 270 | } | |
| 271 | ||
| 272 | 16 | var bChars = string.match(/^[\x20-\x7F\xC8-\xCF]+/); |
| 273 | 16 | if(bChars[0].length === string.length){ |
| 274 | 13 | return string; |
| 275 | } | |
| 276 | ||
| 277 | 3 | return bChars[0] + String.fromCharCode(206) + autoSelectFromA(string.substring(bChars[0].length)); |
| 278 | } | |
| 279 | ||
| 280 | ||
| 281 | 1 | function autoSelectFromC(string){ |
| 282 | 5 | var cMatch = string.match(/^(\xCF*[0-9]{2}\xCF*)+/)[0]; |
| 283 | 5 | var length = cMatch.length; |
| 284 | ||
| 285 | 5 | if(length === string.length){ |
| 286 | 2 | return string; |
| 287 | } | |
| 288 | ||
| 289 | 3 | string = string.substring(length); |
| 290 | ||
| 291 | // Select A/B depending on the longest match | |
| 292 | 3 | var aLength = string.match(/^[\x00-\x5F\xC8-\xCF]*/)[0].length; |
| 293 | 3 | var bLength = string.match(/^[\x20-\x7F\xC8-\xCF]*/)[0].length; |
| 294 | 3 | if(aLength >= bLength){ |
| 295 | 2 | return cMatch + String.fromCharCode(206) + autoSelectFromA(string); |
| 296 | } | |
| 297 | else{ | |
| 298 | 1 | return cMatch + String.fromCharCode(205) + autoSelectFromB(string); |
| 299 | } | |
| 300 | } | |
| 301 | ||
| 302 | 1 | function CODE128AUTO(string) { |
| 303 | // Check the validity of the string, don't even bother auto it when | |
| 304 | //it's not valid | |
| 305 | 19 | if(string.search(validCODE128) !== -1){ |
| 306 | 18 | return new CODE128(autoSelectModes(string)); |
| 307 | } | |
| 308 | 1 | return new CODE128(string); |
| 309 | } | |
| 310 | 1 | function CODE128A(string) { |
| 311 | 3 | var code128 = new CODE128(String.fromCharCode(208) + string); |
| 312 | 3 | code128.valid = function(){ |
| 313 | 2 | return this.string.search(/^[\x00-\x5F\xC8-\xCF]+$/) !== -1; |
| 314 | } | |
| 315 | 3 | return code128; |
| 316 | } | |
| 317 | 1 | function CODE128B(string) { |
| 318 | 3 | var code128 = new CODE128(String.fromCharCode(209) + string); |
| 319 | 3 | code128.valid = function(){ |
| 320 | 2 | return this.string.search(/^[\x20-\x7F\xC8-\xCF]+$/) !== -1; |
| 321 | } | |
| 322 | 3 | return code128; |
| 323 | } | |
| 324 | 1 | function CODE128C(string) { |
| 325 | 4 | var code128 = new CODE128(String.fromCharCode(210) + string); |
| 326 | 4 | code128.valid = function(str){ |
| 327 | 3 | return this.string.search(/^(\xCF*[0-9]{2}\xCF*)+$/) !== -1; |
| 328 | } | |
| 329 | 4 | return code128; |
| 330 | } | |
| 331 | ||
| 332 | //Required to register for both browser and nodejs | |
| 333 | 1 | var register = function(core) { |
| 334 | 1 | core.register(CODE128AUTO, /^CODE128(.?AUTO)?$/, 10); |
| 335 | 1 | core.register(CODE128A, /^CODE128.?A$/i, 2); |
| 336 | 1 | core.register(CODE128B, /^CODE128.?B$/i, 3); |
| 337 | 1 | core.register(CODE128C, /^CODE128.?C$/i, 2); |
| 338 | } | |
| 339 | 2 | try {register(JsBarcode)} catch(e) {} |
| 340 | 2 | try {module.exports.register = register} catch(e) {} |
| 341 |
| Line | Hits | Source |
|---|---|---|
| 1 | 1 | function CODE39(string){ |
| 2 | 9 | this.string = string.toUpperCase(); |
| 3 | ||
| 4 | 9 | var encodings = { |
| 5 | "0": 20957, "1": 29783, "2": 23639, "3": 30485, | |
| 6 | "4": 20951, "5": 29813, "6": 23669, "7": 20855, | |
| 7 | "8": 29789, "9": 23645, "A": 29975, "B": 23831, | |
| 8 | "C": 30533, "D": 22295, "E": 30149, "F": 24005, | |
| 9 | "G": 21623, "H": 29981, "I": 23837, "J": 22301, | |
| 10 | "K": 30023, "L": 23879, "M": 30545, "N": 22343, | |
| 11 | "O": 30161, "P": 24017, "Q": 21959, "R": 30065, | |
| 12 | "S": 23921, "T": 22385, "U": 29015, "V": 18263, | |
| 13 | "W": 29141, "X": 17879, "Y": 29045, "Z": 18293, | |
| 14 | "-": 17783, ".": 29021, " ": 18269, "$": 17477, | |
| 15 | "/": 17489, "+": 17681, "%": 20753, "*": 35770 | |
| 16 | }; | |
| 17 | ||
| 18 | ||
| 19 | 9 | this.getText = function(){ |
| 20 | 9 | return this.string; |
| 21 | }; | |
| 22 | ||
| 23 | 9 | this.encoded = function(){ |
| 24 | 5 | var result = ""; |
| 25 | 5 | result += encodings["*"].toString(2); |
| 26 | 5 | for(var i=0; i<this.string.length; i++){ |
| 27 | 24 | result += encodings[this.string[i]].toString(2) + "0"; |
| 28 | } | |
| 29 | 5 | result += encodings["*"].toString(2); |
| 30 | ||
| 31 | 5 | return result; |
| 32 | }; | |
| 33 | ||
| 34 | //Use the regexp variable for validation | |
| 35 | 9 | this.valid = function(){ |
| 36 | 7 | return this.string.search(/^[0-9A-Z\-\.\ \$\/\+\%]+$/) !== -1; |
| 37 | }; | |
| 38 | } | |
| 39 | ||
| 40 | ||
| 41 | //Required to register for both browser and nodejs | |
| 42 | 1 | var register = function(core){ |
| 43 | 1 | core.register(CODE39, /^CODE.?39$/i, 3); |
| 44 | }; | |
| 45 | 2 | try{register(JsBarcode)} catch(e){} |
| 46 | 2 | try{module.exports.register = register} catch(e){} |
| 47 |
| Line | Hits | Source |
|---|---|---|
| 1 | 1 | function EAN(EANnumber){ |
| 2 | 15 | this.EANnumber = EANnumber+""; |
| 3 | ||
| 4 | //Regexp to test if the EAN code is correct formated | |
| 5 | 15 | var fullEanRegexp = /^[0-9]{13}$/; |
| 6 | 15 | var needLastDigitRegexp = /^[0-9]{12}$/; |
| 7 | ||
| 8 | //Add checksum if it does not exist | |
| 9 | 15 | if(this.EANnumber.search(needLastDigitRegexp)!=-1){ |
| 10 | 2 | this.EANnumber += checksum(this.EANnumber); |
| 11 | } | |
| 12 | ||
| 13 | 15 | this.getText = function(){ |
| 14 | 6 | return this.EANnumber; |
| 15 | }; | |
| 16 | ||
| 17 | 15 | this.valid = function(){ |
| 18 | 12 | return valid(this.EANnumber); |
| 19 | }; | |
| 20 | ||
| 21 | 15 | this.encoded = function (){ |
| 22 | 4 | return createEAN13(this.EANnumber); |
| 23 | } | |
| 24 | ||
| 25 | //Create the binary representation of the EAN code | |
| 26 | //number needs to be a string | |
| 27 | 15 | function createEAN13(number){ |
| 28 | 4 | var encoder = new EANencoder(); |
| 29 | ||
| 30 | //Create the return variable | |
| 31 | 4 | var result = ""; |
| 32 | ||
| 33 | 4 | var structure = encoder.getEANstructure(number); |
| 34 | ||
| 35 | //Get the number to be encoded on the left side of the EAN code | |
| 36 | 4 | var leftSide = number.substr(1,7); |
| 37 | ||
| 38 | //Get the number to be encoded on the right side of the EAN code | |
| 39 | 4 | var rightSide = number.substr(7,6); |
| 40 | ||
| 41 | //Add the start bits | |
| 42 | 4 | result += encoder.startBin; |
| 43 | ||
| 44 | //Add the left side | |
| 45 | 4 | result += encoder.encode(leftSide, structure); |
| 46 | ||
| 47 | //Add the middle bits | |
| 48 | 4 | result += encoder.middleBin; |
| 49 | ||
| 50 | //Add the right side | |
| 51 | 4 | result += encoder.encode(rightSide,"RRRRRR"); |
| 52 | ||
| 53 | //Add the end bits | |
| 54 | 4 | result += encoder.endBin; |
| 55 | ||
| 56 | 4 | return result; |
| 57 | } | |
| 58 | ||
| 59 | //Calulate the checksum digit | |
| 60 | 15 | function checksum(number){ |
| 61 | 6 | var result = 0; |
| 62 | ||
| 63 | 42 | for(var i=0;i<12;i+=2){result+=parseInt(number[i])} |
| 64 | 42 | for(var i=1;i<12;i+=2){result+=parseInt(number[i])*3} |
| 65 | ||
| 66 | 6 | return (10 - (result % 10)) % 10; |
| 67 | } | |
| 68 | ||
| 69 | 15 | function valid(number){ |
| 70 | 12 | if(number.search(fullEanRegexp)!=-1){ |
| 71 | 4 | return number[12] == checksum(number); |
| 72 | } | |
| 73 | else{ | |
| 74 | 8 | return false; |
| 75 | } | |
| 76 | } | |
| 77 | } | |
| 78 | ||
| 79 | 1 | function EAN8(EAN8number){ |
| 80 | 8 | this.EAN8number = EAN8number+""; |
| 81 | ||
| 82 | //Regexp to test if the EAN code is correct formated | |
| 83 | 8 | var fullEanRegexp = /^[0-9]{8}$/; |
| 84 | 8 | var needLastDigitRegexp = /^[0-9]{7}$/; |
| 85 | ||
| 86 | //Add checksum if it does not exist | |
| 87 | 8 | if(this.EAN8number.search(needLastDigitRegexp)!=-1){ |
| 88 | 1 | this.EAN8number += checksum(this.EAN8number); |
| 89 | } | |
| 90 | ||
| 91 | 8 | this.getText = function(){ |
| 92 | 1 | return this.EAN8number; |
| 93 | } | |
| 94 | ||
| 95 | 8 | this.valid = function(){ |
| 96 | 8 | return valid(this.EAN8number); |
| 97 | }; | |
| 98 | ||
| 99 | 8 | this.encoded = function (){ |
| 100 | 2 | return createEAN8(this.EAN8number); |
| 101 | } | |
| 102 | ||
| 103 | 8 | function valid(number){ |
| 104 | 8 | if(number.search(fullEanRegexp)!=-1){ |
| 105 | 3 | return number[7] == checksum(number); |
| 106 | } | |
| 107 | else{ | |
| 108 | 5 | return false; |
| 109 | } | |
| 110 | } | |
| 111 | ||
| 112 | //Calulate the checksum digit | |
| 113 | 8 | function checksum(number){ |
| 114 | 4 | var result = 0; |
| 115 | ||
| 116 | 20 | for(var i=0;i<7;i+=2){result+=parseInt(number[i])*3} |
| 117 | 16 | for(var i=1;i<7;i+=2){result+=parseInt(number[i])} |
| 118 | ||
| 119 | 4 | return (10 - (result % 10)) % 10; |
| 120 | } | |
| 121 | ||
| 122 | 8 | function createEAN8(number){ |
| 123 | 2 | var encoder = new EANencoder(); |
| 124 | ||
| 125 | //Create the return variable | |
| 126 | 2 | var result = ""; |
| 127 | ||
| 128 | //Get the number to be encoded on the left side of the EAN code | |
| 129 | 2 | var leftSide = number.substr(0,4); |
| 130 | ||
| 131 | //Get the number to be encoded on the right side of the EAN code | |
| 132 | 2 | var rightSide = number.substr(4,4); |
| 133 | ||
| 134 | //Add the start bits | |
| 135 | 2 | result += encoder.startBin; |
| 136 | ||
| 137 | //Add the left side | |
| 138 | 2 | result += encoder.encode(leftSide, "LLLL"); |
| 139 | ||
| 140 | //Add the middle bits | |
| 141 | 2 | result += encoder.middleBin; |
| 142 | ||
| 143 | //Add the right side | |
| 144 | 2 | result += encoder.encode(rightSide,"RRRR"); |
| 145 | ||
| 146 | //Add the end bits | |
| 147 | 2 | result += encoder.endBin; |
| 148 | ||
| 149 | 2 | return result; |
| 150 | } | |
| 151 | } | |
| 152 | ||
| 153 | ||
| 154 | 1 | function UPC(UPCnumber){ |
| 155 | 6 | this.ean = new EAN("0"+UPCnumber); |
| 156 | ||
| 157 | 6 | this.getText = function(){ |
| 158 | 1 | return this.ean.getText().substring(1); |
| 159 | } | |
| 160 | ||
| 161 | 6 | this.valid = function(){ |
| 162 | 4 | return this.ean.valid(); |
| 163 | } | |
| 164 | ||
| 165 | 6 | this.encoded = function(){ |
| 166 | 1 | return this.ean.encoded(); |
| 167 | } | |
| 168 | ||
| 169 | } | |
| 170 | ||
| 171 | // | |
| 172 | // Help class that does all the encoding | |
| 173 | // | |
| 174 | 1 | function EANencoder(){ |
| 175 | //The start bits | |
| 176 | 6 | this.startBin = "101"; |
| 177 | //The end bits | |
| 178 | 6 | this.endBin = "101"; |
| 179 | //The middle bits | |
| 180 | 6 | this.middleBin = "01010"; |
| 181 | ||
| 182 | //The L (left) type of encoding | |
| 183 | 6 | var Lbinary = { |
| 184 | 0: "0001101", | |
| 185 | 1: "0011001", | |
| 186 | 2: "0010011", | |
| 187 | 3: "0111101", | |
| 188 | 4: "0100011", | |
| 189 | 5: "0110001", | |
| 190 | 6: "0101111", | |
| 191 | 7: "0111011", | |
| 192 | 8: "0110111", | |
| 193 | 9: "0001011"}; | |
| 194 | ||
| 195 | //The G type of encoding | |
| 196 | 6 | var Gbinary = { |
| 197 | 0: "0100111", | |
| 198 | 1: "0110011", | |
| 199 | 2: "0011011", | |
| 200 | 3: "0100001", | |
| 201 | 4: "0011101", | |
| 202 | 5: "0111001", | |
| 203 | 6: "0000101", | |
| 204 | 7: "0010001", | |
| 205 | 8: "0001001", | |
| 206 | 9: "0010111"}; | |
| 207 | ||
| 208 | //The R (right) type of encoding | |
| 209 | 6 | var Rbinary = { |
| 210 | 0: "1110010", | |
| 211 | 1: "1100110", | |
| 212 | 2: "1101100", | |
| 213 | 3: "1000010", | |
| 214 | 4: "1011100", | |
| 215 | 5: "1001110", | |
| 216 | 6: "1010000", | |
| 217 | 7: "1000100", | |
| 218 | 8: "1001000", | |
| 219 | 9: "1110100"}; | |
| 220 | ||
| 221 | //The left side structure in EAN-13 | |
| 222 | 6 | var EANstructure = { |
| 223 | 0: "LLLLLL", | |
| 224 | 1: "LLGLGG", | |
| 225 | 2: "LLGGLG", | |
| 226 | 3: "LLGGGL", | |
| 227 | 4: "LGLLGG", | |
| 228 | 5: "LGGLLG", | |
| 229 | 6: "LGGGLL", | |
| 230 | 7: "LGLGLG", | |
| 231 | 8: "LGLGGL", | |
| 232 | 9: "LGGLGL"} | |
| 233 | ||
| 234 | 6 | this.getEANstructure = function(number){ |
| 235 | 4 | return EANstructure[number[0]]; |
| 236 | }; | |
| 237 | ||
| 238 | //Convert a numberarray to the representing | |
| 239 | 6 | this.encode = function(number,structure){ |
| 240 | //Create the variable that should be returned at the end of the function | |
| 241 | 12 | var result = ""; |
| 242 | ||
| 243 | //Loop all the numbers | |
| 244 | 12 | for(var i = 0;i<number.length;i++){ |
| 245 | //Using the L, G or R encoding and add it to the returning variable | |
| 246 | 68 | if(structure[i]=="L"){ |
| 247 | 23 | result += Lbinary[number[i]]; |
| 248 | } | |
| 249 | 45 | else if(structure[i]=="G"){ |
| 250 | 9 | result += Gbinary[number[i]]; |
| 251 | } | |
| 252 | 36 | else if(structure[i]=="R"){ |
| 253 | 32 | result += Rbinary[number[i]]; |
| 254 | } | |
| 255 | } | |
| 256 | 12 | return result; |
| 257 | }; | |
| 258 | } | |
| 259 | ||
| 260 | ||
| 261 | //Required to register for both browser and nodejs | |
| 262 | 1 | var register = function(core){ |
| 263 | 1 | core.register(EAN, /^EAN(.?13)?$/i, 8); |
| 264 | 1 | core.register(EAN8, /^EAN.?8$/i, 8); |
| 265 | 1 | core.register(UPC, /^UPC(.?A)?$/i, 8); |
| 266 | } | |
| 267 | 2 | try{register(JsBarcode)} catch(e){} |
| 268 | 2 | try{module.exports.register = register} catch(e){} |
| 269 |
| Line | Hits | Source |
|---|---|---|
| 1 | 1 | function ITF(ITFNumber){ |
| 2 | ||
| 3 | 6 | this.ITFNumber = ITFNumber+""; |
| 4 | ||
| 5 | 6 | this.getText = function(){ |
| 6 | 1 | return this.ITFNumber; |
| 7 | }; | |
| 8 | ||
| 9 | 6 | this.valid = function(){ |
| 10 | 4 | return valid(this.ITFNumber); |
| 11 | }; | |
| 12 | ||
| 13 | 6 | this.encoded = function(){ |
| 14 | //Create the variable that should be returned at the end of the function | |
| 15 | 1 | var result = ""; |
| 16 | ||
| 17 | //Always add the same start bits | |
| 18 | 1 | result += startBin; |
| 19 | ||
| 20 | //Calculate all the digit pairs | |
| 21 | 1 | for(var i=0;i<this.ITFNumber.length;i+=2){ |
| 22 | 3 | result += calculatePair(this.ITFNumber.substr(i,2)); |
| 23 | } | |
| 24 | ||
| 25 | //Always add the same end bits | |
| 26 | 1 | result += endBin; |
| 27 | ||
| 28 | 1 | return result; |
| 29 | } | |
| 30 | ||
| 31 | //The structure for the all digits, 1 is wide and 0 is narrow | |
| 32 | 6 | var digitStructure = { |
| 33 | "0":"00110" | |
| 34 | ,"1":"10001" | |
| 35 | ,"2":"01001" | |
| 36 | ,"3":"11000" | |
| 37 | ,"4":"00101" | |
| 38 | ,"5":"10100" | |
| 39 | ,"6":"01100" | |
| 40 | ,"7":"00011" | |
| 41 | ,"8":"10010" | |
| 42 | ,"9":"01010"} | |
| 43 | ||
| 44 | //The start bits | |
| 45 | 6 | var startBin = "1010"; |
| 46 | //The end bits | |
| 47 | 6 | var endBin = "11101"; |
| 48 | ||
| 49 | //Regexp for a valid Inter25 code | |
| 50 | 6 | var regexp = /^([0-9][0-9])+$/; |
| 51 | ||
| 52 | //Calculate the data of a number pair | |
| 53 | 6 | function calculatePair(twoNumbers){ |
| 54 | 3 | var result = ""; |
| 55 | ||
| 56 | 3 | var number1Struct = digitStructure[twoNumbers[0]]; |
| 57 | 3 | var number2Struct = digitStructure[twoNumbers[1]]; |
| 58 | ||
| 59 | //Take every second bit and add to the result | |
| 60 | 3 | for(var i=0;i<5;i++){ |
| 61 | 15 | result += (number1Struct[i]=="1") ? "111" : "1"; |
| 62 | 15 | result += (number2Struct[i]=="1") ? "000" : "0"; |
| 63 | } | |
| 64 | 3 | return result; |
| 65 | } | |
| 66 | ||
| 67 | 6 | function valid(number){ |
| 68 | 4 | return number.search(regexp)!==-1; |
| 69 | } | |
| 70 | } | |
| 71 | ||
| 72 | //Required to register for both browser and nodejs | |
| 73 | 1 | var register = function(core){ |
| 74 | 1 | core.register(ITF, /^ITF$/i, 4); |
| 75 | }; | |
| 76 | 2 | try{register(JsBarcode)} catch(e){} |
| 77 | 2 | try{module.exports.register = register} catch(e){} |
| 78 |
| Line | Hits | Source |
|---|---|---|
| 1 | 1 | function ITF14(string){ |
| 2 | 9 | this.string = string+""; |
| 3 | } | |
| 4 | ||
| 5 | 1 | ITF14.prototype.getText = function(){ |
| 6 | 1 | return this.string; |
| 7 | }; | |
| 8 | ||
| 9 | 1 | ITF14.prototype.valid = function(){ |
| 10 | 6 | return valid(this.string); |
| 11 | }; | |
| 12 | ||
| 13 | 1 | ITF14.prototype.encoded = function(){ |
| 14 | //Create the variable that should be returned at the end of the function | |
| 15 | 2 | var result = ""; |
| 16 | ||
| 17 | //If checksum is not already calculated, do it | |
| 18 | 2 | if(this.string.length == 13){ |
| 19 | 1 | this.string += checksum(this.string); |
| 20 | } | |
| 21 | ||
| 22 | //Always add the same start bits | |
| 23 | 2 | result += startBin; |
| 24 | ||
| 25 | //Calculate all the digit pairs | |
| 26 | 2 | for(var i=0;i<14;i+=2){ |
| 27 | 14 | result += calculatePair(this.string.substr(i,2)); |
| 28 | } | |
| 29 | ||
| 30 | //Always add the same end bits | |
| 31 | 2 | result += endBin; |
| 32 | ||
| 33 | 2 | return result; |
| 34 | }; | |
| 35 | ||
| 36 | //The structure for the all digits, 1 is wide and 0 is narrow | |
| 37 | 1 | var digitStructure = { |
| 38 | "0":"00110" | |
| 39 | ,"1":"10001" | |
| 40 | ,"2":"01001" | |
| 41 | ,"3":"11000" | |
| 42 | ,"4":"00101" | |
| 43 | ,"5":"10100" | |
| 44 | ,"6":"01100" | |
| 45 | ,"7":"00011" | |
| 46 | ,"8":"10010" | |
| 47 | ,"9":"01010"} | |
| 48 | ||
| 49 | //The start bits | |
| 50 | 1 | var startBin = "1010"; |
| 51 | //The end bits | |
| 52 | 1 | var endBin = "11101"; |
| 53 | ||
| 54 | //Regexp for a valid ITF14 code | |
| 55 | 1 | var regexp = /^[0-9]{13,14}$/; |
| 56 | ||
| 57 | //Calculate the data of a number pair | |
| 58 | 1 | function calculatePair(twoNumbers){ |
| 59 | 14 | var result = ""; |
| 60 | ||
| 61 | 14 | var number1Struct = digitStructure[twoNumbers[0]]; |
| 62 | 14 | var number2Struct = digitStructure[twoNumbers[1]]; |
| 63 | ||
| 64 | //Take every second bit and add to the result | |
| 65 | 14 | for(var i=0;i<5;i++){ |
| 66 | 70 | result += (number1Struct[i]=="1") ? "111" : "1"; |
| 67 | 70 | result += (number2Struct[i]=="1") ? "000" : "0"; |
| 68 | } | |
| 69 | 14 | return result; |
| 70 | } | |
| 71 | ||
| 72 | //Calulate the checksum digit | |
| 73 | 1 | function checksum(numberString){ |
| 74 | 3 | var result = 0; |
| 75 | ||
| 76 | 42 | for(var i=0;i<13;i++){result+=parseInt(numberString[i])*(3-(i%2)*2)} |
| 77 | ||
| 78 | 3 | return 10 - (result % 10); |
| 79 | } | |
| 80 | ||
| 81 | 1 | function valid(number){ |
| 82 | 6 | if(number.search(regexp)==-1){ |
| 83 | 3 | return false; |
| 84 | } | |
| 85 | //Check checksum if it is already calculated | |
| 86 | 3 | else if(number.length==14){ |
| 87 | 2 | return number[13] == checksum(number); |
| 88 | } | |
| 89 | 1 | return true; |
| 90 | } | |
| 91 | ||
| 92 | //Required to register for both browser and nodejs | |
| 93 | 1 | var register = function(core){ |
| 94 | 1 | core.register(ITF14, /^ITF.?14$/i, 5); |
| 95 | } | |
| 96 | 2 | try{register(JsBarcode)} catch(e){} |
| 97 | 2 | try{module.exports.register = register} catch(e){} |
| 98 |
| Line | Hits | Source |
|---|---|---|
| 1 | 1 | var prototype = {}; |
| 2 | ||
| 3 | 1 | prototype.getText = function(){ |
| 4 | 11 | return this.string; |
| 5 | }; | |
| 6 | ||
| 7 | 1 | prototype.encoded = function(){ |
| 8 | 2 | var ret = "110"; |
| 9 | ||
| 10 | 2 | for(var i=0;i<this.string.length;i++){ |
| 11 | 16 | var digit = parseInt(this.string[i]); |
| 12 | 16 | var bin = digit.toString(2); |
| 13 | 16 | bin = addZeroes(bin, 4-bin.length); |
| 14 | 16 | for(var b=0;b<bin.length;b++){ |
| 15 | 64 | ret += bin[b]==0 ? "100" : "110"; |
| 16 | } | |
| 17 | } | |
| 18 | ||
| 19 | 2 | ret += "1001"; |
| 20 | 2 | return ret; |
| 21 | }; | |
| 22 | ||
| 23 | 1 | prototype.valid = function(){ |
| 24 | 7 | return this.string.search(/^[0-9]+$/) != -1; |
| 25 | }; | |
| 26 | ||
| 27 | 1 | function MSI(string){ |
| 28 | 5 | this.string = ""+string; |
| 29 | } | |
| 30 | ||
| 31 | 1 | MSI.prototype = Object.create(prototype); |
| 32 | ||
| 33 | 1 | function MSI10(string){ |
| 34 | 3 | this.string = ""+string; |
| 35 | 3 | this.string += mod10(this.string); |
| 36 | } | |
| 37 | 1 | MSI10.prototype = Object.create(prototype); |
| 38 | ||
| 39 | 1 | function MSI11(string){ |
| 40 | 4 | this.string = "" + string; |
| 41 | 4 | this.string += mod11(this.string); |
| 42 | } | |
| 43 | 1 | MSI11.prototype = Object.create(prototype); |
| 44 | ||
| 45 | 1 | function MSI1010(string){ |
| 46 | 2 | this.string = "" + string; |
| 47 | 2 | this.string += mod10(this.string); |
| 48 | 2 | this.string += mod10(this.string); |
| 49 | } | |
| 50 | 1 | MSI1010.prototype = Object.create(prototype); |
| 51 | ||
| 52 | 1 | function MSI1110(string){ |
| 53 | 2 | this.string = "" + string; |
| 54 | 2 | this.string += mod11(this.string); |
| 55 | 2 | this.string += mod10(this.string); |
| 56 | } | |
| 57 | 1 | MSI1110.prototype = Object.create(prototype); |
| 58 | ||
| 59 | 1 | function mod10(number){ |
| 60 | 9 | var sum = 0; |
| 61 | 9 | for(var i=0;i<number.length;i++){ |
| 62 | 54 | var n = parseInt(number[i]); |
| 63 | 54 | if((i + number.length) % 2 == 0){ |
| 64 | 24 | sum += n; |
| 65 | } | |
| 66 | else{ | |
| 67 | 30 | sum += (n*2)%10 + Math.floor((n*2)/10) |
| 68 | } | |
| 69 | } | |
| 70 | 9 | return (10-(sum%10))%10; |
| 71 | } | |
| 72 | ||
| 73 | 1 | function mod11(number){ |
| 74 | 6 | var sum = 0; |
| 75 | 6 | var weights = [2,3,4,5,6,7]; |
| 76 | 6 | for(var i=0;i<number.length;i++){ |
| 77 | 46 | var n = parseInt(number[number.length-1-i]); |
| 78 | 46 | sum += weights[i % weights.length] * n; |
| 79 | } | |
| 80 | 6 | return (11-(sum%11))%11; |
| 81 | } | |
| 82 | ||
| 83 | 1 | function addZeroes(number, n){ |
| 84 | 16 | for(var i=0;i<n;i++){ |
| 85 | 24 | number = "0"+number; |
| 86 | } | |
| 87 | 16 | return number; |
| 88 | } | |
| 89 | ||
| 90 | //Required to register for both browser and nodejs | |
| 91 | 1 | var register = function(core){ |
| 92 | 1 | core.register(MSI, /^MSI$/i, 4); |
| 93 | 1 | core.register(MSI10, /^MSI.?10$/i); |
| 94 | 1 | core.register(MSI11, /^MSI.?11$/i); |
| 95 | 1 | core.register(MSI1010, /^MSI.?1010$/i); |
| 96 | 1 | core.register(MSI1110, /^MSI.?1110$/i); |
| 97 | } | |
| 98 | 2 | try{register(JsBarcode)} catch(e){} |
| 99 | 2 | try{module.exports.register = register} catch(e){} |
| 100 |
| Line | Hits | Source |
|---|---|---|
| 1 | 1 | function pharmacode(number){ |
| 2 | //Ensure that the input is inturpreted as a number | |
| 3 | 6 | this.number = parseInt(number); |
| 4 | ||
| 5 | 6 | this.getText = function(){ |
| 6 | 1 | return this.number + ""; |
| 7 | }; | |
| 8 | ||
| 9 | 6 | function recursiveEncoding(code,state){ |
| 10 | //End condition | |
| 11 | 21 | if(code.length == 0) return ""; |
| 12 | ||
| 13 | 15 | var generated; |
| 14 | 15 | var nextState = false; |
| 15 | 15 | var nZeros = zeros(code); |
| 16 | 15 | if(nZeros == 0){ |
| 17 | 7 | generated = state ? "001" : "00111"; |
| 18 | 7 | nextState = state; |
| 19 | } | |
| 20 | else{ | |
| 21 | 8 | generated = "001".repeat(nZeros - (state ? 1 : 0)); |
| 22 | 8 | generated += "00111"; |
| 23 | } | |
| 24 | 15 | return recursiveEncoding(code.substr(0,code.length - nZeros - 1),nextState) + generated; |
| 25 | }; | |
| 26 | ||
| 27 | 6 | this.encoded = function(){ |
| 28 | 3 | return recursiveEncoding(this.number.toString(2),true).substr(2); |
| 29 | }; | |
| 30 | ||
| 31 | 6 | this.valid = function(){ |
| 32 | 2 | return this.number >= 3 && this.number <= 131070; |
| 33 | }; | |
| 34 | ||
| 35 | //A help function to calculate the zeros at the end of a string (the code) | |
| 36 | 6 | var zeros = function(code){ |
| 37 | 15 | var i = code.length - 1; |
| 38 | 15 | var zeros = 0; |
| 39 | 15 | while(code[i]=="0" || i<0){ |
| 40 | 13 | zeros++; |
| 41 | 13 | i--; |
| 42 | } | |
| 43 | 15 | return zeros; |
| 44 | }; | |
| 45 | ||
| 46 | //http://stackoverflow.com/a/202627 | |
| 47 | 6 | String.prototype.repeat = function( num ) |
| 48 | { | |
| 49 | 8 | return new Array( num + 1 ).join( this ); |
| 50 | } | |
| 51 | }; | |
| 52 | ||
| 53 | //Required to register for both browser and nodejs | |
| 54 | 1 | var register = function(core){ |
| 55 | 1 | core.register(pharmacode, /^pharmacode$/i, 2); |
| 56 | } | |
| 57 | 2 | try{register(JsBarcode)} catch(e){} |
| 58 | 2 | try{module.exports.register = register} catch(e){} |
| 59 |