Form submission with the Android picker

Learn how to use Filestack in form uploads on Android

Select and Upload Files

The Filestack SDK can simplify the process of uploading and serving files within Android apps. This tutorial will walk you through integrating Filestack into an account creation form, using the SDK to upload and serve profile images. The details of the base app are omitted here, but the full source code is also available. Refer to the SDK repo for full installation and configuration instructions.

implementation 'com.filestack:filestack-android:X.Y.Z'

This is the account creation form we’ll be working with in our example.

When the user taps the “Select” button, we want to display the picker. To do so, let’s define the following method that’s called for the button’s onClick event. The method does some configuration then starts the FsActivity class. In this example we’re using an account without security enabled so we’re only passing in an API key and OAuth URL. The URL is used when users authorize access to cloud accounts. We’re also restricting file selections to only images.

// Handles user clicking select button, launches the picker UI
private void selectImage() {
    // For simplicity we're loading credentials from a string res, don't do this in production
    String apiKey = getString(R.string.filestack_api_key);
    Config config = new Config(apiKey, "https://form.samples.android.filestack.com");
    Context context = getContext();
    Intent pickerIntent = new Intent(context, FsActivity.class);
    pickerIntent.putExtra(FsConstants.EXTRA_CONFIG, config);
    // Restrict file selections to just images
    String[] mimeTypes = {"image/*"};
    pickerIntent.putExtra(FsConstants.EXTRA_MIME_TYPES, mimeTypes);
    context.startActivity(pickerIntent);
}

This is now what the user sees after tapping “Select”. After the user selects a file to upload, the SDK automatically begins uploading the file asynchronously in a background service.

Receive Upload Results

The SDK asynchronously uploads user selections and returns the resulting metadata using Android system broadcasts. This is similar to the pub-sub design pattern. You need to register a broadcast receiver to subscribe to upload events from the SDK. You can define and register a simple broadcast receiver inside your MainActivity. Notice we both register and unregister the receiver to prevent memory leaks.

public class MainActivity extends AppCompatActivity {

    private UploadReceiver uploadReceiver;
    private FileLink fileLink;

    // Receives upload broadcasts from SDK service
    public class UploadReceiver extends BroadcastReceiver {

        @Override
        public void onReceive(Context context, Intent intent) {
            fileLink = (FileLink) intent.getSerializableExtra(FsConstants.EXTRA_FILE_LINK);
        }
    }

    public FileLink getFileLink() {
        return fileLink;
    }

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        // Register the receiver for upload broadcasts
        IntentFilter filter = new IntentFilter(FsConstants.BROADCAST_UPLOAD);
        uploadReceiver = new UploadReceiver();
        LocalBroadcastManager.getInstance(this).registerReceiver(uploadReceiver, filter);
    }

    @Override
    protected void onDestroy() {
        super.onDestroy();
        // Unregister the receiver to avoid leaking it outside tne activity context
        LocalBroadcastManager.getInstance(this).unregisterReceiver(uploadReceiver);
    }

}

Display the Image

Once the FileLink is received by the broadcast receiver, we can generate a URL and load it into the ImageView. In this example we’re generating a transformation URL that returns an image resized to fit the pixel width and height of our ImageView. This reduces bandwidth usage and download delays. The following code snippets retrieves the FileLink in a Fragment’s onResume method.

@Override
public void onResume() {
    super.onResume();

    // If MainActivity contains a FileLink when the fragment resumes, load the image from it
    // So in this case we check the activity for data, rather than have it push to the fragment
    FileLink fileLink = ((MainActivity) getActivity()).getFileLink();
    if (fileLink != null) {
        int dimen = getResources().getDimensionPixelSize(R.dimen.form_image);
        String url = getAdaptiveUrl(fileLink, dimen);
        // Picasso is a useful utility to load the URL into an ImageView
        Picasso.with(getContext()).load(url).into(imageView);
    }
}