Description
The Issue
Consider the following common use case:
- A user is prompted to select an image for uploading to a server
- The user selects a photo and then is presented with a loading indicator while the photo is uploaded
- After the upload is finished, the loading indicator is hidden
I'm currently implementing this using @nstudio/nativescript-loading-indicator
(v4.3.4) and @nativescript/imagepicker (v3.0.1):
// Get the image
const imagePicker = create({
mode: 'single',
mediaType: ImagePickerMediaType.Image,
prompt: 'Select a photo',
});
await imagePicker.authorize();
const selection = await imagePicker.present();
const selectedImages = selection.map((selectedImage) => selectedImage.asset);
// Upload the image
const loadingIndicator = new LoadingIndicator();
loadingIndicator.show({
message: 'Uploading photo...',
});
await uploadPhoto(selectedImages[0]);
loadingIndicator.hide();
You would expect the loading indicator to display right after the image is selected, but it never does. From what I can tell, this is because the loading indictor is displaying right away, but it displays in the context of the image picker modal which is in the process of closing. Thus, you never see it back in the view that presented the image picker.
Workaround
By using a setTimeout
to wait for the modal to fully close, the loading indicator can display correctly:
...
const selection = await imagePicker.present();
const selectedImages = selection.map((selectedImage) => selectedImage.asset);
setTimeout(async () => {
const loadingIndicator = new LoadingIndicator();
loadingIndicator.show({
message: 'Uploading photo...',
});
await uploadPhoto(selectedImages[0]);
loadingIndicator.hide();
}, 250); // Wait for the iOS image picker to close.
Reproduction
Minimal example on StackBlitz
Notice that there is no loading indicator. Uncomment lines 23 and 37 in main-view-model.ts
to re-enable the setTimeout
. Re-run and notice that the loading indicator now displays correctly.
Expected Behavior
ImagePicker.present
waits for the modal to be fully closed before resolving the Promise, thus avoiding this type of issue altogether.