feat(ios): improve share extension UX and fix image reload issues
Improve iOS share extension implementation to skip interstitial UI and fix issues with subsequent image shares not updating the view. iOS Share Extension Improvements: - Replace SLComposeServiceViewController with custom UIViewController to eliminate interstitial "Post" button UI - Use minimal URL (timesafari://) instead of deep link for app launch - Implement app lifecycle detection via Capacitor appStateChange listener instead of relying solely on deep links Deep Link and Navigation Fixes: - Remove "shared-photo" from deep link schemas (no longer needed) - Add empty path URL handling for share extension launches - Implement processing lock to prevent duplicate image processing - Add retry mechanism (300ms delay) to handle race conditions with AppDelegate writing temp files - Use router.replace() when already on /shared-photo route to force refresh - Clear old images from temp DB before storing new ones - Delete temp file immediately after reading to prevent stale data SharedPhotoView Component: - Add route watcher (@Watch) to reload image when fileName query parameter changes - Extract image loading logic into reusable loadSharedImage() method - Improve error handling to clear image state on failures This fixes the issue where sharing a second image while already on SharedPhotoView would display the previous image instead of the new one.
This commit is contained in:
@@ -120,7 +120,7 @@
|
||||
|
||||
<script lang="ts">
|
||||
import axios from "axios";
|
||||
import { Component, Vue } from "vue-facing-decorator";
|
||||
import { Component, Vue, Watch } from "vue-facing-decorator";
|
||||
import {
|
||||
RouteLocationNormalizedLoaded,
|
||||
RouteLocationRaw,
|
||||
@@ -191,7 +191,29 @@ export default class SharedPhotoView extends Vue {
|
||||
*/
|
||||
async mounted() {
|
||||
this.notify = createNotifyHelpers(this.$notify);
|
||||
await this.loadSharedImage();
|
||||
}
|
||||
|
||||
/**
|
||||
* Watches for route query changes to reload image when navigating
|
||||
* to the same route with different query parameters (e.g., new fileName)
|
||||
*/
|
||||
@Watch("$route.query.fileName")
|
||||
async onFileNameChange(newFileName: string | undefined) {
|
||||
if (newFileName) {
|
||||
await this.loadSharedImage();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Loads the shared image from temporary storage
|
||||
*
|
||||
* Retrieves the shared image data from the temp database, converts it to a blob,
|
||||
* and updates component state. Cleans up temporary storage after successful loading.
|
||||
*
|
||||
* @async
|
||||
*/
|
||||
private async loadSharedImage() {
|
||||
try {
|
||||
// Get activeDid from active_identity table (single source of truth)
|
||||
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
||||
@@ -209,6 +231,9 @@ export default class SharedPhotoView extends Vue {
|
||||
this.imageFileName = this.$route.query["fileName"] as string;
|
||||
} else {
|
||||
logger.error("No appropriate image found in temp storage.", temp);
|
||||
// Clear image state if no temp data found
|
||||
this.imageBlob = undefined;
|
||||
this.imageFileName = undefined;
|
||||
}
|
||||
} catch (err: unknown) {
|
||||
logger.error("Got an error loading an identifier:", err);
|
||||
@@ -216,6 +241,9 @@ export default class SharedPhotoView extends Vue {
|
||||
NOTIFY_SHARED_PHOTO_LOAD_ERROR.message,
|
||||
TIMEOUTS.STANDARD,
|
||||
);
|
||||
// Clear image state on error
|
||||
this.imageBlob = undefined;
|
||||
this.imageFileName = undefined;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user