diff --git a/bundle-analysis.html b/bundle-analysis.html
new file mode 100644
index 0000000..2cd30d0
--- /dev/null
+++ b/bundle-analysis.html
@@ -0,0 +1,4842 @@
+
+
+
+
+
+
+
+ Rollup Visualizer
+
+
+
+
+
+
+
+
+
diff --git a/data.json b/data.json
index 7b2b2ca..d20e4f7 100644
--- a/data.json
+++ b/data.json
@@ -6,7 +6,8 @@
"link4": "لقطة الشاشة",
"link5": "ملاحظة",
"link6": "اتصل بنا",
- "link7":"الخصوصية"
+ "link7":"الخصوصية",
+ "link8":"تحميل"
},
"Home": {
"title": "احصل على تنزيل مجاني لتطبيق",
@@ -183,8 +184,8 @@
"privacy": "© زاكر 2024.جميع الحقوق محفوظة"
},
"Links": {
- "google_play_link": "/",
- "apple_store_link": "/",
+ "google_play_link": "https://play.google.com/store",
+ "apple_store_link": "https://apps.apple.com",
"facebook": "/",
"telegram": "/",
"instagram": "/",
@@ -205,5 +206,9 @@
"NotFound": {
"title":"عذرا الصفخة غير موجودة",
"description":"ارجع للصفحة الرئيسية"
+ },
+ "Download": {
+ "title":"",
+ "description":""
}
}
diff --git a/index.html b/index.html
index 22c7974..8beb06b 100644
--- a/index.html
+++ b/index.html
@@ -4,9 +4,9 @@
-
+
- Website
+ Zaker
diff --git a/package-lock.json b/package-lock.json
index 162ebff..2758594 100644
--- a/package-lock.json
+++ b/package-lock.json
@@ -16,7 +16,8 @@
"react-icons": "^5.3.0",
"react-player": "^2.16.0",
"react-router-dom": "^6.27.0",
- "swiper": "^11.1.14"
+ "swiper": "^11.1.14",
+ "zustand": "^5.0.0"
},
"devDependencies": {
"@types/node": "^22.5.1",
@@ -4810,6 +4811,34 @@
"funding": {
"url": "https://github.com/sponsors/sindresorhus"
}
+ },
+ "node_modules/zustand": {
+ "version": "5.0.0",
+ "resolved": "https://registry.npmjs.org/zustand/-/zustand-5.0.0.tgz",
+ "integrity": "sha512-LE+VcmbartOPM+auOjCCLQOsQ05zUTp8RkgwRzefUk+2jISdMMFnxvyTjA4YNWr5ZGXYbVsEMZosttuxUBkojQ==",
+ "engines": {
+ "node": ">=12.20.0"
+ },
+ "peerDependencies": {
+ "@types/react": ">=18.0.0",
+ "immer": ">=9.0.6",
+ "react": ">=18.0.0",
+ "use-sync-external-store": ">=1.2.0"
+ },
+ "peerDependenciesMeta": {
+ "@types/react": {
+ "optional": true
+ },
+ "immer": {
+ "optional": true
+ },
+ "react": {
+ "optional": true
+ },
+ "use-sync-external-store": {
+ "optional": true
+ }
+ }
}
},
"dependencies": {
@@ -7978,6 +8007,12 @@
"resolved": "https://registry.npmjs.org/yocto-queue/-/yocto-queue-0.1.0.tgz",
"integrity": "sha512-rVksvsnNCdJ/ohGc6xgPwyN8eheCxsiLM8mxuE/t/mOVqJewPuO1miLpTHQiRgTKCLexL4MeAFVagts7HmNZ2Q==",
"dev": true
+ },
+ "zustand": {
+ "version": "5.0.0",
+ "resolved": "https://registry.npmjs.org/zustand/-/zustand-5.0.0.tgz",
+ "integrity": "sha512-LE+VcmbartOPM+auOjCCLQOsQ05zUTp8RkgwRzefUk+2jISdMMFnxvyTjA4YNWr5ZGXYbVsEMZosttuxUBkojQ==",
+ "requires": {}
}
}
}
diff --git a/package.json b/package.json
index 8694127..1ca9aee 100644
--- a/package.json
+++ b/package.json
@@ -19,7 +19,8 @@
"react-icons": "^5.3.0",
"react-player": "^2.16.0",
"react-router-dom": "^6.27.0",
- "swiper": "^11.1.14"
+ "swiper": "^11.1.14",
+ "zustand": "^5.0.0"
},
"devDependencies": {
"@types/node": "^22.5.1",
diff --git a/src/App.tsx b/src/App.tsx
index d482190..9c613a8 100644
--- a/src/App.tsx
+++ b/src/App.tsx
@@ -1,44 +1,32 @@
+import './styles/App/index.scss';
import { BrowserRouter as Router, Route, Routes } from 'react-router-dom';
-import { lazy, Suspense } from 'react';
+import { Suspense } from 'react';
import { Spin } from 'antd';
import Layout from './components/layout/Layout';
-import './styles/App/index.scss';
-const PrivacyPage = lazy(() => import("./pages/Privacy/Page"));
-const Page = lazy(() => import("./pages/Main/Page"));
-const NotFoundPage = lazy(() => import("./pages/NotFound/NotFound"));
+import { routes } from './Routes';
const App = () => {
+
return (
- }>
-
-
-
-
- }
- />
- }>
-
-
-
-
- }
- />
- }>
-
-
- }
- />
+ {routes.map((route:any) => (
+ }>
+ {route.withLayout ? (
+
+
+
+ ) : (
+
+ )}
+
+ }
+ />
+ ))}
);
diff --git a/src/Routes.tsx b/src/Routes.tsx
index 865b639..87edc9f 100644
--- a/src/Routes.tsx
+++ b/src/Routes.tsx
@@ -1,8 +1,31 @@
-import './styles/App/index.scss';
-import HomePage from './pages/HomePage';
+import { lazy } from 'react';
+import { RouteConfig } from './types/RoutesType';
-const Routes = () => {
- return ;
-};
+const DownloadPage = lazy(() => import("./pages/Download/Download"));
+const PrivacyPage = lazy(() => import("./pages/Privacy/Page"));
+const Page = lazy(() => import("./pages/Main/Page"));
+const NotFoundPage = lazy(() => import("./pages/NotFound/NotFound"));
+
+ export const routes: RouteConfig[] = [
+ {
+ path: '/',
+ Component: Page,
+ withLayout: true,
+ },
+ {
+ path: '/privacy',
+ Component: PrivacyPage,
+ withLayout: true,
+ },
+ {
+ path: '/download',
+ Component: DownloadPage,
+ withLayout: false,
+ },
+ {
+ path: '*',
+ Component: NotFoundPage,
+ withLayout: false,
+ },
+ ];
-export default Routes;
diff --git a/src/components/layout/NavBar.tsx b/src/components/layout/NavBar.tsx
index 0f25a1b..73dd11f 100644
--- a/src/components/layout/NavBar.tsx
+++ b/src/components/layout/NavBar.tsx
@@ -23,6 +23,7 @@ const NavBar: React.FC = () => {
{ path: RoutesEnums.NOTE, label: navBarData.link5 },
{ path: RoutesEnums.CONTACT, label: navBarData.link6 },
{ path: RoutesEnums.PRIVACY, label: navBarData.link7 },
+ { path: RoutesEnums.DOWNLOAD, label: navBarData.link8 },
];
const [Open, setOpen] = useState(false);
const handleToggle = () => {
@@ -57,7 +58,6 @@ const NavBar: React.FC = () => {
const handleClick = () => {
setActive(link.path);
};
- console.log(link);
const isActive =
Active === '' && link.path === '/#' ? true : Active === link.path;
diff --git a/src/enums/RoutesEnums.ts b/src/enums/RoutesEnums.ts
index b4ec319..03074ac 100644
--- a/src/enums/RoutesEnums.ts
+++ b/src/enums/RoutesEnums.ts
@@ -6,4 +6,5 @@ export enum RoutesEnums {
NOTE = '/#note',
CONTACT = '/#contact_us',
PRIVACY = '/privacy',
+ DOWNLOAD = '/download',
}
diff --git a/src/pages/Download/Download.tsx b/src/pages/Download/Download.tsx
new file mode 100644
index 0000000..35329e0
--- /dev/null
+++ b/src/pages/Download/Download.tsx
@@ -0,0 +1,34 @@
+import { useEffect } from 'react';
+import { useDetectDeviceType } from '../../states/DeviceTypeState';
+import DownloadPage from '../DownloadPage'
+import { detectDeviceType } from '../../utils/DetectDeviceType';
+import { Spin } from 'antd';
+import Layout from '../../components/layout/Layout';
+import { ExternalRedirect } from '../../utils/ExternalRedirect';
+
+const Download = () => {
+ const { DeviceType, setDeviceType }: any = useDetectDeviceType();
+
+ useEffect(() => {
+ setDeviceType(detectDeviceType());
+ }, [setDeviceType]);
+
+ if (!DeviceType) {
+ return ;
+ }
+ return (
+
+ {
+ DeviceType === 'desktop' ? (
+
+
+
+ ) : (
+
+ )
+ }
+
+ )
+}
+
+export default Download
\ No newline at end of file
diff --git a/src/states/DeviceTypeState.ts b/src/states/DeviceTypeState.ts
new file mode 100644
index 0000000..58033aa
--- /dev/null
+++ b/src/states/DeviceTypeState.ts
@@ -0,0 +1,13 @@
+import { create } from 'zustand';
+
+
+
+interface ModalState {
+ DeviceType: string;
+ setDeviceType: (value: string) => void;
+}
+export const useDetectDeviceType = create((set) => ({
+ DeviceType: "",
+ setDeviceType: (value: string) => set(() => ({ DeviceType: value })),
+}));
+
diff --git a/src/styles/App/classNames.scss b/src/styles/App/classNames.scss
index 194f386..bb75ba6 100644
--- a/src/styles/App/classNames.scss
+++ b/src/styles/App/classNames.scss
@@ -31,7 +31,7 @@
outline: none;
border: none;
border-radius: 10px;
- padding: 3vw 1vw;
+ padding: 35px 15px;
background: var(--secondary);
color: var(--white);
display: flex;
diff --git a/src/styles/pages/HowItWork.scss b/src/styles/pages/HowItWork.scss
index 61bc107..2bfaa0d 100644
--- a/src/styles/pages/HowItWork.scss
+++ b/src/styles/pages/HowItWork.scss
@@ -29,6 +29,7 @@
margin-top: 40px;
> img {
width: 600px;
+ height: 500px;
}
> span {
display: flex;
@@ -96,6 +97,7 @@
margin-top: 40px;
> img {
width: 300px;
+ height: 250px;
order: 0;
}
> span {
diff --git a/src/types/RoutesType.ts b/src/types/RoutesType.ts
new file mode 100644
index 0000000..7e3e2e1
--- /dev/null
+++ b/src/types/RoutesType.ts
@@ -0,0 +1,5 @@
+export interface RouteConfig {
+ path: string;
+ Component: React.LazyExoticComponent | React.FC;
+ withLayout: boolean;
+}
\ No newline at end of file
diff --git a/src/utils/DetectDeviceType.ts b/src/utils/DetectDeviceType.ts
new file mode 100644
index 0000000..b6f29fb
--- /dev/null
+++ b/src/utils/DetectDeviceType.ts
@@ -0,0 +1,16 @@
+export const detectDeviceType = () => {
+ const ua = navigator.userAgent;
+
+ // Check if it's an iOS device
+ const isIOS = /iPad|iPhone|iPod/.test(ua) && !(window as any).MSStream;
+
+ if (/android/i.test(ua)) {
+ return 'android';
+ } else if (isIOS) {
+ return 'ios';
+ } else {
+ return 'desktop';
+ }
+ };
+
+
diff --git a/src/utils/ExternalRedirect.ts b/src/utils/ExternalRedirect.ts
new file mode 100644
index 0000000..90f7e1e
--- /dev/null
+++ b/src/utils/ExternalRedirect.ts
@@ -0,0 +1,9 @@
+import { useEffect } from "react";
+
+export const ExternalRedirect = ({ url }: { url: string }) => {
+ useEffect(() => {
+ window.location.href = url;
+ }, [url]);
+
+ return null; // This component renders nothing
+ };
\ No newline at end of file