> For the complete documentation index, see [llms.txt](https://docs.facephi.com/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://docs.facephi.com/docs.facephi-en/sdks/sdk-mobile/android-sdk/componentes-modulos/subida-de-ficheros-y-gestion-de-qr.md).

# File upload and QR Code management - Capture

## Introduction <a href="#id-1-introduccion" id="id-1-introduccion"></a>

Document capture and QR Code reading and generation are performed with the ***CaptureComponent***.

This component will allow document upload by taking a photo with the device camera or from the gallery.

***

## Dependency <a href="#id-2-dependencia" id="id-2-dependencia"></a>

The specific dependency for the component is:

```
implementation "com.facephi.androidsdk:capture_component:$version"
```

***

## Available controllers <a href="#id-3-controladores-disponibles" id="id-3-controladores-disponibles"></a>

| **Controller**         | **Description**                 |
| ---------------------- | ------------------------------- |
| FileUploaderController | Controller for document capture |
| QrReaderController     | Controller for QR capture       |
| QrGeneratorController  | Controller for QR generation    |

***

## Simplified Launch <a href="#id-4-lanzamiento-simplificado" id="id-4-lanzamiento-simplificado"></a>

Once the SDK has been initialized and a new operation has been created, the component can be launched. Any of its controllers can be used to execute its functionality.

Launching document capture:

```kotlin
val response = SDKController.launch(
    FileUploaderController(FileUploaderConfigurationData(...))
)
when (response) {
    is SdkResult.Error -> Napier.d("ERROR - ${response.error.name}")
    is SdkResult.Success -> response.data
}
```

Launching QR capture:

```kotlin
val response = SDKController.launch(
    QrReaderController(QrCaptureConfigurationData(...))
)
when (response) {
    is SdkResult.Error -> Napier.d("ERROR - ${response.error.name}")
    is SdkResult.Success -> response.data
}
```

Launching QR generation:

```kotlin
val response = SDKController.launch(
    QrGeneratorController(QrGeneratorConfiguration(...))
)
when (response) {
    is SdkResult.Error -> Napier.d("ERROR - ${response.error.name}")
    is SdkResult.Success -> response.data
}
```

***

## Basic configuration <a href="#id-5-configuracion-basica" id="id-5-configuracion-basica"></a>

For the component capture and QR capture controllers, the configuration can be generated with default parameters. For QR generation, the text to be used will be needed:

```
QrGeneratorConfiguration(source = "QR text")
```

***

## Receiving the result <a href="#id-6-recepcion-del-resultado" id="id-6-recepcion-del-resultado"></a>

The launch will return the information in SdkResult format. It can distinguish between a successful and unsuccessful launch:

```kotlin
when (response) {
    is SdkResult.Error -> Napier.d("ERROR - ${response.error}")
    is SdkResult.Success -> response.data
}
```

### Receiving errors <a href="#id-61-recepcion-de-errores" id="id-61-recepcion-de-errores"></a>

The errors will be returned as a 'CaptureError' object.

List of errors:

* CAP\_ACTIVITY\_RESULT\_MSG\_ERROR: The result returned by the activity is incorrect or does not contain the necessary information to continue.
* CAP\_APPLICATION\_CONTEXT\_ERROR: The required application context is null or not valid, preventing the capture module from being initialized correctly.
* CAP\_CAMERA\_ERROR: An internal error has occurred related to the device camera (open, initialization, or capture failure).
* CAP\_CAMERA\_PERMISSION\_DENIED: The user has denied the permissions required to access the camera.
* CAP\_CANCEL\_BY\_USER: The user has manually canceled the capture process.
* CAP\_CANCEL\_LAUNCH: The process has been generally canceled by the SDK or by an external action.
* CAP\_COMPONENT\_LICENSE\_ERROR: The component license is not valid, has expired, or does not match the required configuration.
* CAP\_EMPTY\_LICENSE: The license string is empty or has not been provided.
* CAP\_FETCH\_DATA\_ERROR: An error occurred while obtaining or processing the data needed to execute the Flow. *(Includes additional information in the field `error`.)*
* CAP\_FLOW\_ERROR: An internal error has occurred during the execution of the capture Flow. *(Includes additional information in the field `error`.)*
* CAP\_INITIALIZATION\_ERROR: Error initializing the necessary SDK components. *(Includes detailed information in the field `error`.)*
* CAP\_FILE\_UPLOADER\_CAPTURE\_ERROR: Error during the process of uploading the files generated in the capture.
* CAP\_IMAGE\_TOO\_LARGE: The image selected from the gallery exceeds the maximum size configured in `maxGalleryImageSizeKb`.
* CAP\_MANAGER\_NOT\_INITIALIZED: The managers required to execute the process have not been initialized correctly.
* CAP\_NO\_DATA\_ERROR: The required input data are null, missing, or insufficient to continue the process.
* CAP\_OPERATION\_NOT\_CREATED: It was not possible to create or retrieve an active operation needed to continue. *(Includes detailed information in the field `error`.)*
* CAP\_QR\_CAPTURE\_ERROR: Error during QR Code capture or reading.
* CAP\_QR\_GENERATION\_ERROR: Error generating the requested QR Code.
* CAP\_TIMEOUT: The maximum allowed time has been reached in one of the stages of the process.
* CAP\_FLOW\_VIDEO\_RECORDING\_ERROR: Error during video recording within the established Flow.
* CAP\_FLOW\_TRACKING\_ERROR: Error while performing the Tracking required to complete the capture Flow.

### Receipt of the correct result - *data* <a href="#id-62-recepcion-del-resultado-correcto-data" id="id-62-recepcion-del-resultado-correcto-data"></a>

#### **Receipt of the document capture result**

In the SdkResult.Success part - *data*, we will have the class *FileUploaderResult*.

The fields returned in the result are as follows:

***capturedDocumentList***

List of captured files. They can be images or PDFs. The fields returned for each are:

* mimeType
* timestampMillis
* content: Document content. It will be different if it is an image or a PDF document. To differentiate it:

```kotlin
capturedDocumentList.forEach { documentData ->
                            when (val content = documentData.content) {
                                is FileContent.UploaderImage -> {
                                    // Uploader: New image found
                                    // content.image
                                }

                                is FileContent.UploaderDocument -> {
                                    // Uploader: New document found
                                    // content.bytes
                                }
                            }
                        }
```

#### **Receipt of the QR capture result**

In the SdkResult.Success part - *data*, we will have the class *QrResult*.

The fields returned in the result are as follows:

***qrText***

Text obtained from the QR Code

#### **Receipt of the QR generation result**

In the SdkResult.Success part - *data*, we will have an SdkImage with the created QR code.

***

## Advanced information <a href="#id-7-informacion-avanzada" id="id-7-informacion-avanzada"></a>

This section expands the component information.

### Advanced component configuration <a href="#id-71-configuracion-avanzada-del-componente" id="id-71-configuracion-avanzada-del-componente"></a>

#### **Document capture configuration**

To launch the current component, an object must be created *FileUploaderConfigurationData* which will be the configuration of the component controller.

Below are all the fields that are part of this class.

* `vibrationEnabled`: Indicates vibration activation when the Widget finishes successfully.
* `extractionTimeout`: Sets the maximum time the capture can take.
* `showDiagnostic`: Show diagnostic screens at the end of the process.
* `showPreviousTip`: Shows a screen before launching the capture with information about the process to be performed and a launch button.
* `maxScannedDocs`: Maximum number of documents that can be captured
* `allowGallery`: Access to the gallery is enabled for obtaining images or PDFs
* `onlyGalleryMode`: If active, the Flow opens directly in gallery mode and does not show camera capture. By default `true`.
* `maxGalleryImageSizeKb`: Maximum allowed size for images selected from the gallery, in KB. By default `2048`; if exceeded, it returns `CAP_IMAGE_TOO_LARGE`.

#### **QR capture configuration**

To launch the current component, an object must be created *QrCaptureConfigurationData* which will be the configuration of the component controller.

Below are all the fields that are part of this class.

* `vibrationEnabled`: Indicates vibration activation when the Widget finishes successfully.
* `extractionTimeout`: Sets the maximum time the capture can take.
* `showDiagnostic`: Show diagnostic screens at the end of the process.
* `showPreviousTip`: Shows a screen before launching the capture with information about the process to be performed and a launch button.
* `showTutorial`: Indicates whether the component activates the tutorial screen. This view intuitively explains how the capture is performed.
* `cameraShape`: Allows choosing between a square and a round mask.

***

## Component customization <a href="#id-8-personalizacion-del-componente" id="id-8-personalizacion-del-componente"></a>

Apart from the changes that can be made at the SDK level (which are explained in the document of ([SDK Customization](/docs.facephi-en/sdks/sdk-mobile/android-sdk/personalizacion.md)), this particular component allows modification of its interface.

### Texts <a href="#id-81-textos" id="id-81-textos"></a>

If you want to modify the texts of the SDK, you should include the following XML file in the client's application, and modify the value of each *String* with the desired one.

```
<resources>
    <!-- Previous Tip -->
    <string name="capture_component_qr_tip_title">Scan the QR Code</string>
    <string name="capture_component_qr_tip_message">&lt;b&gt; Focus &lt;/b&gt; the QR Code &lt;b&gt; inside the frame &lt;/b&gt;</string>
    <string name="capture_component_qr_tip_button">Start</string>
    <string name="capture_component_qr_tip_anim_desc">Animation of a mobile phone taking a photo of a QR Code. A frame appears on the phone screen. When the QR Code fits inside the frame, the application takes a photo.</string>
    <string name="capture_component_qr_tutorial_1_anim_desc">A QR Code is shown on a white background. The edges of the QR Code are not clearly visible. Through an animation, the background changes color.</string>
    <string name="capture_component_qr_tutorial_2_anim_desc">A mobile phone takes a photo of a QR Code. The QR Code appears horizontally, and the phone is in vertical position. A frame appears on the phone screen. When the QR Code fits inside the frame, the application takes a photo.</string>
    <!-- Tutorial -->
    <string name="capture_component_qr_tutorial_1">Make sure the QR Code has &lt;b&gt; enough light &lt;/b&gt; and &lt;b&gt; there are no reflections &lt;/b&gt; or glare on the code.</string>
    <string name="capture_component_qr_tutorial_2">Fit the edges of the QR Code inside the frame.</string>
    <!-- Process -->
    <string name="capture_component_qr_camera_message">Keep the QR in the center</string>
    <string name="capture_component_button_message">Capture</string>
    <!-- Diagnostic -->
    <string name="capture_component_timeout_title">Time exceeded</string>
    <string name="capture_component_timeout_desc">We apologize. The capture could not be completed</string>
    <string name="capture_component_internal_error_title">There was a technical problem</string>
    <string name="capture_component_internal_error_desc">We apologize. The capture could not be completed</string>

    <!-- WIDGET -->
    <!-- Previous Tip -->
    <string name="capture_widget_tip_title">Scan documents</string>
    <string name="capture_widget_tip_message">Take a photo of the document, or upload an image.&lt;br&gt;&lt;br&gt; You can scan several documents before finishing.</string>
    <string name="capture_widget_tip_message_alt">Take a photo of the document, or upload an image. You can scan several documents before finishing.</string>
    <string name="capture_widget_tip_button">Start</string>
    <string name="capture_widget_tip_button_alt">Start document capture</string>
    <string name="capture_widget_tip_close_button_alt">Back</string>
    <string name="capture_widget_tip_info_button_alt">See tips</string>
    <string name="capture_widget_tip_anim_desc">Animation of a mobile phone taking a photo of a document. A frame appears on the phone screen. When the document fits inside the frame, the application takes a photo.</string>
    <!-- Camera -->
    <string name="capture_widget_document_camera_button_gallery">Gallery</string>
    <string name="capture_widget_document_camera_button_capture">Capture</string>
    <string name="capture_widget_document_camera_button_cancel">Cancel capture</string>
    <string name="capture_widget_document_camera_button_finish">Finish</string>
    <!-- Gallery -->
    <string name="capture_widget_gallery_images">Images</string>
    <string name="capture_widget_gallery_pdf">Select PDF</string>
    <string name="capture_widget_gallery_cancel">Cancel</string>
    <!-- Confirmation -->
    <string name="capture_widget_image_captured">Image captured</string>
    <string name="capture_widget_confirmation_message">Can all the data be read clearly and sharply?</string>
    <string name="capture_widget_confirmation_retry">NO, I WANT TO RETAKE THE PHOTOS</string>
    <string name="capture_widget_confirmation_continue">Yes, finish</string>
    <string name="capture_widget_confirmation_delete">Delete photo</string>
    <string name="capture_widget_confirmation_image_unavailable">Preview not available</string>
    <string name="capture_widget_confirmation_no_images">No captures available</string>
    <string name="capture_widget_confirmation_delete_dialog_title">Do you want to delete this document?</string>
    <string name="capture_widget_confirmation_delete_dialog_message">By deleting this document, you will not be able to recover it. You will need to take a new photo.</string>
    <string name="capture_widget_confirmation_delete_dialog_cancel">CANCEL</string>
    <string name="capture_widget_confirmation_delete_dialog_confirm">DELETE DOCUMENT</string>
    <!-- Diagnostic -->
    <string name="capture_widget_timeout_title">Time exceeded</string>
    <string name="capture_widget_timeout_desc">We apologize. The capture could not be completed</string>
    <string name="capture_widget_internal_error_title">There was a technical problem</string>
    <string name="capture_widget_internal_error_desc">We apologize. The capture could not be completed</string>

</resources>

```

### Animations <a href="#id-82-animaciones" id="id-82-animaciones"></a>

If you want to modify the SDK animations (lottie), you should include the animations with the same name in the application's res/raw/ folder.

```
qr_anim_tip_1.json
qr_anim_tip_2.json
capture_anim_tip.json
```
