diff --git a/components/Alert.tsx b/components/Alert.tsx index 4fffdfb..bfe1333 100644 --- a/components/Alert.tsx +++ b/components/Alert.tsx @@ -1,24 +1,22 @@ -import {useTranslation} from 'next-i18next'; - interface AlertProps { onClose: () => void; - errorMessage: string; + message: string; + isWarning: boolean; } function Alert(props: AlertProps): JSX.Element { - const { t } = useTranslation(['index', 'errors']); - return ( -
- {props.errorMessage} - - - {t('index:errorClose')} - - - +
+ {props.message} + { + !props.isWarning && + + + + + + }
) } diff --git a/components/Button.tsx b/components/Button.tsx new file mode 100644 index 0000000..2346a43 --- /dev/null +++ b/components/Button.tsx @@ -0,0 +1,21 @@ +interface ButtonProps { + text?: string, + icon?: string, + onClick: () => void, +} + +function Button(props: ButtonProps): JSX.Element { + return ( + + ) +} + +export default Button; \ No newline at end of file diff --git a/components/Check.tsx b/components/Check.tsx index cd7a3f3..d8f8847 100644 --- a/components/Check.tsx +++ b/components/Check.tsx @@ -1,20 +1,16 @@ -import {useTranslation} from 'next-i18next'; - interface CheckProps { text: string; } function Check(props: CheckProps): JSX.Element { - const { t } = useTranslation(["index"]); - - return ( -
  • - - - - {props.text} -
  • - ) + return ( +
  • + + + + {props.text} +
  • + ) } export default Check; \ No newline at end of file diff --git a/components/Form.tsx b/components/Form.tsx index 5f30517..059c93c 100644 --- a/components/Form.tsx +++ b/components/Form.tsx @@ -13,6 +13,7 @@ import {getPayloadBodyFromFile, getPayloadBodyFromQR} from "../src/process"; import {PassData} from "../src/pass"; import {COLORS} from "../src/colors"; import Colors from './Colors'; +import Button from './Button'; function Form(): JSX.Element { const {t} = useTranslation(['index', 'errors', 'common']); @@ -59,6 +60,44 @@ function Form(): JSX.Element { }); } }, [inputFile]) + + // Whether Safari is used or not + let [isSafari, setIsSafari] = useState(true); + + // Check if Safari is used + useEffect(() => { + const navigator = window.navigator; + setIsSafari( + navigator.vendor && + navigator.vendor.indexOf('Apple') > -1 && + navigator.userAgent && + navigator.userAgent.indexOf('CriOS') == -1 && + navigator.userAgent.indexOf('FxiOS') == -1 + ) + }, []); + + // Whether Safari is used or not + let [isShareDialogAvailable, setIsShareDialogAvailable] = useState(false); + + // Check if share dialog is available + useEffect(() => { + setIsShareDialogAvailable(window.navigator && window.navigator.share !== undefined); + }, []); + + // Open share dialog + async function showShareDialog() { + const shareData = { + title: document.title, + text: t('common:title') + ' – ' + t('common:subtitle'), + url: window.location.protocol + "//" + window.location.host, + }; + + try { + await window.navigator.share(shareData); + } catch(error) { + console.log(error); + } + } // Show file Dialog async function showFileDialog() { @@ -102,7 +141,7 @@ function Form(): JSX.Element { // Start decoding from video device await codeReader.decodeFromVideoDevice(undefined, previewElem, - (result, error, controls) => { + (result, _error, controls) => { if (result !== undefined) { setQrCode(result); setFile(undefined); @@ -113,9 +152,6 @@ function Form(): JSX.Element { setGlobalControls(undefined); setIsCameraOpen(false); } - if (error !== undefined) { - setErrorMessage(error.message); - } } ) ); @@ -164,22 +200,15 @@ function Form(): JSX.Element { return (
    + { + !isSafari && {}}/> + }

    {t('index:selectCertificateDescription')}

    - - +
    }/> + { + errorMessage && setErrorMessage(undefined)}/> + } + + { + isShareDialogAvailable &&