├── .gitignore
├── .gitignore~
├── README.md
├── app
├── .gitignore
├── build.gradle
├── proguard-rules.pro
├── release
│ └── output.json
└── src
│ ├── main
│ ├── AndroidManifest.xml
│ ├── ic_launcher-web.png
│ ├── java
│ │ └── com
│ │ │ └── peerbits
│ │ │ └── nfccardread
│ │ │ ├── NFCCardReading.java
│ │ │ ├── NFCPayActivity.java
│ │ │ ├── NFCRead.java
│ │ │ ├── NFCWrite.java
│ │ │ ├── NfcHome.java
│ │ │ └── SplashActivity.java
│ └── res
│ │ ├── anim
│ │ └── swinging.xml
│ │ ├── drawable-hdpi
│ │ ├── bg_card.png
│ │ ├── bg_home.png
│ │ ├── bg_splash.png
│ │ ├── ic_back.png
│ │ ├── ic_card_chip.png
│ │ ├── ic_card_reader.png
│ │ ├── ic_home.png
│ │ ├── ic_launcher.png
│ │ ├── ic_read_nfc.png
│ │ ├── ic_splash.png
│ │ ├── ic_write_nfc.png
│ │ ├── img_card.png
│ │ ├── img_card_read.png
│ │ └── img_card_write.png
│ │ ├── drawable-ldpi
│ │ ├── bg_card.png
│ │ ├── bg_home.png
│ │ ├── ic_back.png
│ │ ├── ic_card_chip.png
│ │ ├── ic_card_reader.png
│ │ ├── ic_home.png
│ │ ├── ic_launcher.png
│ │ ├── ic_read_nfc.png
│ │ ├── ic_splash.png
│ │ ├── ic_write_nfc.png
│ │ ├── img_card.png
│ │ ├── img_card_read.png
│ │ └── img_card_write.png
│ │ ├── drawable-mdpi
│ │ ├── bg_card.png
│ │ ├── bg_splash.png
│ │ ├── ic_back.png
│ │ ├── ic_card_chip.png
│ │ ├── ic_card_reader.png
│ │ ├── ic_home.png
│ │ ├── ic_launcher.png
│ │ ├── ic_read_nfc.png
│ │ ├── ic_splash.png
│ │ ├── ic_write_nfc.png
│ │ ├── img_card.png
│ │ ├── img_card_read.png
│ │ └── img_card_write.png
│ │ ├── drawable-nodpi
│ │ ├── button_background.xml
│ │ ├── button_press.xml
│ │ ├── gif_card.gif
│ │ ├── gif_read.gif
│ │ ├── gif_sucess.gif
│ │ ├── gif_write.gif
│ │ ├── ic_nfc.png
│ │ ├── img_tag_reader.png
│ │ └── nfc_write_img.png
│ │ ├── drawable-xhdpi
│ │ ├── bg_card.png
│ │ ├── bg_home.png
│ │ ├── bg_splash.png
│ │ ├── ic_back.png
│ │ ├── ic_card_chip.png
│ │ ├── ic_card_reader.png
│ │ ├── ic_home.png
│ │ ├── ic_launcher.png
│ │ ├── ic_read_nfc.png
│ │ ├── ic_splash.png
│ │ ├── ic_write_nfc.png
│ │ ├── img_card.png
│ │ ├── img_card_read.png
│ │ └── img_card_write.png
│ │ ├── drawable-xxhdpi
│ │ ├── bg_card.png
│ │ ├── bg_home.png
│ │ ├── bg_splash.png
│ │ ├── ic_back.png
│ │ ├── ic_card_chip.png
│ │ ├── ic_card_reader.png
│ │ ├── ic_home.png
│ │ ├── ic_launcher.png
│ │ ├── ic_read_nfc.png
│ │ ├── ic_splash.png
│ │ ├── ic_write_nfc.png
│ │ ├── img_card.png
│ │ ├── img_card_read.png
│ │ └── img_card_write.png
│ │ ├── drawable-xxxhdpi
│ │ ├── bg_card.png
│ │ ├── bg_home.png
│ │ ├── bg_splash.png
│ │ ├── ic_back.png
│ │ ├── ic_card_chip.png
│ │ ├── ic_card_reader.png
│ │ ├── ic_home.png
│ │ ├── ic_launcher.png
│ │ ├── ic_read_nfc.png
│ │ ├── ic_splash.png
│ │ ├── ic_write_nfc.png
│ │ ├── img_card.png
│ │ ├── img_card_read.png
│ │ └── img_card_write.png
│ │ ├── drawable
│ │ └── card_bg.xml
│ │ ├── layout
│ │ ├── nfc_cardread.xml
│ │ ├── nfc_home.xml
│ │ ├── nfc_pay.xml
│ │ ├── nfc_read.xml
│ │ ├── nfc_write.xml
│ │ └── splash.xml
│ │ ├── mipmap-hdpi
│ │ ├── master_logo.png
│ │ └── visa_logo.png
│ │ ├── mipmap-mdpi
│ │ ├── master_logo.png
│ │ └── visa_logo.png
│ │ ├── mipmap-xhdpi
│ │ ├── master_logo.png
│ │ └── visa_logo.png
│ │ ├── mipmap-xxhdpi
│ │ ├── master_logo.png
│ │ └── visa_logo.png
│ │ ├── mipmap-xxxhdpi
│ │ ├── master_logo.png
│ │ └── visa_logo.png
│ │ ├── values-v21
│ │ └── styles.xml
│ │ ├── values-w820dp
│ │ └── dimens.xml
│ │ ├── values
│ │ ├── colors.xml
│ │ ├── dimens.xml
│ │ ├── strings.xml
│ │ └── styles.xml
│ │ └── xml
│ │ └── nfc_tech_filter.xml
│ └── test
│ └── java
│ └── com
│ └── peerbits
│ └── nfccardread
│ └── ExampleUnitTest.java
├── build.gradle
├── creditCardNfcReader
├── .gitignore
├── build.gradle
├── libs
│ ├── bit-lib4j-1.4.12.jar
│ ├── commons-collections4-4.0.jar
│ └── commons-lang3-3.0.jar
├── proguard-rules.pro
└── src
│ └── main
│ ├── AndroidManifest.xml
│ ├── java
│ └── com
│ │ └── peerbits
│ │ └── creditCardNfcReader
│ │ ├── CardNfcAsyncTask.java
│ │ ├── enums
│ │ ├── CommandEnum.java
│ │ ├── EmvCardScheme.java
│ │ ├── SwEnum.java
│ │ ├── TagTypeEnum.java
│ │ └── TagValueTypeEnum.java
│ │ ├── exception
│ │ ├── CommunicationException.java
│ │ └── TlvException.java
│ │ ├── iso7816emv
│ │ ├── ByteArrayWrapper.java
│ │ ├── EmvTags.java
│ │ ├── EmvTerminal.java
│ │ ├── ITag.java
│ │ ├── TLV.java
│ │ ├── TagAndLength.java
│ │ ├── TerminalTransactionQualifiers.java
│ │ └── impl
│ │ │ └── TagImpl.java
│ │ ├── model
│ │ ├── AbstractData.java
│ │ ├── Afl.java
│ │ ├── EmvCard.java
│ │ ├── EmvTransactionRecord.java
│ │ ├── Service.java
│ │ └── enums
│ │ │ ├── CountryCodeEnum.java
│ │ │ ├── CurrencyEnum.java
│ │ │ ├── IKeyEnum.java
│ │ │ ├── ServiceCode1Enum.java
│ │ │ ├── ServiceCode2Enum.java
│ │ │ ├── ServiceCode3Enum.java
│ │ │ └── TransactionTypeEnum.java
│ │ ├── parser
│ │ ├── EmvParser.java
│ │ ├── IProvider.java
│ │ └── apdu
│ │ │ ├── IFile.java
│ │ │ ├── annotation
│ │ │ ├── AnnotationData.java
│ │ │ ├── AnnotationUtils.java
│ │ │ └── Data.java
│ │ │ └── impl
│ │ │ ├── AbstractByteBean.java
│ │ │ └── DataFactory.java
│ │ └── utils
│ │ ├── AtrUtils.java
│ │ ├── BytesUtils.java
│ │ ├── CardNfcUtils.java
│ │ ├── CommandApdu.java
│ │ ├── EnumUtils.java
│ │ ├── Provider.java
│ │ ├── ResponseUtils.java
│ │ ├── TlvUtil.java
│ │ └── TrackUtils.java
│ └── res
│ ├── values
│ └── strings.xml
│ └── xml
│ └── nfc_tech_filter.xml
├── dotlib
├── .gitignore
├── build.gradle
├── proguard-rules.pro
└── src
│ ├── androidTest
│ └── java
│ │ └── com
│ │ └── bhargavms
│ │ └── dotloader
│ │ └── ApplicationTest.java
│ ├── main
│ ├── AndroidManifest.xml
│ ├── java
│ │ └── com
│ │ │ └── bhargavms
│ │ │ └── dotloader
│ │ │ ├── AnimationRepeater.java
│ │ │ ├── CubicBezierInterpolator.java
│ │ │ ├── Dot.java
│ │ │ └── DotLoader.java
│ └── res
│ │ └── values
│ │ ├── attrs.xml
│ │ └── strings.xml
│ └── test
│ └── java
│ └── com
│ └── bhargavms
│ └── dotloader
│ └── ExampleUnitTest.java
├── gradle.properties
├── gradle
└── wrapper
│ ├── gradle-wrapper.jar
│ └── gradle-wrapper.properties
├── gradlew
├── gradlew.bat
├── screenshots
├── Screenshot_20160428-122024.png
├── Screenshot_20160428-122036.png
└── Screenshot_20160428-122045.png
└── settings.gradle
/.gitignore:
--------------------------------------------------------------------------------
1 | #built application files
2 | *.apk
3 | *.ap_
4 |
5 | # files for the dex VM
6 | *.dex
7 |
8 | # Java class files
9 | *.class
10 |
11 | # generated files
12 | bin/
13 | gen/
14 |
15 | # Local configuration file (sdk path, etc)
16 | local.properties
17 |
18 | # Windows thumbnail db
19 | Thumbs.db
20 |
21 | # OSX files
22 | .DS_Store
23 |
24 | # Eclipse project files
25 | .classpath
26 | .project
27 |
28 | # Android Studio
29 | *.iml
30 | .idea
31 | #.idea/workspace.xml - remove # and delete .idea if it better suit your needs.
32 | .gradle
33 | build/
34 |
35 | #NDK
36 | obj/
37 |
--------------------------------------------------------------------------------
/.gitignore~:
--------------------------------------------------------------------------------
1 | # Directories #
2 | /build/
3 | */bin/*
4 | */gen/*
5 | */target/*
6 | target/*
7 | target/*.pom
8 | target/*.asc
9 | */proguard/*
10 |
11 | # OS Files #
12 | .DS_Store
13 |
14 | *.class
15 |
16 | # Package Files #
17 | *.war
18 | *.ear
19 | *.db
20 |
21 | ######################
22 | # Windows
23 | ######################
24 |
25 | # Windows image file caches
26 | Thumbs.db
27 |
28 | # Folder config file
29 | Desktop.ini
30 |
31 | ######################
32 | # OSX
33 | ######################
34 |
35 | .DS_Store
36 | .svn
37 |
38 | # Thumbnails
39 | ._*
40 |
41 | # Files that might appear on external disk
42 | .Spotlight-V100
43 | .Trashes
44 |
45 |
46 | ######################
47 | # Eclipse
48 | ######################
49 |
50 | *.pydevproject
51 | .project
52 | .metadata
53 | bin/**
54 | tmp/**
55 | tmp/**/*
56 | *.tmp
57 | *.bak
58 | *.swp
59 | *~.nib
60 | local.properties
61 | .classpath
62 | .settings/
63 | .loadpath
64 | /src/main/resources/rebel.xml
65 | # External tool builders
66 | .externalToolBuilders/
67 |
68 | # Locally stored "Eclipse launch configurations"
69 | *.launch
70 |
71 | # CDT-specific
72 | .cproject
73 |
74 | # PDT-specific
75 | .buildpath
76 | pom.xml.releaseBackup
77 |
78 | release.properties
79 | target/parent-1.0.0-SNAPSHOT.jar
80 | Status
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | # NFC Token & Credit Card reader
2 |
3 | This Project helps developer to read data from credit card: card number, expired date, card type , Read & Write data in NFC tocken.
4 |
5 | 1. [Screenshots](#screenshots)
6 | 2. [PlayStoreLink](#storelink)
7 | 3. [License](#license)
8 |
9 | Screenshots
10 |
11 |
12 |
13 |
14 |
15 |
16 |
17 |
18 |
19 | PlayStoreLink
20 | https://play.google.com/store/apps/details?id=com.peerbits.nfccardread
21 |
22 |
23 |
24 | ### License
25 | The MIT License (MIT)
26 |
27 | Copyright (c) 2018 Credit Card & NFC Token Reader
28 |
29 | Permission is hereby granted, free of charge, to any person obtaining a copy
30 | of this software and associated documentation files (the "Software"), to deal
31 | in the Software without restriction, including without limitation the rights
32 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
33 | copies of the Software, and to permit persons to whom the Software is
34 | furnished to do so, subject to the following conditions:
35 |
36 | The above copyright notice and this permission notice shall be included in all
37 | copies or substantial portions of the Software.
38 |
39 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
40 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
41 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
42 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
43 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
44 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
45 | SOFTWARE.
46 |
--------------------------------------------------------------------------------
/app/.gitignore:
--------------------------------------------------------------------------------
1 | /build
2 |
--------------------------------------------------------------------------------
/app/build.gradle:
--------------------------------------------------------------------------------
1 | apply plugin: 'com.android.application'
2 |
3 | android {
4 | compileSdkVersion 27
5 | buildToolsVersion '27.0.3'
6 |
7 | defaultConfig {
8 | applicationId "com.peerbits.nfccardread"
9 | minSdkVersion 16
10 | targetSdkVersion 27
11 | versionCode 1
12 | versionName "1.0"
13 | }
14 | buildTypes {
15 | release {
16 | minifyEnabled false
17 | proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
18 | }
19 | }
20 | }
21 |
22 | dependencies {
23 | implementation fileTree(include: ['*.jar'], dir: 'libs')
24 | testImplementation 'junit:junit:4.12'
25 | implementation 'com.android.support:appcompat-v7:27.0.0-alpha1'
26 | implementation 'com.android.support:design:27.0.0'
27 | implementation project(':creditCardNfcReader')
28 | implementation 'com.github.bhargavms:DotLoader:1.0.0'
29 | implementation 'pl.droidsonroids.gif:android-gif-drawable:1.2.15'
30 | implementation 'com.intuit.sdp:sdp-android:1.0.6'
31 | // You can include the library from implementation as well
32 | // implementation 'com.github.pro100svitlo:creditCardNfcReader:1.0.3'
33 |
34 | }
35 |
--------------------------------------------------------------------------------
/app/proguard-rules.pro:
--------------------------------------------------------------------------------
1 | # Add project specific ProGuard rules here.
2 | # By default, the flags in this file are appended to flags specified
3 | # in /home/pro100svitlo/Android/SDK/tools/proguard/proguard-android.txt
4 | # You can edit the include path and order by changing the proguardFiles
5 | # directive in build.gradle.
6 | #
7 | # For more details, see
8 | # http://developer.android.com/guide/developing/tools/proguard.html
9 |
10 | # Add any project specific keep options here:
11 |
12 | # If your project uses WebView with JS, uncomment the following
13 | # and specify the fully qualified class name to the JavaScript interface
14 | # class:
15 | #-keepclassmembers class fqcn.of.javascript.interface.for.webview {
16 | # public *;
17 | #}
18 |
--------------------------------------------------------------------------------
/app/release/output.json:
--------------------------------------------------------------------------------
1 | [{"outputType":{"type":"APK"},"apkInfo":{"type":"MAIN","splits":[],"versionCode":1,"versionName":"1.0","enabled":true,"outputFile":"app-release.apk","fullName":"release","baseName":"release"},"path":"app-release.apk","properties":{}}]
--------------------------------------------------------------------------------
/app/src/main/AndroidManifest.xml:
--------------------------------------------------------------------------------
1 |
2 |
4 |
5 |
6 |
7 |
10 |
11 |
16 |
22 |
23 |
24 |
25 |
26 |
27 |
28 |
29 |
30 |
31 |
34 |
35 |
36 |
37 |
40 |
43 |
46 |
49 |
52 |
53 |
54 |
55 |
--------------------------------------------------------------------------------
/app/src/main/ic_launcher-web.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/ic_launcher-web.png
--------------------------------------------------------------------------------
/app/src/main/java/com/peerbits/nfccardread/NFCPayActivity.java:
--------------------------------------------------------------------------------
1 | package com.peerbits.nfccardread;
2 |
3 | import android.app.Activity;
4 | import android.content.Intent;
5 | import android.os.Bundle;
6 | import android.util.Log;
7 | import android.view.View;
8 | import android.widget.ImageView;
9 | import android.widget.TextView;
10 | import android.widget.Toast;
11 |
12 | import com.peerbits.creditCardNfcReader.CardNfcAsyncTask;
13 |
14 | public class NFCPayActivity extends Activity implements View.OnClickListener {
15 |
16 | public static final String TAG = NFCPayActivity.class.getSimpleName();
17 |
18 | private TextView tvCardNumber;
19 | private TextView tvEXPDate;
20 | private ImageView mCardLogoIcon, ivBack;
21 | private String card = "", cardType = "", expiredDate = "";
22 |
23 | @Override
24 | protected void onCreate(Bundle savedInstanceState) {
25 | super.onCreate(savedInstanceState);
26 | setContentView(R.layout.nfc_pay);
27 | initViews();
28 |
29 | Bundle extras = getIntent().getExtras();
30 |
31 | if (extras != null) {
32 | card = extras.getString("card");
33 | cardType = extras.getString("cardType");
34 | expiredDate = extras.getString("expiredDate");
35 |
36 | tvCardNumber.setText("" + card);
37 | tvEXPDate.setText("" + expiredDate);
38 |
39 | parseCardType(cardType);
40 | }
41 | ivBack.setOnClickListener(new View.OnClickListener() {
42 | @Override
43 | public void onClick(View view) {
44 | finish();
45 | }
46 | });
47 | }
48 |
49 |
50 | private void parseCardType(String cardType) {
51 |
52 | Log.e("CardTyoe", " " + cardType);
53 | if (cardType.equals(CardNfcAsyncTask.CARD_UNKNOWN)) {
54 | Toast.makeText(NFCPayActivity.this, getString(R.string.snack_unknown_bank_card), Toast.LENGTH_LONG).show();
55 | } else if (cardType.equals(CardNfcAsyncTask.CARD_VISA)) {
56 | mCardLogoIcon.setImageResource(R.mipmap.visa_logo);
57 | } else if (cardType.equals(CardNfcAsyncTask.CARD_NAB_VISA)) {
58 | mCardLogoIcon.setImageResource(R.mipmap.visa_logo);
59 | }
60 | }
61 |
62 | private void initViews() {
63 |
64 |
65 | tvCardNumber = findViewById(R.id.tvCardNumber);
66 | tvEXPDate = findViewById(R.id.tvEXPDate);
67 | ivBack = findViewById(R.id.ivBack);
68 | mCardLogoIcon = findViewById(R.id.ivCardIcon);
69 | }
70 |
71 |
72 | @Override
73 | public void onClick(View view) {
74 | Intent intent;
75 | switch (view.getId()) {
76 | case R.id.rlReadNFCTAG:
77 | intent = new Intent(this, NFCRead.class);
78 | this.startActivity(intent);
79 | break;
80 |
81 | case R.id.rlWriteWithNFC:
82 | intent = new Intent(this, NFCWrite.class);
83 | this.startActivity(intent);
84 | break;
85 |
86 | case R.id.rlCreditCard:
87 | intent = new Intent(this, NFCCardReading.class);
88 | this.startActivity(intent);
89 | break;
90 | }
91 | }
92 |
93 |
94 | }
95 |
--------------------------------------------------------------------------------
/app/src/main/java/com/peerbits/nfccardread/NFCRead.java:
--------------------------------------------------------------------------------
1 | package com.peerbits.nfccardread;
2 |
3 | import android.app.Activity;
4 | import android.app.PendingIntent;
5 | import android.content.Intent;
6 | import android.content.IntentFilter;
7 | import android.nfc.NdefMessage;
8 | import android.nfc.NdefRecord;
9 | import android.nfc.NfcAdapter;
10 | import android.nfc.Tag;
11 | import android.nfc.tech.MifareClassic;
12 | import android.nfc.tech.Ndef;
13 | import android.nfc.tech.NdefFormatable;
14 | import android.nfc.tech.NfcA;
15 | import android.os.Bundle;
16 | import android.os.IBinder;
17 | import android.os.Parcel;
18 | import android.os.Parcelable;
19 | import android.util.Log;
20 | import android.view.View;
21 | import android.widget.ImageView;
22 | import android.widget.TextView;
23 | import android.widget.Toast;
24 |
25 | import com.bhargavms.dotloader.DotLoader;
26 |
27 | import java.io.IOException;
28 |
29 | public class NFCRead extends Activity {
30 |
31 | public static final String TAG = NFCRead.class.getSimpleName();
32 | private TextView tvNFCMessage;
33 | private NfcAdapter mNfcAdapter;
34 | private DotLoader dotloader;
35 | private ImageView ivBack;
36 |
37 | @Override
38 | protected void onCreate(Bundle savedInstanceState) {
39 | super.onCreate(savedInstanceState);
40 | setContentView(R.layout.nfc_read);
41 | initViews();
42 | ivBack.setOnClickListener(new View.OnClickListener() {
43 | @Override
44 | public void onClick(View view) {
45 | finish();
46 | }
47 | });
48 | }
49 |
50 | private void initViews() {
51 | tvNFCMessage = findViewById(R.id.tvNFCMessage);
52 | dotloader = findViewById(R.id.text_dot_loader);
53 | mNfcAdapter = NfcAdapter.getDefaultAdapter(this);
54 | ivBack = findViewById(R.id.ivBack);
55 | }
56 |
57 | @Override
58 | protected void onResume() {
59 | super.onResume();
60 |
61 | IntentFilter tagDetected = new IntentFilter(NfcAdapter.ACTION_TAG_DISCOVERED);
62 | IntentFilter ndefDetected = new IntentFilter(NfcAdapter.ACTION_NDEF_DISCOVERED);
63 | IntentFilter techDetected = new IntentFilter(NfcAdapter.ACTION_TECH_DISCOVERED);
64 | IntentFilter[] nfcIntentFilter = new IntentFilter[]{techDetected, tagDetected, ndefDetected};
65 |
66 | PendingIntent pendingIntent = PendingIntent.getActivity(
67 | this, 0, new Intent(this, getClass()).addFlags(Intent.FLAG_ACTIVITY_SINGLE_TOP), 0);
68 | if (mNfcAdapter != null)
69 | mNfcAdapter.enableForegroundDispatch(this, pendingIntent, nfcIntentFilter, null);
70 | }
71 |
72 | @Override
73 | protected void onPause() {
74 | super.onPause();
75 | if (mNfcAdapter != null)
76 | mNfcAdapter.disableForegroundDispatch(this);
77 | }
78 |
79 | @Override
80 | protected void onNewIntent(Intent intent) {
81 | Tag tag = intent.getParcelableExtra(NfcAdapter.EXTRA_TAG);
82 | patchTag(tag);
83 | if (tag != null) {
84 | readFromNFC(tag, intent);
85 | }
86 | }
87 |
88 |
89 | public Tag patchTag(Tag oTag) {
90 | if (oTag == null)
91 | return null;
92 |
93 | String[] sTechList = oTag.getTechList();
94 |
95 | Parcel oParcel, nParcel;
96 |
97 | oParcel = Parcel.obtain();
98 | oTag.writeToParcel(oParcel, 0);
99 | oParcel.setDataPosition(0);
100 |
101 | int len = oParcel.readInt();
102 | byte[] id = null;
103 | if (len >= 0) {
104 | id = new byte[len];
105 | oParcel.readByteArray(id);
106 | }
107 | int[] oTechList = new int[oParcel.readInt()];
108 | oParcel.readIntArray(oTechList);
109 | Bundle[] oTechExtras = oParcel.createTypedArray(Bundle.CREATOR);
110 | int serviceHandle = oParcel.readInt();
111 | int isMock = oParcel.readInt();
112 | IBinder tagService;
113 | if (isMock == 0) {
114 | tagService = oParcel.readStrongBinder();
115 | } else {
116 | tagService = null;
117 | }
118 | oParcel.recycle();
119 |
120 | int nfca_idx = -1;
121 | int mc_idx = -1;
122 |
123 | for (int idx = 0; idx < sTechList.length; idx++) {
124 | if (sTechList[idx] == NfcA.class.getName()) {
125 | nfca_idx = idx;
126 | } else if (sTechList[idx] == MifareClassic.class.getName()) {
127 | mc_idx = idx;
128 | }
129 | }
130 |
131 | if (nfca_idx >= 0 && mc_idx >= 0 && oTechExtras[mc_idx] == null) {
132 | oTechExtras[mc_idx] = oTechExtras[nfca_idx];
133 | } else {
134 | return oTag;
135 | }
136 |
137 | nParcel = Parcel.obtain();
138 | nParcel.writeInt(id.length);
139 | nParcel.writeByteArray(id);
140 | nParcel.writeInt(oTechList.length);
141 | nParcel.writeIntArray(oTechList);
142 | nParcel.writeTypedArray(oTechExtras, 0);
143 | nParcel.writeInt(serviceHandle);
144 | nParcel.writeInt(isMock);
145 | if (isMock == 0) {
146 | nParcel.writeStrongBinder(tagService);
147 | }
148 | nParcel.setDataPosition(0);
149 | Tag nTag = Tag.CREATOR.createFromParcel(nParcel);
150 | nParcel.recycle();
151 |
152 | return nTag;
153 | }
154 |
155 | private void readFromNFC(Tag tag, Intent intent) {
156 |
157 | try {
158 | Ndef ndef = Ndef.get(tag);
159 | if (ndef != null) {
160 | ndef.connect();
161 | NdefMessage ndefMessage = ndef.getNdefMessage();
162 |
163 | if (ndefMessage != null) {
164 | /*String message = new String(ndefMessage.getRecords()[0].getPayload());
165 | Log.d(TAG, "NFC found.. "+"readFromNFC: "+message );
166 | tvNFCMessage.setText(message);*/
167 |
168 | Parcelable[] messages = intent.getParcelableArrayExtra(NfcAdapter.EXTRA_NDEF_MESSAGES);
169 |
170 | if (messages != null) {
171 | NdefMessage[] ndefMessages = new NdefMessage[messages.length];
172 | for (int i = 0; i < messages.length; i++) {
173 | ndefMessages[i] = (NdefMessage) messages[i];
174 | }
175 | NdefRecord record = ndefMessages[0].getRecords()[0];
176 |
177 | byte[] payload = record.getPayload();
178 | String text = new String(payload);
179 | tvNFCMessage.setText(text);
180 | dotloader.setVisibility(View.GONE);
181 | Log.e("tag", "vahid --> " + text);
182 | ndef.close();
183 |
184 | }
185 |
186 | } else {
187 | Toast.makeText(this, "Not able to read from NFC, Please try again...", Toast.LENGTH_LONG).show();
188 |
189 | }
190 | } else {
191 | NdefFormatable format = NdefFormatable.get(tag);
192 | if (format != null) {
193 | try {
194 | format.connect();
195 | NdefMessage ndefMessage = ndef.getNdefMessage();
196 |
197 | if (ndefMessage != null) {
198 | String message = new String(ndefMessage.getRecords()[0].getPayload());
199 | Log.d(TAG, "NFC found.. " + "readFromNFC: " + message);
200 | tvNFCMessage.setText(message);
201 | ndef.close();
202 | } else {
203 | Toast.makeText(this, "Not able to read from NFC, Please try again...", Toast.LENGTH_LONG).show();
204 |
205 | }
206 | } catch (IOException e) {
207 | e.printStackTrace();
208 | }
209 | } else {
210 | Toast.makeText(this, "NFC is not readable", Toast.LENGTH_LONG).show();
211 | }
212 | }
213 | } catch (Exception e) {
214 | e.printStackTrace();
215 | }
216 |
217 | }
218 | }
219 |
--------------------------------------------------------------------------------
/app/src/main/java/com/peerbits/nfccardread/NFCWrite.java:
--------------------------------------------------------------------------------
1 | package com.peerbits.nfccardread;
2 |
3 | import android.app.Activity;
4 | import android.app.PendingIntent;
5 | import android.content.Intent;
6 | import android.content.IntentFilter;
7 | import android.nfc.NdefMessage;
8 | import android.nfc.NdefRecord;
9 | import android.nfc.NfcAdapter;
10 | import android.nfc.Tag;
11 | import android.nfc.tech.Ndef;
12 | import android.nfc.tech.NdefFormatable;
13 | import android.os.Bundle;
14 | import android.text.TextUtils;
15 | import android.view.View;
16 | import android.widget.EditText;
17 | import android.widget.ImageView;
18 | import android.widget.Toast;
19 |
20 | import java.io.IOException;
21 |
22 | public class NFCWrite extends Activity {
23 |
24 | public static final String TAG = NFCWrite.class.getSimpleName();
25 | private EditText evTagMessage;
26 | private NfcAdapter mNfcAdapter;
27 | private boolean isWrite = true;
28 | private ImageView ivBack;
29 |
30 | @Override
31 | protected void onCreate(Bundle savedInstanceState) {
32 | super.onCreate(savedInstanceState);
33 | setContentView(R.layout.nfc_write);
34 | initViews();
35 | ivBack.setOnClickListener(new View.OnClickListener() {
36 | @Override
37 | public void onClick(View view) {
38 | finish();
39 | }
40 | });
41 | }
42 |
43 | private void initViews() {
44 | ivBack = findViewById(R.id.ivBack);
45 | evTagMessage = findViewById(R.id.evTagMessage);
46 | mNfcAdapter = NfcAdapter.getDefaultAdapter(this);
47 | }
48 |
49 | public boolean writeTag(Tag tag, NdefMessage message) {
50 | int size = message.toByteArray().length;
51 | try {
52 | Ndef ndef = Ndef.get(tag);
53 | if (ndef != null) {
54 | ndef.connect();
55 | if (!ndef.isWritable()) {
56 | return false;
57 | }
58 | if (ndef.getMaxSize() < size) {
59 | return false;
60 | }
61 | ndef.writeNdefMessage(message);
62 | return true;
63 | } else {
64 | NdefFormatable format = NdefFormatable.get(tag);
65 | if (format != null) {
66 | try {
67 | format.connect();
68 | format.format(message);
69 | return true;
70 | } catch (IOException e) {
71 | return false;
72 | }
73 | } else {
74 | return false;
75 | }
76 | }
77 | } catch (Exception e) {
78 | return false;
79 | }
80 | }
81 |
82 | @Override
83 | protected void onResume() {
84 | super.onResume();
85 |
86 | IntentFilter tagDetected = new IntentFilter(NfcAdapter.ACTION_TAG_DISCOVERED);
87 | IntentFilter ndefDetected = new IntentFilter(NfcAdapter.ACTION_NDEF_DISCOVERED);
88 | IntentFilter techDetected = new IntentFilter(NfcAdapter.ACTION_TECH_DISCOVERED);
89 | IntentFilter[] nfcIntentFilter = new IntentFilter[]{techDetected, tagDetected, ndefDetected};
90 |
91 | PendingIntent pendingIntent = PendingIntent.getActivity(
92 | this, 0, new Intent(this, getClass()).addFlags(Intent.FLAG_ACTIVITY_SINGLE_TOP), 0);
93 | if (mNfcAdapter != null)
94 | mNfcAdapter.enableForegroundDispatch(this, pendingIntent, nfcIntentFilter, null);
95 | }
96 |
97 | @Override
98 | protected void onPause() {
99 | super.onPause();
100 | if (mNfcAdapter != null)
101 | mNfcAdapter.disableForegroundDispatch(this);
102 | }
103 |
104 | @Override
105 | protected void onNewIntent(Intent intent) {
106 | Tag tag = intent.getParcelableExtra(NfcAdapter.EXTRA_TAG);
107 |
108 | if (tag != null) {
109 | if (isWrite) {
110 | String messageToWrite = evTagMessage.getText().toString();
111 |
112 | if (messageToWrite != null && (!TextUtils.equals(messageToWrite, "null")) && (!TextUtils.isEmpty(messageToWrite))) {
113 | NdefRecord record = NdefRecord.createMime(messageToWrite, messageToWrite.getBytes());
114 | NdefMessage message = new NdefMessage(new NdefRecord[]{record});
115 |
116 | if (writeTag(tag, message)) {
117 | Toast.makeText(this, (getString(R.string.message_write_success)), Toast.LENGTH_SHORT).show();
118 | finish();
119 | } else {
120 | Toast.makeText(this, (getString(R.string.message_write_error)), Toast.LENGTH_SHORT).show();
121 | }
122 | } else {
123 | evTagMessage.setError("Please enter the text to write");
124 | /*Toast.makeText(this,"Please enter the text to write",Toast.LENGTH_LONG).show();*/
125 | }
126 | }
127 | }
128 | }
129 |
130 | }
131 |
--------------------------------------------------------------------------------
/app/src/main/java/com/peerbits/nfccardread/NfcHome.java:
--------------------------------------------------------------------------------
1 | package com.peerbits.nfccardread;
2 |
3 | import android.app.Activity;
4 | import android.content.Intent;
5 | import android.os.Bundle;
6 | import android.view.View;
7 | import android.view.animation.Animation;
8 | import android.view.animation.AnimationUtils;
9 | import android.widget.ImageView;
10 | import android.widget.RelativeLayout;
11 |
12 | public class NfcHome extends Activity implements View.OnClickListener {
13 |
14 | public static final String TAG = NfcHome.class.getSimpleName();
15 | private RelativeLayout rlRead;
16 | private RelativeLayout rlWrite;
17 | private RelativeLayout rlCreditCard;
18 | private ImageView ivHomeicon;
19 | private Animation mAnimation;
20 |
21 | @Override
22 | protected void onCreate(Bundle savedInstanceState) {
23 | super.onCreate(savedInstanceState);
24 | setContentView(R.layout.nfc_home);
25 | initViews();
26 | rlRead.setOnClickListener(this);
27 | rlWrite.setOnClickListener(this);
28 | rlCreditCard.setOnClickListener(this);
29 | }
30 |
31 | private void initViews() {
32 |
33 | rlRead = findViewById(R.id.rlReadNFCTAG);
34 | rlWrite = findViewById(R.id.rlWriteWithNFC);
35 | rlCreditCard = findViewById(R.id.rlCreditCard);
36 | ivHomeicon = findViewById(R.id.ivHomeicon);
37 | mAnimation = AnimationUtils.loadAnimation(NfcHome.this, R.anim.swinging);
38 | }
39 |
40 |
41 | @Override
42 | public void onClick(View view) {
43 | Intent intent;
44 | switch (view.getId()) {
45 | case R.id.rlReadNFCTAG:
46 | intent = new Intent(this, NFCRead.class);
47 | this.startActivity(intent);
48 | break;
49 |
50 | case R.id.rlWriteWithNFC:
51 | intent = new Intent(this, NFCWrite.class);
52 | this.startActivity(intent);
53 | break;
54 |
55 | case R.id.rlCreditCard:
56 | intent = new Intent(this, NFCCardReading.class);
57 | this.startActivity(intent);
58 | break;
59 | }
60 | }
61 |
62 | @Override
63 | public void onResume() {
64 | super.onResume();
65 | ivHomeicon.startAnimation(mAnimation);
66 | }
67 |
68 | @Override
69 | public void onPause() {
70 | ivHomeicon.clearAnimation();
71 | super.onPause();
72 | }
73 | }
74 |
--------------------------------------------------------------------------------
/app/src/main/java/com/peerbits/nfccardread/SplashActivity.java:
--------------------------------------------------------------------------------
1 | package com.peerbits.nfccardread;
2 |
3 | import android.app.Activity;
4 | import android.content.Context;
5 | import android.content.Intent;
6 | import android.os.Bundle;
7 | import android.os.Handler;
8 |
9 | public class SplashActivity extends Activity {
10 |
11 | public static final String TAG = SplashActivity.class.getSimpleName();
12 |
13 | Context context = SplashActivity.this;
14 |
15 | @Override
16 | protected void onCreate(Bundle savedInstanceState) {
17 | super.onCreate(savedInstanceState);
18 | setContentView(R.layout.splash);
19 |
20 | new Handler().postDelayed(new Runnable() {
21 | @Override
22 | public void run() {
23 | /* Create an Intent that will start the Menu-Activity. */
24 | Intent i = new Intent(context, NfcHome.class);
25 | startActivity(i);
26 | finish();
27 | }
28 | }, 1000);
29 | }
30 |
31 |
32 | }
33 |
--------------------------------------------------------------------------------
/app/src/main/res/anim/swinging.xml:
--------------------------------------------------------------------------------
1 |
2 |
--------------------------------------------------------------------------------
/app/src/main/res/drawable-hdpi/bg_card.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-hdpi/bg_card.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-hdpi/bg_home.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-hdpi/bg_home.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-hdpi/bg_splash.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-hdpi/bg_splash.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-hdpi/ic_back.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-hdpi/ic_back.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-hdpi/ic_card_chip.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-hdpi/ic_card_chip.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-hdpi/ic_card_reader.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-hdpi/ic_card_reader.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-hdpi/ic_home.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-hdpi/ic_home.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-hdpi/ic_launcher.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-hdpi/ic_launcher.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-hdpi/ic_read_nfc.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-hdpi/ic_read_nfc.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-hdpi/ic_splash.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-hdpi/ic_splash.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-hdpi/ic_write_nfc.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-hdpi/ic_write_nfc.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-hdpi/img_card.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-hdpi/img_card.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-hdpi/img_card_read.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-hdpi/img_card_read.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-hdpi/img_card_write.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-hdpi/img_card_write.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-ldpi/bg_card.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-ldpi/bg_card.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-ldpi/bg_home.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-ldpi/bg_home.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-ldpi/ic_back.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-ldpi/ic_back.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-ldpi/ic_card_chip.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-ldpi/ic_card_chip.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-ldpi/ic_card_reader.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-ldpi/ic_card_reader.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-ldpi/ic_home.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-ldpi/ic_home.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-ldpi/ic_launcher.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-ldpi/ic_launcher.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-ldpi/ic_read_nfc.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-ldpi/ic_read_nfc.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-ldpi/ic_splash.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-ldpi/ic_splash.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-ldpi/ic_write_nfc.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-ldpi/ic_write_nfc.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-ldpi/img_card.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-ldpi/img_card.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-ldpi/img_card_read.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-ldpi/img_card_read.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-ldpi/img_card_write.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-ldpi/img_card_write.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-mdpi/bg_card.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-mdpi/bg_card.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-mdpi/bg_splash.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-mdpi/bg_splash.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-mdpi/ic_back.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-mdpi/ic_back.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-mdpi/ic_card_chip.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-mdpi/ic_card_chip.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-mdpi/ic_card_reader.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-mdpi/ic_card_reader.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-mdpi/ic_home.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-mdpi/ic_home.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-mdpi/ic_launcher.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-mdpi/ic_launcher.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-mdpi/ic_read_nfc.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-mdpi/ic_read_nfc.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-mdpi/ic_splash.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-mdpi/ic_splash.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-mdpi/ic_write_nfc.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-mdpi/ic_write_nfc.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-mdpi/img_card.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-mdpi/img_card.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-mdpi/img_card_read.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-mdpi/img_card_read.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-mdpi/img_card_write.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-mdpi/img_card_write.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-nodpi/button_background.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
--------------------------------------------------------------------------------
/app/src/main/res/drawable-nodpi/button_press.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
--------------------------------------------------------------------------------
/app/src/main/res/drawable-nodpi/gif_card.gif:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-nodpi/gif_card.gif
--------------------------------------------------------------------------------
/app/src/main/res/drawable-nodpi/gif_read.gif:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-nodpi/gif_read.gif
--------------------------------------------------------------------------------
/app/src/main/res/drawable-nodpi/gif_sucess.gif:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-nodpi/gif_sucess.gif
--------------------------------------------------------------------------------
/app/src/main/res/drawable-nodpi/gif_write.gif:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-nodpi/gif_write.gif
--------------------------------------------------------------------------------
/app/src/main/res/drawable-nodpi/ic_nfc.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-nodpi/ic_nfc.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-nodpi/img_tag_reader.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-nodpi/img_tag_reader.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-nodpi/nfc_write_img.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-nodpi/nfc_write_img.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-xhdpi/bg_card.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-xhdpi/bg_card.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-xhdpi/bg_home.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-xhdpi/bg_home.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-xhdpi/bg_splash.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-xhdpi/bg_splash.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-xhdpi/ic_back.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-xhdpi/ic_back.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-xhdpi/ic_card_chip.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-xhdpi/ic_card_chip.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-xhdpi/ic_card_reader.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-xhdpi/ic_card_reader.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-xhdpi/ic_home.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-xhdpi/ic_home.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-xhdpi/ic_launcher.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-xhdpi/ic_launcher.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-xhdpi/ic_read_nfc.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-xhdpi/ic_read_nfc.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-xhdpi/ic_splash.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-xhdpi/ic_splash.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-xhdpi/ic_write_nfc.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-xhdpi/ic_write_nfc.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-xhdpi/img_card.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-xhdpi/img_card.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-xhdpi/img_card_read.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-xhdpi/img_card_read.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-xhdpi/img_card_write.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-xhdpi/img_card_write.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-xxhdpi/bg_card.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-xxhdpi/bg_card.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-xxhdpi/bg_home.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-xxhdpi/bg_home.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-xxhdpi/bg_splash.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-xxhdpi/bg_splash.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-xxhdpi/ic_back.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-xxhdpi/ic_back.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-xxhdpi/ic_card_chip.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-xxhdpi/ic_card_chip.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-xxhdpi/ic_card_reader.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-xxhdpi/ic_card_reader.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-xxhdpi/ic_home.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-xxhdpi/ic_home.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-xxhdpi/ic_launcher.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-xxhdpi/ic_launcher.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-xxhdpi/ic_read_nfc.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-xxhdpi/ic_read_nfc.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-xxhdpi/ic_splash.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-xxhdpi/ic_splash.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-xxhdpi/ic_write_nfc.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-xxhdpi/ic_write_nfc.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-xxhdpi/img_card.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-xxhdpi/img_card.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-xxhdpi/img_card_read.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-xxhdpi/img_card_read.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-xxhdpi/img_card_write.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-xxhdpi/img_card_write.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-xxxhdpi/bg_card.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-xxxhdpi/bg_card.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-xxxhdpi/bg_home.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-xxxhdpi/bg_home.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-xxxhdpi/bg_splash.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-xxxhdpi/bg_splash.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-xxxhdpi/ic_back.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-xxxhdpi/ic_back.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-xxxhdpi/ic_card_chip.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-xxxhdpi/ic_card_chip.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-xxxhdpi/ic_card_reader.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-xxxhdpi/ic_card_reader.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-xxxhdpi/ic_home.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-xxxhdpi/ic_home.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-xxxhdpi/ic_launcher.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-xxxhdpi/ic_launcher.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-xxxhdpi/ic_read_nfc.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-xxxhdpi/ic_read_nfc.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-xxxhdpi/ic_splash.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-xxxhdpi/ic_splash.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-xxxhdpi/ic_write_nfc.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-xxxhdpi/ic_write_nfc.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-xxxhdpi/img_card.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-xxxhdpi/img_card.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-xxxhdpi/img_card_read.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-xxxhdpi/img_card_read.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable-xxxhdpi/img_card_write.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/drawable-xxxhdpi/img_card_write.png
--------------------------------------------------------------------------------
/app/src/main/res/drawable/card_bg.xml:
--------------------------------------------------------------------------------
1 |
2 |
4 |
7 |
11 |
17 |
--------------------------------------------------------------------------------
/app/src/main/res/layout/nfc_cardread.xml:
--------------------------------------------------------------------------------
1 |
2 |
8 |
9 |
13 |
14 |
15 |
26 |
27 |
35 |
36 |
37 |
38 |
51 |
52 |
58 |
59 |
66 |
67 |
68 |
69 |
70 |
71 |
78 |
79 |
88 |
89 |
97 |
98 |
99 |
108 |
109 |
110 |
--------------------------------------------------------------------------------
/app/src/main/res/layout/nfc_home.xml:
--------------------------------------------------------------------------------
1 |
2 |
5 |
6 |
12 |
21 |
22 |
30 |
31 |
37 |
38 |
45 |
46 |
54 |
63 |
64 |
73 |
74 |
75 |
76 |
77 |
78 |
85 |
86 |
87 |
94 |
95 |
103 |
112 |
113 |
122 |
123 |
124 |
125 |
126 |
132 |
133 |
134 |
141 |
142 |
150 |
159 |
160 |
169 |
170 |
171 |
172 |
173 |
174 |
175 |
176 |
--------------------------------------------------------------------------------
/app/src/main/res/layout/nfc_pay.xml:
--------------------------------------------------------------------------------
1 |
2 |
6 |
7 |
8 |
9 |
14 |
15 |
16 |
27 |
28 |
36 |
37 |
38 |
39 |
40 |
41 |
49 |
50 |
56 |
66 |
78 |
79 |
89 |
90 |
100 |
101 |
112 |
113 |
123 |
124 |
125 |
126 |
127 |
139 |
140 |
--------------------------------------------------------------------------------
/app/src/main/res/layout/nfc_read.xml:
--------------------------------------------------------------------------------
1 |
2 |
8 |
9 |
10 |
14 |
15 |
16 |
27 |
28 |
36 |
37 |
38 |
39 |
40 |
41 |
54 |
55 |
63 |
64 |
71 |
72 |
81 |
82 |
90 |
91 |
92 |
93 |
--------------------------------------------------------------------------------
/app/src/main/res/layout/nfc_write.xml:
--------------------------------------------------------------------------------
1 |
2 |
6 |
7 |
11 |
12 |
13 |
24 |
25 |
33 |
34 |
35 |
36 |
37 |
50 |
51 |
58 |
59 |
67 |
68 |
69 |
--------------------------------------------------------------------------------
/app/src/main/res/layout/splash.xml:
--------------------------------------------------------------------------------
1 |
2 |
8 |
16 |
17 |
26 |
27 |
--------------------------------------------------------------------------------
/app/src/main/res/mipmap-hdpi/master_logo.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/mipmap-hdpi/master_logo.png
--------------------------------------------------------------------------------
/app/src/main/res/mipmap-hdpi/visa_logo.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/mipmap-hdpi/visa_logo.png
--------------------------------------------------------------------------------
/app/src/main/res/mipmap-mdpi/master_logo.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/mipmap-mdpi/master_logo.png
--------------------------------------------------------------------------------
/app/src/main/res/mipmap-mdpi/visa_logo.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/mipmap-mdpi/visa_logo.png
--------------------------------------------------------------------------------
/app/src/main/res/mipmap-xhdpi/master_logo.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/mipmap-xhdpi/master_logo.png
--------------------------------------------------------------------------------
/app/src/main/res/mipmap-xhdpi/visa_logo.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/mipmap-xhdpi/visa_logo.png
--------------------------------------------------------------------------------
/app/src/main/res/mipmap-xxhdpi/master_logo.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/mipmap-xxhdpi/master_logo.png
--------------------------------------------------------------------------------
/app/src/main/res/mipmap-xxhdpi/visa_logo.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/mipmap-xxhdpi/visa_logo.png
--------------------------------------------------------------------------------
/app/src/main/res/mipmap-xxxhdpi/master_logo.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/mipmap-xxxhdpi/master_logo.png
--------------------------------------------------------------------------------
/app/src/main/res/mipmap-xxxhdpi/visa_logo.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/app/src/main/res/mipmap-xxxhdpi/visa_logo.png
--------------------------------------------------------------------------------
/app/src/main/res/values-v21/styles.xml:
--------------------------------------------------------------------------------
1 | >
2 |
3 |
9 |
10 |
--------------------------------------------------------------------------------
/app/src/main/res/values-w820dp/dimens.xml:
--------------------------------------------------------------------------------
1 |
2 |
5 | 64dp
6 |
7 |
--------------------------------------------------------------------------------
/app/src/main/res/values/colors.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 | #143F64
4 | #0A2642
5 | #FF9800
6 |
7 |
8 |
9 | - #ffffff
10 | - #ffffff
11 | - #ffffff
12 | - #ffffff
13 |
14 |
15 |
16 |
--------------------------------------------------------------------------------
/app/src/main/res/values/dimens.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 | 16dp
4 | 16dp
5 | 16dp
6 |
7 |
--------------------------------------------------------------------------------
/app/src/main/res/values/strings.xml:
--------------------------------------------------------------------------------
1 |
2 | NFC Peerbits
3 | https://github.com/pro100svitlo/Credit-Card-NFC-Reader#questions-and-help
4 | There is no NFC module on this device
5 | Please put your card to back panel of the phone
6 | Scanning ...
7 | Please do not remove or move card during reading.
8 | This is unknown bank card.
9 | Please do not move card, try again !
10 | Unknown EMV card
11 | NFC is locked on this card.
12 | NFC is turned off.
13 | You need turn on NFC module for scanning. Wish turn on it now?
14 | Turn on
15 | Dismiss
16 | Error Writing Message !
17 | Successfully written to Tag !
18 | Writing to Tag..
19 | NFC Tag Detected !
20 | Read from NFC Tag
21 | Write to NFC Tag
22 | Tap the NFC Tag to your device !
23 | Message
24 | Payment With NFC
25 | Read with NFC
26 | Write with NFC
27 | Scan with NFC
28 | Sample Loyalty Card
29 | Account Number
30 | TODO
31 | NFC
32 | Home Nfc
33 | Tap your NFC tag on \n mobile to read
34 | Tap your NFC tag on \n mobile to write
35 | Tap your Credit Card on \n mobile to read
36 | Reading
37 | Scanning
38 | Expiry
39 | CARD NUMBER
40 | PAYNOW
41 | Payment
42 | 02/18
43 | XXXX - XXXX - XXXX - 4444
44 | Write with NFC
45 | Tap your NFC tag on mobile to read
46 | Tap your NFC tag on mobile to read
47 | Read with NFC
48 | TODO
49 | Read with NFC Card
50 | Tap your Credit Card on mobile to read
51 |
52 |
53 |
--------------------------------------------------------------------------------
/app/src/main/res/values/styles.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
9 |
10 |
11 |
12 |
19 |
20 |
21 |
--------------------------------------------------------------------------------
/app/src/main/res/xml/nfc_tech_filter.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | android.nfc.tech.IsoDep
6 |
7 |
8 |
--------------------------------------------------------------------------------
/app/src/test/java/com/peerbits/nfccardread/ExampleUnitTest.java:
--------------------------------------------------------------------------------
1 | package com.peerbits.nfccardread;
2 |
3 | import org.junit.Test;
4 |
5 | import static org.junit.Assert.*;
6 |
7 | /**
8 | * To work on unit tests, switch the Test Artifact in the Build Variants view.
9 | */
10 | public class ExampleUnitTest {
11 | @Test
12 | public void addition_isCorrect() throws Exception {
13 | assertEquals(4, 2 + 2);
14 | }
15 | }
--------------------------------------------------------------------------------
/build.gradle:
--------------------------------------------------------------------------------
1 | // Top-level build file where you can add configuration options common to all sub-projects/modules.
2 |
3 | buildscript {
4 | repositories {
5 | jcenter()
6 | google()
7 | }
8 | dependencies {
9 | classpath 'com.android.tools.build:gradle:3.1.4'
10 | classpath 'com.novoda:bintray-release:0.8.0'
11 |
12 | // NOTE: Do not place your application dependencies here; they belong
13 | // in the individual module build.gradle files
14 | }
15 | }
16 |
17 | allprojects {
18 | repositories {
19 | jcenter()
20 | google()
21 | maven { url "https://jitpack.io" }
22 | }
23 | }
24 |
25 | subprojects {
26 | tasks.withType(Javadoc).all { enabled = false }
27 | }
28 |
29 | task clean(type: Delete) {
30 | delete rootProject.buildDir
31 | }
32 |
--------------------------------------------------------------------------------
/creditCardNfcReader/.gitignore:
--------------------------------------------------------------------------------
1 | /build
2 |
--------------------------------------------------------------------------------
/creditCardNfcReader/build.gradle:
--------------------------------------------------------------------------------
1 | apply plugin: 'com.android.library'
2 | apply plugin: 'com.novoda.bintray-release'
3 |
4 | android {
5 | compileSdkVersion 28
6 | buildToolsVersion '27.0.3'
7 | defaultConfig {
8 | multiDexEnabled true
9 | minSdkVersion 16
10 | targetSdkVersion 28
11 | versionCode 2
12 | versionName "1.0.2"
13 | }
14 | buildTypes {
15 | release {
16 | proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
17 | }
18 | }
19 | }
20 |
21 | dependencies {
22 | implementation fileTree(dir: 'libs', include: ['*.jar'])
23 | implementation 'com.noveogroup.android:android-logger:1.3.5'
24 | implementation 'com.parse.bolts:bolts-android:1.1.2'
25 | implementation files('libs/commons-lang3-3.0.jar')
26 | implementation files('libs/commons-collections4-4.0.jar')
27 | implementation 'commons-io:commons-io:2.4'
28 | }
29 |
30 | publish {
31 | groupId = 'com.github.pro100svitlo'
32 | artifactId = 'creditCardNfcReader'
33 | publishVersion = '1.0.3'
34 | desc = 'Library that help developer to get data from credit card with NFC'
35 | licences = ['MIT']
36 | website = 'https://github.com/pro100svitlo/Credit-Card-NFC-Reader'
37 | }
38 |
--------------------------------------------------------------------------------
/creditCardNfcReader/libs/bit-lib4j-1.4.12.jar:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/creditCardNfcReader/libs/bit-lib4j-1.4.12.jar
--------------------------------------------------------------------------------
/creditCardNfcReader/libs/commons-collections4-4.0.jar:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/creditCardNfcReader/libs/commons-collections4-4.0.jar
--------------------------------------------------------------------------------
/creditCardNfcReader/libs/commons-lang3-3.0.jar:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/creditCardNfcReader/libs/commons-lang3-3.0.jar
--------------------------------------------------------------------------------
/creditCardNfcReader/proguard-rules.pro:
--------------------------------------------------------------------------------
1 | # Add project specific ProGuard rules here.
2 | # By default, the flags in this file are appended to flags specified
3 | # in /home/pro100svitlo/Android/SDK/tools/proguard/proguard-android.txt
4 | # You can edit the include path and order by changing the proguardFiles
5 | # directive in build.gradle.
6 | #
7 | # For more details, see
8 | # http://developer.android.com/guide/developing/tools/proguard.html
9 |
10 | # Add any project specific keep options here:
11 |
12 | # If your project uses WebView with JS, uncomment the following
13 | # and specify the fully qualified class name to the JavaScript interface
14 | # class:
15 | #-keepclassmembers class fqcn.of.javascript.interface.for.webview {
16 | # public *;
17 | #}
18 |
--------------------------------------------------------------------------------
/creditCardNfcReader/src/main/AndroidManifest.xml:
--------------------------------------------------------------------------------
1 |
3 |
4 |
5 |
7 |
10 |
11 |
12 |
13 |
--------------------------------------------------------------------------------
/creditCardNfcReader/src/main/java/com/peerbits/creditCardNfcReader/CardNfcAsyncTask.java:
--------------------------------------------------------------------------------
1 | package com.peerbits.creditCardNfcReader;
2 |
3 | import android.content.Intent;
4 | import android.nfc.NfcAdapter;
5 | import android.nfc.Tag;
6 | import android.nfc.tech.IsoDep;
7 | import android.os.AsyncTask;
8 | import android.util.Log;
9 |
10 | import com.peerbits.creditCardNfcReader.enums.EmvCardScheme;
11 | import com.peerbits.creditCardNfcReader.model.EmvCard;
12 | import com.peerbits.creditCardNfcReader.parser.EmvParser;
13 | import com.peerbits.creditCardNfcReader.utils.Provider;
14 |
15 |
16 | import org.apache.commons.io.IOUtils;
17 | import org.apache.commons.lang3.StringUtils;
18 |
19 | import java.io.IOException;
20 |
21 | /**
22 | * Created by pro100svitlo on 21.03.16.
23 | */
24 | public class CardNfcAsyncTask extends AsyncTask{
25 |
26 | public static class Builder {
27 | private Tag mTag;
28 | private CardNfcInterface mInterface;
29 | private boolean mFromStart;
30 |
31 |
32 | public Builder(CardNfcInterface i, Intent intent, boolean fromCreate) {
33 | mInterface = i;
34 | mTag = intent.getParcelableExtra(NfcAdapter.EXTRA_TAG);
35 | mFromStart = fromCreate;
36 | }
37 |
38 | public CardNfcAsyncTask build() {
39 | return new CardNfcAsyncTask(this);
40 | }
41 | }
42 |
43 | public interface CardNfcInterface {
44 | void startNfcReadCard();
45 |
46 | void cardIsReadyToRead();
47 |
48 | void doNotMoveCardSoFast();
49 |
50 | void unknownEmvCard();
51 |
52 | void cardWithLockedNfc();
53 |
54 | void finishNfcReadCard();
55 | }
56 |
57 | public final static String CARD_UNKNOWN = EmvCardScheme.UNKNOWN.toString();
58 | public final static String CARD_VISA = EmvCardScheme.VISA.toString();
59 | public final static String CARD_NAB_VISA = EmvCardScheme.NAB_VISA.toString();
60 | public final static String CARD_MASTER_CARD = EmvCardScheme.MASTER_CARD.toString();
61 | public final static String CARD_AMERICAN_EXPRESS = EmvCardScheme.AMERICAN_EXPRESS.toString();
62 | public final static String CARD_CB = EmvCardScheme.CB.toString();
63 | public final static String CARD_LINK = EmvCardScheme.LINK.toString();
64 | public final static String CARD_JCB = EmvCardScheme.JCB.toString();
65 | public final static String CARD_DANKORT = EmvCardScheme.DANKORT.toString();
66 | public final static String CARD_COGEBAN = EmvCardScheme.COGEBAN.toString();
67 | public final static String CARD_DISCOVER = EmvCardScheme.DISCOVER.toString();
68 | public final static String CARD_BANRISUL = EmvCardScheme.BANRISUL.toString();
69 | public final static String CARD_SPAN = EmvCardScheme.SPAN.toString();
70 | public final static String CARD_INTERAC = EmvCardScheme.INTERAC.toString();
71 | public final static String CARD_ZIP = EmvCardScheme.ZIP.toString();
72 | public final static String CARD_UNIONPAY = EmvCardScheme.UNIONPAY.toString();
73 | public final static String CARD_EAPS = EmvCardScheme.EAPS.toString();
74 | public final static String CARD_VERVE = EmvCardScheme.VERVE.toString();
75 | public final static String CARD_TENN = EmvCardScheme.TENN.toString();
76 | public final static String CARD_RUPAY = EmvCardScheme.RUPAY.toString();
77 | public final static String CARD_ПРО100 = EmvCardScheme.ПРО100.toString();
78 | public final static String CARD_ZKA = EmvCardScheme.ZKA.toString();
79 | public final static String CARD_BANKAXEPT = EmvCardScheme.BANKAXEPT.toString();
80 | public final static String CARD_BRADESCO = EmvCardScheme.BRADESCO.toString();
81 | public final static String CARD_MIDLAND = EmvCardScheme.MIDLAND.toString();
82 | public final static String CARD_PBS = EmvCardScheme.PBS.toString();
83 | public final static String CARD_ETRANZACT = EmvCardScheme.ETRANZACT.toString();
84 | public final static String CARD_GOOGLE = EmvCardScheme.GOOGLE.toString();
85 | public final static String CARD_INTER_SWITCH = EmvCardScheme.INTER_SWITCH.toString();
86 |
87 | private final static String NFC_A_TAG = "TAG: Tech [android.nfc.tech.IsoDep, android.nfc.tech.NfcA]";
88 | private final static String NFC_B_TAG = "TAG: Tech [android.nfc.tech.IsoDep, android.nfc.tech.NfcB]";
89 | private final String UNKNOWN_CARD_MESS =
90 | "===========================================================================\n\n"+
91 | "Hi! This library is not familiar with your credit card. \n " +
92 | "Please, write me an email with information of your bank: \n" +
93 | "country, bank name, card type, etc) and i will try to do my best, \n" +
94 | "to add your bank as a known one into this lib. \n" +
95 | "Great thanks for using and reporting!!! \n" +
96 | "Here is my email: pro100svitlo@gmail.com. \n\n" +
97 | "===========================================================================";
98 |
99 | private Provider mProvider = new Provider();
100 | private boolean mException;
101 | private EmvCard mCard;
102 | private CardNfcInterface mInterface;
103 | private Tag mTag;
104 | private String mCardNumber;
105 | private String mExpireDate;
106 | private String mCardType;
107 | private String mHolderFirstName;
108 | private String mHolderLastName;
109 | private int mCardCvv;
110 |
111 | private CardNfcAsyncTask(Builder b) {
112 | mTag = b.mTag;
113 | if (mTag != null) {
114 | mInterface = b.mInterface;
115 | try {
116 | if (mTag.toString().equals(NFC_A_TAG) || mTag.toString().equals(NFC_B_TAG)) {
117 | execute();
118 | } else {
119 | if (!b.mFromStart) {
120 | mInterface.unknownEmvCard();
121 | }
122 | clearAll();
123 | }
124 | } catch (NullPointerException e) {
125 | e.printStackTrace();
126 | }
127 | }
128 | }
129 |
130 | public String getCardNumber() {
131 | return mCardNumber;
132 | }
133 |
134 | public String getCardExpireDate() {
135 | return mExpireDate;
136 | }
137 |
138 | public String getCardType() {
139 | return mCardType;
140 | }
141 |
142 | public String getCardFirstName() {
143 | return mHolderFirstName;
144 | }
145 |
146 | public String getCardLastName() {
147 | return mHolderLastName;
148 | }
149 |
150 | public int getCardCvv() {
151 | return mCardCvv;
152 | }
153 |
154 |
155 | @Override
156 | protected void onPreExecute() {
157 | super.onPreExecute();
158 | mInterface.startNfcReadCard();
159 | mProvider.getLog().setLength(0);
160 | }
161 |
162 | @Override
163 | protected Object doInBackground(final Void... params) {
164 |
165 | Object result = null;
166 |
167 | try {
168 | doInBackground();
169 | } catch (Exception e) {
170 | result = e;
171 | Log.e(CardNfcAsyncTask.class.getName(), e.getMessage(), e);
172 | }
173 |
174 | return result;
175 | }
176 |
177 | @Override
178 | protected void onPostExecute(final Object result) {
179 | if (!mException) {
180 | if (mCard != null) {
181 | if (StringUtils.isNotBlank(mCard.getCardNumber())) {
182 | /* mCardNumber = mCard.getCardNumber();
183 | mExpireDate = mCard.getExpireDate();
184 | mCardType = mCard.getType().toString();*/
185 |
186 | mCardNumber = mCard.getCardNumber() +mCard.getHolderFirstname() +mCard.getHolderLastname();
187 | mExpireDate = mCard.getExpireDate() +mCard.getLeftPinTry();
188 | mCardType = mCard.getType().toString();
189 | mHolderFirstName = mCard.getHolderFirstname();
190 | mHolderLastName = mCard.getHolderLastname();
191 | mCardCvv = mCard.getLeftPinTry();
192 | Log.e("mHolderLastName", "--> "+mCard.getHolderLastname());
193 | Log.e("mHolderFirstName", "--> "+mCard.getHolderFirstname());
194 |
195 | if (mCardType.equals(EmvCardScheme.UNKNOWN.toString())){
196 | Log.d("creditCardNfcReader", UNKNOWN_CARD_MESS);
197 | }
198 | mInterface.cardIsReadyToRead();
199 | } else if (mCard.isNfcLocked()) {
200 | mInterface.cardWithLockedNfc();
201 | }
202 | } else {
203 | mInterface.unknownEmvCard();
204 | }
205 | } else {
206 | mInterface.doNotMoveCardSoFast();
207 | }
208 | mInterface.finishNfcReadCard();
209 | clearAll();
210 | }
211 |
212 | private void doInBackground(){
213 | IsoDep mIsoDep = IsoDep.get(mTag);
214 | if (mIsoDep == null) {
215 | mInterface.doNotMoveCardSoFast();
216 | return;
217 | }
218 | mException = false;
219 |
220 | try {
221 | // Open connection
222 | mIsoDep.connect();
223 |
224 | mProvider.setmTagCom(mIsoDep);
225 |
226 | EmvParser parser = new EmvParser(mProvider, true);
227 | mCard = parser.readEmvCard();
228 | } catch (IOException e) {
229 | mException = true;
230 | } finally {
231 | IOUtils.closeQuietly(mIsoDep);
232 | }
233 | }
234 |
235 | private void clearAll() {
236 | mInterface = null;
237 | mProvider = null;
238 | mCard = null;
239 | mTag = null;
240 | mCardNumber = null;
241 | mExpireDate = null;
242 | mCardType = null;
243 | mHolderFirstName =null;
244 | mHolderLastName = null;
245 | }
246 | }
--------------------------------------------------------------------------------
/creditCardNfcReader/src/main/java/com/peerbits/creditCardNfcReader/enums/CommandEnum.java:
--------------------------------------------------------------------------------
1 | package com.peerbits.creditCardNfcReader.enums;
2 |
3 | /**
4 | * Enum which define all EMV apdu
5 | *
6 | */
7 | public enum CommandEnum {
8 |
9 | /**
10 | * Select command
11 | */
12 | SELECT(0x00, 0xA4, 0x04, 0x00),
13 |
14 | /**
15 | * Read record command
16 | */
17 | READ_RECORD(0x00, 0xB2, 0x00, 0x00),
18 |
19 | /**
20 | * GPO Command
21 | */
22 | GPO(0x80, 0xA8, 0x00, 0x00),
23 |
24 | /**
25 | * GPO Command
26 | */
27 | GET_DATA(0x80, 0xCA, 0x00, 0x00);
28 |
29 | /**
30 | * Class byte
31 | */
32 | private final int cla;
33 |
34 | /**
35 | * Instruction byte
36 | */
37 | private final int ins;
38 |
39 | /**
40 | * Parameter 1 byte
41 | */
42 | private final int p1;
43 |
44 | /**
45 | * Parameter 2 byte
46 | */
47 | private final int p2;
48 |
49 | /**
50 | * Constructor using field
51 | *
52 | * @param cla
53 | * class
54 | * @param ins
55 | * instruction
56 | * @param p1
57 | * parameter 1
58 | * @param p2
59 | * parameter 2
60 | */
61 | private CommandEnum(final int cla, final int ins, final int p1, final int p2) {
62 | this.cla = cla;
63 | this.ins = ins;
64 | this.p1 = p1;
65 | this.p2 = p2;
66 | }
67 |
68 | /**
69 | * Method used to get the field cla
70 | *
71 | * @return the cla
72 | */
73 | public int getCla() {
74 | return cla;
75 | }
76 |
77 | /**
78 | * Method used to get the field ins
79 | *
80 | * @return the ins
81 | */
82 | public int getIns() {
83 | return ins;
84 | }
85 |
86 | /**
87 | * Method used to get the field p1
88 | *
89 | * @return the p1
90 | */
91 | public int getP1() {
92 | return p1;
93 | }
94 |
95 | /**
96 | * Method used to get the field p2
97 | *
98 | * @return the p2
99 | */
100 | public int getP2() {
101 | return p2;
102 | }
103 |
104 | }
105 |
--------------------------------------------------------------------------------
/creditCardNfcReader/src/main/java/com/peerbits/creditCardNfcReader/enums/EmvCardScheme.java:
--------------------------------------------------------------------------------
1 | package com.peerbits.creditCardNfcReader.enums;
2 |
3 | import com.peerbits.creditCardNfcReader.utils.BytesUtils;
4 |
5 | import org.apache.commons.lang3.StringUtils;
6 |
7 | import java.util.regex.Pattern;
8 |
9 |
10 | /**
11 | * Class used to define all supported NFC EMV paycard. http://en.wikipedia.org/wiki/Europay_Mastercard_Visa
12 | *
13 | */
14 | public enum EmvCardScheme {
15 |
16 | UNKNOWN("",""),
17 |
18 | VISA("VISA", "^4[0-9]{6,}$", "A0 00 00 00 03", "A0 00 00 00 03 10 10", "A0 00 00 00 98 08 48"), //
19 | NAB_VISA("VISA", "^4[0-9]{6,}$", "A0 00 00 00 03", "A0 00 00 03", "A0 00 00 00 03 10 10", "A0 00 00 00 98 08 48"),
20 | MASTER_CARD("Master card", "^5[1-5][0-9]{5,}$", "A0 00 00 00 04", "A0 00 00 00 05"), //
21 | AMERICAN_EXPRESS("American express", "^3[47][0-9]{5,}$", "A0 00 00 00 25"), //
22 | CB("CB", null, "A0 00 00 00 42"), //
23 | LINK("LINK", null, "A0 00 00 00 29"), //
24 | JCB("JCB", "^(?:2131|1800|35[0-9]{3})[0-9]{3,}$", "A0 00 00 00 65"), //
25 | DANKORT("Dankort", null, "A0 00 00 01 21 10 10"), //
26 | COGEBAN("CoGeBan", null, "A0 00 00 01 41 00 01"), //
27 | DISCOVER("Discover", "(6011|65|64[4-9]|622)[0-9]*", "A0 00 00 01 52 30 10"), //
28 | BANRISUL("Banrisul", null, "A0 00 00 01 54"), //
29 | SPAN("Saudi Payments Network", null, "A0 00 00 02 28"), //
30 | INTERAC("Interac", null, "A0 00 00 02 77"), //
31 | ZIP("Discover Card", null, "A0 00 00 03 24"), //
32 | UNIONPAY("UnionPay", "^62[0-9]{14,17}", "A0 00 00 03 33"), //
33 | EAPS("Euro Alliance of Payment Schemes", null, "A0 00 00 03 59"), //
34 | VERVE("Verve", null, "A0 00 00 03 71"), //
35 | TENN("The Exchange Network ATM Network", null, "A0 00 00 04 39"), //
36 | RUPAY("Rupay", null, "A0 00 00 05 24 10 10"), //
37 | ПРО100("ПРО100", null, "A0 00 00 04 32 00 01"), //
38 | ZKA("ZKA", null, "D2 76 00 00 25 45 50 01 00"), //
39 | BANKAXEPT("Bankaxept", null, "D5 78 00 00 02 10 10"), //
40 | BRADESCO("BRADESCO", null, "F0 00 00 00 03 00 01"),
41 | MIDLAND("Midland", null, "A0 00 00 00 24 01"), //
42 | PBS("PBS", null, "A0 00 00 01 21 10 10"), //
43 | ETRANZACT("eTranzact", null, "A0 00 00 04 54"), //
44 | GOOGLE("Google", null, "A0 00 00 04 76 6C"), //
45 | INTER_SWITCH("InterSwitch", null, "A0 00 00 03 71 00 01");
46 |
47 | /**
48 | * array of Card AID or partial AID (RID)
49 | */
50 | private final String[] aids;
51 |
52 | /**
53 | * array of Aid in byte
54 | */
55 | private final byte[][] aidsByte;
56 |
57 | /**
58 | * Card scheme (card number IIN ranges)
59 | */
60 | private final String name;
61 |
62 | /**
63 | * Card number pattern regex
64 | */
65 | private final Pattern pattern;
66 |
67 | /**
68 | * Constructor using fields
69 | *
70 | * @param
71 | * Card AID or RID
72 | * @param pScheme
73 | * scheme name
74 | * @param pRegex
75 | * Card regex
76 | */
77 | EmvCardScheme(final String pScheme, final String pRegex, final String... pAids) {
78 | aids = pAids;
79 | aidsByte = new byte[pAids.length][];
80 | for (int i = 0; i < aids.length; i++) {
81 | aidsByte[i] = BytesUtils.fromString(pAids[i]);
82 | }
83 | name = pScheme;
84 | if (StringUtils.isNotBlank(pRegex)) {
85 | pattern = Pattern.compile(pRegex);
86 | } else {
87 | pattern = null;
88 | }
89 | }
90 |
91 | /**
92 | * Method used to get the field aid
93 | *
94 | * @return the aid
95 | */
96 | public String[] getAid() {
97 | return aids;
98 | }
99 |
100 | /**
101 | * Method used to get the field name
102 | *
103 | * @return the name
104 | */
105 | public String getName() {
106 | return name;
107 | }
108 |
109 | /**
110 | * Get card type by AID
111 | *
112 | * @param pAid
113 | * card AID
114 | * @return CardType or null
115 | */
116 | public static EmvCardScheme getCardTypeByAid(final String pAid) {
117 | EmvCardScheme ret = EmvCardScheme.UNKNOWN ;
118 | if (pAid != null) {
119 | String aid = StringUtils.deleteWhitespace(pAid);
120 | for (EmvCardScheme val : EmvCardScheme.values()) {
121 | for (String schemeAid : val.getAid()) {
122 | if (aid.startsWith(StringUtils.deleteWhitespace(schemeAid))) {
123 | ret = val;
124 | break;
125 | }
126 | }
127 | }
128 | }
129 | return ret;
130 | }
131 |
132 | /**
133 | * Method used to the the card type with regex
134 | *
135 | * @param pCardNumber
136 | * card number
137 | * @return the type of the card using regex
138 | */
139 | public static EmvCardScheme getCardTypeByCardNumber(final String pCardNumber) {
140 | EmvCardScheme ret = EmvCardScheme.UNKNOWN;
141 | if (pCardNumber != null) {
142 | for (EmvCardScheme val : EmvCardScheme.values()) {
143 | if (val.pattern != null && val.pattern.matcher(StringUtils.deleteWhitespace(pCardNumber)).matches()) {
144 | ret = val;
145 | break;
146 | }
147 | }
148 | }
149 | return ret;
150 | }
151 |
152 | /**
153 | * Method used to get the field aidByte
154 | *
155 | * @return the aidByte
156 | */
157 | public byte[][] getAidByte() {
158 | return aidsByte;
159 | }
160 |
161 | }
162 |
--------------------------------------------------------------------------------
/creditCardNfcReader/src/main/java/com/peerbits/creditCardNfcReader/enums/TagTypeEnum.java:
--------------------------------------------------------------------------------
1 | package com.peerbits.creditCardNfcReader.enums;
2 |
3 | public enum TagTypeEnum {
4 |
5 | /**
6 | * The value field of a primitive data object contains a data element for financial transaction interchange
7 | */
8 | PRIMITIVE,
9 | /**
10 | * The value field of a constructed data object contains one or more primitive or constructed data objects. The value field of
11 | * a constructed data object is called a template.
12 | */
13 | CONSTRUCTED
14 | }
--------------------------------------------------------------------------------
/creditCardNfcReader/src/main/java/com/peerbits/creditCardNfcReader/enums/TagValueTypeEnum.java:
--------------------------------------------------------------------------------
1 | package com.peerbits.creditCardNfcReader.enums;
2 |
3 | public enum TagValueTypeEnum {
4 | BINARY, NUMERIC, TEXT, MIXED, DOL, TEMPLATE
5 | }
6 |
--------------------------------------------------------------------------------
/creditCardNfcReader/src/main/java/com/peerbits/creditCardNfcReader/exception/CommunicationException.java:
--------------------------------------------------------------------------------
1 | package com.peerbits.creditCardNfcReader.exception;
2 |
3 | import java.io.IOException;
4 |
5 | /**
6 | * Exception during communication with EMV card
7 | *
8 | */
9 | public class CommunicationException extends IOException {
10 |
11 | /**
12 | * Default constructor
13 | *
14 | * @param pMessage
15 | * Exception message
16 | */
17 | public CommunicationException(final String pMessage) {
18 | super(pMessage);
19 | }
20 |
21 | }
22 |
--------------------------------------------------------------------------------
/creditCardNfcReader/src/main/java/com/peerbits/creditCardNfcReader/exception/TlvException.java:
--------------------------------------------------------------------------------
1 | package com.peerbits.creditCardNfcReader.exception;
2 |
3 | /**
4 | * Exception during TLV reading
5 | *
6 | */
7 | public class TlvException extends RuntimeException {
8 |
9 | /**
10 | * Constructor using field
11 | *
12 | * @param pCause
13 | * cause
14 | */
15 | public TlvException(final String pCause) {
16 | super(pCause);
17 | }
18 |
19 | }
20 |
--------------------------------------------------------------------------------
/creditCardNfcReader/src/main/java/com/peerbits/creditCardNfcReader/iso7816emv/ByteArrayWrapper.java:
--------------------------------------------------------------------------------
1 | package com.peerbits.creditCardNfcReader.iso7816emv;
2 |
3 | import java.util.Arrays;
4 |
5 | public final class ByteArrayWrapper {
6 |
7 | private final byte[] data;
8 | private final int hashcode;
9 |
10 | private ByteArrayWrapper(final byte[] data) {
11 | this.data = data;
12 | hashcode = Arrays.hashCode(data);
13 | }
14 |
15 | public static ByteArrayWrapper wrapperAround(final byte[] data) {
16 | if (data == null) {
17 | throw new NullPointerException();
18 | }
19 | return new ByteArrayWrapper(data);
20 | }
21 |
22 | @Override
23 | public boolean equals(final Object other) {
24 | if (!(other instanceof ByteArrayWrapper)) {
25 | return false;
26 | }
27 | return Arrays.equals(data, ((ByteArrayWrapper) other).data);
28 | }
29 |
30 | @Override
31 | public int hashCode() {
32 | return hashcode;
33 | }
34 | }
--------------------------------------------------------------------------------
/creditCardNfcReader/src/main/java/com/peerbits/creditCardNfcReader/iso7816emv/EmvTerminal.java:
--------------------------------------------------------------------------------
1 | package com.peerbits.creditCardNfcReader.iso7816emv;
2 |
3 | import com.peerbits.creditCardNfcReader.utils.BytesUtils;
4 | import com.peerbits.creditCardNfcReader.model.enums.CountryCodeEnum;
5 | import com.peerbits.creditCardNfcReader.model.enums.CurrencyEnum;
6 | import com.peerbits.creditCardNfcReader.model.enums.TransactionTypeEnum;
7 |
8 | import org.apache.commons.lang3.StringUtils;
9 |
10 | import java.security.SecureRandom;
11 | import java.text.SimpleDateFormat;
12 | import java.util.Date;
13 |
14 | /**
15 | * Factory to create Tag value
16 | */
17 | public final class EmvTerminal {
18 |
19 | /**
20 | * Random
21 | */
22 | private static final SecureRandom random = new SecureRandom();
23 |
24 | /**
25 | * Method used to construct value from tag and length
26 | *
27 | * @param pTagAndLength
28 | * tag and length value
29 | * @return tag value in byte
30 | */
31 | public static byte[] constructValue(final TagAndLength pTagAndLength) {
32 | byte ret[] = new byte[pTagAndLength.getLength()];
33 | byte val[] = null;
34 | if (pTagAndLength.getTag() == EmvTags.TERMINAL_TRANSACTION_QUALIFIERS) {
35 | TerminalTransactionQualifiers terminalQual = new TerminalTransactionQualifiers();
36 | terminalQual.setContactlessEMVmodeSupported(true);
37 | terminalQual.setReaderIsOfflineOnly(true);
38 | val = terminalQual.getBytes();
39 | } else if (pTagAndLength.getTag() == EmvTags.TERMINAL_COUNTRY_CODE) {
40 | val = BytesUtils.fromString(StringUtils.leftPad(String.valueOf(CountryCodeEnum.FR.getNumeric()), pTagAndLength.getLength() * 2,
41 | "0"));
42 | } else if (pTagAndLength.getTag() == EmvTags.TRANSACTION_CURRENCY_CODE) {
43 | val = BytesUtils.fromString(StringUtils.leftPad(String.valueOf(CurrencyEnum.EUR.getISOCodeNumeric()),
44 | pTagAndLength.getLength() * 2, "0"));
45 | } else if (pTagAndLength.getTag() == EmvTags.TRANSACTION_DATE) {
46 | SimpleDateFormat sdf = new SimpleDateFormat("yyMMdd");
47 | val = BytesUtils.fromString(sdf.format(new Date()));
48 | } else if (pTagAndLength.getTag() == EmvTags.TRANSACTION_TYPE) {
49 | val = new byte[] { (byte) TransactionTypeEnum.PURCHASE.getKey() };
50 | } else if (pTagAndLength.getTag() == EmvTags.AMOUNT_AUTHORISED_NUMERIC) {
51 | val = BytesUtils.fromString("00");
52 | } else if (pTagAndLength.getTag() == EmvTags.TERMINAL_TYPE) {
53 | val = new byte[] { 0x22 };
54 | } else if (pTagAndLength.getTag() == EmvTags.TERMINAL_CAPABILITIES) {
55 | val = new byte[] { (byte) 0xE0, (byte) 0xA0, 0x00 };
56 | } else if (pTagAndLength.getTag() == EmvTags.ADDITIONAL_TERMINAL_CAPABILITIES) {
57 | val = new byte[] { (byte) 0x8e, (byte) 0, (byte) 0xb0, 0x50, 0x05 };
58 | } else if (pTagAndLength.getTag() == EmvTags.DS_REQUESTED_OPERATOR_ID) {
59 | val = BytesUtils.fromString("7345123215904501");
60 | } else if (pTagAndLength.getTag() == EmvTags.UNPREDICTABLE_NUMBER) {
61 | random.nextBytes(ret);
62 | }
63 | if (val != null) {
64 | System.arraycopy(val, 0, ret, 0, Math.min(val.length, ret.length));
65 | }
66 | return ret;
67 | }
68 |
69 | /**
70 | * Private Constructor
71 | */
72 | private EmvTerminal() {
73 | }
74 |
75 | }
76 |
--------------------------------------------------------------------------------
/creditCardNfcReader/src/main/java/com/peerbits/creditCardNfcReader/iso7816emv/ITag.java:
--------------------------------------------------------------------------------
1 | package com.peerbits.creditCardNfcReader.iso7816emv;
2 |
3 | import com.peerbits.creditCardNfcReader.enums.TagTypeEnum;
4 | import com.peerbits.creditCardNfcReader.enums.TagValueTypeEnum;
5 |
6 |
7 | public interface ITag {
8 |
9 | enum Class {
10 | UNIVERSAL, APPLICATION, CONTEXT_SPECIFIC, PRIVATE
11 | }
12 |
13 | boolean isConstructed();
14 |
15 | byte[] getTagBytes();
16 |
17 | String getName();
18 |
19 | String getDescription();
20 |
21 | TagTypeEnum getType();
22 |
23 | TagValueTypeEnum getTagValueType();
24 |
25 | Class getTagClass();
26 |
27 | int getNumTagBytes();
28 |
29 | }
30 |
--------------------------------------------------------------------------------
/creditCardNfcReader/src/main/java/com/peerbits/creditCardNfcReader/iso7816emv/TLV.java:
--------------------------------------------------------------------------------
1 | package com.peerbits.creditCardNfcReader.iso7816emv;
2 |
3 | /**
4 | * Tag and length value
5 | *
6 | */
7 | public class TLV {
8 |
9 | /**
10 | * Tag
11 | */
12 | private ITag tag;
13 | /**
14 | * length in bytes
15 | */
16 | private byte[] rawEncodedLengthBytes;
17 | /**
18 | * Value in bytes
19 | */
20 | private byte[] valueBytes;
21 | /**
22 | * Tag length
23 | */
24 | private int length;
25 |
26 | /**
27 | *
28 | * @param tag
29 | * @param length
30 | * contains the number of value bytes (parsed from the rawEncodedLengthBytes)
31 | * @param rawLengthBytes
32 | * the raw encoded length bytes
33 | * @param valueBytes
34 | */
35 | public TLV(final ITag tag, final int length, final byte[] rawEncodedLengthBytes, final byte[] valueBytes) {
36 | if (valueBytes == null || length != valueBytes.length) {
37 | // Assert
38 | throw new IllegalArgumentException("length != bytes.length");
39 | }
40 | this.tag = tag;
41 | this.rawEncodedLengthBytes = rawEncodedLengthBytes;
42 | this.valueBytes = valueBytes;
43 | this.length = length;
44 | }
45 |
46 | /**
47 | * Method used to get the field tag
48 | *
49 | * @return the tag
50 | */
51 | public ITag getTag() {
52 | return tag;
53 | }
54 |
55 | /**
56 | * Setter for the field tag
57 | *
58 | * @param tag
59 | * the tag to set
60 | */
61 | public void setTag(final ITag tag) {
62 | this.tag = tag;
63 | }
64 |
65 | /**
66 | * Method used to get the field rawEncodedLengthBytes
67 | *
68 | * @return the rawEncodedLengthBytes
69 | */
70 | public byte[] getRawEncodedLengthBytes() {
71 | return rawEncodedLengthBytes;
72 | }
73 |
74 | /**
75 | * Setter for the field rawEncodedLengthBytes
76 | *
77 | * @param rawEncodedLengthBytes
78 | * the rawEncodedLengthBytes to set
79 | */
80 | public void setRawEncodedLengthBytes(final byte[] rawEncodedLengthBytes) {
81 | this.rawEncodedLengthBytes = rawEncodedLengthBytes;
82 | }
83 |
84 | /**
85 | * Method used to get the field valueBytes
86 | *
87 | * @return the valueBytes
88 | */
89 | public byte[] getValueBytes() {
90 | return valueBytes;
91 | }
92 |
93 | /**
94 | * Setter for the field valueBytes
95 | *
96 | * @param valueBytes
97 | * the valueBytes to set
98 | */
99 | public void setValueBytes(final byte[] valueBytes) {
100 | this.valueBytes = valueBytes;
101 | }
102 |
103 | /**
104 | * Method used to get the field length
105 | *
106 | * @return the length
107 | */
108 | public int getLength() {
109 | return length;
110 | }
111 |
112 | /**
113 | * Setter for the field length
114 | *
115 | * @param length
116 | * the length to set
117 | */
118 | public void setLength(final int length) {
119 | this.length = length;
120 | }
121 |
122 | /**
123 | * Get tag bytes
124 | *
125 | * @return tag bytes
126 | */
127 | public byte[] getTagBytes() {
128 | return tag.getTagBytes();
129 | }
130 |
131 | }
132 |
--------------------------------------------------------------------------------
/creditCardNfcReader/src/main/java/com/peerbits/creditCardNfcReader/iso7816emv/TagAndLength.java:
--------------------------------------------------------------------------------
1 | package com.peerbits.creditCardNfcReader.iso7816emv;
2 |
3 | import java.util.Arrays;
4 |
5 | public class TagAndLength {
6 | private ITag tag;
7 | private int length;
8 |
9 | public TagAndLength(final ITag tag, final int length) {
10 | this.tag = tag;
11 | this.length = length;
12 | }
13 |
14 | public ITag getTag() {
15 | return tag;
16 | }
17 |
18 | public int getLength() {
19 | return length;
20 | }
21 |
22 | public byte[] getBytes() {
23 | byte[] tagBytes = tag.getTagBytes();
24 | byte[] tagAndLengthBytes = Arrays.copyOf(tagBytes, tagBytes.length + 1);
25 | tagAndLengthBytes[tagAndLengthBytes.length - 1] = (byte) length;
26 | return tagAndLengthBytes;
27 | }
28 |
29 | @Override
30 | public String toString() {
31 | return tag.toString() + " length: " + length;
32 | }
33 |
34 | }
35 |
--------------------------------------------------------------------------------
/creditCardNfcReader/src/main/java/com/peerbits/creditCardNfcReader/iso7816emv/TerminalTransactionQualifiers.java:
--------------------------------------------------------------------------------
1 | package com.peerbits.creditCardNfcReader.iso7816emv;
2 |
3 | import com.peerbits.creditCardNfcReader.utils.BytesUtils;
4 |
5 | import java.util.Arrays;
6 |
7 | /**
8 | * This implementation is a mix of EMV & VISA TTQ
9 | *
10 | * VISA: Terminal Transaction Qualifiers (Tag '9F66') is a reader data element indicating capabilities (e.g., MSD or qVSDC) and
11 | * transaction-specific requirements (e.g., online) of the reader. It is requested by the card in the PDOL and used by the card to
12 | * determine how to process the transaction (for example, process using MSD or qVSDC, process offline or online).
13 | *
14 | */
15 | public class TerminalTransactionQualifiers {
16 |
17 | private byte[] data = new byte[4];
18 |
19 | public TerminalTransactionQualifiers() {
20 | }
21 |
22 | public boolean contactlessMagneticStripeSupported() {
23 | return BytesUtils.matchBitByBitIndex(data[0], 7);
24 | }
25 |
26 | public boolean contactlessVSDCsupported() {
27 | return BytesUtils.matchBitByBitIndex(data[0], 6);
28 | }
29 |
30 | public boolean contactlessEMVmodeSupported() {
31 | return BytesUtils.matchBitByBitIndex(data[0], 5);
32 | }
33 |
34 | public boolean contactEMVsupported() {
35 | return BytesUtils.matchBitByBitIndex(data[0], 4);
36 | }
37 |
38 | public boolean readerIsOfflineOnly() {
39 | return BytesUtils.matchBitByBitIndex(data[0], 3);
40 | }
41 |
42 | public boolean onlinePINsupported() {
43 | return BytesUtils.matchBitByBitIndex(data[0], 2);
44 | }
45 |
46 | public boolean signatureSupported() {
47 | return BytesUtils.matchBitByBitIndex(data[0], 1);
48 | }
49 |
50 | public boolean onlineCryptogramRequired() {
51 | return BytesUtils.matchBitByBitIndex(data[1], 7);
52 | }
53 |
54 | public boolean cvmRequired() {
55 | return BytesUtils.matchBitByBitIndex(data[1], 6);
56 | }
57 |
58 | public boolean contactChipOfflinePINsupported() {
59 | return BytesUtils.matchBitByBitIndex(data[1], 5);
60 | }
61 |
62 | public boolean issuerUpdateProcessingSupported() {
63 | return BytesUtils.matchBitByBitIndex(data[2], 7);
64 | }
65 |
66 | public boolean consumerDeviceCVMsupported() {
67 | return BytesUtils.matchBitByBitIndex(data[2], 6);
68 | }
69 |
70 | public void setContactlessMagneticStripeSupported(final boolean value) {
71 | data[0] = BytesUtils.setBit(data[0], 7, value);
72 | }
73 |
74 | public void setContactlessVSDCsupported(final boolean value) {
75 | data[0] = BytesUtils.setBit(data[0], 6, value);
76 | if (value) {
77 | /*
78 | * A reader that supports contactless VSDC in addition to qVSDC shall not indicate support for qVSDC in the Terminal
79 | * Transaction Qualifiers (set byte 1 bit 6 to b'0'). The reader shall restore this bit to b'1' prior to deactivation
80 | */
81 | setContactlessEMVmodeSupported(false);
82 | }
83 | }
84 |
85 | public void setContactlessEMVmodeSupported(final boolean value) {
86 | data[0] = BytesUtils.setBit(data[0], 5, value);
87 | }
88 |
89 | public void setContactEMVsupported(final boolean value) {
90 | data[0] = BytesUtils.setBit(data[0], 4, value);
91 | }
92 |
93 | public void setReaderIsOfflineOnly(final boolean value) {
94 | data[0] = BytesUtils.setBit(data[0], 3, value);
95 | }
96 |
97 | public void setOnlinePINsupported(final boolean value) {
98 | data[0] = BytesUtils.setBit(data[0], 2, value);
99 | }
100 |
101 | public void setSignatureSupported(final boolean value) {
102 | data[0] = BytesUtils.setBit(data[0], 1, value);
103 | }
104 |
105 | public void setOnlineCryptogramRequired(final boolean value) {
106 | data[1] = BytesUtils.setBit(data[1], 7, value);
107 | }
108 |
109 | public void setCvmRequired(final boolean value) {
110 | data[1] = BytesUtils.setBit(data[1], 6, value);
111 | }
112 |
113 | public void setContactChipOfflinePINsupported(final boolean value) {
114 | data[1] = BytesUtils.setBit(data[1], 5, value);
115 | }
116 |
117 | public void setIssuerUpdateProcessingSupported(final boolean value) {
118 | data[2] = BytesUtils.setBit(data[2], 7, value);
119 | }
120 |
121 | public void setConsumerDeviceCVMsupported(final boolean value) {
122 | data[2] = BytesUtils.setBit(data[2], 6, value);
123 | }
124 |
125 | // The rest of the bits in the second byte are RFU (Reserved for Future Use)
126 |
127 | public byte[] getBytes() {
128 | return Arrays.copyOf(data, data.length);
129 | }
130 | }
--------------------------------------------------------------------------------
/creditCardNfcReader/src/main/java/com/peerbits/creditCardNfcReader/iso7816emv/impl/TagImpl.java:
--------------------------------------------------------------------------------
1 | package com.peerbits.creditCardNfcReader.iso7816emv.impl;
2 |
3 | import com.peerbits.creditCardNfcReader.utils.BytesUtils;
4 | import com.peerbits.creditCardNfcReader.enums.TagTypeEnum;
5 | import com.peerbits.creditCardNfcReader.enums.TagValueTypeEnum;
6 | import com.peerbits.creditCardNfcReader.iso7816emv.ITag;
7 |
8 | import java.util.Arrays;
9 |
10 |
11 | public final class TagImpl implements ITag {
12 |
13 | private final byte[] idBytes;
14 | public final String name;
15 | private final String description;
16 | private final TagValueTypeEnum tagValueType;
17 | private final Class tagClass;
18 | private final TagTypeEnum type;
19 |
20 | public TagImpl(final String id, final TagValueTypeEnum tagValueType, final String name, final String description) {
21 | this(BytesUtils.fromString(id), tagValueType, name, description);
22 | }
23 |
24 | public TagImpl(final byte[] idBytes, final TagValueTypeEnum tagValueType, final String name, final String description) {
25 | if (idBytes == null) {
26 | throw new IllegalArgumentException("Param id cannot be null");
27 | }
28 | if (idBytes.length == 0) {
29 | throw new IllegalArgumentException("Param id cannot be empty");
30 | }
31 | if (tagValueType == null) {
32 | throw new IllegalArgumentException("Param tagValueType cannot be null");
33 | }
34 | this.idBytes = idBytes;
35 | this.name = name;
36 | this.description = description;
37 | this.tagValueType = tagValueType;
38 |
39 | if (BytesUtils.matchBitByBitIndex(this.idBytes[0], 5)) {
40 | type = TagTypeEnum.CONSTRUCTED;
41 | } else {
42 | type = TagTypeEnum.PRIMITIVE;
43 | }
44 | // Bits 8 and 7 of the first byte of the tag field indicate a class.
45 | // The value 00 indicates a data object of the universal class.
46 | // The value 01 indicates a data object of the application class.
47 | // The value 10 indicates a data object of the context-specific class.
48 | // The value 11 indicates a data object of the private class.
49 | byte classValue = (byte) (this.idBytes[0] >>> 6 & 0x03);
50 | switch (classValue) {
51 | case (byte) 0x01:
52 | tagClass = Class.APPLICATION;
53 | break;
54 | case (byte) 0x02:
55 | tagClass = Class.CONTEXT_SPECIFIC;
56 | break;
57 | case (byte) 0x03:
58 | tagClass = Class.PRIVATE;
59 | break;
60 | default:
61 | tagClass = Class.UNIVERSAL;
62 | break;
63 | }
64 |
65 | }
66 |
67 | @Override
68 | public boolean isConstructed() {
69 | return type == TagTypeEnum.CONSTRUCTED;
70 | }
71 |
72 | @Override
73 | public byte[] getTagBytes() {
74 | return idBytes;
75 | }
76 |
77 | @Override
78 | public String getName() {
79 | return name;
80 | }
81 |
82 | @Override
83 | public String getDescription() {
84 | return description;
85 | }
86 |
87 | @Override
88 | public TagValueTypeEnum getTagValueType() {
89 | return tagValueType;
90 | }
91 |
92 | @Override
93 | public TagTypeEnum getType() {
94 | return type;
95 | }
96 |
97 | @Override
98 | public Class getTagClass() {
99 | return tagClass;
100 | }
101 |
102 | @Override
103 | public boolean equals(final Object other) {
104 | if (!(other instanceof ITag)) {
105 | return false;
106 | }
107 | ITag that = (ITag) other;
108 | if (getTagBytes().length != that.getTagBytes().length) {
109 | return false;
110 | }
111 |
112 | return Arrays.equals(getTagBytes(), that.getTagBytes());
113 | }
114 |
115 | @Override
116 | public int hashCode() {
117 | int hash = 3;
118 | hash = 59 * hash + Arrays.hashCode(idBytes);
119 | return hash;
120 | }
121 |
122 | @Override
123 | public int getNumTagBytes() {
124 | return idBytes.length;
125 | }
126 |
127 | @Override
128 | public String toString() {
129 | StringBuilder sb = new StringBuilder();
130 | sb.append("Tag[");
131 | sb.append(BytesUtils.bytesToString(getTagBytes()));
132 | sb.append("] Name=");
133 | sb.append(getName());
134 | sb.append(", TagType=");
135 | sb.append(getType());
136 | sb.append(", ValueType=");
137 | sb.append(getTagValueType());
138 | sb.append(", Class=");
139 | sb.append(tagClass);
140 | return sb.toString();
141 | }
142 | }
--------------------------------------------------------------------------------
/creditCardNfcReader/src/main/java/com/peerbits/creditCardNfcReader/model/AbstractData.java:
--------------------------------------------------------------------------------
1 | package com.peerbits.creditCardNfcReader.model;
2 |
3 | import org.apache.commons.lang3.builder.ToStringBuilder;
4 |
5 | import java.io.Serializable;
6 |
7 | /**
8 | * Abstract class used to provide some commons methods to bean
9 | *
10 | */
11 | public abstract class AbstractData implements Serializable {
12 |
13 | /**
14 | * Generated serial UID
15 | */
16 | private static final long serialVersionUID = -456811026151402726L;
17 |
18 | @Override
19 | public String toString() {
20 | return ToStringBuilder.reflectionToString(this);
21 | }
22 |
23 | }
24 |
--------------------------------------------------------------------------------
/creditCardNfcReader/src/main/java/com/peerbits/creditCardNfcReader/model/Afl.java:
--------------------------------------------------------------------------------
1 | package com.peerbits.creditCardNfcReader.model;
2 |
3 | /**
4 | * Class used to describe Application file locator
5 | *
6 | */
7 | public class Afl {
8 |
9 | /**
10 | * SFI
11 | */
12 | private int sfi;
13 |
14 | /**
15 | * record
16 | */
17 | private int firstRecord;
18 |
19 | /**
20 | * Last record
21 | */
22 | private int lastRecord;
23 |
24 | /**
25 | * Offline authentication
26 | */
27 | private boolean offlineAuthentication;
28 |
29 | /**
30 | * Method used to get the field sfi
31 | *
32 | * @return the sfi
33 | */
34 | public int getSfi() {
35 | return sfi;
36 | }
37 |
38 | /**
39 | * Setter for the field sfi
40 | *
41 | * @param sfi
42 | * the sfi to set
43 | */
44 | public void setSfi(final int sfi) {
45 | this.sfi = sfi;
46 | }
47 |
48 | /**
49 | * Method used to get the field firstRecord
50 | *
51 | * @return the firstRecord
52 | */
53 | public int getFirstRecord() {
54 | return firstRecord;
55 | }
56 |
57 | /**
58 | * Setter for the field firstRecord
59 | *
60 | * @param firstRecord
61 | * the firstRecord to set
62 | */
63 | public void setFirstRecord(final int firstRecord) {
64 | this.firstRecord = firstRecord;
65 | }
66 |
67 | /**
68 | * Method used to get the field lastRecord
69 | *
70 | * @return the lastRecord
71 | */
72 | public int getLastRecord() {
73 | return lastRecord;
74 | }
75 |
76 | /**
77 | * Setter for the field lastRecord
78 | *
79 | * @param lastRecord
80 | * the lastRecord to set
81 | */
82 | public void setLastRecord(final int lastRecord) {
83 | this.lastRecord = lastRecord;
84 | }
85 |
86 | /**
87 | * Method used to get the field offlineAuthentication
88 | *
89 | * @return the offlineAuthentication
90 | */
91 | public boolean isOfflineAuthentication() {
92 | return offlineAuthentication;
93 | }
94 |
95 | /**
96 | * Setter for the field offlineAuthentication
97 | *
98 | * @param offlineAuthentication
99 | * the offlineAuthentication to set
100 | */
101 | public void setOfflineAuthentication(final boolean offlineAuthentication) {
102 | this.offlineAuthentication = offlineAuthentication;
103 | }
104 |
105 | }
106 |
--------------------------------------------------------------------------------
/creditCardNfcReader/src/main/java/com/peerbits/creditCardNfcReader/model/EmvCard.java:
--------------------------------------------------------------------------------
1 | package com.peerbits.creditCardNfcReader.model;
2 |
3 | import com.peerbits.creditCardNfcReader.enums.EmvCardScheme;
4 |
5 | import java.util.Collection;
6 | import java.util.List;
7 |
8 | /**
9 | * Bean used to describe data in EMV card
10 | *
11 | */
12 | public class EmvCard extends AbstractData {
13 |
14 | /**
15 | * Generated serial UID
16 | */
17 | private static final long serialVersionUID = 736740432469989941L;
18 |
19 | /**
20 | * Card AID
21 | */
22 | private String aid;
23 |
24 | /**
25 | * Holder Lastname
26 | */
27 | private String holderLastname;
28 |
29 | /**
30 | * Holder Firstname
31 | */
32 | private String holderFirstname;
33 |
34 | /**
35 | * Card number
36 | */
37 | private String cardNumber;
38 |
39 | /**
40 | * Expiration date
41 | */
42 | private String expireDate;
43 |
44 | /**
45 | * Card type
46 | */
47 | private EmvCardScheme type;
48 |
49 | /**
50 | * Left PIN try
51 | */
52 | private int leftPinTry;
53 |
54 | /**
55 | * Application label
56 | */
57 | private String applicationLabel;
58 |
59 | /**
60 | * List of issued payment
61 | */
62 | private List listTransactions;
63 |
64 | /**
65 | * List of Atr description
66 | */
67 | private Collection atrDescription;
68 |
69 | /**
70 | * Card services
71 | */
72 | private Service service;
73 |
74 | /**
75 | * Indicate if the nfc is locked on the card
76 | */
77 | private boolean nfcLocked;
78 |
79 | /**
80 | * Method used to get the field aid
81 | *
82 | * @return the aid
83 | */
84 | public String getAid() {
85 | return aid;
86 | }
87 |
88 | /**
89 | * Setter for the field aid
90 | *
91 | * @param aid
92 | * the aid to set
93 | */
94 | public void setAid(final String aid) {
95 | this.aid = aid;
96 | }
97 |
98 | /**
99 | * Method used to get the field holderLastname
100 | *
101 | * @return the holderLastname
102 | */
103 | public String getHolderLastname() {
104 | return holderLastname;
105 | }
106 |
107 | /**
108 | * Setter for the field holderLastname
109 | *
110 | * @param holderLastname
111 | * the holderLastname to set
112 | */
113 | public void setHolderLastname(final String holderLastname) {
114 | this.holderLastname = holderLastname;
115 | }
116 |
117 | /**
118 | * Method used to get the field holderFirstname
119 | *
120 | * @return the holderFirstname
121 | */
122 | public String getHolderFirstname() {
123 | return holderFirstname;
124 | }
125 |
126 | /**
127 | * Setter for the field holderFirstname
128 | *
129 | * @param holderFirstname
130 | * the holderFirstname to set
131 | */
132 | public void setHolderFirstname(final String holderFirstname) {
133 | this.holderFirstname = holderFirstname;
134 | }
135 |
136 | /**
137 | * Method used to get the field cardNumber
138 | *
139 | * @return the cardNumber
140 | */
141 | public String getCardNumber() {
142 | return cardNumber;
143 | }
144 |
145 | /**
146 | * Setter for the field cardNumber
147 | *
148 | * @param cardNumber
149 | * the cardNumber to set
150 | */
151 | public void setCardNumber(final String cardNumber) {
152 | this.cardNumber = cardNumber;
153 | }
154 |
155 | /**
156 | * Method used to get the field expireDate
157 | *
158 | * @return the expireDate
159 | */
160 | public String getExpireDate() {
161 | return expireDate;
162 | }
163 |
164 | /**
165 | * Setter for the field expireDate
166 | *
167 | * @param expireDate
168 | * the expireDate to set
169 | */
170 | public void setExpireDate(final String expireDate) {
171 | this.expireDate = expireDate;
172 | }
173 |
174 | /**
175 | * Method used to get the field listTransactions
176 | *
177 | * @return the listTransactions
178 | */
179 | public List getListTransactions() {
180 | return listTransactions;
181 | }
182 |
183 | /**
184 | * Setter for the field listTransactions
185 | *
186 | * @param listTransactions
187 | * the listTransactions to set
188 | */
189 | public void setListTransactions(final List listTransactions) {
190 | this.listTransactions = listTransactions;
191 | }
192 |
193 | /**
194 | * Method used to get the field type
195 | *
196 | * @return the type
197 | */
198 | public EmvCardScheme getType() {
199 | return type;
200 | }
201 |
202 | /**
203 | * Setter for the field type
204 | *
205 | * @param type
206 | * the type to set
207 | */
208 | public void setType(final EmvCardScheme type) {
209 | this.type = type;
210 | }
211 |
212 | /**
213 | * Method used to get the field applicationLabel
214 | *
215 | * @return the applicationLabel
216 | */
217 | public String getApplicationLabel() {
218 | return applicationLabel;
219 | }
220 |
221 | /**
222 | * Setter for the field applicationLabel
223 | *
224 | * @param applicationLabel
225 | * the applicationLabel to set
226 | */
227 | public void setApplicationLabel(final String applicationLabel) {
228 | this.applicationLabel = applicationLabel;
229 | }
230 |
231 | @Override
232 | public boolean equals(final Object arg0) {
233 | return arg0 instanceof EmvCard && cardNumber != null && cardNumber.equals(((EmvCard) arg0).getCardNumber());
234 | }
235 |
236 | /**
237 | * Method used to get the field leftPinTry
238 | *
239 | * @return the leftPinTry
240 | */
241 | public int getLeftPinTry() {
242 | return leftPinTry;
243 | }
244 |
245 | /**
246 | * Setter for the field leftPinTry
247 | *
248 | * @param leftPinTry
249 | * the leftPinTry to set
250 | */
251 | public void setLeftPinTry(final int leftPinTry) {
252 | this.leftPinTry = leftPinTry;
253 | }
254 |
255 | /**
256 | * Method used to get the field atrDescription
257 | *
258 | * @return the atrDescription
259 | */
260 | public Collection getAtrDescription() {
261 | return atrDescription;
262 | }
263 |
264 | /**
265 | * Setter for the field atrDescription
266 | *
267 | * @param atrDescription
268 | * the atrDescription to set
269 | */
270 | public void setAtrDescription(final Collection atrDescription) {
271 | this.atrDescription = atrDescription;
272 | }
273 |
274 | /**
275 | * Method used to get the field service
276 | *
277 | * @return the service
278 | */
279 | public Service getService() {
280 | return service;
281 | }
282 |
283 | /**
284 | * Setter for the field service
285 | *
286 | * @param service
287 | * the service to set
288 | */
289 | public void setService(final Service service) {
290 | this.service = service;
291 | }
292 |
293 | /**
294 | * Method used to get the field nfcLocked
295 | *
296 | * @return the nfcLocked
297 | */
298 | public boolean isNfcLocked() {
299 | return nfcLocked;
300 | }
301 |
302 | /**
303 | * Setter for the field nfcLocked
304 | *
305 | * @param nfcLocked
306 | * the nfcLocked to set
307 | */
308 | public void setNfcLocked(final boolean nfcLocked) {
309 | this.nfcLocked = nfcLocked;
310 | }
311 |
312 | }
313 |
--------------------------------------------------------------------------------
/creditCardNfcReader/src/main/java/com/peerbits/creditCardNfcReader/model/EmvTransactionRecord.java:
--------------------------------------------------------------------------------
1 | package com.peerbits.creditCardNfcReader.model;
2 |
3 | import com.peerbits.creditCardNfcReader.model.enums.CountryCodeEnum;
4 | import com.peerbits.creditCardNfcReader.model.enums.CurrencyEnum;
5 | import com.peerbits.creditCardNfcReader.model.enums.TransactionTypeEnum;
6 | import com.peerbits.creditCardNfcReader.parser.apdu.annotation.Data;
7 | import com.peerbits.creditCardNfcReader.parser.apdu.impl.AbstractByteBean;
8 | import com.peerbits.creditCardNfcReader.parser.apdu.impl.DataFactory;
9 |
10 | import java.io.Serializable;
11 | import java.util.Date;
12 |
13 | /**
14 | * Bean used to describe EMV transaction record
15 | *
16 | */
17 | public class EmvTransactionRecord extends AbstractByteBean implements Serializable {
18 |
19 | /**
20 | * Generated serial UID
21 | */
22 | private static final long serialVersionUID = -7050737312961921452L;
23 |
24 | /**
25 | * Amount authorized (Amount need to be formated with currency)
26 | */
27 | @Data(index = 1, size = 48, format = DataFactory.BCD_FORMAT, tag = "9f02")
28 | private Float amount;
29 |
30 | /**
31 | * Cryptogram information data
32 | */
33 | @Data(index = 2, size = 8, readHexa = true, tag = "9f27")
34 | private String cyptogramData;
35 |
36 | /**
37 | * Terminal country code
38 | */
39 | @Data(index = 3, size = 16, tag = "9f1a")
40 | private CountryCodeEnum terminalCountry;
41 |
42 | /**
43 | * Currency
44 | */
45 | @Data(index = 4, size = 16, tag = "5f2a")
46 | private CurrencyEnum currency;
47 |
48 | /**
49 | * Transaction date
50 | */
51 | @Data(index = 5, size = 24, dateStandard = DataFactory.BCD_DATE, format = "yyMMdd", tag = "9a")
52 | private Date date;
53 |
54 | /**
55 | * Transaction type (0:Payment, other:Withdrawal)
56 | */
57 | @Data(index = 6, size = 8, readHexa = true, tag = "9c")
58 | private TransactionTypeEnum transactionType;
59 |
60 | /**
61 | * Transaction time
62 | */
63 | @Data(index = 7, size = 24, dateStandard = DataFactory.BCD_DATE, format = "HHmmss", tag = "9f21")
64 | private Date time;
65 |
66 | /**
67 | * Method used to get the field amount
68 | *
69 | * @return the amount
70 | */
71 | public Float getAmount() {
72 | return amount;
73 | }
74 |
75 | /**
76 | * Method used to get the field cyptogramData
77 | *
78 | * @return the cyptogramData
79 | */
80 | public String getCyptogramData() {
81 | return cyptogramData;
82 | }
83 |
84 | /**
85 | * Method used to get the field currency
86 | *
87 | * @return the currency
88 | */
89 | public CurrencyEnum getCurrency() {
90 | return currency;
91 | }
92 |
93 | /**
94 | * Method used to get the field transactionType
95 | *
96 | * @return the transactionType
97 | */
98 | public TransactionTypeEnum getTransactionType() {
99 | return transactionType;
100 | }
101 |
102 | /**
103 | * Method used to get the field terminalCountry
104 | *
105 | * @return the terminalCountry
106 | */
107 | public CountryCodeEnum getTerminalCountry() {
108 | return terminalCountry;
109 | }
110 |
111 | /**
112 | * Setter for the field amount
113 | *
114 | * @param amount
115 | * the amount to set
116 | */
117 | public void setAmount(final Float amount) {
118 | this.amount = amount;
119 | }
120 |
121 | /**
122 | * Setter for the field cyptogramData
123 | *
124 | * @param cyptogramData
125 | * the cyptogramData to set
126 | */
127 | public void setCyptogramData(final String cyptogramData) {
128 | this.cyptogramData = cyptogramData;
129 | }
130 |
131 | /**
132 | * Setter for the field terminalCountry
133 | *
134 | * @param terminalCountry
135 | * the terminalCountry to set
136 | */
137 | public void setTerminalCountry(final CountryCodeEnum terminalCountry) {
138 | this.terminalCountry = terminalCountry;
139 | }
140 |
141 | /**
142 | * Setter for the field currency
143 | *
144 | * @param currency
145 | * the currency to set
146 | */
147 | public void setCurrency(final CurrencyEnum currency) {
148 | this.currency = currency;
149 | }
150 |
151 | /**
152 | * Setter for the field transactionType
153 | *
154 | * @param transactionType
155 | * the transactionType to set
156 | */
157 | public void setTransactionType(final TransactionTypeEnum transactionType) {
158 | this.transactionType = transactionType;
159 | }
160 |
161 | /**
162 | * Method used to get the field date
163 | *
164 | * @return the date
165 | */
166 | public Date getDate() {
167 | return date;
168 | }
169 |
170 | /**
171 | * Setter for the field date
172 | *
173 | * @param date
174 | * the date to set
175 | */
176 | public void setDate(final Date date) {
177 | this.date = date;
178 | }
179 |
180 | /**
181 | * Method used to get the field time
182 | *
183 | * @return the time
184 | */
185 | public Date getTime() {
186 | return time;
187 | }
188 |
189 | /**
190 | * Setter for the field time
191 | *
192 | * @param time
193 | * the time to set
194 | */
195 | public void setTime(final Date time) {
196 | this.time = time;
197 | }
198 |
199 | }
200 |
--------------------------------------------------------------------------------
/creditCardNfcReader/src/main/java/com/peerbits/creditCardNfcReader/model/Service.java:
--------------------------------------------------------------------------------
1 | package com.peerbits.creditCardNfcReader.model;
2 |
3 | import com.peerbits.creditCardNfcReader.utils.BytesUtils;
4 | import com.peerbits.creditCardNfcReader.model.enums.ServiceCode1Enum;
5 | import com.peerbits.creditCardNfcReader.model.enums.ServiceCode2Enum;
6 | import com.peerbits.creditCardNfcReader.model.enums.ServiceCode3Enum;
7 | import com.peerbits.creditCardNfcReader.utils.EnumUtils;
8 |
9 | import org.apache.commons.lang3.StringUtils;
10 |
11 | import fr.devnied.bitlib.BitUtils;
12 |
13 | /**
14 | * Track 2 service
15 | *
16 | */
17 | public class Service extends AbstractData{
18 |
19 | /**
20 | * Generated serial UID
21 | */
22 | private static final long serialVersionUID = 5154895810563519768L;
23 |
24 | /**
25 | * Service code 1
26 | */
27 | private ServiceCode1Enum serviceCode1;
28 |
29 | /**
30 | * Service code 2
31 | */
32 | private ServiceCode2Enum serviceCode2;
33 |
34 | /**
35 | * Service code 3
36 | */
37 | private ServiceCode3Enum serviceCode3;
38 |
39 | /**
40 | * Constructor with service bytes array parameter
41 | *
42 | * @param pData
43 | * service as byte array
44 | */
45 | public Service(final String pData) {
46 | if (pData != null && pData.length() == 3) {
47 | BitUtils bit = new BitUtils(BytesUtils.fromString(StringUtils.rightPad(pData, 4, "0")));
48 | serviceCode1 = EnumUtils.getValue(bit.getNextInteger(4), ServiceCode1Enum.class);
49 | serviceCode2 = EnumUtils.getValue(bit.getNextInteger(4), ServiceCode2Enum.class);
50 | serviceCode3 = EnumUtils.getValue(bit.getNextInteger(4), ServiceCode3Enum.class);
51 | }
52 | }
53 |
54 | /**
55 | * Method used to get the field serviceCode1
56 | *
57 | * @return the serviceCode1
58 | */
59 | public ServiceCode1Enum getServiceCode1() {
60 | return serviceCode1;
61 | }
62 |
63 | /**
64 | * Method used to get the field serviceCode2
65 | *
66 | * @return the serviceCode2
67 | */
68 | public ServiceCode2Enum getServiceCode2() {
69 | return serviceCode2;
70 | }
71 |
72 | /**
73 | * Method used to get the field serviceCode3
74 | *
75 | * @return the serviceCode3
76 | */
77 | public ServiceCode3Enum getServiceCode3() {
78 | return serviceCode3;
79 | }
80 |
81 | }
82 |
--------------------------------------------------------------------------------
/creditCardNfcReader/src/main/java/com/peerbits/creditCardNfcReader/model/enums/IKeyEnum.java:
--------------------------------------------------------------------------------
1 | package com.peerbits.creditCardNfcReader.model.enums;
2 |
3 | /**
4 | * Interface for Key enum
5 | *
6 | */
7 | public interface IKeyEnum {
8 |
9 | /**
10 | * Get the key of the current enum
11 | *
12 | * @return the key value
13 | */
14 | int getKey();
15 |
16 | }
17 |
--------------------------------------------------------------------------------
/creditCardNfcReader/src/main/java/com/peerbits/creditCardNfcReader/model/enums/ServiceCode1Enum.java:
--------------------------------------------------------------------------------
1 | package com.peerbits.creditCardNfcReader.model.enums;
2 |
3 | /**
4 | * Service code, position 1 values.
5 | */
6 | public enum ServiceCode1Enum implements IKeyEnum {
7 |
8 | INTERNATIONNAL(1, "International interchange", "None"),
9 | INTERNATIONNAL_ICC(2, "International interchange", "Integrated circuit card"),
10 | NATIONAL(5, "National interchange", "None"),
11 | NATIONAL_ICC(6, "National interchange", "Integrated circuit card"),
12 | PRIVATE(7, "Private", "None");
13 |
14 | private final int value;
15 | private final String interchange;
16 | private final String technology;
17 |
18 | /**
19 | * Constructor using fields
20 | *
21 | * @param value
22 | * @param interchange
23 | * @param technology
24 | */
25 | private ServiceCode1Enum(final int value, final String interchange, final String technology) {
26 | this.value = value;
27 | this.interchange = interchange;
28 | this.technology = technology;
29 | }
30 |
31 | /**
32 | * Method used to get the field interchange
33 | *
34 | * @return the interchange
35 | */
36 | public String getInterchange() {
37 | return interchange;
38 | }
39 |
40 | /**
41 | * Method used to get the field technology
42 | *
43 | * @return the technology
44 | */
45 | public String getTechnology() {
46 | return technology;
47 | }
48 |
49 | @Override
50 | public int getKey() {
51 | return value;
52 | }
53 |
54 | }
--------------------------------------------------------------------------------
/creditCardNfcReader/src/main/java/com/peerbits/creditCardNfcReader/model/enums/ServiceCode2Enum.java:
--------------------------------------------------------------------------------
1 | package com.peerbits.creditCardNfcReader.model.enums;
2 |
3 | /**
4 | * Service code, position 2 values.
5 | */
6 | public enum ServiceCode2Enum implements IKeyEnum {
7 |
8 | NORMAL(0, "Normal"),
9 | BY_ISSUER(2, "By issuer"),
10 | BY_ISSUER_WIHOUT_BI_AGREEMENT(4, "By issuer unless explicit bilateral agreement applies");
11 |
12 | private final int value;
13 | private final String authorizationProcessing;
14 |
15 | private ServiceCode2Enum(final int value, final String authorizationProcessing) {
16 | this.value = value;
17 | this.authorizationProcessing = authorizationProcessing;
18 | }
19 |
20 | /**
21 | * Gets the authorization processing rules.
22 | *
23 | * @return Authorization processing rules.
24 | */
25 | public String getAuthorizationProcessing() {
26 | return authorizationProcessing;
27 | }
28 |
29 | @Override
30 | public int getKey() {
31 | return value;
32 | }
33 |
34 | }
--------------------------------------------------------------------------------
/creditCardNfcReader/src/main/java/com/peerbits/creditCardNfcReader/model/enums/ServiceCode3Enum.java:
--------------------------------------------------------------------------------
1 | package com.peerbits.creditCardNfcReader.model.enums;
2 |
3 | /**
4 | * Service code, position 2 values.
5 | */
6 | public enum ServiceCode3Enum implements IKeyEnum {
7 |
8 | NO_RESTRICTION_PIN_REQUIRED(0, "No restrictions", "PIN required"),
9 | NO_RESTRICTION(1, "No restrictions", "None"),
10 | GOODS_SERVICES(2, "Goods and services only", "None"),
11 | ATM_ONLY(3, "ATM only", "PIN required"),
12 | CASH_ONLY(4, "Cash only", "None"),
13 | GOODS_SERVICES_PIN_REQUIRED(5, "Goods and services only", "PIN required"),
14 | NO_RESTRICTION_PIN_IF_PED(6, "No restrictions", "Prompt for PIN if PED present"),
15 | GOODS_SERVICES_PIN_IF_PED(7, "Goods and services only", "Prompt for PIN if PED present"), ;
16 |
17 | private final int value;
18 | private final String allowedServices;
19 | private final String pinRequirements;
20 |
21 | private ServiceCode3Enum(final int value, final String allowedServices, final String pinRequirements) {
22 | this.value = value;
23 | this.allowedServices = allowedServices;
24 | this.pinRequirements = pinRequirements;
25 | }
26 |
27 | /**
28 | * Gets the allowed services.
29 | *
30 | * @return Allowed services.
31 | */
32 | public String getAllowedServices() {
33 | return allowedServices;
34 | }
35 |
36 | /**
37 | * Gets the the PIN requirements.
38 | *
39 | * @return PIN requirements.
40 | */
41 | public String getPinRequirements() {
42 | return pinRequirements;
43 | }
44 |
45 | @Override
46 | public int getKey() {
47 | return value;
48 | }
49 |
50 | }
--------------------------------------------------------------------------------
/creditCardNfcReader/src/main/java/com/peerbits/creditCardNfcReader/model/enums/TransactionTypeEnum.java:
--------------------------------------------------------------------------------
1 | package com.peerbits.creditCardNfcReader.model.enums;
2 |
3 | /**
4 | * Transaction type
5 | *
6 | */
7 | public enum TransactionTypeEnum implements IKeyEnum {
8 |
9 | /**
10 | * '00' for a purchase transaction
11 | */
12 | PURCHASE(0x00),
13 | /**
14 | * '01' Cach advance
15 | */
16 | CASH_ADVANCE(0x01),
17 | /**
18 | * '09' for a purchase with cashback
19 | */
20 | CASHBACK(0x09),
21 | /**
22 | * '20' for a refund transaction
23 | */
24 | REFUND(0x20);
25 |
26 | /**
27 | * Value
28 | */
29 | private final int value;
30 |
31 | /**
32 | * Constructor using field
33 | *
34 | * @param value
35 | */
36 | private TransactionTypeEnum(final int value) {
37 | this.value = value;
38 | }
39 |
40 | @Override
41 | public int getKey() {
42 | return value;
43 | }
44 | }
45 |
--------------------------------------------------------------------------------
/creditCardNfcReader/src/main/java/com/peerbits/creditCardNfcReader/parser/IProvider.java:
--------------------------------------------------------------------------------
1 | package com.peerbits.creditCardNfcReader.parser;
2 |
3 | import com.peerbits.creditCardNfcReader.exception.CommunicationException;
4 |
5 | /**
6 | * Interface for provider for transmit command to card
7 | */
8 | public interface IProvider {
9 |
10 | /**
11 | * Method used to transmit and receive card response
12 | *
13 | * @param pCommand
14 | * command to send to card
15 | * @return byte array returned by card
16 | */
17 | byte[] transceive(byte[] pCommand) throws CommunicationException;
18 |
19 | }
20 |
--------------------------------------------------------------------------------
/creditCardNfcReader/src/main/java/com/peerbits/creditCardNfcReader/parser/apdu/IFile.java:
--------------------------------------------------------------------------------
1 | package com.peerbits.creditCardNfcReader.parser.apdu;
2 |
3 | import com.peerbits.creditCardNfcReader.iso7816emv.TagAndLength;
4 |
5 | import java.util.List;
6 |
7 | /**
8 | * Interface for File to parse
9 | */
10 | public interface IFile {
11 |
12 | /**
13 | * Method to parse byte data
14 | *
15 | * @param pData
16 | * byte to parse
17 | * @param pList
18 | * Tag and length
19 | */
20 | void parse(final byte[] pData, final List pList);
21 |
22 | }
23 |
--------------------------------------------------------------------------------
/creditCardNfcReader/src/main/java/com/peerbits/creditCardNfcReader/parser/apdu/annotation/AnnotationData.java:
--------------------------------------------------------------------------------
1 | package com.peerbits.creditCardNfcReader.parser.apdu.annotation;
2 |
3 | import com.peerbits.creditCardNfcReader.iso7816emv.EmvTags;
4 | import com.peerbits.creditCardNfcReader.iso7816emv.ITag;
5 |
6 | import java.lang.reflect.Field;
7 |
8 | import fr.devnied.bitlib.BytesUtils;
9 |
10 | /**
11 | * Bean which manage all annotation data
12 | *
13 | */
14 | public class AnnotationData implements Comparable, Cloneable {
15 |
16 | /**
17 | * The size of the field
18 | */
19 | private int size;
20 |
21 | /**
22 | * Index of the field
23 | */
24 | private int index;
25 |
26 | /**
27 | * read String as hexa value
28 | */
29 | private boolean readHexa;
30 |
31 | /**
32 | * Field to modify
33 | */
34 | private Field field;
35 |
36 | /**
37 | * The date standard
38 | */
39 | private int dateStandard;
40 |
41 | /**
42 | * Date format
43 | */
44 | private String format;
45 |
46 | /**
47 | * Tag
48 | */
49 | private ITag tag;
50 |
51 | /**
52 | * Skip data
53 | */
54 | private boolean skip;
55 |
56 | /**
57 | * Comparable method {@inheritDoc}
58 | *
59 | */
60 | @Override
61 | public int compareTo(final AnnotationData pO) {
62 | return Integer.valueOf(index).compareTo(pO.getIndex());
63 | }
64 |
65 | /**
66 | * Equals method {@inheritDoc}
67 | *
68 | */
69 | @Override
70 | public boolean equals(final Object pObj) {
71 | boolean ret = false;
72 | if (pObj instanceof AnnotationData) {
73 | ret = index == ((AnnotationData) pObj).getIndex();
74 | }
75 | return ret;
76 | }
77 |
78 | /**
79 | * Method used to get the field size
80 | *
81 | * @return the size
82 | */
83 | public int getSize() {
84 | return size;
85 | }
86 |
87 | /**
88 | * Setter for the field size
89 | *
90 | * @param size
91 | * the size to set
92 | */
93 | public void setSize(final int size) {
94 | this.size = size;
95 | }
96 |
97 | /**
98 | * Method used to get the field index
99 | *
100 | * @return the index
101 | */
102 | public int getIndex() {
103 | return index;
104 | }
105 |
106 | /**
107 | * Method used to get the field readHexa
108 | *
109 | * @return the readHexa
110 | */
111 | public boolean isReadHexa() {
112 | return readHexa;
113 | }
114 |
115 | /**
116 | * Method used to get the field field
117 | *
118 | * @return the field
119 | */
120 | public Field getField() {
121 | return field;
122 | }
123 |
124 | /**
125 | * Method used to get the field dateStandard
126 | *
127 | * @return the dateStandard
128 | */
129 | public int getDateStandard() {
130 | return dateStandard;
131 | }
132 |
133 | /**
134 | * Method used to get the field format
135 | *
136 | * @return the format
137 | */
138 | public String getFormat() {
139 | return format;
140 | }
141 |
142 | /**
143 | * Setter for the field field
144 | *
145 | * @param field
146 | * the field to set
147 | */
148 | public void setField(final Field field) {
149 | this.field = field;
150 | }
151 |
152 | /**
153 | * Method used to get the field tag
154 | *
155 | * @return the tag
156 | */
157 | public ITag getTag() {
158 | return tag;
159 | }
160 |
161 | /**
162 | * Initialization from annotation
163 | *
164 | * @param pData
165 | * annotation data
166 | */
167 | public void initFromAnnotation(final Data pData) {
168 | dateStandard = pData.dateStandard();
169 | format = pData.format();
170 | index = pData.index();
171 | readHexa = pData.readHexa();
172 | size = pData.size();
173 | if (pData.tag() != null) {
174 | tag = EmvTags.find(BytesUtils.fromString(pData.tag()));
175 | }
176 | }
177 |
178 | @Override
179 | protected Object clone() throws CloneNotSupportedException {
180 | AnnotationData data = new AnnotationData();
181 | data.dateStandard = dateStandard;
182 | data.field = field;
183 | data.format = new String(format);
184 | data.index = index;
185 | data.readHexa = readHexa;
186 | data.size = size;
187 | data.tag = tag;
188 | return data;
189 | }
190 |
191 | /**
192 | * Method used to get the field skip
193 | *
194 | * @return the skip
195 | */
196 | public boolean isSkip() {
197 | return skip;
198 | }
199 |
200 | /**
201 | * Setter for the field skip
202 | *
203 | * @param skip
204 | * the skip to set
205 | */
206 | public void setSkip(final boolean skip) {
207 | this.skip = skip;
208 | }
209 |
210 | }
211 |
--------------------------------------------------------------------------------
/creditCardNfcReader/src/main/java/com/peerbits/creditCardNfcReader/parser/apdu/annotation/AnnotationUtils.java:
--------------------------------------------------------------------------------
1 | package com.peerbits.creditCardNfcReader.parser.apdu.annotation;
2 |
3 | import com.peerbits.creditCardNfcReader.iso7816emv.ITag;
4 | import com.peerbits.creditCardNfcReader.model.EmvTransactionRecord;
5 | import com.peerbits.creditCardNfcReader.parser.apdu.IFile;
6 |
7 | import java.lang.reflect.Field;
8 | import java.util.HashMap;
9 | import java.util.Map;
10 | import java.util.Set;
11 | import java.util.TreeSet;
12 |
13 | /**
14 | * Class used to manage all annotation
15 | *
16 | */
17 | public final class AnnotationUtils {
18 |
19 | /**
20 | * List of annoted class
21 | */
22 | @SuppressWarnings("unchecked")
23 | private static final Class extends IFile>[] LISTE_CLASS = new Class[] { EmvTransactionRecord.class };
24 |
25 | /**
26 | * AnnotationUtils singleton
27 | */
28 | private static final AnnotationUtils INSTANCE = new AnnotationUtils();
29 |
30 | /**
31 | * Method to get the unique instance of the class
32 | *
33 | * @return AnnotationUtils instance
34 | */
35 | public static AnnotationUtils getInstance() {
36 | return INSTANCE;
37 | }
38 |
39 | /**
40 | * Map which contain
41 | */
42 | private final Map> map;
43 | private final Map> mapSet;
44 |
45 | /**
46 | * Private default constructor
47 | */
48 | private AnnotationUtils() {
49 | map = new HashMap>();
50 | mapSet = new HashMap>();
51 | extractAnnotation();
52 | }
53 |
54 | /**
55 | * Method to extract all annotation information and store them in the map
56 | */
57 | private void extractAnnotation() {
58 | for (Class extends IFile> clazz : LISTE_CLASS) {
59 |
60 | Map maps = new HashMap();
61 | Set set = new TreeSet();
62 |
63 | Field[] fields = clazz.getDeclaredFields();
64 | for (Field field : fields) {
65 | AnnotationData param = new AnnotationData();
66 | field.setAccessible(true);
67 | param.setField(field);
68 | Data annotation = field.getAnnotation(Data.class);
69 | if (annotation != null) {
70 | param.initFromAnnotation(annotation);
71 | maps.put(param.getTag(), param);
72 | try {
73 | set.add((AnnotationData) param.clone());
74 | } catch (CloneNotSupportedException e) {
75 | // do nothing
76 | }
77 | }
78 | }
79 | mapSet.put(clazz.getName(), set);
80 | map.put(clazz.getName(), maps);
81 | }
82 | }
83 |
84 | /**
85 | * Getter map set
86 | *
87 | * @return the map
88 | */
89 | public Map> getMapSet() {
90 | return mapSet;
91 | }
92 |
93 | /**
94 | * Getter map
95 | *
96 | * @return the map
97 | */
98 | public Map> getMap() {
99 | return map;
100 | }
101 |
102 | }
103 |
--------------------------------------------------------------------------------
/creditCardNfcReader/src/main/java/com/peerbits/creditCardNfcReader/parser/apdu/annotation/Data.java:
--------------------------------------------------------------------------------
1 | package com.peerbits.creditCardNfcReader.parser.apdu.annotation;
2 |
3 | import java.lang.annotation.ElementType;
4 | import java.lang.annotation.Retention;
5 | import java.lang.annotation.RetentionPolicy;
6 | import java.lang.annotation.Target;
7 |
8 | import fr.devnied.bitlib.BitUtils;
9 |
10 | /**
11 | * Annotation to describe field information
12 | *
13 | */
14 | @Target(ElementType.FIELD)
15 | @Retention(RetentionPolicy.RUNTIME)
16 | public @interface Data {
17 |
18 | /**
19 | * Format date
20 | */
21 | String format() default BitUtils.DATE_FORMAT;
22 |
23 | /**
24 | * The current date standard
25 | */
26 | int dateStandard() default 0;
27 |
28 | /**
29 | * index of data
30 | */
31 | int index();
32 |
33 | /**
34 | * Read the string in hexa
35 | */
36 | boolean readHexa() default false;
37 |
38 | /**
39 | * Number of bytes
40 | */
41 | int size();
42 |
43 | /**
44 | * Tag Name
45 | */
46 | String tag();
47 | }
48 |
--------------------------------------------------------------------------------
/creditCardNfcReader/src/main/java/com/peerbits/creditCardNfcReader/parser/apdu/impl/AbstractByteBean.java:
--------------------------------------------------------------------------------
1 | package com.peerbits.creditCardNfcReader.parser.apdu.impl;
2 |
3 | import com.peerbits.creditCardNfcReader.iso7816emv.ITag;
4 | import com.peerbits.creditCardNfcReader.iso7816emv.TagAndLength;
5 | import com.peerbits.creditCardNfcReader.model.AbstractData;
6 | import com.peerbits.creditCardNfcReader.parser.apdu.IFile;
7 | import com.peerbits.creditCardNfcReader.parser.apdu.annotation.AnnotationData;
8 | import com.peerbits.creditCardNfcReader.parser.apdu.annotation.AnnotationUtils;
9 |
10 | import org.slf4j.Logger;
11 | import org.slf4j.LoggerFactory;
12 |
13 | import java.lang.reflect.Field;
14 | import java.util.ArrayList;
15 | import java.util.Collection;
16 | import java.util.Iterator;
17 | import java.util.List;
18 | import java.util.Map;
19 |
20 | import fr.devnied.bitlib.BitUtils;
21 |
22 | /**
23 | * Abstract class for all object to parse
24 | */
25 | public abstract class AbstractByteBean extends AbstractData implements IFile {
26 |
27 | /**
28 | * Generated serial UID
29 | */
30 | private static final long serialVersionUID = -2016039522844322383L;
31 |
32 | /**
33 | * Logger of the class
34 | */
35 | private static final Logger LOGGER = LoggerFactory.getLogger(AbstractByteBean.class.getName());
36 |
37 | /**
38 | * Method to get the annotation set from the current class
39 | *
40 | * @return An annotation set which contain all annotation data
41 | */
42 | private Collection getAnnotationSet(final List pTags) {
43 | Collection ret = null;
44 | if (pTags != null) {
45 | Map data = AnnotationUtils.getInstance().getMap().get(getClass().getName());
46 | ret = new ArrayList(data.size());
47 | for (TagAndLength tal : pTags) {
48 | AnnotationData ann = data.get(tal.getTag());
49 | if (ann != null) {
50 | ann.setSize(tal.getLength() * BitUtils.BYTE_SIZE);
51 | } else {
52 | ann = new AnnotationData();
53 | ann.setSkip(true);
54 | ann.setSize(tal.getLength() * BitUtils.BYTE_SIZE);
55 | }
56 | ret.add(ann);
57 | }
58 | } else {
59 | ret = AnnotationUtils.getInstance().getMapSet().get(getClass().getName());
60 | }
61 | return ret;
62 | }
63 |
64 | /**
65 | * Method to parse byte data
66 | *
67 | * @param pData
68 | * byte to parse
69 | * @param pTags
70 | */
71 | @Override
72 | public void parse(final byte[] pData, final List pTags) {
73 | Collection set = getAnnotationSet(pTags);
74 | BitUtils bit = new BitUtils(pData);
75 | Iterator it = set.iterator();
76 | while (it.hasNext()) {
77 | AnnotationData data = it.next();
78 | if (data.isSkip()) {
79 | bit.addCurrentBitIndex(data.getSize());
80 | } else {
81 | Object obj = DataFactory.getObject(data, bit);
82 | setField(data.getField(), this, obj);
83 | }
84 | }
85 | }
86 |
87 | /**
88 | * Method used to set the value of a field
89 | *
90 | * @param field
91 | * the field to set
92 | * @param pData
93 | * Object containing the field
94 | * @param pValue
95 | * the value of the field
96 | */
97 | protected void setField(final Field field, final IFile pData, final Object pValue) {
98 | if (field != null) {
99 | try {
100 | field.set(pData, pValue);
101 | } catch (IllegalArgumentException e) {
102 | LOGGER.error("Parameters of fied.set are not valid", e);
103 | } catch (IllegalAccessException e) {
104 | LOGGER.error("Impossible to set the Field :" + field.getName(), e);
105 | }
106 | }
107 | }
108 | }
109 |
--------------------------------------------------------------------------------
/creditCardNfcReader/src/main/java/com/peerbits/creditCardNfcReader/parser/apdu/impl/DataFactory.java:
--------------------------------------------------------------------------------
1 | package com.peerbits.creditCardNfcReader.parser.apdu.impl;
2 |
3 | import com.peerbits.creditCardNfcReader.model.enums.IKeyEnum;
4 | import com.peerbits.creditCardNfcReader.parser.apdu.annotation.AnnotationData;
5 | import com.peerbits.creditCardNfcReader.utils.EnumUtils;
6 |
7 | import org.slf4j.Logger;
8 | import org.slf4j.LoggerFactory;
9 |
10 | import java.util.Date;
11 |
12 | import fr.devnied.bitlib.BitUtils;
13 |
14 | /**
15 | * Factory to parse data
16 | */
17 | public final class DataFactory {
18 |
19 | /**
20 | * Logger of this class
21 | */
22 | public static final Logger LOGGER = LoggerFactory.getLogger(DataFactory.class.getName());
23 |
24 | /**
25 | * Constant for EN1545-1 (Date format)
26 | */
27 | public static final int BCD_DATE = 1;
28 |
29 | /**
30 | * Half byte size
31 | */
32 | public static final int HALF_BYTE_SIZE = 4;
33 |
34 | /**
35 | * BCD format
36 | */
37 | public static final String BCD_FORMAT = "BCD_Format";
38 |
39 | /**
40 | * Method to get a date from the bytes array
41 | *
42 | * @param pAnnotation
43 | * annotation data
44 | * @param pBit
45 | * table bytes
46 | * @return The date read of null
47 | */
48 | private static Date getDate(final AnnotationData pAnnotation, final BitUtils pBit) {
49 | Date date = null;
50 | if (pAnnotation.getDateStandard() == BCD_DATE) {
51 | date = pBit.getNextDate(pAnnotation.getSize(), pAnnotation.getFormat(), true);
52 | } else {
53 | date = pBit.getNextDate(pAnnotation.getSize(), pAnnotation.getFormat());
54 | }
55 | return date;
56 | }
57 |
58 | /**
59 | * This method is used to get an integer
60 | *
61 | * @param pAnnotation
62 | * annotation
63 | * @param pObject
64 | * the object to set
65 | * @param pBit
66 | * bit array
67 | */
68 | private static int getInteger(final AnnotationData pAnnotation, final BitUtils pBit) {
69 | return pBit.getNextInteger(pAnnotation.getSize());
70 | }
71 |
72 | /**
73 | * Method to read and object from the bytes tab
74 | *
75 | * @param pAnnotation
76 | * all information data
77 | * @param pBit
78 | * bytes tab
79 | * @return an object
80 | */
81 | public static Object getObject(final AnnotationData pAnnotation, final BitUtils pBit) {
82 | Object obj = null;
83 | Class> clazz = pAnnotation.getField().getType();
84 |
85 | if (clazz.equals(Integer.class)) {
86 | obj = getInteger(pAnnotation, pBit);
87 | } else if (clazz.equals(Float.class)) {
88 | obj = getFloat(pAnnotation, pBit);
89 | } else if (clazz.equals(String.class)) {
90 | obj = getString(pAnnotation, pBit);
91 | } else if (clazz.equals(Date.class)) {
92 | obj = getDate(pAnnotation, pBit);
93 | } else if (clazz.equals(Boolean.class)) {
94 | obj = pBit.getNextBoolean();
95 | } else if (clazz.isEnum()) {
96 | obj = getEnum(pAnnotation, pBit);
97 | }
98 | return obj;
99 | }
100 |
101 | /**
102 | * Method use to get float
103 | *
104 | * @param pAnnotation
105 | * annotation
106 | * @param pBit
107 | * bit utils
108 | * @return
109 | */
110 | private static Float getFloat(final AnnotationData pAnnotation, final BitUtils pBit) {
111 | Float ret = null;
112 |
113 | if (BCD_FORMAT.equals(pAnnotation.getFormat())) {
114 | ret = Float.parseFloat(pBit.getNextHexaString(pAnnotation.getSize()));
115 | } else {
116 | ret = (float) getInteger(pAnnotation, pBit);
117 | }
118 |
119 | return ret;
120 | }
121 |
122 | /**
123 | * This method is used to get an enum with his key
124 | *
125 | * @param pAnnotation
126 | * annotation
127 | * @param pBit
128 | * bit array
129 | */
130 | @SuppressWarnings("unchecked")
131 | private static IKeyEnum getEnum(final AnnotationData pAnnotation, final BitUtils pBit) {
132 | int val = 0;
133 | try {
134 | val = Integer.parseInt(pBit.getNextHexaString(pAnnotation.getSize()), pAnnotation.isReadHexa() ? 16 : 10);
135 | } catch (NumberFormatException nfe) {
136 | // do nothing
137 | }
138 | return EnumUtils.getValue(val, (Class extends IKeyEnum>) pAnnotation.getField().getType());
139 | }
140 |
141 | /**
142 | * This method get a string (Hexa or ASCII) from a bit table
143 | *
144 | * @param pAnnotation
145 | * annotation data
146 | * @param pBit
147 | * bit table
148 | * @return A string
149 | */
150 | private static String getString(final AnnotationData pAnnotation, final BitUtils pBit) {
151 | String obj = null;
152 |
153 | if (pAnnotation.isReadHexa()) {
154 | obj = pBit.getNextHexaString(pAnnotation.getSize());
155 | } else {
156 | obj = pBit.getNextString(pAnnotation.getSize()).trim();
157 | }
158 |
159 | return obj;
160 | }
161 |
162 | /**
163 | * Private constructor
164 | */
165 | private DataFactory() {
166 | }
167 | }
168 |
--------------------------------------------------------------------------------
/creditCardNfcReader/src/main/java/com/peerbits/creditCardNfcReader/utils/AtrUtils.java:
--------------------------------------------------------------------------------
1 | package com.peerbits.creditCardNfcReader.utils;
2 |
3 | import android.util.Log;
4 |
5 | import org.apache.commons.collections4.MultiMap;
6 | import org.apache.commons.collections4.map.MultiValueMap;
7 | import org.apache.commons.io.IOUtils;
8 | import org.apache.commons.lang3.CharEncoding;
9 | import org.apache.commons.lang3.StringUtils;
10 |
11 | import java.io.BufferedReader;
12 | import java.io.IOException;
13 | import java.io.InputStream;
14 | import java.io.InputStreamReader;
15 | import java.util.Collection;
16 |
17 | /**
18 | * Created by pro100svitlo on 15.05.16.
19 | */
20 |
21 | public final class AtrUtils {
22 |
23 | private static String TAG = "creditCardNfcReader";
24 | /**
25 | * MultiMap containing ATR
26 | */
27 | private static final MultiMap MAP = new MultiValueMap();
28 |
29 | static {
30 | InputStream is = null;
31 | InputStreamReader isr = null;
32 | BufferedReader br = null;
33 |
34 | try {
35 | is = AtrUtils.class.getResourceAsStream("/smartcard_list.txt");
36 | isr = new InputStreamReader(is, CharEncoding.UTF_8);
37 | br = new BufferedReader(isr);
38 |
39 | int lineNumber = 0;
40 | String line;
41 | String currentATR = null;
42 | while ((line = br.readLine()) != null) {
43 | ++lineNumber;
44 | if (line.startsWith("#") || line.trim().length() == 0) { // comment ^#/ empty line ^$/
45 | continue;
46 | } else if (line.startsWith("\t") && currentATR != null) {
47 | MAP.put(currentATR, line.replace("\t", "").trim());
48 | } else if (line.startsWith("3")) { // ATR hex
49 | currentATR = StringUtils.deleteWhitespace(line.toUpperCase());
50 | } else {
51 | Log.d(TAG, "Encountered unexpected line in atr list: currentATR=" + currentATR + " Line(" + lineNumber
52 | + ") = " + line);
53 | }
54 | }
55 | } catch (IOException e) {
56 | throw new RuntimeException(e);
57 | } finally {
58 | IOUtils.closeQuietly(br);
59 | IOUtils.closeQuietly(isr);
60 | IOUtils.closeQuietly(is);
61 | }
62 | }
63 |
64 | /**
65 | * Method used to find description from ATR
66 | *
67 | * @param pAtr
68 | * Card ATR
69 | * @return list of description
70 | */
71 | @SuppressWarnings("unchecked")
72 | public static final Collection getDescription(final String pAtr) {
73 | Collection ret = null;
74 | if (StringUtils.isNotBlank(pAtr)) {
75 | String val = StringUtils.deleteWhitespace(pAtr);
76 | for (String key : MAP.keySet()) {
77 | if (val.matches("^" + key + "$")) {
78 | ret = (Collection) MAP.get(key);
79 | break;
80 | }
81 | }
82 | }
83 | return ret;
84 | }
85 |
86 | /**
87 | * Method used to find ATR description from ATS (Answer to select)
88 | *
89 | * @param pAts
90 | * EMV card ATS
91 | * @return card description
92 | */
93 | @SuppressWarnings("unchecked")
94 | public static final Collection getDescriptionFromAts(final String pAts) {
95 | Collection ret = null;
96 | if (StringUtils.isNotBlank(pAts)) {
97 | String val = StringUtils.deleteWhitespace(pAts);
98 | for (String key : MAP.keySet()) {
99 | if (key.contains(val)) { // TODO Fix this
100 | ret = (Collection) MAP.get(key);
101 | break;
102 | }
103 | }
104 | }
105 | return ret;
106 | }
107 |
108 | /**
109 | * Private constructor
110 | */
111 | private AtrUtils() {
112 | }
113 |
114 | }
115 |
--------------------------------------------------------------------------------
/creditCardNfcReader/src/main/java/com/peerbits/creditCardNfcReader/utils/BytesUtils.java:
--------------------------------------------------------------------------------
1 | package com.peerbits.creditCardNfcReader.utils;
2 |
3 | import java.math.BigInteger;
4 | import java.util.Locale;
5 |
6 | public final class BytesUtils {
7 | private static final int MAX_BIT_INTEGER = 31;
8 | private static final int HEXA = 16;
9 | private static final String FORMAT_NOSPACE = "%02x";
10 | private static final String FORMAT_SPACE = "%02x ";
11 | private static final int DEFAULT_MASK = 255;
12 |
13 | public static int byteArrayToInt(byte[] byteArray) {
14 | if(byteArray == null) {
15 | throw new IllegalArgumentException("Parameter \'byteArray\' cannot be null");
16 | } else {
17 | return byteArrayToInt(byteArray, 0, byteArray.length);
18 | }
19 | }
20 |
21 | public static int byteArrayToInt(byte[] byteArray, int startPos, int length) {
22 | if(byteArray == null) {
23 | throw new IllegalArgumentException("Parameter \'byteArray\' cannot be null");
24 | } else if(length > 0 && length <= 4) {
25 | if(startPos >= 0 && byteArray.length >= startPos + length) {
26 | int value = 0;
27 |
28 | for(int i = 0; i < length; ++i) {
29 | value += (byteArray[startPos + i] & 255) << 8 * (length - i - 1);
30 | }
31 |
32 | return value;
33 | } else {
34 | throw new IllegalArgumentException("Length or startPos not valid");
35 | }
36 | } else {
37 | throw new IllegalArgumentException("Length must be between 1 and 4. Length = " + length);
38 | }
39 | }
40 |
41 | public static String bytesToString(byte[] pBytes) {
42 | return formatByte(pBytes, "%02x ", false);
43 | }
44 |
45 | public static String bytesToString(byte[] pBytes, boolean pTruncate) {
46 | return formatByte(pBytes, "%02x ", pTruncate);
47 | }
48 |
49 | public static String bytesToStringNoSpace(byte pByte) {
50 | return formatByte(new byte[]{pByte}, "%02x", false);
51 | }
52 |
53 | public static String bytesToStringNoSpace(byte[] pBytes) {
54 | return formatByte(pBytes, "%02x", false);
55 | }
56 |
57 | public static String bytesToStringNoSpace(byte[] pBytes, boolean pTruncate) {
58 | return formatByte(pBytes, "%02x", pTruncate);
59 | }
60 |
61 | private static String formatByte(byte[] pByte, String pFormat, boolean pTruncate) {
62 | StringBuffer sb = new StringBuffer();
63 | if(pByte == null) {
64 | sb.append("");
65 | } else {
66 | boolean t = false;
67 | byte[] arr$ = pByte;
68 | int len$ = pByte.length;
69 |
70 | for(int i$ = 0; i$ < len$; ++i$) {
71 | byte b = arr$[i$];
72 | if(b != 0 || !pTruncate || t) {
73 | t = true;
74 | sb.append(String.format(pFormat, new Object[]{Integer.valueOf(b & 255)}));
75 | }
76 | }
77 | }
78 |
79 | return sb.toString().toUpperCase(Locale.getDefault()).trim();
80 | }
81 |
82 | public static byte[] fromString(String pData) {
83 | if(pData == null) {
84 | throw new IllegalArgumentException("Argument can\'t be null");
85 | } else {
86 | String text = pData.replace(" ", "");
87 | if(text.length() % 2 != 0) {
88 | throw new IllegalArgumentException("Hex binary needs to be even-length :" + pData);
89 | } else {
90 | byte[] commandByte = new byte[Math.round((float)text.length() / 2.0F)];
91 | int j = 0;
92 |
93 | for(int i = 0; i < text.length(); i += 2) {
94 | Integer val = Integer.valueOf(Integer.parseInt(text.substring(i, i + 2), 16));
95 | commandByte[j++] = val.byteValue();
96 | }
97 |
98 | return commandByte;
99 | }
100 | }
101 | }
102 |
103 | public static boolean matchBitByBitIndex(int pVal, int pBitIndex) {
104 | if(pBitIndex >= 0 && pBitIndex <= 31) {
105 | return (pVal & 1 << pBitIndex) != 0;
106 | } else {
107 | throw new IllegalArgumentException("parameter \'pBitIndex\' must be between 0 and 31. pBitIndex=" + pBitIndex);
108 | }
109 | }
110 |
111 | public static byte setBit(byte pData, int pBitIndex, boolean pOn) {
112 | if(pBitIndex >= 0 && pBitIndex <= 7) {
113 | byte ret;
114 | if(pOn) {
115 | ret = (byte)(pData | 1 << pBitIndex);
116 | } else {
117 | ret = (byte)(pData & ~(1 << pBitIndex));
118 | }
119 |
120 | return ret;
121 | } else {
122 | throw new IllegalArgumentException("parameter \'pBitIndex\' must be between 0 and 7. pBitIndex=" + pBitIndex);
123 | }
124 | }
125 |
126 | public static String toBinary(byte[] pBytes) {
127 | String ret = null;
128 | if(pBytes != null && pBytes.length > 0) {
129 | BigInteger val = new BigInteger(bytesToStringNoSpace(pBytes), 16);
130 | StringBuilder build = new StringBuilder(val.toString(2));
131 |
132 | for(int i = build.length(); i < pBytes.length * 8; ++i) {
133 | build.insert(0, 0);
134 | }
135 |
136 | ret = build.toString();
137 | }
138 |
139 | return ret;
140 | }
141 |
142 | public static byte[] toByteArray(int value) {
143 | return new byte[]{(byte)(value >> 24), (byte)(value >> 16), (byte)(value >> 8), (byte)value};
144 | }
145 |
146 | private BytesUtils() {
147 | }
148 | }
149 |
--------------------------------------------------------------------------------
/creditCardNfcReader/src/main/java/com/peerbits/creditCardNfcReader/utils/CardNfcUtils.java:
--------------------------------------------------------------------------------
1 | package com.peerbits.creditCardNfcReader.utils;
2 |
3 | import android.app.Activity;
4 | import android.app.PendingIntent;
5 | import android.content.Context;
6 | import android.content.Intent;
7 | import android.content.IntentFilter;
8 | import android.nfc.NfcAdapter;
9 | import android.nfc.tech.IsoDep;
10 | import android.nfc.tech.NfcA;
11 |
12 | /**
13 | * Created by pro100svitlo on 31.03.16.
14 | */
15 | public class CardNfcUtils {
16 |
17 | private final NfcAdapter mNfcAdapter;
18 | private final PendingIntent mPendingIntent;
19 | private final Activity mActivity;
20 | private static final IntentFilter[] INTENT_FILTER = new IntentFilter[] {
21 | new IntentFilter(NfcAdapter.ACTION_TECH_DISCOVERED),
22 | new IntentFilter(NfcAdapter.ACTION_TAG_DISCOVERED)};
23 | private static final String[][] TECH_LIST = new String[][] { {
24 | NfcA.class.getName(), IsoDep.class.getName() } };
25 |
26 | public CardNfcUtils(final Activity pActivity) {
27 | mActivity = pActivity;
28 | mNfcAdapter = NfcAdapter.getDefaultAdapter(mActivity);
29 | mPendingIntent = PendingIntent.getActivity(mActivity, 0,
30 | new Intent(mActivity, mActivity.getClass()).addFlags(Intent.FLAG_ACTIVITY_SINGLE_TOP), 0);
31 | }
32 |
33 | public void disableDispatch() {
34 | if (mNfcAdapter != null) {
35 | mNfcAdapter.disableForegroundDispatch(mActivity);
36 | }
37 | }
38 |
39 | public void enableDispatch() {
40 | if (mNfcAdapter != null) {
41 | mNfcAdapter.enableForegroundDispatch(mActivity, mPendingIntent, INTENT_FILTER, TECH_LIST);
42 | }
43 | }
44 | }
45 |
--------------------------------------------------------------------------------
/creditCardNfcReader/src/main/java/com/peerbits/creditCardNfcReader/utils/CommandApdu.java:
--------------------------------------------------------------------------------
1 | package com.peerbits.creditCardNfcReader.utils;
2 |
3 | import com.peerbits.creditCardNfcReader.enums.CommandEnum;
4 |
5 | public class CommandApdu {
6 |
7 | protected int mCla = 0x00;
8 |
9 | protected int mIns = 0x00;
10 |
11 | protected int mP1 = 0x00;
12 |
13 | protected int mP2 = 0x00;
14 |
15 | protected int mLc = 0x00;
16 |
17 | protected byte[] mData = new byte[0];
18 |
19 | protected int mLe = 0x00;
20 |
21 | protected boolean mLeUsed = false;
22 |
23 | public CommandApdu(final CommandEnum pEnum, final byte[] data, final int le) {
24 | mCla = pEnum.getCla();
25 | mIns = pEnum.getIns();
26 | mP1 = pEnum.getP1();
27 | mP2 = pEnum.getP2();
28 | mLc = data == null ? 0 : data.length;
29 | mData = data;
30 | mLe = le;
31 | mLeUsed = true;
32 | }
33 |
34 | public CommandApdu(final CommandEnum pEnum, final int p1, final int p2, final int le) {
35 | mCla = pEnum.getCla();
36 | mIns = pEnum.getIns();
37 | mP1 = p1;
38 | mP2 = p2;
39 | mLe = le;
40 | mLeUsed = true;
41 | }
42 |
43 | public CommandApdu(final CommandEnum pEnum, final int p1, final int p2) {
44 | mCla = pEnum.getCla();
45 | mIns = pEnum.getIns();
46 | mP1 = p1;
47 | mP2 = p2;
48 | mLeUsed = false;
49 | }
50 |
51 | public byte[] toBytes() {
52 | int length = 4; // CLA, INS, P1, P2
53 | if (mData != null && mData.length != 0) {
54 | length += 1; // LC
55 | length += mData.length; // DATA
56 | }
57 | if (mLeUsed) {
58 | length += 1; // LE
59 | }
60 |
61 | byte[] apdu = new byte[length];
62 |
63 | int index = 0;
64 | apdu[index] = (byte) mCla;
65 | index++;
66 | apdu[index] = (byte) mIns;
67 | index++;
68 | apdu[index] = (byte) mP1;
69 | index++;
70 | apdu[index] = (byte) mP2;
71 | index++;
72 | if (mData != null && mData.length != 0) {
73 | apdu[index] = (byte) mLc;
74 | index++;
75 | System.arraycopy(mData, 0, apdu, index, mData.length);
76 | index += mData.length;
77 | }
78 | if (mLeUsed) {
79 | apdu[index] += (byte) mLe; // LE
80 | }
81 |
82 | return apdu;
83 | }
84 |
85 | }
86 |
--------------------------------------------------------------------------------
/creditCardNfcReader/src/main/java/com/peerbits/creditCardNfcReader/utils/EnumUtils.java:
--------------------------------------------------------------------------------
1 | package com.peerbits.creditCardNfcReader.utils;
2 |
3 | import com.peerbits.creditCardNfcReader.model.enums.IKeyEnum;
4 |
5 | import org.slf4j.Logger;
6 | import org.slf4j.LoggerFactory;
7 |
8 | /**
9 | * Utils class which provided methods to manipulate Enum
10 | */
11 | public final class EnumUtils {
12 |
13 | /**
14 | * Class logger
15 | */
16 | private static final Logger LOGGER = LoggerFactory.getLogger(EnumUtils.class);
17 |
18 | /**
19 | * Get the value of and enum from his key
20 | *
21 | * @param pKey
22 | * key to find
23 | * @param pClass
24 | * Enum class
25 | * @return Enum instance of the specified key or null otherwise
26 | */
27 | @SuppressWarnings("unchecked")
28 | public static T getValue(final int pKey, final Class pClass) {
29 | for (IKeyEnum val : pClass.getEnumConstants()) {
30 | if (val.getKey() == pKey) {
31 | return (T) val;
32 | }
33 | }
34 | LOGGER.error("Unknow value:" + pKey + " for Enum:" + pClass.getName());
35 | return null;
36 | }
37 |
38 | /**
39 | * Private constructor
40 | */
41 | private EnumUtils() {
42 | }
43 | }
44 |
--------------------------------------------------------------------------------
/creditCardNfcReader/src/main/java/com/peerbits/creditCardNfcReader/utils/Provider.java:
--------------------------------------------------------------------------------
1 | package com.peerbits.creditCardNfcReader.utils;
2 |
3 | import android.nfc.tech.IsoDep;
4 | import android.util.Log;
5 |
6 | import com.peerbits.creditCardNfcReader.enums.SwEnum;
7 | import com.peerbits.creditCardNfcReader.exception.CommunicationException;
8 | import com.peerbits.creditCardNfcReader.parser.IProvider;
9 |
10 | import java.io.IOException;
11 |
12 | public class Provider implements IProvider{
13 |
14 |
15 | private static final String TAG = Provider.class.getName();
16 |
17 | private StringBuffer log = new StringBuffer();
18 |
19 | private IsoDep mTagCom;
20 |
21 | public void setmTagCom(final IsoDep mTagCom) {
22 | this.mTagCom = mTagCom;
23 | }
24 |
25 |
26 | public StringBuffer getLog() {
27 | return log;
28 | }
29 |
30 | @Override
31 | public byte[] transceive(byte[] pCommand) throws CommunicationException {
32 | log.append("=================
");
33 | log.append("send: " + BytesUtils.bytesToString(pCommand)).append("
");
34 |
35 | byte[] response = null;
36 | try {
37 | // send command to emv card
38 | response = mTagCom.transceive(pCommand);
39 | } catch (IOException e) {
40 | throw new CommunicationException(e.getMessage());
41 | }
42 |
43 | log.append("resp: " + BytesUtils.bytesToString(response)).append("
");
44 | Log.d(TAG, "resp: " + BytesUtils.bytesToString(response));
45 | try {
46 | Log.d(TAG, "resp: " + TlvUtil.prettyPrintAPDUResponse(response));
47 | SwEnum val = SwEnum.getSW(response);
48 | if (val != null) {
49 | Log.d(TAG, "resp: " + val.getDetail());
50 | }
51 | log.append("").append(TlvUtil.prettyPrintAPDUResponse(response).replace("\n", "
").replace(" ", " "))
52 | .append("
");
53 | } catch (Exception e) {
54 | }
55 |
56 | return response;
57 | }
58 | }
59 |
--------------------------------------------------------------------------------
/creditCardNfcReader/src/main/java/com/peerbits/creditCardNfcReader/utils/ResponseUtils.java:
--------------------------------------------------------------------------------
1 | package com.peerbits.creditCardNfcReader.utils;
2 |
3 | import com.peerbits.creditCardNfcReader.enums.SwEnum;
4 |
5 | import org.slf4j.Logger;
6 | import org.slf4j.LoggerFactory;
7 |
8 | import java.util.Arrays;
9 |
10 | import fr.devnied.bitlib.BytesUtils;
11 |
12 |
13 | /**
14 | * Method used to manipulate response from APDU command
15 | *
16 | */
17 | public final class ResponseUtils {
18 |
19 | /**
20 | * Class logger
21 | */
22 | private static final Logger LOGGER = LoggerFactory.getLogger(ResponseUtils.class);
23 |
24 | /**
25 | * Method used to check if the last command return SW1SW2 == 9000
26 | *
27 | * @param pByte
28 | * response to the last command
29 | * @return true if the status is 9000 false otherwise
30 | */
31 | public static boolean isSucceed(final byte[] pByte) {
32 | return isEquals(pByte, SwEnum.SW_9000);
33 | }
34 |
35 | /**
36 | * Method used to check equality with the last command return SW1SW2 == pEnum
37 | *
38 | * @param pByte
39 | * response to the last command
40 | * @param pEnum
41 | * response to check
42 | * @return true if the response of the last command is equals to pEnum
43 | */
44 | public static boolean isEquals(final byte[] pByte, final SwEnum pEnum) {
45 | SwEnum val = SwEnum.getSW(pByte);
46 | if (LOGGER.isDebugEnabled() && pByte != null) {
47 | byte[] ooo = Arrays.copyOfRange(pByte, pByte.length - 2, pByte.length);
48 | String q = BytesUtils.bytesToStringNoSpace(ooo);
49 | LOGGER.debug("Response Status <"
50 | + q + "> : "
51 | + (val != null ? val.getDetail() : "Unknow"));
52 | }
53 | return val != null && val == pEnum;
54 | }
55 |
56 |
57 | /**
58 | * Private constructor
59 | */
60 | private ResponseUtils() {
61 | }
62 |
63 | }
64 |
--------------------------------------------------------------------------------
/creditCardNfcReader/src/main/java/com/peerbits/creditCardNfcReader/utils/TrackUtils.java:
--------------------------------------------------------------------------------
1 | package com.peerbits.creditCardNfcReader.utils;
2 |
3 | import com.peerbits.creditCardNfcReader.iso7816emv.EmvTags;
4 | import com.peerbits.creditCardNfcReader.model.EmvCard;
5 | import com.peerbits.creditCardNfcReader.model.Service;
6 |
7 | import org.slf4j.Logger;
8 | import org.slf4j.LoggerFactory;
9 |
10 | import java.util.regex.Matcher;
11 | import java.util.regex.Pattern;
12 |
13 | import fr.devnied.bitlib.BytesUtils;
14 |
15 | /**
16 | * Extract track data
17 | */
18 | public final class TrackUtils {
19 |
20 | /**
21 | * Class logger
22 | */
23 | private static final Logger LOGGER = LoggerFactory.getLogger(TrackUtils.class);
24 |
25 | /**
26 | * Track 2 pattern
27 | */
28 | private static final Pattern TRACK2_PATTERN = Pattern.compile("([0-9]{1,19})D([0-9]{4})([0-9]{3})?(.*)");
29 |
30 | /**
31 | * Extract track 2 data
32 | *
33 | * @param pEmvCard
34 | * Object card representation
35 | * @param pData
36 | * data to parse
37 | * @return true if the extraction succeed false otherwise
38 | */
39 | public static boolean extractTrack2Data(final EmvCard pEmvCard, final byte[] pData) {
40 | boolean ret = false;
41 | byte[] track2 = TlvUtil.getValue(pData, EmvTags.TRACK_2_EQV_DATA, EmvTags.TRACK2_DATA);
42 |
43 | if (track2 != null) {
44 | String data = BytesUtils.bytesToStringNoSpace(track2);
45 | Matcher m = TRACK2_PATTERN.matcher(data);
46 | // Check pattern
47 | if (m.find()) {
48 | // read card number
49 | pEmvCard.setCardNumber(m.group(1));
50 | // Read expire date
51 | String month = m.group(2).substring(2,4);
52 | String year = m.group(2).substring(0,2);
53 | pEmvCard.setExpireDate(month+"/"+year);
54 | // Read service
55 | pEmvCard.setService(new Service(m.group(3)));
56 | ret = true;
57 | }
58 | }
59 | return ret;
60 | }
61 |
62 | /**
63 | * Private constructor
64 | */
65 | private TrackUtils() {
66 | }
67 |
68 | }
69 |
--------------------------------------------------------------------------------
/creditCardNfcReader/src/main/res/values/strings.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
--------------------------------------------------------------------------------
/creditCardNfcReader/src/main/res/xml/nfc_tech_filter.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | android.nfc.tech.IsoDep
6 |
7 |
8 |
--------------------------------------------------------------------------------
/dotlib/.gitignore:
--------------------------------------------------------------------------------
1 | /build
2 |
--------------------------------------------------------------------------------
/dotlib/build.gradle:
--------------------------------------------------------------------------------
1 | apply plugin: 'com.android.library'
2 | apply plugin: 'com.github.dcendents.android-maven'
3 |
4 | group='com.github.bhargavms'
5 |
6 | android {
7 | compileSdkVersion 25
8 | buildToolsVersion "25.0.3"
9 |
10 | defaultConfig {
11 | minSdkVersion 11
12 | targetSdkVersion 25
13 | versionCode 4
14 | versionName "1.1.0"
15 | }
16 | buildTypes {
17 | release {
18 | minifyEnabled false
19 | proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
20 | }
21 | }
22 | }
23 |
24 | dependencies {
25 | testCompile 'junit:junit:4.12'
26 | }
27 |
--------------------------------------------------------------------------------
/dotlib/proguard-rules.pro:
--------------------------------------------------------------------------------
1 | # Add project specific ProGuard rules here.
2 | # By default, the flags in this file are appended to flags specified
3 | # in C:\Users\Bhargav\AppData\Local\Android\sdk/tools/proguard/proguard-android.txt
4 | # You can edit the include path and order by changing the proguardFiles
5 | # directive in build.gradle.
6 | #
7 | # For more details, see
8 | # http://developer.android.com/guide/developing/tools/proguard.html
9 |
10 | # Add any project specific keep options here:
11 |
12 | # If your project uses WebView with JS, uncomment the following
13 | # and specify the fully qualified class name to the JavaScript interface
14 | # class:
15 | #-keepclassmembers class fqcn.of.javascript.interface.for.webview {
16 | # public *;
17 | #}
18 |
--------------------------------------------------------------------------------
/dotlib/src/androidTest/java/com/bhargavms/dotloader/ApplicationTest.java:
--------------------------------------------------------------------------------
1 | package com.bhargavms.dotloader;
2 |
3 | import android.app.Application;
4 | import android.test.ApplicationTestCase;
5 |
6 | /**
7 | * Testing Fundamentals
8 | */
9 | public class ApplicationTest extends ApplicationTestCase {
10 | public ApplicationTest() {
11 | super(Application.class);
12 | }
13 | }
--------------------------------------------------------------------------------
/dotlib/src/main/AndroidManifest.xml:
--------------------------------------------------------------------------------
1 |
3 |
4 |
7 |
8 |
9 |
10 |
11 |
--------------------------------------------------------------------------------
/dotlib/src/main/java/com/bhargavms/dotloader/AnimationRepeater.java:
--------------------------------------------------------------------------------
1 | package com.bhargavms.dotloader;
2 |
3 | import android.animation.Animator;
4 |
5 | /**
6 | * Created by bhargav on 5/27/17.
7 | */
8 |
9 | class AnimationRepeater implements Animator.AnimatorListener {
10 | private boolean alternate = true;
11 | private Dot mDot;
12 | private Integer[] mColors;
13 |
14 | AnimationRepeater(Dot dot, Integer[] colors) {
15 | this.mDot = dot;
16 | mColors = colors;
17 | }
18 |
19 | @Override
20 | public void onAnimationStart(Animator animator) {
21 |
22 | }
23 |
24 | @Override
25 | public void onAnimationEnd(Animator animator) {
26 |
27 | }
28 |
29 | @Override
30 | public void onAnimationCancel(Animator animator) {
31 |
32 | }
33 |
34 | @Override
35 | public void onAnimationRepeat(Animator animator) {
36 | if (alternate) {
37 | mDot.colorAnimator.setObjectValues(
38 | mColors[mDot.mCurrentColorIndex],
39 | mColors[mDot.incrementColorIndex()]
40 | );
41 | mDot.colorAnimator.start();
42 | alternate = false;
43 | } else {
44 | alternate = true;
45 | }
46 | }
47 | }
48 |
--------------------------------------------------------------------------------
/dotlib/src/main/java/com/bhargavms/dotloader/CubicBezierInterpolator.java:
--------------------------------------------------------------------------------
1 | package com.bhargavms.dotloader;
2 |
3 | import android.graphics.PointF;
4 | import android.view.animation.Interpolator;
5 |
6 | /**
7 | * Derived from: https://github.com/rdallasgray/bez
8 | */
9 | public class CubicBezierInterpolator implements Interpolator {
10 |
11 | protected PointF start;
12 | protected PointF end;
13 | protected PointF a = new PointF();
14 | protected PointF b = new PointF();
15 | protected PointF c = new PointF();
16 |
17 | public CubicBezierInterpolator(PointF start, PointF end) throws IllegalArgumentException {
18 | if (start.x < 0 || start.x > 1) {
19 | throw new IllegalArgumentException("startX value must be in the range [0, 1]");
20 | }
21 | if (end.x < 0 || end.x > 1) {
22 | throw new IllegalArgumentException("endX value must be in the range [0, 1]");
23 | }
24 | this.start = start;
25 | this.end = end;
26 | }
27 |
28 | public CubicBezierInterpolator(float startX, float startY, float endX, float endY) {
29 | this(new PointF(startX, startY), new PointF(endX, endY));
30 | }
31 |
32 | public CubicBezierInterpolator(double startX, double startY, double endX, double endY) {
33 | this((float) startX, (float) startY, (float) endX, (float) endY);
34 | }
35 |
36 | @Override
37 | public float getInterpolation(float time) {
38 | return getBezierCoordinateY(getXForTime(time));
39 | }
40 |
41 | protected float getBezierCoordinateY(float time) {
42 | c.y = 3 * start.y;
43 | b.y = 3 * (end.y - start.y) - c.y;
44 | a.y = 1 - c.y - b.y;
45 | return time * (c.y + time * (b.y + time * a.y));
46 | }
47 |
48 | protected float getXForTime(float time) {
49 | float x = time;
50 | float z;
51 | for (int i = 1; i < 14; i++) {
52 | z = getBezierCoordinateX(x) - time;
53 | if (Math.abs(z) < 1e-3) {
54 | break;
55 | }
56 | x -= z / getXDerivate(x);
57 | }
58 | return x;
59 | }
60 |
61 | private float getXDerivate(float t) {
62 | return c.x + t * (2 * b.x + 3 * a.x * t);
63 | }
64 |
65 | private float getBezierCoordinateX(float time) {
66 | c.x = 3 * start.x;
67 | b.x = 3 * (end.x - start.x) - c.x;
68 | a.x = 1 - c.x - b.x;
69 | return time * (c.x + time * (b.x + time * a.x));
70 | }
71 | }
--------------------------------------------------------------------------------
/dotlib/src/main/java/com/bhargavms/dotloader/Dot.java:
--------------------------------------------------------------------------------
1 | package com.bhargavms.dotloader;
2 |
3 | import android.animation.ValueAnimator;
4 | import android.graphics.Canvas;
5 | import android.graphics.Color;
6 | import android.graphics.Paint;
7 |
8 | /**
9 | * Created by Bhargav on 7/20/2016.
10 | */
11 | class Dot {
12 | private Paint mPaint;
13 | int mCurrentColorIndex;
14 | private int mDotRadius;
15 | private Integer[] mColors;
16 | float cx;
17 | float cy;
18 | int position;
19 | ValueAnimator positionAnimator;
20 | ValueAnimator colorAnimator;
21 |
22 | Dot(DotLoader parent, int dotRadius, int position) {
23 | this.position = position;
24 | mColors = parent.mColors;
25 | mCurrentColorIndex = 0;
26 | mDotRadius = dotRadius;
27 |
28 | mPaint = new Paint(Paint.ANTI_ALIAS_FLAG);
29 | mPaint.setColor(mColors[mCurrentColorIndex]);
30 | mPaint.setShadowLayer(5.5f, 6.0f, 6.0f, Color.BLACK);
31 | mPaint.setStyle(Paint.Style.FILL);
32 | }
33 |
34 | void setColorIndex(int index) {
35 | mCurrentColorIndex = index;
36 | mPaint.setColor(mColors[index]);
37 | }
38 |
39 | void setColor(int color) {
40 | mPaint.setColor(color);
41 | }
42 |
43 | private int getCurrentColor() {
44 | return mColors[mCurrentColorIndex];
45 | }
46 |
47 | public int incrementAndGetColor() {
48 | incrementColorIndex();
49 | return getCurrentColor();
50 | }
51 |
52 | void applyNextColor() {
53 | mCurrentColorIndex++;
54 | if (mCurrentColorIndex >= mColors.length)
55 | mCurrentColorIndex = 0;
56 | mPaint.setColor(mColors[mCurrentColorIndex]);
57 | }
58 |
59 | int incrementColorIndex() {
60 | mCurrentColorIndex++;
61 | if (mCurrentColorIndex >= mColors.length)
62 | mCurrentColorIndex = 0;
63 | return mCurrentColorIndex;
64 | }
65 |
66 | void draw(Canvas canvas) {
67 | canvas.drawCircle(cx, cy, mDotRadius, mPaint);
68 | }
69 | }
70 |
--------------------------------------------------------------------------------
/dotlib/src/main/res/values/attrs.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
--------------------------------------------------------------------------------
/dotlib/src/main/res/values/strings.xml:
--------------------------------------------------------------------------------
1 |
2 | dotloader
3 |
4 |
--------------------------------------------------------------------------------
/dotlib/src/test/java/com/bhargavms/dotloader/ExampleUnitTest.java:
--------------------------------------------------------------------------------
1 | package com.bhargavms.dotloader;
2 |
3 | import org.junit.Test;
4 |
5 | import static org.junit.Assert.*;
6 |
7 | /**
8 | * To work on unit tests, switch the Test Artifact in the Build Variants view.
9 | */
10 | public class ExampleUnitTest {
11 | @Test
12 | public void addition_isCorrect() throws Exception {
13 | assertEquals(4, 2 + 2);
14 | }
15 | }
--------------------------------------------------------------------------------
/gradle.properties:
--------------------------------------------------------------------------------
1 | # Project-wide Gradle settings.
2 |
3 | # IDE (e.g. Android Studio) users:
4 | # Gradle settings configured through the IDE *will override*
5 | # any settings specified in this file.
6 |
7 | # For more details on how to configure your build environment visit
8 | # http://www.gradle.org/docs/current/userguide/build_environment.html
9 |
10 | # Specifies the JVM arguments used for the daemon process.
11 | # The setting is particularly useful for tweaking memory settings.
12 | # Default value: -Xmx10248m -XX:MaxPermSize=256m
13 | # org.gradle.jvmargs=-Xmx2048m -XX:MaxPermSize=512m -XX:+HeapDumpOnOutOfMemoryError -Dfile.encoding=UTF-8
14 |
15 | # When configured, Gradle will run in incubating parallel mode.
16 | # This option should only be used with decoupled projects. More details, visit
17 | # http://www.gradle.org/docs/current/userguide/multi_project_builds.html#sec:decoupled_projects
18 | # org.gradle.parallel=true
--------------------------------------------------------------------------------
/gradle/wrapper/gradle-wrapper.jar:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/gradle/wrapper/gradle-wrapper.jar
--------------------------------------------------------------------------------
/gradle/wrapper/gradle-wrapper.properties:
--------------------------------------------------------------------------------
1 | #Thu Nov 01 16:28:30 IST 2018
2 | distributionBase=GRADLE_USER_HOME
3 | distributionPath=wrapper/dists
4 | zipStoreBase=GRADLE_USER_HOME
5 | zipStorePath=wrapper/dists
6 | distributionUrl=https\://services.gradle.org/distributions/gradle-4.4-all.zip
7 |
--------------------------------------------------------------------------------
/gradlew:
--------------------------------------------------------------------------------
1 | #!/usr/bin/env bash
2 |
3 | ##############################################################################
4 | ##
5 | ## Gradle start up script for UN*X
6 | ##
7 | ##############################################################################
8 |
9 | # Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.
10 | DEFAULT_JVM_OPTS=""
11 |
12 | APP_NAME="Gradle"
13 | APP_BASE_NAME=`basename "$0"`
14 |
15 | # Use the maximum available, or set MAX_FD != -1 to use that value.
16 | MAX_FD="maximum"
17 |
18 | warn ( ) {
19 | echo "$*"
20 | }
21 |
22 | die ( ) {
23 | echo
24 | echo "$*"
25 | echo
26 | exit 1
27 | }
28 |
29 | # OS specific support (must be 'true' or 'false').
30 | cygwin=false
31 | msys=false
32 | darwin=false
33 | case "`uname`" in
34 | CYGWIN* )
35 | cygwin=true
36 | ;;
37 | Darwin* )
38 | darwin=true
39 | ;;
40 | MINGW* )
41 | msys=true
42 | ;;
43 | esac
44 |
45 | # Attempt to set APP_HOME
46 | # Resolve links: $0 may be a link
47 | PRG="$0"
48 | # Need this for relative symlinks.
49 | while [ -h "$PRG" ] ; do
50 | ls=`ls -ld "$PRG"`
51 | link=`expr "$ls" : '.*-> \(.*\)$'`
52 | if expr "$link" : '/.*' > /dev/null; then
53 | PRG="$link"
54 | else
55 | PRG=`dirname "$PRG"`"/$link"
56 | fi
57 | done
58 | SAVED="`pwd`"
59 | cd "`dirname \"$PRG\"`/" >/dev/null
60 | APP_HOME="`pwd -P`"
61 | cd "$SAVED" >/dev/null
62 |
63 | CLASSPATH=$APP_HOME/gradle/wrapper/gradle-wrapper.jar
64 |
65 | # Determine the Java command to use to start the JVM.
66 | if [ -n "$JAVA_HOME" ] ; then
67 | if [ -x "$JAVA_HOME/jre/sh/java" ] ; then
68 | # IBM's JDK on AIX uses strange locations for the executables
69 | JAVACMD="$JAVA_HOME/jre/sh/java"
70 | else
71 | JAVACMD="$JAVA_HOME/bin/java"
72 | fi
73 | if [ ! -x "$JAVACMD" ] ; then
74 | die "ERROR: JAVA_HOME is set to an invalid directory: $JAVA_HOME
75 |
76 | Please set the JAVA_HOME variable in your environment to match the
77 | location of your Java installation."
78 | fi
79 | else
80 | JAVACMD="java"
81 | which java >/dev/null 2>&1 || die "ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH.
82 |
83 | Please set the JAVA_HOME variable in your environment to match the
84 | location of your Java installation."
85 | fi
86 |
87 | # Increase the maximum file descriptors if we can.
88 | if [ "$cygwin" = "false" -a "$darwin" = "false" ] ; then
89 | MAX_FD_LIMIT=`ulimit -H -n`
90 | if [ $? -eq 0 ] ; then
91 | if [ "$MAX_FD" = "maximum" -o "$MAX_FD" = "max" ] ; then
92 | MAX_FD="$MAX_FD_LIMIT"
93 | fi
94 | ulimit -n $MAX_FD
95 | if [ $? -ne 0 ] ; then
96 | warn "Could not set maximum file descriptor limit: $MAX_FD"
97 | fi
98 | else
99 | warn "Could not query maximum file descriptor limit: $MAX_FD_LIMIT"
100 | fi
101 | fi
102 |
103 | # For Darwin, add options to specify how the application appears in the dock
104 | if $darwin; then
105 | GRADLE_OPTS="$GRADLE_OPTS \"-Xdock:name=$APP_NAME\" \"-Xdock:icon=$APP_HOME/media/gradle.icns\""
106 | fi
107 |
108 | # For Cygwin, switch paths to Windows format before running java
109 | if $cygwin ; then
110 | APP_HOME=`cygpath --path --mixed "$APP_HOME"`
111 | CLASSPATH=`cygpath --path --mixed "$CLASSPATH"`
112 | JAVACMD=`cygpath --unix "$JAVACMD"`
113 |
114 | # We build the pattern for arguments to be converted via cygpath
115 | ROOTDIRSRAW=`find -L / -maxdepth 1 -mindepth 1 -type d 2>/dev/null`
116 | SEP=""
117 | for dir in $ROOTDIRSRAW ; do
118 | ROOTDIRS="$ROOTDIRS$SEP$dir"
119 | SEP="|"
120 | done
121 | OURCYGPATTERN="(^($ROOTDIRS))"
122 | # Add a user-defined pattern to the cygpath arguments
123 | if [ "$GRADLE_CYGPATTERN" != "" ] ; then
124 | OURCYGPATTERN="$OURCYGPATTERN|($GRADLE_CYGPATTERN)"
125 | fi
126 | # Now convert the arguments - kludge to limit ourselves to /bin/sh
127 | i=0
128 | for arg in "$@" ; do
129 | CHECK=`echo "$arg"|egrep -c "$OURCYGPATTERN" -`
130 | CHECK2=`echo "$arg"|egrep -c "^-"` ### Determine if an option
131 |
132 | if [ $CHECK -ne 0 ] && [ $CHECK2 -eq 0 ] ; then ### Added a condition
133 | eval `echo args$i`=`cygpath --path --ignore --mixed "$arg"`
134 | else
135 | eval `echo args$i`="\"$arg\""
136 | fi
137 | i=$((i+1))
138 | done
139 | case $i in
140 | (0) set -- ;;
141 | (1) set -- "$args0" ;;
142 | (2) set -- "$args0" "$args1" ;;
143 | (3) set -- "$args0" "$args1" "$args2" ;;
144 | (4) set -- "$args0" "$args1" "$args2" "$args3" ;;
145 | (5) set -- "$args0" "$args1" "$args2" "$args3" "$args4" ;;
146 | (6) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" ;;
147 | (7) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" ;;
148 | (8) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" "$args7" ;;
149 | (9) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" "$args7" "$args8" ;;
150 | esac
151 | fi
152 |
153 | # Split up the JVM_OPTS And GRADLE_OPTS values into an array, following the shell quoting and substitution rules
154 | function splitJvmOpts() {
155 | JVM_OPTS=("$@")
156 | }
157 | eval splitJvmOpts $DEFAULT_JVM_OPTS $JAVA_OPTS $GRADLE_OPTS
158 | JVM_OPTS[${#JVM_OPTS[*]}]="-Dorg.gradle.appname=$APP_BASE_NAME"
159 |
160 | exec "$JAVACMD" "${JVM_OPTS[@]}" -classpath "$CLASSPATH" org.gradle.wrapper.GradleWrapperMain "$@"
161 |
--------------------------------------------------------------------------------
/gradlew.bat:
--------------------------------------------------------------------------------
1 | @if "%DEBUG%" == "" @echo off
2 | @rem ##########################################################################
3 | @rem
4 | @rem Gradle startup script for Windows
5 | @rem
6 | @rem ##########################################################################
7 |
8 | @rem Set local scope for the variables with windows NT shell
9 | if "%OS%"=="Windows_NT" setlocal
10 |
11 | @rem Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.
12 | set DEFAULT_JVM_OPTS=
13 |
14 | set DIRNAME=%~dp0
15 | if "%DIRNAME%" == "" set DIRNAME=.
16 | set APP_BASE_NAME=%~n0
17 | set APP_HOME=%DIRNAME%
18 |
19 | @rem Find java.exe
20 | if defined JAVA_HOME goto findJavaFromJavaHome
21 |
22 | set JAVA_EXE=java.exe
23 | %JAVA_EXE% -version >NUL 2>&1
24 | if "%ERRORLEVEL%" == "0" goto init
25 |
26 | echo.
27 | echo ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH.
28 | echo.
29 | echo Please set the JAVA_HOME variable in your environment to match the
30 | echo location of your Java installation.
31 |
32 | goto fail
33 |
34 | :findJavaFromJavaHome
35 | set JAVA_HOME=%JAVA_HOME:"=%
36 | set JAVA_EXE=%JAVA_HOME%/bin/java.exe
37 |
38 | if exist "%JAVA_EXE%" goto init
39 |
40 | echo.
41 | echo ERROR: JAVA_HOME is set to an invalid directory: %JAVA_HOME%
42 | echo.
43 | echo Please set the JAVA_HOME variable in your environment to match the
44 | echo location of your Java installation.
45 |
46 | goto fail
47 |
48 | :init
49 | @rem Get command-line arguments, handling Windowz variants
50 |
51 | if not "%OS%" == "Windows_NT" goto win9xME_args
52 | if "%@eval[2+2]" == "4" goto 4NT_args
53 |
54 | :win9xME_args
55 | @rem Slurp the command line arguments.
56 | set CMD_LINE_ARGS=
57 | set _SKIP=2
58 |
59 | :win9xME_args_slurp
60 | if "x%~1" == "x" goto execute
61 |
62 | set CMD_LINE_ARGS=%*
63 | goto execute
64 |
65 | :4NT_args
66 | @rem Get arguments from the 4NT Shell from JP Software
67 | set CMD_LINE_ARGS=%$
68 |
69 | :execute
70 | @rem Setup the command line
71 |
72 | set CLASSPATH=%APP_HOME%\gradle\wrapper\gradle-wrapper.jar
73 |
74 | @rem Execute Gradle
75 | "%JAVA_EXE%" %DEFAULT_JVM_OPTS% %JAVA_OPTS% %GRADLE_OPTS% "-Dorg.gradle.appname=%APP_BASE_NAME%" -classpath "%CLASSPATH%" org.gradle.wrapper.GradleWrapperMain %CMD_LINE_ARGS%
76 |
77 | :end
78 | @rem End local scope for the variables with windows NT shell
79 | if "%ERRORLEVEL%"=="0" goto mainEnd
80 |
81 | :fail
82 | rem Set variable GRADLE_EXIT_CONSOLE if you need the _script_ return code instead of
83 | rem the _cmd.exe /c_ return code!
84 | if not "" == "%GRADLE_EXIT_CONSOLE%" exit 1
85 | exit /b 1
86 |
87 | :mainEnd
88 | if "%OS%"=="Windows_NT" endlocal
89 |
90 | :omega
91 |
--------------------------------------------------------------------------------
/screenshots/Screenshot_20160428-122024.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/screenshots/Screenshot_20160428-122024.png
--------------------------------------------------------------------------------
/screenshots/Screenshot_20160428-122036.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/screenshots/Screenshot_20160428-122036.png
--------------------------------------------------------------------------------
/screenshots/Screenshot_20160428-122045.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Peerbits/Android-NFC/e0f3de8499dd74476415004f95fd45e68228795f/screenshots/Screenshot_20160428-122045.png
--------------------------------------------------------------------------------
/settings.gradle:
--------------------------------------------------------------------------------
1 | include ':app', ':creditCardNfcReader'
2 |
--------------------------------------------------------------------------------