From a86b1a0ea32b8e1db6882dbd690eebcb79fdd18e Mon Sep 17 00:00:00 2001 From: Adrian Castro <22133246+castdrian@users.noreply.github.com> Date: Tue, 26 Mar 2024 20:52:15 +0100 Subject: [PATCH] feat: context menu on downloaditem --- apps/expo/src/components/DownloadItem.tsx | 97 +++++++++++++------ .../expo/src/hooks/DownloadManagerContext.tsx | 5 + 2 files changed, 73 insertions(+), 29 deletions(-) diff --git a/apps/expo/src/components/DownloadItem.tsx b/apps/expo/src/components/DownloadItem.tsx index 1e8f116..103b9a2 100644 --- a/apps/expo/src/components/DownloadItem.tsx +++ b/apps/expo/src/components/DownloadItem.tsx @@ -1,8 +1,13 @@ import type { Asset } from "expo-media-library"; +import type { NativeSyntheticEvent } from "react-native"; +import type { ContextMenuOnPressNativeEvent } from "react-native-context-menu-view"; import React from "react"; +import ContextMenu from "react-native-context-menu-view"; import { TouchableOpacity } from "react-native-gesture-handler"; import { Progress, Spinner, Text, View } from "tamagui"; +import { useDownloadManager } from "~/hooks/DownloadManagerContext"; + export interface DownloadItemProps { id: string; filename: string; @@ -18,6 +23,11 @@ export interface DownloadItemProps { isHLS?: boolean; } +enum ContextMenuActions { + Cancel = "Cancel", + Remove = "Remove", +} + const formatBytes = (bytes: number, decimals = 2) => { if (bytes === 0) return "0 Bytes"; const k = 1024; @@ -44,6 +54,24 @@ export const DownloadItem: React.FC = ({ const percentage = progress * 100; const formattedFileSize = formatBytes(fileSize); const formattedDownloaded = formatBytes(downloaded); + const { removeDownload, cancelDownload } = useDownloadManager(); + + const contextMenuActions = [ + { + title: ContextMenuActions.Remove, + }, + ...(!isFinished ? [{ title: ContextMenuActions.Cancel }] : []), + ]; + + const onContextMenuPress = ( + e: NativeSyntheticEvent, + ) => { + if (e.nativeEvent.name === ContextMenuActions.Cancel) { + void cancelDownload(id); + } else if (e.nativeEvent.name === ContextMenuActions.Remove) { + removeDownload(id); + } + }; const renderStatus = () => { if (statusText) { @@ -72,39 +100,50 @@ export const DownloadItem: React.FC = ({ }; return ( - onPress(asset)} - onLongPress={() => onLongPress(id)} - activeOpacity={0.7} + - - - {filename} - - - - + onPress(asset)} + onLongPress={() => onLongPress(id)} + activeOpacity={0.7} + > - - {isHLS - ? `${percentage.toFixed()}% - ${downloaded} of ${fileSize} segments` - : `${percentage.toFixed()}% - ${formattedDownloaded} of ${formattedFileSize}`} + + {filename} - {renderStatus()} + + + + + + {isHLS + ? `${percentage.toFixed()}% - ${downloaded} of ${fileSize} segments` + : `${percentage.toFixed()}% - ${formattedDownloaded} of ${formattedFileSize}`} + + {renderStatus()} + - - + + ); }; diff --git a/apps/expo/src/hooks/DownloadManagerContext.tsx b/apps/expo/src/hooks/DownloadManagerContext.tsx index a1d3ead..4fa82b2 100644 --- a/apps/expo/src/hooks/DownloadManagerContext.tsx +++ b/apps/expo/src/hooks/DownloadManagerContext.tsx @@ -84,6 +84,11 @@ export const DownloadManagerProvider: React.FC<{ children: ReactNode }> = ({ if (downloadItem?.downloadResumable) { await downloadItem.downloadResumable.cancelAsync(); } + toastController.show("Download cancelled", { + burntOptions: { preset: "done" }, + native: true, + duration: 500, + }); }; const startDownload = async (