Repository: 465857721/IDCardOCR_China
Branch: master
Commit: c93231a20ae0
Files: 35
Total size: 55.5 KB
Directory structure:
gitextract_pqg52avl/
├── .idea/
│ ├── compiler.xml
│ ├── copyright/
│ │ └── profiles_settings.xml
│ ├── encodings.xml
│ ├── gradle.xml
│ ├── misc.xml
│ ├── modules.xml
│ ├── runConfigurations.xml
│ └── vcs.xml
├── README.md
├── app/
│ ├── assets/
│ │ └── eng.traineddata
│ ├── build.gradle
│ ├── proguard-rules.pro
│ └── src/
│ ├── androidTest/
│ │ └── java/
│ │ └── com/
│ │ └── kingsoft/
│ │ └── idcardocr_china/
│ │ └── ExampleInstrumentedTest.java
│ ├── main/
│ │ ├── AndroidManifest.xml
│ │ ├── java/
│ │ │ └── com/
│ │ │ └── kingsoft/
│ │ │ └── idcardocr_china/
│ │ │ ├── MainActivity.java
│ │ │ └── idcardocr/
│ │ │ ├── AutoFocusManager.java
│ │ │ ├── CameraActivity.java
│ │ │ ├── CameraManager.java
│ │ │ └── PreviewBorderView.java
│ │ └── res/
│ │ ├── layout/
│ │ │ ├── activity_camera.xml
│ │ │ └── activity_main.xml
│ │ ├── values/
│ │ │ ├── attrs.xml
│ │ │ ├── colors.xml
│ │ │ ├── dimens.xml
│ │ │ ├── strings.xml
│ │ │ └── styles.xml
│ │ └── values-w820dp/
│ │ └── dimens.xml
│ └── test/
│ └── java/
│ └── com/
│ └── kingsoft/
│ └── idcardocr_china/
│ └── ExampleUnitTest.java
├── build.gradle
├── gradle/
│ └── wrapper/
│ ├── gradle-wrapper.jar
│ └── gradle-wrapper.properties
├── gradle.properties
├── gradlew
├── gradlew.bat
└── settings.gradle
================================================
FILE CONTENTS
================================================
================================================
FILE: .idea/compiler.xml
================================================
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="CompilerConfiguration">
<resourceExtensions />
<wildcardResourcePatterns>
<entry name="!?*.java" />
<entry name="!?*.form" />
<entry name="!?*.class" />
<entry name="!?*.groovy" />
<entry name="!?*.scala" />
<entry name="!?*.flex" />
<entry name="!?*.kt" />
<entry name="!?*.clj" />
<entry name="!?*.aj" />
</wildcardResourcePatterns>
<annotationProcessing>
<profile default="true" name="Default" enabled="false">
<processorPath useClasspath="true" />
</profile>
</annotationProcessing>
</component>
</project>
================================================
FILE: .idea/copyright/profiles_settings.xml
================================================
<component name="CopyrightManager">
<settings default="" />
</component>
================================================
FILE: .idea/encodings.xml
================================================
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="Encoding">
<file url="PROJECT" charset="UTF-8" />
</component>
</project>
================================================
FILE: .idea/gradle.xml
================================================
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="GradleSettings">
<option name="linkedExternalProjectsSettings">
<GradleProjectSettings>
<option name="distributionType" value="DEFAULT_WRAPPED" />
<option name="externalProjectPath" value="$PROJECT_DIR$" />
<option name="modules">
<set>
<option value="$PROJECT_DIR$" />
<option value="$PROJECT_DIR$/app" />
</set>
</option>
<option name="resolveModulePerSourceSet" value="false" />
</GradleProjectSettings>
</option>
</component>
</project>
================================================
FILE: .idea/misc.xml
================================================
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="EntryPointsManager">
<entry_points version="2.0" />
</component>
<component name="NullableNotNullManager">
<option name="myDefaultNullable" value="android.support.annotation.Nullable" />
<option name="myDefaultNotNull" value="android.support.annotation.NonNull" />
<option name="myNullables">
<value>
<list size="4">
<item index="0" class="java.lang.String" itemvalue="org.jetbrains.annotations.Nullable" />
<item index="1" class="java.lang.String" itemvalue="javax.annotation.Nullable" />
<item index="2" class="java.lang.String" itemvalue="edu.umd.cs.findbugs.annotations.Nullable" />
<item index="3" class="java.lang.String" itemvalue="android.support.annotation.Nullable" />
</list>
</value>
</option>
<option name="myNotNulls">
<value>
<list size="4">
<item index="0" class="java.lang.String" itemvalue="org.jetbrains.annotations.NotNull" />
<item index="1" class="java.lang.String" itemvalue="javax.annotation.Nonnull" />
<item index="2" class="java.lang.String" itemvalue="edu.umd.cs.findbugs.annotations.NonNull" />
<item index="3" class="java.lang.String" itemvalue="android.support.annotation.NonNull" />
</list>
</value>
</option>
</component>
<component name="ProjectInspectionProfilesVisibleTreeState">
<entry key="Project Default">
<profile-state>
<expanded-state>
<State>
<id />
</State>
<State>
<id>Abstraction issuesJava</id>
</State>
<State>
<id>Android > Lint > Correctness</id>
</State>
<State>
<id>Android > Lint > Correctness > Messages</id>
</State>
<State>
<id>Android > Lint > Performance</id>
</State>
<State>
<id>Android > Lint > Security</id>
</State>
<State>
<id>Android > Lint > Usability > Icons</id>
</State>
<State>
<id>Internationalization issuesJava</id>
</State>
<State>
<id>J2ME issuesJava</id>
</State>
<State>
<id>Java</id>
</State>
<State>
<id>Java language level issuesJava</id>
</State>
<State>
<id>Logging issuesJava</id>
</State>
<State>
<id>Numeric issuesJava</id>
</State>
<State>
<id>Portability issuesJava</id>
</State>
<State>
<id>Security issuesJava</id>
</State>
<State>
<id>Serialization issuesJava</id>
</State>
</expanded-state>
<selected-state>
<State>
<id>Android</id>
</State>
</selected-state>
</profile-state>
</entry>
</component>
<component name="ProjectLevelVcsManager" settingsEditedManually="false">
<OptionsSetting value="true" id="Add" />
<OptionsSetting value="true" id="Remove" />
<OptionsSetting value="true" id="Checkout" />
<OptionsSetting value="true" id="Update" />
<OptionsSetting value="true" id="Status" />
<OptionsSetting value="true" id="Edit" />
<ConfirmationsSetting value="0" id="Add" />
<ConfirmationsSetting value="0" id="Remove" />
</component>
<component name="ProjectRootManager" version="2" languageLevel="JDK_1_7" default="true" assert-keyword="true" jdk-15="true" project-jdk-name="1.8" project-jdk-type="JavaSDK">
<output url="file://$PROJECT_DIR$/build/classes" />
</component>
<component name="ProjectType">
<option name="id" value="Android" />
</component>
<component name="SvnConfiguration">
<configuration useDefault="false">C:\Users\周康\AppData\Roaming\Subversion</configuration>
</component>
<component name="masterDetails">
<states>
<state key="ProjectJDKs.UI">
<settings>
<last-edited>1.8</last-edited>
<splitter-proportions>
<option name="proportions">
<list>
<option value="0.2" />
</list>
</option>
</splitter-proportions>
</settings>
</state>
</states>
</component>
</project>
================================================
FILE: .idea/modules.xml
================================================
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="ProjectModuleManager">
<modules>
<module fileurl="file://$PROJECT_DIR$/IDCardOCR_China.iml" filepath="$PROJECT_DIR$/IDCardOCR_China.iml" />
<module fileurl="file://$PROJECT_DIR$/app/app.iml" filepath="$PROJECT_DIR$/app/app.iml" />
</modules>
</component>
</project>
================================================
FILE: .idea/runConfigurations.xml
================================================
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="RunConfigurationProducerService">
<option name="ignoredProducers">
<set>
<option value="org.jetbrains.plugins.gradle.execution.test.runner.AllInPackageGradleConfigurationProducer" />
<option value="org.jetbrains.plugins.gradle.execution.test.runner.TestClassGradleConfigurationProducer" />
<option value="org.jetbrains.plugins.gradle.execution.test.runner.TestMethodGradleConfigurationProducer" />
</set>
</option>
</component>
</project>
================================================
FILE: .idea/vcs.xml
================================================
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="VcsDirectoryMappings">
<mapping directory="$PROJECT_DIR$" vcs="Git" />
</component>
</project>
================================================
FILE: README.md
================================================
# IDCardOCR_China
基于tesseract,实现摄像头扫描识别中国二代身份证
# Usage
demo主要提供思路,通过摄像头取景,预览裁剪,ocr识别.
# ScreenShots

# TODO
- 姓名ocr识别
- 民族识别
# 建议
1.对esseract进行训练,目前用的文件为eng数据,没有针对二代身份证进行优化,可以自己进行训练,只识别1-0和英文X。数据包也会相应减小。
( baseApi.setVariable("tessedit_char_whitelist", "0123456789Xx");)也可以设置白名单,代码里设置了,但是这样没有减少训练文件的大小.
2.目前demo仅仅识别了身份证号码,可以裁剪出来其他信息进行ocr,后续进行优化....
#Thanks
https://github.com/tdk-farkas/CameraSFZ 身份证裁剪
#Changelog
V0.0.2(2016/12/24)
- 6.0权限适配
- 识别单词设置白名单 增加识别率
V0.0.1(2016/12/01)
- 项目导入
================================================
FILE: app/build.gradle
================================================
apply plugin: 'com.android.application'
android {
compileSdkVersion 25
buildToolsVersion "25.0.2"
defaultConfig {
applicationId "com.kingsoft.idcardocr_china"
minSdkVersion 21
targetSdkVersion 25
versionCode 1
versionName "1.0"
testInstrumentationRunner "android.support.test.runner.AndroidJUnitRunner"
}
buildTypes {
release {
minifyEnabled false
proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
}
}
}
dependencies {
compile fileTree(dir: 'libs', include: ['*.jar'])
androidTestCompile('com.android.support.test.espresso:espresso-core:2.2.2', {
exclude group: 'com.android.support', module: 'support-annotations'
})
compile 'com.android.support:appcompat-v7:25.0.0'
testCompile 'junit:junit:4.12'
compile 'com.rmtheis:tess-two:6.1.1'
compile 'com.anthonycr.grant:permissions:1.0'
}
================================================
FILE: app/proguard-rules.pro
================================================
# Add project specific ProGuard rules here.
# By default, the flags in this file are appended to flags specified
# in C:\dev\android-sdk-windows/tools/proguard/proguard-android.txt
# You can edit the include path and order by changing the proguardFiles
# directive in build.gradle.
#
# For more details, see
# http://developer.android.com/guide/developing/tools/proguard.html
# Add any project specific keep options here:
# If your project uses WebView with JS, uncomment the following
# and specify the fully qualified class name to the JavaScript interface
# class:
#-keepclassmembers class fqcn.of.javascript.interface.for.webview {
# public *;
#}
================================================
FILE: app/src/androidTest/java/com/kingsoft/idcardocr_china/ExampleInstrumentedTest.java
================================================
package com.kingsoft.idcardocr_china;
import android.content.Context;
import android.support.test.InstrumentationRegistry;
import android.support.test.runner.AndroidJUnit4;
import org.junit.Test;
import org.junit.runner.RunWith;
import static org.junit.Assert.*;
/**
* Instrumentation test, which will execute on an Android device.
*
* @see <a href="http://d.android.com/tools/testing">Testing documentation</a>
*/
@RunWith(AndroidJUnit4.class)
public class ExampleInstrumentedTest {
@Test
public void useAppContext() throws Exception {
// Context of the app under test.
Context appContext = InstrumentationRegistry.getTargetContext();
assertEquals("com.kingsoft.idcardocr_china", appContext.getPackageName());
}
}
================================================
FILE: app/src/main/AndroidManifest.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.kingsoft.idcardocr_china">
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"/>
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
<uses-permission android:name="android.permission.CAMERA"/>
<application
android:allowBackup="true"
android:icon="@mipmap/ic_launcher"
android:label="@string/app_name"
android:supportsRtl="true"
android:theme="@style/AppTheme">
<activity android:name=".MainActivity">
<intent-filter>
<action android:name="android.intent.action.MAIN"/>
<category android:name="android.intent.category.LAUNCHER"/>
</intent-filter>
</activity>
<activity
android:name=".idcardocr.CameraActivity"
android:screenOrientation="landscape"
android:theme="@android:style/Theme.NoTitleBar.Fullscreen"/>
</application>
</manifest>
================================================
FILE: app/src/main/java/com/kingsoft/idcardocr_china/MainActivity.java
================================================
package com.kingsoft.idcardocr_china;
import android.content.Context;
import android.content.Intent;
import android.os.Bundle;
import android.os.Handler;
import android.os.Message;
import android.support.v7.app.AppCompatActivity;
import android.view.View;
import android.widget.TextView;
import android.widget.Toast;
import com.anthonycr.grant.PermissionsManager;
import com.anthonycr.grant.PermissionsResultAction;
import com.kingsoft.idcardocr_china.idcardocr.CameraActivity;
public class MainActivity extends AppCompatActivity {
private static final int GETPERMISSION_SUCCESS = 1;//获取权限成功
private static final int GETPERMISSION_FAILER = 2;//获取权限失败
private TextView tv_id;
private int MY_SCAN_REQUEST_CODE = 100;
private Context mContext;
private MyHandler myHandler = new MyHandler();
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
mContext = this;
tv_id = (TextView) findViewById(R.id.tv_id);
findViewById(R.id.btn_go).setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
// getPermissions();
requestAllPermission();
}
});
}
private void requestAllPermission() {
PermissionsManager.getInstance().requestAllManifestPermissionsIfNecessary(MainActivity.this,
new PermissionsResultAction() {
@Override
public void onGranted() {
myHandler.sendEmptyMessage(GETPERMISSION_SUCCESS);
}
@Override
public void onDenied(String permission) {
myHandler.sendEmptyMessage(GETPERMISSION_FAILER);
}
});
}
//因为权限管理类无法监听系统,所以需要重写onRequestPermissionResult方法,更新权限管理类,并回调结果。这个是必须要有的。
@Override
public void onRequestPermissionsResult(int requestCode, String[] permissions, int[] grantResults) {
PermissionsManager.getInstance().notifyPermissionsChange(permissions, grantResults);
}
@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
if (requestCode == MY_SCAN_REQUEST_CODE && resultCode == RESULT_OK && data != null) {
String id = data.getStringExtra("id");
Toast.makeText(this, id, Toast.LENGTH_LONG).show();
if (id != null && id.length() == 18) {
tv_id.setText(id);
}
}
}
private class MyHandler extends Handler {
@Override
public void handleMessage(Message msg) {
super.handleMessage(msg);
switch (msg.what) {
case GETPERMISSION_SUCCESS:
Intent scanIntent = new Intent(mContext, CameraActivity.class);
startActivityForResult(scanIntent, MY_SCAN_REQUEST_CODE);
break;
case GETPERMISSION_FAILER:
Toast.makeText(mContext, "此功能须获摄像头权限1111111", Toast.LENGTH_LONG).show();
break;
}
}
}
}
================================================
FILE: app/src/main/java/com/kingsoft/idcardocr_china/idcardocr/AutoFocusManager.java
================================================
package com.kingsoft.idcardocr_china.idcardocr;
import android.hardware.Camera;
import android.os.AsyncTask;
import android.util.Log;
import java.util.ArrayList;
import java.util.Collection;
import java.util.concurrent.RejectedExecutionException;
public class AutoFocusManager implements Camera.AutoFocusCallback{
private static final String TAG = AutoFocusManager.class.getSimpleName();
private static final long AUTO_FOCUS_INTERVAL_MS = 3000L;
private static final Collection<String> FOCUS_MODES_CALLING_AF;
static {
FOCUS_MODES_CALLING_AF = new ArrayList<String>(2);
FOCUS_MODES_CALLING_AF.add(Camera.Parameters.FOCUS_MODE_AUTO);
FOCUS_MODES_CALLING_AF.add(Camera.Parameters.FOCUS_MODE_MACRO);
}
private boolean stopped;
private boolean focusing;
private final boolean useAutoFocus;
private final Camera camera;
private AsyncTask<?,?,?> outstandingTask;
private Camera.PreviewCallback mp;
public AutoFocusManager(Camera camera, Camera.PreviewCallback mp) {
this.camera = camera;
String currentFocusMode = camera.getParameters().getFocusMode();
useAutoFocus = FOCUS_MODES_CALLING_AF.contains(currentFocusMode);
Log.e(TAG, "Current focus mode '" + currentFocusMode + "'; use auto focus? " + useAutoFocus);
this.mp = mp;
start();
}
@Override
public synchronized void onAutoFocus(final boolean success, Camera theCamera) {
// if(success){
// camera.takePicture(null, null, myjpegCallback);
// }
;
focusing = false;
autoFocusAgainLater();
}
private synchronized void autoFocusAgainLater() {
if (!stopped && outstandingTask == null) {
AutoFocusTask newTask = new AutoFocusTask();
try {
newTask.executeOnExecutor(AsyncTask.THREAD_POOL_EXECUTOR);
outstandingTask = newTask;
} catch (RejectedExecutionException ree) {
Log.e(TAG, "Could not request auto focus", ree);
}
}
}
/**
* 开始自动对焦
*/
public synchronized void start() {
// camera.setOneShotPreviewCallback(new Camera.PreviewCallback() {
// @Override
// public void onPreviewFrame(byte[] data, Camera camera)
// });
if (useAutoFocus) {
outstandingTask = null;
if (!stopped && !focusing) {
try {
camera.setOneShotPreviewCallback(mp);
camera.autoFocus(this);
focusing = true;
} catch (RuntimeException re) {
// Have heard RuntimeException reported in Android 4.0.x+; continue?
Log.e(TAG, "Unexpected exception while focusing", re);
// Try again later to keep cycle going
autoFocusAgainLater();
}
}
}
}
private synchronized void cancelOutstandingTask() {
if (outstandingTask != null) {
if (outstandingTask.getStatus() != AsyncTask.Status.FINISHED) {
outstandingTask.cancel(true);
}
outstandingTask = null;
}
}
/**
* 停止自动对焦
*/
public synchronized void stop() {
stopped = true;
if (useAutoFocus) {
cancelOutstandingTask();
// Doesn't hurt to call this even if not focusing
try {
camera.cancelAutoFocus();
} catch (RuntimeException re) {
// Have heard RuntimeException reported in Android 4.0.x+; continue?
Log.e(TAG, "Unexpected exception while cancelling focusing", re);
}
}
}
private final class AutoFocusTask extends AsyncTask<Object,Object,Object> {
@Override
protected Object doInBackground(Object... voids) {
try {
Thread.sleep(AUTO_FOCUS_INTERVAL_MS);
} catch (InterruptedException e) {
// continue
}
start();
return null;
}
}
}
================================================
FILE: app/src/main/java/com/kingsoft/idcardocr_china/idcardocr/CameraActivity.java
================================================
package com.kingsoft.idcardocr_china.idcardocr;
import android.app.Activity;
import android.content.Intent;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.graphics.ImageFormat;
import android.graphics.Rect;
import android.graphics.YuvImage;
import android.hardware.Camera;
import android.os.Bundle;
import android.os.Environment;
import android.os.Handler;
import android.util.Log;
import android.view.SurfaceHolder;
import android.view.SurfaceView;
import android.view.View;
import android.widget.Button;
import android.widget.TextView;
import com.googlecode.tesseract.android.TessBaseAPI;
import com.kingsoft.idcardocr_china.R;
import java.io.ByteArrayOutputStream;
import java.io.File;
import java.io.FileOutputStream;
import java.io.InputStream;
import java.io.OutputStream;
public class CameraActivity extends Activity implements SurfaceHolder.Callback, Camera.PreviewCallback {
private TessBaseAPI baseApi;
// Camera.PreviewCallback mp = ;
private CameraManager cameraManager;
private boolean hasSurface;
private String type;
private Button btn_close, light, btn_resacn;
private boolean toggleLight = false;
private Handler mHandler;
private TextView tv_lightstate, tv_input;
private String sdPath;
// private ImageView iv_close;
// private View ErrorView;
private int times = 0;
private Long opentime;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
opentime = System.currentTimeMillis();
sdPath = Environment.getExternalStorageDirectory() + "/ayy/";
try {
copyAssetFile();
} catch (Exception e) {
e.printStackTrace();
}
baseApi = new TessBaseAPI();
baseApi.init(sdPath, "eng");
baseApi.setVariable("tessedit_char_whitelist", "0123456789Xx");
// baseApi.
setContentView(R.layout.activity_camera);
tv_lightstate = (TextView) findViewById(R.id.tv_openlight);
mHandler = new Handler();
initLayoutParams();
}
/**
* 重置surface宽高比例为3:4,不重置的话图形会拉伸变形
*/
private void initLayoutParams() {
// ErrorView = findViewById(R.id.ll_cameraerrorview);
btn_close = (Button) findViewById(R.id.btn_close);
light = (Button) findViewById(R.id.light);
btn_close.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
setResult(RESULT_CANCELED);
onBackPressed();
}
});
light.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
long time = System.currentTimeMillis();// 摄像头 初始化 需要时间
if (time - opentime > 2000) {
opentime = time;
if (!toggleLight) {
toggleLight = true;
tv_lightstate.setText("关闭闪关灯");
cameraManager.openLight();
} else {
toggleLight = false;
tv_lightstate.setText("打开闪关灯");
cameraManager.offLight();
}
}
}
});
// btn_resacn = (Button) findViewById(R.id.btn_rescan);
// btn_resacn.setOnClickListener(new View.OnClickListener() {
// @Override
// public void onClick(View v) {
// times = 0;
// ErrorView.setVisibility(View.GONE);
// }
// });
// tv_input = (TextView) findViewById(R.id.tv_inputbyself);
// tv_input.setOnClickListener(new View.OnClickListener() {
// @Override
// public void onClick(View v) {
// setResult(RESULT_CANCELED);
// onBackPressed();
// }
// });
// iv_close = (ImageView) findViewById(R.id.iv_closetips);
// iv_close.setOnClickListener(new View.OnClickListener() {
// @Override
// public void onClick(View v) {
// times = 0;
// ErrorView.setVisibility(View.GONE);
//
// }
// });
}
@Override
protected void onResume() {
super.onResume();
/**
* 初始化camera
*/
cameraManager = new CameraManager();
SurfaceView surfaceView = (SurfaceView) findViewById(R.id.surfaceview);
SurfaceHolder surfaceHolder = surfaceView.getHolder();
if (hasSurface) {
// activity在paused时但不会stopped,因此surface仍旧存在;
// surfaceCreated()不会调用,因此在这里初始化camera
initCamera(surfaceHolder);
} else {
// 重置callback,等待surfaceCreated()来初始化camera
surfaceHolder.addCallback(this);
}
}
@Override
public void surfaceCreated(SurfaceHolder holder) {
if (!hasSurface) {
hasSurface = true;
initCamera(holder);
}
}
@Override
public void surfaceChanged(SurfaceHolder holder, int format, int width, int height) {
}
@Override
public void surfaceDestroyed(SurfaceHolder holder) {
hasSurface = false;
}
/**
* 初始camera
*
* @param surfaceHolder SurfaceHolder
*/
private void initCamera(SurfaceHolder surfaceHolder) {
if (surfaceHolder == null) {
throw new IllegalStateException("No SurfaceHolder provided");
}
if (cameraManager.isOpen()) {
return;
}
try {
// 打开Camera硬件设备
cameraManager.openDriver(surfaceHolder, this);
// 创建一个handler来打开预览,并抛出一个运行时异常
cameraManager.startPreview(this);
} catch (Exception ioe) {
Log.d("zk", ioe.toString());
}
}
@Override
protected void onPause() {
/**
* 停止camera,是否资源操作
*/
cameraManager.stopPreview();
cameraManager.closeDriver();
if (!hasSurface) {
SurfaceView surfaceView = (SurfaceView) findViewById(R.id.surfaceview);
SurfaceHolder surfaceHolder = surfaceView.getHolder();
surfaceHolder.removeCallback(this);
}
super.onPause();
}
private boolean copyAssetFile() throws Exception {
String dir = sdPath + "/tessdata";
String filePath = sdPath + "/tessdata/eng.traineddata";
File f = new File(dir);
if (f.exists()) {
} else {
f.mkdirs();
}
File dataFile = new File(filePath);
if (dataFile.exists()) {
return true;// 文件存在
} else {
InputStream in = this.getAssets().open("eng.traineddata");
File outFile = new File(filePath);
if (outFile.exists()) {
outFile.delete();
}
OutputStream out = new FileOutputStream(outFile);
byte[] buf = new byte[1024];
int len;
while ((len = in.read(buf)) > 0) {
out.write(buf, 0, len);
}
in.close();
out.close();
}
return false;
}
public String doOcr(Bitmap bitmap) {
bitmap = bitmap.copy(Bitmap.Config.ARGB_8888, true);
baseApi.setImage(bitmap);
String text = baseApi.getUTF8Text();
baseApi.clear();
// baseApi.end();
return text;
}
@Override
public void onBackPressed() {
if (baseApi != null)
baseApi.end();
super.onBackPressed();
}
@Override
public void onPreviewFrame(byte[] data, Camera camera) {
ByteArrayOutputStream baos;
byte[] rawImage;
Bitmap bitmap;
Camera.Size previewSize = camera.getParameters().getPreviewSize();//获取尺寸,格式转换的时候要用到
BitmapFactory.Options newOpts = new BitmapFactory.Options();
newOpts.inJustDecodeBounds = true;
YuvImage yuvimage = new YuvImage(
data,
ImageFormat.NV21,
previewSize.width,
previewSize.height,
null);
baos = new ByteArrayOutputStream();
yuvimage.compressToJpeg(new Rect(0, 0, previewSize.width, previewSize.height), 100, baos);// 80--JPG图片的质量[0-100],100最高
rawImage = baos.toByteArray();
//将rawImage转换成bitmap
BitmapFactory.Options options = new BitmapFactory.Options();
options.inPreferredConfig = Bitmap.Config.RGB_565;
bitmap = BitmapFactory.decodeByteArray(rawImage, 0, rawImage.length, options);
if (bitmap == null) {
Log.d("zka", "bitmap is nlll");
return;
} else {
int height = bitmap.getHeight();
int width = bitmap.getWidth();
final Bitmap bitmap1 = Bitmap.createBitmap(bitmap, (width - height) / 2, height / 6, height, height * 2 / 3);
int x, y, w, h;
x = (int) (bitmap1.getWidth() * 0.340);
y = (int) (bitmap1.getHeight() * 0.800);
w = (int) (bitmap1.getWidth() * 0.6 + 0.5f);
h = (int) (bitmap1.getHeight() * 0.12 + 0.5f);
Bitmap bit_hm = Bitmap.createBitmap(bitmap1, x, y, w, h);
String id = doOcr(bit_hm);
// if (++times > 10)
// ErrorView.setVisibility(View.VISIBLE);
if (id.length() == 18) {
Intent i = new Intent();
i.putExtra("id", id);
setResult(RESULT_OK, i);
onBackPressed();
}
}
}
}
================================================
FILE: app/src/main/java/com/kingsoft/idcardocr_china/idcardocr/CameraManager.java
================================================
package com.kingsoft.idcardocr_china.idcardocr;
import android.content.Context;
import android.hardware.Camera;
import android.hardware.Camera.Size;
import android.util.DisplayMetrics;
import android.util.Log;
import android.view.SurfaceHolder;
import java.io.IOException;
import java.util.List;
public class CameraManager {
private static final String TAG = CameraManager.class.getName();
private Camera camera;
private Camera.Parameters parameters;
private AutoFocusManager autoFocusManager;
private int requestedCameraId = -1;
private boolean initialized;
private boolean previewing;
private Size mPreviewSize;
private List<Size> mSupportedPreviewSizes;
/**
* 打开摄像头
*
* @param cameraId 摄像头id
* @return Camera
*/
public Camera open(int cameraId, Context mContext) {
int nucameras = Camera.getNumberOfCameras();
if (nucameras == 0) {
Log.e(TAG, "No cameras!");
return null;
}
boolean explicitRequest = cameraId >= 0;
if (!explicitRequest) {
// Select a camera if no explicit camera requested
int index = 0;
while (index < nucameras) {
Camera.CameraInfo cameraInfo = new Camera.CameraInfo();
Camera.getCameraInfo(index, cameraInfo);
if (cameraInfo.facing == Camera.CameraInfo.CAMERA_FACING_BACK) {
break;
}
index++;
}
cameraId = index;
}
Camera camera;
if (cameraId < nucameras) {
Log.e(TAG, "Opening camera #" + cameraId);
camera = Camera.open(cameraId);
} else {
if (explicitRequest) {
Log.e(TAG, "Requested camera does not exist: " + cameraId);
camera = null;
} else {
Log.e(TAG, "No camera facing back; returning camera #0");
camera = Camera.open(0);
}
}
mSupportedPreviewSizes = camera.getParameters()
.getSupportedPreviewSizes();
if (mSupportedPreviewSizes != null) {
mPreviewSize = getOptimalPreviewSize(
mSupportedPreviewSizes, getScreenWidth(mContext), getScreenHeight(mContext));
}
Log.d("zkcam", "w=" + getScreenWidth(mContext));
Log.d("zkcam", "h=" + getScreenHeight(mContext));
Camera.Parameters parameters = camera.getParameters();
parameters.setPreviewSize(mPreviewSize.width,
mPreviewSize.height);
Log.d("zkcam", "pw=" + mPreviewSize.width);
Log.d("zkcam", "ph=" + mPreviewSize.height);
camera.setParameters(parameters);
return camera;
}
private Camera.Size getOptimalPreviewSize(List<Size> sizes, int w, int h) {
final double ASPECT_TOLERANCE = 0.2;
double targetRatio = (double) w / h;
if (sizes == null) return null;
Camera.Size optimalSize = null;
double minDiff = Double.MAX_VALUE;
int targetHeight = h;
for (Camera.Size size : sizes) {
double ratio = (double) size.width / size.height;
if (Math.abs(ratio - targetRatio) > ASPECT_TOLERANCE) continue;
if (Math.abs(size.height - targetHeight) < minDiff) {
optimalSize = size;
minDiff = Math.abs(size.height - targetHeight);
}
}
if (optimalSize == null) {
minDiff = Double.MAX_VALUE;
for (Camera.Size size : sizes) {
if (Math.abs(size.height - targetHeight) < minDiff) {
optimalSize = size;
minDiff = Math.abs(size.height - targetHeight);
}
}
}
return optimalSize;
}
/**
* 打开camera
*
* @param holder SurfaceHolder
* @throws IOException IOException
*/
public synchronized void openDriver(SurfaceHolder holder, Context mContext)
throws IOException {
Log.e(TAG, "openDriver");
Camera theCamera = camera;
if (theCamera == null) {
theCamera = open(requestedCameraId, mContext);
if (theCamera == null) {
throw new IOException();
}
camera = theCamera;
}
theCamera.setPreviewDisplay(holder);
// if (!initialized) {
// initialized = true;
// parameters = camera.getParameters();
// parameters.setPreviewSize(800, 600);
// parameters.setPictureFormat(ImageFormat.JPEG);
// parameters.setJpegQuality(100);
// parameters.setPictureSize(800, 600);
//// theCamera.setParameters(parameters);
// }
}
/**
* camera是否打开
*
* @return camera是否打开
*/
public synchronized boolean isOpen() {
return camera != null;
}
/**
* 关闭camera
*/
public synchronized void closeDriver() {
Log.e(TAG, "closeDriver");
if (camera != null) {
camera.release();
camera = null;
}
}
/**
* 开始预览
*/
public synchronized void startPreview(Camera.PreviewCallback mp) {
Log.e(TAG, "startPreview");
Camera theCamera = camera;
if (theCamera != null && !previewing) {
// theCamera.setOneShotPreviewCallback(mp);
theCamera.startPreview();
previewing = true;
autoFocusManager = new AutoFocusManager(camera, mp);
}
// camera.setPreviewCallback(new Camera.PreviewCallback() {
// @Override
// public void onPreviewFrame(byte[] data, Camera camera) {
// Log.d("zka","onPreviewFrame");
// }
// });
}
/**
* 关闭预览
*/
public synchronized void stopPreview() {
Log.e(TAG, "stopPreview");
if (autoFocusManager != null) {
autoFocusManager.stop();
autoFocusManager = null;
}
if (camera != null && previewing) {
camera.stopPreview();
previewing = false;
}
}
/**
* 打开闪光灯
*/
public synchronized void openLight() {
Log.e(TAG, "openLight");
if (camera != null) {
parameters = camera.getParameters();
parameters.setFlashMode(Camera.Parameters.FLASH_MODE_TORCH);
camera.setParameters(parameters);
}
}
/**
* 关闭闪光灯
*/
public synchronized void offLight() {
Log.e(TAG, "offLight");
if (camera != null) {
parameters = camera.getParameters();
parameters.setFlashMode(Camera.Parameters.FLASH_MODE_OFF);
camera.setParameters(parameters);
}
}
/**
* 拍照
*
* @param shutter ShutterCallback
* @param raw PictureCallback
* @param jpeg PictureCallback
*/
public synchronized void takePicture(final Camera.ShutterCallback shutter, final Camera.PictureCallback raw,
final Camera.PictureCallback jpeg) {
camera.takePicture(shutter, raw, jpeg);
}
public int getScreenWidth(Context context) {
DisplayMetrics dm = context.getResources().getDisplayMetrics();
return dm.widthPixels;
}
/**
* 获得屏幕高度
*
* @param context 上下文
* @return 屏幕除去通知栏的高度
*/
public int getScreenHeight(Context context) {
DisplayMetrics dm = context.getResources().getDisplayMetrics();
return dm.heightPixels;
}
}
================================================
FILE: app/src/main/java/com/kingsoft/idcardocr_china/idcardocr/PreviewBorderView.java
================================================
package com.kingsoft.idcardocr_china.idcardocr;
import android.content.Context;
import android.content.res.TypedArray;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.graphics.PixelFormat;
import android.graphics.PorterDuff;
import android.graphics.PorterDuffXfermode;
import android.graphics.RectF;
import android.util.AttributeSet;
import android.util.Log;
import android.util.TypedValue;
import android.view.SurfaceHolder;
import android.view.SurfaceView;
import com.kingsoft.idcardocr_china.R;
public class PreviewBorderView extends SurfaceView implements SurfaceHolder.Callback, Runnable {
private static final String DEFAULT_TIPS_TEXT = "请将身份证照片面置于框内扫描,并尽量对齐边框";
private static final int DEFAULT_TIPS_TEXT_SIZE = 18;
private static final int DEFAULT_TIPS_TEXT_COLOR = Color.GREEN;
private int mScreenH;
private int mScreenW;
private Canvas mCanvas;
private Paint mPaint;
private Paint mPaintLine;
private SurfaceHolder mHolder;
private Thread mThread;
/**
* 自定义属性
*/
private float tipTextSize;
private int tipTextColor;
private String tipText;
public PreviewBorderView(Context context) {
this(context, null);
}
public PreviewBorderView(Context context, AttributeSet attrs) {
this(context, attrs, 0);
}
public PreviewBorderView(Context context, AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
initAttrs(context, attrs);
init();
}
/**
* 初始化自定义属性
*
* @param context Context
* @param attrs AttributeSet
*/
private void initAttrs(Context context, AttributeSet attrs) {
TypedArray a = context.obtainStyledAttributes(attrs, R.styleable.PreviewBorderView);
try {
tipTextSize = a.getDimension(R.styleable.PreviewBorderView_tipTextSize, TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, DEFAULT_TIPS_TEXT_SIZE, getResources().getDisplayMetrics()));
tipTextColor = a.getColor(R.styleable.PreviewBorderView_tipTextColor, DEFAULT_TIPS_TEXT_COLOR);
tipText = a.getString(R.styleable.PreviewBorderView_tipText);
if (tipText == null) {
tipText = DEFAULT_TIPS_TEXT;
}
} finally {
a.recycle();
}
}
/**
* 初始化绘图变量
*/
private void init() {
this.mHolder = getHolder();
this.mHolder.addCallback(this);
this.mHolder.setFormat(PixelFormat.TRANSPARENT);
setZOrderOnTop(true);
setZOrderMediaOverlay(true);
this.mPaint = new Paint();
this.mPaint.setAntiAlias(true);
this.mPaint.setColor(Color.WHITE);
this.mPaint.setStyle(Paint.Style.FILL_AND_STROKE);
this.mPaint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.CLEAR));
this.mPaintLine = new Paint();
this.mPaintLine.setColor(Color.WHITE);
this.mPaintLine.setStrokeWidth(3.0F);
setKeepScreenOn(true);
}
/**
* 绘制取景框
*/
private void draw() {
try {
this.mCanvas = this.mHolder.lockCanvas();
this.mCanvas.drawARGB(100, 0, 0, 0);
// this.mScreenW = (this.mScreenH * 4 / 3);
Log.e("TAG", "mScreenW:" + mScreenW + " mScreenH:" + mScreenH);
this.mCanvas.drawRect(new RectF(this.mScreenW / 2 - this.mScreenH * 2 / 3 + this.mScreenH * 1 / 6, this.mScreenH * 1 / 6, this.mScreenW / 2 + this.mScreenH * 2 / 3 - this.mScreenH * 1 / 6, this.mScreenH - this.mScreenH * 1 / 6), this.mPaint);
this.mCanvas.drawLine(this.mScreenW / 2 - this.mScreenH * 2 / 3 + this.mScreenH * 1 / 6, this.mScreenH * 1 / 6, this.mScreenW / 2 - this.mScreenH * 2 / 3 + this.mScreenH * 1 / 6, this.mScreenH * 1 / 6 + 150, this.mPaintLine);
this.mCanvas.drawLine(this.mScreenW / 2 - this.mScreenH * 2 / 3 + this.mScreenH * 1 / 6, this.mScreenH * 1 / 6, this.mScreenW / 2 - this.mScreenH * 2 / 3 + this.mScreenH * 1 / 6 + 150, this.mScreenH * 1 / 6, this.mPaintLine);
this.mCanvas.drawLine(this.mScreenW / 2 + this.mScreenH * 2 / 3 - this.mScreenH * 1 / 6, this.mScreenH * 1 / 6, this.mScreenW / 2 + this.mScreenH * 2 / 3 - this.mScreenH * 1 / 6, this.mScreenH * 1 / 6 + 150, this.mPaintLine);
this.mCanvas.drawLine(this.mScreenW / 2 + this.mScreenH * 2 / 3 - this.mScreenH * 1 / 6, this.mScreenH * 1 / 6, this.mScreenW / 2 + this.mScreenH * 2 / 3 - this.mScreenH * 1 / 6 - 150, this.mScreenH * 1 / 6, this.mPaintLine);
this.mCanvas.drawLine(this.mScreenW / 2 - this.mScreenH * 2 / 3 + this.mScreenH * 1 / 6, this.mScreenH - this.mScreenH * 1 / 6, this.mScreenW / 2 - this.mScreenH * 2 / 3 + this.mScreenH * 1 / 6, this.mScreenH - this.mScreenH * 1 / 6 - 150, this.mPaintLine);
this.mCanvas.drawLine(this.mScreenW / 2 - this.mScreenH * 2 / 3 + this.mScreenH * 1 / 6, this.mScreenH - this.mScreenH * 1 / 6, this.mScreenW / 2 - this.mScreenH * 2 / 3 + this.mScreenH * 1 / 6 + 150, this.mScreenH - this.mScreenH * 1 / 6, this.mPaintLine);
this.mCanvas.drawLine(this.mScreenW / 2 + this.mScreenH * 2 / 3 - this.mScreenH * 1 / 6, this.mScreenH - this.mScreenH * 1 / 6, this.mScreenW / 2 + this.mScreenH * 2 / 3 - this.mScreenH * 1 / 6, this.mScreenH - this.mScreenH * 1 / 6 - 150, this.mPaintLine);
this.mCanvas.drawLine(this.mScreenW / 2 + this.mScreenH * 2 / 3 - this.mScreenH * 1 / 6, this.mScreenH - this.mScreenH * 1 / 6, this.mScreenW / 2 + this.mScreenH * 2 / 3 - this.mScreenH * 1 / 6 - 150, this.mScreenH - this.mScreenH * 1 / 6, this.mPaintLine);
mPaintLine.setTextSize(tipTextSize);
mPaintLine.setAntiAlias(true);
mPaintLine.setDither(true);
float length = mPaintLine.measureText(tipText);
this.mCanvas.drawText(tipText, this.mScreenW / 2 - this.mScreenH * 2 / 3 + this.mScreenH * 1 / 6 + this.mScreenH / 2 - length / 2, this.mScreenH * 1 / 2 - tipTextSize, mPaintLine);
Log.e("TAG", "left:" + (this.mScreenW / 2 - this.mScreenH * 2 / 3 + this.mScreenH * 1 / 6));
Log.e("TAG", "top:" + (this.mScreenH * 1 / 6));
Log.e("TAG", "right:" + (this.mScreenW / 2 + this.mScreenH * 2 / 3 - this.mScreenH * 1 / 6));
Log.e("TAG", "bottom:" + (this.mScreenH - this.mScreenH * 1 / 6));
} catch (Exception e) {
e.printStackTrace();
} finally {
if (this.mCanvas != null) {
this.mHolder.unlockCanvasAndPost(this.mCanvas);
}
}
}
@Override
public void surfaceCreated(SurfaceHolder holder) {
//获得宽高,开启子线程绘图
this.mScreenW = getWidth();
this.mScreenH = getHeight();
this.mThread = new Thread(this);
this.mThread.start();
}
@Override
public void surfaceChanged(SurfaceHolder holder, int format, int width, int height) {
}
@Override
public void surfaceDestroyed(SurfaceHolder holder) {
//停止线程
try {
mThread.interrupt();
mThread = null;
} catch (Exception e) {
e.printStackTrace();
}
}
@Override
public void run() {
//子线程绘图
draw();
}
}
================================================
FILE: app/src/main/res/layout/activity_camera.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="fill_parent"
android:layout_height="fill_parent">
<SurfaceView
android:id="@+id/surfaceview"
android:layout_width="wrap_content"
android:layout_height="wrap_content"/>
<com.kingsoft.idcardocr_china.idcardocr.PreviewBorderView
xmlns:app="http://schemas.android.com/apk/res-auto"
android:id="@+id/borderview"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentLeft="true"
android:layout_centerHorizontal="true"
android:layout_centerInParent="true"
app:tipTextSize="16dp"
/>
<Button
android:id="@+id/btn_close"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginLeft="10dp"
android:layout_marginTop="10dp"
android:background="@mipmap/carmer_back"/>
<LinearLayout
android:id="@+id/linearlaout"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentRight="true"
android:layout_marginRight="10dp"
android:layout_marginTop="10dp"
android:gravity="center"
android:orientation="vertical">
<Button
android:id="@+id/light"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:background="@mipmap/open_falshlight"
android:textColor="#ffffffff"/>
<TextView
android:id="@+id/tv_openlight"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="打开闪光灯"
android:textColor="#ffffffff"/>
</LinearLayout>
</RelativeLayout>
================================================
FILE: app/src/main/res/layout/activity_main.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:id="@+id/activity_main"
android:orientation="vertical"
android:layout_width="match_parent"
android:layout_height="match_parent">
<Button
android:id="@+id/btn_go"
android:layout_marginTop="20dp"
android:textSize="20sp"
android:text="开始扫描"
android:layout_width="match_parent"
android:layout_height="wrap_content"/>
<TextView
android:id="@+id/tv_id"
android:textSize="20sp"
android:layout_marginTop="20dp"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="身份证号:"/>
</LinearLayout>
================================================
FILE: app/src/main/res/values/attrs.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<resources>
<declare-styleable name="CircleImageView">
<attr name="border_width" format="dimension" />
<attr name="border_color" format="color" />
</declare-styleable>
<declare-styleable name="PreviewBorderView">
<attr name="tipText" format="string"/>
<attr name="tipTextColor" format="color|reference"/>
<attr name="tipTextSize" format="dimension"/>
</declare-styleable>
</resources>
================================================
FILE: app/src/main/res/values/colors.xml
================================================
<?xml version="1.0" encoding="utf-8"?>
<resources>
<color name="colorPrimary">#3F51B5</color>
<color name="colorPrimaryDark">#303F9F</color>
<color name="colorAccent">#FF4081</color>
</resources>
================================================
FILE: app/src/main/res/values/dimens.xml
================================================
<resources>
<!-- Default screen margins, per the Android Design guidelines. -->
<dimen name="activity_horizontal_margin">16dp</dimen>
<dimen name="activity_vertical_margin">16dp</dimen>
</resources>
================================================
FILE: app/src/main/res/values/strings.xml
================================================
<resources>
<string name="app_name">IDCardOCR_China</string>
</resources>
================================================
FILE: app/src/main/res/values/styles.xml
================================================
<resources>
<!-- Base application theme. -->
<style name="AppTheme" parent="Theme.AppCompat.Light.DarkActionBar">
<!-- Customize your theme here. -->
<item name="colorPrimary">@color/colorPrimary</item>
<item name="colorPrimaryDark">@color/colorPrimaryDark</item>
<item name="colorAccent">@color/colorAccent</item>
</style>
</resources>
================================================
FILE: app/src/main/res/values-w820dp/dimens.xml
================================================
<resources>
<!-- Example customization of dimensions originally defined in res/values/dimens.xml
(such as screen margins) for screens with more than 820dp of available width. This
would include 7" and 10" devices in landscape (~960dp and ~1280dp respectively). -->
<dimen name="activity_horizontal_margin">64dp</dimen>
</resources>
================================================
FILE: app/src/test/java/com/kingsoft/idcardocr_china/ExampleUnitTest.java
================================================
package com.kingsoft.idcardocr_china;
import org.junit.Test;
import static org.junit.Assert.*;
/**
* Example local unit test, which will execute on the development machine (host).
*
* @see <a href="http://d.android.com/tools/testing">Testing documentation</a>
*/
public class ExampleUnitTest {
@Test
public void addition_isCorrect() throws Exception {
assertEquals(4, 2 + 2);
}
}
================================================
FILE: build.gradle
================================================
// Top-level build file where you can add configuration options common to all sub-projects/modules.
buildscript {
repositories {
jcenter()
}
dependencies {
classpath 'com.android.tools.build:gradle:2.2.3'
// NOTE: Do not place your application dependencies here; they belong
// in the individual module build.gradle files
}
}
allprojects {
repositories {
jcenter()
}
}
task clean(type: Delete) {
delete rootProject.buildDir
}
================================================
FILE: gradle/wrapper/gradle-wrapper.properties
================================================
#Mon Dec 28 10:00:20 PST 2015
distributionBase=GRADLE_USER_HOME
distributionPath=wrapper/dists
zipStoreBase=GRADLE_USER_HOME
zipStorePath=wrapper/dists
distributionUrl=https\://services.gradle.org/distributions/gradle-2.14.1-all.zip
================================================
FILE: gradle.properties
================================================
# Project-wide Gradle settings.
# IDE (e.g. Android Studio) users:
# Gradle settings configured through the IDE *will override*
# any settings specified in this file.
# For more details on how to configure your build environment visit
# http://www.gradle.org/docs/current/userguide/build_environment.html
# Specifies the JVM arguments used for the daemon process.
# The setting is particularly useful for tweaking memory settings.
org.gradle.jvmargs=-Xmx1536m
# When configured, Gradle will run in incubating parallel mode.
# This option should only be used with decoupled projects. More details, visit
# http://www.gradle.org/docs/current/userguide/multi_project_builds.html#sec:decoupled_projects
# org.gradle.parallel=true
================================================
FILE: gradlew
================================================
#!/usr/bin/env bash
##############################################################################
##
## Gradle start up script for UN*X
##
##############################################################################
# Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.
DEFAULT_JVM_OPTS=""
APP_NAME="Gradle"
APP_BASE_NAME=`basename "$0"`
# Use the maximum available, or set MAX_FD != -1 to use that value.
MAX_FD="maximum"
warn ( ) {
echo "$*"
}
die ( ) {
echo
echo "$*"
echo
exit 1
}
# OS specific support (must be 'true' or 'false').
cygwin=false
msys=false
darwin=false
case "`uname`" in
CYGWIN* )
cygwin=true
;;
Darwin* )
darwin=true
;;
MINGW* )
msys=true
;;
esac
# Attempt to set APP_HOME
# Resolve links: $0 may be a link
PRG="$0"
# Need this for relative symlinks.
while [ -h "$PRG" ] ; do
ls=`ls -ld "$PRG"`
link=`expr "$ls" : '.*-> \(.*\)$'`
if expr "$link" : '/.*' > /dev/null; then
PRG="$link"
else
PRG=`dirname "$PRG"`"/$link"
fi
done
SAVED="`pwd`"
cd "`dirname \"$PRG\"`/" >/dev/null
APP_HOME="`pwd -P`"
cd "$SAVED" >/dev/null
CLASSPATH=$APP_HOME/gradle/wrapper/gradle-wrapper.jar
# Determine the Java command to use to start the JVM.
if [ -n "$JAVA_HOME" ] ; then
if [ -x "$JAVA_HOME/jre/sh/java" ] ; then
# IBM's JDK on AIX uses strange locations for the executables
JAVACMD="$JAVA_HOME/jre/sh/java"
else
JAVACMD="$JAVA_HOME/bin/java"
fi
if [ ! -x "$JAVACMD" ] ; then
die "ERROR: JAVA_HOME is set to an invalid directory: $JAVA_HOME
Please set the JAVA_HOME variable in your environment to match the
location of your Java installation."
fi
else
JAVACMD="java"
which java >/dev/null 2>&1 || die "ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH.
Please set the JAVA_HOME variable in your environment to match the
location of your Java installation."
fi
# Increase the maximum file descriptors if we can.
if [ "$cygwin" = "false" -a "$darwin" = "false" ] ; then
MAX_FD_LIMIT=`ulimit -H -n`
if [ $? -eq 0 ] ; then
if [ "$MAX_FD" = "maximum" -o "$MAX_FD" = "max" ] ; then
MAX_FD="$MAX_FD_LIMIT"
fi
ulimit -n $MAX_FD
if [ $? -ne 0 ] ; then
warn "Could not set maximum file descriptor limit: $MAX_FD"
fi
else
warn "Could not query maximum file descriptor limit: $MAX_FD_LIMIT"
fi
fi
# For Darwin, add options to specify how the application appears in the dock
if $darwin; then
GRADLE_OPTS="$GRADLE_OPTS \"-Xdock:name=$APP_NAME\" \"-Xdock:icon=$APP_HOME/media/gradle.icns\""
fi
# For Cygwin, switch paths to Windows format before running java
if $cygwin ; then
APP_HOME=`cygpath --path --mixed "$APP_HOME"`
CLASSPATH=`cygpath --path --mixed "$CLASSPATH"`
JAVACMD=`cygpath --unix "$JAVACMD"`
# We build the pattern for arguments to be converted via cygpath
ROOTDIRSRAW=`find -L / -maxdepth 1 -mindepth 1 -type d 2>/dev/null`
SEP=""
for dir in $ROOTDIRSRAW ; do
ROOTDIRS="$ROOTDIRS$SEP$dir"
SEP="|"
done
OURCYGPATTERN="(^($ROOTDIRS))"
# Add a user-defined pattern to the cygpath arguments
if [ "$GRADLE_CYGPATTERN" != "" ] ; then
OURCYGPATTERN="$OURCYGPATTERN|($GRADLE_CYGPATTERN)"
fi
# Now convert the arguments - kludge to limit ourselves to /bin/sh
i=0
for arg in "$@" ; do
CHECK=`echo "$arg"|egrep -c "$OURCYGPATTERN" -`
CHECK2=`echo "$arg"|egrep -c "^-"` ### Determine if an option
if [ $CHECK -ne 0 ] && [ $CHECK2 -eq 0 ] ; then ### Added a condition
eval `echo args$i`=`cygpath --path --ignore --mixed "$arg"`
else
eval `echo args$i`="\"$arg\""
fi
i=$((i+1))
done
case $i in
(0) set -- ;;
(1) set -- "$args0" ;;
(2) set -- "$args0" "$args1" ;;
(3) set -- "$args0" "$args1" "$args2" ;;
(4) set -- "$args0" "$args1" "$args2" "$args3" ;;
(5) set -- "$args0" "$args1" "$args2" "$args3" "$args4" ;;
(6) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" ;;
(7) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" ;;
(8) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" "$args7" ;;
(9) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" "$args7" "$args8" ;;
esac
fi
# Split up the JVM_OPTS And GRADLE_OPTS values into an array, following the shell quoting and substitution rules
function splitJvmOpts() {
JVM_OPTS=("$@")
}
eval splitJvmOpts $DEFAULT_JVM_OPTS $JAVA_OPTS $GRADLE_OPTS
JVM_OPTS[${#JVM_OPTS[*]}]="-Dorg.gradle.appname=$APP_BASE_NAME"
exec "$JAVACMD" "${JVM_OPTS[@]}" -classpath "$CLASSPATH" org.gradle.wrapper.GradleWrapperMain "$@"
================================================
FILE: gradlew.bat
================================================
@if "%DEBUG%" == "" @echo off
@rem ##########################################################################
@rem
@rem Gradle startup script for Windows
@rem
@rem ##########################################################################
@rem Set local scope for the variables with windows NT shell
if "%OS%"=="Windows_NT" setlocal
@rem Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.
set DEFAULT_JVM_OPTS=
set DIRNAME=%~dp0
if "%DIRNAME%" == "" set DIRNAME=.
set APP_BASE_NAME=%~n0
set APP_HOME=%DIRNAME%
@rem Find java.exe
if defined JAVA_HOME goto findJavaFromJavaHome
set JAVA_EXE=java.exe
%JAVA_EXE% -version >NUL 2>&1
if "%ERRORLEVEL%" == "0" goto init
echo.
echo ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH.
echo.
echo Please set the JAVA_HOME variable in your environment to match the
echo location of your Java installation.
goto fail
:findJavaFromJavaHome
set JAVA_HOME=%JAVA_HOME:"=%
set JAVA_EXE=%JAVA_HOME%/bin/java.exe
if exist "%JAVA_EXE%" goto init
echo.
echo ERROR: JAVA_HOME is set to an invalid directory: %JAVA_HOME%
echo.
echo Please set the JAVA_HOME variable in your environment to match the
echo location of your Java installation.
goto fail
:init
@rem Get command-line arguments, handling Windowz variants
if not "%OS%" == "Windows_NT" goto win9xME_args
if "%@eval[2+2]" == "4" goto 4NT_args
:win9xME_args
@rem Slurp the command line arguments.
set CMD_LINE_ARGS=
set _SKIP=2
:win9xME_args_slurp
if "x%~1" == "x" goto execute
set CMD_LINE_ARGS=%*
goto execute
:4NT_args
@rem Get arguments from the 4NT Shell from JP Software
set CMD_LINE_ARGS=%$
:execute
@rem Setup the command line
set CLASSPATH=%APP_HOME%\gradle\wrapper\gradle-wrapper.jar
@rem Execute Gradle
"%JAVA_EXE%" %DEFAULT_JVM_OPTS% %JAVA_OPTS% %GRADLE_OPTS% "-Dorg.gradle.appname=%APP_BASE_NAME%" -classpath "%CLASSPATH%" org.gradle.wrapper.GradleWrapperMain %CMD_LINE_ARGS%
:end
@rem End local scope for the variables with windows NT shell
if "%ERRORLEVEL%"=="0" goto mainEnd
:fail
rem Set variable GRADLE_EXIT_CONSOLE if you need the _script_ return code instead of
rem the _cmd.exe /c_ return code!
if not "" == "%GRADLE_EXIT_CONSOLE%" exit 1
exit /b 1
:mainEnd
if "%OS%"=="Windows_NT" endlocal
:omega
================================================
FILE: settings.gradle
================================================
include ':app'
gitextract_pqg52avl/ ├── .idea/ │ ├── compiler.xml │ ├── copyright/ │ │ └── profiles_settings.xml │ ├── encodings.xml │ ├── gradle.xml │ ├── misc.xml │ ├── modules.xml │ ├── runConfigurations.xml │ └── vcs.xml ├── README.md ├── app/ │ ├── assets/ │ │ └── eng.traineddata │ ├── build.gradle │ ├── proguard-rules.pro │ └── src/ │ ├── androidTest/ │ │ └── java/ │ │ └── com/ │ │ └── kingsoft/ │ │ └── idcardocr_china/ │ │ └── ExampleInstrumentedTest.java │ ├── main/ │ │ ├── AndroidManifest.xml │ │ ├── java/ │ │ │ └── com/ │ │ │ └── kingsoft/ │ │ │ └── idcardocr_china/ │ │ │ ├── MainActivity.java │ │ │ └── idcardocr/ │ │ │ ├── AutoFocusManager.java │ │ │ ├── CameraActivity.java │ │ │ ├── CameraManager.java │ │ │ └── PreviewBorderView.java │ │ └── res/ │ │ ├── layout/ │ │ │ ├── activity_camera.xml │ │ │ └── activity_main.xml │ │ ├── values/ │ │ │ ├── attrs.xml │ │ │ ├── colors.xml │ │ │ ├── dimens.xml │ │ │ ├── strings.xml │ │ │ └── styles.xml │ │ └── values-w820dp/ │ │ └── dimens.xml │ └── test/ │ └── java/ │ └── com/ │ └── kingsoft/ │ └── idcardocr_china/ │ └── ExampleUnitTest.java ├── build.gradle ├── gradle/ │ └── wrapper/ │ ├── gradle-wrapper.jar │ └── gradle-wrapper.properties ├── gradle.properties ├── gradlew ├── gradlew.bat └── settings.gradle
SYMBOL INDEX (57 symbols across 7 files)
FILE: app/src/androidTest/java/com/kingsoft/idcardocr_china/ExampleInstrumentedTest.java
class ExampleInstrumentedTest (line 17) | @RunWith(AndroidJUnit4.class)
method useAppContext (line 19) | @Test
FILE: app/src/main/java/com/kingsoft/idcardocr_china/MainActivity.java
class MainActivity (line 17) | public class MainActivity extends AppCompatActivity {
method onCreate (line 25) | @Override
method requestAllPermission (line 40) | private void requestAllPermission() {
method onRequestPermissionsResult (line 56) | @Override
method onActivityResult (line 62) | @Override
class MyHandler (line 75) | private class MyHandler extends Handler {
method handleMessage (line 76) | @Override
FILE: app/src/main/java/com/kingsoft/idcardocr_china/idcardocr/AutoFocusManager.java
class AutoFocusManager (line 12) | public class AutoFocusManager implements Camera.AutoFocusCallback{
method AutoFocusManager (line 28) | public AutoFocusManager(Camera camera, Camera.PreviewCallback mp) {
method onAutoFocus (line 37) | @Override
method autoFocusAgainLater (line 49) | private synchronized void autoFocusAgainLater() {
method start (line 64) | public synchronized void start() {
method cancelOutstandingTask (line 87) | private synchronized void cancelOutstandingTask() {
method stop (line 99) | public synchronized void stop() {
class AutoFocusTask (line 114) | private final class AutoFocusTask extends AsyncTask<Object,Object,Obje...
method doInBackground (line 115) | @Override
FILE: app/src/main/java/com/kingsoft/idcardocr_china/idcardocr/CameraActivity.java
class CameraActivity (line 31) | public class CameraActivity extends Activity implements SurfaceHolder.Ca...
method onCreate (line 49) | @Override
method initLayoutParams (line 73) | private void initLayoutParams() {
method onResume (line 133) | @Override
method surfaceCreated (line 153) | @Override
method surfaceChanged (line 161) | @Override
method surfaceDestroyed (line 166) | @Override
method initCamera (line 176) | private void initCamera(SurfaceHolder surfaceHolder) {
method onPause (line 194) | @Override
method copyAssetFile (line 209) | private boolean copyAssetFile() throws Exception {
method doOcr (line 242) | public String doOcr(Bitmap bitmap) {
method onBackPressed (line 252) | @Override
method onPreviewFrame (line 259) | @Override
FILE: app/src/main/java/com/kingsoft/idcardocr_china/idcardocr/CameraManager.java
class CameraManager (line 13) | public class CameraManager {
method open (line 32) | public Camera open(int cameraId, Context mContext) {
method getOptimalPreviewSize (line 82) | private Camera.Size getOptimalPreviewSize(List<Size> sizes, int w, int...
method openDriver (line 122) | public synchronized void openDriver(SurfaceHolder holder, Context mCon...
method isOpen (line 151) | public synchronized boolean isOpen() {
method closeDriver (line 158) | public synchronized void closeDriver() {
method startPreview (line 169) | public synchronized void startPreview(Camera.PreviewCallback mp) {
method stopPreview (line 189) | public synchronized void stopPreview() {
method openLight (line 204) | public synchronized void openLight() {
method offLight (line 216) | public synchronized void offLight() {
method takePicture (line 232) | public synchronized void takePicture(final Camera.ShutterCallback shut...
method getScreenWidth (line 240) | public int getScreenWidth(Context context) {
method getScreenHeight (line 251) | public int getScreenHeight(Context context) {
FILE: app/src/main/java/com/kingsoft/idcardocr_china/idcardocr/PreviewBorderView.java
class PreviewBorderView (line 21) | public class PreviewBorderView extends SurfaceView implements SurfaceHol...
method PreviewBorderView (line 39) | public PreviewBorderView(Context context) {
method PreviewBorderView (line 43) | public PreviewBorderView(Context context, AttributeSet attrs) {
method PreviewBorderView (line 47) | public PreviewBorderView(Context context, AttributeSet attrs, int defS...
method initAttrs (line 59) | private void initAttrs(Context context, AttributeSet attrs) {
method init (line 78) | private void init() {
method draw (line 98) | private void draw() {
method surfaceCreated (line 134) | @Override
method surfaceChanged (line 143) | @Override
method surfaceDestroyed (line 148) | @Override
method run (line 159) | @Override
FILE: app/src/test/java/com/kingsoft/idcardocr_china/ExampleUnitTest.java
class ExampleUnitTest (line 12) | public class ExampleUnitTest {
method addition_isCorrect (line 13) | @Test
Condensed preview — 35 files, each showing path, character count, and a content snippet. Download the .json file or copy for the full structured content (63K chars).
[
{
"path": ".idea/compiler.xml",
"chars": 686,
"preview": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<project version=\"4\">\n <component name=\"CompilerConfiguration\">\n <resourceExt"
},
{
"path": ".idea/copyright/profiles_settings.xml",
"chars": 74,
"preview": "<component name=\"CopyrightManager\">\n <settings default=\"\" />\n</component>"
},
{
"path": ".idea/encodings.xml",
"chars": 159,
"preview": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<project version=\"4\">\n <component name=\"Encoding\">\n <file url=\"PROJECT\" chars"
},
{
"path": ".idea/gradle.xml",
"chars": 626,
"preview": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<project version=\"4\">\n <component name=\"GradleSettings\">\n <option name=\"linke"
},
{
"path": ".idea/misc.xml",
"chars": 4462,
"preview": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<project version=\"4\">\n <component name=\"EntryPointsManager\">\n <entry_points v"
},
{
"path": ".idea/modules.xml",
"chars": 367,
"preview": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<project version=\"4\">\n <component name=\"ProjectModuleManager\">\n <modules>\n "
},
{
"path": ".idea/runConfigurations.xml",
"chars": 564,
"preview": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<project version=\"4\">\n <component name=\"RunConfigurationProducerService\">\n <o"
},
{
"path": ".idea/vcs.xml",
"chars": 180,
"preview": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<project version=\"4\">\n <component name=\"VcsDirectoryMappings\">\n <mapping dire"
},
{
"path": "README.md",
"chars": 607,
"preview": "# IDCardOCR_China\n基于tesseract,实现摄像头扫描识别中国二代身份证\n# Usage\ndemo主要提供思路,通过摄像头取景,预览裁剪,ocr识别.\n# ScreenShots\n  users:\n# Gradle settings configured through the IDE *will o"
},
{
"path": "gradlew",
"chars": 4971,
"preview": "#!/usr/bin/env bash\n\n##############################################################################\n##\n## Gradle start "
},
{
"path": "gradlew.bat",
"chars": 2314,
"preview": "@if \"%DEBUG%\" == \"\" @echo off\n@rem ##########################################################################\n@rem\n@rem "
},
{
"path": "settings.gradle",
"chars": 15,
"preview": "include ':app'\n"
}
]
// ... and 2 more files (download for full content)
About this extraction
This page contains the full source code of the 465857721/IDCardOCR_China GitHub repository, extracted and formatted as plain text for AI agents and large language models (LLMs). The extraction includes 35 files (55.5 KB), approximately 15.2k tokens, and a symbol index with 57 extracted functions, classes, methods, constants, and types. Use this with OpenClaw, Claude, ChatGPT, Cursor, Windsurf, or any other AI tool that accepts text input. You can copy the full output to your clipboard or download it as a .txt file.
Extracted by GitExtract — free GitHub repo to text converter for AI. Built by Nikandr Surkov.