[
  {
    "path": ".gitignore",
    "content": "# Built application files\n*.apk\n*.ap_\n\n# Files for the ART/Dalvik VM\n*.dex\n\n# Java class files\n*.class\n\n# Generated files\nbin/\ngen/\nout/\n\n# Gradle files\n.gradle/\nbuild/\n\n# Local configuration file (sdk path, etc)\nlocal.properties\n\n# Proguard folder generated by Eclipse\nproguard/\n\n# Log Files\n*.log\n\n# Android Studio Navigation editor temp files\n.navigation/\n\n# Android Studio captures folder\ncaptures/\n\n# Intellij\n*.iml\n.idea/workspace.xml\n.idea/tasks.xml\n.idea/gradle.xml\n.idea/dictionaries\n.idea/libraries\n\n# Keystore files\n*.jks\n\n# External native build folder generated in Android Studio 2.2 and later\n.externalNativeBuild\n\n# Google Services (e.g. APIs or Firebase)\ngoogle-services.json\n\n# Freeline\nfreeline.py\nfreeline/\nfreeline_project_description.json\n"
  },
  {
    "path": ".idea/codeStyles/Project.xml",
    "content": "<component name=\"ProjectCodeStyleConfiguration\">\n  <code_scheme name=\"Project\" version=\"173\">\n    <Objective-C-extensions>\n      <file>\n        <option name=\"com.jetbrains.cidr.lang.util.OCDeclarationKind\" value=\"Import\" />\n        <option name=\"com.jetbrains.cidr.lang.util.OCDeclarationKind\" value=\"Macro\" />\n        <option name=\"com.jetbrains.cidr.lang.util.OCDeclarationKind\" value=\"Typedef\" />\n        <option name=\"com.jetbrains.cidr.lang.util.OCDeclarationKind\" value=\"Enum\" />\n        <option name=\"com.jetbrains.cidr.lang.util.OCDeclarationKind\" value=\"Constant\" />\n        <option name=\"com.jetbrains.cidr.lang.util.OCDeclarationKind\" value=\"Global\" />\n        <option name=\"com.jetbrains.cidr.lang.util.OCDeclarationKind\" value=\"Struct\" />\n        <option name=\"com.jetbrains.cidr.lang.util.OCDeclarationKind\" value=\"FunctionPredecl\" />\n        <option name=\"com.jetbrains.cidr.lang.util.OCDeclarationKind\" value=\"Function\" />\n      </file>\n      <class>\n        <option name=\"com.jetbrains.cidr.lang.util.OCDeclarationKind\" value=\"Property\" />\n        <option name=\"com.jetbrains.cidr.lang.util.OCDeclarationKind\" value=\"Synthesize\" />\n        <option name=\"com.jetbrains.cidr.lang.util.OCDeclarationKind\" value=\"InitMethod\" />\n        <option name=\"com.jetbrains.cidr.lang.util.OCDeclarationKind\" value=\"StaticMethod\" />\n        <option name=\"com.jetbrains.cidr.lang.util.OCDeclarationKind\" value=\"InstanceMethod\" />\n        <option name=\"com.jetbrains.cidr.lang.util.OCDeclarationKind\" value=\"DeallocMethod\" />\n      </class>\n      <extensions>\n        <pair source=\"cpp\" header=\"h\" fileNamingConvention=\"NONE\" />\n        <pair source=\"c\" header=\"h\" fileNamingConvention=\"NONE\" />\n      </extensions>\n    </Objective-C-extensions>\n  </code_scheme>\n</component>"
  },
  {
    "path": ".idea/inspectionProfiles/Project_Default.xml",
    "content": "<component name=\"InspectionProjectProfileManager\">\n  <profile version=\"1.0\">\n    <option name=\"myName\" value=\"Project Default\" />\n    <inspection_tool class=\"JavaDoc\" enabled=\"true\" level=\"WARNING\" enabled_by_default=\"true\">\n      <option name=\"TOP_LEVEL_CLASS_OPTIONS\">\n        <value>\n          <option name=\"ACCESS_JAVADOC_REQUIRED_FOR\" value=\"none\" />\n          <option name=\"REQUIRED_TAGS\" value=\"\" />\n        </value>\n      </option>\n      <option name=\"INNER_CLASS_OPTIONS\">\n        <value>\n          <option name=\"ACCESS_JAVADOC_REQUIRED_FOR\" value=\"none\" />\n          <option name=\"REQUIRED_TAGS\" value=\"\" />\n        </value>\n      </option>\n      <option name=\"METHOD_OPTIONS\">\n        <value>\n          <option name=\"ACCESS_JAVADOC_REQUIRED_FOR\" value=\"none\" />\n          <option name=\"REQUIRED_TAGS\" value=\"@return@param@throws or @exception\" />\n        </value>\n      </option>\n      <option name=\"FIELD_OPTIONS\">\n        <value>\n          <option name=\"ACCESS_JAVADOC_REQUIRED_FOR\" value=\"none\" />\n          <option name=\"REQUIRED_TAGS\" value=\"\" />\n        </value>\n      </option>\n      <option name=\"IGNORE_DEPRECATED\" value=\"false\" />\n      <option name=\"IGNORE_JAVADOC_PERIOD\" value=\"true\" />\n      <option name=\"IGNORE_DUPLICATED_THROWS\" value=\"false\" />\n      <option name=\"IGNORE_POINT_TO_ITSELF\" value=\"false\" />\n      <option name=\"myAdditionalJavadocTags\" value=\"date\" />\n    </inspection_tool>\n  </profile>\n</component>"
  },
  {
    "path": ".idea/misc.xml",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<project version=\"4\">\n  <component name=\"NullableNotNullManager\">\n    <option name=\"myDefaultNullable\" value=\"android.support.annotation.Nullable\" />\n    <option name=\"myDefaultNotNull\" value=\"android.support.annotation.NonNull\" />\n    <option name=\"myNullables\">\n      <value>\n        <list size=\"7\">\n          <item index=\"0\" class=\"java.lang.String\" itemvalue=\"org.jetbrains.annotations.Nullable\" />\n          <item index=\"1\" class=\"java.lang.String\" itemvalue=\"javax.annotation.Nullable\" />\n          <item index=\"2\" class=\"java.lang.String\" itemvalue=\"javax.annotation.CheckForNull\" />\n          <item index=\"3\" class=\"java.lang.String\" itemvalue=\"edu.umd.cs.findbugs.annotations.Nullable\" />\n          <item index=\"4\" class=\"java.lang.String\" itemvalue=\"android.support.annotation.Nullable\" />\n          <item index=\"5\" class=\"java.lang.String\" itemvalue=\"androidx.annotation.Nullable\" />\n          <item index=\"6\" class=\"java.lang.String\" itemvalue=\"androidx.annotation.RecentlyNullable\" />\n        </list>\n      </value>\n    </option>\n    <option name=\"myNotNulls\">\n      <value>\n        <list size=\"6\">\n          <item index=\"0\" class=\"java.lang.String\" itemvalue=\"org.jetbrains.annotations.NotNull\" />\n          <item index=\"1\" class=\"java.lang.String\" itemvalue=\"javax.annotation.Nonnull\" />\n          <item index=\"2\" class=\"java.lang.String\" itemvalue=\"edu.umd.cs.findbugs.annotations.NonNull\" />\n          <item index=\"3\" class=\"java.lang.String\" itemvalue=\"android.support.annotation.NonNull\" />\n          <item index=\"4\" class=\"java.lang.String\" itemvalue=\"androidx.annotation.NonNull\" />\n          <item index=\"5\" class=\"java.lang.String\" itemvalue=\"androidx.annotation.RecentlyNonNull\" />\n        </list>\n      </value>\n    </option>\n  </component>\n  <component name=\"ProjectRootManager\" version=\"2\" languageLevel=\"JDK_1_7\" project-jdk-name=\"1.8\" project-jdk-type=\"JavaSDK\">\n    <output url=\"file://$PROJECT_DIR$/build/classes\" />\n  </component>\n  <component name=\"ProjectType\">\n    <option name=\"id\" value=\"Android\" />\n  </component>\n</project>"
  },
  {
    "path": ".idea/modules.xml",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<project version=\"4\">\n  <component name=\"ProjectModuleManager\">\n    <modules>\n      <module fileurl=\"file://$PROJECT_DIR$/YZxing.iml\" filepath=\"$PROJECT_DIR$/YZxing.iml\" />\n      <module fileurl=\"file://$PROJECT_DIR$/YZxing-lib/YZxing-lib.iml\" filepath=\"$PROJECT_DIR$/YZxing-lib/YZxing-lib.iml\" />\n      <module fileurl=\"file://$PROJECT_DIR$/app/app.iml\" filepath=\"$PROJECT_DIR$/app/app.iml\" />\n    </modules>\n  </component>\n</project>"
  },
  {
    "path": ".idea/runConfigurations.xml",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<project version=\"4\">\n  <component name=\"RunConfigurationProducerService\">\n    <option name=\"ignoredProducers\">\n      <set>\n        <option value=\"org.jetbrains.plugins.gradle.execution.test.runner.AllInPackageGradleConfigurationProducer\" />\n        <option value=\"org.jetbrains.plugins.gradle.execution.test.runner.TestClassGradleConfigurationProducer\" />\n        <option value=\"org.jetbrains.plugins.gradle.execution.test.runner.TestMethodGradleConfigurationProducer\" />\n      </set>\n    </option>\n  </component>\n</project>"
  },
  {
    "path": ".idea/vcs.xml",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<project version=\"4\">\n  <component name=\"VcsDirectoryMappings\">\n    <mapping directory=\"\" vcs=\"Git\" />\n  </component>\n</project>"
  },
  {
    "path": "LICENSE",
    "content": "                                 Apache License\n                           Version 2.0, January 2004\n                        http://www.apache.org/licenses/\n\n   TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION\n\n   1. Definitions.\n\n      \"License\" shall mean the terms and conditions for use, reproduction,\n      and distribution as defined by Sections 1 through 9 of this document.\n\n      \"Licensor\" shall mean the copyright owner or entity authorized by\n      the copyright owner that is granting the License.\n\n      \"Legal Entity\" shall mean the union of the acting entity and all\n      other entities that control, are controlled by, or are under common\n      control with that entity. For the purposes of this definition,\n      \"control\" means (i) the power, direct or indirect, to cause the\n      direction or management of such entity, whether by contract or\n      otherwise, or (ii) ownership of fifty percent (50%) or more of the\n      outstanding shares, or (iii) beneficial ownership of such entity.\n\n      \"You\" (or \"Your\") shall mean an individual or Legal Entity\n      exercising permissions granted by this License.\n\n      \"Source\" form shall mean the preferred form for making modifications,\n      including but not limited to software source code, documentation\n      source, and configuration files.\n\n      \"Object\" form shall mean any form resulting from mechanical\n      transformation or translation of a Source form, including but\n      not limited to compiled object code, generated documentation,\n      and conversions to other media types.\n\n      \"Work\" shall mean the work of authorship, whether in Source or\n      Object form, made available under the License, as indicated by a\n      copyright notice that is included in or attached to the work\n      (an example is provided in the Appendix below).\n\n      \"Derivative Works\" shall mean any work, whether in Source or Object\n      form, that is based on (or derived from) the Work and for which the\n      editorial revisions, annotations, elaborations, or other modifications\n      represent, as a whole, an original work of authorship. For the purposes\n      of this License, Derivative Works shall not include works that remain\n      separable from, or merely link (or bind by name) to the interfaces of,\n      the Work and Derivative Works thereof.\n\n      \"Contribution\" shall mean any work of authorship, including\n      the original version of the Work and any modifications or additions\n      to that Work or Derivative Works thereof, that is intentionally\n      submitted to Licensor for inclusion in the Work by the copyright owner\n      or by an individual or Legal Entity authorized to submit on behalf of\n      the copyright owner. For the purposes of this definition, \"submitted\"\n      means any form of electronic, verbal, or written communication sent\n      to the Licensor or its representatives, including but not limited to\n      communication on electronic mailing lists, source code control systems,\n      and issue tracking systems that are managed by, or on behalf of, the\n      Licensor for the purpose of discussing and improving the Work, but\n      excluding communication that is conspicuously marked or otherwise\n      designated in writing by the copyright owner as \"Not a Contribution.\"\n\n      \"Contributor\" shall mean Licensor and any individual or Legal Entity\n      on behalf of whom a Contribution has been received by Licensor and\n      subsequently incorporated within the Work.\n\n   2. Grant of Copyright License. Subject to the terms and conditions of\n      this License, each Contributor hereby grants to You a perpetual,\n      worldwide, non-exclusive, no-charge, royalty-free, irrevocable\n      copyright license to reproduce, prepare Derivative Works of,\n      publicly display, publicly perform, sublicense, and distribute the\n      Work and such Derivative Works in Source or Object form.\n\n   3. Grant of Patent License. Subject to the terms and conditions of\n      this License, each Contributor hereby grants to You a perpetual,\n      worldwide, non-exclusive, no-charge, royalty-free, irrevocable\n      (except as stated in this section) patent license to make, have made,\n      use, offer to sell, sell, import, and otherwise transfer the Work,\n      where such license applies only to those patent claims licensable\n      by such Contributor that are necessarily infringed by their\n      Contribution(s) alone or by combination of their Contribution(s)\n      with the Work to which such Contribution(s) was submitted. If You\n      institute patent litigation against any entity (including a\n      cross-claim or counterclaim in a lawsuit) alleging that the Work\n      or a Contribution incorporated within the Work constitutes direct\n      or contributory patent infringement, then any patent licenses\n      granted to You under this License for that Work shall terminate\n      as of the date such litigation is filed.\n\n   4. Redistribution. You may reproduce and distribute copies of the\n      Work or Derivative Works thereof in any medium, with or without\n      modifications, and in Source or Object form, provided that You\n      meet the following conditions:\n\n      (a) You must give any other recipients of the Work or\n          Derivative Works a copy of this License; and\n\n      (b) You must cause any modified files to carry prominent notices\n          stating that You changed the files; and\n\n      (c) You must retain, in the Source form of any Derivative Works\n          that You distribute, all copyright, patent, trademark, and\n          attribution notices from the Source form of the Work,\n          excluding those notices that do not pertain to any part of\n          the Derivative Works; and\n\n      (d) If the Work includes a \"NOTICE\" text file as part of its\n          distribution, then any Derivative Works that You distribute must\n          include a readable copy of the attribution notices contained\n          within such NOTICE file, excluding those notices that do not\n          pertain to any part of the Derivative Works, in at least one\n          of the following places: within a NOTICE text file distributed\n          as part of the Derivative Works; within the Source form or\n          documentation, if provided along with the Derivative Works; or,\n          within a display generated by the Derivative Works, if and\n          wherever such third-party notices normally appear. The contents\n          of the NOTICE file are for informational purposes only and\n          do not modify the License. You may add Your own attribution\n          notices within Derivative Works that You distribute, alongside\n          or as an addendum to the NOTICE text from the Work, provided\n          that such additional attribution notices cannot be construed\n          as modifying the License.\n\n      You may add Your own copyright statement to Your modifications and\n      may provide additional or different license terms and conditions\n      for use, reproduction, or distribution of Your modifications, or\n      for any such Derivative Works as a whole, provided Your use,\n      reproduction, and distribution of the Work otherwise complies with\n      the conditions stated in this License.\n\n   5. Submission of Contributions. Unless You explicitly state otherwise,\n      any Contribution intentionally submitted for inclusion in the Work\n      by You to the Licensor shall be under the terms and conditions of\n      this License, without any additional terms or conditions.\n      Notwithstanding the above, nothing herein shall supersede or modify\n      the terms of any separate license agreement you may have executed\n      with Licensor regarding such Contributions.\n\n   6. Trademarks. This License does not grant permission to use the trade\n      names, trademarks, service marks, or product names of the Licensor,\n      except as required for reasonable and customary use in describing the\n      origin of the Work and reproducing the content of the NOTICE file.\n\n   7. Disclaimer of Warranty. Unless required by applicable law or\n      agreed to in writing, Licensor provides the Work (and each\n      Contributor provides its Contributions) on an \"AS IS\" BASIS,\n      WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or\n      implied, including, without limitation, any warranties or conditions\n      of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A\n      PARTICULAR PURPOSE. You are solely responsible for determining the\n      appropriateness of using or redistributing the Work and assume any\n      risks associated with Your exercise of permissions under this License.\n\n   8. Limitation of Liability. In no event and under no legal theory,\n      whether in tort (including negligence), contract, or otherwise,\n      unless required by applicable law (such as deliberate and grossly\n      negligent acts) or agreed to in writing, shall any Contributor be\n      liable to You for damages, including any direct, indirect, special,\n      incidental, or consequential damages of any character arising as a\n      result of this License or out of the use or inability to use the\n      Work (including but not limited to damages for loss of goodwill,\n      work stoppage, computer failure or malfunction, or any and all\n      other commercial damages or losses), even if such Contributor\n      has been advised of the possibility of such damages.\n\n   9. Accepting Warranty or Additional Liability. While redistributing\n      the Work or Derivative Works thereof, You may choose to offer,\n      and charge a fee for, acceptance of support, warranty, indemnity,\n      or other liability obligations and/or rights consistent with this\n      License. However, in accepting such obligations, You may act only\n      on Your own behalf and on Your sole responsibility, not on behalf\n      of any other Contributor, and only if You agree to indemnify,\n      defend, and hold each Contributor harmless for any liability\n      incurred by, or claims asserted against, such Contributor by reason\n      of your accepting any such warranty or additional liability.\n\n   END OF TERMS AND CONDITIONS\n\n   APPENDIX: How to apply the Apache License to your work.\n\n      To apply the Apache License to your work, attach the following\n      boilerplate notice, with the fields enclosed by brackets \"[]\"\n      replaced with your own identifying information. (Don't include\n      the brackets!)  The text should be enclosed in the appropriate\n      comment syntax for the file format. We also recommend that a\n      file or class name and description of purpose be included on the\n      same \"printed page\" as the copyright notice for easier\n      identification within third-party archives.\n\n   Copyright [yyyy] [name of copyright owner]\n\n   Licensed under the Apache License, Version 2.0 (the \"License\");\n   you may not use this file except in compliance with the License.\n   You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n   Unless required by applicable law or agreed to in writing, software\n   distributed under the License is distributed on an \"AS IS\" BASIS,\n   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n   See the License for the specific language governing permissions and\n   limitations under the License.\n"
  },
  {
    "path": "README.md",
    "content": "# YZxing\n一款仿微信扫一扫界面，基于zxing实现的扫码库。  \n### **实现效果** ###  \n![image](https://github.com/MRYangY/YZxing/blob/master/app/src/main/res/drawable-xhdpi/screenshot_2.png) ![image](https://github.com/MRYangY/YZxing/blob/master/app/src/main/res/drawable-xhdpi/screenshot_1.png)  \n\n### **使用方式** ###  \n  \n~~首先通过在build.gradle文件中添加如下编译语句将YZxing-lib库添加到项目中。  \n  compile 'com.yangy:YZxing-lib:1.1'~~\n（或者在直接把本仓库里面的YZxing库下载下来，添加到项目中。）  \n然后在点击跳转到扫码界面的点击事件中，调用如下方法：  \n Intent intent = new Intent(this, ScannerActivity.class);  \n        //这里可以用intent传递一些参数，比如扫码聚焦框尺寸大小，支持的扫码类型。  \n//        //设置扫码框的宽  \n//        intent.putExtra(Constant.EXTRA_SCANNER_FRAME_WIDTH, 400);  \n//        //设置扫码框的高  \n//        intent.putExtra(Constant.EXTRA_SCANNER_FRAME_HEIGHT, 400);  \n//        //设置扫码框距顶部的位置  \n//        intent.putExtra(Constant.EXTRA_SCANNER_FRAME_TOP_PADDING, 100);  \n//        Bundle bundle = new Bundle();  \n//        //设置支持的扫码类型  \n//        bundle.putSerializable(Constant.EXTRA_SCAN_CODE_TYPE, mHashMap);  \n//        intent.putExtras(bundle);  \n        startActivityForResult(intent, RESULT_REQUEST_CODE);  \n\n这里可以使用intent传递一些配置参数。支持有设置扫码框的大小，及位置；设置支持的扫码类型。目前支持的自定义配置不多，后续有机会再扩充。 跳转的时候要有startActivityForResult来跳转，这样在扫码成功之后，返回的结果可以在onActivityResult方法中处理代码如下：  \n@Override  \n    protected void onActivityResult(int requestCode, int resultCode, Intent data) {  \n        if (resultCode == RESULT_OK) {  \n        \n            switch (requestCode) {  \n            \n                case RESULT_REQUEST_CODE:  \n                \n                    if (data == null) return;  \n                    \n                    String type = data.getStringExtra(Constant.EXTRA_RESULT_CODE_TYPE);  \n                    \n                    String content = data.getStringExtra(Constant.EXTRA_RESULT_CONTENT);  \n                    \n                    Toast.makeText(MainActivity.this,\"codeType:\" + type  \n                    \n                            + \"-----content:\" + content,Toast.LENGTH_SHORT).show();  \n                            \n                    break;  \n                    \n                default:  \n                \n                    break;  \n                    \n\n            }  \n            \n        }  \n        \n        super.onActivityResult(requestCode, resultCode, data);  \n        \n    }  \n     \n     \n----------------------------------------  \n     \n     \n     \n## **YZxing版本更新说明** ##  \n\n目前最新版为v2.2！！\n\n-------------\n     \n   目前YZxing已经更新到了v2.1  ，更新内容有：  \n     1.修改空指针导致的的闪退bug。  \n     2.添加从相册获取二维码功能（用户可以选择是否使用该功能）。  \n     \n     \n        \n      首先通过在build.gradle文件中添加如下编译语句将YZxing-lib库添加到项目中。  \n  compile 'com.yangy:YZxing-lib:2.1'  \n（或者在直接把本仓库里面的YZxing库下载下来，添加到项目中。）   \n\n     使用方式与1.1版本一致，注意的是如需使用**从相册获取二维码功能**则需要在intent中添加是否启用scan_from_pic，默认是FALSE：  \n     **//        //设置是否启用从相册获取二维码。  \n     \n//        intent.putExtra(Constant.EXTRA_IS_ENABLE_SCAN_FROM_PIC,true);**     \n  \n### **从照片获取二维码的效果如下：** ### \n\n![image](https://github.com/MRYangY/YZxing/blob/master/app/src/main/res/effect-picture/scan_form_pic_%20effect.gif)\n\n\n## **觉得还不错的就动动手指给个star吧(*^__^*)** ##\n   \n   \n   \n   \n   \n## **关于二维码功能的分析请移步至文章** ##\nhttps://blog.csdn.net/qq_34902522/column/info/28769\n\n"
  },
  {
    "path": "YZxing-lib/.gitignore",
    "content": "/build\n"
  },
  {
    "path": "YZxing-lib/build.gradle",
    "content": "apply plugin: 'com.android.library'\napply plugin: 'com.jfrog.bintray'\napply plugin: 'com.github.dcendents.android-maven'\n\ndef siteUrl = 'https://github.com/MRYangY/YZxing'   // 项目的主页\ndef gitUrl = 'https://github.com/MRYangY/YZxing.git'   // Git仓库的url\nProperties properties = new Properties()\nproperties.load(project.rootProject.file('local.properties').newDataInputStream())\n\nversion = \"2.2\" //发布版本号\ngroup = \"com.yangy\" //最终引用形式，如compile 'com.yangy.lfilepicker:1.0.0'，其中lfilepicker在后面配置\nandroid {\n    compileSdkVersion 26\n    buildToolsVersion \"25.0.3\"\n\n    defaultConfig {\n        minSdkVersion 19\n        targetSdkVersion 26\n        versionCode 1\n        versionName \"1.0\"\n\n        testInstrumentationRunner \"android.support.test.runner.AndroidJUnitRunner\"\n\n    }\n    buildTypes {\n        release {\n            minifyEnabled false\n            proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'\n        }\n    }\n}\n\ndependencies {\n    compile fileTree(dir: 'libs', include: ['*.jar'])\n    androidTestCompile('com.android.support.test.espresso:espresso-core:2.2.2', {\n        exclude group: 'com.android.support', module: 'support-annotations'\n    })\n    compile 'com.android.support:appcompat-v7:26.+'\n    compile 'com.android.support.constraint:constraint-layout:1.0.2'\n    testCompile 'junit:junit:4.12'\n    compile 'com.google.zxing:core:3.3.0'\n}\n\nbintray {\n    user = properties.getProperty(\"bintray.user\")\n    key = properties.getProperty(\"bintray.apikey\")\n    pkg {\n        repo = 'YZXing'//自己创建的仓库名字\n        name = 'yzxing'//上传到JCenter的名字,最终引用的名字\n        websiteUrl = siteUrl\n        vcsUrl = gitUrl\n        licenses = ['Apache-2.0']//不能随便写，只能是仓库创建时选择的license type\n        userOrg = 'yangyulibrary' //自己创建的organization名称\n        publish = true // 是否是公开项目，公开别人可以引用\n\n        version {\n            name = '2.2'\n            desc = '基于zxing的扫码库，样式类似于微信扫一扫'//描述，自己定义\n            released  = new Date()\n            vcsTag = 'v2.2'\n            attributes = ['gradle-plugin': 'com.use.less:com.use.less.gradle:gradle-useless-plugin']\n        }\n    }\n    configurations = ['archives']\n}\n\ninstall {\n    repositories.mavenInstaller {\n        // This generates POM.xml with proper parameters\n        pom {\n            project {\n                packaging 'aar'\n                // Add your description here\n                name 'yangy Android'\n                description 'yangy open library.'\n                url siteUrl\n                // Set your license\n                licenses {\n                    license {\n                        name 'Apache-2.0' //和之前自己定义的协议一致\n                        url 'https://raw.githubusercontent.com/minggo620/Pluto-Android/master/LICENSE'\n                    }\n                }\n                developers {\n                    developer {\n                        id 'mryangy423'        //填写bintray或者github的用户名\n                        name 'mryangy423'         //姓名\n                        email 'mryangy423@gmail.com'//邮箱\n                    }\n                }\n                scm {\n                    connection gitUrl\n                    developerConnection gitUrl\n                    url siteUrl\n                }\n            }\n        }\n\n        task sourcesJar(type: Jar) {\n            from android.sourceSets.main.java.srcDirs\n            classifier = 'sources'\n        }\n        task javadoc(type: Javadoc) {\n            failOnError false //必须添加以免出错\n            source = android.sourceSets.main.java.srcDirs\n            classpath += project.files(android.getBootClasspath().join(File.pathSeparator))\n        }\n        task javadocJar(type: Jar, dependsOn: javadoc) {\n            classifier = 'javadoc'\n            from javadoc.destinationDir\n        }\n        artifacts {\n            archives javadocJar\n            archives sourcesJar\n        }\n\n        javadoc {\n            options{\n                //如果你的项目里面有中文注释的话，必须将格式设置为UTF-8，不然会出现乱码\n                encoding \"UTF-8\"\n                charSet 'UTF-8'\n                author true\n                version true\n                links \"http://docs.oracle.com/javase/7/docs/api\"\n            }\n        }\n\n    }\n}\n\n"
  },
  {
    "path": "YZxing-lib/proguard-rules.pro",
    "content": "# Add project specific ProGuard rules here.\n# By default, the flags in this file are appended to flags specified\n# in /Users/yangyu/Library/Android/sdk/tools/proguard/proguard-android.txt\n# You can edit the include path and order by changing the proguardFiles\n# directive in build.gradle.\n#\n# For more details, see\n#   http://developer.android.com/guide/developing/tools/proguard.html\n\n# Add any project specific keep options here:\n\n# If your project uses WebView with JS, uncomment the following\n# and specify the fully qualified class name to the JavaScript interface\n# class:\n#-keepclassmembers class fqcn.of.javascript.interface.for.webview {\n#   public *;\n#}\n\n# Uncomment this to preserve the line number information for\n# debugging stack traces.\n#-keepattributes SourceFile,LineNumberTable\n\n# If you keep the line number information, uncomment this to\n# hide the original source file name.\n#-renamesourcefileattribute SourceFile\n"
  },
  {
    "path": "YZxing-lib/src/androidTest/java/com/example/qrcode/ExampleInstrumentedTest.java",
    "content": "package com.example.qrcode;\n\nimport android.content.Context;\nimport android.support.test.InstrumentationRegistry;\nimport android.support.test.runner.AndroidJUnit4;\n\nimport org.junit.Test;\nimport org.junit.runner.RunWith;\n\nimport static org.junit.Assert.*;\n\n/**\n * Instrumentation test, which will execute on an Android device.\n *\n * @see <a href=\"http://d.android.com/tools/testing\">Testing documentation</a>\n */\n@RunWith(AndroidJUnit4.class)\npublic class ExampleInstrumentedTest {\n    @Test\n    public void useAppContext() throws Exception {\n        // Context of the app under test.\n        Context appContext = InstrumentationRegistry.getTargetContext();\n\n        assertEquals(\"com.example.qrcode.test\", appContext.getPackageName());\n    }\n}\n"
  },
  {
    "path": "YZxing-lib/src/main/AndroidManifest.xml",
    "content": "<manifest xmlns:android=\"http://schemas.android.com/apk/res/android\"\n\n    package=\"com.example.qrcode\">\n    <uses-permission android:name=\"android.permission.CAMERA\"/>\n    <uses-permission android:name=\"android.permission.WRITE_EXTERNAL_STORAGE\"/>\n    <uses-permission android:name=\"android.permission.INTERNET\"/>\n\n    <application android:allowBackup=\"true\"\n        android:label=\"@string/app_name\"\n        android:supportsRtl=\"true\"\n        >\n\n        <activity android:name=\".ScannerActivity\"\n            android:screenOrientation=\"portrait\"\n            android:theme=\"@style/MyAppTheme\"\n            />\n        <activity android:name=\".ShowResultActivity\"\n            android:theme=\"@style/MyAppTheme\"/>\n        <activity android:name=\".BarcodeActivity\"\n            android:theme=\"@style/MyAppTheme\"/>\n    </application>\n\n</manifest>\n"
  },
  {
    "path": "YZxing-lib/src/main/java/com/example/qrcode/BarcodeActivity.java",
    "content": "package com.example.qrcode;\n\nimport android.app.Activity;\nimport android.graphics.Bitmap;\nimport android.graphics.Point;\nimport android.os.Bundle;\nimport android.os.Handler;\nimport android.os.Looper;\nimport android.support.annotation.Nullable;\nimport android.text.TextUtils;\nimport android.util.Log;\nimport android.view.Display;\nimport android.view.View;\nimport android.view.WindowManager;\nimport android.widget.Button;\nimport android.widget.EditText;\nimport android.widget.ImageView;\nimport android.widget.RadioButton;\nimport android.widget.RadioGroup;\nimport android.widget.Toast;\n\nimport com.google.zxing.BarcodeFormat;\nimport com.google.zxing.EncodeHintType;\nimport com.google.zxing.MultiFormatWriter;\nimport com.google.zxing.common.BitMatrix;\n\nimport java.util.EnumMap;\nimport java.util.Map;\n\n/**\n * Create by rain\n * <p>\n * DATE:18-10-26\n * <p>\n * Describe:\n **/\npublic class BarcodeActivity extends Activity {\n    private static final String TAG = \"BarcodeActivity\";\n    private static final int WHITE = 0xFFFFFFFF;\n    private static final int BLACK = 0xFF000000;\n\n    private static final int CODE_TYPE_QR_CODE = 0x11;\n    private static final int CODE_TYPE_CODE_128 = 0x12;\n\n    private int mType = CODE_TYPE_QR_CODE;\n\n    private EditText mInputContentView;\n    private Button mEncodeView;\n    private ImageView mBarcodeImageView;\n    private RadioGroup mRgCodeType;\n    private RadioButton mRbQrCode;\n    private RadioButton mRb128Code;\n\n    private Bitmap bitmap;\n\n    private Handler mHandler = new Handler(Looper.getMainLooper());\n\n    private int smallerDimension;\n    private int barcodeImageWidth;\n    private int barcodeImageHeight;\n\n\n    @Override\n    protected void onCreate(@Nullable Bundle savedInstanceState) {\n        super.onCreate(savedInstanceState);\n        setContentView(R.layout.layout_activity_barcode);\n        mInputContentView = findViewById(R.id.et_input_content);\n        mEncodeView = findViewById(R.id.bt_encode);\n        mEncodeView.setOnClickListener(mEncodeListener);\n        mBarcodeImageView = findViewById(R.id.barcode_image);\n        mRgCodeType = findViewById(R.id.rg_code_type);\n        mRbQrCode = findViewById(R.id.rb_qr_code);\n        mRb128Code = findViewById(R.id.rb_code_128);\n        mRgCodeType.setOnCheckedChangeListener(onCheckedChangeListener);\n\n        WindowManager manager = (WindowManager) getSystemService(WINDOW_SERVICE);\n        Display display = manager.getDefaultDisplay();\n        Point displaySize = new Point();\n        display.getSize(displaySize);\n        int width = displaySize.x;\n        int height = displaySize.y;\n        smallerDimension = width < height ? width : height;\n        smallerDimension = smallerDimension * 7 / 8;\n        barcodeImageWidth = smallerDimension;\n        barcodeImageHeight = smallerDimension;\n        Log.e(TAG, \"onCreate: smallerDimension = \" + smallerDimension);\n    }\n\n    private RadioGroup.OnCheckedChangeListener onCheckedChangeListener = new RadioGroup.OnCheckedChangeListener() {\n        @Override\n        public void onCheckedChanged(RadioGroup group, int checkedId) {\n            barcodeImageWidth = smallerDimension;\n            if (checkedId == R.id.rb_qr_code) {\n                mType = CODE_TYPE_QR_CODE;\n                barcodeImageHeight = smallerDimension;\n            } else if (checkedId == R.id.rb_code_128) {\n                mType = CODE_TYPE_CODE_128;\n                barcodeImageHeight = smallerDimension / 2;\n            }\n        }\n    };\n\n    private View.OnClickListener mEncodeListener = new View.OnClickListener() {\n        @Override\n        public void onClick(View v) {\n            String text = mInputContentView.getText().toString();\n            if (TextUtils.isEmpty(text)) {\n                Toast.makeText(BarcodeActivity.this, \"请先输入条形码内容!!\", Toast.LENGTH_SHORT).show();\n                return;\n            }\n            encode(text);\n        }\n    };\n\n    private void encode(String content) {\n        Log.e(TAG, \"encode: content = \" + content);\n        if (content == null) {\n            return;\n        }\n        Map<EncodeHintType, Object> hints = null;\n        String encoding = guessAppropriateEncoding(content);\n        if (encoding != null) {\n            hints = new EnumMap<>(EncodeHintType.class);\n            hints.put(EncodeHintType.CHARACTER_SET, encoding);\n        }\n        BitMatrix result;\n        try {\n            result = new MultiFormatWriter().encode(content, getWantedCodeType(mType)\n                    , barcodeImageWidth, barcodeImageHeight, hints);\n            int width = result.getWidth();\n            int height = result.getHeight();\n            int[] pixels = new int[width * height];\n            for (int y = 0; y < height; y++) {\n                int offset = y * width;\n                for (int x = 0; x < width; x++) {\n                    pixels[offset + x] = result.get(x, y) ? BLACK : WHITE;\n                }\n            }\n\n            bitmap = Bitmap.createBitmap(width, height, Bitmap.Config.ARGB_8888);\n            bitmap.setPixels(pixels, 0, width, 0, 0, width, height);\n            mHandler.post(mUpdateImageRunnable);\n        } catch (Exception iae) {\n            // Unsupported format\n            Log.e(TAG, \"encode: \" + iae.getMessage());\n        }\n    }\n\n\n    private Runnable mUpdateImageRunnable = new Runnable() {\n        @Override\n        public void run() {\n            mBarcodeImageView.setImageBitmap(bitmap);\n        }\n    };\n\n    /**\n     * get apposite barcode type\n     *\n     * @param type\n     * @return\n     */\n    private BarcodeFormat getWantedCodeType(int type) {\n        switch (type) {\n            case CODE_TYPE_QR_CODE:\n                return BarcodeFormat.QR_CODE;\n            case CODE_TYPE_CODE_128:\n                return BarcodeFormat.CODE_128;\n            default:\n                return BarcodeFormat.QR_CODE;\n        }\n    }\n\n\n    private static String guessAppropriateEncoding(CharSequence contents) {\n        // Very crude at the moment\n        for (int i = 0; i < contents.length(); i++) {\n            if (contents.charAt(i) > 0xFF) {\n                return \"UTF-8\";\n            }\n        }\n        return null;\n    }\n}\n"
  },
  {
    "path": "YZxing-lib/src/main/java/com/example/qrcode/BeepManager.java",
    "content": "package com.example.qrcode;\n\nimport android.app.Activity;\nimport android.content.Context;\nimport android.content.SharedPreferences;\nimport android.content.res.AssetFileDescriptor;\nimport android.media.AudioManager;\nimport android.media.MediaPlayer;\nimport android.os.Vibrator;\nimport android.preference.PreferenceManager;\nimport android.util.Log;\n\nimport java.io.Closeable;\nimport java.io.IOException;\n\n/**\n * Created by yangyu on 17/10/19.\n */\n\npublic final class BeepManager implements MediaPlayer.OnErrorListener, Closeable {\n\n    private static final String TAG = BeepManager.class.getSimpleName();\n\n    private static final float BEEP_VOLUME = 0.10f;\n    private static final long VIBRATE_DURATION = 200L;\n\n    private final Activity activity;\n    private MediaPlayer mediaPlayer;\n    private boolean playBeep;\n    private boolean vibrate;\n\n    BeepManager(Activity activity) {\n        this.activity = activity;\n        this.mediaPlayer = null;\n        updatePrefs();\n    }\n\n    synchronized void updatePrefs() {\n        SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(activity);\n        playBeep = shouldBeep(prefs, activity);\n        vibrate = prefs.getBoolean(Constant.KEY_VIBRATE, false);\n        if (playBeep && mediaPlayer == null) {\n            // The volume on STREAM_SYSTEM is not adjustable, and users found it too loud,\n            // so we now play on the music stream.\n            activity.setVolumeControlStream(AudioManager.STREAM_MUSIC);\n            mediaPlayer = buildMediaPlayer(activity);\n        }\n    }\n\n    synchronized void playBeepSoundAndVibrate() {\n        if (playBeep && mediaPlayer != null) {\n            mediaPlayer.start();\n        }\n        if (vibrate) {\n            Vibrator vibrator = (Vibrator) activity.getSystemService(Context.VIBRATOR_SERVICE);\n            vibrator.vibrate(VIBRATE_DURATION);\n        }\n    }\n\n    private static boolean shouldBeep(SharedPreferences prefs, Context activity) {\n        boolean shouldPlayBeep = prefs.getBoolean(Constant.KEY_PLAY_BEEP, true);\n        if (shouldPlayBeep) {\n            // See if sound settings overrides this\n            AudioManager audioService = (AudioManager) activity.getSystemService(Context.AUDIO_SERVICE);\n            if (audioService.getRingerMode() != AudioManager.RINGER_MODE_NORMAL) {\n                shouldPlayBeep = false;\n            }\n        }\n        return shouldPlayBeep;\n    }\n\n    private MediaPlayer buildMediaPlayer(Context activity) {\n        MediaPlayer mediaPlayer = new MediaPlayer();\n        try (AssetFileDescriptor file = activity.getResources().openRawResourceFd(R.raw.beep)) {\n            mediaPlayer.setDataSource(file.getFileDescriptor(), file.getStartOffset(), file.getLength());\n            mediaPlayer.setOnErrorListener(this);\n            mediaPlayer.setAudioStreamType(AudioManager.STREAM_MUSIC);\n            mediaPlayer.setLooping(false);\n            mediaPlayer.setVolume(BEEP_VOLUME, BEEP_VOLUME);\n            mediaPlayer.prepare();\n            return mediaPlayer;\n        } catch (IOException ioe) {\n            Log.w(TAG, ioe);\n            mediaPlayer.release();\n            return null;\n        }\n    }\n\n    @Override\n    public synchronized boolean onError(MediaPlayer mp, int what, int extra) {\n        if (what == MediaPlayer.MEDIA_ERROR_SERVER_DIED) {\n            // we are finished, so put up an appropriate error toast if required and finish\n            activity.finish();\n        } else {\n            // possibly media player error, so release and recreate\n            close();\n            updatePrefs();\n        }\n        return true;\n    }\n\n    @Override\n    public synchronized void close() {\n        if (mediaPlayer != null) {\n            mediaPlayer.release();\n            mediaPlayer = null;\n        }\n    }\n\n}\n"
  },
  {
    "path": "YZxing-lib/src/main/java/com/example/qrcode/Constant.java",
    "content": "package com.example.qrcode;\n\n/**\n * Created by yangyu on 17/10/29.\n */\n\npublic class Constant {\n    public static final int MESSAGE_SCANNER_DECODE = 0;\n    public static final int MESSAGE_SCANNER_DECODE_SUCCEEDED = 1;\n    public static final int MESSAGE_SCANNER_DECODE_FAIL = 2;\n    public static final int MESSAGE_SCANNER_QUIT = 3;\n\n    public static final String KEY_AUTO_FOCUS = \"auto_focus\";\n    public static final String KEY_DISABLE_CONTINUOUS_FOCUS = \"continuous_focus\";\n    public static final String KEY_VIBRATE = \"beep_vibrate\";\n    public static final String KEY_PLAY_BEEP = \"beep_play\";\n\n    public static final String EXTRA_SCANNER_FRAME_WIDTH = \"scan_frame_width\";\n    public static final String EXTRA_SCANNER_FRAME_HEIGHT = \"scan_frame_height\";\n    public static final String EXTRA_SCANNER_FRAME_TOP_PADDING = \"scan_frame_top_padding\";\n    public static final String EXTRA_SCAN_CODE_TYPE = \"scan_code_type\";\n    public static final String EXTRA_IS_ENABLE_SCAN_FROM_PIC = \"is_enable_scan_from_pic\";\n\n    public static final String EXTRA_RESULT_CODE_TYPE = \"result_code_type\";\n    public static final String EXTRA_RESULT_CONTENT = \"result_content\";\n\n\n    public static final String EXTRA_RESULT_TEXT_FROM_PIC = \"text_from_pic\";\n}\n"
  },
  {
    "path": "YZxing-lib/src/main/java/com/example/qrcode/ScannerActivity.java",
    "content": "package com.example.qrcode;\n\nimport android.Manifest;\nimport android.content.Intent;\nimport android.content.pm.PackageManager;\nimport android.graphics.Bitmap;\nimport android.graphics.Color;\nimport android.net.Uri;\nimport android.os.Bundle;\nimport android.os.Handler;\nimport android.os.Message;\nimport android.support.annotation.NonNull;\nimport android.support.annotation.Nullable;\nimport android.support.v4.app.ActivityCompat;\nimport android.support.v4.content.ContextCompat;\nimport android.support.v7.app.AppCompatActivity;\nimport android.support.v7.widget.Toolbar;\nimport android.util.Log;\nimport android.view.KeyEvent;\nimport android.view.Menu;\nimport android.view.MenuItem;\nimport android.view.SurfaceHolder;\nimport android.view.SurfaceView;\nimport android.view.View;\n\nimport com.example.qrcode.camera.CameraManager;\nimport com.example.qrcode.decode.InactivityTimer;\nimport com.example.qrcode.decode.ScannerHandler;\nimport com.example.qrcode.utils.CommonUtils;\nimport com.example.qrcode.utils.DecodeUtils;\nimport com.example.qrcode.utils.UriUtils;\nimport com.example.qrcode.view.ScannerView;\nimport com.google.zxing.BarcodeFormat;\nimport com.google.zxing.Result;\n\nimport java.io.IOException;\nimport java.lang.ref.WeakReference;\nimport java.util.Collection;\nimport java.util.EnumSet;\nimport java.util.HashMap;\nimport java.util.Set;\n\n\n/**\n * Created by yangyu on 17/10/18.\n */\n\npublic class ScannerActivity extends AppCompatActivity implements SurfaceHolder.Callback {\n    private static final String TAG = \"ScannerActivity\";\n\n    public static final String BARCODE_FORMAT = \"support_barcode_format\";\n    public final int PERMISSION_REQUEST_CODE_WRITE_EXTERNAL_STORAGE = 0X11;\n    public final int REQUEST_CODE_GET_PIC_URI = 0X12;\n    private final int MESSAGE_DECODE_FROM_BITMAP = 0;\n\n    private Toolbar mToolBar;\n    private ScannerView mScannerView;\n    private SurfaceView mSurfaceView;\n\n    private InactivityTimer mInactivityTimer;\n    private BeepManager beepManager;\n\n    private com.example.qrcode.camera.CameraManager cameraManager;\n    private ScannerHandler handler;\n    private Collection<BarcodeFormat> decodeFormats;\n\n    private int mScanFocusWidth;\n    private int mScanFocusHeight;\n    private int mScanFocusTopPadding;\n\n    private boolean isEnableScanFromPicture;\n    private boolean hasSurface;\n    private MyHandler mHandler;\n\n    private static class MyHandler extends Handler {\n        private WeakReference<ScannerActivity> activity;\n\n        MyHandler(ScannerActivity mainActivityWeakReference) {\n            activity = new WeakReference<ScannerActivity>(mainActivityWeakReference);\n        }\n\n        @Override\n        public void handleMessage(Message msg) {\n            super.handleMessage(msg);\n            ScannerActivity activity = this.activity.get();\n            if (activity != null) {\n                if (msg.what == activity.MESSAGE_DECODE_FROM_BITMAP) {\n                    Bitmap bm = (Bitmap) msg.obj;\n                    DecodeUtils.DecodeAsyncTask decodeAsyncTask = new DecodeUtils.DecodeAsyncTask(activity);\n                    decodeAsyncTask.execute(bm);\n                }\n            }\n        }\n    }\n\n    @Override\n    protected void onCreate(@Nullable Bundle savedInstanceState) {\n        super.onCreate(savedInstanceState);\n        setContentView(R.layout.layout_activity_scanner);\n        initView();\n        hasSurface = false;\n        Intent intent = getIntent();\n        if (intent != null) {\n            mScanFocusWidth = intent.getIntExtra(Constant.EXTRA_SCANNER_FRAME_WIDTH, -1);\n            mScanFocusHeight = intent.getIntExtra(Constant.EXTRA_SCANNER_FRAME_HEIGHT, -1);\n            mScanFocusTopPadding = intent.getIntExtra(Constant.EXTRA_SCANNER_FRAME_TOP_PADDING, -1);\n            isEnableScanFromPicture = intent.getBooleanExtra(Constant.EXTRA_IS_ENABLE_SCAN_FROM_PIC, false);\n            Bundle b = intent.getExtras();\n            if (b != null) {\n                HashMap<String, Set> formats = (HashMap<String, Set>) b.getSerializable(Constant.EXTRA_SCAN_CODE_TYPE);\n                if (formats != null) {\n                    decodeFormats = formats.get(BARCODE_FORMAT);\n                } else {\n                    decodeFormats = EnumSet.of(BarcodeFormat.QR_CODE\n                            , BarcodeFormat.CODE_128);\n                }\n            } else {\n                decodeFormats = EnumSet.of(BarcodeFormat.QR_CODE\n                        , BarcodeFormat.CODE_128);\n            }\n\n        }\n        Log.e(TAG, \"onCreate:decodeFormats :\" + decodeFormats.size() + \"--\" + decodeFormats.toString());\n        mInactivityTimer = new InactivityTimer(this);\n        beepManager = new BeepManager(this);\n        mHandler = new MyHandler(this);\n    }\n\n    @Override\n    protected void onResume() {\n        super.onResume();\n        cameraManager = new CameraManager(this);\n        cameraManager.setManualFramingRect(mScanFocusWidth, mScanFocusHeight, mScanFocusTopPadding);\n        mScannerView.setCameraManager(cameraManager);\n        SurfaceHolder holder = mSurfaceView.getHolder();\n\n        if (hasSurface) {\n            initCamera(holder);\n        } else {\n            holder.addCallback(this);\n        }\n        mInactivityTimer.onResume();\n        beepManager.updatePrefs();\n    }\n\n    @Override\n    protected void onPause() {\n        super.onPause();\n        if (handler != null) {\n            handler.quitSynchronously();\n            handler = null;\n        }\n        cameraManager.closeDriver();\n        mInactivityTimer.onPause();\n        beepManager.close();\n    }\n\n    @Override\n    protected void onDestroy() {\n        cameraManager.clearFramingRect();\n        mInactivityTimer.shutdown();\n        super.onDestroy();\n    }\n\n    @Override\n    public boolean onKeyDown(int keyCode, KeyEvent event) {\n        switch (keyCode) {\n            case KeyEvent.KEYCODE_VOLUME_DOWN:\n                //关闭灯光\n                cameraManager.setTorch(false);\n                return true;\n            case KeyEvent.KEYCODE_VOLUME_UP:\n                //开启闪光灯\n                cameraManager.setTorch(true);\n                return true;\n        }\n        return super.onKeyDown(keyCode, event);\n    }\n\n    @Override\n    public boolean onCreateOptionsMenu(Menu menu) {\n        if (isEnableScanFromPicture) {\n            getMenuInflater().inflate(R.menu.menu_scan, menu);\n            return true;\n        } else {\n            return super.onCreateOptionsMenu(menu);\n        }\n    }\n\n    @Override\n    public boolean onOptionsItemSelected(MenuItem item) {\n        int itemId = item.getItemId();\n        if (itemId == R.id.scan_from_picture) {\n            //先申请权限\n            int checked = ContextCompat.checkSelfPermission(ScannerActivity.this\n                    , Manifest.permission.WRITE_EXTERNAL_STORAGE);\n            if (checked == PackageManager.PERMISSION_GRANTED) {\n                goPicture();\n            } else {\n                ActivityCompat.requestPermissions(ScannerActivity.this\n                        , new String[]{Manifest.permission.WRITE_EXTERNAL_STORAGE}, PERMISSION_REQUEST_CODE_WRITE_EXTERNAL_STORAGE);\n            }\n        } else if (itemId == R.id.encode_barcode) {\n            startActivity(new Intent(ScannerActivity.this, BarcodeActivity.class));\n        }\n        return true;\n    }\n\n    private void goPicture() {\n        Intent intent = new Intent(Intent.ACTION_GET_CONTENT);\n        intent.setType(\"image/*\");\n        startActivityForResult(intent, REQUEST_CODE_GET_PIC_URI);\n    }\n\n    private void initView() {\n        mToolBar = (Toolbar) findViewById(R.id.tool_bar);\n        mToolBar.setTitle(\"二维码/条形码\");\n        mToolBar.setTitleTextColor(Color.WHITE);\n        setSupportActionBar(mToolBar);\n        mToolBar.setNavigationOnClickListener(new View.OnClickListener() {\n            @Override\n            public void onClick(View v) {\n                finish();\n            }\n        });\n        mSurfaceView = (SurfaceView) findViewById(R.id.surface);\n        mScannerView = (ScannerView) findViewById(R.id.scan_view);\n    }\n\n\n    private void initCamera(SurfaceHolder surfaceHolder) {\n        if (surfaceHolder == null) {\n            throw new IllegalStateException(\"No SurfaceHolder provided\");\n        }\n        if (cameraManager.isOpen()) {\n            Log.w(TAG, \"initCamera() while already open -- late SurfaceView callback?\");\n            return;\n        }\n        try {\n            cameraManager.openDriver(surfaceHolder);\n            if (handler == null) {\n                handler = new ScannerHandler(this, decodeFormats, \"utf-8\", cameraManager);\n            }\n        } catch (IOException ioe) {\n            Log.w(TAG, ioe);\n        } catch (RuntimeException e) {\n            Log.w(TAG, \"Unexpected error initializing camera\", e);\n        }\n    }\n\n    @Override\n    public void surfaceCreated(SurfaceHolder holder) {\n        if (holder == null) {\n            Log.e(TAG, \"*** WARNING *** surfaceCreated() gave us a null surface!\");\n        }\n        if (!hasSurface) {\n            hasSurface = true;\n            initCamera(holder);\n        }\n    }\n\n    @Override\n    public void surfaceChanged(SurfaceHolder holder, int format, int width, int height) {\n    }\n\n    @Override\n    public void surfaceDestroyed(SurfaceHolder holder) {\n        hasSurface = false;\n    }\n\n    //在这里处理扫码结果\n    public void handDecode(final Result result) {\n        mInactivityTimer.onActivity();\n        beepManager.playBeepSoundAndVibrate();\n//        AlertDialog.Builder mScannerDialogBuilder = new AlertDialog.Builder(this);\n//        mScannerDialogBuilder.setMessage(\"codeType:\" + result.getBarcodeFormat() + \"-----content:\" + result.getText());\n//        mScannerDialogBuilder.setCancelable(false);\n//        mScannerDialogBuilder.setPositiveButton(\"确定\", new DialogInterface.OnClickListener() {\n//            @Override\n//            public void onClick(DialogInterface dialog, int which) {\n//                dialog.dismiss();\n//                ScannerActivity.this.finish();\n//            }\n//        });\n//        mScannerDialogBuilder.create().show();\n        Intent data = new Intent();\n        BarcodeFormat format = result.getBarcodeFormat();\n        String type = format.toString();\n        data.putExtra(Constant.EXTRA_RESULT_CODE_TYPE, type);\n        data.putExtra(Constant.EXTRA_RESULT_CONTENT, result.getText());\n        setResult(RESULT_OK, data);\n        finish();\n    }\n\n    public CameraManager getCameraManager() {\n        return cameraManager;\n    }\n\n    public Handler getHandler() {\n        return handler;\n    }\n\n    @Override\n    protected void onActivityResult(int requestCode, int resultCode, Intent data) {\n        super.onActivityResult(requestCode, resultCode, data);\n        if (resultCode == RESULT_OK) {\n            switch (requestCode) {\n                case REQUEST_CODE_GET_PIC_URI:\n                    Uri uri = data.getData();\n                    String imagePath = UriUtils.getPicturePathFromUri(ScannerActivity.this, uri);\n                    //对获取到的二维码照片进行压缩\n                    Bitmap bitmap = CommonUtils.compressPicture(imagePath);\n                    Message message = mHandler.obtainMessage(MESSAGE_DECODE_FROM_BITMAP, bitmap);\n                    mHandler.sendMessage(message);\n                    Log.e(TAG, \"onActivityResult: uri:\" + uri.toString());\n                    break;\n            }\n        }\n    }\n\n    @Override\n    public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults) {\n        super.onRequestPermissionsResult(requestCode, permissions, grantResults);\n        if (requestCode == PERMISSION_REQUEST_CODE_WRITE_EXTERNAL_STORAGE) {\n            if (grantResults.length > 0 && grantResults[0] == PackageManager.PERMISSION_GRANTED) {\n                goPicture();\n                return;\n            }\n        }\n    }\n\n\n}\n"
  },
  {
    "path": "YZxing-lib/src/main/java/com/example/qrcode/ShowResultActivity.java",
    "content": "package com.example.qrcode;\n\nimport android.content.Intent;\nimport android.graphics.Bitmap;\nimport android.os.Bundle;\nimport android.support.annotation.Nullable;\nimport android.support.v7.app.AppCompatActivity;\nimport android.util.Log;\nimport android.util.Patterns;\nimport android.view.View;\nimport android.webkit.WebChromeClient;\nimport android.webkit.WebSettings;\nimport android.webkit.WebView;\nimport android.webkit.WebViewClient;\nimport android.widget.ProgressBar;\nimport android.widget.TextView;\n\n/**\n * Created by yangyu on 2017/11/28.\n */\n\npublic class ShowResultActivity extends AppCompatActivity {\n    private static final String TAG = \"ShowResultActivity\";\n\n    private WebView webView;\n    private TextView tv;\n    private ProgressBar pb;\n\n    private String resultText;\n\n    @Override\n    protected void onCreate(@Nullable Bundle savedInstanceState) {\n        super.onCreate(savedInstanceState);\n        setContentView(R.layout.layout_activity_show_result);\n        webView = (WebView) findViewById(R.id.web_content);\n        tv = (TextView) findViewById(R.id.tv);\n        pb = (ProgressBar) findViewById(R.id.progress);\n\n        WebSettings webSettings = webView.getSettings();\n        webSettings.setJavaScriptEnabled(true);\n        webSettings.setUseWideViewPort(true);\n        webSettings.setLoadWithOverviewMode(true);\n        webView.setWebChromeClient(webChromeClient);\n        webView.setWebViewClient(webViewClient);\n\n        Intent intent = getIntent();\n        if (intent != null) {\n            resultText = intent.getStringExtra(Constant.EXTRA_RESULT_TEXT_FROM_PIC);\n            if (Patterns.WEB_URL.matcher(resultText).matches()) {\n                //是一个web url\n                tv.setVisibility(View.GONE);\n                webView.setVisibility(View.VISIBLE);\n                webView.loadUrl(resultText);\n            } else {\n                //不是web url\n                tv.setVisibility(View.VISIBLE);\n                webView.setVisibility(View.GONE);\n                pb.setVisibility(View.GONE);\n                tv.setText(resultText);\n            }\n        }\n    }\n\n    private WebViewClient webViewClient = new WebViewClient() {\n        @Override\n        public boolean shouldOverrideUrlLoading(WebView view, String url) {\n            view.loadUrl(url);\n            return true;\n        }\n\n        @Override\n        public void onPageStarted(WebView view, String url, Bitmap favicon) {\n            super.onPageStarted(view, url, favicon);\n        }\n\n        @Override\n        public void onPageFinished(WebView view, String url) {\n            super.onPageFinished(view, url);\n        }\n    };\n\n    private WebChromeClient webChromeClient = new WebChromeClient() {\n        @Override\n        public void onProgressChanged(WebView view, int newProgress) {\n            super.onProgressChanged(view, newProgress);\n            if (newProgress == 100) {\n                pb.setVisibility(View.GONE);\n            } else {\n                pb.setVisibility(View.VISIBLE);\n                pb.setProgress(newProgress);\n            }\n        }\n\n        @Override\n        public void onReceivedTitle(WebView view, String title) {\n            super.onReceivedTitle(view, title);\n            Log.e(TAG, \"onReceivedTitle: \" + title);\n        }\n    };\n}\n\n"
  },
  {
    "path": "YZxing-lib/src/main/java/com/example/qrcode/callback/PreviewCallback.java",
    "content": "package com.example.qrcode.callback;\n\nimport android.graphics.Point;\nimport android.hardware.Camera;\nimport android.os.Handler;\nimport android.os.Message;\nimport android.util.Log;\n\nimport com.example.qrcode.camera.CameraConfigurationManager;\n\n/**\n * Created by yangyu on 17/10/19.\n */\n\npublic class PreviewCallback implements Camera.PreviewCallback {\n\n    private static final String TAG = PreviewCallback.class.getSimpleName();\n\n    private final CameraConfigurationManager configManager;\n    private Handler previewHandler;\n    private int previewMessage;\n\n    public PreviewCallback(CameraConfigurationManager configManager) {\n        this.configManager = configManager;\n    }\n\n    public void setHandler(Handler previewHandler, int previewMessage) {\n        this.previewHandler = previewHandler;\n        this.previewMessage = previewMessage;\n    }\n\n    @Override\n    public void onPreviewFrame(byte[] data, Camera camera) {\n        Point cameraResolution = configManager.getCameraResolution();\n        Handler thePreviewHandler = previewHandler;\n        if (cameraResolution != null && thePreviewHandler != null) {\n            Message message = thePreviewHandler.obtainMessage(previewMessage, cameraResolution.x,\n                    cameraResolution.y, data);\n            message.sendToTarget();\n            previewHandler = null;\n        } else {\n            Log.d(TAG, \"Got preview callback, but no handler or resolution available\");\n        }\n    }\n\n}"
  },
  {
    "path": "YZxing-lib/src/main/java/com/example/qrcode/camera/AutoFocusManager.java",
    "content": "package com.example.qrcode.camera;\n\nimport android.content.Context;\nimport android.content.SharedPreferences;\nimport android.hardware.Camera;\nimport android.os.AsyncTask;\nimport android.preference.PreferenceManager;\nimport android.util.Log;\n\nimport com.example.qrcode.Constant;\n\nimport java.util.ArrayList;\nimport java.util.Collection;\nimport java.util.concurrent.RejectedExecutionException;\n\n/**\n * Created by yangyu on 17/10/19.\n */\n\nfinal class AutoFocusManager implements Camera.AutoFocusCallback {\n\n    private static final String TAG = AutoFocusManager.class.getSimpleName();\n\n    private static final long AUTO_FOCUS_INTERVAL_MS = 2000L;\n    private static final Collection<String> FOCUS_MODES_CALLING_AF;\n\n    static {\n        FOCUS_MODES_CALLING_AF = new ArrayList<>(2);\n        FOCUS_MODES_CALLING_AF.add(Camera.Parameters.FOCUS_MODE_AUTO);\n        FOCUS_MODES_CALLING_AF.add(Camera.Parameters.FOCUS_MODE_MACRO);\n    }\n\n    private boolean stopped;\n    private boolean focusing;\n    private final boolean useAutoFocus;\n    private final Camera camera;\n    private AsyncTask<?, ?, ?> outstandingTask;\n\n    AutoFocusManager(Context context, Camera camera) {\n        this.camera = camera;\n        SharedPreferences sharedPrefs = PreferenceManager.getDefaultSharedPreferences(context);\n        String currentFocusMode = camera.getParameters().getFocusMode();\n        useAutoFocus =\n                sharedPrefs.getBoolean(Constant.KEY_AUTO_FOCUS, true) &&\n                        FOCUS_MODES_CALLING_AF.contains(currentFocusMode);\n        Log.i(TAG, \"Current focus mode '\" + currentFocusMode + \"'; use auto focus? \" + useAutoFocus);\n        start();\n    }\n\n    @Override\n    public synchronized void onAutoFocus(boolean success, Camera theCamera) {\n        focusing = false;\n        autoFocusAgainLater();\n    }\n\n    private synchronized void autoFocusAgainLater() {\n        if (!stopped && outstandingTask == null) {\n            AutoFocusTask newTask = new AutoFocusTask();\n            try {\n                newTask.executeOnExecutor(AsyncTask.THREAD_POOL_EXECUTOR);\n                outstandingTask = newTask;\n            } catch (RejectedExecutionException ree) {\n                Log.w(TAG, \"Could not request auto focus\", ree);\n            }\n        }\n    }\n\n    synchronized void start() {\n        if (useAutoFocus) {\n            outstandingTask = null;\n            if (!stopped && !focusing) {\n                try {\n                    camera.autoFocus(this);\n                    focusing = true;\n                } catch (RuntimeException re) {\n                    // Have heard RuntimeException reported in Android 4.0.x+; continue?\n                    Log.w(TAG, \"Unexpected exception while focusing\", re);\n                    // Try again later to keep cycle going\n                    autoFocusAgainLater();\n                }\n            }\n        }\n    }\n\n    private synchronized void cancelOutstandingTask() {\n        if (outstandingTask != null) {\n            if (outstandingTask.getStatus() != AsyncTask.Status.FINISHED) {\n                outstandingTask.cancel(true);\n            }\n            outstandingTask = null;\n        }\n    }\n\n    synchronized void stop() {\n        stopped = true;\n        if (useAutoFocus) {\n            cancelOutstandingTask();\n            // Doesn't hurt to call this even if not focusing\n            try {\n                camera.cancelAutoFocus();\n            } catch (RuntimeException re) {\n                // Have heard RuntimeException reported in Android 4.0.x+; continue?\n                Log.w(TAG, \"Unexpected exception while cancelling focusing\", re);\n            }\n        }\n    }\n\n    private final class AutoFocusTask extends AsyncTask<Object, Object, Object> {\n        @Override\n        protected Object doInBackground(Object... voids) {\n            try {\n                Thread.sleep(AUTO_FOCUS_INTERVAL_MS);\n            } catch (InterruptedException e) {\n                // continue\n            }\n            start();\n            return null;\n        }\n    }\n\n}\n"
  },
  {
    "path": "YZxing-lib/src/main/java/com/example/qrcode/camera/CameraConfigurationManager.java",
    "content": "package com.example.qrcode.camera;\n\n/**\n * Created by yangyu on 17/10/18.\n */\n\nimport android.content.Context;\nimport android.content.SharedPreferences;\nimport android.graphics.Point;\nimport android.hardware.Camera;\nimport android.preference.PreferenceManager;\nimport android.util.Log;\nimport android.view.Display;\nimport android.view.WindowManager;\n\nimport com.example.qrcode.Constant;\nimport com.example.qrcode.utils.CameraConfigurationUtils;\n\n/**\n * A class which deals with reading, parsing, and setting the camera parameters which are used to\n * configure the camera hardware.\n */\n@SuppressWarnings(\"deprecation\") // camera APIs\npublic final class CameraConfigurationManager {\n\n    private static final String TAG = \"CameraConfiguration\";\n\n    private final Context context;\n    private Point screenResolution;\n    private Point cameraResolution;\n    private Point bestPreviewSize;\n\n    CameraConfigurationManager(Context context) {\n        this.context = context;\n    }\n\n    /**\n     * Reads, one time, values from the camera that are needed by the app.\n     */\n    void initFromCameraParameters(OpenCamera camera) {\n        Camera.Parameters parameters = camera.getCamera().getParameters();\n        WindowManager manager = (WindowManager) context.getSystemService(Context.WINDOW_SERVICE);\n        Display display = manager.getDefaultDisplay();\n        Point theScreenResolution = new Point();\n        display.getSize(theScreenResolution);\n        screenResolution = theScreenResolution;\n        Log.i(TAG, \"Screen resolution in current orientation: \" + screenResolution);\n        cameraResolution = CameraConfigurationUtils.findBestPreviewSizeValue(parameters, screenResolution);\n        Log.i(TAG, \"Camera resolution: \" + cameraResolution);\n        bestPreviewSize = CameraConfigurationUtils.findBestPreviewSizeValue(parameters, screenResolution);\n        Log.i(TAG, \"Best available preview size: \" + bestPreviewSize);\n    }\n\n    void setDesiredCameraParameters(OpenCamera camera, boolean safeMode) {\n\n        Camera theCamera = camera.getCamera();\n        Camera.Parameters parameters = theCamera.getParameters();\n\n        if (parameters == null) {\n            Log.w(TAG, \"Device error: no camera parameters are available. Proceeding without configuration.\");\n            return;\n        }\n\n        Log.i(TAG, \"Initial camera parameters: \" + parameters.flatten());\n\n        if (safeMode) {\n            Log.w(TAG, \"In camera config safe mode -- most settings will not be honored\");\n        }\n\n        SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(context);\n        CameraConfigurationUtils.setFocus(\n                parameters,\n                prefs.getBoolean(Constant.KEY_AUTO_FOCUS, true),\n                prefs.getBoolean(Constant.KEY_DISABLE_CONTINUOUS_FOCUS, true),\n                safeMode);\n\n        parameters.setPreviewSize(bestPreviewSize.x, bestPreviewSize.y);\n\n        theCamera.setParameters(parameters);\n        //设置屏幕方向为垂直方向\n        theCamera.setDisplayOrientation(90);\n    }\n\n    public Point getCameraResolution() {\n        return cameraResolution;\n    }\n\n    Point getScreenResolution() {\n        return screenResolution;\n    }\n\n    boolean getTorchState(Camera camera) {\n        if (camera != null) {\n            Camera.Parameters parameters = camera.getParameters();\n            if (parameters != null) {\n                String flashMode = parameters.getFlashMode();\n                return flashMode != null &&\n                        (Camera.Parameters.FLASH_MODE_ON.equals(flashMode) ||\n                                Camera.Parameters.FLASH_MODE_TORCH.equals(flashMode));\n            }\n        }\n        return false;\n    }\n\n    void setTorch(Camera camera, boolean newSetting) {\n        Camera.Parameters parameters = camera.getParameters();\n        doSetTorch(parameters, newSetting, false);\n        camera.setParameters(parameters);\n    }\n\n    private void doSetTorch(Camera.Parameters parameters, boolean newSetting, boolean safeMode) {\n        CameraConfigurationUtils.setTorch(parameters, newSetting);\n    }\n\n}\n"
  },
  {
    "path": "YZxing-lib/src/main/java/com/example/qrcode/camera/CameraFacing.java",
    "content": "package com.example.qrcode.camera;\n\n/**\n * Created by yangyu on 17/10/18.\n */\n\nenum CameraFacing {\n\n    BACK,  // must be value 0!\n    FRONT, // must be value 1!\n\n}\n\n"
  },
  {
    "path": "YZxing-lib/src/main/java/com/example/qrcode/camera/CameraManager.java",
    "content": "package com.example.qrcode.camera;\n\n/**\n * Created by yangyu on 17/10/18.\n */\n\nimport android.content.Context;\nimport android.graphics.Point;\nimport android.graphics.Rect;\nimport android.hardware.Camera;\nimport android.os.Handler;\nimport android.util.Log;\nimport android.view.SurfaceHolder;\n\nimport com.example.qrcode.callback.PreviewCallback;\nimport com.google.zxing.PlanarYUVLuminanceSource;\n\nimport java.io.IOException;\n\n/**\n * This object wraps the Camera service object and expects to be the only one talking to it. The\n * implementation encapsulates the steps needed to take preview-sized images, which are used for\n * both preview and decoding.\n *\n * @author dswitkin@google.com (Daniel Switkin)\n */\n@SuppressWarnings(\"deprecation\") // camera APIs\npublic final class CameraManager {\n\n    private static final String TAG = CameraManager.class.getSimpleName();\n\n    private static final int MIN_FRAME_WIDTH = 240;\n    private static final int MIN_FRAME_HEIGHT = 240;\n    private static final int MAX_FRAME_WIDTH = 1200; // = 5/8 * 1920\n    private static final int MAX_FRAME_HEIGHT = 675; // = 5/8 * 1080\n    private static final int DEFAULT_TOP_PADDINF = 200;\n\n    private final Context context;\n    private final CameraConfigurationManager configManager;\n    private OpenCamera camera;\n    private AutoFocusManager autoFocusManager;\n    private Rect framingRect;\n    private boolean initialized;\n    private boolean previewing;\n    private int requestedCameraId = OpenCameraInterface.NO_REQUESTED_CAMERA;\n    private int requestedFramingRectWidth;\n    private int requestedFramingRectHeight;\n    private int requestedFramingRectTopPadding;\n    /**\n     * Preview frames are delivered here, which we pass on to the registered handler. Make sure to\n     * clear the handler so it will only receive one message.\n     */\n    private final PreviewCallback previewCallback;\n\n    public CameraManager(Context context) {\n        this.context = context;\n        this.configManager = new CameraConfigurationManager(context);\n        previewCallback = new PreviewCallback(configManager);\n    }\n\n    /**\n     * Opens the camera driver and initializes the hardware parameters.\n     *\n     * @param holder The surface object which the camera will draw preview frames into.\n     * @throws IOException Indicates the camera driver failed to open.\n     */\n    public synchronized void openDriver(SurfaceHolder holder) throws IOException {\n        OpenCamera theCamera = camera;\n        if (theCamera == null) {\n            theCamera = OpenCameraInterface.open(requestedCameraId);\n            if (theCamera == null) {\n                throw new IOException(\"Camera.open() failed to return object from driver\");\n            }\n            camera = theCamera;\n        }\n\n        if (!initialized) {\n            initialized = true;\n            configManager.initFromCameraParameters(theCamera);\n            if (requestedFramingRectWidth > 0 && requestedFramingRectHeight > 0) {\n                setManualFramingRect(requestedFramingRectWidth, requestedFramingRectHeight\n                        , requestedFramingRectTopPadding > 0 ? requestedFramingRectTopPadding : -1);\n                requestedFramingRectWidth = 0;\n                requestedFramingRectHeight = 0;\n            }\n        }\n\n        Camera cameraObject = theCamera.getCamera();\n        try {\n            configManager.setDesiredCameraParameters(theCamera, false);\n        } catch (RuntimeException re) {\n        }\n        cameraObject.setPreviewDisplay(holder);\n\n    }\n\n    public synchronized boolean isOpen() {\n        return camera != null;\n    }\n\n    /**\n     * Closes the camera driver if still in use.\n     */\n    public synchronized void closeDriver() {\n        if (camera != null) {\n            camera.getCamera().release();\n            camera = null;\n        }\n    }\n\n    public synchronized void clearFramingRect(){\n        // Make sure to clear these each time we close the camera, so that any scanning rect\n        // requested by intent is forgotten.\n        framingRect = null;\n    }\n\n    /**\n     * Asks the camera hardware to begin drawing preview frames to the screen.\n     */\n    public synchronized void startPreview() {\n        OpenCamera theCamera = camera;\n        if (theCamera != null && !previewing) {\n            theCamera.getCamera().startPreview();\n            previewing = true;\n            autoFocusManager = new AutoFocusManager(context, theCamera.getCamera());\n        }\n    }\n\n    /**\n     * Tells the camera to stop drawing preview frames.\n     */\n    public synchronized void stopPreview() {\n        if (autoFocusManager != null) {\n            autoFocusManager.stop();\n            autoFocusManager = null;\n        }\n        if (camera != null && previewing) {\n            camera.getCamera().stopPreview();\n            previewCallback.setHandler(null, 0);\n            previewing = false;\n        }\n    }\n\n    /**\n     * @param newSetting if {@code true}, light should be turned on if currently off. And vice versa.\n     */\n    public synchronized void setTorch(boolean newSetting) {\n        OpenCamera theCamera = camera;\n        if (theCamera != null && newSetting != configManager.getTorchState(theCamera.getCamera())) {\n            boolean wasAutoFocusManager = autoFocusManager != null;\n            if (wasAutoFocusManager) {\n                autoFocusManager.stop();\n                autoFocusManager = null;\n            }\n            configManager.setTorch(theCamera.getCamera(), newSetting);\n            if (wasAutoFocusManager) {\n                autoFocusManager = new AutoFocusManager(context, theCamera.getCamera());\n                autoFocusManager.start();\n            }\n        }\n    }\n\n    /**\n     * A single preview frame will be returned to the handler supplied. The data will arrive as byte[]\n     * in the message.obj field, with width and height encoded as message.arg1 and message.arg2,\n     * respectively.\n     *\n     * @param handler The handler to send the message to.\n     * @param message The what field of the message to be sent.\n     */\n    public synchronized void requestPreviewFrame(Handler handler, int message) {\n        OpenCamera theCamera = camera;\n        if (theCamera != null && previewing) {\n            previewCallback.setHandler(handler, message);\n            theCamera.getCamera().setOneShotPreviewCallback(previewCallback);\n        }\n    }\n\n    /**\n     * Calculates the framing rect which the UI should draw to show the user where to place the\n     * barcode. This target helps with alignment as well as forces the user to hold the device\n     * far enough away to ensure the image will be in focus.\n     *\n     * @return The rectangle to draw on screen in window coordinates.\n     */\n    public synchronized Rect getFramingRect() {\n        if (framingRect == null) {\n            if (camera == null) {\n                return null;\n            }\n            Point screenResolution = configManager.getScreenResolution();\n            if (screenResolution == null) {\n                // Called early, before init even finished\n                return null;\n            }\n\n            int width = findDesiredDimensionInRange(screenResolution.x, MIN_FRAME_WIDTH, MAX_FRAME_WIDTH);\n            int height = findDesiredDimensionInRange(screenResolution.y, MIN_FRAME_HEIGHT, MAX_FRAME_HEIGHT);\n\n            int leftOffset = (screenResolution.x - width) / 2;\n            int topOffset = DEFAULT_TOP_PADDINF;\n            framingRect = new Rect(leftOffset, topOffset, leftOffset + width, topOffset + height);\n            Log.d(TAG, \"Calculated framing rect: \" + framingRect);\n        }\n        return framingRect;\n    }\n\n    private static int findDesiredDimensionInRange(int resolution, int hardMin, int hardMax) {\n        int dim = 5 * resolution / 8; // Target 5/8 of each dimension\n        if (dim < hardMin) {\n            return hardMin;\n        }\n        if (dim > hardMax) {\n            return hardMax;\n        }\n        return dim;\n    }\n\n//    /**\n//     * Like {@link #getFramingRect} but coordinates are in terms of the preview frame,\n//     * not UI / screen.\n//     *\n//     * @return {@link Rect} expressing barcode scan area in terms of the preview size\n//     */\n//    public synchronized Rect getFramingRectInPreview() {\n//        if (framingRectInPreview == null) {\n//            Rect framingRect = getFramingRect();\n//            if (framingRect == null) {\n//                return null;\n//            }\n//            Rect rect = new Rect(framingRect);\n//            Point cameraResolution = configManager.getCameraResolution();\n//            Point screenResolution = configManager.getScreenResolution();\n//            if (cameraResolution == null || screenResolution == null) {\n//                // Called early, before init even finished\n//                return null;\n//            }\n//            rect.left = rect.left * cameraResolution.x / screenResolution.x;\n//            rect.right = rect.right * cameraResolution.x / screenResolution.x;\n//            rect.top = rect.top * cameraResolution.y / screenResolution.y;\n//            rect.bottom = rect.bottom * cameraResolution.y / screenResolution.y;\n//            framingRectInPreview = rect;\n//        }\n//        return framingRectInPreview;\n//    }\n\n\n    /**\n     * 设置camera ID\n     *\n     * @param cameraId camera ID of the camera to use. A negative value means \"no preference\".\n     */\n    public synchronized void setManualCameraId(int cameraId) {\n        requestedCameraId = cameraId;\n    }\n\n    /**\n     * 设置扫码框的大小\n     *\n     * @param width  The width in pixels to scan.\n     * @param height The height in pixels to scan.\n     */\n    public synchronized void setManualFramingRect(int width, int height, int topPadding) {\n        if (initialized) {\n            Point screenResolution = configManager.getScreenResolution();\n            if (width > screenResolution.x) {\n                width = screenResolution.x;\n            }\n            if (height > screenResolution.y) {\n                height = screenResolution.y;\n            }\n            int leftOffset = (screenResolution.x - width) / 2;\n            int topOffset = topPadding < 0 ? DEFAULT_TOP_PADDINF : topPadding;\n            framingRect = new Rect(leftOffset, topOffset, leftOffset + width, topOffset + height);\n        } else {\n            requestedFramingRectWidth = width;\n            requestedFramingRectHeight = height;\n            requestedFramingRectTopPadding = topPadding;\n        }\n    }\n\n    /**\n     * A factory method to build the appropriate LuminanceSource object based on the format\n     * of the preview buffers, as described by Camera.Parameters.\n     *\n     * @param data   A preview frame.\n     * @param width  The width of the image.\n     * @param height The height of the image.\n     * @return A PlanarYUVLuminanceSource instance.\n     */\n    public PlanarYUVLuminanceSource buildLuminanceSource(byte[] data, int width, int height) {\n        return new PlanarYUVLuminanceSource(data, width, height, 0, 0,\n                width, height, false);\n    }\n\n}\n"
  },
  {
    "path": "YZxing-lib/src/main/java/com/example/qrcode/camera/OpenCamera.java",
    "content": "package com.example.qrcode.camera;\n\nimport android.hardware.Camera;\n\n/**\n * Created by yangyu on 17/10/18.\n */\n\npublic final class OpenCamera {\n\n    private final int index;\n    private final Camera camera;\n    private final CameraFacing facing;\n    private final int orientation;\n\n    public OpenCamera(int index, Camera camera, CameraFacing facing, int orientation) {\n        this.index = index;\n        this.camera = camera;\n        this.facing = facing;\n        this.orientation = orientation;\n    }\n\n    public Camera getCamera() {\n        return camera;\n    }\n\n    public CameraFacing getFacing() {\n        return facing;\n    }\n\n    public int getOrientation() {\n        return orientation;\n    }\n\n    @Override\n    public String toString() {\n        return \"Camera #\" + index + \" : \" + facing + ',' + orientation;\n    }\n\n}\n"
  },
  {
    "path": "YZxing-lib/src/main/java/com/example/qrcode/camera/OpenCameraInterface.java",
    "content": "package com.example.qrcode.camera;\n\n/**\n * Created by yangyu on 17/10/18.\n */\n\nimport android.hardware.Camera;\nimport android.util.Log;\n\n/**\n * Abstraction over the {@link Camera} API that helps open them and return their metadata.\n */\n@SuppressWarnings(\"deprecation\") // camera APIs\npublic final class OpenCameraInterface {\n\n    private static final String TAG = OpenCameraInterface.class.getName();\n\n    /** For {@link #open(int)}, means no preference for which camera to open. */\n    public static final int NO_REQUESTED_CAMERA = -1;\n\n    private OpenCameraInterface() {\n    }\n\n    /**\n     * Opens the requested camera with {@link Camera#open(int)}, if one exists.\n     *\n     * @param cameraId camera ID of the camera to use. A negative value\n     *  or {@link #NO_REQUESTED_CAMERA} means \"no preference\", in which case a rear-facing\n     *  camera is returned if possible or else any camera\n     * @return handle to {@link OpenCamera} that was opened\n     */\n    public static OpenCamera open(int cameraId) {\n\n        int numCameras = Camera.getNumberOfCameras();\n        if (numCameras == 0) {\n            Log.w(TAG, \"No cameras!\");\n            return null;\n        }\n\n        boolean explicitRequest = cameraId >= 0;\n\n        Camera.CameraInfo selectedCameraInfo = null;\n        int index;\n        if (explicitRequest) {\n            index = cameraId;\n            selectedCameraInfo = new Camera.CameraInfo();\n            Camera.getCameraInfo(index, selectedCameraInfo);\n        } else {\n            index = 0;\n            while (index < numCameras) {\n                Camera.CameraInfo cameraInfo = new Camera.CameraInfo();\n                Camera.getCameraInfo(index, cameraInfo);\n                CameraFacing reportedFacing = CameraFacing.values()[cameraInfo.facing];\n                if (reportedFacing == CameraFacing.BACK) {\n                    selectedCameraInfo = cameraInfo;\n                    break;\n                }\n                index++;\n            }\n        }\n\n        Camera camera;\n        if (index < numCameras) {\n            Log.i(TAG, \"Opening camera #\" + index);\n            camera = Camera.open(index);\n        } else {\n            if (explicitRequest) {\n                Log.w(TAG, \"Requested camera does not exist: \" + cameraId);\n                camera = null;\n            } else {\n                Log.i(TAG, \"No camera facing \" + CameraFacing.BACK + \"; returning camera #0\");\n                camera = Camera.open(0);\n                selectedCameraInfo = new Camera.CameraInfo();\n                Camera.getCameraInfo(0, selectedCameraInfo);\n            }\n        }\n\n        if (camera == null) {\n            return null;\n        }\n        return new OpenCamera(index,\n                camera,\n                CameraFacing.values()[selectedCameraInfo.facing],\n                selectedCameraInfo.orientation);\n    }\n\n}\n\n"
  },
  {
    "path": "YZxing-lib/src/main/java/com/example/qrcode/decode/DecodeHandler.java",
    "content": "package com.example.qrcode.decode;\n\nimport android.os.Bundle;\nimport android.os.Handler;\nimport android.os.Looper;\nimport android.os.Message;\nimport android.util.Log;\n\nimport com.example.qrcode.Constant;\nimport com.example.qrcode.ScannerActivity;\nimport com.google.zxing.BinaryBitmap;\nimport com.google.zxing.DecodeHintType;\nimport com.google.zxing.MultiFormatReader;\nimport com.google.zxing.PlanarYUVLuminanceSource;\nimport com.google.zxing.ReaderException;\nimport com.google.zxing.Result;\nimport com.google.zxing.common.HybridBinarizer;\n\nimport java.util.Arrays;\nimport java.util.Map;\n\n/**\n * Created by yangyu on 17/10/19.\n */\n\nfinal class DecodeHandler extends Handler {\n\n    private static final String TAG = DecodeHandler.class.getSimpleName();\n\n    private final ScannerActivity activity;\n    private final MultiFormatReader multiFormatReader;\n    private boolean running = true;\n    private byte[] mRotatedData;\n\n    DecodeHandler(ScannerActivity activity, Map<DecodeHintType, Object> hints) {\n        multiFormatReader = new MultiFormatReader();\n        multiFormatReader.setHints(hints);\n        this.activity = activity;\n    }\n\n    @Override\n    public void handleMessage(Message message) {\n        if (message == null || !running) {\n            return;\n        }\n        if (message.what == Constant.MESSAGE_SCANNER_DECODE) {\n            decode((byte[]) message.obj, message.arg1, message.arg2);\n\n        } else if (message.what == Constant.MESSAGE_SCANNER_QUIT) {\n            running = false;\n            Looper.myLooper().quit();\n\n        }\n    }\n\n    /**\n     * Decode the data within the viewfinder rectangle, and time how long it took. For efficiency,\n     * reuse the same reader objects from one decode to the next.\n     *\n     * @param data   The YUV preview frame.\n     * @param width  The width of the preview frame.\n     * @param height The height of the preview frame.\n     */\n    private void decode(byte[] data, int width, int height) {\n        //这里需要对扫码的数据进行宽高的调换，原来扫码的是横屏数据，需要转化成竖屏。\n        if (null == mRotatedData) {\n            mRotatedData = new byte[width * height];\n        } else {\n            if (mRotatedData.length < width * height) {\n                mRotatedData = new byte[width * height];\n            }\n        }\n        Arrays.fill(mRotatedData, (byte) 0);\n        for (int y = 0; y < height; y++) {\n            for (int x = 0; x < width; x++) {\n                if (x + y * width >= data.length) {\n                    break;\n                }\n                mRotatedData[x * height + height - y - 1] = data[x + y * width];\n            }\n        }\n        int tmp = width;\n        width = height;\n        height = tmp;\n        long start = System.currentTimeMillis();\n        Result rawResult = null;\n        PlanarYUVLuminanceSource source = activity.getCameraManager().buildLuminanceSource(mRotatedData, width, height);\n        if (source != null) {\n            BinaryBitmap bitmap = new BinaryBitmap(new HybridBinarizer(source));\n            try {\n                rawResult = multiFormatReader.decodeWithState(bitmap);\n            } catch (ReaderException re) {\n                // continue\n                Log.e(TAG, \"decode: re:\" + re.getMessage());\n            } finally {\n                multiFormatReader.reset();\n            }\n        }\n\n        Handler handler = activity.getHandler();\n        if (rawResult != null) {\n            // Don't log the barcode contents for security.\n            long end = System.currentTimeMillis();\n            Log.d(TAG, \"Found barcode in \" + (end - start) + \" ms\");\n            if (handler != null) {\n                Message message = Message.obtain(handler, Constant.MESSAGE_SCANNER_DECODE_SUCCEEDED, rawResult);\n                Bundle bundle = new Bundle();\n                message.setData(bundle);\n                message.sendToTarget();\n            }\n        } else {\n            if (handler != null) {\n                Message message = Message.obtain(handler, Constant.MESSAGE_SCANNER_DECODE_FAIL);\n                message.sendToTarget();\n            }\n        }\n    }\n}"
  },
  {
    "path": "YZxing-lib/src/main/java/com/example/qrcode/decode/DecodeThread.java",
    "content": "package com.example.qrcode.decode;\n\n/**\n * Created by yangyu on 17/10/18.\n */\n\nimport android.os.Handler;\nimport android.os.Looper;\n\nimport com.example.qrcode.ScannerActivity;\nimport com.google.zxing.BarcodeFormat;\nimport com.google.zxing.DecodeHintType;\n\nimport java.util.Collection;\nimport java.util.EnumMap;\nimport java.util.Map;\nimport java.util.concurrent.CountDownLatch;\n\n/**\n * This thread does all the heavy lifting of decoding the images.\n *\n * @author dswitkin@google.com (Daniel Switkin)\n */\nfinal class DecodeThread extends Thread {\n\n    private final ScannerActivity activity;\n    private final Map<DecodeHintType, Object> hints;\n    private Handler handler;\n    private final CountDownLatch handlerInitLatch;\n\n    DecodeThread(ScannerActivity activity,\n                 Collection<BarcodeFormat> decodeFormats,\n                 String characterSet\n    ) {\n        this.activity = activity;\n        handlerInitLatch = new CountDownLatch(1);\n        hints = new EnumMap<>(DecodeHintType.class);\n        hints.put(DecodeHintType.POSSIBLE_FORMATS, decodeFormats);\n        if (characterSet != null) {\n            hints.put(DecodeHintType.CHARACTER_SET, characterSet);\n        }\n        hints.put(DecodeHintType.TRY_HARDER, true);\n    }\n\n    Handler getHandler() {\n        try {\n            handlerInitLatch.await();\n        } catch (InterruptedException ie) {\n\n        }\n        return handler;\n    }\n\n    @Override\n    public void run() {\n        Looper.prepare();\n        handler = new DecodeHandler(activity, hints);\n        handlerInitLatch.countDown();\n        Looper.loop();\n    }\n\n}\n"
  },
  {
    "path": "YZxing-lib/src/main/java/com/example/qrcode/decode/InactivityTimer.java",
    "content": "package com.example.qrcode.decode;\n\nimport android.app.Activity;\nimport android.content.BroadcastReceiver;\nimport android.content.Context;\nimport android.content.Intent;\nimport android.content.IntentFilter;\nimport android.os.AsyncTask;\nimport android.os.BatteryManager;\nimport android.util.Log;\n\nimport java.util.concurrent.RejectedExecutionException;\n\n/**\n * Created by yangyu on 17/10/30.\n */\n\npublic final class InactivityTimer {\n    private static final String TAG = InactivityTimer.class.getSimpleName();\n\n    private static final long INACTIVITY_DELAY_MS = 5 * 60 * 1000L;\n\n    private final Activity activity;\n    private final BroadcastReceiver powerStatusReceiver;\n    private boolean registered;\n    private AsyncTask<Object, Object, Object> inactivityTask;\n\n    public InactivityTimer(Activity activity) {\n        this.activity = activity;\n        powerStatusReceiver = new PowerStatusReceiver();\n        registered = false;\n        onActivity();\n    }\n\n    public synchronized void onActivity() {\n        cancel();\n        inactivityTask = new InactivityAsyncTask();\n        try {\n            inactivityTask.executeOnExecutor(AsyncTask.THREAD_POOL_EXECUTOR);\n        } catch (RejectedExecutionException ree) {\n            Log.w(TAG, \"Couldn't schedule inactivity task; ignoring\");\n        }\n    }\n\n    public synchronized void onPause() {\n        cancel();\n        if (registered) {\n            activity.unregisterReceiver(powerStatusReceiver);\n            registered = false;\n        } else {\n            Log.w(TAG, \"PowerStatusReceiver was never registered?\");\n        }\n    }\n\n    public synchronized void onResume() {\n        if (registered) {\n            Log.w(TAG, \"PowerStatusReceiver was already registered?\");\n        } else {\n            activity.registerReceiver(powerStatusReceiver, new IntentFilter(Intent.ACTION_BATTERY_CHANGED));\n            registered = true;\n        }\n        onActivity();\n    }\n\n    private synchronized void cancel() {\n        AsyncTask<?, ?, ?> task = inactivityTask;\n        if (task != null) {\n            task.cancel(true);\n            inactivityTask = null;\n        }\n    }\n\n    public void shutdown() {\n        cancel();\n    }\n\n    private final class PowerStatusReceiver extends BroadcastReceiver {\n        @Override\n        public void onReceive(Context context, Intent intent) {\n            if (Intent.ACTION_BATTERY_CHANGED.equals(intent.getAction())) {\n                // 0 indicates that we're on battery\n                boolean onBatteryNow = intent.getIntExtra(BatteryManager.EXTRA_PLUGGED, -1) <= 0;\n                if (onBatteryNow) {\n                    InactivityTimer.this.onActivity();\n                } else {\n                    InactivityTimer.this.cancel();\n                }\n            }\n        }\n    }\n\n    private final class InactivityAsyncTask extends AsyncTask<Object, Object, Object> {\n        @Override\n        protected Object doInBackground(Object... objects) {\n            try {\n                Thread.sleep(INACTIVITY_DELAY_MS);\n                Log.i(TAG, \"Finishing activity due to inactivity\");\n                activity.finish();\n            } catch (InterruptedException e) {\n                // continue without killing\n            }\n            return null;\n        }\n    }\n}\n"
  },
  {
    "path": "YZxing-lib/src/main/java/com/example/qrcode/decode/ScannerHandler.java",
    "content": "package com.example.qrcode.decode;\n\nimport android.os.Handler;\nimport android.os.Message;\n\nimport com.example.qrcode.Constant;\nimport com.example.qrcode.ScannerActivity;\nimport com.example.qrcode.camera.CameraManager;\nimport com.google.zxing.BarcodeFormat;\nimport com.google.zxing.Result;\n\nimport java.util.Collection;\n\n/**\n * Created by yangyu on 17/10/18.\n */\n\n/**\n * This class handles all the messaging which comprises the state machine for capture.\n *\n * @author dswitkin@google.com (Daniel Switkin)\n */\npublic final class ScannerHandler extends Handler {\n\n    private static final String TAG = ScannerHandler.class.getSimpleName();\n\n    private final ScannerActivity activity;\n    private final DecodeThread decodeThread;\n    private State state;\n    private final CameraManager cameraManager;\n\n    private enum State {\n        PREVIEW,\n        SUCCESS,\n        DONE\n    }\n\n    public ScannerHandler(ScannerActivity activity,\n                          Collection<BarcodeFormat> decodeFormats,\n                          String characterSet,\n                          CameraManager cameraManager) {\n        this.activity = activity;\n        decodeThread = new DecodeThread(activity, decodeFormats, characterSet);\n        decodeThread.start();\n        state = State.SUCCESS;\n\n        // Start ourselves capturing previews and decoding.\n        this.cameraManager = cameraManager;\n        cameraManager.startPreview();\n        restartPreviewAndDecode();\n    }\n\n    @Override\n    public void handleMessage(Message message) {\n        if (message == null) return;\n        switch (message.what) {\n            case Constant.MESSAGE_SCANNER_DECODE_SUCCEEDED:\n                Result r = (Result) message.obj;\n                activity.handDecode(r);\n                break;\n            case Constant.MESSAGE_SCANNER_DECODE_FAIL:\n                state = State.PREVIEW;\n                cameraManager.requestPreviewFrame(decodeThread.getHandler(), Constant.MESSAGE_SCANNER_DECODE);\n                break;\n        }\n    }\n\n    public void quitSynchronously() {\n        state = State.DONE;\n        cameraManager.stopPreview();\n        Message quit = Message.obtain(decodeThread.getHandler(), Constant.MESSAGE_SCANNER_QUIT);\n        quit.sendToTarget();\n        try {\n            // Wait at most half a second; should be enough time, and onPause() will timeout quickly\n            decodeThread.join(500L);\n        } catch (InterruptedException e) {\n            // continue\n        }\n\n        // Be absolutely sure we don't send any queued up messages\n        removeMessages(Constant.MESSAGE_SCANNER_DECODE_SUCCEEDED);\n        removeMessages(Constant.MESSAGE_SCANNER_DECODE_FAIL);\n    }\n\n    private void restartPreviewAndDecode() {\n        if (state == State.SUCCESS) {\n            state = State.PREVIEW;\n            cameraManager.requestPreviewFrame(decodeThread.getHandler(), Constant.MESSAGE_SCANNER_DECODE);\n        }\n    }\n\n}\n"
  },
  {
    "path": "YZxing-lib/src/main/java/com/example/qrcode/utils/CameraConfigurationUtils.java",
    "content": "package com.example.qrcode.utils;\n\n/**\n * Created by yangyu on 17/10/18.\n */\n\nimport android.annotation.TargetApi;\nimport android.graphics.Point;\nimport android.graphics.Rect;\nimport android.hardware.Camera;\nimport android.os.Build;\nimport android.util.Log;\n\nimport java.util.ArrayList;\nimport java.util.Arrays;\nimport java.util.Collection;\nimport java.util.Collections;\nimport java.util.Comparator;\nimport java.util.Iterator;\nimport java.util.List;\nimport java.util.regex.Pattern;\n\n/**\n * Utility methods for configuring the Android camera.\n *\n * @author Sean Owen\n */\n@TargetApi(Build.VERSION_CODES.ICE_CREAM_SANDWICH_MR1)\npublic final class CameraConfigurationUtils {\n\n    private static final String TAG = \"CameraConfiguration\";\n\n    private static final Pattern SEMICOLON = Pattern.compile(\";\");\n\n    private static final int MIN_PREVIEW_PIXELS = 480 * 320; // normal screen\n    private static final float MAX_EXPOSURE_COMPENSATION = 1.5f;\n    private static final float MIN_EXPOSURE_COMPENSATION = 0.0f;\n    private static final double MAX_ASPECT_DISTORTION = 0.15;\n    private static final int MIN_FPS = 10;\n    private static final int MAX_FPS = 20;\n    private static final int AREA_PER_1000 = 400;\n\n    private CameraConfigurationUtils() {\n    }\n\n    public static void setFocus(Camera.Parameters parameters,\n                                boolean autoFocus,\n                                boolean disableContinuous,\n                                boolean safeMode) {\n        List<String> supportedFocusModes = parameters.getSupportedFocusModes();\n        String focusMode = null;\n        if (autoFocus) {\n            if (safeMode || disableContinuous) {\n                focusMode = findSettableValue(\"focus mode\",\n                        supportedFocusModes,\n                        Camera.Parameters.FOCUS_MODE_AUTO);\n            } else {\n                focusMode = findSettableValue(\"focus mode\",\n                        supportedFocusModes,\n                        Camera.Parameters.FOCUS_MODE_CONTINUOUS_PICTURE,\n                        Camera.Parameters.FOCUS_MODE_CONTINUOUS_VIDEO,\n                        Camera.Parameters.FOCUS_MODE_AUTO);\n            }\n        }\n        // Maybe selected auto-focus but not available, so fall through here:\n        if (!safeMode && focusMode == null) {\n            focusMode = findSettableValue(\"focus mode\",\n                    supportedFocusModes,\n                    Camera.Parameters.FOCUS_MODE_MACRO,\n                    Camera.Parameters.FOCUS_MODE_EDOF);\n        }\n        if (focusMode != null) {\n            if (focusMode.equals(parameters.getFocusMode())) {\n                Log.i(TAG, \"Focus mode already set to \" + focusMode);\n            } else {\n                parameters.setFocusMode(focusMode);\n            }\n        }\n    }\n\n    public static void setTorch(Camera.Parameters parameters, boolean on) {\n        List<String> supportedFlashModes = parameters.getSupportedFlashModes();\n        String flashMode;\n        if (on) {\n            flashMode = findSettableValue(\"flash mode\",\n                    supportedFlashModes,\n                    Camera.Parameters.FLASH_MODE_TORCH,\n                    Camera.Parameters.FLASH_MODE_ON);\n        } else {\n            flashMode = findSettableValue(\"flash mode\",\n                    supportedFlashModes,\n                    Camera.Parameters.FLASH_MODE_OFF);\n        }\n        if (flashMode != null) {\n            if (flashMode.equals(parameters.getFlashMode())) {\n                Log.i(TAG, \"Flash mode already set to \" + flashMode);\n            } else {\n                Log.i(TAG, \"Setting flash mode to \" + flashMode);\n                parameters.setFlashMode(flashMode);\n            }\n        }\n    }\n\n\n    public static void setFocusArea(Camera.Parameters parameters) {\n        if (parameters.getMaxNumFocusAreas() > 0) {\n            Log.i(TAG, \"Old focus areas: \" + toString(parameters.getFocusAreas()));\n            List<Camera.Area> middleArea = buildMiddleArea(AREA_PER_1000);\n            Log.i(TAG, \"Setting focus area to : \" + toString(middleArea));\n            parameters.setFocusAreas(middleArea);\n        } else {\n            Log.i(TAG, \"Device does not support focus areas\");\n        }\n    }\n\n    public static void setMetering(Camera.Parameters parameters) {\n        if (parameters.getMaxNumMeteringAreas() > 0) {\n            Log.i(TAG, \"Old metering areas: \" + parameters.getMeteringAreas());\n            List<Camera.Area> middleArea = buildMiddleArea(AREA_PER_1000);\n            Log.i(TAG, \"Setting metering area to : \" + toString(middleArea));\n            parameters.setMeteringAreas(middleArea);\n        } else {\n            Log.i(TAG, \"Device does not support metering areas\");\n        }\n    }\n\n    private static List<Camera.Area> buildMiddleArea(int areaPer1000) {\n        return Collections.singletonList(\n                new Camera.Area(new Rect(-areaPer1000, -areaPer1000, areaPer1000, areaPer1000), 1));\n    }\n\n    public static void setVideoStabilization(Camera.Parameters parameters) {\n        if (parameters.isVideoStabilizationSupported()) {\n            if (parameters.getVideoStabilization()) {\n                Log.i(TAG, \"Video stabilization already enabled\");\n            } else {\n                Log.i(TAG, \"Enabling video stabilization...\");\n                parameters.setVideoStabilization(true);\n            }\n        } else {\n            Log.i(TAG, \"This device does not support video stabilization\");\n        }\n    }\n\n    public static void setBarcodeSceneMode(Camera.Parameters parameters) {\n        if (Camera.Parameters.SCENE_MODE_BARCODE.equals(parameters.getSceneMode())) {\n            Log.i(TAG, \"Barcode scene mode already set\");\n            return;\n        }\n        String sceneMode = findSettableValue(\"scene mode\",\n                parameters.getSupportedSceneModes(),\n                Camera.Parameters.SCENE_MODE_BARCODE);\n        if (sceneMode != null) {\n            parameters.setSceneMode(sceneMode);\n        }\n    }\n\n    public static void setZoom(Camera.Parameters parameters, double targetZoomRatio) {\n        if (parameters.isZoomSupported()) {\n            Integer zoom = indexOfClosestZoom(parameters, targetZoomRatio);\n            if (zoom == null) {\n                return;\n            }\n            if (parameters.getZoom() == zoom) {\n                Log.i(TAG, \"Zoom is already set to \" + zoom);\n            } else {\n                Log.i(TAG, \"Setting zoom to \" + zoom);\n                parameters.setZoom(zoom);\n            }\n        } else {\n            Log.i(TAG, \"Zoom is not supported\");\n        }\n    }\n\n    private static Integer indexOfClosestZoom(Camera.Parameters parameters, double targetZoomRatio) {\n        List<Integer> ratios = parameters.getZoomRatios();\n        Log.i(TAG, \"Zoom ratios: \" + ratios);\n        int maxZoom = parameters.getMaxZoom();\n        if (ratios == null || ratios.isEmpty() || ratios.size() != maxZoom + 1) {\n            Log.w(TAG, \"Invalid zoom ratios!\");\n            return null;\n        }\n        double target100 = 100.0 * targetZoomRatio;\n        double smallestDiff = Double.POSITIVE_INFINITY;\n        int closestIndex = 0;\n        for (int i = 0; i < ratios.size(); i++) {\n            double diff = Math.abs(ratios.get(i) - target100);\n            if (diff < smallestDiff) {\n                smallestDiff = diff;\n                closestIndex = i;\n            }\n        }\n        Log.i(TAG, \"Chose zoom ratio of \" + (ratios.get(closestIndex) / 100.0));\n        return closestIndex;\n    }\n\n    public static void setInvertColor(Camera.Parameters parameters) {\n        if (Camera.Parameters.EFFECT_NEGATIVE.equals(parameters.getColorEffect())) {\n            Log.i(TAG, \"Negative effect already set\");\n            return;\n        }\n        String colorMode = findSettableValue(\"color effect\",\n                parameters.getSupportedColorEffects(),\n                Camera.Parameters.EFFECT_NEGATIVE);\n        if (colorMode != null) {\n            parameters.setColorEffect(colorMode);\n        }\n    }\n\n    public static Point findBestPreviewSizeValue(Camera.Parameters parameters, Point screenResolution) {\n\n        List<Camera.Size> rawSupportedSizes = parameters.getSupportedPreviewSizes();\n        if (rawSupportedSizes == null) {\n            Log.w(TAG, \"Device returned no supported preview sizes; using default\");\n            Camera.Size defaultSize = parameters.getPreviewSize();\n            if (defaultSize == null) {\n                throw new IllegalStateException(\"Parameters contained no preview size!\");\n            }\n            return new Point(defaultSize.width, defaultSize.height);\n        }\n\n        // Sort by size, descending\n        List<Camera.Size> supportedPreviewSizes = new ArrayList<>(rawSupportedSizes);\n        Collections.sort(supportedPreviewSizes, new Comparator<Camera.Size>() {\n            @Override\n            public int compare(Camera.Size a, Camera.Size b) {\n                int aPixels = a.height * a.width;\n                int bPixels = b.height * b.width;\n                if (bPixels < aPixels) {\n                    return -1;\n                }\n                if (bPixels > aPixels) {\n                    return 1;\n                }\n                return 0;\n            }\n        });\n\n        if (Log.isLoggable(TAG, Log.INFO)) {\n            StringBuilder previewSizesString = new StringBuilder();\n            for (Camera.Size supportedPreviewSize : supportedPreviewSizes) {\n                previewSizesString.append(supportedPreviewSize.width).append('x')\n                        .append(supportedPreviewSize.height).append(' ');\n            }\n            Log.i(TAG, \"Supported preview sizes: \" + previewSizesString);\n        }\n\n        double screenAspectRatio = screenResolution.x / (double) screenResolution.y;\n\n        // Remove sizes that are unsuitable\n        Iterator<Camera.Size> it = supportedPreviewSizes.iterator();\n        while (it.hasNext()) {\n            Camera.Size supportedPreviewSize = it.next();\n            int realWidth = supportedPreviewSize.width;\n            int realHeight = supportedPreviewSize.height;\n            if (realWidth * realHeight < MIN_PREVIEW_PIXELS) {\n                it.remove();\n                continue;\n            }\n\n            boolean isCandidatePortrait = realWidth < realHeight;\n            int maybeFlippedWidth = isCandidatePortrait ? realHeight : realWidth;\n            int maybeFlippedHeight = isCandidatePortrait ? realWidth : realHeight;\n            double aspectRatio = maybeFlippedWidth / (double) maybeFlippedHeight;\n            double distortion = Math.abs(aspectRatio - screenAspectRatio);\n            if (distortion > MAX_ASPECT_DISTORTION) {\n                it.remove();\n                continue;\n            }\n\n            if (maybeFlippedWidth == screenResolution.x && maybeFlippedHeight == screenResolution.y) {\n                Point exactPoint = new Point(realWidth, realHeight);\n                Log.i(TAG, \"Found preview size exactly matching screen size: \" + exactPoint);\n                return exactPoint;\n            }\n        }\n\n        // If no exact match, use largest preview size. This was not a great idea on older devices because\n        // of the additional computation needed. We're likely to get here on newer Android 4+ devices, where\n        // the CPU is much more powerful.\n        if (!supportedPreviewSizes.isEmpty()) {\n            Camera.Size largestPreview = supportedPreviewSizes.get(0);\n            Point largestSize = new Point(largestPreview.width, largestPreview.height);\n            Log.i(TAG, \"Using largest suitable preview size: \" + largestSize);\n            return largestSize;\n        }\n\n        // If there is nothing at all suitable, return current preview size\n        Camera.Size defaultPreview = parameters.getPreviewSize();\n        if (defaultPreview == null) {\n            throw new IllegalStateException(\"Parameters contained no preview size!\");\n        }\n        Point defaultSize = new Point(defaultPreview.width, defaultPreview.height);\n        Log.i(TAG, \"No suitable preview sizes, using default: \" + defaultSize);\n        return defaultSize;\n    }\n\n    private static String findSettableValue(String name,\n                                            Collection<String> supportedValues,\n                                            String... desiredValues) {\n        Log.i(TAG, \"Requesting \" + name + \" value from among: \" + Arrays.toString(desiredValues));\n        Log.i(TAG, \"Supported \" + name + \" values: \" + supportedValues);\n        if (supportedValues != null) {\n            for (String desiredValue : desiredValues) {\n                if (supportedValues.contains(desiredValue)) {\n                    Log.i(TAG, \"Can set \" + name + \" to: \" + desiredValue);\n                    return desiredValue;\n                }\n            }\n        }\n        Log.i(TAG, \"No supported values match\");\n        return null;\n    }\n\n    private static String toString(Collection<int[]> arrays) {\n        if (arrays == null || arrays.isEmpty()) {\n            return \"[]\";\n        }\n        StringBuilder buffer = new StringBuilder();\n        buffer.append('[');\n        Iterator<int[]> it = arrays.iterator();\n        while (it.hasNext()) {\n            buffer.append(Arrays.toString(it.next()));\n            if (it.hasNext()) {\n                buffer.append(\", \");\n            }\n        }\n        buffer.append(']');\n        return buffer.toString();\n    }\n\n    private static String toString(Iterable<Camera.Area> areas) {\n        if (areas == null) {\n            return null;\n        }\n        StringBuilder result = new StringBuilder();\n        for (Camera.Area area : areas) {\n            result.append(area.rect).append(':').append(area.weight).append(' ');\n        }\n        return result.toString();\n    }\n\n    public static String collectStats(Camera.Parameters parameters) {\n        return collectStats(parameters.flatten());\n    }\n\n    public static String collectStats(CharSequence flattenedParams) {\n        StringBuilder result = new StringBuilder(1000);\n\n        result.append(\"BOARD=\").append(Build.BOARD).append('\\n');\n        result.append(\"BRAND=\").append(Build.BRAND).append('\\n');\n        result.append(\"CPU_ABI=\").append(Build.CPU_ABI).append('\\n');\n        result.append(\"DEVICE=\").append(Build.DEVICE).append('\\n');\n        result.append(\"DISPLAY=\").append(Build.DISPLAY).append('\\n');\n        result.append(\"FINGERPRINT=\").append(Build.FINGERPRINT).append('\\n');\n        result.append(\"HOST=\").append(Build.HOST).append('\\n');\n        result.append(\"ID=\").append(Build.ID).append('\\n');\n        result.append(\"MANUFACTURER=\").append(Build.MANUFACTURER).append('\\n');\n        result.append(\"MODEL=\").append(Build.MODEL).append('\\n');\n        result.append(\"PRODUCT=\").append(Build.PRODUCT).append('\\n');\n        result.append(\"TAGS=\").append(Build.TAGS).append('\\n');\n        result.append(\"TIME=\").append(Build.TIME).append('\\n');\n        result.append(\"TYPE=\").append(Build.TYPE).append('\\n');\n        result.append(\"USER=\").append(Build.USER).append('\\n');\n        result.append(\"VERSION.CODENAME=\").append(Build.VERSION.CODENAME).append('\\n');\n        result.append(\"VERSION.INCREMENTAL=\").append(Build.VERSION.INCREMENTAL).append('\\n');\n        result.append(\"VERSION.RELEASE=\").append(Build.VERSION.RELEASE).append('\\n');\n        result.append(\"VERSION.SDK_INT=\").append(Build.VERSION.SDK_INT).append('\\n');\n\n        if (flattenedParams != null) {\n            String[] params = SEMICOLON.split(flattenedParams);\n            Arrays.sort(params);\n            for (String param : params) {\n                result.append(param).append('\\n');\n            }\n        }\n\n        return result.toString();\n    }\n\n}\n"
  },
  {
    "path": "YZxing-lib/src/main/java/com/example/qrcode/utils/CommonUtils.java",
    "content": "package com.example.qrcode.utils;\n\nimport android.graphics.Bitmap;\nimport android.graphics.BitmapFactory;\nimport android.util.Log;\n\n/**\n * Created by yangyu on 2017/11/28.\n */\n\npublic class CommonUtils {\n    private static final String TAG = \"CommonUtils\";\n\n    public static Bitmap compressPicture(String imgPath) {\n        BitmapFactory.Options options = new BitmapFactory.Options();\n        options.inJustDecodeBounds = true;\n        BitmapFactory.decodeFile(imgPath, options);\n        Log.e(TAG, \"onActivityResult: 未压缩之前图片的宽：\" + options.outWidth + \"--未压缩之前图片的高：\"\n                + options.outHeight + \"--未压缩之前图片大小:\" + options.outWidth * options.outHeight * 4 / 1024 / 1024 + \"M\");\n\n        options.inSampleSize = calculateInSampleSize(options, 100, 100);\n        Log.e(TAG, \"onActivityResult: inSampleSize:\" + options.inSampleSize);\n        options.inJustDecodeBounds = false;\n        Bitmap afterCompressBm = BitmapFactory.decodeFile(imgPath, options);\n//      //默认的图片格式是Bitmap.Config.ARGB_8888\n        Log.e(TAG, \"onActivityResult: 图片的宽：\" + afterCompressBm.getWidth() + \"--图片的高：\"\n                + afterCompressBm.getHeight() + \"--图片大小:\" + afterCompressBm.getWidth() * afterCompressBm.getHeight() * 4 / 1024 / 1024 + \"M\");\n        return afterCompressBm;\n    }\n\n    private static int calculateInSampleSize(BitmapFactory.Options options, int reqWidth, int reqHeight) {\n        final int height = options.outHeight;\n        final int width = options.outWidth;\n        int inSampleSize = 1;\n\n        if (height > reqHeight || width > reqWidth) {\n\n            final int halfHeight = height / 2;\n            final int halfWidth = width / 2;\n\n            while ((halfHeight / inSampleSize) >= reqHeight\n                    && (halfWidth / inSampleSize) >= reqWidth) {\n                inSampleSize *= 2;\n            }\n        }\n\n        return inSampleSize;\n    }\n}\n"
  },
  {
    "path": "YZxing-lib/src/main/java/com/example/qrcode/utils/DecodeUtils.java",
    "content": "package com.example.qrcode.utils;\n\nimport android.app.Activity;\nimport android.content.Context;\nimport android.content.Intent;\nimport android.graphics.Bitmap;\nimport android.os.AsyncTask;\nimport android.text.TextUtils;\nimport android.util.Log;\nimport android.widget.Toast;\n\nimport com.example.qrcode.Constant;\nimport com.example.qrcode.ShowResultActivity;\nimport com.google.zxing.BinaryBitmap;\nimport com.google.zxing.ChecksumException;\nimport com.google.zxing.DecodeHintType;\nimport com.google.zxing.FormatException;\nimport com.google.zxing.NotFoundException;\nimport com.google.zxing.RGBLuminanceSource;\nimport com.google.zxing.Result;\nimport com.google.zxing.common.HybridBinarizer;\nimport com.google.zxing.qrcode.QRCodeReader;\n\nimport java.lang.ref.WeakReference;\nimport java.util.EnumMap;\nimport java.util.Map;\n\n/**\n * Created by yangyu on 2017/11/27.\n */\n\npublic class DecodeUtils {\n    private static final String TAG = \"DecodeUtils\";\n\n    public static class DecodeAsyncTask extends AsyncTask<Bitmap, Integer, Result> {\n\n        private WeakReference<Context> mContext;\n        private Result result;\n\n        public DecodeAsyncTask(Context mContext) {\n            this.mContext = new WeakReference<Context>(mContext);\n        }\n\n        @Override\n        protected void onPreExecute() {\n            super.onPreExecute();\n        }\n\n        @Override\n        protected Result doInBackground(Bitmap... bitmaps) {\n            result = decodeFromPicture(bitmaps[0]);\n            return result;\n        }\n\n        @Override\n        protected void onPostExecute(Result result) {\n            super.onPostExecute(result);\n            if (result != null) {\n                String text = result.getText();\n                if (!TextUtils.isEmpty(text)) {\n                    Intent intent = new Intent(mContext.get(), ShowResultActivity.class);\n                    intent.putExtra(Constant.EXTRA_RESULT_TEXT_FROM_PIC, text);\n                    mContext.get().startActivity(intent);\n                    if (mContext.get() instanceof Activity) ((Activity) mContext.get()).finish();\n                }\n            } else {\n                Toast.makeText(mContext.get(), \"解码失败\", Toast.LENGTH_SHORT).show();\n            }\n\n        }\n    }\n\n\n    private static Result decodeFromPicture(Bitmap bitmap) {\n        if (bitmap == null) return null;\n        int picWidth = bitmap.getWidth();\n        int picHeight = bitmap.getHeight();\n        int[] pix = new int[picWidth * picHeight];\n        Log.e(TAG, \"decodeFromPicture:图片大小： \" + bitmap.getByteCount() / 1024 / 1024 + \"M\");\n        bitmap.getPixels(pix, 0, picWidth, 0, 0, picWidth, picHeight);\n        //构造LuminanceSource对象\n        RGBLuminanceSource rgbLuminanceSource = new RGBLuminanceSource(picWidth\n                , picHeight, pix);\n        BinaryBitmap bb = new BinaryBitmap(new HybridBinarizer(rgbLuminanceSource));\n        //因为解析的条码类型是二维码，所以这边用QRCodeReader最合适。\n        QRCodeReader qrCodeReader = new QRCodeReader();\n        Map<DecodeHintType, Object> hints = new EnumMap<>(DecodeHintType.class);\n        hints.put(DecodeHintType.CHARACTER_SET, \"utf-8\");\n        hints.put(DecodeHintType.TRY_HARDER, true);\n        Result result = null;\n        try {\n            result = qrCodeReader.decode(bb, hints);\n            return result;\n        } catch (NotFoundException | ChecksumException | FormatException e) {\n            e.printStackTrace();\n            return null;\n        }\n    }\n\n}\n\n\n"
  },
  {
    "path": "YZxing-lib/src/main/java/com/example/qrcode/utils/UriUtils.java",
    "content": "package com.example.qrcode.utils;\n\nimport android.content.ContentUris;\nimport android.content.Context;\nimport android.database.Cursor;\nimport android.net.Uri;\nimport android.os.Build;\nimport android.provider.DocumentsContract;\nimport android.provider.MediaStore;\n\n/**\n * Created by yangyu on 2017/11/27.\n */\n\npublic class UriUtils {\n    public static String getPicturePathFromUri(Context context, Uri uri) {\n        int sdkVersion = Build.VERSION.SDK_INT;\n        if (sdkVersion >= 19) {\n            return getPicturePathFromUriAboveApi19(context, uri);\n        } else {\n            return getPicturePathFromUriBelowAPI19(context, uri);\n        }\n    }\n\n    private static String getPicturePathFromUriBelowAPI19(Context context, Uri uri) {\n        return getDataColumn(context, uri, null, null);\n    }\n\n    private static String getPicturePathFromUriAboveApi19(Context context, Uri uri) {\n        String filePath = null;\n        if (DocumentsContract.isDocumentUri(context, uri)) {\n            // 如果是document类型的 uri, 则通过document id来进行处理\n            String documentId = DocumentsContract.getDocumentId(uri);\n            if (isMediaDocument(uri)) { // MediaProvider\n                // 使用':'分割\n                String id = documentId.split(\":\")[1];\n\n                String selection = MediaStore.Images.Media._ID + \"=?\";\n                String[] selectionArgs = {id};\n                filePath = getDataColumn(context, MediaStore.Images.Media.EXTERNAL_CONTENT_URI, selection, selectionArgs);\n            } else if (isDownloadsDocument(uri)) { // DownloadsProvider\n                Uri contentUri = ContentUris.withAppendedId(Uri.parse(\"content://downloads/public_downloads\"), Long.valueOf(documentId));\n                filePath = getDataColumn(context, contentUri, null, null);\n            }\n        } else if (\"content\".equalsIgnoreCase(uri.getScheme())) {\n            // 如果是 content 类型的 Uri\n            filePath = getDataColumn(context, uri, null, null);\n        } else if (\"file\".equals(uri.getScheme())) {\n            // 如果是 file 类型的 Uri,直接获取图片对应的路径\n            filePath = uri.getPath();\n        }\n        return filePath;\n    }\n\n    private static String getDataColumn(Context context, Uri uri, String selection, String[] selectionArgs) {\n        String path = null;\n\n        String[] projection = new String[]{MediaStore.Images.Media.DATA};\n        Cursor cursor = null;\n        try {\n            cursor = context.getContentResolver().query(uri, projection, selection, selectionArgs, null);\n            if (cursor != null && cursor.moveToFirst()) {\n                int columnIndex = cursor.getColumnIndexOrThrow(projection[0]);\n                path = cursor.getString(columnIndex);\n            }\n        } catch (Exception e) {\n            if (cursor != null) {\n                cursor.close();\n            }\n        }\n        return path;\n    }\n\n    private static boolean isMediaDocument(Uri uri) {\n        return \"com.android.providers.media.documents\".equals(uri.getAuthority());\n    }\n\n    private static boolean isDownloadsDocument(Uri uri) {\n        return \"com.android.providers.downloads.documents\".equals(uri.getAuthority());\n    }\n}\n"
  },
  {
    "path": "YZxing-lib/src/main/java/com/example/qrcode/view/ScannerView.java",
    "content": "package com.example.qrcode.view;\n\nimport android.content.Context;\nimport android.graphics.Canvas;\nimport android.graphics.Color;\nimport android.graphics.Paint;\nimport android.graphics.Rect;\nimport android.support.annotation.Nullable;\nimport android.util.AttributeSet;\nimport android.view.View;\n\nimport com.example.qrcode.R;\nimport com.example.qrcode.camera.CameraManager;\n\n\n/**\n * Created by yangyu on 17/10/30.\n */\n\npublic class ScannerView extends View {\n    private static final int[] SCANNER_ALPHA = {0, 64, 128, 192, 255, 192, 128, 64};\n    private static final long ANIMATION_DELAY = 90L;\n    private Paint mBgPaint;\n    private Paint mCornerPaint;\n    private Paint mFocusFramePaint;\n    private Paint mTipPaint;\n    private Paint mLaserPaint;\n    private CameraManager cameraManager;\n\n    private int mCornerLength;\n    private int mCornerThick;\n    private int mTipPaddingTop;\n    private int mFocusLineThick;\n    private int scannerAlpha;\n\n\n    public ScannerView(Context context) {\n        this(context, null);\n    }\n\n    public ScannerView(Context context, @Nullable AttributeSet attrs) {\n        super(context, attrs);\n        init();\n    }\n\n    /**\n     * 一些初始化操作\n     */\n    private void init() {\n        mBgPaint = new Paint();\n        mCornerPaint = new Paint();\n        mFocusFramePaint = new Paint();\n        mTipPaint = new Paint();\n        mLaserPaint = new Paint();\n\n        mBgPaint.setColor(getResources().getColor(R.color.scan_view_bg));\n        mBgPaint.setAntiAlias(true);\n\n        mCornerPaint.setAntiAlias(true);\n        mCornerPaint.setColor(getResources().getColor(R.color.scan_frame_green_color));\n\n        mFocusFramePaint.setAntiAlias(true);\n        mFocusFramePaint.setColor(Color.WHITE);\n\n        mTipPaint.setAntiAlias(true);\n        mTipPaint.setTextSize(getResources().getDimensionPixelSize(R.dimen.scanner_view_tip_size));\n        mTipPaint.setColor(getResources().getColor(R.color.scan_view_tip_color));\n\n        mLaserPaint.setAntiAlias(true);\n        mLaserPaint.setColor(getResources().getColor(R.color.scan_line_color));\n\n        mCornerLength = getResources().getDimensionPixelSize(R.dimen.scanner_view_corner_width);\n        mCornerThick = getResources().getDimensionPixelSize(R.dimen.scanner_view_corner_thick);\n        mTipPaddingTop = getResources().getDimensionPixelSize(R.dimen.scanner_view_tip_top);\n        mFocusLineThick = getResources().getDimensionPixelSize(R.dimen.scanner_view_focus_line_thick);\n        scannerAlpha = 0;\n    }\n\n    public void setCameraManager(CameraManager cameraManager) {\n        this.cameraManager = cameraManager;\n    }\n\n    @Override\n    protected void onDraw(Canvas canvas) {\n        super.onDraw(canvas);\n        if (cameraManager == null) return;\n        Rect mScannerRect = cameraManager.getFramingRect();\n        if (mScannerRect == null) return;\n        int width = canvas.getWidth();\n        int height = canvas.getHeight();\n        canvas.drawRect(0, 0, width, mScannerRect.top, mBgPaint);\n        canvas.drawRect(0, mScannerRect.top, mScannerRect.left, mScannerRect.bottom + 1, mBgPaint);\n        canvas.drawRect(mScannerRect.right + 1, mScannerRect.top, width, mScannerRect.bottom + 1, mBgPaint);\n        canvas.drawRect(0, mScannerRect.bottom + 1, width, height, mBgPaint);\n        drawCorner(canvas, mScannerRect);\n        drawFocusRect(canvas, mScannerRect);\n        drawTipText(canvas, getResources().getDisplayMetrics().widthPixels, mScannerRect.bottom + mTipPaddingTop);\n        drawLaser(canvas, mScannerRect);\n        //实现动画效果\n        postInvalidateDelayed(ANIMATION_DELAY, mScannerRect.left, mScannerRect.top, mScannerRect.right, mScannerRect.bottom);\n\n    }\n\n    /**\n     * 绘制矩形框的四个角\n     *\n     * @param canvas\n     * @param rect\n     */\n    private void drawCorner(Canvas canvas, Rect rect) {\n        if (rect == null) return;\n        //绘制左上角\n        canvas.drawRect(rect.left, rect.top, rect.left + mCornerLength, rect.top + mCornerThick, mCornerPaint);\n        canvas.drawRect(rect.left, rect.top, rect.left + mCornerThick, rect.top + mCornerLength, mCornerPaint);\n\n        //绘制左下角\n        canvas.drawRect(rect.left, rect.bottom - mCornerThick, rect.left + mCornerLength, rect.bottom, mCornerPaint);\n        canvas.drawRect(rect.left, rect.bottom - mCornerLength, rect.left + mCornerThick, rect.bottom, mCornerPaint);\n\n        //绘制右上角\n        canvas.drawRect(rect.right - mCornerLength, rect.top, rect.right, rect.top + mCornerThick, mCornerPaint);\n        canvas.drawRect(rect.right - mCornerThick, rect.top, rect.right, rect.top + mCornerLength, mCornerPaint);\n\n        //绘制右下角\n        canvas.drawRect(rect.right - mCornerLength, rect.bottom - mCornerThick, rect.right, rect.bottom, mCornerPaint);\n        canvas.drawRect(rect.right - mCornerThick, rect.bottom - mCornerLength, rect.right, rect.bottom, mCornerPaint);\n    }\n\n    /**\n     * 绘制聚焦框\n     */\n    private void drawFocusRect(Canvas canvas, Rect rect) {\n        canvas.drawRect(rect.left + mCornerLength, rect.top, rect.right - mCornerLength, rect.top + mFocusLineThick, mFocusFramePaint);\n        canvas.drawRect(rect.right - mFocusLineThick, rect.top + mCornerLength, rect.right, rect.bottom - mCornerLength, mFocusFramePaint);\n        canvas.drawRect(rect.left + mCornerLength, rect.bottom - mFocusLineThick, rect.right - mCornerLength, rect.bottom, mFocusFramePaint);\n        canvas.drawRect(rect.left, rect.top + mCornerLength, rect.left + mFocusLineThick, rect.bottom - mCornerLength, mFocusFramePaint);\n    }\n\n    //绘制提示语\n    private void drawTipText(Canvas canvas, int w, int h) {\n        String tip = getResources().getString(R.string.scanner_view_tip_text);\n        float l = (w - tip.length() * mTipPaint.getTextSize()) / 2;\n        canvas.drawText(tip, l, h, mTipPaint);\n    }\n\n    /**\n     * 绘制激光线\n     */\n    private void drawLaser(Canvas canvas, Rect rect) {\n        mLaserPaint.setAlpha(SCANNER_ALPHA[scannerAlpha]);\n        scannerAlpha = (scannerAlpha + 1) % SCANNER_ALPHA.length;\n        int middle = rect.height() / 2 + rect.top;\n        canvas.drawRect(rect.left + 2, middle - 1, rect.right - 1, middle + 2, mLaserPaint);\n    }\n\n\n}\n"
  },
  {
    "path": "YZxing-lib/src/main/res/drawable/progressbar_drawable.xml",
    "content": "<layer-list xmlns:android=\"http://schemas.android.com/apk/res/android\">\n\n    <item android:id=\"@android:id/background\">\n        <shape>\n            <corners android:radius=\"5dip\" />\n            <gradient\n                android:startColor=\"#ff9d9e9d\"\n                android:centerColor=\"#ff5a5d5a\"\n                android:centerY=\"0.75\"\n                android:endColor=\"#ff747674\"\n                android:angle=\"270\"\n                />\n        </shape>\n    </item>\n\n    <!--<item android:id=\"@android:id/secondaryProgress\">-->\n        <!--<clip>-->\n            <!--<shape>-->\n                <!--<corners android:radius=\"5dip\" />-->\n                <!--<gradient-->\n                    <!--android:startColor=\"#80ffd300\"-->\n                    <!--android:centerColor=\"#80ffb600\"-->\n                    <!--android:centerY=\"0.75\"-->\n                    <!--android:endColor=\"#a0ffcb00\"-->\n                    <!--android:angle=\"270\"-->\n                    <!--/>-->\n            <!--</shape>-->\n\n        <!--</clip>-->\n    <!--</item>-->\n\n    <item android:id=\"@android:id/progress\">\n        <clip>\n            <shape>\n                <corners android:radius=\"5dip\" />\n                <!--<gradient-->\n                <!--android:startColor=\"#ffffd300\"-->\n                <!--android:centerColor=\"#ffffb600\"-->\n                <!--android:centerY=\"0.75\"-->\n                <!--android:endColor=\"#ffffcb00\"-->\n                <!--android:angle=\"270\"-->\n                <!--/>-->\n                <solid android:color=\"@color/scan_frame_green_color\" />\n            </shape>\n        </clip>\n    </item>\n\n</layer-list>"
  },
  {
    "path": "YZxing-lib/src/main/res/layout/layout_activity_barcode.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<android.support.constraint.ConstraintLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:layout_width=\"match_parent\"\n    android:layout_height=\"match_parent\">\n\n    <EditText\n        android:id=\"@+id/et_input_content\"\n        android:layout_width=\"0dp\"\n        android:layout_height=\"wrap_content\"\n        android:hint=\"请输入条码的内容\"\n        android:paddingTop=\"10dp\"\n        app:layout_constraintLeft_toLeftOf=\"parent\"\n        app:layout_constraintRight_toRightOf=\"parent\" />\n\n\n    <RadioGroup\n        android:id=\"@+id/rg_code_type\"\n        android:layout_width=\"wrap_content\"\n        android:layout_height=\"wrap_content\"\n        android:orientation=\"horizontal\"\n        android:paddingTop=\"10dp\"\n        app:layout_constraintTop_toBottomOf=\"@id/et_input_content\">\n\n        <RadioButton\n            android:id=\"@+id/rb_qr_code\"\n            android:layout_width=\"wrap_content\"\n            android:layout_height=\"wrap_content\"\n            android:checked=\"true\"\n            android:text=\"QR_CODE\" />\n\n        <RadioButton\n            android:id=\"@+id/rb_code_128\"\n            android:layout_width=\"wrap_content\"\n            android:layout_height=\"wrap_content\"\n            android:text=\"CODE_128\" />\n    </RadioGroup>\n\n\n    <Button\n        android:id=\"@+id/bt_encode\"\n        android:layout_width=\"wrap_content\"\n        android:layout_height=\"wrap_content\"\n        android:paddingTop=\"5dp\"\n        android:text=\"生成条码\"\n        app:layout_constraintLeft_toLeftOf=\"parent\"\n        app:layout_constraintRight_toRightOf=\"parent\"\n        app:layout_constraintTop_toBottomOf=\"@id/rg_code_type\" />\n\n    <ImageView\n        android:id=\"@+id/barcode_image\"\n        android:layout_width=\"wrap_content\"\n        android:layout_height=\"wrap_content\"\n        android:layout_marginTop=\"18dp\"\n        app:layout_constraintBottom_toBottomOf=\"parent\"\n        app:layout_constraintLeft_toLeftOf=\"parent\"\n        app:layout_constraintRight_toRightOf=\"parent\"\n        app:layout_constraintTop_toBottomOf=\"@id/bt_encode\" />\n\n</android.support.constraint.ConstraintLayout>"
  },
  {
    "path": "YZxing-lib/src/main/res/layout/layout_activity_scanner.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<RelativeLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:layout_width=\"match_parent\"\n    android:layout_height=\"match_parent\"\n    android:orientation=\"vertical\">\n\n\n    <android.support.v7.widget.Toolbar\n        android:id=\"@+id/tool_bar\"\n        android:layout_width=\"match_parent\"\n        android:layout_height=\"?attr/actionBarSize\"\n        android:background=\"?attr/colorPrimary\"\n        app:navigationIcon=\"@drawable/ic_arrow_back_white_24dp\"\n        app:popupTheme=\"@style/ToolbarPopupTheme\">\n\n    </android.support.v7.widget.Toolbar>\n\n    <SurfaceView\n        android:id=\"@+id/surface\"\n        android:layout_width=\"match_parent\"\n        android:layout_height=\"match_parent\"\n        android:layout_below=\"@id/tool_bar\"\n        android:layout_centerInParent=\"true\" />\n\n    <com.example.qrcode.view.ScannerView\n        android:id=\"@+id/scan_view\"\n        android:layout_width=\"match_parent\"\n        android:layout_height=\"match_parent\"\n        android:layout_below=\"@id/tool_bar\"\n        android:layout_centerInParent=\"true\" />\n\n\n</RelativeLayout>\n"
  },
  {
    "path": "YZxing-lib/src/main/res/layout/layout_activity_show_result.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<RelativeLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    android:layout_width=\"match_parent\"\n    android:layout_height=\"match_parent\">\n\n    <ProgressBar\n        android:id=\"@+id/progress\"\n        style=\"?android:attr/progressBarStyleHorizontal\"\n        android:layout_width=\"match_parent\"\n        android:layout_height=\"3dp\"\n        android:progressDrawable=\"@drawable/progressbar_drawable\"\n\n        />\n\n    <WebView\n        android:id=\"@+id/web_content\"\n        android:layout_width=\"match_parent\"\n        android:layout_height=\"match_parent\"\n        android:layout_below=\"@id/progress\">\n\n    </WebView>\n\n    <TextView\n        android:id=\"@+id/tv\"\n        android:layout_width=\"wrap_content\"\n        android:layout_height=\"wrap_content\"\n        android:layout_centerInParent=\"true\"\n        android:textColor=\"#000\"\n        android:textSize=\"22sp\"\n\n        />\n\n\n</RelativeLayout>"
  },
  {
    "path": "YZxing-lib/src/main/res/menu/menu_scan.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<menu xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\">\n    <item\n        android:id=\"@+id/scan_from_picture\"\n        android:title=\"从相册选取二维码\"\n        app:showAsAction=\"never\" />\n    <item\n        android:id=\"@+id/encode_barcode\"\n        android:title=\"生成条形码\"\n        app:showAsAction=\"never\" />\n</menu>"
  },
  {
    "path": "YZxing-lib/src/main/res/values/colors.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<resources>\n    <color name=\"scan_frame_green_color\">#65E102</color>\n    <color name=\"scan_line_color\">#98C360</color>\n    <color name=\"scan_view_bg\">#64000000</color>\n    <color name=\"scan_view_tip_color\">#AFAFAF</color>\n</resources>"
  },
  {
    "path": "YZxing-lib/src/main/res/values/dimens.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<resources>\n    <dimen name=\"scanner_view_corner_width\">14dp</dimen>\n    <dimen name=\"scanner_view_corner_thick\">4dp</dimen>\n    <dimen name=\"scanner_view_focus_line_thick\">1dp</dimen>\n    <dimen name=\"scanner_view_tip_top\">28dp</dimen>\n    <dimen name=\"scanner_view_tip_size\">14sp</dimen>\n</resources>"
  },
  {
    "path": "YZxing-lib/src/main/res/values/strings.xml",
    "content": "<resources>\n    <string name=\"app_name\">QrCode</string>\n    <string name=\"scanner_view_tip_text\">将二维码/条形码放入框内，即可自动扫描</string>\n</resources>\n"
  },
  {
    "path": "YZxing-lib/src/main/res/values/styles.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<resources>\n\n    <style name=\"MyAppTheme\" parent=\"Theme.AppCompat.Light.NoActionBar\">\n\n        <item name=\"colorPrimary\">#393A3F</item>\n        <item name=\"colorPrimaryDark\">#303135</item>\n    </style>\n\n    <style name=\"ToolbarPopupTheme\" parent=\"@style/ThemeOverlay.AppCompat.Dark\">\n        <!--<item name=\"android:colorBackground\">#000000</item>-->\n        <item name=\"actionOverflowMenuStyle\">@style/OverflowMenuStyle</item> <!--新增一个item，用于控制menu-->\n    </style>\n    <style name=\"OverflowMenuStyle\" parent=\"Widget.AppCompat.Light.PopupMenu.Overflow\">\n        <item name=\"overlapAnchor\">false</item>  <!--把该属性改为false即可使menu位置位于toolbar之下-->\n    </style>\n\n\n</resources>"
  },
  {
    "path": "YZxing-lib/src/test/java/com/example/qrcode/ExampleUnitTest.java",
    "content": "package com.example.qrcode;\n\nimport org.junit.Test;\n\nimport static org.junit.Assert.*;\n\n/**\n * Example local unit test, which will execute on the development machine (host).\n *\n * @see <a href=\"http://d.android.com/tools/testing\">Testing documentation</a>\n */\npublic class ExampleUnitTest {\n    @Test\n    public void addition_isCorrect() throws Exception {\n        assertEquals(4, 2 + 2);\n    }\n}"
  },
  {
    "path": "app/.gitignore",
    "content": "/build\n"
  },
  {
    "path": "app/build.gradle",
    "content": "apply plugin: 'com.android.application'\n\nandroid {\n    compileSdkVersion 26\n    buildToolsVersion \"25.0.3\"\n    defaultConfig {\n        applicationId \"com.example.yzxing\"\n        minSdkVersion 19\n        targetSdkVersion 26\n        versionCode 1\n        versionName \"1.0\"\n        testInstrumentationRunner \"android.support.test.runner.AndroidJUnitRunner\"\n    }\n    buildTypes {\n        release {\n            minifyEnabled false\n            proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'\n        }\n    }\n}\n\ndependencies {\n    compile fileTree(include: ['*.jar'], dir: 'libs')\n    androidTestCompile('com.android.support.test.espresso:espresso-core:2.2.2', {\n        exclude group: 'com.android.support', module: 'support-annotations'\n    })\n    compile 'com.android.support:appcompat-v7:26.+'\n    compile 'com.android.support.constraint:constraint-layout:1.0.2'\n    testCompile 'junit:junit:4.12'\n    compile project(':YZxing-lib')\n}\n"
  },
  {
    "path": "app/proguard-rules.pro",
    "content": "# Add project specific ProGuard rules here.\n# By default, the flags in this file are appended to flags specified\n# in /Users/yangyu/Library/Android/sdk/tools/proguard/proguard-android.txt\n# You can edit the include path and order by changing the proguardFiles\n# directive in build.gradle.\n#\n# For more details, see\n#   http://developer.android.com/guide/developing/tools/proguard.html\n\n# Add any project specific keep options here:\n\n# If your project uses WebView with JS, uncomment the following\n# and specify the fully qualified class name to the JavaScript interface\n# class:\n#-keepclassmembers class fqcn.of.javascript.interface.for.webview {\n#   public *;\n#}\n\n# Uncomment this to preserve the line number information for\n# debugging stack traces.\n#-keepattributes SourceFile,LineNumberTable\n\n# If you keep the line number information, uncomment this to\n# hide the original source file name.\n#-renamesourcefileattribute SourceFile\n"
  },
  {
    "path": "app/src/androidTest/java/com/example/yzxing/ExampleInstrumentedTest.java",
    "content": "package com.example.yzxing;\n\nimport android.content.Context;\nimport android.support.test.InstrumentationRegistry;\nimport android.support.test.runner.AndroidJUnit4;\n\nimport org.junit.Test;\nimport org.junit.runner.RunWith;\n\nimport static org.junit.Assert.*;\n\n/**\n * Instrumentation test, which will execute on an Android device.\n *\n * @see <a href=\"http://d.android.com/tools/testing\">Testing documentation</a>\n */\n@RunWith(AndroidJUnit4.class)\npublic class ExampleInstrumentedTest {\n    @Test\n    public void useAppContext() throws Exception {\n        // Context of the app under test.\n        Context appContext = InstrumentationRegistry.getTargetContext();\n\n        assertEquals(\"com.example.yzxing\", appContext.getPackageName());\n    }\n}\n"
  },
  {
    "path": "app/src/main/AndroidManifest.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<manifest xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    package=\"com.example.yzxing\">\n    <uses-permission android:name=\"android.permission.CAMERA\"/>\n    <application\n        android:allowBackup=\"true\"\n        android:icon=\"@mipmap/ic_launcher\"\n        android:label=\"@string/app_name\"\n        android:roundIcon=\"@mipmap/ic_launcher_round\"\n        android:supportsRtl=\"true\"\n        android:theme=\"@style/AppTheme\">\n        <activity android:name=\".MainActivity\">\n            <intent-filter>\n                <action android:name=\"android.intent.action.MAIN\" />\n\n                <category android:name=\"android.intent.category.LAUNCHER\" />\n            </intent-filter>\n        </activity>\n    </application>\n\n</manifest>"
  },
  {
    "path": "app/src/main/java/com/example/yzxing/MainActivity.java",
    "content": "package com.example.yzxing;\n\nimport android.Manifest;\nimport android.content.Intent;\nimport android.content.pm.PackageManager;\nimport android.os.Bundle;\nimport android.support.annotation.NonNull;\nimport android.support.v4.app.ActivityCompat;\nimport android.support.v4.content.ContextCompat;\nimport android.support.v7.app.AppCompatActivity;\nimport android.view.View;\nimport android.widget.Button;\nimport android.widget.Toast;\n\nimport com.example.qrcode.Constant;\nimport com.example.qrcode.ScannerActivity;\n\n\npublic class MainActivity extends AppCompatActivity {\n\n    private final int REQUEST_PERMISION_CODE_CAMARE = 0;\n    private final int RESULT_REQUEST_CODE = 1;\n    private static final String TAG = \"MainActivity\";\n\n//    private HashMap<String, Set> mHashMap = new HashMap<>();\n\n    @Override\n    protected void onCreate(Bundle savedInstanceState) {\n        super.onCreate(savedInstanceState);\n        setContentView(R.layout.activity_main);\n        Button mScanner = (Button) findViewById(R.id.scanner);\n        mScanner.setOnClickListener(mScannerListener);\n\n//        Set<BarcodeFormat> codeFormats = EnumSet.of(BarcodeFormat.QR_CODE\n//                , BarcodeFormat.CODE_128\n//                , BarcodeFormat.CODE_93 );\n//        mHashMap.put(ScannerActivity.BARCODE_FORMAT, codeFormats);\n    }\n\n    private View.OnClickListener mScannerListener = new View.OnClickListener() {\n        @Override\n        public void onClick(View v) {\n            if (ContextCompat.checkSelfPermission(MainActivity.this, Manifest.permission.CAMERA) == PackageManager.PERMISSION_GRANTED) {\n                goScanner();\n            } else {\n                ActivityCompat.requestPermissions(MainActivity.this, new String[]{Manifest.permission.CAMERA}, REQUEST_PERMISION_CODE_CAMARE);\n            }\n        }\n    };\n\n    private void goScanner() {\n        Intent intent = new Intent(this, ScannerActivity.class);\n        //这里可以用intent传递一些参数，比如扫码聚焦框尺寸大小，支持的扫码类型。\n//        //设置扫码框的宽\n//        intent.putExtra(Constant.EXTRA_SCANNER_FRAME_WIDTH, 400);\n//        //设置扫码框的高\n//        intent.putExtra(Constant.EXTRA_SCANNER_FRAME_HEIGHT, 400);\n//        //设置扫码框距顶部的位置\n//        intent.putExtra(Constant.EXTRA_SCANNER_FRAME_TOP_PADDING, 100);\n//        //设置是否启用从相册获取二维码。\n        intent.putExtra(Constant.EXTRA_IS_ENABLE_SCAN_FROM_PIC,true);\n//        Bundle bundle = new Bundle();\n//        //设置支持的扫码类型\n//        bundle.putSerializable(Constant.EXTRA_SCAN_CODE_TYPE, mHashMap);\n//        intent.putExtras(bundle);\n        startActivityForResult(intent, RESULT_REQUEST_CODE);\n    }\n\n    @Override\n    public void onRequestPermissionsResult(int requestCode,\n                                           @NonNull String permissions[], @NonNull int[] grantResults) {\n        switch (requestCode) {\n            case REQUEST_PERMISION_CODE_CAMARE: {\n                if (grantResults.length > 0\n                        && grantResults[0] == PackageManager.PERMISSION_GRANTED) {\n                    goScanner();\n                }\n                return;\n            }\n\n        }\n    }\n\n    @Override\n    protected void onActivityResult(int requestCode, int resultCode, Intent data) {\n        if (resultCode == RESULT_OK) {\n            switch (requestCode) {\n                case RESULT_REQUEST_CODE:\n                    if (data == null) return;\n                    String type = data.getStringExtra(Constant.EXTRA_RESULT_CODE_TYPE);\n                    String content = data.getStringExtra(Constant.EXTRA_RESULT_CONTENT);\n                    Toast.makeText(MainActivity.this, \"codeType:\" + type\n                            + \"-----content:\" + content, Toast.LENGTH_SHORT).show();\n                    break;\n                default:\n                    break;\n\n            }\n        }\n        super.onActivityResult(requestCode, resultCode, data);\n    }\n}\n"
  },
  {
    "path": "app/src/main/res/layout/activity_main.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<android.support.constraint.ConstraintLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    xmlns:tools=\"http://schemas.android.com/tools\"\n    android:layout_width=\"match_parent\"\n    android:layout_height=\"match_parent\"\n    tools:context=\"com.example.yzxing.MainActivity\">\n\n    <Button\n        android:id=\"@+id/scanner\"\n        android:layout_width=\"wrap_content\"\n        android:layout_height=\"wrap_content\"\n        android:text=\"go scanner!\"\n        app:layout_constraintBottom_toBottomOf=\"parent\"\n        app:layout_constraintLeft_toLeftOf=\"parent\"\n        app:layout_constraintRight_toRightOf=\"parent\"\n        app:layout_constraintTop_toTopOf=\"parent\" />\n\n</android.support.constraint.ConstraintLayout>\n"
  },
  {
    "path": "app/src/main/res/values/colors.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<resources>\n    <color name=\"colorPrimary\">#3F51B5</color>\n    <color name=\"colorPrimaryDark\">#303F9F</color>\n    <color name=\"colorAccent\">#FF4081</color>\n</resources>\n"
  },
  {
    "path": "app/src/main/res/values/strings.xml",
    "content": "<resources>\n    <string name=\"app_name\">YZxing</string>\n</resources>\n"
  },
  {
    "path": "app/src/main/res/values/styles.xml",
    "content": "<resources>\n\n    <!-- Base application theme. -->\n    <style name=\"AppTheme\" parent=\"Theme.AppCompat.Light.DarkActionBar\">\n        <!-- Customize your theme here. -->\n        <item name=\"colorPrimary\">@color/colorPrimary</item>\n        <item name=\"colorPrimaryDark\">@color/colorPrimaryDark</item>\n        <item name=\"colorAccent\">@color/colorAccent</item>\n    </style>\n\n</resources>\n"
  },
  {
    "path": "app/src/test/java/com/example/yzxing/ExampleUnitTest.java",
    "content": "package com.example.yzxing;\n\nimport org.junit.Test;\n\nimport static org.junit.Assert.*;\n\n/**\n * Example local unit test, which will execute on the development machine (host).\n *\n * @see <a href=\"http://d.android.com/tools/testing\">Testing documentation</a>\n */\npublic class ExampleUnitTest {\n    @Test\n    public void addition_isCorrect() throws Exception {\n        assertEquals(4, 2 + 2);\n    }\n}"
  },
  {
    "path": "build.gradle",
    "content": "// Top-level build file where you can add configuration options common to all sub-projects/modules.\n\nbuildscript {\n    repositories {\n        jcenter()\n    }\n    dependencies {\n        classpath 'com.android.tools.build:gradle:2.3.3'\n\n        classpath 'com.github.dcendents:android-maven-gradle-plugin:1.5'\n        classpath 'com.jfrog.bintray.gradle:gradle-bintray-plugin:1.7.3'\n\n        // NOTE: Do not place your application dependencies here; they belong\n        // in the individual module build.gradle files\n    }\n}\n\nallprojects {\n    repositories {\n        jcenter()\n    }\n}\n\ntask clean(type: Delete) {\n    delete rootProject.buildDir\n}\n"
  },
  {
    "path": "gradle/wrapper/gradle-wrapper.properties",
    "content": "#Wed Oct 18 15:21:49 CST 2017\ndistributionBase=GRADLE_USER_HOME\ndistributionPath=wrapper/dists\nzipStoreBase=GRADLE_USER_HOME\nzipStorePath=wrapper/dists\ndistributionUrl=https\\://services.gradle.org/distributions/gradle-3.3-all.zip\n"
  },
  {
    "path": "gradle.properties",
    "content": "# Project-wide Gradle settings.\n\n# IDE (e.g. Android Studio) users:\n# Gradle settings configured through the IDE *will override*\n# any settings specified in this file.\n\n# For more details on how to configure your build environment visit\n# http://www.gradle.org/docs/current/userguide/build_environment.html\n\n# Specifies the JVM arguments used for the daemon process.\n# The setting is particularly useful for tweaking memory settings.\norg.gradle.jvmargs=-Xmx1536m\n\n# When configured, Gradle will run in incubating parallel mode.\n# This option should only be used with decoupled projects. More details, visit\n# http://www.gradle.org/docs/current/userguide/multi_project_builds.html#sec:decoupled_projects\n# org.gradle.parallel=true\n"
  },
  {
    "path": "gradlew",
    "content": "#!/usr/bin/env bash\n\n##############################################################################\n##\n##  Gradle start up script for UN*X\n##\n##############################################################################\n\n# Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.\nDEFAULT_JVM_OPTS=\"\"\n\nAPP_NAME=\"Gradle\"\nAPP_BASE_NAME=`basename \"$0\"`\n\n# Use the maximum available, or set MAX_FD != -1 to use that value.\nMAX_FD=\"maximum\"\n\nwarn ( ) {\n    echo \"$*\"\n}\n\ndie ( ) {\n    echo\n    echo \"$*\"\n    echo\n    exit 1\n}\n\n# OS specific support (must be 'true' or 'false').\ncygwin=false\nmsys=false\ndarwin=false\ncase \"`uname`\" in\n  CYGWIN* )\n    cygwin=true\n    ;;\n  Darwin* )\n    darwin=true\n    ;;\n  MINGW* )\n    msys=true\n    ;;\nesac\n\n# Attempt to set APP_HOME\n# Resolve links: $0 may be a link\nPRG=\"$0\"\n# Need this for relative symlinks.\nwhile [ -h \"$PRG\" ] ; do\n    ls=`ls -ld \"$PRG\"`\n    link=`expr \"$ls\" : '.*-> \\(.*\\)$'`\n    if expr \"$link\" : '/.*' > /dev/null; then\n        PRG=\"$link\"\n    else\n        PRG=`dirname \"$PRG\"`\"/$link\"\n    fi\ndone\nSAVED=\"`pwd`\"\ncd \"`dirname \\\"$PRG\\\"`/\" >/dev/null\nAPP_HOME=\"`pwd -P`\"\ncd \"$SAVED\" >/dev/null\n\nCLASSPATH=$APP_HOME/gradle/wrapper/gradle-wrapper.jar\n\n# Determine the Java command to use to start the JVM.\nif [ -n \"$JAVA_HOME\" ] ; then\n    if [ -x \"$JAVA_HOME/jre/sh/java\" ] ; then\n        # IBM's JDK on AIX uses strange locations for the executables\n        JAVACMD=\"$JAVA_HOME/jre/sh/java\"\n    else\n        JAVACMD=\"$JAVA_HOME/bin/java\"\n    fi\n    if [ ! -x \"$JAVACMD\" ] ; then\n        die \"ERROR: JAVA_HOME is set to an invalid directory: $JAVA_HOME\n\nPlease set the JAVA_HOME variable in your environment to match the\nlocation of your Java installation.\"\n    fi\nelse\n    JAVACMD=\"java\"\n    which java >/dev/null 2>&1 || die \"ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH.\n\nPlease set the JAVA_HOME variable in your environment to match the\nlocation of your Java installation.\"\nfi\n\n# Increase the maximum file descriptors if we can.\nif [ \"$cygwin\" = \"false\" -a \"$darwin\" = \"false\" ] ; then\n    MAX_FD_LIMIT=`ulimit -H -n`\n    if [ $? -eq 0 ] ; then\n        if [ \"$MAX_FD\" = \"maximum\" -o \"$MAX_FD\" = \"max\" ] ; then\n            MAX_FD=\"$MAX_FD_LIMIT\"\n        fi\n        ulimit -n $MAX_FD\n        if [ $? -ne 0 ] ; then\n            warn \"Could not set maximum file descriptor limit: $MAX_FD\"\n        fi\n    else\n        warn \"Could not query maximum file descriptor limit: $MAX_FD_LIMIT\"\n    fi\nfi\n\n# For Darwin, add options to specify how the application appears in the dock\nif $darwin; then\n    GRADLE_OPTS=\"$GRADLE_OPTS \\\"-Xdock:name=$APP_NAME\\\" \\\"-Xdock:icon=$APP_HOME/media/gradle.icns\\\"\"\nfi\n\n# For Cygwin, switch paths to Windows format before running java\nif $cygwin ; then\n    APP_HOME=`cygpath --path --mixed \"$APP_HOME\"`\n    CLASSPATH=`cygpath --path --mixed \"$CLASSPATH\"`\n    JAVACMD=`cygpath --unix \"$JAVACMD\"`\n\n    # We build the pattern for arguments to be converted via cygpath\n    ROOTDIRSRAW=`find -L / -maxdepth 1 -mindepth 1 -type d 2>/dev/null`\n    SEP=\"\"\n    for dir in $ROOTDIRSRAW ; do\n        ROOTDIRS=\"$ROOTDIRS$SEP$dir\"\n        SEP=\"|\"\n    done\n    OURCYGPATTERN=\"(^($ROOTDIRS))\"\n    # Add a user-defined pattern to the cygpath arguments\n    if [ \"$GRADLE_CYGPATTERN\" != \"\" ] ; then\n        OURCYGPATTERN=\"$OURCYGPATTERN|($GRADLE_CYGPATTERN)\"\n    fi\n    # Now convert the arguments - kludge to limit ourselves to /bin/sh\n    i=0\n    for arg in \"$@\" ; do\n        CHECK=`echo \"$arg\"|egrep -c \"$OURCYGPATTERN\" -`\n        CHECK2=`echo \"$arg\"|egrep -c \"^-\"`                                 ### Determine if an option\n\n        if [ $CHECK -ne 0 ] && [ $CHECK2 -eq 0 ] ; then                    ### Added a condition\n            eval `echo args$i`=`cygpath --path --ignore --mixed \"$arg\"`\n        else\n            eval `echo args$i`=\"\\\"$arg\\\"\"\n        fi\n        i=$((i+1))\n    done\n    case $i in\n        (0) set -- ;;\n        (1) set -- \"$args0\" ;;\n        (2) set -- \"$args0\" \"$args1\" ;;\n        (3) set -- \"$args0\" \"$args1\" \"$args2\" ;;\n        (4) set -- \"$args0\" \"$args1\" \"$args2\" \"$args3\" ;;\n        (5) set -- \"$args0\" \"$args1\" \"$args2\" \"$args3\" \"$args4\" ;;\n        (6) set -- \"$args0\" \"$args1\" \"$args2\" \"$args3\" \"$args4\" \"$args5\" ;;\n        (7) set -- \"$args0\" \"$args1\" \"$args2\" \"$args3\" \"$args4\" \"$args5\" \"$args6\" ;;\n        (8) set -- \"$args0\" \"$args1\" \"$args2\" \"$args3\" \"$args4\" \"$args5\" \"$args6\" \"$args7\" ;;\n        (9) set -- \"$args0\" \"$args1\" \"$args2\" \"$args3\" \"$args4\" \"$args5\" \"$args6\" \"$args7\" \"$args8\" ;;\n    esac\nfi\n\n# Split up the JVM_OPTS And GRADLE_OPTS values into an array, following the shell quoting and substitution rules\nfunction splitJvmOpts() {\n    JVM_OPTS=(\"$@\")\n}\neval splitJvmOpts $DEFAULT_JVM_OPTS $JAVA_OPTS $GRADLE_OPTS\nJVM_OPTS[${#JVM_OPTS[*]}]=\"-Dorg.gradle.appname=$APP_BASE_NAME\"\n\nexec \"$JAVACMD\" \"${JVM_OPTS[@]}\" -classpath \"$CLASSPATH\" org.gradle.wrapper.GradleWrapperMain \"$@\"\n"
  },
  {
    "path": "gradlew.bat",
    "content": "@if \"%DEBUG%\" == \"\" @echo off\r\n@rem ##########################################################################\r\n@rem\r\n@rem  Gradle startup script for Windows\r\n@rem\r\n@rem ##########################################################################\r\n\r\n@rem Set local scope for the variables with windows NT shell\r\nif \"%OS%\"==\"Windows_NT\" setlocal\r\n\r\n@rem Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.\r\nset DEFAULT_JVM_OPTS=\r\n\r\nset DIRNAME=%~dp0\r\nif \"%DIRNAME%\" == \"\" set DIRNAME=.\r\nset APP_BASE_NAME=%~n0\r\nset APP_HOME=%DIRNAME%\r\n\r\n@rem Find java.exe\r\nif defined JAVA_HOME goto findJavaFromJavaHome\r\n\r\nset JAVA_EXE=java.exe\r\n%JAVA_EXE% -version >NUL 2>&1\r\nif \"%ERRORLEVEL%\" == \"0\" goto init\r\n\r\necho.\r\necho ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH.\r\necho.\r\necho Please set the JAVA_HOME variable in your environment to match the\r\necho location of your Java installation.\r\n\r\ngoto fail\r\n\r\n:findJavaFromJavaHome\r\nset JAVA_HOME=%JAVA_HOME:\"=%\r\nset JAVA_EXE=%JAVA_HOME%/bin/java.exe\r\n\r\nif exist \"%JAVA_EXE%\" goto init\r\n\r\necho.\r\necho ERROR: JAVA_HOME is set to an invalid directory: %JAVA_HOME%\r\necho.\r\necho Please set the JAVA_HOME variable in your environment to match the\r\necho location of your Java installation.\r\n\r\ngoto fail\r\n\r\n:init\r\n@rem Get command-line arguments, handling Windowz variants\r\n\r\nif not \"%OS%\" == \"Windows_NT\" goto win9xME_args\r\nif \"%@eval[2+2]\" == \"4\" goto 4NT_args\r\n\r\n:win9xME_args\r\n@rem Slurp the command line arguments.\r\nset CMD_LINE_ARGS=\r\nset _SKIP=2\r\n\r\n:win9xME_args_slurp\r\nif \"x%~1\" == \"x\" goto execute\r\n\r\nset CMD_LINE_ARGS=%*\r\ngoto execute\r\n\r\n:4NT_args\r\n@rem Get arguments from the 4NT Shell from JP Software\r\nset CMD_LINE_ARGS=%$\r\n\r\n:execute\r\n@rem Setup the command line\r\n\r\nset CLASSPATH=%APP_HOME%\\gradle\\wrapper\\gradle-wrapper.jar\r\n\r\n@rem Execute Gradle\r\n\"%JAVA_EXE%\" %DEFAULT_JVM_OPTS% %JAVA_OPTS% %GRADLE_OPTS% \"-Dorg.gradle.appname=%APP_BASE_NAME%\" -classpath \"%CLASSPATH%\" org.gradle.wrapper.GradleWrapperMain %CMD_LINE_ARGS%\r\n\r\n:end\r\n@rem End local scope for the variables with windows NT shell\r\nif \"%ERRORLEVEL%\"==\"0\" goto mainEnd\r\n\r\n:fail\r\nrem Set variable GRADLE_EXIT_CONSOLE if you need the _script_ return code instead of\r\nrem the _cmd.exe /c_ return code!\r\nif  not \"\" == \"%GRADLE_EXIT_CONSOLE%\" exit 1\r\nexit /b 1\r\n\r\n:mainEnd\r\nif \"%OS%\"==\"Windows_NT\" endlocal\r\n\r\n:omega\r\n"
  },
  {
    "path": "settings.gradle",
    "content": "include ':app', ':YZxing-lib'\n"
  }
]