about summary refs log tree commit diff
path: root/src
diff options
context:
space:
mode:
authorPaul Frazee <pfrazee@gmail.com>2023-01-26 22:08:10 -0600
committerPaul Frazee <pfrazee@gmail.com>2023-01-26 22:08:10 -0600
commit24559599f3b340a071e96f15b17deb914338d80b (patch)
tree642e91c88aa859e9fca0f7e9941f0c9c67f3c210 /src
parent20eaac6acd9e7b310ace864f6661c1a0e3ea169b (diff)
downloadvoidsky-24559599f3b340a071e96f15b17deb914338d80b.tar.zst
Implement web toast
Diffstat (limited to 'src')
-rw-r--r--src/App.web.tsx4
-rw-r--r--src/view/com/util/Toast.web.tsx75
2 files changed, 77 insertions, 2 deletions
diff --git a/src/App.web.tsx b/src/App.web.tsx
index 67ef680a5..4f9fd3e53 100644
--- a/src/App.web.tsx
+++ b/src/App.web.tsx
@@ -3,7 +3,7 @@ import {SafeAreaProvider} from 'react-native-safe-area-context'
 import * as view from './view/index'
 import {RootStoreModel, setupState, RootStoreProvider} from './state'
 import {WebShell} from './view/shell/web'
-// import Toast from 'react-native-root-toast' TODO
+import {ToastContainer} from './view/com/util/Toast.web'
 
 function App() {
   const [rootStore, setRootStore] = useState<RootStoreModel | undefined>(
@@ -26,9 +26,9 @@ function App() {
       <SafeAreaProvider>
         <WebShell />
       </SafeAreaProvider>
+      <ToastContainer />
     </RootStoreProvider>
   )
-  // <Toast.ToastContainer /> TODO
 }
 
 export default App
diff --git a/src/view/com/util/Toast.web.tsx b/src/view/com/util/Toast.web.tsx
new file mode 100644
index 000000000..bce178b4c
--- /dev/null
+++ b/src/view/com/util/Toast.web.tsx
@@ -0,0 +1,75 @@
+/*
+ * Note: the dataSet properties are used to leverage custom CSS in public/index.html
+ */
+
+import React, {useState, useEffect} from 'react'
+import {StyleSheet, Text, View} from 'react-native'
+import {FontAwesomeIcon} from '@fortawesome/react-native-fontawesome'
+
+const DURATION = 3500
+
+interface ActiveToast {
+  text: string
+}
+type GlobalSetActiveToast = (_activeToast: ActiveToast | undefined) => void
+
+// globals
+// =
+let globalSetActiveToast: GlobalSetActiveToast | undefined
+let toastTimeout: NodeJS.Timeout | undefined
+
+// components
+// =
+type ToastContainerProps = {}
+export const ToastContainer: React.FC<ToastContainerProps> = ({}) => {
+  const [activeToast, setActiveToast] = useState<ActiveToast | undefined>()
+  useEffect(() => {
+    globalSetActiveToast = (t: ActiveToast | undefined) => {
+      setActiveToast(t)
+    }
+  })
+  return (
+    <>
+      {activeToast && (
+        <View style={styles.container}>
+          <FontAwesomeIcon icon="check" size={24} style={styles.icon} />
+          <Text style={styles.text}>{activeToast.text}</Text>
+        </View>
+      )}
+    </>
+  )
+}
+
+// methods
+// =
+export function show(text: string) {
+  if (toastTimeout) {
+    clearTimeout(toastTimeout)
+  }
+  globalSetActiveToast?.({text})
+  toastTimeout = setTimeout(() => {
+    globalSetActiveToast?.(undefined)
+  }, DURATION)
+}
+
+const styles = StyleSheet.create({
+  container: {
+    position: 'absolute',
+    right: 20,
+    bottom: 20,
+    width: 350,
+    padding: 20,
+    flexDirection: 'row',
+    alignItems: 'center',
+    backgroundColor: '#000c',
+    borderRadius: 10,
+  },
+  icon: {
+    color: '#fff',
+  },
+  text: {
+    color: '#fff',
+    fontSize: 18,
+    marginLeft: 10,
+  },
+})