Merge pull request #74 from therajanmaurya/AddIdentificationDocument

Add identification Scan card document
diff --git a/app/src/main/AndroidManifest.xml b/app/src/main/AndroidManifest.xml
index 35ad0f3..9fe55ce 100644
--- a/app/src/main/AndroidManifest.xml
+++ b/app/src/main/AndroidManifest.xml
@@ -3,6 +3,9 @@
           package="com.mifos.apache.fineract">
 
     <uses-permission android:name="android.permission.INTERNET" />
+    <uses-permission android:name="android.permission.CAMERA"/>
+
+    <uses-feature android:name="android.hardware.camera" android:required="false"/>
 
     <application
         android:allowBackup="true"
@@ -12,6 +15,16 @@
         android:name=".MifosApplication"
         android:theme="@style/AppTheme">
 
+        <provider
+            android:name="android.support.v4.content.FileProvider"
+            android:authorities="com.mifos.apache.fineract.fileprovider"
+            android:grantUriPermissions="true"
+            android:exported="false">
+            <meta-data
+                android:name="android.support.FILE_PROVIDER_PATHS"
+                android:resource="@xml/filepaths" />
+        </provider>
+
         <activity android:name=".ui.online.launcher.LauncherActivity">
             <intent-filter>
                 <action android:name="android.intent.action.MAIN"/>
diff --git a/app/src/main/java/com/mifos/apache/fineract/data/datamanager/DataManagerCustomer.java b/app/src/main/java/com/mifos/apache/fineract/data/datamanager/DataManagerCustomer.java
index 664c3ff..ef5d849 100644
--- a/app/src/main/java/com/mifos/apache/fineract/data/datamanager/DataManagerCustomer.java
+++ b/app/src/main/java/com/mifos/apache/fineract/data/datamanager/DataManagerCustomer.java
@@ -15,6 +15,7 @@
 
 import io.reactivex.Completable;
 import io.reactivex.Observable;
+import okhttp3.MultipartBody;
 
 /**
  * @author Rajan Maurya
@@ -65,4 +66,11 @@
         return baseApiManager.getCustomerApi().fetchIdentificationScanCards(customerIdentifier,
                 identificationNumber);
     }
+
+    public Completable uploadIdentificationCardScan(String customerIdentifier,
+            String identificationNumber, String scanIdentifier, String description,
+            MultipartBody.Part file) {
+        return baseApiManager.getCustomerApi().uploadIdentificationCardScan(customerIdentifier,
+                identificationNumber, scanIdentifier, description, file);
+    }
 }
diff --git a/app/src/main/java/com/mifos/apache/fineract/data/services/CustomerService.java b/app/src/main/java/com/mifos/apache/fineract/data/services/CustomerService.java
index a2a5ab5..f9d6b1a 100644
--- a/app/src/main/java/com/mifos/apache/fineract/data/services/CustomerService.java
+++ b/app/src/main/java/com/mifos/apache/fineract/data/services/CustomerService.java
@@ -11,9 +11,12 @@
 
 import io.reactivex.Completable;
 import io.reactivex.Observable;
+import okhttp3.MultipartBody;
 import retrofit2.http.Body;
 import retrofit2.http.GET;
+import retrofit2.http.Multipart;
 import retrofit2.http.POST;
+import retrofit2.http.Part;
 import retrofit2.http.Path;
 import retrofit2.http.Query;
 
@@ -57,4 +60,14 @@
     Observable<List<ScanCard>> fetchIdentificationScanCards(
             @Path("identifier") String identifier,
             @Path("identificationnumber") String identificationnumber);
+
+    @Multipart
+    @POST(EndPoints.API_CUSTOMER_PATH +
+            "/customers/{identifier}/identifications/{identificationnumber}/scans")
+    Completable uploadIdentificationCardScan(
+            @Path("identifier") String identifier,
+            @Path("identificationnumber") String identificationnumber,
+            @Query("scanIdentifier") String scanIdentifier,
+            @Query("description") String description,
+            @Part MultipartBody.Part file);
 }
diff --git a/app/src/main/java/com/mifos/apache/fineract/injection/component/ActivityComponent.java b/app/src/main/java/com/mifos/apache/fineract/injection/component/ActivityComponent.java
index 29df3ab..fc266f6 100644
--- a/app/src/main/java/com/mifos/apache/fineract/injection/component/ActivityComponent.java
+++ b/app/src/main/java/com/mifos/apache/fineract/injection/component/ActivityComponent.java
@@ -17,6 +17,8 @@
         .IdentificationDetailsFragment;
 import com.mifos.apache.fineract.ui.online.identification.identificationlist
         .IdentificationsFragment;
+import com.mifos.apache.fineract.ui.online.identification.uploadidentificationscan
+        .UploadIdentificationCardBottomSheet;
 import com.mifos.apache.fineract.ui.online.launcher.LauncherActivity;
 import com.mifos.apache.fineract.ui.online.loanapplication.BaseFragmentDebtIncome;
 import com.mifos.apache.fineract.ui.online.loanapplication.loanactivity.LoanApplicationActivity;
@@ -75,4 +77,6 @@
     void inject(CreateIdentificationActivity createIdentificationActivity);
 
     void inject(IdentificationDetailsFragment identificationDetailsFragment);
+
+    void inject(UploadIdentificationCardBottomSheet uploadIdentificationCardBottomSheet);
 }
diff --git a/app/src/main/java/com/mifos/apache/fineract/ui/online/identification/identificationdetails/IdentificationDetailsFragment.java b/app/src/main/java/com/mifos/apache/fineract/ui/online/identification/identificationdetails/IdentificationDetailsFragment.java
index 1197564..ebe8e4b 100644
--- a/app/src/main/java/com/mifos/apache/fineract/ui/online/identification/identificationdetails/IdentificationDetailsFragment.java
+++ b/app/src/main/java/com/mifos/apache/fineract/ui/online/identification/identificationdetails/IdentificationDetailsFragment.java
@@ -16,6 +16,10 @@
 import com.mifos.apache.fineract.ui.adapters.IdentificationScanAdapter;
 import com.mifos.apache.fineract.ui.base.MifosBaseActivity;
 import com.mifos.apache.fineract.ui.base.MifosBaseFragment;
+import com.mifos.apache.fineract.ui.online.identification.uploadidentificationscan
+        .AddScanIdentificationListener;
+import com.mifos.apache.fineract.ui.online.identification.uploadidentificationscan
+        .UploadIdentificationCardBottomSheet;
 import com.mifos.apache.fineract.utils.ConstantKeys;
 import com.mifos.apache.fineract.utils.DateUtils;
 
@@ -34,7 +38,7 @@
  */
 public class IdentificationDetailsFragment extends MifosBaseFragment
         implements IdentificationDetailsContract.View,
-        IdentificationScanAdapter.OnItemClickListener {
+        IdentificationScanAdapter.OnItemClickListener, AddScanIdentificationListener {
 
     @BindView(R.id.tv_number)
     TextView tvNumber;
@@ -104,6 +108,17 @@
         return rootView;
     }
 
+    @OnClick(R.id.fab_upload_identification_scan_card)
+    void addIdentificationCard() {
+        UploadIdentificationCardBottomSheet uploadIdentificationCardBottomSheet =
+                new UploadIdentificationCardBottomSheet();
+        uploadIdentificationCardBottomSheet.setIdentifierAndNumber(customerIdentifier,
+                identificationCard.getNumber());
+        uploadIdentificationCardBottomSheet.setAddScanIdentificationListener(this);
+        uploadIdentificationCardBottomSheet.show(getChildFragmentManager(),
+                getString(R.string.upload_new_identification_card_scan));
+    }
+
     @OnClick(R.id.iv_retry)
     void onRetry() {
         identificationDetailsPresenter.fetchIdentificationScanCards(customerIdentifier,
@@ -118,6 +133,15 @@
     }
 
     @Override
+    public void updateScanUploadedIdentification() {
+        tvScansStatus.setVisibility(View.VISIBLE);
+        rvScansUploaded.setVisibility(View.GONE);
+        rlError.setVisibility(View.GONE);
+        identificationDetailsPresenter.fetchIdentificationScanCards(customerIdentifier,
+                identificationCard.getNumber());
+    }
+
+    @Override
     public void showUserInterface() {
         tvNumber.setText(identificationCard.getNumber());
         tvIssuer.setText(identificationCard.getIssuer());
diff --git a/app/src/main/java/com/mifos/apache/fineract/ui/online/identification/uploadidentificationscan/AddScanIdentificationListener.java b/app/src/main/java/com/mifos/apache/fineract/ui/online/identification/uploadidentificationscan/AddScanIdentificationListener.java
new file mode 100644
index 0000000..1b57f87
--- /dev/null
+++ b/app/src/main/java/com/mifos/apache/fineract/ui/online/identification/uploadidentificationscan/AddScanIdentificationListener.java
@@ -0,0 +1,10 @@
+package com.mifos.apache.fineract.ui.online.identification.uploadidentificationscan;
+
+/**
+ * @author Rajan Maurya
+ *         On 03/08/17.
+ */
+public interface AddScanIdentificationListener {
+
+    void updateScanUploadedIdentification();
+}
diff --git a/app/src/main/java/com/mifos/apache/fineract/ui/online/identification/uploadidentificationscan/UploadIdentificationCardBottomSheet.java b/app/src/main/java/com/mifos/apache/fineract/ui/online/identification/uploadidentificationscan/UploadIdentificationCardBottomSheet.java
new file mode 100644
index 0000000..7450ec9
--- /dev/null
+++ b/app/src/main/java/com/mifos/apache/fineract/ui/online/identification/uploadidentificationscan/UploadIdentificationCardBottomSheet.java
@@ -0,0 +1,285 @@
+package com.mifos.apache.fineract.ui.online.identification.uploadidentificationscan;
+
+import static android.app.Activity.RESULT_OK;
+
+import android.Manifest;
+import android.annotation.TargetApi;
+import android.app.Dialog;
+import android.content.DialogInterface;
+import android.content.Intent;
+import android.content.pm.PackageManager;
+import android.graphics.Bitmap;
+import android.os.Build;
+import android.os.Bundle;
+import android.provider.MediaStore;
+import android.support.annotation.NonNull;
+import android.support.design.widget.BottomSheetBehavior;
+import android.support.design.widget.BottomSheetDialog;
+import android.support.design.widget.TextInputLayout;
+import android.text.Editable;
+import android.text.TextWatcher;
+import android.util.Log;
+import android.view.View;
+import android.widget.EditText;
+
+import com.mifos.apache.fineract.R;
+import com.mifos.apache.fineract.ui.base.MifosBaseActivity;
+import com.mifos.apache.fineract.ui.base.MifosBaseBottomSheetDialogFragment;
+import com.mifos.apache.fineract.ui.base.Toaster;
+import com.mifos.apache.fineract.utils.CheckSelfPermissionAndRequest;
+import com.mifos.apache.fineract.utils.ConstantKeys;
+import com.mifos.apache.fineract.utils.ValidateIdentifierUtil;
+import com.mifos.apache.fineract.utils.ValidationUtil;
+
+import java.io.File;
+import java.io.FileOutputStream;
+import java.io.IOException;
+
+import javax.inject.Inject;
+
+import butterknife.BindView;
+import butterknife.ButterKnife;
+import butterknife.OnClick;
+
+/**
+ * @author Rajan Maurya
+ *         On 01/08/17.
+ */
+public class UploadIdentificationCardBottomSheet extends MifosBaseBottomSheetDialogFragment
+        implements UploadIdentificationCardContract.View, TextWatcher {
+
+    public static final String LOG_TAG = UploadIdentificationCardBottomSheet.class.getSimpleName();
+
+    public static final int REQUEST_IMAGE_CAPTURE = 1;
+
+    @BindView(R.id.et_identifier)
+    EditText etIdentifier;
+
+    @BindView(R.id.et_description)
+    EditText etDescription;
+
+    @BindView(R.id.et_selected_file)
+    EditText etSelectFile;
+
+    @BindView(R.id.til_identifier)
+    TextInputLayout tilIdentifier;
+
+    @BindView(R.id.til_description)
+    TextInputLayout tilDescription;
+
+    @BindView(R.id.til_selected_file)
+    TextInputLayout tilSelectedFile;
+
+    @Inject
+    UploadIdentificationCardPresenter uploadIdentificationCardPresenter;
+
+    View rootView;
+
+    private BottomSheetBehavior behavior;
+    private File cachePath;
+    private String customerIdentifier;
+    private String identificationNumber;
+
+    private AddScanIdentificationListener addScanIdentificationListener;
+
+    @NonNull
+    @Override
+    public Dialog onCreateDialog(Bundle savedInstanceState) {
+        BottomSheetDialog dialog = (BottomSheetDialog) super.onCreateDialog(savedInstanceState);
+        rootView = View.inflate(getContext(),
+                R.layout.bottom_sheet_upload_identification_scan_card, null);
+        dialog.setContentView(rootView);
+        behavior = BottomSheetBehavior.from((View) rootView.getParent());
+        ((MifosBaseActivity) getActivity()).getActivityComponent().inject(this);
+        uploadIdentificationCardPresenter.attachView(this);
+        ButterKnife.bind(this, rootView);
+
+        showUserInterface();
+
+        return dialog;
+    }
+
+    @Override
+    public void showUserInterface() {
+        etIdentifier.addTextChangedListener(this);
+        etSelectFile.addTextChangedListener(this);
+        etDescription.addTextChangedListener(this);
+    }
+
+    @OnClick(R.id.btn_upload_identification_card_scan)
+    public void onUploadIdentificationCard() {
+        if (validateIdentifier() && validateDescription() && validateSelectFile()) {
+
+            uploadIdentificationCardPresenter.uploadIdentificationCardScan(customerIdentifier,
+                    identificationNumber, etIdentifier.getText().toString().trim(),
+                    etDescription.getText().toString().trim(), cachePath);
+        }
+    }
+
+    @OnClick(R.id.btn_cancel)
+    void onCancel() {
+        dismiss();
+    }
+
+    @OnClick(R.id.btn_browse_document)
+    void browseDocument() {
+        checkCameraPermission();
+    }
+
+    @Override
+    public void checkCameraPermission() {
+        if (CheckSelfPermissionAndRequest.checkSelfPermission(getActivity(),
+                Manifest.permission.CAMERA)) {
+            openCamera();
+        } else {
+            requestPermission();
+        }
+    }
+
+    @Override
+    public void openCamera() {
+        Intent takePictureIntent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
+        if (takePictureIntent.resolveActivity(getActivity().getPackageManager()) != null) {
+            startActivityForResult(takePictureIntent, REQUEST_IMAGE_CAPTURE);
+        }
+    }
+
+    @Override
+    public void onActivityResult(int requestCode, int resultCode, Intent data) {
+        if (requestCode == REQUEST_IMAGE_CAPTURE && resultCode == RESULT_OK) {
+            Bundle extras = data.getExtras();
+            Bitmap imageBitmap = (Bitmap) extras.get("data");
+            etSelectFile.setText(getString(R.string.scan_file));
+            saveImageInCache(imageBitmap);
+        }
+    }
+
+    @TargetApi(Build.VERSION_CODES.JELLY_BEAN)
+    @Override
+    public void requestPermission() {
+        CheckSelfPermissionAndRequest.requestPermission(
+                (MifosBaseActivity) getActivity(),
+                Manifest.permission.CAMERA,
+                ConstantKeys.PERMISSIONS_REQUEST_CAMERA,
+                getResources().getString(
+                        R.string.dialog_message_camera_permission_denied_prompt),
+                getResources().getString(R.string.dialog_message_camera_permission_never_ask_again),
+                ConstantKeys.PERMISSIONS_CAMERA_STATUS);
+    }
+
+    @Override
+    public void saveImageInCache(Bitmap bitmap) {
+        try {
+            File outputDir = getActivity().getCacheDir();
+            File outputFile = File.createTempFile("scan", "png", outputDir);
+            cachePath = outputFile;
+
+            // overwrites this image every time
+            FileOutputStream stream = new FileOutputStream(outputFile);
+            bitmap.compress(Bitmap.CompressFormat.PNG, 100, stream);
+            stream.close();
+        } catch (IOException e) {
+            Log.d(LOG_TAG, e.getLocalizedMessage());
+        }
+    }
+
+    @Override
+    public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions,
+            @NonNull int[] grantResults) {
+        switch (requestCode) {
+            case ConstantKeys.PERMISSIONS_REQUEST_CAMERA: {
+                if (grantResults.length > 0
+                        && grantResults[0] == PackageManager.PERMISSION_GRANTED) {
+                    openCamera();
+                } else {
+                    Toaster.show(rootView, getString(R.string.permission_denied_camera));
+                }
+            }
+        }
+    }
+
+    @Override
+    public void showScanUploadedSuccessfully() {
+        addScanIdentificationListener.updateScanUploadedIdentification();
+        dismiss();
+    }
+
+    @Override
+    public void showProgressDialog() {
+        showMifosProgressDialog(getString(R.string.uploading_identification_scan_card));
+    }
+
+    @Override
+    public void hideProgressDialog() {
+        hideMifosProgressDialog();
+    }
+
+    @Override
+    public void showError(String message) {
+        Toaster.show(rootView, message);
+    }
+
+    public void setIdentifierAndNumber(String identifier, String identificationNumber) {
+        customerIdentifier = identifier;
+        this.identificationNumber = identificationNumber;
+    }
+
+    public void setAddScanIdentificationListener(AddScanIdentificationListener listener) {
+        addScanIdentificationListener = listener;
+    }
+
+    @Override
+    public boolean validateIdentifier() {
+        return ValidateIdentifierUtil.isValid(getActivity(),
+                etIdentifier.getText().toString().trim(), tilIdentifier);
+    }
+
+    @Override
+    public boolean validateDescription() {
+        return ValidationUtil.isEmpty(getActivity(),
+                etDescription.getText().toString().trim(), tilDescription);
+    }
+
+    @Override
+    public boolean validateSelectFile() {
+        return ValidationUtil.isEmpty(getActivity(),
+                etSelectFile.getText().toString().trim(), tilSelectedFile);
+    }
+
+    @Override
+    public void beforeTextChanged(CharSequence s, int start, int count, int after) {
+    }
+
+    @Override
+    public void onTextChanged(CharSequence s, int start, int before, int count) {
+    }
+
+    @Override
+    public void afterTextChanged(Editable s) {
+        if ((etIdentifier.getText().hashCode() == s.hashCode())) {
+            validateIdentifier();
+        } else if (etDescription.getText().hashCode() == s.hashCode()) {
+            validateDescription();
+        } else if (etSelectFile.getText().hashCode() == s.hashCode()) {
+            validateSelectFile();
+        }
+    }
+
+    @Override
+    public void onDestroyView() {
+        super.onDestroyView();
+        hideMifosProgressDialog();
+        uploadIdentificationCardPresenter.detachView();
+    }
+
+    @Override
+    public void onStart() {
+        super.onStart();
+        behavior.setState(BottomSheetBehavior.STATE_EXPANDED);
+    }
+
+    @Override
+    public void onDismiss(DialogInterface dialog) {
+        super.onDismiss(dialog);
+    }
+}
diff --git a/app/src/main/java/com/mifos/apache/fineract/ui/online/identification/uploadidentificationscan/UploadIdentificationCardContract.java b/app/src/main/java/com/mifos/apache/fineract/ui/online/identification/uploadidentificationscan/UploadIdentificationCardContract.java
new file mode 100644
index 0000000..1a2edc7
--- /dev/null
+++ b/app/src/main/java/com/mifos/apache/fineract/ui/online/identification/uploadidentificationscan/UploadIdentificationCardContract.java
@@ -0,0 +1,48 @@
+package com.mifos.apache.fineract.ui.online.identification.uploadidentificationscan;
+
+import android.graphics.Bitmap;
+
+import com.mifos.apache.fineract.ui.base.MvpView;
+
+import java.io.File;
+
+/**
+ * @author Rajan Maurya
+ *         On 01/08/17.
+ */
+public interface UploadIdentificationCardContract {
+
+    interface View extends MvpView {
+
+        void showUserInterface();
+
+        void checkCameraPermission();
+
+        void openCamera();
+
+        void requestPermission();
+
+        void saveImageInCache(Bitmap bitmap);
+
+        void showScanUploadedSuccessfully();
+
+        void showProgressDialog();
+
+        void hideProgressDialog();
+
+        void showError(String message);
+
+        boolean validateIdentifier();
+
+        boolean validateDescription();
+
+        boolean validateSelectFile();
+    }
+
+    interface Presenter {
+
+        void uploadIdentificationCardScan(String customerIdentifier,
+                String identificationNumber, String scanIdentifier, String description,
+                File file);
+    }
+}
diff --git a/app/src/main/java/com/mifos/apache/fineract/ui/online/identification/uploadidentificationscan/UploadIdentificationCardPresenter.java b/app/src/main/java/com/mifos/apache/fineract/ui/online/identification/uploadidentificationscan/UploadIdentificationCardPresenter.java
new file mode 100644
index 0000000..74a6901
--- /dev/null
+++ b/app/src/main/java/com/mifos/apache/fineract/ui/online/identification/uploadidentificationscan/UploadIdentificationCardPresenter.java
@@ -0,0 +1,85 @@
+package com.mifos.apache.fineract.ui.online.identification.uploadidentificationscan;
+
+import android.content.Context;
+
+import com.mifos.apache.fineract.R;
+import com.mifos.apache.fineract.data.datamanager.DataManagerCustomer;
+import com.mifos.apache.fineract.injection.ApplicationContext;
+import com.mifos.apache.fineract.injection.ConfigPersistent;
+import com.mifos.apache.fineract.ui.base.BasePresenter;
+
+import java.io.File;
+
+import javax.inject.Inject;
+
+import io.reactivex.android.schedulers.AndroidSchedulers;
+import io.reactivex.disposables.CompositeDisposable;
+import io.reactivex.observers.DisposableCompletableObserver;
+import io.reactivex.schedulers.Schedulers;
+import okhttp3.MediaType;
+import okhttp3.MultipartBody;
+import okhttp3.RequestBody;
+
+/**
+ * @author Rajan Maurya
+ *         On 01/08/17.
+ */
+@ConfigPersistent
+public class UploadIdentificationCardPresenter extends
+        BasePresenter<UploadIdentificationCardContract.View>
+        implements UploadIdentificationCardContract.Presenter {
+
+    private DataManagerCustomer dataManagerCustomer;
+    private final CompositeDisposable compositeDisposable;
+
+    @Inject
+    protected UploadIdentificationCardPresenter(@ApplicationContext Context context,
+            DataManagerCustomer dataManagerCustomer) {
+        super(context);
+        this.dataManagerCustomer = dataManagerCustomer;
+        compositeDisposable = new CompositeDisposable();
+    }
+
+    @Override
+    public void attachView(UploadIdentificationCardContract.View mvpView) {
+        super.attachView(mvpView);
+    }
+
+    @Override
+    public void detachView() {
+        super.detachView();
+        compositeDisposable.clear();
+    }
+
+    @Override
+    public void uploadIdentificationCardScan(String customerIdentifier, String identificationNumber,
+            String scanIdentifier, String description, File file) {
+
+        RequestBody requestFile =
+                RequestBody.create(MediaType.parse("image/png"), file);
+        MultipartBody.Part body =
+                MultipartBody.Part.createFormData("image", "scan.png", requestFile);
+
+        checkViewAttached();
+        getMvpView().showProgressDialog();
+        compositeDisposable.add(dataManagerCustomer.uploadIdentificationCardScan(
+                customerIdentifier, identificationNumber, scanIdentifier, description, body)
+                .subscribeOn(Schedulers.io())
+                .observeOn(AndroidSchedulers.mainThread())
+                .subscribeWith(new DisposableCompletableObserver() {
+                    @Override
+                    public void onComplete() {
+                        getMvpView().hideProgressDialog();
+                        getMvpView().showScanUploadedSuccessfully();
+                    }
+
+                    @Override
+                    public void onError(Throwable e) {
+                        getMvpView().hideProgressDialog();
+                        getMvpView().showError(context
+                                .getString(R.string.error_uploading_identification_scan_card));
+                    }
+                })
+        );
+    }
+}
diff --git a/app/src/main/java/com/mifos/apache/fineract/utils/CheckSelfPermissionAndRequest.java b/app/src/main/java/com/mifos/apache/fineract/utils/CheckSelfPermissionAndRequest.java
new file mode 100644
index 0000000..280bdd6
--- /dev/null
+++ b/app/src/main/java/com/mifos/apache/fineract/utils/CheckSelfPermissionAndRequest.java
@@ -0,0 +1,144 @@
+package com.mifos.apache.fineract.utils;
+
+import android.annotation.TargetApi;
+import android.content.Context;
+import android.content.DialogInterface;
+import android.content.Intent;
+import android.content.pm.PackageManager;
+import android.net.Uri;
+import android.os.Build;
+import android.provider.Settings;
+import android.support.v4.app.ActivityCompat;
+import android.support.v4.content.ContextCompat;
+import android.support.v7.app.AppCompatActivity;
+import android.widget.Toast;
+
+import com.mifos.apache.fineract.R;
+import com.mifos.apache.fineract.data.local.PreferencesHelper;
+
+/**
+ * This Class is the CheckSelfPermissionAndRequest Class
+ * Created by Rajan Maurya on 03/08/16.
+ */
+public class CheckSelfPermissionAndRequest {
+
+
+    /**
+     * This Method Check the Permission is granted or not to the App. If the Permission granted,
+     * returns true and If not permission denied then returns false.
+     *
+     * @param context    Context
+     * @param permission Manifest.permission...Permission...
+     * @return Boolean True or False.
+     */
+    public static Boolean checkSelfPermission(Context context, String permission) {
+        return ContextCompat.checkSelfPermission(context, permission) ==
+                PackageManager.PERMISSION_GRANTED;
+    }
+
+    /**
+     * This Method is requesting to device to grant the permission. When App is trying to
+     * request the device to grant the permission, then their is Three cases.
+     * 1. First case Device Prompt the Permission Dialog to user and user accepted or denied the
+     * Permission.
+     * 2. Second case will come, if user will denied the permission, after onclick dialog denied
+     * button and next time App ask for permission, It will show a Material Dialog and there
+     * will be a message to tell the user that you have denied the permission before, So do
+     * you want to give this permission to app or not, If yes then click on Re-Try dialog button
+     * and if not then click on Dialog button "I'M Sure", to not to give this permission to the
+     * app.
+     * <p/>
+     * And as user will click on "Re-Try" dialog button, he will be prompt with the with
+     * permission dialog with "[-] never ask again" and have two options first one to click on
+     * denied button again and put Un check the never ask check box. In this case, user will
+     * prompt with permission dialog with "[-] never ask again" in the loop, whenever app ask
+     * for that permission.
+     * <p/>
+     * and If user will click on "[_/] never ask again" check box then permission dialog with
+     * that permission will not prompt to the user.
+     * 3. Third case will came. when user have denied to accept permission with never ask again.
+     * then user will prompt with dialog and message that you have denied this permission with
+     * never ask again. but this is necessary permission to this app feature. and to grant
+     * this permission please click on dialog app settings button and give the permission to
+     * work with this feature.
+     *
+     * @param activity               AppCompatActivity
+     * @param permission             Manifest.permission...Permission...
+     * @param permissionRequestCode  Permission Request Code.
+     * @param dialogMessageRetry     Dialog Message Retry
+     * @param messageNeverAskAgain   Dialog Message Never Ask Again
+     * @param permissionDeniedStatus Permission Denied Status
+     */
+    @TargetApi(Build.VERSION_CODES.JELLY_BEAN)
+    public static void requestPermission(final AppCompatActivity activity,
+                                         final String permission,
+                                         final int permissionRequestCode,
+                                         final String dialogMessageRetry,
+                                         final String messageNeverAskAgain,
+                                         final String permissionDeniedStatus) {
+        // Should we show an explanation?
+        if (ActivityCompat.shouldShowRequestPermissionRationale(activity, permission)) {
+
+            // Show an explanation to the user *asynchronously* -- don't block
+            // this thread waiting for the user's response! After the user
+            // sees the explanation, try again to request the permission.
+            new MaterialDialog.Builder().init(activity)
+                    .setTitle(R.string.dialog_permission_denied)
+                    .setMessage(dialogMessageRetry)
+                    .setPositiveButton(R.string.dialog_action_re_try,
+                            new DialogInterface.OnClickListener() {
+                                @Override
+                                public void onClick(DialogInterface dialog, int which) {
+                                    ActivityCompat.requestPermissions(activity, new
+                                                    String[]{permission},
+                                            permissionRequestCode);
+                                }
+                            })
+                    .setNegativeButton(R.string.dialog_action_i_am_sure)
+                    .createMaterialDialog()
+                    .show();
+        } else {
+
+            //Requesting Permission, first time to the device.
+            PreferencesHelper preferencesHelper = new PreferencesHelper(activity.
+                    getApplicationContext());
+            if (preferencesHelper.getBoolean(permissionDeniedStatus, true)) {
+                preferencesHelper.putBoolean(permissionDeniedStatus, false);
+
+                ActivityCompat.requestPermissions(activity, new String[]{permission},
+                        permissionRequestCode);
+            } else {
+                //Requesting Permission, more the one time and opening the setting to change
+                // the Permission in App Settings.
+                new MaterialDialog.Builder().init(activity)
+                        .setMessage(messageNeverAskAgain)
+                        .setNegativeButton(R.string.dialog_action_cancel)
+                        .setPositiveButton(R.string.dialog_action_app_settings,
+                                new DialogInterface.OnClickListener() {
+                                    @Override
+                                    public void onClick(DialogInterface dialog, int which) {
+                                        //Making the Intent to grant the permission
+                                        Intent intent =
+                                                new Intent(Settings
+                                                        .ACTION_APPLICATION_DETAILS_SETTINGS);
+                                        Uri uri = Uri.fromParts(activity.getResources().getString(
+                                                R.string.package_name), activity.getPackageName()
+                                                , null);
+                                        intent.setData(uri);
+                                        PackageManager pm = activity.getPackageManager();
+                                        if (intent.resolveActivity(pm) != null) {
+                                            activity.startActivityForResult(intent,
+                                                    ConstantKeys.REQUEST_PERMISSION_SETTING);
+                                        } else {
+                                            Toast.makeText(activity, activity.getString(
+                                                            R.string.msg_setting_activity_not_found)
+                                                    , Toast.LENGTH_LONG).show();
+                                        }
+                                    }
+                                })
+                        .createMaterialDialog()
+                        .show();
+            }
+        }
+    }
+}
\ No newline at end of file
diff --git a/app/src/main/java/com/mifos/apache/fineract/utils/ConstantKeys.java b/app/src/main/java/com/mifos/apache/fineract/utils/ConstantKeys.java
index feb1939..0503944 100644
--- a/app/src/main/java/com/mifos/apache/fineract/utils/ConstantKeys.java
+++ b/app/src/main/java/com/mifos/apache/fineract/utils/ConstantKeys.java
@@ -12,4 +12,10 @@
     public static final String ACCOUNT_IDENTIFIER = "account_identifier";
     public static final String LOAN_CREDITWORTHINESSSNAPSHOTS = "loan_creditWorthinessSnapshots";
     public static final String IDENTIFICATION_CARD = "identification_card";
+
+    public static final int REQUEST_PERMISSION_SETTING = 254;
+
+    public static final int PERMISSIONS_REQUEST_CAMERA = 1;
+    public static final String PERMISSIONS_CAMERA_STATUS = "camera_status";
+
 }
diff --git a/app/src/main/java/com/mifos/apache/fineract/utils/MaterialDialog.java b/app/src/main/java/com/mifos/apache/fineract/utils/MaterialDialog.java
new file mode 100644
index 0000000..fb160e9
--- /dev/null
+++ b/app/src/main/java/com/mifos/apache/fineract/utils/MaterialDialog.java
@@ -0,0 +1,166 @@
+package com.mifos.apache.fineract.utils;
+
+import android.content.Context;
+import android.content.DialogInterface;
+import android.support.annotation.StringRes;
+import android.support.v7.app.AlertDialog;
+
+import com.mifos.apache.fineract.R;
+
+/**
+ * This Class is the Material Dialog Builder Class
+ * Created by Rajan Maurya on 03/08/16.
+ */
+public final class MaterialDialog  {
+
+    public static class Builder {
+
+        private AlertDialog.Builder materialDialogBuilder;
+
+        //This is the Default Builder Initialization with Material Style
+        public Builder init(Context context) {
+            materialDialogBuilder =
+                    new AlertDialog.Builder(context, R.style.MaterialAlertDialogStyle);
+            return this;
+        }
+
+        //This method set the custom Material Style
+        public Builder init(Context context, int theme) {
+            materialDialogBuilder = new AlertDialog.Builder(context, theme);
+            return this;
+        }
+
+        //This method set the String Title
+        public Builder setTitle(String title) {
+            materialDialogBuilder.setTitle(title);
+            return this;
+        }
+
+        //This Method set the String Resources to Title
+        public Builder setTitle(@StringRes int title) {
+            materialDialogBuilder.setTitle(title);
+            return this;
+        }
+
+        //This Method set the String Message
+        public Builder setMessage(String message) {
+            materialDialogBuilder.setMessage(message);
+            return this;
+        }
+
+        //This Method set the String Resources message
+        public Builder setMessage(@StringRes int message) {
+            materialDialogBuilder.setMessage(message);
+            return this;
+        }
+
+        //This Method set String Test to the Positive Button and set the Onclick null
+        public Builder setPositiveButton(String positiveText) {
+            materialDialogBuilder.setPositiveButton(positiveText, null);
+            return this;
+        }
+
+        //This Method Set the String Resources Text To Positive Button
+        public Builder setPositiveButton(@StringRes int  positiveText) {
+            materialDialogBuilder.setPositiveButton(positiveText, null);
+            return this;
+        }
+
+        //This Method set the String Text to Positive Button and set the OnClick Event to it
+        public Builder setPositiveButton(String positiveText,
+                DialogInterface.OnClickListener listener) {
+            materialDialogBuilder.setPositiveButton(positiveText, listener);
+            return this;
+        }
+
+        //This method set the String Resources text To Positive button and set the Onclick Event
+        public Builder setPositiveButton(@StringRes int positiveText,
+                DialogInterface.OnClickListener listener) {
+            materialDialogBuilder.setPositiveButton(positiveText, listener);
+            return this;
+        }
+
+        //This Method the String Text to Negative Button and Set the onclick event to null
+        public Builder setNegativeButton(String negativeText) {
+            materialDialogBuilder.setNegativeButton(negativeText, null);
+            return this;
+        }
+
+        //This Method set the String Resources Text to Negative button
+        // and set the onclick event to null
+        public Builder setNegativeButton(@StringRes int negativeText) {
+            materialDialogBuilder.setNegativeButton(negativeText, null);
+            return this;
+        }
+
+        //This Method set String Text to Negative Button and
+        //Set the Onclick event
+        public Builder setNegativeButton(String negativeText,
+                DialogInterface.OnClickListener listener) {
+            materialDialogBuilder.setNegativeButton(negativeText, listener);
+            return this;
+        }
+
+        //This method set String Resources Text to Negative Button and set Onclick Event
+        public Builder setNegativeButton(@StringRes int negativeText,
+                DialogInterface.OnClickListener listener) {
+            materialDialogBuilder.setNegativeButton(negativeText, listener);
+            return this;
+        }
+
+        //This Method the String Text to Neutral Button and Set the onclick event to null
+        public Builder setNeutralButton(String neutralText) {
+            materialDialogBuilder.setNeutralButton(neutralText, null);
+            return this;
+        }
+
+        //This Method set the String Resources Text to Neutral button
+        // and set the onclick event to null
+        public Builder setNeutralButton(@StringRes int neutralText) {
+            materialDialogBuilder.setNeutralButton(neutralText, null);
+            return this;
+        }
+
+        //This Method set String Text to Neutral Button and
+        //Set the Onclick event
+        public Builder setNeutralButton(String neutralText,
+                DialogInterface.OnClickListener listener) {
+            materialDialogBuilder.setNeutralButton(neutralText, listener);
+            return this;
+        }
+
+        //This method set String Resources Text to Neutral Button and set Onclick Event
+        public Builder setNeutralButton(@StringRes int neutralText,
+                DialogInterface.OnClickListener listener) {
+            materialDialogBuilder.setNeutralButton(neutralText, listener);
+            return this;
+        }
+
+        public Builder setCancelable(Boolean cancelable) {
+            materialDialogBuilder.setCancelable(cancelable);
+            return this;
+        }
+
+        public Builder setItems(int items, DialogInterface.OnClickListener listener) {
+            materialDialogBuilder.setItems(items, listener);
+            return this;
+        }
+
+        public Builder setItems(CharSequence[] items, DialogInterface.OnClickListener listener) {
+            materialDialogBuilder.setItems(items, listener);
+            return this;
+        }
+
+        //This Method Create the Final Material Dialog
+        public Builder createMaterialDialog() {
+            materialDialogBuilder.create();
+            return this;
+        }
+
+        //This Method Show the Dialog
+        public Builder show() {
+            materialDialogBuilder.show();
+            return this;
+        }
+    }
+}
diff --git a/app/src/main/java/com/mifos/apache/fineract/utils/ValidateIdentifierUtil.java b/app/src/main/java/com/mifos/apache/fineract/utils/ValidateIdentifierUtil.java
new file mode 100644
index 0000000..11e95f8
--- /dev/null
+++ b/app/src/main/java/com/mifos/apache/fineract/utils/ValidateIdentifierUtil.java
@@ -0,0 +1,65 @@
+package com.mifos.apache.fineract.utils;
+
+import android.content.Context;
+import android.support.design.widget.TextInputLayout;
+import android.text.TextUtils;
+
+import com.mifos.apache.fineract.R;
+
+import java.io.UnsupportedEncodingException;
+import java.net.URLEncoder;
+
+/**
+ * @author Rajan Maurya
+ *         On 02/08/17.
+ */
+public class ValidateIdentifierUtil {
+
+    public static boolean isValid(Context context, String string, TextInputLayout textInputLayout) {
+        if (TextUtils.isEmpty(string)) {
+            showTextInputLayoutError(textInputLayout, context.getString(R.string.required));
+            return false;
+        }
+        return validate(context, string, textInputLayout);
+    }
+
+    private static boolean validate(Context context, String string,
+            TextInputLayout textInputLayout) {
+        if (string.length() < 3) {
+            showTextInputLayoutError(textInputLayout,
+                    context.getString(R.string.must_be_at_least_three_characters, 3));
+            return false;
+        }
+
+        if (string.length() > 32) {
+            showTextInputLayoutError(textInputLayout,
+                    context.getString(R.string.only_thirty_two_character_allowed));
+            return false;
+        }
+
+        try {
+            if (encode(string).equals(string)) {
+                showTextInputLayoutError(textInputLayout, null);
+                return true;
+            } else {
+                showTextInputLayoutError(textInputLayout, context.getString(
+                        R.string.only_alphabetic_decimal_digits_characters_allowed));
+                return false; //If we can't encode with UTF-8, then there are no valid names.
+            }
+        } catch (UnsupportedEncodingException e) {
+            showTextInputLayoutError(textInputLayout,
+                    context.getString(R.string.only_alphabetic_decimal_digits_characters_allowed));
+            return false; //If we can't encode with UTF-8, then there are no valid names.
+        }
+    }
+
+    private static String encode(String identifier) throws UnsupportedEncodingException {
+        return URLEncoder.encode(identifier, "UTF-8");
+    }
+
+    public static void showTextInputLayoutError(TextInputLayout textInputLayout,
+            String errorMessage) {
+        textInputLayout.setErrorEnabled(true);
+        textInputLayout.setError(errorMessage);
+    }
+}
diff --git a/app/src/main/java/com/mifos/apache/fineract/utils/ValidationUtil.java b/app/src/main/java/com/mifos/apache/fineract/utils/ValidationUtil.java
index 97fbdaa..eba04ad 100644
--- a/app/src/main/java/com/mifos/apache/fineract/utils/ValidationUtil.java
+++ b/app/src/main/java/com/mifos/apache/fineract/utils/ValidationUtil.java
@@ -1,5 +1,11 @@
 package com.mifos.apache.fineract.utils;
 
+import android.content.Context;
+import android.support.design.widget.TextInputLayout;
+import android.text.TextUtils;
+
+import com.mifos.apache.fineract.R;
+
 import java.io.UnsupportedEncodingException;
 import java.net.URLEncoder;
 
@@ -33,4 +39,14 @@
         }
         return true;
     }
+
+    public static boolean isEmpty(Context context, String string, TextInputLayout inputLayout) {
+        if (TextUtils.isEmpty(string)) {
+            ValidateIdentifierUtil.showTextInputLayoutError(inputLayout,
+                    context.getString(R.string.required));
+            return false;
+        }
+        ValidateIdentifierUtil.showTextInputLayoutError(inputLayout, null);
+        return true;
+    }
 }
diff --git a/app/src/main/res/drawable/ic_cancel_black_24dp.xml b/app/src/main/res/drawable/ic_cancel_black_24dp.xml
new file mode 100644
index 0000000..7d2b57e
--- /dev/null
+++ b/app/src/main/res/drawable/ic_cancel_black_24dp.xml
@@ -0,0 +1,9 @@
+<vector xmlns:android="http://schemas.android.com/apk/res/android"
+        android:width="24dp"
+        android:height="24dp"
+        android:viewportWidth="24.0"
+        android:viewportHeight="24.0">
+    <path
+        android:fillColor="#FF000000"
+        android:pathData="M12,2C6.47,2 2,6.47 2,12s4.47,10 10,10 10,-4.47 10,-10S17.53,2 12,2zM17,15.59L15.59,17 12,13.41 8.41,17 7,15.59 10.59,12 7,8.41 8.41,7 12,10.59 15.59,7 17,8.41 13.41,12 17,15.59z"/>
+</vector>
diff --git a/app/src/main/res/layout/bottom_sheet_upload_identification_scan_card.xml b/app/src/main/res/layout/bottom_sheet_upload_identification_scan_card.xml
new file mode 100644
index 0000000..0efb1bf
--- /dev/null
+++ b/app/src/main/res/layout/bottom_sheet_upload_identification_scan_card.xml
@@ -0,0 +1,160 @@
+<?xml version="1.0" encoding="utf-8"?>
+<android.support.design.widget.CoordinatorLayout
+    xmlns:android="http://schemas.android.com/apk/res/android"
+    android:layout_height="match_parent"
+    android:layout_width="match_parent">
+
+    <android.support.v4.widget.NestedScrollView
+        xmlns:android="http://schemas.android.com/apk/res/android"
+        xmlns:app="http://schemas.android.com/apk/res-auto"
+        android:layout_height="match_parent"
+        android:layout_width="match_parent"
+        android:visibility="visible"
+        app:layout_behavior="@string/appbar_scrolling_view_behavior">
+
+        <LinearLayout
+            android:layout_height="wrap_content"
+            android:layout_width="match_parent"
+            android:orientation="vertical"
+            android:paddingBottom="@dimen/layout_padding_24dp">
+
+            <LinearLayout
+                android:layout_height="wrap_content"
+                android:layout_width="match_parent"
+                android:orientation="vertical">
+
+                <TextView
+                    style="@style/Base.TextAppearance.AppCompat.Large"
+                    android:id="@+id/tv_header"
+                    android:layout_height="match_parent"
+                    android:layout_width="match_parent"
+                    android:paddingBottom="@dimen/layout_padding_30dp"
+                    android:paddingLeft="@dimen/layout_padding_24dp"
+                    android:paddingRight="@dimen/layout_padding_24dp"
+                    android:paddingStart="@dimen/layout_padding_24dp"
+                    android:paddingTop="@dimen/layout_padding_24dp"
+                    android:text="@string/upload_new_identification_card_scan"
+                    android:textColor="@color/colorPrimaryDark"
+                    android:textStyle="bold"/>
+
+                <android.support.design.widget.TextInputLayout
+                    android:id="@+id/til_identifier"
+                    android:layout_height="match_parent"
+                    android:layout_width="match_parent"
+                    android:paddingLeft="@dimen/layout_padding_24dp"
+                    android:paddingRight="@dimen/layout_padding_24dp">
+
+                    <EditText
+                        android:hint="@string/identifier"
+                        android:id="@+id/et_identifier"
+                        android:inputType="text"
+                        android:layout_height="match_parent"
+                        android:layout_width="match_parent"/>
+                </android.support.design.widget.TextInputLayout>
+
+                <android.support.design.widget.TextInputLayout
+                    android:id="@+id/til_description"
+                    android:layout_height="match_parent"
+                    android:layout_width="match_parent"
+                    android:paddingLeft="@dimen/layout_padding_24dp"
+                    android:paddingRight="@dimen/layout_padding_24dp"
+                    android:paddingTop="@dimen/layout_padding_16dp">
+
+                    <EditText
+                        android:hint="@string/description"
+                        android:id="@+id/et_description"
+                        android:inputType="textMultiLine"
+                        android:layout_height="match_parent"
+                        android:layout_width="match_parent"
+                        android:scrollHorizontally="false"
+                        android:scrollbars="vertical"/>
+                </android.support.design.widget.TextInputLayout>
+
+
+                <LinearLayout
+                    android:gravity="center"
+                    android:layout_height="match_parent"
+                    android:layout_width="match_parent"
+                    android:orientation="horizontal"
+                    android:paddingLeft="@dimen/layout_padding_24dp"
+                    android:paddingRight="@dimen/layout_padding_24dp"
+                    android:paddingTop="@dimen/layout_padding_16dp"
+                    android:weightSum="1">
+
+                    <android.support.design.widget.TextInputLayout
+                        android:id="@+id/til_selected_file"
+                        android:gravity="center"
+                        android:layout_height="wrap_content"
+                        android:layout_weight=".7"
+                        android:layout_width="wrap_content"
+                        android:paddingEnd="@dimen/layout_padding_8dp"
+                        android:paddingLeft="0dp"
+                        android:paddingRight="@dimen/layout_padding_8dp"
+                        android:paddingStart="0dp">
+                        <EditText
+                            android:hint="@string/selected_file"
+                            android:id="@+id/et_selected_file"
+                            android:inputType="text"
+                            android:lines="1"
+                            android:layout_height="match_parent"
+                            android:layout_width="match_parent"
+                            android:scrollHorizontally="false"
+                            android:enabled="false"
+                            android:scrollbars="vertical"/>
+                    </android.support.design.widget.TextInputLayout>
+
+                    <Button
+                        android:drawableLeft="@drawable/ic_folder_black_24dp"
+                        android:drawableStart="@drawable/ic_folder_black_24dp"
+                        android:id="@+id/btn_browse_document"
+                        android:layout_height="wrap_content"
+                        android:layout_weight=".3"
+                        android:layout_width="wrap_content"
+                        android:text="@string/browse"
+                        android:textAllCaps="true"/>
+
+                </LinearLayout>
+
+            </LinearLayout>
+
+            <LinearLayout
+                android:layout_gravity="end"
+                android:layout_height="match_parent"
+                android:layout_width="match_parent"
+                android:orientation="horizontal"
+                android:paddingEnd="@dimen/layout_padding_24dp"
+                android:paddingLeft="@dimen/layout_padding_64dp"
+                android:paddingRight="@dimen/layout_padding_24dp"
+                android:paddingStart="@dimen/layout_padding_64dp"
+                android:paddingTop="@dimen/layout_padding_24dp"
+                android:weightSum="1">
+
+                <Button
+                    android:id="@+id/btn_cancel"
+                    android:layout_height="wrap_content"
+                    android:layout_marginEnd="@dimen/layout_padding_16dp"
+                    android:layout_marginRight="@dimen/layout_padding_16dp"
+                    android:layout_weight=".5"
+                    android:layout_width="wrap_content"
+                    android:text="@string/cancel"
+                    android:textAllCaps="false"/>
+
+                <Button
+                    android:id="@+id/btn_upload_identification_card_scan"
+                    android:layout_height="wrap_content"
+                    android:layout_weight=".5"
+                    android:layout_width="wrap_content"
+                    android:text="@string/upload"
+                    android:textAllCaps="false"
+                />
+
+            </LinearLayout>
+
+        </LinearLayout>
+
+    </android.support.v4.widget.NestedScrollView>
+
+</android.support.design.widget.CoordinatorLayout>
+
+
+
diff --git a/app/src/main/res/layout/fragment_identification_details.xml b/app/src/main/res/layout/fragment_identification_details.xml
index 1244acf..b9ea89e 100644
--- a/app/src/main/res/layout/fragment_identification_details.xml
+++ b/app/src/main/res/layout/fragment_identification_details.xml
@@ -235,7 +235,7 @@
 
     <android.support.design.widget.FloatingActionButton
         android:clickable="true"
-        android:id="@+id/fab_edit_customer_loan"
+        android:id="@+id/fab_upload_identification_scan_card"
         android:layout_gravity="bottom|end"
         android:layout_height="wrap_content"
         android:layout_margin="@dimen/layout_padding_16dp"
diff --git a/app/src/main/res/values/dimens.xml b/app/src/main/res/values/dimens.xml
index ce1be26..204e34e 100644
--- a/app/src/main/res/values/dimens.xml
+++ b/app/src/main/res/values/dimens.xml
@@ -13,6 +13,7 @@
     <dimen name="layout_padding_16dp">16dp</dimen>
     <dimen name="layout_padding_24dp">24dp</dimen>
     <dimen name="layout_padding_30dp">30dp</dimen>
+    <dimen name="layout_padding_50dp">50dp</dimen>
     <dimen name="layout_padding_64dp">64dp</dimen>
     <dimen name="layout_padding_75dp">75dp</dimen>
 
diff --git a/app/src/main/res/values/strings.xml b/app/src/main/res/values/strings.xml
index 563c1f7..e3c3e5b 100644
--- a/app/src/main/res/values/strings.xml
+++ b/app/src/main/res/values/strings.xml
@@ -82,7 +82,7 @@
     <string name="edit_income">Edit Income</string>
     <string name="debt_income">Debt Income</string>
     <string name="name">Name</string>
-    <string name="browse">Browse</string>
+    <string name="browse">Browse…</string>
     <string name="fetching_customer_please_wait">Fetching customer please wait…</string>
     <string name="creating_loan_please_wait">Creating loan please wait…</string>
     <string name="creating_customer_please_wait">Creating customer please wait…</string>
@@ -114,6 +114,13 @@
     <string name="expiration_date">Expiration date</string>
     <string name="scans_uploaded">Scans uploaded</string>
     <string name="loading_scans_please_wait">Loading scans please wait…</string>
+    <string name="identifier">Identifier</string>
+    <string name="selected_file">Selected file</string>
+    <string name="upload_new_identification_card_scan">Upload new Identification card scan</string>
+    <string name="upload">Upload</string>
+    <string name="package_name" translatable="false">package</string>
+    <string name="scan_file">scanFile.png</string>
+    <string name="uploading_identification_scan_card">Uploading identification scan card…</string>
 
 
     <!--Edit Text hint required-->
@@ -174,8 +181,28 @@
     <string name="error_fetching_identification_list">Error while fetching identification cards</string>
     <string name="error_creating_identification_card">Error while creating identification card</string>
     <string name="error_fetching_scans">Error while fetching scan cards</string>
+    <string name="error_uploading_identification_scan_card">Error while uploading identification scan card</string>
 
 
+    <!--Material Dialog-->
+    <string name="dialog_action_ok">OK</string>
+    <string name="dialog_action_cancel">Cancel</string>
+    <string name="dialog_action_back">Back</string>
+    <string name="dialog_permission_denied">Permission Denied</string>
+    <string name="dialog_action_i_am_sure">I\'M Sure</string>
+    <string name="dialog_action_re_try">Retry</string>
+    <string name="dialog_action_app_settings">App Settings</string>
+    <string name="dialog_message_camera_permission_denied_prompt">Without camera permission you will
+        not be able to scan the document. Are you sure you want to deny this
+        permission?</string>
+    <string name="dialog_message_camera_permission_never_ask_again">You have denied permission to
+        use camera, without this permission you will not be able to scan the document.
+        Please enable it in settings</string>
+    <string name="msg_setting_activity_not_found">Something went wrong finding Settings activity.
+        \nGo to \'Settings\' and grant permission manually.
+    </string>
+    <string name="permission_denied_camera">Permission Denied to use Camera</string>
+
     <!--Customer Current status-->
     <string name="active">ACTIVE</string>
     <string name="pending">PENDING</string>
diff --git a/app/src/main/res/values/styles.xml b/app/src/main/res/values/styles.xml
index f8175c3..56b8f21 100644
--- a/app/src/main/res/values/styles.xml
+++ b/app/src/main/res/values/styles.xml
@@ -34,4 +34,10 @@
         <item name="android:padding">@dimen/layout_padding_7dp</item>
     </style>
 
+    <style name="MaterialAlertDialogStyle" parent="Theme.AppCompat.Light.Dialog.Alert">
+        <item name="colorAccent">@color/colorPrimary</item>
+        <item name="android:textColorPrimary">@color/black</item>
+        <item name="android:background">@color/white</item>
+    </style>
+
 </resources>
diff --git a/app/src/main/res/xml/filepaths.xml b/app/src/main/res/xml/filepaths.xml
new file mode 100644
index 0000000..a0bcef4
--- /dev/null
+++ b/app/src/main/res/xml/filepaths.xml
@@ -0,0 +1,4 @@
+<?xml version="1.0" encoding="utf-8"?>
+<paths xmlns:android="http://schemas.android.com/apk/res/android">
+    <cache-path name="shared_images" path="images/"/>
+</paths>