├── .babelrc ├── .codebeatignore ├── .editorconfig ├── .github ├── FUNDING.yml ├── ISSUE_TEMPLATE │ ├── bug_report.md │ └── feature_request.md ├── PULL_REQUEST_TEMPLATE.md ├── main.workflow └── workflows │ ├── nodejs.yml │ └── npmpublish.yml ├── .gitignore ├── .prettierrc ├── .travis.yml ├── LICENSE ├── README.md ├── docs ├── assets │ ├── css │ │ └── main.css │ ├── images │ │ ├── icons.png │ │ ├── icons@2x.png │ │ ├── widgets.png │ │ └── widgets@2x.png │ └── js │ │ ├── main.js │ │ └── search.js ├── index.html └── modules.html ├── index.html ├── jest.config.js ├── nodemon.json ├── package-lock.json ├── package.json ├── renovate.json ├── rollup.config.ts ├── src ├── .eslintrc.json ├── codabar │ └── index.ts ├── code-128 │ └── index.ts ├── code-39 │ └── index.ts ├── code-93 │ └── index.ts ├── code2of5 │ └── index.ts ├── ean │ └── index.ts ├── index.ts └── utilities │ ├── BARCODE_DECODERS.ts │ ├── ImageDataLike.ts │ ├── adaptiveThreshold.ts │ ├── combineAllPossible.ts │ ├── createImageData.ts │ ├── getImageDataFromSource.ts │ ├── getLines.ts │ └── isUrl.ts ├── test ├── .eslintrc.json ├── index.test.ts └── sample-images │ ├── 33c64780-a9c0-e92a-820c-fae7011c11e2.gif │ ├── 33c64780-a9c0-e92a-820c-fae7011c11e2.png │ ├── 65794755-0f1bd580-e126-11e9-8918-24618efdc76c.png │ ├── L89HE1806005080432.gif │ ├── L89HE1806005080432.png │ ├── codabar.jpg │ ├── code-128-000.jpg │ ├── code-128-3107cde3-d1ff-0f93-a215-4109753c0c9e.png │ ├── code-128-eeb00f0c-0c7e-a937-1794-25685779ba0c.png │ ├── code-128-no-padding.jpg │ ├── code-128.jpg │ ├── code-2of5-interleaved.jpg │ ├── code-2of5.jpg │ ├── code-39.jpg │ ├── code-93-no-padding.jpg │ ├── code-93.jpg │ ├── ean-13-5901234123457.png │ ├── ean-13.jpg │ ├── ean-8.jpg │ ├── empty.jpg │ ├── medianFilterTest.png │ ├── small-padding.png │ └── small.png ├── tools ├── gh-pages-publish.ts ├── semantic-release-prepare.ts └── tmp.ts ├── tsconfig.json ├── typedoc.json └── yarn.lock /.babelrc: -------------------------------------------------------------------------------- 1 | { 2 | "presets": [ 3 | [ 4 | "@babel/preset-env", 5 | { 6 | "useBuiltIns": "usage", 7 | "corejs": 3 8 | } 9 | ] 10 | ] 11 | } 12 | -------------------------------------------------------------------------------- /.codebeatignore: -------------------------------------------------------------------------------- 1 | docs/** 2 | tools/** 3 | -------------------------------------------------------------------------------- /.editorconfig: -------------------------------------------------------------------------------- 1 | #root = true 2 | 3 | [*] 4 | indent_style = space 5 | end_of_line = lf 6 | charset = utf-8 7 | trim_trailing_whitespace = true 8 | insert_final_newline = true 9 | max_line_length = 100 10 | indent_size = 2 11 | 12 | [*.md] 13 | trim_trailing_whitespace = false 14 | -------------------------------------------------------------------------------- /.github/FUNDING.yml: -------------------------------------------------------------------------------- 1 | # These are supported funding model platforms 2 | 3 | github: mubaidr 4 | patreon: mubaidr 5 | open_collective: mubaidr 6 | ko_fi: # Replace with a single Ko-fi username 7 | tidelift: # Replace with a single Tidelift platform-name/package-name e.g., npm/babel 8 | community_bridge: # Replace with a single Community Bridge project-name e.g., cloud-foundry 9 | liberapay: # Replace with a single Liberapay username 10 | issuehunt: mubaidr 11 | otechie: # Replace with a single Otechie username 12 | custom: # Replace with a single custom sponsorship URL 13 | -------------------------------------------------------------------------------- /.github/ISSUE_TEMPLATE/bug_report.md: -------------------------------------------------------------------------------- 1 | --- 2 | name: Bug report 3 | about: Create a report to help us improve 4 | title: '' 5 | labels: bug 6 | assignees: mubaidr 7 | 8 | --- 9 | 10 | **Describe the bug** 11 | A clear and concise description of what the bug is. 12 | 13 | **To Reproduce** 14 | Steps to reproduce the behavior: 15 | 16 | **Expected behavior** 17 | A clear and concise description of what you expected to happen. 18 | 19 | **Screenshots** 20 | If applicable, add screenshots to help explain your problem. 21 | 22 | **Desktop (please complete the following information):** 23 | - Node Or Browser version [e.g. 10] 24 | - Library version [e.g. 22] 25 | 26 | **Additional context** 27 | Add any other context about the problem here. 28 | -------------------------------------------------------------------------------- /.github/ISSUE_TEMPLATE/feature_request.md: -------------------------------------------------------------------------------- 1 | --- 2 | name: Feature request 3 | about: Suggest an idea for this project 4 | title: '' 5 | labels: enhancement 6 | assignees: mubaidr 7 | 8 | --- 9 | 10 | **Is your feature request related to a problem? Please describe.** 11 | A clear and concise description of what the problem is. Ex. I'm always frustrated when [...] 12 | 13 | **Describe the solution you'd like** 14 | A clear and concise description of what you want to happen. 15 | 16 | **Describe alternatives you've considered** 17 | A clear and concise description of any alternative solutions or features you've considered. 18 | 19 | **Additional context** 20 | Add any other context or screenshots about the feature request here. 21 | -------------------------------------------------------------------------------- /.github/PULL_REQUEST_TEMPLATE.md: -------------------------------------------------------------------------------- 1 | # Description 2 | 3 | Please include a summary of the change and which issue is fixed. 4 | 5 | Fixes # (issue) 6 | 7 | ## Type of change 8 | 9 | Please delete options that are not relevant. 10 | 11 | - [ ] Bug fix (non-breaking change which fixes an issue) 12 | - [ ] New feature (non-breaking change which adds functionality) 13 | - [ ] Breaking change (fix or feature that would cause existing functionality to not work as expected) 14 | - [ ] This change requires a documentation update 15 | 16 | # How Has This Been Tested? 17 | 18 | Please describe the tests that you ran to verify your changes. Provide instructions so we can reproduce. Please also list any relevant details for your test configuration 19 | 20 | - [ ] Test A 21 | - [ ] Test B 22 | 23 | # Checklist: 24 | 25 | - [ ] My code follows the style guidelines of this project 26 | - [ ] I have performed a self-review of my own code 27 | - [ ] I have commented my code, particularly in hard-to-understand areas 28 | - [ ] I have made corresponding changes to the documentation 29 | - [ ] My changes generate no new warnings 30 | - [ ] I have added tests that prove my fix is effective or that my feature works 31 | - [ ] New and existing unit tests pass locally with my changes 32 | - [ ] Any dependent changes have been merged and published in downstream modules 33 | -------------------------------------------------------------------------------- /.github/main.workflow: -------------------------------------------------------------------------------- 1 | workflow "New workflow" { 2 | on = "push" 3 | resolves = ["GitHub Action for npm-2"] 4 | } 5 | 6 | action "GitHub Action for npm" { 7 | uses = "actions/npm@e7aaefe" 8 | runs = "npm install" 9 | } 10 | 11 | action "GitHub Action for npm-1" { 12 | uses = "actions/npm@e7aaefe" 13 | needs = ["GitHub Action for npm"] 14 | runs = "npm run test" 15 | } 16 | 17 | action "GitHub Action for npm-2" { 18 | uses = "actions/npm@e7aaefe" 19 | needs = ["GitHub Action for npm-1"] 20 | runs = "npm run build" 21 | } 22 | -------------------------------------------------------------------------------- /.github/workflows/nodejs.yml: -------------------------------------------------------------------------------- 1 | name: Node CI 2 | 3 | on: [push] 4 | 5 | jobs: 6 | build: 7 | 8 | runs-on: ubuntu-latest 9 | 10 | strategy: 11 | matrix: 12 | node-version: [20.x] 13 | 14 | steps: 15 | - uses: actions/checkout@v1 16 | - name: Use Node.js ${{ matrix.node-version }} 17 | uses: actions/setup-node@v1 18 | with: 19 | node-version: ${{ matrix.node-version }} 20 | - name: npm install, build, and test 21 | run: | 22 | npm install 23 | npm run build --if-present 24 | npm test 25 | -------------------------------------------------------------------------------- /.github/workflows/npmpublish.yml: -------------------------------------------------------------------------------- 1 | name: Node.js Package 2 | 3 | on: 4 | release: 5 | types: [created] 6 | 7 | jobs: 8 | build: 9 | runs-on: ubuntu-latest 10 | steps: 11 | - uses: actions/checkout@v1 12 | - uses: actions/setup-node@v1 13 | with: 14 | node-version: 20 15 | - run: npm ci 16 | - run: npm test 17 | 18 | publish-npm: 19 | needs: build 20 | runs-on: ubuntu-latest 21 | steps: 22 | - uses: actions/checkout@v1 23 | - uses: actions/setup-node@v1 24 | with: 25 | node-version: 20 26 | registry-url: https://registry.npmjs.org/ 27 | - run: npm ci 28 | - run: npm publish 29 | env: 30 | NODE_AUTH_TOKEN: ${{secrets.npm_token}} 31 | 32 | publish-gpr: 33 | needs: build 34 | runs-on: ubuntu-latest 35 | steps: 36 | - uses: actions/checkout@v1 37 | - uses: actions/setup-node@v1 38 | with: 39 | node-version: 20 40 | registry-url: https://npm.pkg.github.com/ 41 | scope: '@mubaidr' 42 | - run: npm ci 43 | - run: npm publish 44 | env: 45 | NODE_AUTH_TOKEN: ${{secrets.GITHUB_TOKEN}} 46 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | node_modules 2 | coverage 3 | .nyc_output 4 | .DS_Store 5 | *.log 6 | .vscode 7 | .idea 8 | dist 9 | compiled 10 | .awcache 11 | .rpt2_cache 12 | tmp/** 13 | -------------------------------------------------------------------------------- /.prettierrc: -------------------------------------------------------------------------------- 1 | { 2 | "semi": false, 3 | "singleQuote": true, 4 | "tabWidth": 2, 5 | "trailingComma": "es5", 6 | "useTabs": false 7 | } 8 | -------------------------------------------------------------------------------- /.travis.yml: -------------------------------------------------------------------------------- 1 | language: node_js 2 | cache: 3 | directories: 4 | - ~/.npm 5 | node_js: 6 | - '12' 7 | - '10' 8 | - '8' 9 | script: 10 | - npm run test:prod && npm run build 11 | - npm install codecov -g 12 | after_success: 13 | - npm run report-coverage 14 | - codecov 15 | - if [ "$TRAVIS_BRANCH" = "master" -a "$TRAVIS_PULL_REQUEST" = "false" ]; then npm run deploy-docs; fi 16 | - if [ "$TRAVIS_BRANCH" = "master" -a "$TRAVIS_PULL_REQUEST" = "false" ]; then npm run semantic-release; fi 17 | branches: 18 | except: 19 | - /^v\d+\.\d+\.\d+$/ 20 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | Copyright 2017 Muhammad Ubaid Raza 2 | 3 | Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: 4 | 5 | The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. 6 | 7 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 8 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # Javascript-Barcode-Reader 2 | 3 | Simple & Fast Barcode decoder for Browsers and Node.js capapable of reading Code128 (UCC/EAN-128), Code93, Code39, Standard/Industrial 2 of 5, Interleaved 2 of 5, Codabar and EAN-13 barcodes. 4 | 5 | [![Build Status](https://travis-ci.org/mubaidr/Javascript-Barcode-Reader.svg?branch=master)](https://travis-ci.org/mubaidr/Javascript-Barcode-Reader) 6 | [![codebeat badge](https://codebeat.co/badges/8f27170b-909e-489f-ae93-459664c47422)](https://codebeat.co/projects/github-com-mubaidr-javascript-barcode-reader-master) 7 | [![codecov](https://codecov.io/gh/mubaidr/Javascript-Barcode-Reader/branch/master/graph/badge.svg)](https://codecov.io/gh/mubaidr/Javascript-Barcode-Reader) 8 | [![All Contributors](https://img.shields.io/badge/all_contributors-1-orange.svg?style=flat-square)](#contributors) 9 | [![Rate on Openbase](https://badges.openbase.com/js/rating/javascript-barcode-reader.svg)](https://openbase.com/js/javascript-barcode-reader?utm_source=embedded&utm_medium=badge&utm_campaign=rate-badge) 10 | 11 | [![NPM](https://nodei.co/npm/javascript-barcode-reader.png)](https://nodei.co/npm/javascript-barcode-reader/) 12 | 13 | 14 | 15 | 16 | 17 | ## Try now 18 | 19 | https://codesandbox.io/s/javascript-barcode-reader-liium 20 | 21 | ## Available decoders 22 | 23 | - EAN-13 24 | - EAN-8 25 | - Code-39 26 | - Code-93 27 | - Code-2of5 28 | - standard 29 | - Interleaved 30 | - Codabar 31 | - Code-128 (UCC/EAN-128) 32 | 33 | ## How to use 34 | 35 | ### Install 36 | 37 | Recommended way to install is by using package manager (npm, yarn etc): 38 | 39 | ```bash 40 | npm i javascript-barcode-reader 41 | ``` 42 | 43 | or use cdn: 44 | 45 | ```html 46 | 47 | ``` 48 | 49 | or download manually: 50 | 51 | [javascript-barcode-reader](https://unpkg.com/javascript-barcode-reader) 52 | 53 | ### Node.js 54 | 55 | ```ts 56 | import javascriptBarcodeReader from 'javascript-barcode-reader' 57 | 58 | javascriptBarcodeReader({ 59 | /* Image file Path || {data: Uint8ClampedArray, width, height} || HTML5 Canvas ImageData */ 60 | image: source, 61 | barcode: 'code-2of5', 62 | // barcodeType: 'industrial', 63 | options: { 64 | // useAdaptiveThreshold: true // for images with shaded/ gradient portions 65 | // singlePass: true 66 | } 67 | }) 68 | .then(code => { 69 | console.log(code) 70 | }) 71 | .catch(err => { 72 | console.log(err) 73 | }) 74 | ``` 75 | 76 | ### Browser 77 | 78 | `javascriptBarcodeReader` will be available as global in Browsers. 79 | 80 | ```js 81 | javascriptBarcodeReader({ 82 | /* Image ID || HTML5 Image || HTML5 Canvas || HTML5 Canvas ImageData || Image URL */ 83 | image: source, 84 | barcode: 'code-2of5', 85 | // barcodeType: 'industrial', 86 | options: { 87 | // useAdaptiveThreshold: true // for images with shaded/ gradient portions 88 | // singlePass: true 89 | } 90 | }) 91 | .then(code => { 92 | console.log(code) 93 | }) 94 | .catch(err => { 95 | console.log(err) 96 | }) 97 | ``` 98 | 99 | ## Note 100 | 101 | - This script does not implement logic to locate/rotate barcode in the given image. 102 | - Make sure the barcode image is the only thing in the image. Otherwise this script will most probably fail. 103 | 104 | ## Contributing 105 | 106 | - Each decoder is defined in `src` directory as a module. 107 | - Tests are defined in the `tests` directory using `Jest`. 108 | 109 | ## Contributors 110 | 111 | Thanks goes to these wonderful people ([emoji key](https://allcontributors.org/docs/en/emoji-key)): 112 | 113 | 114 | 115 |
Cristian Nitescu
Cristian Nitescu

💻
116 | 117 | 118 | 119 | This project follows the [all-contributors](https://github.com/all-contributors/all-contributors) specification. Contributions of any kind welcome! 120 | -------------------------------------------------------------------------------- /docs/assets/css/main.css: -------------------------------------------------------------------------------- 1 | :root { 2 | --color-background: #fdfdfd; 3 | --color-text: #222; 4 | --color-text-aside: #707070; 5 | --color-link: #4da6ff; 6 | --color-menu-divider: #eee; 7 | --color-menu-divider-focus: #000; 8 | --color-menu-label: #707070; 9 | --color-panel: #fff; 10 | --color-panel-divider: #eee; 11 | --color-comment-tag: #707070; 12 | --color-comment-tag-text: #fff; 13 | --color-code-background: rgba(0, 0, 0, 0.04); 14 | --color-ts: #9600ff; 15 | --color-ts-interface: #647f1b; 16 | --color-ts-enum: #937210; 17 | --color-ts-class: #0672de; 18 | --color-ts-private: #707070; 19 | --color-toolbar: #fff; 20 | --color-toolbar-text: #333; 21 | } 22 | 23 | /*! normalize.css v1.1.3 | MIT License | git.io/normalize */ 24 | /* ========================================================================== 25 | * * HTML5 display definitions 26 | * * ========================================================================== */ 27 | /** 28 | * * Correct `block` display not defined in IE 6/7/8/9 and Firefox 3. */ 29 | article, aside, details, figcaption, figure, footer, header, hgroup, main, nav, section, summary { 30 | display: block; 31 | } 32 | 33 | /** 34 | * * Correct `inline-block` display not defined in IE 6/7/8/9 and Firefox 3. */ 35 | audio, canvas, video { 36 | display: inline-block; 37 | *display: inline; 38 | *zoom: 1; 39 | } 40 | 41 | /** 42 | * * Prevent modern browsers from displaying `audio` without controls. 43 | * * Remove excess height in iOS 5 devices. */ 44 | audio:not([controls]) { 45 | display: none; 46 | height: 0; 47 | } 48 | 49 | /** 50 | * * Address styling not present in IE 7/8/9, Firefox 3, and Safari 4. 51 | * * Known issue: no IE 6 support. */ 52 | [hidden] { 53 | display: none; 54 | } 55 | 56 | /* ========================================================================== 57 | * * Base 58 | * * ========================================================================== */ 59 | /** 60 | * * 1. Correct text resizing oddly in IE 6/7 when body `font-size` is set using 61 | * * `em` units. 62 | * * 2. Prevent iOS text size adjust after orientation change, without disabling 63 | * * user zoom. */ 64 | html { 65 | font-size: 100%; 66 | /* 1 */ 67 | -ms-text-size-adjust: 100%; 68 | /* 2 */ 69 | -webkit-text-size-adjust: 100%; 70 | /* 2 */ 71 | font-family: sans-serif; 72 | } 73 | 74 | /** 75 | * * Address `font-family` inconsistency between `textarea` and other form 76 | * * elements. */ 77 | button, input, select, textarea { 78 | font-family: sans-serif; 79 | } 80 | 81 | /** 82 | * * Address margins handled incorrectly in IE 6/7. */ 83 | body { 84 | margin: 0; 85 | } 86 | 87 | /* ========================================================================== 88 | * * Links 89 | * * ========================================================================== */ 90 | /** 91 | * * Address `outline` inconsistency between Chrome and other browsers. */ 92 | a:focus { 93 | outline: thin dotted; 94 | } 95 | a:active, a:hover { 96 | outline: 0; 97 | } 98 | 99 | /** 100 | * * Improve readability when focused and also mouse hovered in all browsers. */ 101 | /* ========================================================================== 102 | * * Typography 103 | * * ========================================================================== */ 104 | /** 105 | * * Address font sizes and margins set differently in IE 6/7. 106 | * * Address font sizes within `section` and `article` in Firefox 4+, Safari 5, 107 | * * and Chrome. */ 108 | h1 { 109 | font-size: 2em; 110 | margin: 0.67em 0; 111 | } 112 | 113 | h2 { 114 | font-size: 1.5em; 115 | margin: 0.83em 0; 116 | } 117 | 118 | h3 { 119 | font-size: 1.17em; 120 | margin: 1em 0; 121 | } 122 | 123 | h4, .tsd-index-panel h3 { 124 | font-size: 1em; 125 | margin: 1.33em 0; 126 | } 127 | 128 | h5 { 129 | font-size: 0.83em; 130 | margin: 1.67em 0; 131 | } 132 | 133 | h6 { 134 | font-size: 0.67em; 135 | margin: 2.33em 0; 136 | } 137 | 138 | /** 139 | * * Address styling not present in IE 7/8/9, Safari 5, and Chrome. */ 140 | abbr[title] { 141 | border-bottom: 1px dotted; 142 | } 143 | 144 | /** 145 | * * Address style set to `bolder` in Firefox 3+, Safari 4/5, and Chrome. */ 146 | b, strong { 147 | font-weight: bold; 148 | } 149 | 150 | blockquote { 151 | margin: 1em 40px; 152 | } 153 | 154 | /** 155 | * * Address styling not present in Safari 5 and Chrome. */ 156 | dfn { 157 | font-style: italic; 158 | } 159 | 160 | /** 161 | * * Address differences between Firefox and other browsers. 162 | * * Known issue: no IE 6/7 normalization. */ 163 | hr { 164 | -moz-box-sizing: content-box; 165 | box-sizing: content-box; 166 | height: 0; 167 | } 168 | 169 | /** 170 | * * Address styling not present in IE 6/7/8/9. */ 171 | mark { 172 | background: #ff0; 173 | color: #000; 174 | } 175 | 176 | /** 177 | * * Address margins set differently in IE 6/7. */ 178 | p, pre { 179 | margin: 1em 0; 180 | } 181 | 182 | /** 183 | * * Correct font family set oddly in IE 6, Safari 4/5, and Chrome. */ 184 | code, kbd, pre, samp { 185 | font-family: monospace, serif; 186 | _font-family: "courier new", monospace; 187 | font-size: 1em; 188 | } 189 | 190 | /** 191 | * * Improve readability of pre-formatted text in all browsers. */ 192 | pre { 193 | white-space: pre; 194 | white-space: pre-wrap; 195 | word-wrap: break-word; 196 | } 197 | 198 | /** 199 | * * Address CSS quotes not supported in IE 6/7. */ 200 | q { 201 | quotes: none; 202 | } 203 | q:before, q:after { 204 | content: ""; 205 | content: none; 206 | } 207 | 208 | /** 209 | * * Address `quotes` property not supported in Safari 4. */ 210 | /** 211 | * * Address inconsistent and variable font size in all browsers. */ 212 | small { 213 | font-size: 80%; 214 | } 215 | 216 | /** 217 | * * Prevent `sub` and `sup` affecting `line-height` in all browsers. */ 218 | sub { 219 | font-size: 75%; 220 | line-height: 0; 221 | position: relative; 222 | vertical-align: baseline; 223 | } 224 | 225 | sup { 226 | font-size: 75%; 227 | line-height: 0; 228 | position: relative; 229 | vertical-align: baseline; 230 | top: -0.5em; 231 | } 232 | 233 | sub { 234 | bottom: -0.25em; 235 | } 236 | 237 | /* ========================================================================== 238 | * * Lists 239 | * * ========================================================================== */ 240 | /** 241 | * * Address margins set differently in IE 6/7. */ 242 | dl, menu, ol, ul { 243 | margin: 1em 0; 244 | } 245 | 246 | dd { 247 | margin: 0 0 0 40px; 248 | } 249 | 250 | /** 251 | * * Address paddings set differently in IE 6/7. */ 252 | menu, ol, ul { 253 | padding: 0 0 0 40px; 254 | } 255 | 256 | /** 257 | * * Correct list images handled incorrectly in IE 7. */ 258 | nav ul, nav ol { 259 | list-style: none; 260 | list-style-image: none; 261 | } 262 | 263 | /* ========================================================================== 264 | * * Embedded content 265 | * * ========================================================================== */ 266 | /** 267 | * * 1. Remove border when inside `a` element in IE 6/7/8/9 and Firefox 3. 268 | * * 2. Improve image quality when scaled in IE 7. */ 269 | img { 270 | border: 0; 271 | /* 1 */ 272 | -ms-interpolation-mode: bicubic; 273 | } 274 | 275 | /* 2 */ 276 | /** 277 | * * Correct overflow displayed oddly in IE 9. */ 278 | svg:not(:root) { 279 | overflow: hidden; 280 | } 281 | 282 | /* ========================================================================== 283 | * * Figures 284 | * * ========================================================================== */ 285 | /** 286 | * * Address margin not present in IE 6/7/8/9, Safari 5, and Opera 11. */ 287 | figure, form { 288 | margin: 0; 289 | } 290 | 291 | /* ========================================================================== 292 | * * Forms 293 | * * ========================================================================== */ 294 | /** 295 | * * Correct margin displayed oddly in IE 6/7. */ 296 | /** 297 | * * Define consistent border, margin, and padding. */ 298 | fieldset { 299 | border: 1px solid #c0c0c0; 300 | margin: 0 2px; 301 | padding: 0.35em 0.625em 0.75em; 302 | } 303 | 304 | /** 305 | * * 1. Correct color not being inherited in IE 6/7/8/9. 306 | * * 2. Correct text not wrapping in Firefox 3. 307 | * * 3. Correct alignment displayed oddly in IE 6/7. */ 308 | legend { 309 | border: 0; 310 | /* 1 */ 311 | padding: 0; 312 | white-space: normal; 313 | /* 2 */ 314 | *margin-left: -7px; 315 | } 316 | 317 | /* 3 */ 318 | /** 319 | * * 1. Correct font size not being inherited in all browsers. 320 | * * 2. Address margins set differently in IE 6/7, Firefox 3+, Safari 5, 321 | * * and Chrome. 322 | * * 3. Improve appearance and consistency in all browsers. */ 323 | button, input, select, textarea { 324 | font-size: 100%; 325 | /* 1 */ 326 | margin: 0; 327 | /* 2 */ 328 | vertical-align: baseline; 329 | /* 3 */ 330 | *vertical-align: middle; 331 | } 332 | 333 | /* 3 */ 334 | /** 335 | * * Address Firefox 3+ setting `line-height` on `input` using `!important` in 336 | * * the UA stylesheet. */ 337 | button, input { 338 | line-height: normal; 339 | } 340 | 341 | /** 342 | * * Address inconsistent `text-transform` inheritance for `button` and `select`. 343 | * * All other form control elements do not inherit `text-transform` values. 344 | * * Correct `button` style inheritance in Chrome, Safari 5+, and IE 6+. 345 | * * Correct `select` style inheritance in Firefox 4+ and Opera. */ 346 | button, select { 347 | text-transform: none; 348 | } 349 | 350 | /** 351 | * * 1. Avoid the WebKit bug in Android 4.0.* where (2) destroys native `audio` 352 | * * and `video` controls. 353 | * * 2. Correct inability to style clickable `input` types in iOS. 354 | * * 3. Improve usability and consistency of cursor style between image-type 355 | * * `input` and others. 356 | * * 4. Remove inner spacing in IE 7 without affecting normal text inputs. 357 | * * Known issue: inner spacing remains in IE 6. */ 358 | button, html input[type=button] { 359 | -webkit-appearance: button; 360 | /* 2 */ 361 | cursor: pointer; 362 | /* 3 */ 363 | *overflow: visible; 364 | } 365 | 366 | /* 4 */ 367 | input[type=reset], input[type=submit] { 368 | -webkit-appearance: button; 369 | /* 2 */ 370 | cursor: pointer; 371 | /* 3 */ 372 | *overflow: visible; 373 | } 374 | 375 | /* 4 */ 376 | /** 377 | * * Re-set default cursor for disabled elements. */ 378 | button[disabled], html input[disabled] { 379 | cursor: default; 380 | } 381 | 382 | /** 383 | * * 1. Address box sizing set to content-box in IE 8/9. 384 | * * 2. Remove excess padding in IE 8/9. 385 | * * 3. Remove excess padding in IE 7. 386 | * * Known issue: excess padding remains in IE 6. */ 387 | input { 388 | /* 3 */ 389 | } 390 | input[type=checkbox], input[type=radio] { 391 | box-sizing: border-box; 392 | /* 1 */ 393 | padding: 0; 394 | /* 2 */ 395 | *height: 13px; 396 | /* 3 */ 397 | *width: 13px; 398 | } 399 | input[type=search] { 400 | -webkit-appearance: textfield; 401 | /* 1 */ 402 | -moz-box-sizing: content-box; 403 | -webkit-box-sizing: content-box; 404 | /* 2 */ 405 | box-sizing: content-box; 406 | } 407 | input[type=search]::-webkit-search-cancel-button, input[type=search]::-webkit-search-decoration { 408 | -webkit-appearance: none; 409 | } 410 | 411 | /** 412 | * * 1. Address `appearance` set to `searchfield` in Safari 5 and Chrome. 413 | * * 2. Address `box-sizing` set to `border-box` in Safari 5 and Chrome 414 | * * (include `-moz` to future-proof). */ 415 | /** 416 | * * Remove inner padding and search cancel button in Safari 5 and Chrome 417 | * * on OS X. */ 418 | /** 419 | * * Remove inner padding and border in Firefox 3+. */ 420 | button::-moz-focus-inner, input::-moz-focus-inner { 421 | border: 0; 422 | padding: 0; 423 | } 424 | 425 | /** 426 | * * 1. Remove default vertical scrollbar in IE 6/7/8/9. 427 | * * 2. Improve readability and alignment in all browsers. */ 428 | textarea { 429 | overflow: auto; 430 | /* 1 */ 431 | vertical-align: top; 432 | } 433 | 434 | /* 2 */ 435 | /* ========================================================================== 436 | * * Tables 437 | * * ========================================================================== */ 438 | /** 439 | * * Remove most spacing between table cells. */ 440 | table { 441 | border-collapse: collapse; 442 | border-spacing: 0; 443 | } 444 | 445 | ul.tsd-descriptions > li > :first-child, .tsd-panel > :first-child, .col > :first-child, .col-11 > :first-child, .col-10 > :first-child, .col-9 > :first-child, .col-8 > :first-child, .col-7 > :first-child, .col-6 > :first-child, .col-5 > :first-child, .col-4 > :first-child, .col-3 > :first-child, .col-2 > :first-child, .col-1 > :first-child, 446 | ul.tsd-descriptions > li > :first-child > :first-child, 447 | .tsd-panel > :first-child > :first-child, 448 | .col > :first-child > :first-child, 449 | .col-11 > :first-child > :first-child, 450 | .col-10 > :first-child > :first-child, 451 | .col-9 > :first-child > :first-child, 452 | .col-8 > :first-child > :first-child, 453 | .col-7 > :first-child > :first-child, 454 | .col-6 > :first-child > :first-child, 455 | .col-5 > :first-child > :first-child, 456 | .col-4 > :first-child > :first-child, 457 | .col-3 > :first-child > :first-child, 458 | .col-2 > :first-child > :first-child, 459 | .col-1 > :first-child > :first-child, 460 | ul.tsd-descriptions > li > :first-child > :first-child > :first-child, 461 | .tsd-panel > :first-child > :first-child > :first-child, 462 | .col > :first-child > :first-child > :first-child, 463 | .col-11 > :first-child > :first-child > :first-child, 464 | .col-10 > :first-child > :first-child > :first-child, 465 | .col-9 > :first-child > :first-child > :first-child, 466 | .col-8 > :first-child > :first-child > :first-child, 467 | .col-7 > :first-child > :first-child > :first-child, 468 | .col-6 > :first-child > :first-child > :first-child, 469 | .col-5 > :first-child > :first-child > :first-child, 470 | .col-4 > :first-child > :first-child > :first-child, 471 | .col-3 > :first-child > :first-child > :first-child, 472 | .col-2 > :first-child > :first-child > :first-child, 473 | .col-1 > :first-child > :first-child > :first-child { 474 | margin-top: 0; 475 | } 476 | ul.tsd-descriptions > li > :last-child, .tsd-panel > :last-child, .col > :last-child, .col-11 > :last-child, .col-10 > :last-child, .col-9 > :last-child, .col-8 > :last-child, .col-7 > :last-child, .col-6 > :last-child, .col-5 > :last-child, .col-4 > :last-child, .col-3 > :last-child, .col-2 > :last-child, .col-1 > :last-child, 477 | ul.tsd-descriptions > li > :last-child > :last-child, 478 | .tsd-panel > :last-child > :last-child, 479 | .col > :last-child > :last-child, 480 | .col-11 > :last-child > :last-child, 481 | .col-10 > :last-child > :last-child, 482 | .col-9 > :last-child > :last-child, 483 | .col-8 > :last-child > :last-child, 484 | .col-7 > :last-child > :last-child, 485 | .col-6 > :last-child > :last-child, 486 | .col-5 > :last-child > :last-child, 487 | .col-4 > :last-child > :last-child, 488 | .col-3 > :last-child > :last-child, 489 | .col-2 > :last-child > :last-child, 490 | .col-1 > :last-child > :last-child, 491 | ul.tsd-descriptions > li > :last-child > :last-child > :last-child, 492 | .tsd-panel > :last-child > :last-child > :last-child, 493 | .col > :last-child > :last-child > :last-child, 494 | .col-11 > :last-child > :last-child > :last-child, 495 | .col-10 > :last-child > :last-child > :last-child, 496 | .col-9 > :last-child > :last-child > :last-child, 497 | .col-8 > :last-child > :last-child > :last-child, 498 | .col-7 > :last-child > :last-child > :last-child, 499 | .col-6 > :last-child > :last-child > :last-child, 500 | .col-5 > :last-child > :last-child > :last-child, 501 | .col-4 > :last-child > :last-child > :last-child, 502 | .col-3 > :last-child > :last-child > :last-child, 503 | .col-2 > :last-child > :last-child > :last-child, 504 | .col-1 > :last-child > :last-child > :last-child { 505 | margin-bottom: 0; 506 | } 507 | 508 | .container { 509 | max-width: 1200px; 510 | margin: 0 auto; 511 | padding: 0 40px; 512 | } 513 | @media (max-width: 640px) { 514 | .container { 515 | padding: 0 20px; 516 | } 517 | } 518 | 519 | .container-main { 520 | padding-bottom: 200px; 521 | } 522 | 523 | .row { 524 | display: flex; 525 | position: relative; 526 | margin: 0 -10px; 527 | } 528 | .row:after { 529 | visibility: hidden; 530 | display: block; 531 | content: ""; 532 | clear: both; 533 | height: 0; 534 | } 535 | 536 | .col, .col-11, .col-10, .col-9, .col-8, .col-7, .col-6, .col-5, .col-4, .col-3, .col-2, .col-1 { 537 | box-sizing: border-box; 538 | float: left; 539 | padding: 0 10px; 540 | } 541 | 542 | .col-1 { 543 | width: 8.3333333333%; 544 | } 545 | 546 | .offset-1 { 547 | margin-left: 8.3333333333%; 548 | } 549 | 550 | .col-2 { 551 | width: 16.6666666667%; 552 | } 553 | 554 | .offset-2 { 555 | margin-left: 16.6666666667%; 556 | } 557 | 558 | .col-3 { 559 | width: 25%; 560 | } 561 | 562 | .offset-3 { 563 | margin-left: 25%; 564 | } 565 | 566 | .col-4 { 567 | width: 33.3333333333%; 568 | } 569 | 570 | .offset-4 { 571 | margin-left: 33.3333333333%; 572 | } 573 | 574 | .col-5 { 575 | width: 41.6666666667%; 576 | } 577 | 578 | .offset-5 { 579 | margin-left: 41.6666666667%; 580 | } 581 | 582 | .col-6 { 583 | width: 50%; 584 | } 585 | 586 | .offset-6 { 587 | margin-left: 50%; 588 | } 589 | 590 | .col-7 { 591 | width: 58.3333333333%; 592 | } 593 | 594 | .offset-7 { 595 | margin-left: 58.3333333333%; 596 | } 597 | 598 | .col-8 { 599 | width: 66.6666666667%; 600 | } 601 | 602 | .offset-8 { 603 | margin-left: 66.6666666667%; 604 | } 605 | 606 | .col-9 { 607 | width: 75%; 608 | } 609 | 610 | .offset-9 { 611 | margin-left: 75%; 612 | } 613 | 614 | .col-10 { 615 | width: 83.3333333333%; 616 | } 617 | 618 | .offset-10 { 619 | margin-left: 83.3333333333%; 620 | } 621 | 622 | .col-11 { 623 | width: 91.6666666667%; 624 | } 625 | 626 | .offset-11 { 627 | margin-left: 91.6666666667%; 628 | } 629 | 630 | .tsd-kind-icon { 631 | display: block; 632 | position: relative; 633 | padding-left: 20px; 634 | text-indent: -20px; 635 | } 636 | .tsd-kind-icon:before { 637 | content: ""; 638 | display: inline-block; 639 | vertical-align: middle; 640 | width: 17px; 641 | height: 17px; 642 | margin: 0 3px 2px 0; 643 | background-image: url(../images/icons.png); 644 | } 645 | @media (-webkit-min-device-pixel-ratio: 1.5), (min-resolution: 144dpi) { 646 | .tsd-kind-icon:before { 647 | background-image: url(../images/icons@2x.png); 648 | background-size: 238px 204px; 649 | } 650 | } 651 | 652 | .tsd-signature.tsd-kind-icon:before { 653 | background-position: 0 -153px; 654 | } 655 | 656 | .tsd-kind-object-literal > .tsd-kind-icon:before { 657 | background-position: 0px -17px; 658 | } 659 | .tsd-kind-object-literal.tsd-is-protected > .tsd-kind-icon:before { 660 | background-position: -17px -17px; 661 | } 662 | .tsd-kind-object-literal.tsd-is-private > .tsd-kind-icon:before { 663 | background-position: -34px -17px; 664 | } 665 | 666 | .tsd-kind-class > .tsd-kind-icon:before { 667 | background-position: 0px -34px; 668 | } 669 | .tsd-kind-class.tsd-is-protected > .tsd-kind-icon:before { 670 | background-position: -17px -34px; 671 | } 672 | .tsd-kind-class.tsd-is-private > .tsd-kind-icon:before { 673 | background-position: -34px -34px; 674 | } 675 | 676 | .tsd-kind-class.tsd-has-type-parameter > .tsd-kind-icon:before { 677 | background-position: 0px -51px; 678 | } 679 | .tsd-kind-class.tsd-has-type-parameter.tsd-is-protected > .tsd-kind-icon:before { 680 | background-position: -17px -51px; 681 | } 682 | .tsd-kind-class.tsd-has-type-parameter.tsd-is-private > .tsd-kind-icon:before { 683 | background-position: -34px -51px; 684 | } 685 | 686 | .tsd-kind-interface > .tsd-kind-icon:before { 687 | background-position: 0px -68px; 688 | } 689 | .tsd-kind-interface.tsd-is-protected > .tsd-kind-icon:before { 690 | background-position: -17px -68px; 691 | } 692 | .tsd-kind-interface.tsd-is-private > .tsd-kind-icon:before { 693 | background-position: -34px -68px; 694 | } 695 | 696 | .tsd-kind-interface.tsd-has-type-parameter > .tsd-kind-icon:before { 697 | background-position: 0px -85px; 698 | } 699 | .tsd-kind-interface.tsd-has-type-parameter.tsd-is-protected > .tsd-kind-icon:before { 700 | background-position: -17px -85px; 701 | } 702 | .tsd-kind-interface.tsd-has-type-parameter.tsd-is-private > .tsd-kind-icon:before { 703 | background-position: -34px -85px; 704 | } 705 | 706 | .tsd-kind-namespace > .tsd-kind-icon:before { 707 | background-position: 0px -102px; 708 | } 709 | .tsd-kind-namespace.tsd-is-protected > .tsd-kind-icon:before { 710 | background-position: -17px -102px; 711 | } 712 | .tsd-kind-namespace.tsd-is-private > .tsd-kind-icon:before { 713 | background-position: -34px -102px; 714 | } 715 | 716 | .tsd-kind-module > .tsd-kind-icon:before { 717 | background-position: 0px -102px; 718 | } 719 | .tsd-kind-module.tsd-is-protected > .tsd-kind-icon:before { 720 | background-position: -17px -102px; 721 | } 722 | .tsd-kind-module.tsd-is-private > .tsd-kind-icon:before { 723 | background-position: -34px -102px; 724 | } 725 | 726 | .tsd-kind-enum > .tsd-kind-icon:before { 727 | background-position: 0px -119px; 728 | } 729 | .tsd-kind-enum.tsd-is-protected > .tsd-kind-icon:before { 730 | background-position: -17px -119px; 731 | } 732 | .tsd-kind-enum.tsd-is-private > .tsd-kind-icon:before { 733 | background-position: -34px -119px; 734 | } 735 | 736 | .tsd-kind-enum-member > .tsd-kind-icon:before { 737 | background-position: 0px -136px; 738 | } 739 | .tsd-kind-enum-member.tsd-is-protected > .tsd-kind-icon:before { 740 | background-position: -17px -136px; 741 | } 742 | .tsd-kind-enum-member.tsd-is-private > .tsd-kind-icon:before { 743 | background-position: -34px -136px; 744 | } 745 | 746 | .tsd-kind-signature > .tsd-kind-icon:before { 747 | background-position: 0px -153px; 748 | } 749 | .tsd-kind-signature.tsd-is-protected > .tsd-kind-icon:before { 750 | background-position: -17px -153px; 751 | } 752 | .tsd-kind-signature.tsd-is-private > .tsd-kind-icon:before { 753 | background-position: -34px -153px; 754 | } 755 | 756 | .tsd-kind-type-alias > .tsd-kind-icon:before { 757 | background-position: 0px -170px; 758 | } 759 | .tsd-kind-type-alias.tsd-is-protected > .tsd-kind-icon:before { 760 | background-position: -17px -170px; 761 | } 762 | .tsd-kind-type-alias.tsd-is-private > .tsd-kind-icon:before { 763 | background-position: -34px -170px; 764 | } 765 | 766 | .tsd-kind-type-alias.tsd-has-type-parameter > .tsd-kind-icon:before { 767 | background-position: 0px -187px; 768 | } 769 | .tsd-kind-type-alias.tsd-has-type-parameter.tsd-is-protected > .tsd-kind-icon:before { 770 | background-position: -17px -187px; 771 | } 772 | .tsd-kind-type-alias.tsd-has-type-parameter.tsd-is-private > .tsd-kind-icon:before { 773 | background-position: -34px -187px; 774 | } 775 | 776 | .tsd-kind-variable > .tsd-kind-icon:before { 777 | background-position: -136px -0px; 778 | } 779 | .tsd-kind-variable.tsd-is-protected > .tsd-kind-icon:before { 780 | background-position: -153px -0px; 781 | } 782 | .tsd-kind-variable.tsd-is-private > .tsd-kind-icon:before { 783 | background-position: -119px -0px; 784 | } 785 | .tsd-kind-variable.tsd-parent-kind-class > .tsd-kind-icon:before { 786 | background-position: -51px -0px; 787 | } 788 | .tsd-kind-variable.tsd-parent-kind-class.tsd-is-inherited > .tsd-kind-icon:before { 789 | background-position: -68px -0px; 790 | } 791 | .tsd-kind-variable.tsd-parent-kind-class.tsd-is-protected > .tsd-kind-icon:before { 792 | background-position: -85px -0px; 793 | } 794 | .tsd-kind-variable.tsd-parent-kind-class.tsd-is-protected.tsd-is-inherited > .tsd-kind-icon:before { 795 | background-position: -102px -0px; 796 | } 797 | .tsd-kind-variable.tsd-parent-kind-class.tsd-is-private > .tsd-kind-icon:before { 798 | background-position: -119px -0px; 799 | } 800 | .tsd-kind-variable.tsd-parent-kind-enum > .tsd-kind-icon:before { 801 | background-position: -170px -0px; 802 | } 803 | .tsd-kind-variable.tsd-parent-kind-enum.tsd-is-protected > .tsd-kind-icon:before { 804 | background-position: -187px -0px; 805 | } 806 | .tsd-kind-variable.tsd-parent-kind-enum.tsd-is-private > .tsd-kind-icon:before { 807 | background-position: -119px -0px; 808 | } 809 | .tsd-kind-variable.tsd-parent-kind-interface > .tsd-kind-icon:before { 810 | background-position: -204px -0px; 811 | } 812 | .tsd-kind-variable.tsd-parent-kind-interface.tsd-is-inherited > .tsd-kind-icon:before { 813 | background-position: -221px -0px; 814 | } 815 | 816 | .tsd-kind-property > .tsd-kind-icon:before { 817 | background-position: -136px -0px; 818 | } 819 | .tsd-kind-property.tsd-is-protected > .tsd-kind-icon:before { 820 | background-position: -153px -0px; 821 | } 822 | .tsd-kind-property.tsd-is-private > .tsd-kind-icon:before { 823 | background-position: -119px -0px; 824 | } 825 | .tsd-kind-property.tsd-parent-kind-class > .tsd-kind-icon:before { 826 | background-position: -51px -0px; 827 | } 828 | .tsd-kind-property.tsd-parent-kind-class.tsd-is-inherited > .tsd-kind-icon:before { 829 | background-position: -68px -0px; 830 | } 831 | .tsd-kind-property.tsd-parent-kind-class.tsd-is-protected > .tsd-kind-icon:before { 832 | background-position: -85px -0px; 833 | } 834 | .tsd-kind-property.tsd-parent-kind-class.tsd-is-protected.tsd-is-inherited > .tsd-kind-icon:before { 835 | background-position: -102px -0px; 836 | } 837 | .tsd-kind-property.tsd-parent-kind-class.tsd-is-private > .tsd-kind-icon:before { 838 | background-position: -119px -0px; 839 | } 840 | .tsd-kind-property.tsd-parent-kind-enum > .tsd-kind-icon:before { 841 | background-position: -170px -0px; 842 | } 843 | .tsd-kind-property.tsd-parent-kind-enum.tsd-is-protected > .tsd-kind-icon:before { 844 | background-position: -187px -0px; 845 | } 846 | .tsd-kind-property.tsd-parent-kind-enum.tsd-is-private > .tsd-kind-icon:before { 847 | background-position: -119px -0px; 848 | } 849 | .tsd-kind-property.tsd-parent-kind-interface > .tsd-kind-icon:before { 850 | background-position: -204px -0px; 851 | } 852 | .tsd-kind-property.tsd-parent-kind-interface.tsd-is-inherited > .tsd-kind-icon:before { 853 | background-position: -221px -0px; 854 | } 855 | 856 | .tsd-kind-get-signature > .tsd-kind-icon:before { 857 | background-position: -136px -17px; 858 | } 859 | .tsd-kind-get-signature.tsd-is-protected > .tsd-kind-icon:before { 860 | background-position: -153px -17px; 861 | } 862 | .tsd-kind-get-signature.tsd-is-private > .tsd-kind-icon:before { 863 | background-position: -119px -17px; 864 | } 865 | .tsd-kind-get-signature.tsd-parent-kind-class > .tsd-kind-icon:before { 866 | background-position: -51px -17px; 867 | } 868 | .tsd-kind-get-signature.tsd-parent-kind-class.tsd-is-inherited > .tsd-kind-icon:before { 869 | background-position: -68px -17px; 870 | } 871 | .tsd-kind-get-signature.tsd-parent-kind-class.tsd-is-protected > .tsd-kind-icon:before { 872 | background-position: -85px -17px; 873 | } 874 | .tsd-kind-get-signature.tsd-parent-kind-class.tsd-is-protected.tsd-is-inherited > .tsd-kind-icon:before { 875 | background-position: -102px -17px; 876 | } 877 | .tsd-kind-get-signature.tsd-parent-kind-class.tsd-is-private > .tsd-kind-icon:before { 878 | background-position: -119px -17px; 879 | } 880 | .tsd-kind-get-signature.tsd-parent-kind-enum > .tsd-kind-icon:before { 881 | background-position: -170px -17px; 882 | } 883 | .tsd-kind-get-signature.tsd-parent-kind-enum.tsd-is-protected > .tsd-kind-icon:before { 884 | background-position: -187px -17px; 885 | } 886 | .tsd-kind-get-signature.tsd-parent-kind-enum.tsd-is-private > .tsd-kind-icon:before { 887 | background-position: -119px -17px; 888 | } 889 | .tsd-kind-get-signature.tsd-parent-kind-interface > .tsd-kind-icon:before { 890 | background-position: -204px -17px; 891 | } 892 | .tsd-kind-get-signature.tsd-parent-kind-interface.tsd-is-inherited > .tsd-kind-icon:before { 893 | background-position: -221px -17px; 894 | } 895 | 896 | .tsd-kind-set-signature > .tsd-kind-icon:before { 897 | background-position: -136px -34px; 898 | } 899 | .tsd-kind-set-signature.tsd-is-protected > .tsd-kind-icon:before { 900 | background-position: -153px -34px; 901 | } 902 | .tsd-kind-set-signature.tsd-is-private > .tsd-kind-icon:before { 903 | background-position: -119px -34px; 904 | } 905 | .tsd-kind-set-signature.tsd-parent-kind-class > .tsd-kind-icon:before { 906 | background-position: -51px -34px; 907 | } 908 | .tsd-kind-set-signature.tsd-parent-kind-class.tsd-is-inherited > .tsd-kind-icon:before { 909 | background-position: -68px -34px; 910 | } 911 | .tsd-kind-set-signature.tsd-parent-kind-class.tsd-is-protected > .tsd-kind-icon:before { 912 | background-position: -85px -34px; 913 | } 914 | .tsd-kind-set-signature.tsd-parent-kind-class.tsd-is-protected.tsd-is-inherited > .tsd-kind-icon:before { 915 | background-position: -102px -34px; 916 | } 917 | .tsd-kind-set-signature.tsd-parent-kind-class.tsd-is-private > .tsd-kind-icon:before { 918 | background-position: -119px -34px; 919 | } 920 | .tsd-kind-set-signature.tsd-parent-kind-enum > .tsd-kind-icon:before { 921 | background-position: -170px -34px; 922 | } 923 | .tsd-kind-set-signature.tsd-parent-kind-enum.tsd-is-protected > .tsd-kind-icon:before { 924 | background-position: -187px -34px; 925 | } 926 | .tsd-kind-set-signature.tsd-parent-kind-enum.tsd-is-private > .tsd-kind-icon:before { 927 | background-position: -119px -34px; 928 | } 929 | .tsd-kind-set-signature.tsd-parent-kind-interface > .tsd-kind-icon:before { 930 | background-position: -204px -34px; 931 | } 932 | .tsd-kind-set-signature.tsd-parent-kind-interface.tsd-is-inherited > .tsd-kind-icon:before { 933 | background-position: -221px -34px; 934 | } 935 | 936 | .tsd-kind-accessor > .tsd-kind-icon:before { 937 | background-position: -136px -51px; 938 | } 939 | .tsd-kind-accessor.tsd-is-protected > .tsd-kind-icon:before { 940 | background-position: -153px -51px; 941 | } 942 | .tsd-kind-accessor.tsd-is-private > .tsd-kind-icon:before { 943 | background-position: -119px -51px; 944 | } 945 | .tsd-kind-accessor.tsd-parent-kind-class > .tsd-kind-icon:before { 946 | background-position: -51px -51px; 947 | } 948 | .tsd-kind-accessor.tsd-parent-kind-class.tsd-is-inherited > .tsd-kind-icon:before { 949 | background-position: -68px -51px; 950 | } 951 | .tsd-kind-accessor.tsd-parent-kind-class.tsd-is-protected > .tsd-kind-icon:before { 952 | background-position: -85px -51px; 953 | } 954 | .tsd-kind-accessor.tsd-parent-kind-class.tsd-is-protected.tsd-is-inherited > .tsd-kind-icon:before { 955 | background-position: -102px -51px; 956 | } 957 | .tsd-kind-accessor.tsd-parent-kind-class.tsd-is-private > .tsd-kind-icon:before { 958 | background-position: -119px -51px; 959 | } 960 | .tsd-kind-accessor.tsd-parent-kind-enum > .tsd-kind-icon:before { 961 | background-position: -170px -51px; 962 | } 963 | .tsd-kind-accessor.tsd-parent-kind-enum.tsd-is-protected > .tsd-kind-icon:before { 964 | background-position: -187px -51px; 965 | } 966 | .tsd-kind-accessor.tsd-parent-kind-enum.tsd-is-private > .tsd-kind-icon:before { 967 | background-position: -119px -51px; 968 | } 969 | .tsd-kind-accessor.tsd-parent-kind-interface > .tsd-kind-icon:before { 970 | background-position: -204px -51px; 971 | } 972 | .tsd-kind-accessor.tsd-parent-kind-interface.tsd-is-inherited > .tsd-kind-icon:before { 973 | background-position: -221px -51px; 974 | } 975 | 976 | .tsd-kind-function > .tsd-kind-icon:before { 977 | background-position: -136px -68px; 978 | } 979 | .tsd-kind-function.tsd-is-protected > .tsd-kind-icon:before { 980 | background-position: -153px -68px; 981 | } 982 | .tsd-kind-function.tsd-is-private > .tsd-kind-icon:before { 983 | background-position: -119px -68px; 984 | } 985 | .tsd-kind-function.tsd-parent-kind-class > .tsd-kind-icon:before { 986 | background-position: -51px -68px; 987 | } 988 | .tsd-kind-function.tsd-parent-kind-class.tsd-is-inherited > .tsd-kind-icon:before { 989 | background-position: -68px -68px; 990 | } 991 | .tsd-kind-function.tsd-parent-kind-class.tsd-is-protected > .tsd-kind-icon:before { 992 | background-position: -85px -68px; 993 | } 994 | .tsd-kind-function.tsd-parent-kind-class.tsd-is-protected.tsd-is-inherited > .tsd-kind-icon:before { 995 | background-position: -102px -68px; 996 | } 997 | .tsd-kind-function.tsd-parent-kind-class.tsd-is-private > .tsd-kind-icon:before { 998 | background-position: -119px -68px; 999 | } 1000 | .tsd-kind-function.tsd-parent-kind-enum > .tsd-kind-icon:before { 1001 | background-position: -170px -68px; 1002 | } 1003 | .tsd-kind-function.tsd-parent-kind-enum.tsd-is-protected > .tsd-kind-icon:before { 1004 | background-position: -187px -68px; 1005 | } 1006 | .tsd-kind-function.tsd-parent-kind-enum.tsd-is-private > .tsd-kind-icon:before { 1007 | background-position: -119px -68px; 1008 | } 1009 | .tsd-kind-function.tsd-parent-kind-interface > .tsd-kind-icon:before { 1010 | background-position: -204px -68px; 1011 | } 1012 | .tsd-kind-function.tsd-parent-kind-interface.tsd-is-inherited > .tsd-kind-icon:before { 1013 | background-position: -221px -68px; 1014 | } 1015 | 1016 | .tsd-kind-method > .tsd-kind-icon:before { 1017 | background-position: -136px -68px; 1018 | } 1019 | .tsd-kind-method.tsd-is-protected > .tsd-kind-icon:before { 1020 | background-position: -153px -68px; 1021 | } 1022 | .tsd-kind-method.tsd-is-private > .tsd-kind-icon:before { 1023 | background-position: -119px -68px; 1024 | } 1025 | .tsd-kind-method.tsd-parent-kind-class > .tsd-kind-icon:before { 1026 | background-position: -51px -68px; 1027 | } 1028 | .tsd-kind-method.tsd-parent-kind-class.tsd-is-inherited > .tsd-kind-icon:before { 1029 | background-position: -68px -68px; 1030 | } 1031 | .tsd-kind-method.tsd-parent-kind-class.tsd-is-protected > .tsd-kind-icon:before { 1032 | background-position: -85px -68px; 1033 | } 1034 | .tsd-kind-method.tsd-parent-kind-class.tsd-is-protected.tsd-is-inherited > .tsd-kind-icon:before { 1035 | background-position: -102px -68px; 1036 | } 1037 | .tsd-kind-method.tsd-parent-kind-class.tsd-is-private > .tsd-kind-icon:before { 1038 | background-position: -119px -68px; 1039 | } 1040 | .tsd-kind-method.tsd-parent-kind-enum > .tsd-kind-icon:before { 1041 | background-position: -170px -68px; 1042 | } 1043 | .tsd-kind-method.tsd-parent-kind-enum.tsd-is-protected > .tsd-kind-icon:before { 1044 | background-position: -187px -68px; 1045 | } 1046 | .tsd-kind-method.tsd-parent-kind-enum.tsd-is-private > .tsd-kind-icon:before { 1047 | background-position: -119px -68px; 1048 | } 1049 | .tsd-kind-method.tsd-parent-kind-interface > .tsd-kind-icon:before { 1050 | background-position: -204px -68px; 1051 | } 1052 | .tsd-kind-method.tsd-parent-kind-interface.tsd-is-inherited > .tsd-kind-icon:before { 1053 | background-position: -221px -68px; 1054 | } 1055 | 1056 | .tsd-kind-call-signature > .tsd-kind-icon:before { 1057 | background-position: -136px -68px; 1058 | } 1059 | .tsd-kind-call-signature.tsd-is-protected > .tsd-kind-icon:before { 1060 | background-position: -153px -68px; 1061 | } 1062 | .tsd-kind-call-signature.tsd-is-private > .tsd-kind-icon:before { 1063 | background-position: -119px -68px; 1064 | } 1065 | .tsd-kind-call-signature.tsd-parent-kind-class > .tsd-kind-icon:before { 1066 | background-position: -51px -68px; 1067 | } 1068 | .tsd-kind-call-signature.tsd-parent-kind-class.tsd-is-inherited > .tsd-kind-icon:before { 1069 | background-position: -68px -68px; 1070 | } 1071 | .tsd-kind-call-signature.tsd-parent-kind-class.tsd-is-protected > .tsd-kind-icon:before { 1072 | background-position: -85px -68px; 1073 | } 1074 | .tsd-kind-call-signature.tsd-parent-kind-class.tsd-is-protected.tsd-is-inherited > .tsd-kind-icon:before { 1075 | background-position: -102px -68px; 1076 | } 1077 | .tsd-kind-call-signature.tsd-parent-kind-class.tsd-is-private > .tsd-kind-icon:before { 1078 | background-position: -119px -68px; 1079 | } 1080 | .tsd-kind-call-signature.tsd-parent-kind-enum > .tsd-kind-icon:before { 1081 | background-position: -170px -68px; 1082 | } 1083 | .tsd-kind-call-signature.tsd-parent-kind-enum.tsd-is-protected > .tsd-kind-icon:before { 1084 | background-position: -187px -68px; 1085 | } 1086 | .tsd-kind-call-signature.tsd-parent-kind-enum.tsd-is-private > .tsd-kind-icon:before { 1087 | background-position: -119px -68px; 1088 | } 1089 | .tsd-kind-call-signature.tsd-parent-kind-interface > .tsd-kind-icon:before { 1090 | background-position: -204px -68px; 1091 | } 1092 | .tsd-kind-call-signature.tsd-parent-kind-interface.tsd-is-inherited > .tsd-kind-icon:before { 1093 | background-position: -221px -68px; 1094 | } 1095 | 1096 | .tsd-kind-function.tsd-has-type-parameter > .tsd-kind-icon:before { 1097 | background-position: -136px -85px; 1098 | } 1099 | .tsd-kind-function.tsd-has-type-parameter.tsd-is-protected > .tsd-kind-icon:before { 1100 | background-position: -153px -85px; 1101 | } 1102 | .tsd-kind-function.tsd-has-type-parameter.tsd-is-private > .tsd-kind-icon:before { 1103 | background-position: -119px -85px; 1104 | } 1105 | .tsd-kind-function.tsd-has-type-parameter.tsd-parent-kind-class > .tsd-kind-icon:before { 1106 | background-position: -51px -85px; 1107 | } 1108 | .tsd-kind-function.tsd-has-type-parameter.tsd-parent-kind-class.tsd-is-inherited > .tsd-kind-icon:before { 1109 | background-position: -68px -85px; 1110 | } 1111 | .tsd-kind-function.tsd-has-type-parameter.tsd-parent-kind-class.tsd-is-protected > .tsd-kind-icon:before { 1112 | background-position: -85px -85px; 1113 | } 1114 | .tsd-kind-function.tsd-has-type-parameter.tsd-parent-kind-class.tsd-is-protected.tsd-is-inherited > .tsd-kind-icon:before { 1115 | background-position: -102px -85px; 1116 | } 1117 | .tsd-kind-function.tsd-has-type-parameter.tsd-parent-kind-class.tsd-is-private > .tsd-kind-icon:before { 1118 | background-position: -119px -85px; 1119 | } 1120 | .tsd-kind-function.tsd-has-type-parameter.tsd-parent-kind-enum > .tsd-kind-icon:before { 1121 | background-position: -170px -85px; 1122 | } 1123 | .tsd-kind-function.tsd-has-type-parameter.tsd-parent-kind-enum.tsd-is-protected > .tsd-kind-icon:before { 1124 | background-position: -187px -85px; 1125 | } 1126 | .tsd-kind-function.tsd-has-type-parameter.tsd-parent-kind-enum.tsd-is-private > .tsd-kind-icon:before { 1127 | background-position: -119px -85px; 1128 | } 1129 | .tsd-kind-function.tsd-has-type-parameter.tsd-parent-kind-interface > .tsd-kind-icon:before { 1130 | background-position: -204px -85px; 1131 | } 1132 | .tsd-kind-function.tsd-has-type-parameter.tsd-parent-kind-interface.tsd-is-inherited > .tsd-kind-icon:before { 1133 | background-position: -221px -85px; 1134 | } 1135 | 1136 | .tsd-kind-method.tsd-has-type-parameter > .tsd-kind-icon:before { 1137 | background-position: -136px -85px; 1138 | } 1139 | .tsd-kind-method.tsd-has-type-parameter.tsd-is-protected > .tsd-kind-icon:before { 1140 | background-position: -153px -85px; 1141 | } 1142 | .tsd-kind-method.tsd-has-type-parameter.tsd-is-private > .tsd-kind-icon:before { 1143 | background-position: -119px -85px; 1144 | } 1145 | .tsd-kind-method.tsd-has-type-parameter.tsd-parent-kind-class > .tsd-kind-icon:before { 1146 | background-position: -51px -85px; 1147 | } 1148 | .tsd-kind-method.tsd-has-type-parameter.tsd-parent-kind-class.tsd-is-inherited > .tsd-kind-icon:before { 1149 | background-position: -68px -85px; 1150 | } 1151 | .tsd-kind-method.tsd-has-type-parameter.tsd-parent-kind-class.tsd-is-protected > .tsd-kind-icon:before { 1152 | background-position: -85px -85px; 1153 | } 1154 | .tsd-kind-method.tsd-has-type-parameter.tsd-parent-kind-class.tsd-is-protected.tsd-is-inherited > .tsd-kind-icon:before { 1155 | background-position: -102px -85px; 1156 | } 1157 | .tsd-kind-method.tsd-has-type-parameter.tsd-parent-kind-class.tsd-is-private > .tsd-kind-icon:before { 1158 | background-position: -119px -85px; 1159 | } 1160 | .tsd-kind-method.tsd-has-type-parameter.tsd-parent-kind-enum > .tsd-kind-icon:before { 1161 | background-position: -170px -85px; 1162 | } 1163 | .tsd-kind-method.tsd-has-type-parameter.tsd-parent-kind-enum.tsd-is-protected > .tsd-kind-icon:before { 1164 | background-position: -187px -85px; 1165 | } 1166 | .tsd-kind-method.tsd-has-type-parameter.tsd-parent-kind-enum.tsd-is-private > .tsd-kind-icon:before { 1167 | background-position: -119px -85px; 1168 | } 1169 | .tsd-kind-method.tsd-has-type-parameter.tsd-parent-kind-interface > .tsd-kind-icon:before { 1170 | background-position: -204px -85px; 1171 | } 1172 | .tsd-kind-method.tsd-has-type-parameter.tsd-parent-kind-interface.tsd-is-inherited > .tsd-kind-icon:before { 1173 | background-position: -221px -85px; 1174 | } 1175 | 1176 | .tsd-kind-constructor > .tsd-kind-icon:before { 1177 | background-position: -136px -102px; 1178 | } 1179 | .tsd-kind-constructor.tsd-is-protected > .tsd-kind-icon:before { 1180 | background-position: -153px -102px; 1181 | } 1182 | .tsd-kind-constructor.tsd-is-private > .tsd-kind-icon:before { 1183 | background-position: -119px -102px; 1184 | } 1185 | .tsd-kind-constructor.tsd-parent-kind-class > .tsd-kind-icon:before { 1186 | background-position: -51px -102px; 1187 | } 1188 | .tsd-kind-constructor.tsd-parent-kind-class.tsd-is-inherited > .tsd-kind-icon:before { 1189 | background-position: -68px -102px; 1190 | } 1191 | .tsd-kind-constructor.tsd-parent-kind-class.tsd-is-protected > .tsd-kind-icon:before { 1192 | background-position: -85px -102px; 1193 | } 1194 | .tsd-kind-constructor.tsd-parent-kind-class.tsd-is-protected.tsd-is-inherited > .tsd-kind-icon:before { 1195 | background-position: -102px -102px; 1196 | } 1197 | .tsd-kind-constructor.tsd-parent-kind-class.tsd-is-private > .tsd-kind-icon:before { 1198 | background-position: -119px -102px; 1199 | } 1200 | .tsd-kind-constructor.tsd-parent-kind-enum > .tsd-kind-icon:before { 1201 | background-position: -170px -102px; 1202 | } 1203 | .tsd-kind-constructor.tsd-parent-kind-enum.tsd-is-protected > .tsd-kind-icon:before { 1204 | background-position: -187px -102px; 1205 | } 1206 | .tsd-kind-constructor.tsd-parent-kind-enum.tsd-is-private > .tsd-kind-icon:before { 1207 | background-position: -119px -102px; 1208 | } 1209 | .tsd-kind-constructor.tsd-parent-kind-interface > .tsd-kind-icon:before { 1210 | background-position: -204px -102px; 1211 | } 1212 | .tsd-kind-constructor.tsd-parent-kind-interface.tsd-is-inherited > .tsd-kind-icon:before { 1213 | background-position: -221px -102px; 1214 | } 1215 | 1216 | .tsd-kind-constructor-signature > .tsd-kind-icon:before { 1217 | background-position: -136px -102px; 1218 | } 1219 | .tsd-kind-constructor-signature.tsd-is-protected > .tsd-kind-icon:before { 1220 | background-position: -153px -102px; 1221 | } 1222 | .tsd-kind-constructor-signature.tsd-is-private > .tsd-kind-icon:before { 1223 | background-position: -119px -102px; 1224 | } 1225 | .tsd-kind-constructor-signature.tsd-parent-kind-class > .tsd-kind-icon:before { 1226 | background-position: -51px -102px; 1227 | } 1228 | .tsd-kind-constructor-signature.tsd-parent-kind-class.tsd-is-inherited > .tsd-kind-icon:before { 1229 | background-position: -68px -102px; 1230 | } 1231 | .tsd-kind-constructor-signature.tsd-parent-kind-class.tsd-is-protected > .tsd-kind-icon:before { 1232 | background-position: -85px -102px; 1233 | } 1234 | .tsd-kind-constructor-signature.tsd-parent-kind-class.tsd-is-protected.tsd-is-inherited > .tsd-kind-icon:before { 1235 | background-position: -102px -102px; 1236 | } 1237 | .tsd-kind-constructor-signature.tsd-parent-kind-class.tsd-is-private > .tsd-kind-icon:before { 1238 | background-position: -119px -102px; 1239 | } 1240 | .tsd-kind-constructor-signature.tsd-parent-kind-enum > .tsd-kind-icon:before { 1241 | background-position: -170px -102px; 1242 | } 1243 | .tsd-kind-constructor-signature.tsd-parent-kind-enum.tsd-is-protected > .tsd-kind-icon:before { 1244 | background-position: -187px -102px; 1245 | } 1246 | .tsd-kind-constructor-signature.tsd-parent-kind-enum.tsd-is-private > .tsd-kind-icon:before { 1247 | background-position: -119px -102px; 1248 | } 1249 | .tsd-kind-constructor-signature.tsd-parent-kind-interface > .tsd-kind-icon:before { 1250 | background-position: -204px -102px; 1251 | } 1252 | .tsd-kind-constructor-signature.tsd-parent-kind-interface.tsd-is-inherited > .tsd-kind-icon:before { 1253 | background-position: -221px -102px; 1254 | } 1255 | 1256 | .tsd-kind-index-signature > .tsd-kind-icon:before { 1257 | background-position: -136px -119px; 1258 | } 1259 | .tsd-kind-index-signature.tsd-is-protected > .tsd-kind-icon:before { 1260 | background-position: -153px -119px; 1261 | } 1262 | .tsd-kind-index-signature.tsd-is-private > .tsd-kind-icon:before { 1263 | background-position: -119px -119px; 1264 | } 1265 | .tsd-kind-index-signature.tsd-parent-kind-class > .tsd-kind-icon:before { 1266 | background-position: -51px -119px; 1267 | } 1268 | .tsd-kind-index-signature.tsd-parent-kind-class.tsd-is-inherited > .tsd-kind-icon:before { 1269 | background-position: -68px -119px; 1270 | } 1271 | .tsd-kind-index-signature.tsd-parent-kind-class.tsd-is-protected > .tsd-kind-icon:before { 1272 | background-position: -85px -119px; 1273 | } 1274 | .tsd-kind-index-signature.tsd-parent-kind-class.tsd-is-protected.tsd-is-inherited > .tsd-kind-icon:before { 1275 | background-position: -102px -119px; 1276 | } 1277 | .tsd-kind-index-signature.tsd-parent-kind-class.tsd-is-private > .tsd-kind-icon:before { 1278 | background-position: -119px -119px; 1279 | } 1280 | .tsd-kind-index-signature.tsd-parent-kind-enum > .tsd-kind-icon:before { 1281 | background-position: -170px -119px; 1282 | } 1283 | .tsd-kind-index-signature.tsd-parent-kind-enum.tsd-is-protected > .tsd-kind-icon:before { 1284 | background-position: -187px -119px; 1285 | } 1286 | .tsd-kind-index-signature.tsd-parent-kind-enum.tsd-is-private > .tsd-kind-icon:before { 1287 | background-position: -119px -119px; 1288 | } 1289 | .tsd-kind-index-signature.tsd-parent-kind-interface > .tsd-kind-icon:before { 1290 | background-position: -204px -119px; 1291 | } 1292 | .tsd-kind-index-signature.tsd-parent-kind-interface.tsd-is-inherited > .tsd-kind-icon:before { 1293 | background-position: -221px -119px; 1294 | } 1295 | 1296 | .tsd-kind-event > .tsd-kind-icon:before { 1297 | background-position: -136px -136px; 1298 | } 1299 | .tsd-kind-event.tsd-is-protected > .tsd-kind-icon:before { 1300 | background-position: -153px -136px; 1301 | } 1302 | .tsd-kind-event.tsd-is-private > .tsd-kind-icon:before { 1303 | background-position: -119px -136px; 1304 | } 1305 | .tsd-kind-event.tsd-parent-kind-class > .tsd-kind-icon:before { 1306 | background-position: -51px -136px; 1307 | } 1308 | .tsd-kind-event.tsd-parent-kind-class.tsd-is-inherited > .tsd-kind-icon:before { 1309 | background-position: -68px -136px; 1310 | } 1311 | .tsd-kind-event.tsd-parent-kind-class.tsd-is-protected > .tsd-kind-icon:before { 1312 | background-position: -85px -136px; 1313 | } 1314 | .tsd-kind-event.tsd-parent-kind-class.tsd-is-protected.tsd-is-inherited > .tsd-kind-icon:before { 1315 | background-position: -102px -136px; 1316 | } 1317 | .tsd-kind-event.tsd-parent-kind-class.tsd-is-private > .tsd-kind-icon:before { 1318 | background-position: -119px -136px; 1319 | } 1320 | .tsd-kind-event.tsd-parent-kind-enum > .tsd-kind-icon:before { 1321 | background-position: -170px -136px; 1322 | } 1323 | .tsd-kind-event.tsd-parent-kind-enum.tsd-is-protected > .tsd-kind-icon:before { 1324 | background-position: -187px -136px; 1325 | } 1326 | .tsd-kind-event.tsd-parent-kind-enum.tsd-is-private > .tsd-kind-icon:before { 1327 | background-position: -119px -136px; 1328 | } 1329 | .tsd-kind-event.tsd-parent-kind-interface > .tsd-kind-icon:before { 1330 | background-position: -204px -136px; 1331 | } 1332 | .tsd-kind-event.tsd-parent-kind-interface.tsd-is-inherited > .tsd-kind-icon:before { 1333 | background-position: -221px -136px; 1334 | } 1335 | 1336 | .tsd-is-static > .tsd-kind-icon:before { 1337 | background-position: -136px -153px; 1338 | } 1339 | .tsd-is-static.tsd-is-protected > .tsd-kind-icon:before { 1340 | background-position: -153px -153px; 1341 | } 1342 | .tsd-is-static.tsd-is-private > .tsd-kind-icon:before { 1343 | background-position: -119px -153px; 1344 | } 1345 | .tsd-is-static.tsd-parent-kind-class > .tsd-kind-icon:before { 1346 | background-position: -51px -153px; 1347 | } 1348 | .tsd-is-static.tsd-parent-kind-class.tsd-is-inherited > .tsd-kind-icon:before { 1349 | background-position: -68px -153px; 1350 | } 1351 | .tsd-is-static.tsd-parent-kind-class.tsd-is-protected > .tsd-kind-icon:before { 1352 | background-position: -85px -153px; 1353 | } 1354 | .tsd-is-static.tsd-parent-kind-class.tsd-is-protected.tsd-is-inherited > .tsd-kind-icon:before { 1355 | background-position: -102px -153px; 1356 | } 1357 | .tsd-is-static.tsd-parent-kind-class.tsd-is-private > .tsd-kind-icon:before { 1358 | background-position: -119px -153px; 1359 | } 1360 | .tsd-is-static.tsd-parent-kind-enum > .tsd-kind-icon:before { 1361 | background-position: -170px -153px; 1362 | } 1363 | .tsd-is-static.tsd-parent-kind-enum.tsd-is-protected > .tsd-kind-icon:before { 1364 | background-position: -187px -153px; 1365 | } 1366 | .tsd-is-static.tsd-parent-kind-enum.tsd-is-private > .tsd-kind-icon:before { 1367 | background-position: -119px -153px; 1368 | } 1369 | .tsd-is-static.tsd-parent-kind-interface > .tsd-kind-icon:before { 1370 | background-position: -204px -153px; 1371 | } 1372 | .tsd-is-static.tsd-parent-kind-interface.tsd-is-inherited > .tsd-kind-icon:before { 1373 | background-position: -221px -153px; 1374 | } 1375 | 1376 | .tsd-is-static.tsd-kind-function > .tsd-kind-icon:before { 1377 | background-position: -136px -170px; 1378 | } 1379 | .tsd-is-static.tsd-kind-function.tsd-is-protected > .tsd-kind-icon:before { 1380 | background-position: -153px -170px; 1381 | } 1382 | .tsd-is-static.tsd-kind-function.tsd-is-private > .tsd-kind-icon:before { 1383 | background-position: -119px -170px; 1384 | } 1385 | .tsd-is-static.tsd-kind-function.tsd-parent-kind-class > .tsd-kind-icon:before { 1386 | background-position: -51px -170px; 1387 | } 1388 | .tsd-is-static.tsd-kind-function.tsd-parent-kind-class.tsd-is-inherited > .tsd-kind-icon:before { 1389 | background-position: -68px -170px; 1390 | } 1391 | .tsd-is-static.tsd-kind-function.tsd-parent-kind-class.tsd-is-protected > .tsd-kind-icon:before { 1392 | background-position: -85px -170px; 1393 | } 1394 | .tsd-is-static.tsd-kind-function.tsd-parent-kind-class.tsd-is-protected.tsd-is-inherited > .tsd-kind-icon:before { 1395 | background-position: -102px -170px; 1396 | } 1397 | .tsd-is-static.tsd-kind-function.tsd-parent-kind-class.tsd-is-private > .tsd-kind-icon:before { 1398 | background-position: -119px -170px; 1399 | } 1400 | .tsd-is-static.tsd-kind-function.tsd-parent-kind-enum > .tsd-kind-icon:before { 1401 | background-position: -170px -170px; 1402 | } 1403 | .tsd-is-static.tsd-kind-function.tsd-parent-kind-enum.tsd-is-protected > .tsd-kind-icon:before { 1404 | background-position: -187px -170px; 1405 | } 1406 | .tsd-is-static.tsd-kind-function.tsd-parent-kind-enum.tsd-is-private > .tsd-kind-icon:before { 1407 | background-position: -119px -170px; 1408 | } 1409 | .tsd-is-static.tsd-kind-function.tsd-parent-kind-interface > .tsd-kind-icon:before { 1410 | background-position: -204px -170px; 1411 | } 1412 | .tsd-is-static.tsd-kind-function.tsd-parent-kind-interface.tsd-is-inherited > .tsd-kind-icon:before { 1413 | background-position: -221px -170px; 1414 | } 1415 | 1416 | .tsd-is-static.tsd-kind-method > .tsd-kind-icon:before { 1417 | background-position: -136px -170px; 1418 | } 1419 | .tsd-is-static.tsd-kind-method.tsd-is-protected > .tsd-kind-icon:before { 1420 | background-position: -153px -170px; 1421 | } 1422 | .tsd-is-static.tsd-kind-method.tsd-is-private > .tsd-kind-icon:before { 1423 | background-position: -119px -170px; 1424 | } 1425 | .tsd-is-static.tsd-kind-method.tsd-parent-kind-class > .tsd-kind-icon:before { 1426 | background-position: -51px -170px; 1427 | } 1428 | .tsd-is-static.tsd-kind-method.tsd-parent-kind-class.tsd-is-inherited > .tsd-kind-icon:before { 1429 | background-position: -68px -170px; 1430 | } 1431 | .tsd-is-static.tsd-kind-method.tsd-parent-kind-class.tsd-is-protected > .tsd-kind-icon:before { 1432 | background-position: -85px -170px; 1433 | } 1434 | .tsd-is-static.tsd-kind-method.tsd-parent-kind-class.tsd-is-protected.tsd-is-inherited > .tsd-kind-icon:before { 1435 | background-position: -102px -170px; 1436 | } 1437 | .tsd-is-static.tsd-kind-method.tsd-parent-kind-class.tsd-is-private > .tsd-kind-icon:before { 1438 | background-position: -119px -170px; 1439 | } 1440 | .tsd-is-static.tsd-kind-method.tsd-parent-kind-enum > .tsd-kind-icon:before { 1441 | background-position: -170px -170px; 1442 | } 1443 | .tsd-is-static.tsd-kind-method.tsd-parent-kind-enum.tsd-is-protected > .tsd-kind-icon:before { 1444 | background-position: -187px -170px; 1445 | } 1446 | .tsd-is-static.tsd-kind-method.tsd-parent-kind-enum.tsd-is-private > .tsd-kind-icon:before { 1447 | background-position: -119px -170px; 1448 | } 1449 | .tsd-is-static.tsd-kind-method.tsd-parent-kind-interface > .tsd-kind-icon:before { 1450 | background-position: -204px -170px; 1451 | } 1452 | .tsd-is-static.tsd-kind-method.tsd-parent-kind-interface.tsd-is-inherited > .tsd-kind-icon:before { 1453 | background-position: -221px -170px; 1454 | } 1455 | 1456 | .tsd-is-static.tsd-kind-call-signature > .tsd-kind-icon:before { 1457 | background-position: -136px -170px; 1458 | } 1459 | .tsd-is-static.tsd-kind-call-signature.tsd-is-protected > .tsd-kind-icon:before { 1460 | background-position: -153px -170px; 1461 | } 1462 | .tsd-is-static.tsd-kind-call-signature.tsd-is-private > .tsd-kind-icon:before { 1463 | background-position: -119px -170px; 1464 | } 1465 | .tsd-is-static.tsd-kind-call-signature.tsd-parent-kind-class > .tsd-kind-icon:before { 1466 | background-position: -51px -170px; 1467 | } 1468 | .tsd-is-static.tsd-kind-call-signature.tsd-parent-kind-class.tsd-is-inherited > .tsd-kind-icon:before { 1469 | background-position: -68px -170px; 1470 | } 1471 | .tsd-is-static.tsd-kind-call-signature.tsd-parent-kind-class.tsd-is-protected > .tsd-kind-icon:before { 1472 | background-position: -85px -170px; 1473 | } 1474 | .tsd-is-static.tsd-kind-call-signature.tsd-parent-kind-class.tsd-is-protected.tsd-is-inherited > .tsd-kind-icon:before { 1475 | background-position: -102px -170px; 1476 | } 1477 | .tsd-is-static.tsd-kind-call-signature.tsd-parent-kind-class.tsd-is-private > .tsd-kind-icon:before { 1478 | background-position: -119px -170px; 1479 | } 1480 | .tsd-is-static.tsd-kind-call-signature.tsd-parent-kind-enum > .tsd-kind-icon:before { 1481 | background-position: -170px -170px; 1482 | } 1483 | .tsd-is-static.tsd-kind-call-signature.tsd-parent-kind-enum.tsd-is-protected > .tsd-kind-icon:before { 1484 | background-position: -187px -170px; 1485 | } 1486 | .tsd-is-static.tsd-kind-call-signature.tsd-parent-kind-enum.tsd-is-private > .tsd-kind-icon:before { 1487 | background-position: -119px -170px; 1488 | } 1489 | .tsd-is-static.tsd-kind-call-signature.tsd-parent-kind-interface > .tsd-kind-icon:before { 1490 | background-position: -204px -170px; 1491 | } 1492 | .tsd-is-static.tsd-kind-call-signature.tsd-parent-kind-interface.tsd-is-inherited > .tsd-kind-icon:before { 1493 | background-position: -221px -170px; 1494 | } 1495 | 1496 | .tsd-is-static.tsd-kind-event > .tsd-kind-icon:before { 1497 | background-position: -136px -187px; 1498 | } 1499 | .tsd-is-static.tsd-kind-event.tsd-is-protected > .tsd-kind-icon:before { 1500 | background-position: -153px -187px; 1501 | } 1502 | .tsd-is-static.tsd-kind-event.tsd-is-private > .tsd-kind-icon:before { 1503 | background-position: -119px -187px; 1504 | } 1505 | .tsd-is-static.tsd-kind-event.tsd-parent-kind-class > .tsd-kind-icon:before { 1506 | background-position: -51px -187px; 1507 | } 1508 | .tsd-is-static.tsd-kind-event.tsd-parent-kind-class.tsd-is-inherited > .tsd-kind-icon:before { 1509 | background-position: -68px -187px; 1510 | } 1511 | .tsd-is-static.tsd-kind-event.tsd-parent-kind-class.tsd-is-protected > .tsd-kind-icon:before { 1512 | background-position: -85px -187px; 1513 | } 1514 | .tsd-is-static.tsd-kind-event.tsd-parent-kind-class.tsd-is-protected.tsd-is-inherited > .tsd-kind-icon:before { 1515 | background-position: -102px -187px; 1516 | } 1517 | .tsd-is-static.tsd-kind-event.tsd-parent-kind-class.tsd-is-private > .tsd-kind-icon:before { 1518 | background-position: -119px -187px; 1519 | } 1520 | .tsd-is-static.tsd-kind-event.tsd-parent-kind-enum > .tsd-kind-icon:before { 1521 | background-position: -170px -187px; 1522 | } 1523 | .tsd-is-static.tsd-kind-event.tsd-parent-kind-enum.tsd-is-protected > .tsd-kind-icon:before { 1524 | background-position: -187px -187px; 1525 | } 1526 | .tsd-is-static.tsd-kind-event.tsd-parent-kind-enum.tsd-is-private > .tsd-kind-icon:before { 1527 | background-position: -119px -187px; 1528 | } 1529 | .tsd-is-static.tsd-kind-event.tsd-parent-kind-interface > .tsd-kind-icon:before { 1530 | background-position: -204px -187px; 1531 | } 1532 | .tsd-is-static.tsd-kind-event.tsd-parent-kind-interface.tsd-is-inherited > .tsd-kind-icon:before { 1533 | background-position: -221px -187px; 1534 | } 1535 | 1536 | @keyframes fade-in { 1537 | from { 1538 | opacity: 0; 1539 | } 1540 | to { 1541 | opacity: 1; 1542 | } 1543 | } 1544 | @keyframes fade-out { 1545 | from { 1546 | opacity: 1; 1547 | visibility: visible; 1548 | } 1549 | to { 1550 | opacity: 0; 1551 | } 1552 | } 1553 | @keyframes fade-in-delayed { 1554 | 0% { 1555 | opacity: 0; 1556 | } 1557 | 33% { 1558 | opacity: 0; 1559 | } 1560 | 100% { 1561 | opacity: 1; 1562 | } 1563 | } 1564 | @keyframes fade-out-delayed { 1565 | 0% { 1566 | opacity: 1; 1567 | visibility: visible; 1568 | } 1569 | 66% { 1570 | opacity: 0; 1571 | } 1572 | 100% { 1573 | opacity: 0; 1574 | } 1575 | } 1576 | @keyframes shift-to-left { 1577 | from { 1578 | transform: translate(0, 0); 1579 | } 1580 | to { 1581 | transform: translate(-25%, 0); 1582 | } 1583 | } 1584 | @keyframes unshift-to-left { 1585 | from { 1586 | transform: translate(-25%, 0); 1587 | } 1588 | to { 1589 | transform: translate(0, 0); 1590 | } 1591 | } 1592 | @keyframes pop-in-from-right { 1593 | from { 1594 | transform: translate(100%, 0); 1595 | } 1596 | to { 1597 | transform: translate(0, 0); 1598 | } 1599 | } 1600 | @keyframes pop-out-to-right { 1601 | from { 1602 | transform: translate(0, 0); 1603 | visibility: visible; 1604 | } 1605 | to { 1606 | transform: translate(100%, 0); 1607 | } 1608 | } 1609 | body { 1610 | background: var(--color-background); 1611 | font-family: "Segoe UI", sans-serif; 1612 | font-size: 16px; 1613 | color: var(--color-text); 1614 | } 1615 | 1616 | a { 1617 | color: var(--color-link); 1618 | text-decoration: none; 1619 | } 1620 | a:hover { 1621 | text-decoration: underline; 1622 | } 1623 | 1624 | code, pre { 1625 | font-family: Menlo, Monaco, Consolas, "Courier New", monospace; 1626 | padding: 0.2em; 1627 | margin: 0; 1628 | font-size: 14px; 1629 | background-color: var(--color-code-background); 1630 | } 1631 | 1632 | pre { 1633 | padding: 10px; 1634 | } 1635 | pre code { 1636 | padding: 0; 1637 | font-size: 100%; 1638 | background-color: transparent; 1639 | } 1640 | 1641 | blockquote { 1642 | margin: 1em 0; 1643 | padding-left: 1em; 1644 | border-left: 4px solid gray; 1645 | } 1646 | 1647 | .tsd-typography { 1648 | line-height: 1.333em; 1649 | } 1650 | .tsd-typography ul { 1651 | list-style: square; 1652 | padding: 0 0 0 20px; 1653 | margin: 0; 1654 | } 1655 | .tsd-typography h4, .tsd-typography .tsd-index-panel h3, .tsd-index-panel .tsd-typography h3, .tsd-typography h5, .tsd-typography h6 { 1656 | font-size: 1em; 1657 | margin: 0; 1658 | } 1659 | .tsd-typography h5, .tsd-typography h6 { 1660 | font-weight: normal; 1661 | } 1662 | .tsd-typography p, .tsd-typography ul, .tsd-typography ol { 1663 | margin: 1em 0; 1664 | } 1665 | 1666 | @media (min-width: 901px) and (max-width: 1024px) { 1667 | html.default .col-content { 1668 | width: 72%; 1669 | } 1670 | html.default .col-menu { 1671 | width: 28%; 1672 | } 1673 | html.default .tsd-navigation { 1674 | padding-left: 10px; 1675 | } 1676 | } 1677 | @media (max-width: 900px) { 1678 | html.default .col-content { 1679 | float: none; 1680 | width: 100%; 1681 | } 1682 | html.default .col-menu { 1683 | position: fixed !important; 1684 | overflow: auto; 1685 | -webkit-overflow-scrolling: touch; 1686 | z-index: 1024; 1687 | top: 0 !important; 1688 | bottom: 0 !important; 1689 | left: auto !important; 1690 | right: 0 !important; 1691 | width: 100%; 1692 | padding: 20px 20px 0 0; 1693 | max-width: 450px; 1694 | visibility: hidden; 1695 | background-color: var(--color-panel); 1696 | transform: translate(100%, 0); 1697 | } 1698 | html.default .col-menu > *:last-child { 1699 | padding-bottom: 20px; 1700 | } 1701 | html.default .overlay { 1702 | content: ""; 1703 | display: block; 1704 | position: fixed; 1705 | z-index: 1023; 1706 | top: 0; 1707 | left: 0; 1708 | right: 0; 1709 | bottom: 0; 1710 | background-color: rgba(0, 0, 0, 0.75); 1711 | visibility: hidden; 1712 | } 1713 | html.default.to-has-menu .overlay { 1714 | animation: fade-in 0.4s; 1715 | } 1716 | html.default.to-has-menu header, 1717 | html.default.to-has-menu footer, 1718 | html.default.to-has-menu .col-content { 1719 | animation: shift-to-left 0.4s; 1720 | } 1721 | html.default.to-has-menu .col-menu { 1722 | animation: pop-in-from-right 0.4s; 1723 | } 1724 | html.default.from-has-menu .overlay { 1725 | animation: fade-out 0.4s; 1726 | } 1727 | html.default.from-has-menu header, 1728 | html.default.from-has-menu footer, 1729 | html.default.from-has-menu .col-content { 1730 | animation: unshift-to-left 0.4s; 1731 | } 1732 | html.default.from-has-menu .col-menu { 1733 | animation: pop-out-to-right 0.4s; 1734 | } 1735 | html.default.has-menu body { 1736 | overflow: hidden; 1737 | } 1738 | html.default.has-menu .overlay { 1739 | visibility: visible; 1740 | } 1741 | html.default.has-menu header, 1742 | html.default.has-menu footer, 1743 | html.default.has-menu .col-content { 1744 | transform: translate(-25%, 0); 1745 | } 1746 | html.default.has-menu .col-menu { 1747 | visibility: visible; 1748 | transform: translate(0, 0); 1749 | } 1750 | } 1751 | 1752 | .tsd-page-title { 1753 | padding: 70px 0 20px 0; 1754 | margin: 0 0 40px 0; 1755 | background: var(--color-panel); 1756 | box-shadow: 0 0 5px rgba(0, 0, 0, 0.35); 1757 | } 1758 | .tsd-page-title h1 { 1759 | margin: 0; 1760 | } 1761 | 1762 | .tsd-breadcrumb { 1763 | margin: 0; 1764 | padding: 0; 1765 | color: var(--color-text-aside); 1766 | } 1767 | .tsd-breadcrumb a { 1768 | color: var(--color-text-aside); 1769 | text-decoration: none; 1770 | } 1771 | .tsd-breadcrumb a:hover { 1772 | text-decoration: underline; 1773 | } 1774 | .tsd-breadcrumb li { 1775 | display: inline; 1776 | } 1777 | .tsd-breadcrumb li:after { 1778 | content: " / "; 1779 | } 1780 | 1781 | html.minimal .container { 1782 | margin: 0; 1783 | } 1784 | html.minimal .container-main { 1785 | padding-top: 50px; 1786 | padding-bottom: 0; 1787 | } 1788 | html.minimal .content-wrap { 1789 | padding-left: 300px; 1790 | } 1791 | html.minimal .tsd-navigation { 1792 | position: fixed !important; 1793 | overflow: auto; 1794 | -webkit-overflow-scrolling: touch; 1795 | box-sizing: border-box; 1796 | z-index: 1; 1797 | left: 0; 1798 | top: 40px; 1799 | bottom: 0; 1800 | width: 300px; 1801 | padding: 20px; 1802 | margin: 0; 1803 | } 1804 | html.minimal .tsd-member .tsd-member { 1805 | margin-left: 0; 1806 | } 1807 | html.minimal .tsd-page-toolbar { 1808 | position: fixed; 1809 | z-index: 2; 1810 | } 1811 | html.minimal #tsd-filter .tsd-filter-group { 1812 | right: 0; 1813 | transform: none; 1814 | } 1815 | html.minimal footer { 1816 | background-color: transparent; 1817 | } 1818 | html.minimal footer .container { 1819 | padding: 0; 1820 | } 1821 | html.minimal .tsd-generator { 1822 | padding: 0; 1823 | } 1824 | @media (max-width: 900px) { 1825 | html.minimal .tsd-navigation { 1826 | display: none; 1827 | } 1828 | html.minimal .content-wrap { 1829 | padding-left: 0; 1830 | } 1831 | } 1832 | 1833 | dl.tsd-comment-tags { 1834 | overflow: hidden; 1835 | } 1836 | dl.tsd-comment-tags dt { 1837 | float: left; 1838 | padding: 1px 5px; 1839 | margin: 0 10px 0 0; 1840 | border-radius: 4px; 1841 | border: 1px solid var(--color-comment-tag); 1842 | color: var(--color-comment-tag); 1843 | font-size: 0.8em; 1844 | font-weight: normal; 1845 | } 1846 | dl.tsd-comment-tags dd { 1847 | margin: 0 0 10px 0; 1848 | } 1849 | dl.tsd-comment-tags dd:before, dl.tsd-comment-tags dd:after { 1850 | display: table; 1851 | content: " "; 1852 | } 1853 | dl.tsd-comment-tags dd pre, dl.tsd-comment-tags dd:after { 1854 | clear: both; 1855 | } 1856 | dl.tsd-comment-tags p { 1857 | margin: 0; 1858 | } 1859 | 1860 | .tsd-panel.tsd-comment .lead { 1861 | font-size: 1.1em; 1862 | line-height: 1.333em; 1863 | margin-bottom: 2em; 1864 | } 1865 | .tsd-panel.tsd-comment .lead:last-child { 1866 | margin-bottom: 0; 1867 | } 1868 | 1869 | .toggle-protected .tsd-is-private { 1870 | display: none; 1871 | } 1872 | 1873 | .toggle-public .tsd-is-private, 1874 | .toggle-public .tsd-is-protected, 1875 | .toggle-public .tsd-is-private-protected { 1876 | display: none; 1877 | } 1878 | 1879 | .toggle-inherited .tsd-is-inherited { 1880 | display: none; 1881 | } 1882 | 1883 | .toggle-externals .tsd-is-external { 1884 | display: none; 1885 | } 1886 | 1887 | #tsd-filter { 1888 | position: relative; 1889 | display: inline-block; 1890 | height: 40px; 1891 | vertical-align: bottom; 1892 | } 1893 | .no-filter #tsd-filter { 1894 | display: none; 1895 | } 1896 | #tsd-filter .tsd-filter-group { 1897 | display: inline-block; 1898 | height: 40px; 1899 | vertical-align: bottom; 1900 | white-space: nowrap; 1901 | } 1902 | #tsd-filter input { 1903 | display: none; 1904 | } 1905 | @media (max-width: 900px) { 1906 | #tsd-filter .tsd-filter-group { 1907 | display: block; 1908 | position: absolute; 1909 | top: 40px; 1910 | right: 20px; 1911 | height: auto; 1912 | background-color: var(--color-panel); 1913 | visibility: hidden; 1914 | transform: translate(50%, 0); 1915 | box-shadow: 0 0 4px rgba(0, 0, 0, 0.25); 1916 | } 1917 | .has-options #tsd-filter .tsd-filter-group { 1918 | visibility: visible; 1919 | } 1920 | .to-has-options #tsd-filter .tsd-filter-group { 1921 | animation: fade-in 0.2s; 1922 | } 1923 | .from-has-options #tsd-filter .tsd-filter-group { 1924 | animation: fade-out 0.2s; 1925 | } 1926 | #tsd-filter label, 1927 | #tsd-filter .tsd-select { 1928 | display: block; 1929 | padding-right: 20px; 1930 | } 1931 | } 1932 | 1933 | footer { 1934 | border-top: 1px solid var(--color-panel-divider); 1935 | background-color: var(--color-panel); 1936 | } 1937 | footer.with-border-bottom { 1938 | border-bottom: 1px solid var(--color-panel-divider); 1939 | } 1940 | footer .tsd-legend-group { 1941 | font-size: 0; 1942 | } 1943 | footer .tsd-legend { 1944 | display: inline-block; 1945 | width: 25%; 1946 | padding: 0; 1947 | font-size: 16px; 1948 | list-style: none; 1949 | line-height: 1.333em; 1950 | vertical-align: top; 1951 | } 1952 | @media (max-width: 900px) { 1953 | footer .tsd-legend { 1954 | width: 50%; 1955 | } 1956 | } 1957 | 1958 | .tsd-hierarchy { 1959 | list-style: square; 1960 | padding: 0 0 0 20px; 1961 | margin: 0; 1962 | } 1963 | .tsd-hierarchy .target { 1964 | font-weight: bold; 1965 | } 1966 | 1967 | .tsd-index-panel .tsd-index-content { 1968 | margin-bottom: -30px !important; 1969 | } 1970 | .tsd-index-panel .tsd-index-section { 1971 | margin-bottom: 30px !important; 1972 | } 1973 | .tsd-index-panel h3 { 1974 | margin: 0 -20px 10px -20px; 1975 | padding: 0 20px 10px 20px; 1976 | border-bottom: 1px solid var(--color-panel-divider); 1977 | } 1978 | .tsd-index-panel ul.tsd-index-list { 1979 | -webkit-column-count: 3; 1980 | -moz-column-count: 3; 1981 | -ms-column-count: 3; 1982 | -o-column-count: 3; 1983 | column-count: 3; 1984 | -webkit-column-gap: 20px; 1985 | -moz-column-gap: 20px; 1986 | -ms-column-gap: 20px; 1987 | -o-column-gap: 20px; 1988 | column-gap: 20px; 1989 | padding: 0; 1990 | list-style: none; 1991 | line-height: 1.333em; 1992 | } 1993 | @media (max-width: 900px) { 1994 | .tsd-index-panel ul.tsd-index-list { 1995 | -webkit-column-count: 1; 1996 | -moz-column-count: 1; 1997 | -ms-column-count: 1; 1998 | -o-column-count: 1; 1999 | column-count: 1; 2000 | } 2001 | } 2002 | @media (min-width: 901px) and (max-width: 1024px) { 2003 | .tsd-index-panel ul.tsd-index-list { 2004 | -webkit-column-count: 2; 2005 | -moz-column-count: 2; 2006 | -ms-column-count: 2; 2007 | -o-column-count: 2; 2008 | column-count: 2; 2009 | } 2010 | } 2011 | .tsd-index-panel ul.tsd-index-list li { 2012 | -webkit-page-break-inside: avoid; 2013 | -moz-page-break-inside: avoid; 2014 | -ms-page-break-inside: avoid; 2015 | -o-page-break-inside: avoid; 2016 | page-break-inside: avoid; 2017 | } 2018 | .tsd-index-panel a, 2019 | .tsd-index-panel .tsd-parent-kind-module a { 2020 | color: var(--color-ts); 2021 | } 2022 | .tsd-index-panel .tsd-parent-kind-interface a { 2023 | color: var(--color-ts-interface); 2024 | } 2025 | .tsd-index-panel .tsd-parent-kind-enum a { 2026 | color: var(--color-ts-enum); 2027 | } 2028 | .tsd-index-panel .tsd-parent-kind-class a { 2029 | color: var(--color-ts-class); 2030 | } 2031 | .tsd-index-panel .tsd-kind-module a { 2032 | color: var(--color-ts); 2033 | } 2034 | .tsd-index-panel .tsd-kind-interface a { 2035 | color: var(--color-ts-interface); 2036 | } 2037 | .tsd-index-panel .tsd-kind-enum a { 2038 | color: var(--color-ts-enum); 2039 | } 2040 | .tsd-index-panel .tsd-kind-class a { 2041 | color: var(--color-ts-class); 2042 | } 2043 | .tsd-index-panel .tsd-is-private a { 2044 | color: var(--color-ts-private); 2045 | } 2046 | 2047 | .tsd-flag { 2048 | display: inline-block; 2049 | padding: 1px 5px; 2050 | border-radius: 4px; 2051 | color: var(--color-comment-tag-text); 2052 | background-color: var(--color-comment-tag); 2053 | text-indent: 0; 2054 | font-size: 14px; 2055 | font-weight: normal; 2056 | } 2057 | 2058 | .tsd-anchor { 2059 | position: absolute; 2060 | top: -100px; 2061 | } 2062 | 2063 | .tsd-member { 2064 | position: relative; 2065 | } 2066 | .tsd-member .tsd-anchor + h3 { 2067 | margin-top: 0; 2068 | margin-bottom: 0; 2069 | border-bottom: none; 2070 | } 2071 | .tsd-member a[data-tsd-kind] { 2072 | color: var(--color-ts); 2073 | } 2074 | .tsd-member a[data-tsd-kind=Interface] { 2075 | color: var(--color-ts-interface); 2076 | } 2077 | .tsd-member a[data-tsd-kind=Enum] { 2078 | color: var(--color-ts-enum); 2079 | } 2080 | .tsd-member a[data-tsd-kind=Class] { 2081 | color: var(--color-ts-class); 2082 | } 2083 | .tsd-member a[data-tsd-kind=Private] { 2084 | color: var(--color-ts-private); 2085 | } 2086 | 2087 | .tsd-navigation { 2088 | margin: 0 0 0 40px; 2089 | } 2090 | .tsd-navigation a { 2091 | display: block; 2092 | padding-top: 2px; 2093 | padding-bottom: 2px; 2094 | border-left: 2px solid transparent; 2095 | color: var(--color-text); 2096 | text-decoration: none; 2097 | transition: border-left-color 0.1s; 2098 | } 2099 | .tsd-navigation a:hover { 2100 | text-decoration: underline; 2101 | } 2102 | .tsd-navigation ul { 2103 | margin: 0; 2104 | padding: 0; 2105 | list-style: none; 2106 | } 2107 | .tsd-navigation li { 2108 | padding: 0; 2109 | } 2110 | 2111 | .tsd-navigation.primary { 2112 | padding-bottom: 40px; 2113 | } 2114 | .tsd-navigation.primary a { 2115 | display: block; 2116 | padding-top: 6px; 2117 | padding-bottom: 6px; 2118 | } 2119 | .tsd-navigation.primary ul li a { 2120 | padding-left: 5px; 2121 | } 2122 | .tsd-navigation.primary ul li li a { 2123 | padding-left: 25px; 2124 | } 2125 | .tsd-navigation.primary ul li li li a { 2126 | padding-left: 45px; 2127 | } 2128 | .tsd-navigation.primary ul li li li li a { 2129 | padding-left: 65px; 2130 | } 2131 | .tsd-navigation.primary ul li li li li li a { 2132 | padding-left: 85px; 2133 | } 2134 | .tsd-navigation.primary ul li li li li li li a { 2135 | padding-left: 105px; 2136 | } 2137 | .tsd-navigation.primary > ul { 2138 | border-bottom: 1px solid var(--color-panel-divider); 2139 | } 2140 | .tsd-navigation.primary li { 2141 | border-top: 1px solid var(--color-panel-divider); 2142 | } 2143 | .tsd-navigation.primary li.current > a { 2144 | font-weight: bold; 2145 | } 2146 | .tsd-navigation.primary li.label span { 2147 | display: block; 2148 | padding: 20px 0 6px 5px; 2149 | color: var(--color-menu-label); 2150 | } 2151 | .tsd-navigation.primary li.globals + li > span, .tsd-navigation.primary li.globals + li > a { 2152 | padding-top: 20px; 2153 | } 2154 | 2155 | .tsd-navigation.secondary { 2156 | max-height: calc(100vh - 1rem - 40px); 2157 | overflow: auto; 2158 | position: -webkit-sticky; 2159 | position: sticky; 2160 | top: calc(.5rem + 40px); 2161 | transition: 0.3s; 2162 | } 2163 | .tsd-navigation.secondary.tsd-navigation--toolbar-hide { 2164 | max-height: calc(100vh - 1rem); 2165 | top: 0.5rem; 2166 | } 2167 | .tsd-navigation.secondary ul { 2168 | transition: opacity 0.2s; 2169 | } 2170 | .tsd-navigation.secondary ul li a { 2171 | padding-left: 25px; 2172 | } 2173 | .tsd-navigation.secondary ul li li a { 2174 | padding-left: 45px; 2175 | } 2176 | .tsd-navigation.secondary ul li li li a { 2177 | padding-left: 65px; 2178 | } 2179 | .tsd-navigation.secondary ul li li li li a { 2180 | padding-left: 85px; 2181 | } 2182 | .tsd-navigation.secondary ul li li li li li a { 2183 | padding-left: 105px; 2184 | } 2185 | .tsd-navigation.secondary ul li li li li li li a { 2186 | padding-left: 125px; 2187 | } 2188 | .tsd-navigation.secondary ul.current a { 2189 | border-left-color: var(--color-panel-divider); 2190 | } 2191 | .tsd-navigation.secondary li.focus > a, 2192 | .tsd-navigation.secondary ul.current li.focus > a { 2193 | border-left-color: var(--color-menu-divider-focus); 2194 | } 2195 | .tsd-navigation.secondary li.current { 2196 | margin-top: 20px; 2197 | margin-bottom: 20px; 2198 | border-left-color: var(--color-panel-divider); 2199 | } 2200 | .tsd-navigation.secondary li.current > a { 2201 | font-weight: bold; 2202 | } 2203 | 2204 | @media (min-width: 901px) { 2205 | .menu-sticky-wrap { 2206 | position: static; 2207 | } 2208 | } 2209 | 2210 | .tsd-panel { 2211 | margin: 20px 0; 2212 | padding: 20px; 2213 | background-color: var(--color-panel); 2214 | box-shadow: 0 0 4px rgba(0, 0, 0, 0.25); 2215 | } 2216 | .tsd-panel:empty { 2217 | display: none; 2218 | } 2219 | .tsd-panel > h1, .tsd-panel > h2, .tsd-panel > h3 { 2220 | margin: 1.5em -20px 10px -20px; 2221 | padding: 0 20px 10px 20px; 2222 | border-bottom: 1px solid var(--color-panel-divider); 2223 | } 2224 | .tsd-panel > h1.tsd-before-signature, .tsd-panel > h2.tsd-before-signature, .tsd-panel > h3.tsd-before-signature { 2225 | margin-bottom: 0; 2226 | border-bottom: 0; 2227 | } 2228 | .tsd-panel table { 2229 | display: block; 2230 | width: 100%; 2231 | overflow: auto; 2232 | margin-top: 10px; 2233 | word-break: normal; 2234 | word-break: keep-all; 2235 | } 2236 | .tsd-panel table th { 2237 | font-weight: bold; 2238 | } 2239 | .tsd-panel table th, .tsd-panel table td { 2240 | padding: 6px 13px; 2241 | border: 1px solid #ddd; 2242 | } 2243 | .tsd-panel table tr { 2244 | background-color: #fff; 2245 | border-top: 1px solid #ccc; 2246 | } 2247 | .tsd-panel table tr:nth-child(2n) { 2248 | background-color: #f8f8f8; 2249 | } 2250 | 2251 | .tsd-panel-group { 2252 | margin: 60px 0; 2253 | } 2254 | .tsd-panel-group > h1, .tsd-panel-group > h2, .tsd-panel-group > h3 { 2255 | padding-left: 20px; 2256 | padding-right: 20px; 2257 | } 2258 | 2259 | #tsd-search { 2260 | transition: background-color 0.2s; 2261 | } 2262 | #tsd-search .title { 2263 | position: relative; 2264 | z-index: 2; 2265 | } 2266 | #tsd-search .field { 2267 | position: absolute; 2268 | left: 0; 2269 | top: 0; 2270 | right: 40px; 2271 | height: 40px; 2272 | } 2273 | #tsd-search .field input { 2274 | box-sizing: border-box; 2275 | position: relative; 2276 | top: -50px; 2277 | z-index: 1; 2278 | width: 100%; 2279 | padding: 0 10px; 2280 | opacity: 0; 2281 | outline: 0; 2282 | border: 0; 2283 | background: transparent; 2284 | color: var(--color-text); 2285 | } 2286 | #tsd-search .field label { 2287 | position: absolute; 2288 | overflow: hidden; 2289 | right: -40px; 2290 | } 2291 | #tsd-search .field input, 2292 | #tsd-search .title { 2293 | transition: opacity 0.2s; 2294 | } 2295 | #tsd-search .results { 2296 | position: absolute; 2297 | visibility: hidden; 2298 | top: 40px; 2299 | width: 100%; 2300 | margin: 0; 2301 | padding: 0; 2302 | list-style: none; 2303 | box-shadow: 0 0 4px rgba(0, 0, 0, 0.25); 2304 | } 2305 | #tsd-search .results li { 2306 | padding: 0 10px; 2307 | background-color: var(--color-background); 2308 | } 2309 | #tsd-search .results li:nth-child(even) { 2310 | background-color: var(--color-panel); 2311 | } 2312 | #tsd-search .results li.state { 2313 | display: none; 2314 | } 2315 | #tsd-search .results li.current, 2316 | #tsd-search .results li:hover { 2317 | background-color: var(--color-panel-divider); 2318 | } 2319 | #tsd-search .results a { 2320 | display: block; 2321 | } 2322 | #tsd-search .results a:before { 2323 | top: 10px; 2324 | } 2325 | #tsd-search .results span.parent { 2326 | color: var(--color-text-aside); 2327 | font-weight: normal; 2328 | } 2329 | #tsd-search.has-focus { 2330 | background-color: var(--color-panel-divider); 2331 | } 2332 | #tsd-search.has-focus .field input { 2333 | top: 0; 2334 | opacity: 1; 2335 | } 2336 | #tsd-search.has-focus .title { 2337 | z-index: 0; 2338 | opacity: 0; 2339 | } 2340 | #tsd-search.has-focus .results { 2341 | visibility: visible; 2342 | } 2343 | #tsd-search.loading .results li.state.loading { 2344 | display: block; 2345 | } 2346 | #tsd-search.failure .results li.state.failure { 2347 | display: block; 2348 | } 2349 | 2350 | .tsd-signature { 2351 | margin: 0 0 1em 0; 2352 | padding: 10px; 2353 | border: 1px solid var(--color-panel-divider); 2354 | font-family: Menlo, Monaco, Consolas, "Courier New", monospace; 2355 | font-size: 14px; 2356 | overflow-x: auto; 2357 | } 2358 | .tsd-signature.tsd-kind-icon { 2359 | padding-left: 30px; 2360 | } 2361 | .tsd-signature.tsd-kind-icon:before { 2362 | top: 10px; 2363 | left: 10px; 2364 | } 2365 | .tsd-panel > .tsd-signature { 2366 | margin-left: -20px; 2367 | margin-right: -20px; 2368 | border-width: 1px 0; 2369 | } 2370 | .tsd-panel > .tsd-signature.tsd-kind-icon { 2371 | padding-left: 40px; 2372 | } 2373 | .tsd-panel > .tsd-signature.tsd-kind-icon:before { 2374 | left: 20px; 2375 | } 2376 | 2377 | .tsd-signature-symbol { 2378 | color: var(--color-text-aside); 2379 | font-weight: normal; 2380 | } 2381 | 2382 | .tsd-signature-type { 2383 | font-style: italic; 2384 | font-weight: normal; 2385 | } 2386 | 2387 | .tsd-signatures { 2388 | padding: 0; 2389 | margin: 0 0 1em 0; 2390 | border: 1px solid var(--color-panel-divider); 2391 | } 2392 | .tsd-signatures .tsd-signature { 2393 | margin: 0; 2394 | border-width: 1px 0 0 0; 2395 | transition: background-color 0.1s; 2396 | } 2397 | .tsd-signatures .tsd-signature:first-child { 2398 | border-top-width: 0; 2399 | } 2400 | .tsd-signatures .tsd-signature.current { 2401 | background-color: var(--color-panel-divider); 2402 | } 2403 | .tsd-signatures.active > .tsd-signature { 2404 | cursor: pointer; 2405 | } 2406 | .tsd-panel > .tsd-signatures { 2407 | margin-left: -20px; 2408 | margin-right: -20px; 2409 | border-width: 1px 0; 2410 | } 2411 | .tsd-panel > .tsd-signatures .tsd-signature.tsd-kind-icon { 2412 | padding-left: 40px; 2413 | } 2414 | .tsd-panel > .tsd-signatures .tsd-signature.tsd-kind-icon:before { 2415 | left: 20px; 2416 | } 2417 | .tsd-panel > a.anchor + .tsd-signatures { 2418 | border-top-width: 0; 2419 | margin-top: -20px; 2420 | } 2421 | 2422 | ul.tsd-descriptions { 2423 | position: relative; 2424 | overflow: hidden; 2425 | padding: 0; 2426 | list-style: none; 2427 | } 2428 | ul.tsd-descriptions.active > .tsd-description { 2429 | display: none; 2430 | } 2431 | ul.tsd-descriptions.active > .tsd-description.current { 2432 | display: block; 2433 | } 2434 | ul.tsd-descriptions.active > .tsd-description.fade-in { 2435 | animation: fade-in-delayed 0.3s; 2436 | } 2437 | ul.tsd-descriptions.active > .tsd-description.fade-out { 2438 | animation: fade-out-delayed 0.3s; 2439 | position: absolute; 2440 | display: block; 2441 | top: 0; 2442 | left: 0; 2443 | right: 0; 2444 | opacity: 0; 2445 | visibility: hidden; 2446 | } 2447 | ul.tsd-descriptions h4, ul.tsd-descriptions .tsd-index-panel h3, .tsd-index-panel ul.tsd-descriptions h3 { 2448 | font-size: 16px; 2449 | margin: 1em 0 0.5em 0; 2450 | } 2451 | 2452 | ul.tsd-parameters, 2453 | ul.tsd-type-parameters { 2454 | list-style: square; 2455 | margin: 0; 2456 | padding-left: 20px; 2457 | } 2458 | ul.tsd-parameters > li.tsd-parameter-signature, 2459 | ul.tsd-type-parameters > li.tsd-parameter-signature { 2460 | list-style: none; 2461 | margin-left: -20px; 2462 | } 2463 | ul.tsd-parameters h5, 2464 | ul.tsd-type-parameters h5 { 2465 | font-size: 16px; 2466 | margin: 1em 0 0.5em 0; 2467 | } 2468 | ul.tsd-parameters .tsd-comment, 2469 | ul.tsd-type-parameters .tsd-comment { 2470 | margin-top: -0.5em; 2471 | } 2472 | 2473 | .tsd-sources { 2474 | font-size: 14px; 2475 | color: var(--color-text-aside); 2476 | margin: 0 0 1em 0; 2477 | } 2478 | .tsd-sources a { 2479 | color: var(--color-text-aside); 2480 | text-decoration: underline; 2481 | } 2482 | .tsd-sources ul, .tsd-sources p { 2483 | margin: 0 !important; 2484 | } 2485 | .tsd-sources ul { 2486 | list-style: none; 2487 | padding: 0; 2488 | } 2489 | 2490 | .tsd-page-toolbar { 2491 | position: fixed; 2492 | z-index: 1; 2493 | top: 0; 2494 | left: 0; 2495 | width: 100%; 2496 | height: 40px; 2497 | color: var(--color-toolbar-text); 2498 | background: var(--color-toolbar); 2499 | border-bottom: 1px solid var(--color-panel-divider); 2500 | transition: transform 0.3s linear; 2501 | } 2502 | .tsd-page-toolbar a { 2503 | color: var(--color-toolbar-text); 2504 | text-decoration: none; 2505 | } 2506 | .tsd-page-toolbar a.title { 2507 | font-weight: bold; 2508 | } 2509 | .tsd-page-toolbar a.title:hover { 2510 | text-decoration: underline; 2511 | } 2512 | .tsd-page-toolbar .table-wrap { 2513 | display: table; 2514 | width: 100%; 2515 | height: 40px; 2516 | } 2517 | .tsd-page-toolbar .table-cell { 2518 | display: table-cell; 2519 | position: relative; 2520 | white-space: nowrap; 2521 | line-height: 40px; 2522 | } 2523 | .tsd-page-toolbar .table-cell:first-child { 2524 | width: 100%; 2525 | } 2526 | 2527 | .tsd-page-toolbar--hide { 2528 | transform: translateY(-100%); 2529 | } 2530 | 2531 | .tsd-select .tsd-select-list li:before, .tsd-select .tsd-select-label:before, .tsd-widget:before { 2532 | content: ""; 2533 | display: inline-block; 2534 | width: 40px; 2535 | height: 40px; 2536 | margin: 0 -8px 0 0; 2537 | background-image: url(../images/widgets.png); 2538 | background-repeat: no-repeat; 2539 | text-indent: -1024px; 2540 | vertical-align: bottom; 2541 | } 2542 | @media (-webkit-min-device-pixel-ratio: 1.5), (min-resolution: 144dpi) { 2543 | .tsd-select .tsd-select-list li:before, .tsd-select .tsd-select-label:before, .tsd-widget:before { 2544 | background-image: url(../images/widgets@2x.png); 2545 | background-size: 320px 40px; 2546 | } 2547 | } 2548 | 2549 | .tsd-widget { 2550 | display: inline-block; 2551 | overflow: hidden; 2552 | opacity: 0.6; 2553 | height: 40px; 2554 | transition: opacity 0.1s, background-color 0.2s; 2555 | vertical-align: bottom; 2556 | cursor: pointer; 2557 | } 2558 | .tsd-widget:hover { 2559 | opacity: 0.8; 2560 | } 2561 | .tsd-widget.active { 2562 | opacity: 1; 2563 | background-color: var(--color-panel-divider); 2564 | } 2565 | .tsd-widget.no-caption { 2566 | width: 40px; 2567 | } 2568 | .tsd-widget.no-caption:before { 2569 | margin: 0; 2570 | } 2571 | .tsd-widget.search:before { 2572 | background-position: 0 0; 2573 | } 2574 | .tsd-widget.menu:before { 2575 | background-position: -40px 0; 2576 | } 2577 | .tsd-widget.options:before { 2578 | background-position: -80px 0; 2579 | } 2580 | .tsd-widget.options, .tsd-widget.menu { 2581 | display: none; 2582 | } 2583 | @media (max-width: 900px) { 2584 | .tsd-widget.options, .tsd-widget.menu { 2585 | display: inline-block; 2586 | } 2587 | } 2588 | input[type=checkbox] + .tsd-widget:before { 2589 | background-position: -120px 0; 2590 | } 2591 | input[type=checkbox]:checked + .tsd-widget:before { 2592 | background-position: -160px 0; 2593 | } 2594 | 2595 | .tsd-select { 2596 | position: relative; 2597 | display: inline-block; 2598 | height: 40px; 2599 | transition: opacity 0.1s, background-color 0.2s; 2600 | vertical-align: bottom; 2601 | cursor: pointer; 2602 | } 2603 | .tsd-select .tsd-select-label { 2604 | opacity: 0.6; 2605 | transition: opacity 0.2s; 2606 | } 2607 | .tsd-select .tsd-select-label:before { 2608 | background-position: -240px 0; 2609 | } 2610 | .tsd-select.active .tsd-select-label { 2611 | opacity: 0.8; 2612 | } 2613 | .tsd-select.active .tsd-select-list { 2614 | visibility: visible; 2615 | opacity: 1; 2616 | transition-delay: 0s; 2617 | } 2618 | .tsd-select .tsd-select-list { 2619 | position: absolute; 2620 | visibility: hidden; 2621 | top: 40px; 2622 | left: 0; 2623 | margin: 0; 2624 | padding: 0; 2625 | opacity: 0; 2626 | list-style: none; 2627 | box-shadow: 0 0 4px rgba(0, 0, 0, 0.25); 2628 | transition: visibility 0s 0.2s, opacity 0.2s; 2629 | } 2630 | .tsd-select .tsd-select-list li { 2631 | padding: 0 20px 0 0; 2632 | background-color: var(--color-background); 2633 | } 2634 | .tsd-select .tsd-select-list li:before { 2635 | background-position: 40px 0; 2636 | } 2637 | .tsd-select .tsd-select-list li:nth-child(even) { 2638 | background-color: var(--color-panel); 2639 | } 2640 | .tsd-select .tsd-select-list li:hover { 2641 | background-color: var(--color-panel-divider); 2642 | } 2643 | .tsd-select .tsd-select-list li.selected:before { 2644 | background-position: -200px 0; 2645 | } 2646 | @media (max-width: 900px) { 2647 | .tsd-select .tsd-select-list { 2648 | top: 0; 2649 | left: auto; 2650 | right: 100%; 2651 | margin-right: -5px; 2652 | } 2653 | .tsd-select .tsd-select-label:before { 2654 | background-position: -280px 0; 2655 | } 2656 | } 2657 | 2658 | img { 2659 | max-width: 100%; 2660 | } 2661 | -------------------------------------------------------------------------------- /docs/assets/images/icons.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mubaidr/Javascript-Barcode-Reader/68127eea851c05c643e4da68138ba693581a825f/docs/assets/images/icons.png -------------------------------------------------------------------------------- /docs/assets/images/icons@2x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mubaidr/Javascript-Barcode-Reader/68127eea851c05c643e4da68138ba693581a825f/docs/assets/images/icons@2x.png -------------------------------------------------------------------------------- /docs/assets/images/widgets.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mubaidr/Javascript-Barcode-Reader/68127eea851c05c643e4da68138ba693581a825f/docs/assets/images/widgets.png -------------------------------------------------------------------------------- /docs/assets/images/widgets@2x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mubaidr/Javascript-Barcode-Reader/68127eea851c05c643e4da68138ba693581a825f/docs/assets/images/widgets@2x.png -------------------------------------------------------------------------------- /docs/assets/js/search.js: -------------------------------------------------------------------------------- 1 | window.searchData = {"kinds":{"64":"Function"},"rows":[{"id":0,"kind":64,"name":"default","url":"modules.html#default","classes":"tsd-kind-function"}],"index":{"version":"2.3.9","fields":["name","parent"],"fieldVectors":[["name/0",[0,2.877]],["parent/0",[]]],"invertedIndex":[["default",{"_index":0,"name":{"0":{}},"parent":{}}]],"pipeline":[]}} -------------------------------------------------------------------------------- /docs/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | javascript-barcode-reader 7 | 8 | 9 | 10 | 11 | 12 | 13 |
14 |
15 |
16 |
17 | 28 |
29 |
30 | Options 31 |
32 |
33 | All 34 |
    35 |
  • Public
  • 36 |
  • Public/Protected
  • 37 |
  • All
  • 38 |
39 |
40 | 41 | 42 | 43 | 44 |
45 |
46 | Menu 47 |
48 |
49 |
50 |
51 |
52 |
53 |

javascript-barcode-reader

54 |
55 |
56 |
57 |
58 |
59 |
60 |
61 | 62 |

Javascript-Barcode-Reader

63 |
64 |

Simple & Fast Barcode decoder for Browsers and Node.js capapable of reading Code128 (UCC/EAN-128), Code93, Code39, Standard/Industrial 2 of 5, Interleaved 2 of 5, Codabar and EAN-13 barcodes.

65 |

Build Status 66 | codebeat badge 67 | codecov 68 | All Contributors 69 | Rate on Openbase

70 |

NPM

71 | 72 | 73 | 74 | 75 |

Try now

76 |
77 |

https://codesandbox.io/s/javascript-barcode-reader-liium

78 | 79 |

Available decoders

80 |
81 |
    82 |
  • EAN-13
  • 83 |
  • EAN-8
  • 84 |
  • Code-39
  • 85 |
  • Code-93
  • 86 |
  • Code-2of5
      87 |
    • standard
    • 88 |
    • Interleaved
    • 89 |
    90 |
  • 91 |
  • Codabar
  • 92 |
  • Code-128 (UCC/EAN-128)
  • 93 |
94 | 95 |

How to use

96 |
97 | 98 |

Install

99 |
100 |

Recommended way to install is by using package manager (npm, yarn etc):

101 |
npm i javascript-barcode-reader
102 | 
103 |

or use cdn:

104 |
<script src="//unpkg.com/javascript-barcode-reader"></script>
105 | 
106 |

or download manually:

107 |

javascript-barcode-reader

108 | 109 |

Node.js

110 |
111 |
import javascriptBarcodeReader from 'javascript-barcode-reader'
112 | 
113 | javascriptBarcodeReader({
114 |   /* Image file Path || {data: Uint8ClampedArray, width, height} || HTML5 Canvas ImageData */
115 |   image: source,
116 |   barcode: 'code-2of5',
117 |   // barcodeType: 'industrial',
118 |   options: {    
119 |     // useAdaptiveThreshold: true // for images with sahded portions
120 |     // singlePass: true
121 |   }
122 | })
123 |   .then(code => {
124 |     console.log(code)
125 |   })
126 |   .catch(err => {
127 |     console.log(err)
128 |   })
129 | 
130 | 131 |

Browser

132 |
133 |

javascriptBarcodeReader will be available as global in Browsers.

134 |
javascriptBarcodeReader({
135 |   /* Image ID || HTML5 Image || HTML5 Canvas || HTML5 Canvas ImageData || Image URL */
136 |   image: source,
137 |   barcode: 'code-2of5',
138 |   // barcodeType: 'industrial',
139 |   options: {
140 |     // useAdaptiveThreshold: true // for images with sahded portions
141 |     // singlePass: true
142 |   }
143 | })
144 |   .then(code => {
145 |     console.log(code)
146 |   })
147 |   .catch(err => {
148 |     console.log(err)
149 |   })
150 | 
151 | 152 |

Note

153 |
154 |
    155 |
  • This script does not implement logic to locate/rotate barcode in the given image.
  • 156 |
  • Make sure the barcode image is the only thing in the image. Otherwise this script will most probably fail.
  • 157 |
158 | 159 |

Contributing

160 |
161 |
    162 |
  • Each decoder is defined in src directory as a module.
  • 163 |
  • Tests are defined in the tests directory using Jest.
  • 164 |
165 | 166 |

Contributors

167 |
168 |

Thanks goes to these wonderful people (emoji key):

169 | 170 | 171 |
Cristian Nitescu
Cristian Nitescu

💻
172 | 173 |

This project follows the all-contributors specification. Contributions of any kind welcome!

174 |
175 |
176 | 192 |
193 |
194 | 201 |
202 |

Generated using TypeDoc

203 |
204 |
205 | 206 | 207 | -------------------------------------------------------------------------------- /docs/modules.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | javascript-barcode-reader 7 | 8 | 9 | 10 | 11 | 12 | 13 |
14 |
15 |
16 |
17 | 28 |
29 |
30 | Options 31 |
32 |
33 | All 34 |
    35 |
  • Public
  • 36 |
  • Public/Protected
  • 37 |
  • All
  • 38 |
39 |
40 | 41 | 42 | 43 | 44 |
45 |
46 | Menu 47 |
48 |
49 |
50 |
51 |
52 |
53 |

javascript-barcode-reader

54 |
55 |
56 |
57 |
58 |
59 |
60 |
61 |

Index

62 |
63 |
64 |
65 |

Functions

66 | 69 |
70 |
71 |
72 |
73 |
74 |

Functions

75 |
76 | 77 |

default

78 |
    79 |
  • default(__namedParameters: JavascriptBarcodeReader): Promise<string>
  • 80 |
81 |
    82 |
  • 83 | 88 |

    Parameters

    89 |
      90 |
    • 91 |
      __namedParameters: JavascriptBarcodeReader
      92 |
    • 93 |
    94 |

    Returns Promise<string>

    95 |
  • 96 |
97 |
98 |
99 |
100 | 116 |
117 |
118 | 125 |
126 |

Generated using TypeDoc

127 |
128 |
129 | 130 | 131 | -------------------------------------------------------------------------------- /index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 20 | 21 | 22 | 23 | 26 | 27 | 28 | 29 | 30 | 31 | -------------------------------------------------------------------------------- /jest.config.js: -------------------------------------------------------------------------------- 1 | module.exports = { 2 | collectCoverageFrom: ['src/**/*.{js,ts}'], 3 | coveragePathIgnorePatterns: ['/node_modules/', '/test/', '/dist/', '/docs/', '/tools/'], 4 | coverageThreshold: { 5 | global: { 6 | branches: 80, 7 | functions: 100, 8 | lines: 90, 9 | statements: 90, 10 | }, 11 | }, 12 | moduleFileExtensions: ['ts', 'js'], 13 | testEnvironment: 'jsdom', 14 | testEnvironmentOptions: { 15 | resources: 'usable', 16 | }, 17 | testPathIgnorePatterns: ['/node_modules/', '/src/', '/dist/', '/docs/', '/tools/'], 18 | testRegex: '(/__tests__/.*|\\.(test|spec))\\.(ts|tsx|js)$', 19 | transform: { 20 | '.(ts|tsx)': 'ts-jest', 21 | }, 22 | } 23 | -------------------------------------------------------------------------------- /nodemon.json: -------------------------------------------------------------------------------- 1 | { 2 | "env": { 3 | "NODE_ENV": "development" 4 | }, 5 | "exec": "ts-node --transpile-only ./tools/tmp.ts", 6 | "ext": "js,json,ts", 7 | "ignore": ["dist", "*.test.ts", ".git", "node_modules/**/node_modules"], 8 | "restartable": "rs", 9 | "verbose": true, 10 | "watch": ["src"] 11 | } 12 | -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "author": "Muhammad Ubaid Raza ", 3 | "commitlint": { 4 | "extends": [ 5 | "@commitlint/config-conventional" 6 | ] 7 | }, 8 | "config": { 9 | "commitizen": { 10 | "path": "node_modules/cz-conventional-changelog" 11 | } 12 | }, 13 | "dependencies": { 14 | "jimp": "^0.16.1" 15 | }, 16 | "description": "Simple & Fast Barcode decoder for Browser and Node.js", 17 | "devDependencies": { 18 | "@babel/core": "7.14.6", 19 | "@babel/plugin-proposal-class-properties": "7.14.5", 20 | "@babel/plugin-proposal-object-rest-spread": "7.14.7", 21 | "@babel/preset-env": "7.14.7", 22 | "@commitlint/cli": "^12.1.4", 23 | "@commitlint/config-conventional": "^12.1.4", 24 | "@rollup/plugin-commonjs": "^19.0.0", 25 | "@types/babel__core": "^7.1.15", 26 | "@types/babel__preset-env": "^7.9.2", 27 | "@types/core-js": "2.5.4", 28 | "@types/eslint": "^7.2.14", 29 | "@types/eslint-plugin-prettier": "^3.1.0", 30 | "@types/jest": "^26.0.24", 31 | "@types/node": "^16.0.1", 32 | "@types/nodemon": "^1.19.1", 33 | "@types/prettier": "^2.3.2", 34 | "@types/rollup-plugin-json": "^3.0.2", 35 | "@types/semantic-release": "^17.2.1", 36 | "@typescript-eslint/eslint-plugin": "^4.28.2", 37 | "@typescript-eslint/parser": "^4.28.2", 38 | "canvas": "^2.8.0", 39 | "commitizen": "^4.2.4", 40 | "core-js": "3.15.2", 41 | "coveralls": "^3.1.1", 42 | "cross-env": "^7.0.3", 43 | "cz-conventional-changelog": "^3.3.0", 44 | "eslint": "^7.30.0", 45 | "eslint-config-prettier": "^8.3.0", 46 | "eslint-plugin-jest": "^24.3.6", 47 | "eslint-plugin-prettier": "^3.4.0", 48 | "husky": "^7.0.1", 49 | "jest": "^27.0.6", 50 | "jest-config": "^27.0.6", 51 | "jest-environment-jsdom": "^27.0.6", 52 | "lint-staged": "^11.0.0", 53 | "nodemon": "^2.0.9", 54 | "prettier": "^2.3.2", 55 | "rollup": "^2.52.8", 56 | "rollup-plugin-babel": "^4.4.0", 57 | "rollup-plugin-json": "^4.0.0", 58 | "rollup-plugin-node-resolve": "^5.2.0", 59 | "rollup-plugin-sourcemaps": "^0.6.3", 60 | "rollup-plugin-terser": "^7.0.2", 61 | "rollup-plugin-typescript2": "^0.30.0", 62 | "semantic-release": "^17.4.4", 63 | "ts-jest": "^27.0.3", 64 | "ts-node": "^10.0.0", 65 | "typedoc": "^0.21.2", 66 | "typescript": "^4.3.5" 67 | }, 68 | "engines": { 69 | "node": ">=6.0.0" 70 | }, 71 | "files": [ 72 | "src", 73 | "dist" 74 | ], 75 | "homepage": "https://github.com/mubaidr/Javascript-Barcode-Reader#readme", 76 | "keywords": [ 77 | "barcode", 78 | "reader", 79 | "scanner", 80 | "javascript", 81 | "node" 82 | ], 83 | "license": "MIT", 84 | "lint-staged": { 85 | "{src,test}/**/*.ts": [ 86 | "prettier --write", 87 | "git add" 88 | ] 89 | }, 90 | "main": "dist/javascript-barcode-reader.umd.min.js", 91 | "module": "dist/javascript-barcode-reader.es5.min.js", 92 | "name": "javascript-barcode-reader", 93 | "repository": { 94 | "type": "git", 95 | "url": "git://github.com/mubaidr/Javascript-Barcode-Reader.git" 96 | }, 97 | "scripts": { 98 | "build": "tsc --module commonjs && rollup -c rollup.config.ts && typedoc --options typedoc.json", 99 | "commit": "git-cz", 100 | "deploy-docs": "ts-node tools/gh-pages-publish", 101 | "lint": "eslint --ext .js,.ts {src,test}/* --fix && prettier --write \"{test,src,tools}/**/*.{js,ts}\"", 102 | "prebuild": "rimraf dist", 103 | "precommit": "lint-staged", 104 | "report-coverage": "cat ./coverage/lcov.info | coveralls", 105 | "semantic-release": "semantic-release", 106 | "semantic-release-prepare": "ts-node tools/semantic-release-prepare", 107 | "start": "rollup -c rollup.config.ts -w", 108 | "test": "jest --coverage", 109 | "test:prod": "npm run lint && npm run test -- --no-cache", 110 | "test:watch": "jest --watch" 111 | }, 112 | "typings": "dist/types/src/index.d.ts", 113 | "version": "0.6.9" 114 | } 115 | -------------------------------------------------------------------------------- /renovate.json: -------------------------------------------------------------------------------- 1 | { 2 | "extends": [ 3 | "config:base" 4 | ] 5 | } 6 | -------------------------------------------------------------------------------- /rollup.config.ts: -------------------------------------------------------------------------------- 1 | import commonjs from '@rollup/plugin-commonjs' 2 | import babel from 'rollup-plugin-babel' 3 | import json from 'rollup-plugin-json' 4 | import resolve from 'rollup-plugin-node-resolve' 5 | import sourceMaps from 'rollup-plugin-sourcemaps' 6 | import { terser } from 'rollup-plugin-terser' 7 | import typescript from 'rollup-plugin-typescript2' 8 | 9 | const libraryName = 'javascriptBarcodeReader' 10 | 11 | export default { 12 | input: `src/index.ts`, 13 | output: [ 14 | { 15 | file: 'dist/javascript-barcode-reader.umd.min.js', 16 | name: libraryName, 17 | format: 'umd', 18 | sourcemap: true, 19 | globals: { 20 | jimp: 'Jimp', 21 | }, 22 | plugins: [terser()], 23 | }, 24 | { 25 | file: 'dist/javascript-barcode-reader.es5.min.js', 26 | format: 'es', 27 | sourcemap: true, 28 | globals: { 29 | jimp: 'Jimp', 30 | }, 31 | plugins: [terser()], 32 | }, 33 | ], 34 | // Indicate here external modules you don't wanna include in your bundle (i.e.: 'lodash') 35 | external: ['jimp'], 36 | watch: { 37 | include: 'src/**', 38 | }, 39 | plugins: [ 40 | // Allow json resolution 41 | json(), 42 | // Compile TypeScript files 43 | typescript({ useTsconfigDeclarationDir: true }), 44 | // use babel 45 | babel({ 46 | exclude: 'node_modules/**', 47 | }), 48 | // Allow bundling cjs modules (unlike webpack, rollup doesn't understand cjs) 49 | commonjs(), 50 | // Allow node_modules resolution, so you can use 'external' to control 51 | // which external modules to include in the bundle 52 | // https://github.com/rollup/rollup-plugin-node-resolve#usage 53 | resolve(), 54 | 55 | // Resolve source maps to the original source 56 | sourceMaps(), 57 | ], 58 | } 59 | -------------------------------------------------------------------------------- /src/.eslintrc.json: -------------------------------------------------------------------------------- 1 | { 2 | "env": { 3 | "browser": true, 4 | "node": true 5 | }, 6 | "extends": [ 7 | "eslint:recommended", 8 | "plugin:@typescript-eslint/eslint-recommended", 9 | "plugin:@typescript-eslint/recommended", 10 | "plugin:@typescript-eslint/recommended-requiring-type-checking", 11 | "prettier", 12 | "prettier/@typescript-eslint" 13 | ], 14 | "parser": "@typescript-eslint/parser", 15 | "parserOptions": { 16 | "ecmaVersion": 2020, 17 | "parser": "babel-eslint", 18 | "project": "./tsconfig.json", 19 | "sourceType": "module" 20 | }, 21 | "plugins": [ 22 | "@typescript-eslint", 23 | "prettier" 24 | ], 25 | "root": true, 26 | "rules": { 27 | "@typescript-eslint/no-explicit-any": 0, 28 | "no-console": 0, 29 | "semi": 0 30 | } 31 | } 32 | -------------------------------------------------------------------------------- /src/codabar/index.ts: -------------------------------------------------------------------------------- 1 | const CHAR_SET: { 2 | [key: string]: string 3 | } = { 4 | nnnnnww: '0', 5 | nnnnwwn: '1', 6 | nnnwnnw: '2', 7 | wwnnnnn: '3', 8 | nnwnnwn: '4', 9 | wnnnnwn: '5', 10 | nwnnnnw: '6', 11 | nwnnwnn: '7', 12 | nwwnnnn: '8', 13 | wnnwnnn: '9', 14 | nnnwwnn: '-', 15 | nnwwnnn: '$', 16 | wnnnwnw: ':', 17 | wnwnnnw: '/', 18 | wnwnwnn: '.', 19 | nnwwwww: '+', 20 | nnwwnwn: 'A', 21 | nnnwnww: 'B', 22 | nwnwnnw: 'C', 23 | nnnwwwn: 'D', 24 | } 25 | 26 | export function decoder(lines: number[]): string { 27 | const code = [] 28 | 29 | const barThreshold = Math.ceil(lines.reduce((pre, item) => (pre + item) / 2, 0)) 30 | 31 | // Read one encoded character at a time. 32 | while (lines.length > 0) { 33 | const seg = lines.splice(0, 8).splice(0, 7) 34 | const a = seg.map(line => (line < barThreshold ? 'n' : 'w')).join('') 35 | 36 | code.push(CHAR_SET[a]) 37 | } 38 | 39 | return code.join('') 40 | } 41 | -------------------------------------------------------------------------------- /src/code-128/index.ts: -------------------------------------------------------------------------------- 1 | const WIDTH_TBL = [ 2 | '212222', 3 | '222122', 4 | '222221', 5 | '121223', 6 | '121322', 7 | '131222', 8 | '122213', 9 | '122312', 10 | '132212', 11 | '221213', 12 | '221312', 13 | '231212', 14 | '112232', 15 | '122132', 16 | '122231', 17 | '113222', 18 | '123122', 19 | '123221', 20 | '223211', 21 | '221132', 22 | '221231', 23 | '213212', 24 | '223112', 25 | '312131', 26 | '311222', 27 | '321122', 28 | '321221', 29 | '312212', 30 | '322112', 31 | '322211', 32 | '212123', 33 | '212321', 34 | '232121', 35 | '111323', 36 | '131123', 37 | '131321', 38 | '112313', 39 | '132113', 40 | '132311', 41 | '211313', 42 | '231113', 43 | '231311', 44 | '112133', 45 | '112331', 46 | '132131', 47 | '113123', 48 | '113321', 49 | '133121', 50 | '313121', 51 | '211331', 52 | '231131', 53 | '213113', 54 | '213311', 55 | '213131', 56 | '311123', 57 | '311321', 58 | '331121', 59 | '312113', 60 | '312311', 61 | '332111', 62 | '314111', 63 | '221411', 64 | '431111', 65 | '111224', 66 | '111422', 67 | '121124', 68 | '121421', 69 | '141122', 70 | '141221', 71 | '112214', 72 | '112412', 73 | '122114', 74 | '122411', 75 | '142112', 76 | '142211', 77 | '241211', 78 | '221114', 79 | '413111', 80 | '241112', 81 | '134111', 82 | '111242', 83 | '121142', 84 | '121241', 85 | '114212', 86 | '124112', 87 | '124211', 88 | '411212', 89 | '421112', 90 | '421211', 91 | '212141', 92 | '214121', 93 | '412121', 94 | '111143', 95 | '111341', 96 | '131141', 97 | '114113', 98 | '114311', 99 | '411113', 100 | '411311', 101 | '113141', 102 | '114131', 103 | '311141', 104 | '411131', 105 | '211412', 106 | '211214', 107 | '211232', 108 | '233111', 109 | '211133', 110 | '2331112', 111 | ] 112 | 113 | const TBL_A = [ 114 | ' ', 115 | '!', 116 | '"', 117 | '#', 118 | '$', 119 | '%', 120 | '&', 121 | "'", 122 | '(', 123 | ')', 124 | '*', 125 | '+', 126 | ',', 127 | '-', 128 | '.', 129 | '/', 130 | '0', 131 | '1', 132 | '2', 133 | '3', 134 | '4', 135 | '5', 136 | '6', 137 | '7', 138 | '8', 139 | '9', 140 | ':', 141 | ';', 142 | '<', 143 | '=', 144 | '>', 145 | '?', 146 | '@', 147 | 'A', 148 | 'B', 149 | 'C', 150 | 'D', 151 | 'E', 152 | 'F', 153 | 'G', 154 | 'H', 155 | 'I', 156 | 'J', 157 | 'K', 158 | 'L', 159 | 'M', 160 | 'N', 161 | 'O', 162 | 'P', 163 | 'Q', 164 | 'R', 165 | 'S', 166 | 'T', 167 | 'U', 168 | 'V', 169 | 'W', 170 | 'X', 171 | 'Y', 172 | 'Z', 173 | '[', 174 | '\\', 175 | ']', 176 | '^', 177 | '_', 178 | 'NUL', 179 | 'SOH', 180 | 'STX', 181 | 'ETX', 182 | 'EOT', 183 | 'ENQ', 184 | 'ACK', 185 | 'BEL', 186 | 'BS', 187 | 'HT', 188 | 'LF', 189 | 'VT', 190 | 'FF', 191 | 'CR', 192 | 'SO', 193 | 'SI', 194 | 'DLE', 195 | 'DC1', 196 | 'DC2', 197 | 'DC3', 198 | 'DC4', 199 | 'NAK', 200 | 'SYN', 201 | 'ETB', 202 | 'CAN', 203 | 'EM', 204 | 'SUB', 205 | 'ESC', 206 | 'FS', 207 | 'GS', 208 | 'RS', 209 | 'US', 210 | 'FNC 3', 211 | 'FNC 2', 212 | 'Shift B', 213 | 'Code C', 214 | 'Code B', 215 | 'FNC 4', 216 | 'FNC 1', 217 | 'Code A', 218 | 'Code B', 219 | 'Code C', 220 | 'Stop', 221 | 'Reverse Stop', 222 | ] 223 | 224 | const TBL_B = [ 225 | ' ', 226 | '!', 227 | '"', 228 | '#', 229 | '$', 230 | '%', 231 | '&', 232 | "'", 233 | '(', 234 | ')', 235 | '*', 236 | '+', 237 | ',', 238 | '-', 239 | '.', 240 | '/', 241 | '0', 242 | '1', 243 | '2', 244 | '3', 245 | '4', 246 | '5', 247 | '6', 248 | '7', 249 | '8', 250 | '9', 251 | ':', 252 | ';', 253 | '<', 254 | '=', 255 | '>', 256 | '?', 257 | '@', 258 | 'A', 259 | 'B', 260 | 'C', 261 | 'D', 262 | 'E', 263 | 'F', 264 | 'G', 265 | 'H', 266 | 'I', 267 | 'J', 268 | 'K', 269 | 'L', 270 | 'M', 271 | 'N', 272 | 'O', 273 | 'P', 274 | 'Q', 275 | 'R', 276 | 'S', 277 | 'T', 278 | 'U', 279 | 'V', 280 | 'W', 281 | 'X', 282 | 'Y', 283 | 'Z', 284 | '[', 285 | '\\', 286 | ']', 287 | '^', 288 | '_', 289 | '`', 290 | 'a', 291 | 'b', 292 | 'c', 293 | 'd', 294 | 'e', 295 | 'f', 296 | 'g', 297 | 'h', 298 | 'i', 299 | 'j', 300 | 'k', 301 | 'l', 302 | 'm', 303 | 'n', 304 | 'o', 305 | 'p', 306 | 'q', 307 | 'r', 308 | 's', 309 | 't', 310 | 'u', 311 | 'v', 312 | 'w', 313 | 'x', 314 | 'y', 315 | 'z', 316 | '{', 317 | '|', 318 | '}', 319 | '~', 320 | 'DEL', 321 | 'FNC 3', 322 | 'FNC 2', 323 | 'Shift A', 324 | 'Code C', 325 | 'FNC 4', 326 | 'Code A', 327 | 'FNC 1', 328 | 'Code A', 329 | 'Code B', 330 | 'Code C', 331 | 'Stop', 332 | 'Reverse Stop', 333 | ] 334 | 335 | const TBL_C = [ 336 | '00', 337 | '01', 338 | '02', 339 | '03', 340 | '04', 341 | '05', 342 | '06', 343 | '07', 344 | '08', 345 | '09', 346 | '10', 347 | '11', 348 | '12', 349 | '13', 350 | '14', 351 | '15', 352 | '16', 353 | '17', 354 | '18', 355 | '19', 356 | '20', 357 | '21', 358 | '22', 359 | '23', 360 | '24', 361 | '25', 362 | '26', 363 | '27', 364 | '28', 365 | '29', 366 | '30', 367 | '31', 368 | '32', 369 | '33', 370 | '34', 371 | '35', 372 | '36', 373 | '37', 374 | '38', 375 | '39', 376 | '40', 377 | '41', 378 | '42', 379 | '43', 380 | '44', 381 | '45', 382 | '46', 383 | '47', 384 | '48', 385 | '49', 386 | '50', 387 | '51', 388 | '52', 389 | '53', 390 | '54', 391 | '55', 392 | '56', 393 | '57', 394 | '58', 395 | '59', 396 | '60', 397 | '61', 398 | '62', 399 | '63', 400 | '64', 401 | '65', 402 | '66', 403 | '67', 404 | '68', 405 | '69', 406 | '70', 407 | '71', 408 | '72', 409 | '73', 410 | '74', 411 | '75', 412 | '76', 413 | '77', 414 | '78', 415 | '79', 416 | '80', 417 | '81', 418 | '82', 419 | '83', 420 | '84', 421 | '85', 422 | '86', 423 | '87', 424 | '88', 425 | '89', 426 | '90', 427 | '91', 428 | '92', 429 | '93', 430 | '94', 431 | '95', 432 | '96', 433 | '97', 434 | '98', 435 | '99', 436 | 'Code B', 437 | 'Code A', 438 | 'FNC 1', 439 | 'Code A', 440 | 'Code B', 441 | 'Code C', 442 | 'Stop', 443 | 'Reverse Stop', 444 | ] 445 | 446 | const computeGroup = (lines: number[]): number[] => { 447 | const count = lines.length - 13 448 | const factor = 449 | lines.reduce((pre, item, i) => { 450 | if (i >= count) return pre 451 | 452 | return pre + item 453 | }, 0) / 454 | (Math.ceil(count / 6) * 11) 455 | 456 | return lines.map(item => Math.round(item / factor) || 1) 457 | } 458 | 459 | export function decoder(lines: number[]): string { 460 | const code = [] 461 | let lookupTBL = TBL_B 462 | // let sumOP = 0 463 | let letterKey 464 | let letterCodePrev 465 | 466 | const computedLines = computeGroup(lines) 467 | 468 | if (!computedLines) return '' 469 | 470 | // extract terminal bar 471 | computedLines.pop() 472 | 473 | // skip check code and stop code using -13 474 | for (let i = 0; i * 6 < computedLines.length - 13; i += 1) { 475 | letterKey = computedLines.slice(i * 6, (i + 1) * 6).join('') 476 | const keyIndex = WIDTH_TBL.indexOf(letterKey) 477 | const letterCode = lookupTBL[keyIndex] 478 | // sumOP += i * keyIndex 479 | 480 | switch (letterCode) { 481 | case 'Code A': 482 | lookupTBL = TBL_A 483 | break 484 | case 'Code B': 485 | lookupTBL = TBL_B 486 | break 487 | case 'Code C': 488 | lookupTBL = TBL_C 489 | break 490 | case 'FNC 4': 491 | break 492 | default: 493 | if (letterCode) { 494 | if (letterCodePrev === 'FNC 4') { 495 | code.push(letterCode.charCodeAt(0) + 128) 496 | } else { 497 | code.push(letterCode) 498 | } 499 | 500 | letterCodePrev = letterCode 501 | } else { 502 | code.push('?') 503 | } 504 | break 505 | } 506 | } 507 | 508 | // letterKey = computedLines.slice(0, 6).join('') 509 | // if (sumOP % 103 !== WIDTH_TBL.indexOf(letterKey)) return '' 510 | 511 | return code.join('') 512 | } 513 | -------------------------------------------------------------------------------- /src/code-39/index.ts: -------------------------------------------------------------------------------- 1 | const CHAR_SET: { 2 | [key: string]: string 3 | } = { 4 | nnnwwnwnn: '0', 5 | wnnwnnnnw: '1', 6 | nnwwnnnnw: '2', 7 | wnwwnnnnn: '3', 8 | nnnwwnnnw: '4', 9 | wnnwwnnnn: '5', 10 | nnwwwnnnn: '6', 11 | nnnwnnwnw: '7', 12 | wnnwnnwnn: '8', 13 | nnwwnnwnn: '9', 14 | wnnnnwnnw: 'A', 15 | nnwnnwnnw: 'B', 16 | wnwnnwnnn: 'C', 17 | nnnnwwnnw: 'D', 18 | wnnnwwnnn: 'E', 19 | nnwnwwnnn: 'F', 20 | nnnnnwwnw: 'G', 21 | wnnnnwwnn: 'H', 22 | nnwnnwwnn: 'I', 23 | nnnnwwwnn: 'J', 24 | wnnnnnnww: 'K', 25 | nnwnnnnww: 'L', 26 | wnwnnnnwn: 'M', 27 | nnnnwnnww: 'N', 28 | wnnnwnnwn: 'O', 29 | nnwnwnnwn: 'P', 30 | nnnnnnwww: 'Q', 31 | wnnnnnwwn: 'R', 32 | nnwnnnwwn: 'S', 33 | nnnnwnwwn: 'T', 34 | wwnnnnnnw: 'U', 35 | nwwnnnnnw: 'V', 36 | wwwnnnnnn: 'W', 37 | nwnnwnnnw: 'X', 38 | wwnnwnnnn: 'Y', 39 | nwwnwnnnn: 'Z', 40 | nwnnnnwnw: '-', 41 | wwnnnnwnn: '.', 42 | nwwnnnwnn: ' ', 43 | nwnwnwnnn: '$', 44 | nwnwnnnwn: '/', 45 | nwnnnwnwn: '+', 46 | nnnwnwnwn: '%', 47 | nwnnwnwnn: '*', 48 | } 49 | 50 | export function decoder(lines: number[]): string { 51 | const code = [] 52 | 53 | const barThreshold = Math.ceil(lines.reduce((pre, item) => pre + item, 0) / lines.length) 54 | 55 | // Read one encoded character at a time. 56 | while (lines.length > 0) { 57 | const sequenceBar = lines 58 | .splice(0, 10) 59 | .map(line => (line > barThreshold ? 'w' : 'n')) 60 | .slice(0, 9) 61 | .join('') 62 | 63 | code.push(CHAR_SET[sequenceBar]) 64 | } 65 | 66 | if (code.pop() !== '*' || code.shift() !== '*') return '' 67 | 68 | return code.join('') 69 | } 70 | -------------------------------------------------------------------------------- /src/code-93/index.ts: -------------------------------------------------------------------------------- 1 | interface CharValue { 2 | [key: string]: string 3 | } 4 | 5 | const CHAR_SET: CharValue[] = [ 6 | { '100010100': '0' }, 7 | { '101001000': '1' }, 8 | { '101000100': '2' }, 9 | { '101000010': '3' }, 10 | { '100101000': '4' }, 11 | { '100100100': '5' }, 12 | { '100100010': '6' }, 13 | { '101010000': '7' }, 14 | { '100010010': '8' }, 15 | { '100001010': '9' }, 16 | { '110101000': 'A' }, 17 | { '110100100': 'B' }, 18 | { '110100010': 'C' }, 19 | { '110010100': 'D' }, 20 | { '110010010': 'E' }, 21 | { '110001010': 'F' }, 22 | { '101101000': 'G' }, 23 | { '101100100': 'H' }, 24 | { '101100010': 'I' }, 25 | { '100110100': 'J' }, 26 | { '100011010': 'K' }, 27 | { '101011000': 'L' }, 28 | { '101001100': 'M' }, 29 | { '101000110': 'N' }, 30 | { '100101100': 'O' }, 31 | { '100010110': 'P' }, 32 | { '110110100': 'Q' }, 33 | { '110110010': 'R' }, 34 | { '110101100': 'S' }, 35 | { '110100110': 'T' }, 36 | { '110010110': 'U' }, 37 | { '110011010': 'V' }, 38 | { '101101100': 'W' }, 39 | { '101100110': 'X' }, 40 | { '100110110': 'Y' }, 41 | { '100111010': 'Z' }, 42 | { '100101110': '-' }, 43 | { '111010100': '.' }, 44 | { '111010010': ' ' }, 45 | { '111001010': '$' }, 46 | { '101101110': '/' }, 47 | { '101110110': '+' }, 48 | { '110101110': '%' }, 49 | { '100100110': '($)' }, 50 | { '111011010': '(%)' }, 51 | { '111010110': '(/)' }, 52 | { '100110010': '(+)' }, 53 | { '101011110': '*' }, 54 | ] 55 | 56 | export function decoder(lines: number[]): string { 57 | const code = [] 58 | const binary = [] 59 | 60 | // remove termination bar 61 | lines.pop() 62 | 63 | const barThreshold = Math.ceil(lines.reduce((pre, item) => pre + item, 0) / lines.length) 64 | 65 | const minBarWidth = Math.ceil( 66 | lines.reduce((pre, item) => { 67 | if (item < barThreshold) return (pre + item) / 2 68 | return pre 69 | }, 0) 70 | ) 71 | 72 | // leave the padded * 73 | for (let i = 0; i < lines.length; i += 1) { 74 | let segment = lines[i] 75 | 76 | while (segment > 0) { 77 | if (i % 2 === 0) { 78 | binary.push(1) 79 | } else { 80 | binary.push(0) 81 | } 82 | segment -= minBarWidth 83 | } 84 | } 85 | 86 | for (let i = 0; i < binary.length; i += 9) { 87 | const searcKey = binary.slice(i, i + 9).join('') 88 | const char = CHAR_SET.filter(item => Object.keys(item)[0] === searcKey) 89 | code.push(char[0][searcKey]) 90 | } 91 | 92 | if (code.shift() !== '*' || code.pop() !== '*') return '' 93 | 94 | const K = code.pop() 95 | let sum = 0 96 | let letter: string 97 | let Value 98 | const findValue = (item: CharValue): boolean => Object.values(item)[0] === letter 99 | 100 | for (let i = code.length - 1; i >= 0; i -= 1) { 101 | letter = code[i] 102 | Value = CHAR_SET.indexOf(CHAR_SET.filter(findValue)[0]) 103 | sum += Value * (1 + ((code.length - (i + 1)) % 20)) 104 | } 105 | 106 | if (Object.values(CHAR_SET[sum % 47])[0] !== K) return '' 107 | 108 | const C = code.pop() 109 | sum = 0 110 | 111 | for (let i = code.length - 1; i >= 0; i -= 1) { 112 | letter = code[i] 113 | Value = CHAR_SET.indexOf(CHAR_SET.filter(findValue)[0]) 114 | sum += Value * (1 + ((code.length - (i + 1)) % 20)) 115 | } 116 | 117 | if (Object.values(CHAR_SET[sum % 47])[0] !== C) return '' 118 | 119 | return code.join('') 120 | } 121 | -------------------------------------------------------------------------------- /src/code2of5/index.ts: -------------------------------------------------------------------------------- 1 | const CHAR_SET = [ 2 | 'nnwwn', 3 | 'wnnnw', 4 | 'nwnnw', 5 | 'wwnnn', 6 | 'nnwnw', 7 | 'wnwnn', 8 | 'nwwnn', 9 | 'nnnww', 10 | 'wnnwn', 11 | 'nwnwn', 12 | ] 13 | 14 | export function decoder(lines: number[], type?: string): string { 15 | const code = [] 16 | 17 | const barThreshold = Math.ceil(lines.reduce((pre, item) => (pre + item) / 2, 0)) 18 | 19 | if (type === 'interleaved') { 20 | // extract start/ends pair 21 | const startChar = lines 22 | .splice(0, 4) 23 | .map((line: number) => (line > barThreshold ? 'w' : 'n')) 24 | .join('') 25 | 26 | const endChar = lines 27 | .splice(lines.length - 3, 3) 28 | .map((line: number) => (line > barThreshold ? 'w' : 'n')) 29 | .join('') 30 | 31 | if (startChar !== 'nnnn' || endChar !== 'wnn') return '' 32 | 33 | // Read one encoded character at a time. 34 | while (lines.length > 0) { 35 | const seg = lines.splice(0, 10) 36 | 37 | const a = seg 38 | .filter((item, index) => index % 2 === 0) 39 | .map(line => (line > barThreshold ? 'w' : 'n')) 40 | .join('') 41 | 42 | code.push(CHAR_SET.indexOf(a)) 43 | 44 | const b = seg 45 | .filter((item, index) => index % 2 !== 0) 46 | .map(line => (line > barThreshold ? 'w' : 'n')) 47 | .join('') 48 | 49 | code.push(CHAR_SET.indexOf(b)) 50 | } 51 | } else { 52 | // extract start/ends pair 53 | const startChar = lines 54 | .splice(0, 6) 55 | .filter((item: any, index: number) => index % 2 === 0) 56 | .map((line: number) => (line > barThreshold ? 'w' : 'n')) 57 | .join('') 58 | 59 | const endChar = lines 60 | .splice(lines.length - 5, 5) 61 | .filter((item: any, index: number) => index % 2 === 0) 62 | .map((line: number) => (line > barThreshold ? 'w' : 'n')) 63 | .join('') 64 | 65 | if (startChar !== 'wwn' || endChar !== 'wnw') return '' 66 | 67 | // Read one encoded character at a time. 68 | while (lines.length > 0) { 69 | const a = lines 70 | .splice(0, 10) 71 | .filter((item, index) => index % 2 === 0) 72 | .map(line => (line > barThreshold ? 'w' : 'n')) 73 | .join('') 74 | 75 | code.push(CHAR_SET.indexOf(a)) 76 | } 77 | } 78 | 79 | return code.join('') 80 | } 81 | -------------------------------------------------------------------------------- /src/ean/index.ts: -------------------------------------------------------------------------------- 1 | const UPC_SET: { 2 | [key: string]: string 3 | } = { 4 | '3211': '0', 5 | '2221': '1', 6 | '2122': '2', 7 | '1411': '3', 8 | '1132': '4', 9 | '1231': '5', 10 | '1114': '6', 11 | '1312': '7', 12 | '1213': '8', 13 | '3112': '9', 14 | } 15 | 16 | export function decoder(lines: number[], type = '13'): string { 17 | let code = '' 18 | 19 | // start indicator/reference lines 20 | const bar = (lines[0] + lines[1] + lines[2]) / 3 21 | 22 | // remove start pattern 23 | lines.shift() 24 | lines.shift() 25 | lines.shift() 26 | 27 | // remove end pattern 28 | lines.pop() 29 | lines.pop() 30 | lines.pop() 31 | 32 | // remove middle check pattern 33 | 34 | // remove middle check pattern 35 | if (type === '13') { 36 | lines.splice(24, 5) 37 | } else { 38 | lines.splice(16, 5) 39 | } 40 | 41 | for (let i = 0; i < lines.length; i += 4) { 42 | const group = lines.slice(i, i + 4) 43 | 44 | const digits = [group[0] / bar, group[1] / bar, group[2] / bar, group[3] / bar].map(digit => 45 | digit === 1.5 ? 1 : Math.round(digit) 46 | ) 47 | 48 | const result = UPC_SET[digits.join('')] || UPC_SET[digits.reverse().join('')] 49 | 50 | if (result) { 51 | code += result 52 | } else { 53 | code += '?' 54 | } 55 | } 56 | 57 | return code 58 | } 59 | -------------------------------------------------------------------------------- /src/index.ts: -------------------------------------------------------------------------------- 1 | // available decoders 2 | import * as codabar from './codabar' 3 | import * as code128 from './code-128' 4 | import * as code39 from './code-39' 5 | import * as code93 from './code-93' 6 | import * as code2of5 from './code2of5' 7 | import * as ean from './ean' 8 | import { applyAdaptiveThreshold } from './utilities/adaptiveThreshold' 9 | import { BARCODE_DECODERS } from './utilities/BARCODE_DECODERS' 10 | import { combineAllPossible } from './utilities/combineAllPossible' 11 | import { getImageDataFromSource } from './utilities/getImageDataFromSource' 12 | import { getLines } from './utilities/getLines' 13 | import { ImageDataLike } from './utilities/ImageDataLike' 14 | 15 | // detect test env 16 | let isTestEnv: boolean 17 | try { 18 | if (process && process.env.NODE_ENV === 'test') { 19 | isTestEnv = true 20 | } 21 | } catch { 22 | isTestEnv = false 23 | } 24 | 25 | function isImageLike(object: any): object is ImageDataLike { 26 | return object.data && object.width && object.height 27 | } 28 | 29 | type JavascriptBarcodeReader = { 30 | image: string | HTMLImageElement | HTMLCanvasElement | ImageDataLike 31 | barcode: string | BARCODE_DECODERS 32 | barcodeType?: string 33 | options?: { 34 | useAdaptiveThreshold?: boolean 35 | singlePass?: boolean 36 | } 37 | } 38 | 39 | interface DecoderFunction { 40 | (lines: number[], type?: string): string 41 | } 42 | 43 | export default async function javascriptBarcodeReader({ 44 | image, 45 | barcode, 46 | barcodeType, 47 | options, 48 | }: JavascriptBarcodeReader): Promise { 49 | let decoder: DecoderFunction 50 | 51 | switch (barcode) { 52 | case BARCODE_DECODERS.codabar: 53 | decoder = codabar.decoder 54 | break 55 | case BARCODE_DECODERS['code-128']: 56 | decoder = code128.decoder 57 | break 58 | case BARCODE_DECODERS['code-39']: 59 | decoder = code39.decoder 60 | break 61 | case BARCODE_DECODERS['code-93']: 62 | decoder = code93.decoder 63 | break 64 | case BARCODE_DECODERS['code-2of5']: 65 | decoder = code2of5.decoder 66 | break 67 | case BARCODE_DECODERS['ean-13']: 68 | decoder = ean.decoder 69 | barcodeType = '13' 70 | break 71 | case BARCODE_DECODERS['ean-8']: 72 | decoder = ean.decoder 73 | barcodeType = '8' 74 | break 75 | default: 76 | throw new Error(`Invalid barcode specified. Available decoders: ${BARCODE_DECODERS}.`) 77 | } 78 | 79 | const useSinglePass = isTestEnv || (options && options.singlePass) || false 80 | const { data, width, height } = isImageLike(image) ? image : await getImageDataFromSource(image) 81 | const channels = data.length / (width * height) 82 | let finalResult = '' 83 | 84 | // apply adaptive threshold 85 | if (options && options.useAdaptiveThreshold) { 86 | applyAdaptiveThreshold(data, width, height) 87 | } 88 | 89 | // check points for barcode location 90 | const searchPoints = [5, 6, 4, 7, 3, 8, 2, 9, 1] 91 | const searchLineStep = Math.round(height / searchPoints.length) 92 | const rowsToScan = Math.min(2, height) 93 | 94 | for (let i = 0; i < searchPoints.length; i += 1) { 95 | const start = channels * width * Math.floor(searchLineStep * searchPoints[i]) 96 | const end = start + rowsToScan * channels * width 97 | const lines = getLines(data.slice(start, end), width, rowsToScan) 98 | 99 | if (lines.length === 0) { 100 | if (useSinglePass || i === searchPoints.length - 1) { 101 | throw new Error('Failed to detect lines in the image!') 102 | } 103 | 104 | continue 105 | } 106 | 107 | // Run the decoder 108 | const result = decoder(lines, barcodeType) 109 | 110 | if (!result) continue 111 | else if (useSinglePass || !result.includes('?')) return result 112 | 113 | finalResult = combineAllPossible(finalResult, result) 114 | if (!finalResult.includes('?')) return finalResult 115 | } 116 | 117 | return finalResult 118 | } 119 | -------------------------------------------------------------------------------- /src/utilities/BARCODE_DECODERS.ts: -------------------------------------------------------------------------------- 1 | export enum BARCODE_DECODERS { 2 | 'code-128' = 'code-128', 3 | 'code-2of5' = 'code-2of5', 4 | 'code-39' = 'code-39', 5 | 'code-93' = 'code-93', 6 | 'ean-13' = 'ean-13', 7 | 'ean-8' = 'ean-8', 8 | 'codabar' = 'codabar', 9 | } 10 | -------------------------------------------------------------------------------- /src/utilities/ImageDataLike.ts: -------------------------------------------------------------------------------- 1 | export interface ImageDataLike { 2 | data: Uint8ClampedArray 3 | width: number 4 | height: number 5 | } 6 | -------------------------------------------------------------------------------- /src/utilities/adaptiveThreshold.ts: -------------------------------------------------------------------------------- 1 | export function applyAdaptiveThreshold( 2 | data: Uint8ClampedArray, 3 | width: number, 4 | height: number 5 | ): Uint8ClampedArray { 6 | const integralImage = new Array(width * height).fill(0) 7 | const channels = data.length / (width * height) 8 | const t = 0.15 // threshold percentage 9 | const s = Math.floor(height) // bracket size 10 | const s2 = Math.floor(s / 2) 11 | 12 | for (let i = 0; i < width; i += 1) { 13 | let sum = 0 14 | for (let j = 0; j < height; j += 1) { 15 | const pureIndex = j * width + i 16 | const index = pureIndex * channels 17 | // greyscale 18 | const v = (data[index] + data[index + 1] + data[index + 2]) / 3 19 | 20 | data[index] = v 21 | data[index + 1] = v 22 | data[index + 2] = v 23 | sum += v 24 | 25 | if (i === 0) { 26 | integralImage[pureIndex] = sum 27 | } else { 28 | integralImage[pureIndex] = integralImage[pureIndex - 1] + sum 29 | } 30 | } 31 | } 32 | 33 | // skip edge rows 34 | for (let i = 0; i < width; i += 1) { 35 | for (let j = 0; j < height; j += 1) { 36 | const pureIndex = j * width + i 37 | const index = pureIndex * channels 38 | // no. of pixels per window 39 | let x1 = i - s2 40 | let x2 = i + s2 41 | let y1 = j - s2 42 | let y2 = j + s2 43 | 44 | if (x1 < 0) x1 = 0 45 | if (x2 >= width) x2 = width - 1 46 | if (y1 < 0) y1 = 0 47 | if (y2 >= height) y2 = height - 1 48 | 49 | const count = (x2 - x1) * (y2 - y1) 50 | const sum = 51 | integralImage[y2 * width + x2] - 52 | integralImage[y1 * width + x2] - 53 | integralImage[y2 * width + x1] + 54 | integralImage[y1 * width + x1] 55 | let v = 255 56 | 57 | if (data[index] * count < sum * (1 - t)) { 58 | v = 0 59 | } 60 | 61 | data[index] = v 62 | data[index + 1] = v 63 | data[index + 2] = v 64 | } 65 | } 66 | 67 | return data 68 | } 69 | -------------------------------------------------------------------------------- /src/utilities/combineAllPossible.ts: -------------------------------------------------------------------------------- 1 | export function combineAllPossible(finalResult: string, result: string): string { 2 | if (finalResult === '' || result === '') { 3 | return result 4 | } 5 | 6 | const finalResultArr = finalResult.split('') 7 | const resultArr = result.split('') 8 | 9 | resultArr.forEach((char, index) => { 10 | if (!finalResultArr[index] || finalResultArr[index] === '?') { 11 | if (char && char !== '?') { 12 | finalResultArr[index] = char 13 | } 14 | } 15 | }) 16 | 17 | return finalResultArr.join('') 18 | } 19 | -------------------------------------------------------------------------------- /src/utilities/createImageData.ts: -------------------------------------------------------------------------------- 1 | import { ImageDataLike } from './ImageDataLike' 2 | 3 | export function createImageData(image: HTMLImageElement): ImageDataLike { 4 | const canvas = document.createElement('canvas') 5 | const ctx = canvas.getContext('2d') 6 | 7 | if (!ctx) throw new Error('Cannot create canvas 2d context') 8 | 9 | const width = image.naturalWidth 10 | const height = image.naturalHeight 11 | 12 | canvas.width = width 13 | canvas.height = height 14 | ctx.drawImage(image, 0, 0) 15 | 16 | return ctx.getImageData(0, 0, width, height) 17 | } 18 | -------------------------------------------------------------------------------- /src/utilities/getImageDataFromSource.ts: -------------------------------------------------------------------------------- 1 | import * as Jimp from 'jimp' 2 | import { createImageData } from './createImageData' 3 | import { ImageDataLike } from './ImageDataLike' 4 | import { isUrl } from './isUrl' 5 | 6 | const isNode = typeof process === 'object' && process.release && process.release.name === 'node' 7 | 8 | export async function getImageDataFromSource( 9 | source: string | HTMLImageElement | HTMLCanvasElement 10 | ): Promise { 11 | return new Promise((resolve, reject) => { 12 | if (typeof source === 'string') { 13 | if (source.startsWith('#')) { 14 | const imageElement = document.getElementById(source.substr(1)) 15 | 16 | if (imageElement instanceof HTMLImageElement) { 17 | resolve(createImageData(imageElement)) 18 | } 19 | 20 | if (imageElement instanceof HTMLCanvasElement) { 21 | const ctx = imageElement.getContext('2d') 22 | if (!ctx) throw new Error('Cannot create canvas 2d context') 23 | resolve(ctx.getImageData(0, 0, imageElement.width, imageElement.height)) 24 | } 25 | 26 | reject(new Error('Invalid image source specified!')) 27 | } else if (isUrl(source)) { 28 | const img = new Image() 29 | img.onerror = reject 30 | img.onload = (): void => resolve(createImageData(img)) 31 | img.src = source 32 | } else if (isNode) { 33 | Jimp.read(source, (err, image) => { 34 | if (err) { 35 | reject(err) 36 | } else { 37 | const { data, width, height } = image.bitmap 38 | 39 | resolve({ 40 | data: Uint8ClampedArray.from(data), 41 | width, 42 | height, 43 | }) 44 | } 45 | }) 46 | } 47 | } else if (source instanceof HTMLImageElement) { 48 | resolve(createImageData(source)) 49 | } else if (source instanceof HTMLCanvasElement) { 50 | const ctx = source.getContext('2d') 51 | if (!ctx) throw new Error('Cannot create canvas 2d context') 52 | resolve(ctx.getImageData(0, 0, source.width, source.height)) 53 | } 54 | }) 55 | } 56 | -------------------------------------------------------------------------------- /src/utilities/getLines.ts: -------------------------------------------------------------------------------- 1 | export function getLines(data: Uint8ClampedArray, width: number, height: number): number[] { 2 | const lines: number[] = [] 3 | const channels = data.length / (width * height) 4 | let count = 0 5 | let columnAverageLast = 0 6 | 7 | for (let column = 0; column < width; column += 1) { 8 | let columnSum = 0 9 | let columnAverage = 0 10 | 11 | for (let row = 0; row < height; row += 1) { 12 | const index = (row * width + column) * channels 13 | columnSum += Math.sqrt((data[index] ** 2 + data[index + 1] ** 2 + data[index + 2] ** 2) / 3) 14 | } 15 | 16 | // pixels are same in column 17 | columnAverage = columnSum / height >= 127 ? 255 : 0 18 | 19 | // skip white padding in the start & end 20 | if (columnAverage === 255 && count === 0) continue 21 | 22 | // count line width 23 | if (columnAverage === columnAverageLast) { 24 | count += 1 25 | } else { 26 | lines.push(count) 27 | columnAverageLast = columnAverage 28 | count = 1 29 | } 30 | 31 | // skip padding in the last 32 | if (column === width - 1 && columnAverage === 0) { 33 | lines.push(count) 34 | } 35 | } 36 | 37 | return lines 38 | } 39 | -------------------------------------------------------------------------------- /src/utilities/isUrl.ts: -------------------------------------------------------------------------------- 1 | export function isUrl(s: string): boolean { 2 | const regexp = /(ftp|http|https):\/\/(\w+:{0,1}\w*@)?(\S+)(:[0-9]+)?(\/|\/([\w#!:.?+=&%@!\-/]))?/ 3 | 4 | if (s.startsWith('#')) return false 5 | 6 | return regexp.test(s) 7 | } 8 | -------------------------------------------------------------------------------- /test/.eslintrc.json: -------------------------------------------------------------------------------- 1 | { 2 | "env": { 3 | "browser": true, 4 | "jest": true, 5 | "node": true 6 | }, 7 | "extends": [ 8 | "eslint:recommended", 9 | "plugin:@typescript-eslint/eslint-recommended", 10 | "plugin:@typescript-eslint/recommended", 11 | "plugin:@typescript-eslint/recommended-requiring-type-checking", 12 | "prettier", 13 | "prettier/@typescript-eslint" 14 | ], 15 | "parser": "@typescript-eslint/parser", 16 | "parserOptions": { 17 | "ecmaVersion": 2020, 18 | "parser": "babel-eslint", 19 | "project": "./tsconfig.json", 20 | "sourceType": "module" 21 | }, 22 | "plugins": [ 23 | "@typescript-eslint", 24 | "prettier" 25 | ], 26 | "root": true, 27 | "rules": { 28 | "@typescript-eslint/no-explicit-any": 0, 29 | "no-console": 0, 30 | "semi": 0 31 | } 32 | } 33 | -------------------------------------------------------------------------------- /test/index.test.ts: -------------------------------------------------------------------------------- 1 | import * as Jimp from 'jimp' 2 | import * as path from 'path' 3 | import javascriptBarcodeReader from '../src/index' 4 | import { combineAllPossible } from '../src/utilities/combineAllPossible' 5 | import { getImageDataFromSource } from '../src/utilities/getImageDataFromSource' 6 | import { getLines } from '../src/utilities/getLines' 7 | import { isUrl } from '../src/utilities/isUrl' 8 | 9 | async function loadImage(src: string): Promise { 10 | return new Promise((resolve, reject) => { 11 | const img = new Image() 12 | img.onerror = reject 13 | img.onload = (): void => resolve(img) 14 | img.src = src 15 | }) 16 | } 17 | 18 | function loadCanvas(img: HTMLImageElement): HTMLCanvasElement { 19 | const canvas = document.createElement('canvas') 20 | canvas.width = img.naturalWidth 21 | canvas.height = img.naturalHeight 22 | 23 | const ctx = canvas.getContext('2d') 24 | 25 | ctx?.drawImage(img, 0, 0) 26 | 27 | return canvas 28 | } 29 | 30 | beforeAll(async () => { 31 | const imageUrl = 'https://upload.wikimedia.org/wikipedia/en/a/a9/Code_93_wikipedia.png' 32 | const img = await loadImage(imageUrl) 33 | img.id = 'Code_93_wikipedia_image' 34 | 35 | const canvas = loadCanvas(img) 36 | canvas.id = 'Code_93_wikipedia_canvas' 37 | 38 | document.body.appendChild(img) 39 | document.body.appendChild(canvas) 40 | }) 41 | 42 | describe('Count lines in an image', () => { 43 | test('should detect lines in barcode image', async () => { 44 | const rowsToScan = 3 45 | const image = await Jimp.read('./test/sample-images/small-padding.png') 46 | const { data, width, height } = image.bitmap 47 | const channels = data.length / (width * height) 48 | const startIndex = channels * width * Math.floor(height / 2) 49 | const endIndex = startIndex + rowsToScan * channels * width 50 | const lines = getLines( 51 | Uint8ClampedArray.from(data.slice(startIndex, endIndex)), 52 | width, 53 | rowsToScan 54 | ) 55 | 56 | expect(lines.length).toBe(27) 57 | }) 58 | 59 | test('should detect lines in barcode image without padding', async () => { 60 | const rowsToScan = 3 61 | const image = await Jimp.read('./test/sample-images/small.png') 62 | const { data, width, height } = image.bitmap 63 | const channels = data.length / (width * height) 64 | const startIndex = channels * width * Math.floor(height / 2) 65 | const endIndex = startIndex + rowsToScan * channels * width 66 | const lines = getLines( 67 | Uint8ClampedArray.from(data.slice(startIndex, endIndex)), 68 | width, 69 | rowsToScan 70 | ) 71 | 72 | expect(lines.length).toBe(27) 73 | }) 74 | 75 | test('should return zero lines with empty image', async () => { 76 | const rowsToScan = 3 77 | const image = await Jimp.read('./test/sample-images/empty.jpg') 78 | const { data, width, height } = image.bitmap 79 | const channels = data.length / (width * height) 80 | const startIndex = channels * width * Math.floor(height / 2) 81 | const endIndex = startIndex + rowsToScan * channels * width 82 | const lines = getLines( 83 | Uint8ClampedArray.from(data.slice(startIndex, endIndex)), 84 | width, 85 | rowsToScan 86 | ) 87 | 88 | expect(lines.length).toBe(0) 89 | }) 90 | }) 91 | 92 | describe('get imageData from source', () => { 93 | test('should get imageData from url', async () => { 94 | const url = 'https://upload.wikimedia.org/wikipedia/en/a/a9/Code_93_wikipedia.png' 95 | const dataSource = await getImageDataFromSource(url) 96 | 97 | expect(typeof dataSource.data).toBe('object') 98 | expect(typeof dataSource.width).toBe('number') 99 | expect(typeof dataSource.height).toBe('number') 100 | }) 101 | 102 | test('should get imageData from file path', async () => { 103 | const url = path.resolve('./test/sample-images/codabar.jpg') 104 | const dataSource = await getImageDataFromSource(url) 105 | 106 | expect(typeof dataSource.data).toBe('object') 107 | expect(typeof dataSource.width).toBe('number') 108 | expect(typeof dataSource.height).toBe('number') 109 | }) 110 | 111 | test('should get imageData from HTMLImageElement id', async () => { 112 | const dataSource = await getImageDataFromSource('#Code_93_wikipedia_image') 113 | 114 | expect(typeof dataSource.data).toBe('object') 115 | expect(typeof dataSource.width).toBe('number') 116 | expect(typeof dataSource.height).toBe('number') 117 | }) 118 | 119 | test('should get imageData from HTMLCanvasElement id', async () => { 120 | const dataSource = await getImageDataFromSource('#Code_93_wikipedia_canvas') 121 | 122 | expect(typeof dataSource.data).toBe('object') 123 | expect(typeof dataSource.width).toBe('number') 124 | expect(typeof dataSource.height).toBe('number') 125 | }) 126 | 127 | test('should get imageData from HTMLImageElement', async () => { 128 | const imageElement = document.getElementById('Code_93_wikipedia_image') 129 | if (!imageElement || !(imageElement instanceof HTMLImageElement)) return 130 | 131 | const dataSource = await getImageDataFromSource(imageElement) 132 | 133 | expect(typeof dataSource.data).toBe('object') 134 | expect(typeof dataSource.width).toBe('number') 135 | expect(typeof dataSource.height).toBe('number') 136 | }) 137 | 138 | test('should get imageData from HTMLCanvasElement', async () => { 139 | const imageElement = document.getElementById('Code_93_wikipedia_canvas') 140 | if (!imageElement || !(imageElement instanceof HTMLCanvasElement)) return 141 | 142 | const dataSource = await getImageDataFromSource(imageElement) 143 | 144 | expect(typeof dataSource.data).toBe('object') 145 | expect(typeof dataSource.width).toBe('number') 146 | expect(typeof dataSource.height).toBe('number') 147 | }) 148 | 149 | test('should throw with invalid source', () => { 150 | getImageDataFromSource('Olalalala').catch(err => { 151 | expect(err).toBeDefined() 152 | }) 153 | }) 154 | }) 155 | 156 | describe('isUrl', () => { 157 | test('check if string is URL', () => { 158 | const url = 'https://upload.wikimedia.org/wikipedia/en/a/a9/Code_93_wikipedia.png' 159 | 160 | expect(isUrl(url)).toBeTruthy() 161 | expect(isUrl('#someString')).toBeFalsy() 162 | }) 163 | }) 164 | 165 | describe('combineAllPossible', () => { 166 | test('should be able to combine multiple results into one complete', () => { 167 | const result = combineAllPossible('?123456', '012345?') 168 | 169 | expect(result).toBe('0123456') 170 | expect(combineAllPossible('', '')).toBe('') 171 | }) 172 | }) 173 | 174 | describe('extract barcode from local files', () => { 175 | test('should detect barcode codabar', async () => { 176 | const result = await javascriptBarcodeReader({ 177 | image: path.resolve('./test/sample-images/codabar.jpg'), 178 | barcode: 'codabar', 179 | }) 180 | 181 | expect(result).toBe('A40156C') 182 | }) 183 | 184 | test('should detect barcode codabar', async () => { 185 | const result = await javascriptBarcodeReader({ 186 | image: path.resolve('./test/sample-images/codabar.jpg'), 187 | barcode: 'codabar', 188 | options: { 189 | singlePass: true, 190 | }, 191 | }) 192 | 193 | expect(result).toBe('A40156C') 194 | }) 195 | 196 | test('should detect barcode 2 of 5 standard', async () => { 197 | const result = await javascriptBarcodeReader({ 198 | image: path.resolve('./test/sample-images/code-2of5.jpg'), 199 | barcode: 'code-2of5', 200 | }) 201 | 202 | expect(result).toBe('12345670') 203 | }) 204 | 205 | test('should detect barcode 2 of 5 interleaved', async () => { 206 | const result = await javascriptBarcodeReader({ 207 | image: path.resolve('./test/sample-images/code-2of5-interleaved.jpg'), 208 | barcode: 'code-2of5', 209 | barcodeType: 'interleaved', 210 | }) 211 | 212 | expect(result).toBe('12345670') 213 | }) 214 | 215 | test('should detect barcode 39', async () => { 216 | const result = await javascriptBarcodeReader({ 217 | image: path.resolve('./test/sample-images/code-39.jpg'), 218 | barcode: 'code-39', 219 | }) 220 | 221 | expect(result).toBe('10023') 222 | }) 223 | 224 | test('should detect barcode 93', async () => { 225 | const result = await javascriptBarcodeReader({ 226 | image: path.resolve('./test/sample-images/code-93.jpg'), 227 | barcode: 'code-93', 228 | }) 229 | 230 | expect(result).toBe('123ABC') 231 | }) 232 | 233 | test('should detect barcode 128: ABC-abc-1234', async () => { 234 | const result = await javascriptBarcodeReader({ 235 | image: path.resolve('./test/sample-images/code-128.jpg'), 236 | barcode: 'code-128', 237 | }) 238 | 239 | expect(result).toBe('ABC-abc-1234') 240 | }) 241 | 242 | // test('should detect barcode 128: eeb00f0c-0c7e-a937-1794-25685779ba0c', async () => { 243 | // const result = await javascriptBarcodeReader({ 244 | // image: path.resolve('./test/sample-images/code-128-eeb00f0c-0c7e-a937-1794-25685779ba0c.png'), 245 | // barcode: 'code-128', 246 | // }) 247 | 248 | // expect(result).toBe('eeb00f0c-0c7e-a937-1794-25685779ba0c') 249 | // }) 250 | 251 | // test('should detect barcode 128: 3107cde3-d1ff-0f93-a215-4109753c0c9e', async () => { 252 | // const result = await javascriptBarcodeReader({ 253 | // image: path.resolve('./test/sample-images/code-128-3107cde3-d1ff-0f93-a215-4109753c0c9e.png'), 254 | // barcode: 'code-128', 255 | // }) 256 | 257 | // expect(result).toBe('3107cde3-d1ff-0f93-a215-4109753c0c9e') 258 | // }) 259 | 260 | test('should detect barcode EAN-8', async () => { 261 | const result = await javascriptBarcodeReader({ 262 | image: path.resolve('./test/sample-images/ean-8.jpg'), 263 | barcode: 'ean-8', 264 | options: { 265 | useAdaptiveThreshold: true, 266 | }, 267 | }) 268 | 269 | expect(result).toBe('73127727') 270 | }) 271 | 272 | test('should detect barcode EAN-13 small', async () => { 273 | const result = await javascriptBarcodeReader({ 274 | image: path.resolve('./test/sample-images/ean-13-5901234123457.png'), 275 | barcode: 'ean-13', 276 | }) 277 | 278 | expect(result).toBe('901234123457') 279 | }) 280 | 281 | test('should detect barcode EAN-13 large', async () => { 282 | const result = await javascriptBarcodeReader({ 283 | image: path.resolve('./test/sample-images/ean-13.jpg'), 284 | barcode: 'ean-13', 285 | }) 286 | 287 | expect(result).toBe('901234123457') 288 | }) 289 | 290 | test('should detect barcode 128 without padding white bars', async () => { 291 | const result = await javascriptBarcodeReader({ 292 | image: path.resolve('./test/sample-images/code-128-no-padding.jpg'), 293 | barcode: 'code-128', 294 | }) 295 | 296 | expect(result).toBe('12ab#!') 297 | }) 298 | 299 | test('should detect barcode 128 with multiple zeros', async () => { 300 | const result = await javascriptBarcodeReader({ 301 | image: path.resolve('./test/sample-images/code-128-000.jpg'), 302 | barcode: 'code-128', 303 | }) 304 | 305 | expect(result).toBe('79619647103200000134407005') 306 | }) 307 | 308 | test('should detect barcode 128 with default start Code B', async () => { 309 | const result = await javascriptBarcodeReader({ 310 | image: path.resolve('./test/sample-images/L89HE1806005080432.gif'), 311 | barcode: 'code-128', 312 | }) 313 | 314 | expect(result).toBe('L89HE1806005080432') 315 | }) 316 | 317 | test('should detect barcode 93 without padding white bars', async () => { 318 | const result = await javascriptBarcodeReader({ 319 | image: path.resolve('./test/sample-images/code-93-no-padding.jpg'), 320 | barcode: 'code-93', 321 | }) 322 | 323 | expect(result).toBe('WIKIPEDIA') 324 | }) 325 | 326 | test('should detect barcode 93 with bitmap data', async () => { 327 | const image = await Jimp.read('./test/sample-images/code-93-no-padding.jpg') 328 | const { data, width, height } = image.bitmap 329 | 330 | const result = await javascriptBarcodeReader({ 331 | image: { 332 | data: Uint8ClampedArray.from(data), 333 | width, 334 | height, 335 | }, 336 | barcode: 'code-93', 337 | }) 338 | 339 | expect(result).toBe('WIKIPEDIA') 340 | }) 341 | }) 342 | 343 | describe('extract barcode after applying adaptive threhsold', () => { 344 | test('should detect barcode codabar', async () => { 345 | const result = await javascriptBarcodeReader({ 346 | image: path.resolve('./test/sample-images/codabar.jpg'), 347 | barcode: 'codabar', 348 | options: { 349 | useAdaptiveThreshold: true, 350 | }, 351 | }) 352 | 353 | expect(result).toBe('A40156C') 354 | }) 355 | 356 | test('should detect barcode 2 of 5', async () => { 357 | const result = await javascriptBarcodeReader({ 358 | image: path.resolve('./test/sample-images/code-2of5.jpg'), 359 | barcode: 'code-2of5', 360 | options: { 361 | useAdaptiveThreshold: true, 362 | }, 363 | }) 364 | 365 | expect(result).toBe('12345670') 366 | }) 367 | 368 | test('should detect barcode 2 of 5 interleaved', async () => { 369 | const result = await javascriptBarcodeReader({ 370 | image: path.resolve('./test/sample-images/code-2of5-interleaved.jpg'), 371 | barcode: 'code-2of5', 372 | barcodeType: 'interleaved', 373 | options: { 374 | useAdaptiveThreshold: true, 375 | }, 376 | }) 377 | 378 | expect(result).toBe('12345670') 379 | }) 380 | }) 381 | 382 | describe('extract barcode from remote URL', () => { 383 | test('should detect barcode 93 from remote url', async () => { 384 | const result = await javascriptBarcodeReader({ 385 | image: 'https://upload.wikimedia.org/wikipedia/en/a/a9/Code_93_wikipedia.png', 386 | barcode: 'code-93', 387 | }) 388 | expect(result).toBe('WIKIPEDIA') 389 | }) 390 | }) 391 | 392 | describe('Fails', () => { 393 | test('throws when no barcode specified', async () => { 394 | try { 395 | await javascriptBarcodeReader({ 396 | image: 'https://upload.wikimedia.org/wikipedia/en/a/a9/Code_93_wikipedia.png', 397 | barcode: 'oallal', 398 | }) 399 | } catch (err) { 400 | expect(err).toBeDefined() 401 | } 402 | }) 403 | 404 | test('throws when invalid barcode specified', async () => { 405 | try { 406 | await javascriptBarcodeReader({ 407 | image: './test/sample-images/empty.jpg', 408 | barcode: 'none', 409 | }) 410 | } catch (err) { 411 | expect(err).toBeDefined() 412 | } 413 | }) 414 | 415 | test('throws when no barcode found', async () => { 416 | try { 417 | await javascriptBarcodeReader({ 418 | image: './test/sample-images/empty.jpg', 419 | barcode: 'code-93', 420 | }) 421 | } catch (err) { 422 | expect(err).toBeDefined() 423 | } 424 | }) 425 | }) 426 | -------------------------------------------------------------------------------- /test/sample-images/33c64780-a9c0-e92a-820c-fae7011c11e2.gif: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mubaidr/Javascript-Barcode-Reader/68127eea851c05c643e4da68138ba693581a825f/test/sample-images/33c64780-a9c0-e92a-820c-fae7011c11e2.gif -------------------------------------------------------------------------------- /test/sample-images/33c64780-a9c0-e92a-820c-fae7011c11e2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mubaidr/Javascript-Barcode-Reader/68127eea851c05c643e4da68138ba693581a825f/test/sample-images/33c64780-a9c0-e92a-820c-fae7011c11e2.png -------------------------------------------------------------------------------- /test/sample-images/65794755-0f1bd580-e126-11e9-8918-24618efdc76c.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mubaidr/Javascript-Barcode-Reader/68127eea851c05c643e4da68138ba693581a825f/test/sample-images/65794755-0f1bd580-e126-11e9-8918-24618efdc76c.png -------------------------------------------------------------------------------- /test/sample-images/L89HE1806005080432.gif: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mubaidr/Javascript-Barcode-Reader/68127eea851c05c643e4da68138ba693581a825f/test/sample-images/L89HE1806005080432.gif -------------------------------------------------------------------------------- /test/sample-images/L89HE1806005080432.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mubaidr/Javascript-Barcode-Reader/68127eea851c05c643e4da68138ba693581a825f/test/sample-images/L89HE1806005080432.png -------------------------------------------------------------------------------- /test/sample-images/codabar.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mubaidr/Javascript-Barcode-Reader/68127eea851c05c643e4da68138ba693581a825f/test/sample-images/codabar.jpg -------------------------------------------------------------------------------- /test/sample-images/code-128-000.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mubaidr/Javascript-Barcode-Reader/68127eea851c05c643e4da68138ba693581a825f/test/sample-images/code-128-000.jpg -------------------------------------------------------------------------------- /test/sample-images/code-128-3107cde3-d1ff-0f93-a215-4109753c0c9e.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mubaidr/Javascript-Barcode-Reader/68127eea851c05c643e4da68138ba693581a825f/test/sample-images/code-128-3107cde3-d1ff-0f93-a215-4109753c0c9e.png -------------------------------------------------------------------------------- /test/sample-images/code-128-eeb00f0c-0c7e-a937-1794-25685779ba0c.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mubaidr/Javascript-Barcode-Reader/68127eea851c05c643e4da68138ba693581a825f/test/sample-images/code-128-eeb00f0c-0c7e-a937-1794-25685779ba0c.png -------------------------------------------------------------------------------- /test/sample-images/code-128-no-padding.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mubaidr/Javascript-Barcode-Reader/68127eea851c05c643e4da68138ba693581a825f/test/sample-images/code-128-no-padding.jpg -------------------------------------------------------------------------------- /test/sample-images/code-128.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mubaidr/Javascript-Barcode-Reader/68127eea851c05c643e4da68138ba693581a825f/test/sample-images/code-128.jpg -------------------------------------------------------------------------------- /test/sample-images/code-2of5-interleaved.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mubaidr/Javascript-Barcode-Reader/68127eea851c05c643e4da68138ba693581a825f/test/sample-images/code-2of5-interleaved.jpg -------------------------------------------------------------------------------- /test/sample-images/code-2of5.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mubaidr/Javascript-Barcode-Reader/68127eea851c05c643e4da68138ba693581a825f/test/sample-images/code-2of5.jpg -------------------------------------------------------------------------------- /test/sample-images/code-39.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mubaidr/Javascript-Barcode-Reader/68127eea851c05c643e4da68138ba693581a825f/test/sample-images/code-39.jpg -------------------------------------------------------------------------------- /test/sample-images/code-93-no-padding.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mubaidr/Javascript-Barcode-Reader/68127eea851c05c643e4da68138ba693581a825f/test/sample-images/code-93-no-padding.jpg -------------------------------------------------------------------------------- /test/sample-images/code-93.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mubaidr/Javascript-Barcode-Reader/68127eea851c05c643e4da68138ba693581a825f/test/sample-images/code-93.jpg -------------------------------------------------------------------------------- /test/sample-images/ean-13-5901234123457.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mubaidr/Javascript-Barcode-Reader/68127eea851c05c643e4da68138ba693581a825f/test/sample-images/ean-13-5901234123457.png -------------------------------------------------------------------------------- /test/sample-images/ean-13.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mubaidr/Javascript-Barcode-Reader/68127eea851c05c643e4da68138ba693581a825f/test/sample-images/ean-13.jpg -------------------------------------------------------------------------------- /test/sample-images/ean-8.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mubaidr/Javascript-Barcode-Reader/68127eea851c05c643e4da68138ba693581a825f/test/sample-images/ean-8.jpg -------------------------------------------------------------------------------- /test/sample-images/empty.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mubaidr/Javascript-Barcode-Reader/68127eea851c05c643e4da68138ba693581a825f/test/sample-images/empty.jpg -------------------------------------------------------------------------------- /test/sample-images/medianFilterTest.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mubaidr/Javascript-Barcode-Reader/68127eea851c05c643e4da68138ba693581a825f/test/sample-images/medianFilterTest.png -------------------------------------------------------------------------------- /test/sample-images/small-padding.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mubaidr/Javascript-Barcode-Reader/68127eea851c05c643e4da68138ba693581a825f/test/sample-images/small-padding.png -------------------------------------------------------------------------------- /test/sample-images/small.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mubaidr/Javascript-Barcode-Reader/68127eea851c05c643e4da68138ba693581a825f/test/sample-images/small.png -------------------------------------------------------------------------------- /tools/gh-pages-publish.ts: -------------------------------------------------------------------------------- 1 | const { cd, exec, echo, touch } = require('shelljs') 2 | const { readFileSync } = require('fs') 3 | const url = require('url') 4 | 5 | let repoUrl 6 | let pkg = JSON.parse(readFileSync('package.json') as any) 7 | if (typeof pkg.repository === 'object') { 8 | if (!pkg.repository.hasOwnProperty('url')) { 9 | throw new Error('URL does not exist in repository section') 10 | } 11 | repoUrl = pkg.repository.url 12 | } else { 13 | repoUrl = pkg.repository 14 | } 15 | 16 | let parsedUrl = url.parse(repoUrl) 17 | let repository = (parsedUrl.host || '') + (parsedUrl.path || '') 18 | let ghToken = process.env.GH_TOKEN 19 | 20 | echo('Deploying docs!!!') 21 | cd('docs') 22 | touch('.nojekyll') 23 | exec('git init') 24 | exec('git add .') 25 | exec('git config user.name "Muhammad Ubaid Raza"') 26 | exec('git config user.email "mubaidr@gmail.com"') 27 | exec('git commit -m "docs(docs): update gh-pages"') 28 | exec(`git push --force --quiet "https://${ghToken}@${repository}" master:gh-pages`) 29 | echo('Docs deployed!!') 30 | -------------------------------------------------------------------------------- /tools/semantic-release-prepare.ts: -------------------------------------------------------------------------------- 1 | const path = require('path') 2 | const { fork } = require('child_process') 3 | const colors = require('colors') 4 | 5 | const { readFileSync, writeFileSync } = require('fs') 6 | const pkg = JSON.parse(readFileSync(path.resolve(__dirname, '..', 'package.json'))) 7 | 8 | pkg.scripts.prepush = 'npm run test:prod && npm run build' 9 | pkg.scripts.commitmsg = 'commitlint -E HUSKY_GIT_PARAMS' 10 | 11 | writeFileSync(path.resolve(__dirname, '..', 'package.json'), JSON.stringify(pkg, null, 2)) 12 | 13 | // Call husky to set up the hooks 14 | fork(path.resolve(__dirname, '..', 'node_modules', 'husky', 'lib', 'installer', 'bin'), ['install']) 15 | 16 | console.log() 17 | console.log(colors.green('Done!!')) 18 | console.log() 19 | 20 | if (pkg.repository.url.trim()) { 21 | console.log(colors.cyan('Now run:')) 22 | console.log(colors.cyan(' npm install -g semantic-release-cli')) 23 | console.log(colors.cyan(' semantic-release-cli setup')) 24 | console.log() 25 | console.log(colors.cyan('Important! Answer NO to "Generate travis.yml" question')) 26 | console.log() 27 | console.log( 28 | colors.gray('Note: Make sure "repository.url" in your package.json is correct before') 29 | ) 30 | } else { 31 | console.log(colors.red('First you need to set the "repository.url" property in package.json')) 32 | console.log(colors.cyan('Then run:')) 33 | console.log(colors.cyan(' npm install -g semantic-release-cli')) 34 | console.log(colors.cyan(' semantic-release-cli setup')) 35 | console.log() 36 | console.log(colors.cyan('Important! Answer NO to "Generate travis.yml" question')) 37 | } 38 | 39 | console.log() 40 | -------------------------------------------------------------------------------- /tools/tmp.ts: -------------------------------------------------------------------------------- 1 | import * as Jimp from 'jimp' 2 | import { applyMedianFilter } from '../src/utilities/medianFilter' 3 | 4 | async function anon(): Promise { 5 | const image = await Jimp.read('./test/sample-images/L89HE1806005080432.png') 6 | const { data, width, height } = image.bitmap 7 | const dataMedian = applyMedianFilter(Uint8ClampedArray.from(data), width, height) 8 | 9 | new Jimp({ data: Buffer.from(dataMedian), width, height }, (err, image) => { 10 | image.write('./tmp/sample.png') 11 | // this image is 1280 x 768, pixels are loaded from the given buffer. 12 | }) 13 | } 14 | 15 | anon() 16 | -------------------------------------------------------------------------------- /tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "allowSyntheticDefaultImports": true, 4 | "declaration": true, 5 | "declarationDir": "dist/types", 6 | "emitDecoratorMetadata": true, 7 | "experimentalDecorators": true, 8 | "forceConsistentCasingInFileNames": true, 9 | "incremental": true, 10 | "lib": ["es2015", "dom"], 11 | "module": "es2015", 12 | "moduleResolution": "node", 13 | "outDir": "dist/lib", 14 | "sourceMap": true, 15 | "strict": true, 16 | "target": "es2015", 17 | "typeRoots": ["node_modules/@types"] 18 | }, 19 | "include": ["src", "test"] 20 | } 21 | -------------------------------------------------------------------------------- /typedoc.json: -------------------------------------------------------------------------------- 1 | { 2 | "entryPoints": [ 3 | "./src/index.ts" 4 | ], 5 | "out": "docs" 6 | } --------------------------------------------------------------------------------