@burdenoff/microfe-crewfoundry 2026.624.1 → 2026.625.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/crewfoundry/pages/AdminAdminPagePage.js +86 -70
- package/dist/crewfoundry/pages/AdminAdminPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/AnalyticsAnalyticsPagePage.js +104 -88
- package/dist/crewfoundry/pages/AnalyticsAnalyticsPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/AnalyticsEmployeeAnalyticsPagePage.js +91 -75
- package/dist/crewfoundry/pages/AnalyticsEmployeeAnalyticsPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/AnalyticsFinancialAnalyticsPagePage.js +119 -103
- package/dist/crewfoundry/pages/AnalyticsFinancialAnalyticsPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/AnalyticsHiringAnalyticsPagePage.js +107 -91
- package/dist/crewfoundry/pages/AnalyticsHiringAnalyticsPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/CommunicationsAnnouncementsPagePage.js +10 -10
- package/dist/crewfoundry/pages/CommunicationsAnnouncementsPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/CommunicationsCallsPagePage.js +60 -48
- package/dist/crewfoundry/pages/CommunicationsCallsPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/CommunicationsDirectoryPagePage.js +10 -10
- package/dist/crewfoundry/pages/CommunicationsDirectoryPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/CommunicationsFilesPagePage.js +20 -20
- package/dist/crewfoundry/pages/CommunicationsFilesPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/CommunicationsMessagesPagePage.js +22 -22
- package/dist/crewfoundry/pages/CommunicationsMessagesPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/CommunicationsTeamsPagePage.js +7 -7
- package/dist/crewfoundry/pages/CommunicationsTeamsPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/CommunicationsVideoCallsPagePage.js +67 -55
- package/dist/crewfoundry/pages/CommunicationsVideoCallsPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/CompanyClientManagementPagePage.js +54 -42
- package/dist/crewfoundry/pages/CompanyClientManagementPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/CompanyCompanyDashboardPagePage.js +68 -52
- package/dist/crewfoundry/pages/CompanyCompanyDashboardPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/CompanyCompanyProfilePagePage.js +30 -30
- package/dist/crewfoundry/pages/CompanyCompanyProfilePagePage.js.map +1 -1
- package/dist/crewfoundry/pages/CompanyVendorManagementPagePage.js +9 -9
- package/dist/crewfoundry/pages/CompanyVendorManagementPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/DashboardAnalyticsPagePage.js +90 -74
- package/dist/crewfoundry/pages/DashboardAnalyticsPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/DashboardDashboardPagePage.js +166 -132
- package/dist/crewfoundry/pages/DashboardDashboardPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/DashboardEnhancedDashboardPagePage.js +43 -43
- package/dist/crewfoundry/pages/DashboardEnhancedDashboardPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/DashboardExecutiveDashboardPage.js +107 -91
- package/dist/crewfoundry/pages/DashboardExecutiveDashboardPage.js.map +1 -1
- package/dist/crewfoundry/pages/HelpApiDocumentationPagePage.js +35 -35
- package/dist/crewfoundry/pages/HelpApiDocumentationPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/HiringApplicationsPagePage.js +78 -62
- package/dist/crewfoundry/pages/HiringApplicationsPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/HiringCandidatesPagePage.js +17 -17
- package/dist/crewfoundry/pages/HiringCandidatesPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/HiringCreateJobPagePage.js +39 -39
- package/dist/crewfoundry/pages/HiringCreateJobPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/HiringInterviewsPagePage.js +53 -41
- package/dist/crewfoundry/pages/HiringInterviewsPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/HiringJobDetailsPagePage.js +41 -37
- package/dist/crewfoundry/pages/HiringJobDetailsPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/HiringJobsPagePage.js +25 -20
- package/dist/crewfoundry/pages/HiringJobsPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/HrDepartmentsPagePage.js +54 -42
- package/dist/crewfoundry/pages/HrDepartmentsPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/HrEmployeesPagePage.js +76 -60
- package/dist/crewfoundry/pages/HrEmployeesPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/HrLeaveManagementPagePage.js +83 -67
- package/dist/crewfoundry/pages/HrLeaveManagementPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/HrPayrollPagePage.js +86 -70
- package/dist/crewfoundry/pages/HrPayrollPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/HrTimeTrackingPagePage.js +79 -63
- package/dist/crewfoundry/pages/HrTimeTrackingPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/LearningAssessmentsPagePage.js +51 -39
- package/dist/crewfoundry/pages/LearningAssessmentsPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/LearningCertificatesPagePage.js +14 -14
- package/dist/crewfoundry/pages/LearningCertificatesPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/LearningCourseDetailsPagePage.js +29 -25
- package/dist/crewfoundry/pages/LearningCourseDetailsPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/LearningCourseLearningPagePage.js +17 -17
- package/dist/crewfoundry/pages/LearningCourseLearningPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/LearningCoursesPagePage.js +11 -11
- package/dist/crewfoundry/pages/LearningCoursesPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/LearningLearningAnalyticsPagePage.js +76 -60
- package/dist/crewfoundry/pages/LearningLearningAnalyticsPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/LearningLearningPagePage.js +67 -51
- package/dist/crewfoundry/pages/LearningLearningPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/LearningLearningPathDetailPagePage.js +17 -17
- package/dist/crewfoundry/pages/LearningLearningPathDetailPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/LearningLearningPathsPagePage.js +7 -7
- package/dist/crewfoundry/pages/LearningLearningPathsPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/LearningMyLearningPagePage.js +69 -53
- package/dist/crewfoundry/pages/LearningMyLearningPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/MarketplaceBookingManagementPagePage.js +54 -42
- package/dist/crewfoundry/pages/MarketplaceBookingManagementPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/MarketplaceEarningsPagePage.js +66 -54
- package/dist/crewfoundry/pages/MarketplaceEarningsPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/MarketplaceFreelancerProfilePageEnhancedPage.js +37 -37
- package/dist/crewfoundry/pages/MarketplaceFreelancerProfilePageEnhancedPage.js.map +1 -1
- package/dist/crewfoundry/pages/MarketplaceFreelancerProfilePagePage.js +33 -32
- package/dist/crewfoundry/pages/MarketplaceFreelancerProfilePagePage.js.map +1 -1
- package/dist/crewfoundry/pages/MarketplaceMarketplacePagePage.js +54 -42
- package/dist/crewfoundry/pages/MarketplaceMarketplacePagePage.js.map +1 -1
- package/dist/crewfoundry/pages/MarketplaceMarketplaceServicesPagePage.js +11 -11
- package/dist/crewfoundry/pages/MarketplaceMarketplaceServicesPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/MarketplaceMessagingPagePage.js +18 -18
- package/dist/crewfoundry/pages/MarketplaceMessagingPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/MarketplaceMyServicesPagePage.js +7 -7
- package/dist/crewfoundry/pages/MarketplaceMyServicesPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/MarketplaceProjectDetailsPagePage.js +29 -25
- package/dist/crewfoundry/pages/MarketplaceProjectDetailsPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/MarketplaceServiceDetailsPagePage.js +22 -18
- package/dist/crewfoundry/pages/MarketplaceServiceDetailsPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/PaymentsEscrowPagePage.js +55 -43
- package/dist/crewfoundry/pages/PaymentsEscrowPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/PaymentsInvoicesPagePage.js +7 -7
- package/dist/crewfoundry/pages/PaymentsInvoicesPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/PaymentsPaymentDashboardPagePage.js +62 -46
- package/dist/crewfoundry/pages/PaymentsPaymentDashboardPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/PaymentsPaymentMethodsPagePage.js +14 -14
- package/dist/crewfoundry/pages/PaymentsPaymentMethodsPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/PaymentsSecurityPagePage.js +71 -59
- package/dist/crewfoundry/pages/PaymentsSecurityPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/ProjectsCreateProjectPagePage.js +20 -20
- package/dist/crewfoundry/pages/ProjectsCreateProjectPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/ProjectsProjectDetailsPagePage.js +33 -29
- package/dist/crewfoundry/pages/ProjectsProjectDetailsPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/ProjectsProjectsPagePage.js +16 -16
- package/dist/crewfoundry/pages/ProjectsProjectsPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/TeamsTeamAnalyticsPagePage.js +53 -41
- package/dist/crewfoundry/pages/TeamsTeamAnalyticsPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/TeamsTeamDetailPagePage.js +25 -21
- package/dist/crewfoundry/pages/TeamsTeamDetailPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/TeamsTeamDirectoryPagePage.js +9 -9
- package/dist/crewfoundry/pages/TeamsTeamDirectoryPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/TeamsTeamSettingsPagePage.js +48 -48
- package/dist/crewfoundry/pages/TeamsTeamSettingsPagePage.js.map +1 -1
- package/dist/crewfoundry/pages/TeamsTeamsPagePage.js +13 -13
- package/dist/crewfoundry/pages/TeamsTeamsPagePage.js.map +1 -1
- package/package.json +2 -2
|
@@ -1,21 +1,21 @@
|
|
|
1
1
|
import { useCrewFoundryStore as e } from "../store/crewfoundryStore.js";
|
|
2
2
|
import { FolderKanban as t, Users as n } from "lucide-react";
|
|
3
3
|
import { jsx as r, jsxs as i } from "react/jsx-runtime";
|
|
4
|
-
import { Badge as a, Card as o, CardContent as s, CardDescription as c, CardHeader as l, CardTitle as u } from "@burdenoff/fe-libs/ui";
|
|
4
|
+
import { Badge as a, Card as o, CardContent as s, CardDescription as c, CardHeader as l, CardTitle as u, GradientText as d } from "@burdenoff/fe-libs/ui";
|
|
5
5
|
//#region src/crewfoundry/pages/CommunicationsTeamsPagePage.tsx
|
|
6
|
-
function
|
|
7
|
-
let { teams:
|
|
6
|
+
function f() {
|
|
7
|
+
let { teams: f } = e();
|
|
8
8
|
return /* @__PURE__ */ i("div", {
|
|
9
9
|
className: "space-y-6 p-6",
|
|
10
10
|
children: [/* @__PURE__ */ i("div", { children: [/* @__PURE__ */ r("h1", {
|
|
11
11
|
className: "text-2xl font-semibold",
|
|
12
|
-
children: "Team Channels"
|
|
12
|
+
children: /* @__PURE__ */ r(d, { children: "Team Channels" })
|
|
13
13
|
}), /* @__PURE__ */ i("p", {
|
|
14
14
|
className: "text-sm text-text-secondary",
|
|
15
|
-
children: [
|
|
15
|
+
children: [f.length, " active team channels"]
|
|
16
16
|
})] }), /* @__PURE__ */ r("div", {
|
|
17
17
|
className: "grid gap-4 md:grid-cols-2 lg:grid-cols-3",
|
|
18
|
-
children:
|
|
18
|
+
children: f.map((e) => /* @__PURE__ */ i(o, {
|
|
19
19
|
className: "cursor-pointer hover:shadow-md transition-shadow",
|
|
20
20
|
children: [/* @__PURE__ */ i(l, { children: [/* @__PURE__ */ i("div", {
|
|
21
21
|
className: "flex items-center justify-between",
|
|
@@ -57,6 +57,6 @@ function d() {
|
|
|
57
57
|
});
|
|
58
58
|
}
|
|
59
59
|
//#endregion
|
|
60
|
-
export {
|
|
60
|
+
export { f as CommunicationsTeamsPagePage };
|
|
61
61
|
|
|
62
62
|
//# sourceMappingURL=CommunicationsTeamsPagePage.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"CommunicationsTeamsPagePage.js","names":[],"sources":["../../../src/crewfoundry/pages/CommunicationsTeamsPagePage.tsx"],"sourcesContent":["import {\n Badge,\n Card,\n CardContent,\n CardDescription,\n CardHeader,\n CardTitle,\n} from '@burdenoff/fe-libs/ui';\nimport { FolderKanban, Users } from 'lucide-react';\nimport { useCrewFoundryStore } from '../store/crewfoundryStore';\n\nexport function CommunicationsTeamsPagePage() {\n const { teams } = useCrewFoundryStore();\n\n return (\n <div className=\"space-y-6 p-6\">\n <div>\n <h1 className=\"text-2xl font-semibold\">Team Channels</h1>\n <p className=\"text-sm text-text-secondary\">{teams.length} active team channels</p>\n </div>\n <div className=\"grid gap-4 md:grid-cols-2 lg:grid-cols-3\">\n {teams.map((team) => (\n <Card key={team.id} className=\"cursor-pointer hover:shadow-md transition-shadow\">\n <CardHeader>\n <div className=\"flex items-center justify-between\">\n <CardTitle className=\"text-base\">{team.name}</CardTitle>\n <Badge\n variant={team.status === 'active' ? 'default' : 'secondary'}\n className=\"text-[10px]\"\n >\n {team.status}\n </Badge>\n </div>\n <CardDescription>{team.description}</CardDescription>\n </CardHeader>\n <CardContent>\n <div className=\"flex items-center justify-between text-sm text-text-secondary\">\n <span className=\"flex items-center gap-1\">\n <Users className=\"h-3 w-3\" />\n {team.memberCount} members\n </span>\n <span className=\"flex items-center gap-1\">\n <FolderKanban className=\"h-3 w-3\" />\n {team.projectCount} projects\n </span>\n </div>\n <div className=\"mt-2 text-xs text-text-secondary\">\n <span>Lead: {team.leadName}</span> · <span>{team.department}</span>\n </div>\n </CardContent>\n </Card>\n ))}\n </div>\n </div>\n );\n}\n"],"mappings":";;;;;
|
|
1
|
+
{"version":3,"file":"CommunicationsTeamsPagePage.js","names":[],"sources":["../../../src/crewfoundry/pages/CommunicationsTeamsPagePage.tsx"],"sourcesContent":["import {\n Badge,\n Card,\n CardContent,\n CardDescription,\n CardHeader,\n CardTitle,\n GradientText,\n} from '@burdenoff/fe-libs/ui';\nimport { FolderKanban, Users } from 'lucide-react';\nimport { useCrewFoundryStore } from '../store/crewfoundryStore';\n\nexport function CommunicationsTeamsPagePage() {\n const { teams } = useCrewFoundryStore();\n\n return (\n <div className=\"space-y-6 p-6\">\n <div>\n <h1 className=\"text-2xl font-semibold\">\n <GradientText>Team Channels</GradientText>\n </h1>\n <p className=\"text-sm text-text-secondary\">{teams.length} active team channels</p>\n </div>\n <div className=\"grid gap-4 md:grid-cols-2 lg:grid-cols-3\">\n {teams.map((team) => (\n <Card key={team.id} className=\"cursor-pointer hover:shadow-md transition-shadow\">\n <CardHeader>\n <div className=\"flex items-center justify-between\">\n <CardTitle className=\"text-base\">{team.name}</CardTitle>\n <Badge\n variant={team.status === 'active' ? 'default' : 'secondary'}\n className=\"text-[10px]\"\n >\n {team.status}\n </Badge>\n </div>\n <CardDescription>{team.description}</CardDescription>\n </CardHeader>\n <CardContent>\n <div className=\"flex items-center justify-between text-sm text-text-secondary\">\n <span className=\"flex items-center gap-1\">\n <Users className=\"h-3 w-3\" />\n {team.memberCount} members\n </span>\n <span className=\"flex items-center gap-1\">\n <FolderKanban className=\"h-3 w-3\" />\n {team.projectCount} projects\n </span>\n </div>\n <div className=\"mt-2 text-xs text-text-secondary\">\n <span>Lead: {team.leadName}</span> · <span>{team.department}</span>\n </div>\n </CardContent>\n </Card>\n ))}\n </div>\n </div>\n );\n}\n"],"mappings":";;;;;AAYA,SAAgB,IAA8B;CAC5C,IAAM,EAAE,aAAU,GAAqB;AAEvC,QACE,kBAAC,OAAD;EAAK,WAAU;YAAf,CACE,kBAAC,OAAD,EAAA,UAAA,CACE,kBAAC,MAAD;GAAI,WAAU;aACZ,kBAAC,GAAD,EAAA,UAAc,iBAA4B,CAAA;GACvC,CAAA,EACL,kBAAC,KAAD;GAAG,WAAU;aAAb,CAA4C,EAAM,QAAO,wBAAyB;KAC9E,EAAA,CAAA,EACN,kBAAC,OAAD;GAAK,WAAU;aACZ,EAAM,KAAK,MACV,kBAAC,GAAD;IAAoB,WAAU;cAA9B,CACE,kBAAC,GAAD,EAAA,UAAA,CACE,kBAAC,OAAD;KAAK,WAAU;eAAf,CACE,kBAAC,GAAD;MAAW,WAAU;gBAAa,EAAK;MAAiB,CAAA,EACxD,kBAAC,GAAD;MACE,SAAS,EAAK,WAAW,WAAW,YAAY;MAChD,WAAU;gBAET,EAAK;MACA,CAAA,CACJ;QACN,kBAAC,GAAD,EAAA,UAAkB,EAAK,aAA8B,CAAA,CAC1C,EAAA,CAAA,EACb,kBAAC,GAAD,EAAA,UAAA,CACE,kBAAC,OAAD;KAAK,WAAU;eAAf,CACE,kBAAC,QAAD;MAAM,WAAU;gBAAhB;OACE,kBAAC,GAAD,EAAO,WAAU,WAAY,CAAA;OAC5B,EAAK;OAAY;OACb;SACP,kBAAC,QAAD;MAAM,WAAU;gBAAhB;OACE,kBAAC,GAAD,EAAc,WAAU,WAAY,CAAA;OACnC,EAAK;OAAa;OACd;QACH;QACN,kBAAC,OAAD;KAAK,WAAU;eAAf;MACE,kBAAC,QAAD,EAAA,UAAA,CAAM,UAAO,EAAK,SAAgB,EAAA,CAAA;;MAAG,kBAAC,QAAD,EAAA,UAAO,EAAK,YAAkB,CAAA;MAC/D;OACM,EAAA,CAAA,CACT;MA5BI,EAAK,GA4BT,CACP;GACE,CAAA,CACF"}
|
|
@@ -2,45 +2,45 @@ import { useCrewFoundryStore as e } from "../store/crewfoundryStore.js";
|
|
|
2
2
|
import { useMemo as t } from "react";
|
|
3
3
|
import { Calendar as n, Clock as r, Monitor as i, Users as a, Video as o } from "lucide-react";
|
|
4
4
|
import { jsx as s, jsxs as c } from "react/jsx-runtime";
|
|
5
|
-
import { Badge as l, Button as u, Card as d, CardContent as f, CardHeader as p, CardTitle as m } from "@burdenoff/fe-libs/ui";
|
|
5
|
+
import { Badge as l, Button as u, Card as d, CardContent as f, CardHeader as p, CardTitle as m, GlassCard as h, GradientText as g } from "@burdenoff/fe-libs/ui";
|
|
6
6
|
//#region src/crewfoundry/pages/CommunicationsVideoCallsPagePage.tsx
|
|
7
|
-
var
|
|
7
|
+
var _ = (e) => `${Math.max(e, 15)} min`, v = (e) => {
|
|
8
8
|
let t = Math.max(e, 1);
|
|
9
9
|
return `${String(t).padStart(2, "0")}:${String(t * 7 % 60).padStart(2, "0")}`;
|
|
10
|
-
},
|
|
10
|
+
}, y = (e) => {
|
|
11
11
|
let t = new Date(e);
|
|
12
12
|
return Number.isNaN(t.getTime()) ? "Upcoming" : t.toLocaleDateString();
|
|
13
13
|
};
|
|
14
|
-
function
|
|
15
|
-
let { teams:
|
|
16
|
-
let e =
|
|
14
|
+
function b() {
|
|
15
|
+
let { teams: b, interviews: x, announcements: S } = e(), C = t(() => {
|
|
16
|
+
let e = b.slice(0, 6).map((e, t) => ({
|
|
17
17
|
id: `team-${e.id}`,
|
|
18
18
|
title: `${e.name} Sync`,
|
|
19
19
|
host: e.leadName,
|
|
20
|
-
time:
|
|
21
|
-
duration:
|
|
20
|
+
time: y(e.createdAt),
|
|
21
|
+
duration: _(15 + t * 10),
|
|
22
22
|
participants: Math.max(e.memberCount, 2),
|
|
23
23
|
recurring: t % 2 == 0
|
|
24
|
-
})), t =
|
|
24
|
+
})), t = x.slice(0, 4).map((e) => ({
|
|
25
25
|
id: `interview-${e.id}`,
|
|
26
26
|
title: `Interview · ${e.candidateName}`,
|
|
27
27
|
host: e.interviewerName,
|
|
28
|
-
time:
|
|
29
|
-
duration:
|
|
28
|
+
time: y(e.date),
|
|
29
|
+
duration: _(Number.parseInt(e.time.split(":")[0] || "30", 10)),
|
|
30
30
|
participants: 3,
|
|
31
31
|
recurring: !1
|
|
32
32
|
}));
|
|
33
33
|
return [...e, ...t];
|
|
34
|
-
}, [
|
|
34
|
+
}, [x, b]), w = t(() => S.slice(0, 6).map((e) => {
|
|
35
35
|
let t = Math.max(12, Math.round(e.content.length / 40));
|
|
36
36
|
return {
|
|
37
37
|
id: `recording-${e.id}`,
|
|
38
38
|
title: `${e.title} recording`,
|
|
39
|
-
date:
|
|
40
|
-
duration:
|
|
39
|
+
date: y(e.createdAt),
|
|
40
|
+
duration: v(t),
|
|
41
41
|
size: `${(t / 10).toFixed(1)} GB`
|
|
42
42
|
};
|
|
43
|
-
}), [
|
|
43
|
+
}), [S]), T = C.length ? Math.round(C.map((e) => Number.parseInt(e.duration.split(" ")[0], 10)).reduce((e, t) => e + t, 0) / C.length) : 0;
|
|
44
44
|
return /* @__PURE__ */ c("div", {
|
|
45
45
|
className: "space-y-6 p-6",
|
|
46
46
|
children: [
|
|
@@ -48,7 +48,7 @@ function v() {
|
|
|
48
48
|
className: "flex items-center justify-between",
|
|
49
49
|
children: [/* @__PURE__ */ c("div", { children: [/* @__PURE__ */ s("h1", {
|
|
50
50
|
className: "text-2xl font-semibold",
|
|
51
|
-
children: "Video Calls"
|
|
51
|
+
children: /* @__PURE__ */ s(g, { children: "Video Calls" })
|
|
52
52
|
}), /* @__PURE__ */ s("p", {
|
|
53
53
|
className: "text-sm text-text-secondary",
|
|
54
54
|
children: "Video meetings and recordings"
|
|
@@ -67,47 +67,59 @@ function v() {
|
|
|
67
67
|
/* @__PURE__ */ c("div", {
|
|
68
68
|
className: "grid gap-4 md:grid-cols-3",
|
|
69
69
|
children: [
|
|
70
|
-
/* @__PURE__ */ c(
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
70
|
+
/* @__PURE__ */ c(h, {
|
|
71
|
+
treatment: "metric",
|
|
72
|
+
className: "border-border-seam",
|
|
73
|
+
children: [/* @__PURE__ */ c(p, {
|
|
74
|
+
className: "flex flex-row items-center justify-between space-y-0 pb-2",
|
|
75
|
+
children: [/* @__PURE__ */ s(m, {
|
|
76
|
+
className: "text-sm font-medium",
|
|
77
|
+
children: "Upcoming"
|
|
78
|
+
}), /* @__PURE__ */ s(n, { className: "h-4 w-4 text-status-info-text" })]
|
|
79
|
+
}), /* @__PURE__ */ c(f, { children: [/* @__PURE__ */ s("div", {
|
|
80
|
+
className: "text-2xl font-bold tabular-nums",
|
|
81
|
+
children: C.length
|
|
82
|
+
}), /* @__PURE__ */ s("p", {
|
|
83
|
+
className: "text-xs text-text-secondary",
|
|
84
|
+
children: "meetings scheduled"
|
|
85
|
+
})] })]
|
|
86
|
+
}),
|
|
87
|
+
/* @__PURE__ */ c(h, {
|
|
88
|
+
treatment: "metric",
|
|
89
|
+
className: "border-border-seam",
|
|
90
|
+
children: [/* @__PURE__ */ c(p, {
|
|
91
|
+
className: "flex flex-row items-center justify-between space-y-0 pb-2",
|
|
92
|
+
children: [/* @__PURE__ */ s(m, {
|
|
93
|
+
className: "text-sm font-medium",
|
|
94
|
+
children: "Recordings"
|
|
95
|
+
}), /* @__PURE__ */ s(i, { className: "h-4 w-4 text-text-secondary" })]
|
|
96
|
+
}), /* @__PURE__ */ c(f, { children: [/* @__PURE__ */ s("div", {
|
|
97
|
+
className: "text-2xl font-bold tabular-nums",
|
|
98
|
+
children: w.length
|
|
99
|
+
}), /* @__PURE__ */ s("p", {
|
|
100
|
+
className: "text-xs text-text-secondary",
|
|
101
|
+
children: "available"
|
|
102
|
+
})] })]
|
|
103
|
+
}),
|
|
104
|
+
/* @__PURE__ */ c(h, {
|
|
105
|
+
treatment: "metric",
|
|
106
|
+
className: "border-border-seam",
|
|
107
|
+
children: [/* @__PURE__ */ c(p, {
|
|
108
|
+
className: "flex flex-row items-center justify-between space-y-0 pb-2",
|
|
109
|
+
children: [/* @__PURE__ */ s(m, {
|
|
110
|
+
className: "text-sm font-medium",
|
|
111
|
+
children: "Avg Duration"
|
|
112
|
+
}), /* @__PURE__ */ s(r, { className: "h-4 w-4 text-text-secondary" })]
|
|
113
|
+
}), /* @__PURE__ */ s(f, { children: /* @__PURE__ */ c("div", {
|
|
114
|
+
className: "text-2xl font-bold tabular-nums",
|
|
115
|
+
children: [T, " min"]
|
|
116
|
+
}) })]
|
|
117
|
+
})
|
|
106
118
|
]
|
|
107
119
|
}),
|
|
108
120
|
/* @__PURE__ */ c(d, { children: [/* @__PURE__ */ s(p, { children: /* @__PURE__ */ s(m, { children: "Upcoming Meetings" }) }), /* @__PURE__ */ s(f, {
|
|
109
121
|
className: "space-y-3",
|
|
110
|
-
children:
|
|
122
|
+
children: C.map((e) => /* @__PURE__ */ c("div", {
|
|
111
123
|
className: "flex items-center justify-between rounded border p-3",
|
|
112
124
|
children: [/* @__PURE__ */ c("div", { children: [/* @__PURE__ */ s("p", {
|
|
113
125
|
className: "text-sm font-medium",
|
|
@@ -147,7 +159,7 @@ function v() {
|
|
|
147
159
|
})] }),
|
|
148
160
|
/* @__PURE__ */ c(d, { children: [/* @__PURE__ */ s(p, { children: /* @__PURE__ */ s(m, { children: "Recent Recordings" }) }), /* @__PURE__ */ s(f, {
|
|
149
161
|
className: "space-y-3",
|
|
150
|
-
children:
|
|
162
|
+
children: w.map((e) => /* @__PURE__ */ c("div", {
|
|
151
163
|
className: "flex items-center justify-between rounded border p-3",
|
|
152
164
|
children: [/* @__PURE__ */ c("div", { children: [/* @__PURE__ */ s("p", {
|
|
153
165
|
className: "text-sm font-medium",
|
|
@@ -173,6 +185,6 @@ function v() {
|
|
|
173
185
|
});
|
|
174
186
|
}
|
|
175
187
|
//#endregion
|
|
176
|
-
export {
|
|
188
|
+
export { b as CommunicationsVideoCallsPagePage };
|
|
177
189
|
|
|
178
190
|
//# sourceMappingURL=CommunicationsVideoCallsPagePage.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"CommunicationsVideoCallsPagePage.js","names":[],"sources":["../../../src/crewfoundry/pages/CommunicationsVideoCallsPagePage.tsx"],"sourcesContent":["import { useMemo } from 'react';\nimport { Badge, Button, Card, CardContent, CardHeader, CardTitle } from '@burdenoff/fe-libs/ui';\nimport { Calendar, Clock, Monitor, Users, Video } from 'lucide-react';\nimport { useCrewFoundryStore } from '../store/crewfoundryStore';\n\ntype Meeting = {\n id: string;\n title: string;\n host: string;\n time: string;\n duration: string;\n participants: number;\n recurring: boolean;\n};\n\ntype Recording = {\n id: string;\n title: string;\n date: string;\n duration: string;\n size: string;\n};\n\nconst formatMeetingDuration = (minutes: number): string => `${Math.max(minutes, 15)} min`;\n\nconst formatRecordingDuration = (minutes: number): string => {\n const safeMinutes = Math.max(minutes, 1);\n const mm = String(safeMinutes).padStart(2, '0');\n const ss = String((safeMinutes * 7) % 60).padStart(2, '0');\n return `${mm}:${ss}`;\n};\n\nconst formatDate = (value: string): string => {\n const parsed = new Date(value);\n if (Number.isNaN(parsed.getTime())) {\n return 'Upcoming';\n }\n return parsed.toLocaleDateString();\n};\n\nexport function CommunicationsVideoCallsPagePage() {\n const { teams, interviews, announcements } = useCrewFoundryStore();\n\n const upcomingMeetings = useMemo<Meeting[]>(() => {\n const teamMeetings = teams.slice(0, 6).map((team, index) => ({\n id: `team-${team.id}`,\n title: `${team.name} Sync`,\n host: team.leadName,\n time: formatDate(team.createdAt),\n duration: formatMeetingDuration(15 + index * 10),\n participants: Math.max(team.memberCount, 2),\n recurring: index % 2 === 0,\n }));\n\n const interviewMeetings = interviews.slice(0, 4).map((interview) => ({\n id: `interview-${interview.id}`,\n title: `Interview · ${interview.candidateName}`,\n host: interview.interviewerName,\n time: formatDate(interview.date),\n duration: formatMeetingDuration(Number.parseInt(interview.time.split(':')[0] || '30', 10)),\n participants: 3,\n recurring: false,\n }));\n\n return [...teamMeetings, ...interviewMeetings];\n }, [interviews, teams]);\n\n const recentRecordings = useMemo<Recording[]>(() => {\n const source = announcements.slice(0, 6);\n return source.map((announcement) => {\n const durationMinutes = Math.max(12, Math.round(announcement.content.length / 40));\n return {\n id: `recording-${announcement.id}`,\n title: `${announcement.title} recording`,\n date: formatDate(announcement.createdAt),\n duration: formatRecordingDuration(durationMinutes),\n size: `${(durationMinutes / 10).toFixed(1)} GB`,\n };\n });\n }, [announcements]);\n\n const averageDurationMinutes = upcomingMeetings.length\n ? Math.round(\n upcomingMeetings\n .map((meeting) => Number.parseInt(meeting.duration.split(' ')[0], 10))\n .reduce((total, value) => total + value, 0) / upcomingMeetings.length\n )\n : 0;\n\n return (\n <div className=\"space-y-6 p-6\">\n <div className=\"flex items-center justify-between\">\n <div>\n <h1 className=\"text-2xl font-semibold\">Video Calls</h1>\n <p className=\"text-sm text-text-secondary\">Video meetings and recordings</p>\n </div>\n <div className=\"flex gap-2\">\n <Button variant=\"outline\" size=\"sm\">\n <Calendar className=\"mr-1 h-4 w-4\" />\n Schedule\n </Button>\n <Button size=\"sm\">\n <Video className=\"mr-1 h-4 w-4\" />\n Start Meeting\n </Button>\n </div>\n </div>\n\n <div className=\"grid gap-4 md:grid-cols-3\">\n <Card>\n <CardHeader className=\"flex flex-row items-center justify-between space-y-0 pb-2\">\n <CardTitle className=\"text-sm font-medium\">Upcoming</CardTitle>\n <Calendar className=\"h-4 w-4 text-blue-500\" />\n </CardHeader>\n <CardContent>\n <div className=\"text-2xl font-bold\">{upcomingMeetings.length}</div>\n <p className=\"text-xs text-text-secondary\">meetings scheduled</p>\n </CardContent>\n </Card>\n <Card>\n <CardHeader className=\"flex flex-row items-center justify-between space-y-0 pb-2\">\n <CardTitle className=\"text-sm font-medium\">Recordings</CardTitle>\n <Monitor className=\"h-4 w-4 text-text-secondary\" />\n </CardHeader>\n <CardContent>\n <div className=\"text-2xl font-bold\">{recentRecordings.length}</div>\n <p className=\"text-xs text-text-secondary\">available</p>\n </CardContent>\n </Card>\n <Card>\n <CardHeader className=\"flex flex-row items-center justify-between space-y-0 pb-2\">\n <CardTitle className=\"text-sm font-medium\">Avg Duration</CardTitle>\n <Clock className=\"h-4 w-4 text-text-secondary\" />\n </CardHeader>\n <CardContent>\n <div className=\"text-2xl font-bold\">{averageDurationMinutes} min</div>\n </CardContent>\n </Card>\n </div>\n\n <Card>\n <CardHeader>\n <CardTitle>Upcoming Meetings</CardTitle>\n </CardHeader>\n <CardContent className=\"space-y-3\">\n {upcomingMeetings.map((meeting) => (\n <div key={meeting.id} className=\"flex items-center justify-between rounded border p-3\">\n <div>\n <p className=\"text-sm font-medium\">{meeting.title}</p>\n <p className=\"text-xs text-text-secondary\">Hosted by {meeting.host}</p>\n </div>\n <div className=\"flex items-center gap-3\">\n <span className=\"text-xs text-text-secondary\">{meeting.time}</span>\n <Badge variant=\"outline\" className=\"text-[10px]\">\n {meeting.duration}\n </Badge>\n <span className=\"flex items-center gap-1 text-xs\">\n <Users className=\"h-3 w-3\" />\n {meeting.participants}\n </span>\n {meeting.recurring && (\n <Badge variant=\"secondary\" className=\"text-[10px]\">\n recurring\n </Badge>\n )}\n <Button size=\"sm\" className=\"h-7 text-xs\">\n <Video className=\"mr-1 h-3 w-3\" />\n Join\n </Button>\n </div>\n </div>\n ))}\n </CardContent>\n </Card>\n\n <Card>\n <CardHeader>\n <CardTitle>Recent Recordings</CardTitle>\n </CardHeader>\n <CardContent className=\"space-y-3\">\n {recentRecordings.map((recording) => (\n <div\n key={recording.id}\n className=\"flex items-center justify-between rounded border p-3\"\n >\n <div>\n <p className=\"text-sm font-medium\">{recording.title}</p>\n <p className=\"text-xs text-text-secondary\">\n {recording.date} · {recording.duration} · {recording.size}\n </p>\n </div>\n <Button variant=\"outline\" size=\"sm\" className=\"h-7 text-xs\">\n Watch\n </Button>\n </div>\n ))}\n </CardContent>\n </Card>\n </div>\n );\n}\n"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"CommunicationsVideoCallsPagePage.js","names":[],"sources":["../../../src/crewfoundry/pages/CommunicationsVideoCallsPagePage.tsx"],"sourcesContent":["import { useMemo } from 'react';\nimport {\n Badge,\n Button,\n Card,\n CardContent,\n CardHeader,\n CardTitle,\n GlassCard,\n GradientText,\n} from '@burdenoff/fe-libs/ui';\nimport { Calendar, Clock, Monitor, Users, Video } from 'lucide-react';\nimport { useCrewFoundryStore } from '../store/crewfoundryStore';\n\ntype Meeting = {\n id: string;\n title: string;\n host: string;\n time: string;\n duration: string;\n participants: number;\n recurring: boolean;\n};\n\ntype Recording = {\n id: string;\n title: string;\n date: string;\n duration: string;\n size: string;\n};\n\nconst formatMeetingDuration = (minutes: number): string => `${Math.max(minutes, 15)} min`;\n\nconst formatRecordingDuration = (minutes: number): string => {\n const safeMinutes = Math.max(minutes, 1);\n const mm = String(safeMinutes).padStart(2, '0');\n const ss = String((safeMinutes * 7) % 60).padStart(2, '0');\n return `${mm}:${ss}`;\n};\n\nconst formatDate = (value: string): string => {\n const parsed = new Date(value);\n if (Number.isNaN(parsed.getTime())) {\n return 'Upcoming';\n }\n return parsed.toLocaleDateString();\n};\n\nexport function CommunicationsVideoCallsPagePage() {\n const { teams, interviews, announcements } = useCrewFoundryStore();\n\n const upcomingMeetings = useMemo<Meeting[]>(() => {\n const teamMeetings = teams.slice(0, 6).map((team, index) => ({\n id: `team-${team.id}`,\n title: `${team.name} Sync`,\n host: team.leadName,\n time: formatDate(team.createdAt),\n duration: formatMeetingDuration(15 + index * 10),\n participants: Math.max(team.memberCount, 2),\n recurring: index % 2 === 0,\n }));\n\n const interviewMeetings = interviews.slice(0, 4).map((interview) => ({\n id: `interview-${interview.id}`,\n title: `Interview · ${interview.candidateName}`,\n host: interview.interviewerName,\n time: formatDate(interview.date),\n duration: formatMeetingDuration(Number.parseInt(interview.time.split(':')[0] || '30', 10)),\n participants: 3,\n recurring: false,\n }));\n\n return [...teamMeetings, ...interviewMeetings];\n }, [interviews, teams]);\n\n const recentRecordings = useMemo<Recording[]>(() => {\n const source = announcements.slice(0, 6);\n return source.map((announcement) => {\n const durationMinutes = Math.max(12, Math.round(announcement.content.length / 40));\n return {\n id: `recording-${announcement.id}`,\n title: `${announcement.title} recording`,\n date: formatDate(announcement.createdAt),\n duration: formatRecordingDuration(durationMinutes),\n size: `${(durationMinutes / 10).toFixed(1)} GB`,\n };\n });\n }, [announcements]);\n\n const averageDurationMinutes = upcomingMeetings.length\n ? Math.round(\n upcomingMeetings\n .map((meeting) => Number.parseInt(meeting.duration.split(' ')[0], 10))\n .reduce((total, value) => total + value, 0) / upcomingMeetings.length\n )\n : 0;\n\n return (\n <div className=\"space-y-6 p-6\">\n <div className=\"flex items-center justify-between\">\n <div>\n <h1 className=\"text-2xl font-semibold\">\n <GradientText>Video Calls</GradientText>\n </h1>\n <p className=\"text-sm text-text-secondary\">Video meetings and recordings</p>\n </div>\n <div className=\"flex gap-2\">\n <Button variant=\"outline\" size=\"sm\">\n <Calendar className=\"mr-1 h-4 w-4\" />\n Schedule\n </Button>\n <Button size=\"sm\">\n <Video className=\"mr-1 h-4 w-4\" />\n Start Meeting\n </Button>\n </div>\n </div>\n\n <div className=\"grid gap-4 md:grid-cols-3\">\n <GlassCard treatment=\"metric\" className=\"border-border-seam\">\n <CardHeader className=\"flex flex-row items-center justify-between space-y-0 pb-2\">\n <CardTitle className=\"text-sm font-medium\">Upcoming</CardTitle>\n <Calendar className=\"h-4 w-4 text-status-info-text\" />\n </CardHeader>\n <CardContent>\n <div className=\"text-2xl font-bold tabular-nums\">{upcomingMeetings.length}</div>\n <p className=\"text-xs text-text-secondary\">meetings scheduled</p>\n </CardContent>\n </GlassCard>\n <GlassCard treatment=\"metric\" className=\"border-border-seam\">\n <CardHeader className=\"flex flex-row items-center justify-between space-y-0 pb-2\">\n <CardTitle className=\"text-sm font-medium\">Recordings</CardTitle>\n <Monitor className=\"h-4 w-4 text-text-secondary\" />\n </CardHeader>\n <CardContent>\n <div className=\"text-2xl font-bold tabular-nums\">{recentRecordings.length}</div>\n <p className=\"text-xs text-text-secondary\">available</p>\n </CardContent>\n </GlassCard>\n <GlassCard treatment=\"metric\" className=\"border-border-seam\">\n <CardHeader className=\"flex flex-row items-center justify-between space-y-0 pb-2\">\n <CardTitle className=\"text-sm font-medium\">Avg Duration</CardTitle>\n <Clock className=\"h-4 w-4 text-text-secondary\" />\n </CardHeader>\n <CardContent>\n <div className=\"text-2xl font-bold tabular-nums\">{averageDurationMinutes} min</div>\n </CardContent>\n </GlassCard>\n </div>\n\n <Card>\n <CardHeader>\n <CardTitle>Upcoming Meetings</CardTitle>\n </CardHeader>\n <CardContent className=\"space-y-3\">\n {upcomingMeetings.map((meeting) => (\n <div key={meeting.id} className=\"flex items-center justify-between rounded border p-3\">\n <div>\n <p className=\"text-sm font-medium\">{meeting.title}</p>\n <p className=\"text-xs text-text-secondary\">Hosted by {meeting.host}</p>\n </div>\n <div className=\"flex items-center gap-3\">\n <span className=\"text-xs text-text-secondary\">{meeting.time}</span>\n <Badge variant=\"outline\" className=\"text-[10px]\">\n {meeting.duration}\n </Badge>\n <span className=\"flex items-center gap-1 text-xs\">\n <Users className=\"h-3 w-3\" />\n {meeting.participants}\n </span>\n {meeting.recurring && (\n <Badge variant=\"secondary\" className=\"text-[10px]\">\n recurring\n </Badge>\n )}\n <Button size=\"sm\" className=\"h-7 text-xs\">\n <Video className=\"mr-1 h-3 w-3\" />\n Join\n </Button>\n </div>\n </div>\n ))}\n </CardContent>\n </Card>\n\n <Card>\n <CardHeader>\n <CardTitle>Recent Recordings</CardTitle>\n </CardHeader>\n <CardContent className=\"space-y-3\">\n {recentRecordings.map((recording) => (\n <div\n key={recording.id}\n className=\"flex items-center justify-between rounded border p-3\"\n >\n <div>\n <p className=\"text-sm font-medium\">{recording.title}</p>\n <p className=\"text-xs text-text-secondary\">\n {recording.date} · {recording.duration} · {recording.size}\n </p>\n </div>\n <Button variant=\"outline\" size=\"sm\" className=\"h-7 text-xs\">\n Watch\n </Button>\n </div>\n ))}\n </CardContent>\n </Card>\n </div>\n );\n}\n"],"mappings":"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"}
|
|
@@ -1,10 +1,10 @@
|
|
|
1
1
|
import { useCrewFoundryStore as e } from "../store/crewfoundryStore.js";
|
|
2
2
|
import { Building2 as t, DollarSign as n, FolderKanban as r, Plus as i } from "lucide-react";
|
|
3
3
|
import { jsx as a, jsxs as o } from "react/jsx-runtime";
|
|
4
|
-
import { Badge as s, Button as c, Card as l, CardContent as u, CardHeader as d, CardTitle as f } from "@burdenoff/fe-libs/ui";
|
|
4
|
+
import { Badge as s, Button as c, Card as l, CardContent as u, CardHeader as d, CardTitle as f, GlassCard as p, GradientText as m } from "@burdenoff/fe-libs/ui";
|
|
5
5
|
//#region src/crewfoundry/pages/CompanyClientManagementPagePage.tsx
|
|
6
|
-
function
|
|
7
|
-
let { clients:
|
|
6
|
+
function h() {
|
|
7
|
+
let { clients: h } = e(), g = h.reduce((e, t) => e + t.revenue, 0), _ = h.filter((e) => e.status === "active");
|
|
8
8
|
return /* @__PURE__ */ o("div", {
|
|
9
9
|
className: "space-y-6 p-6",
|
|
10
10
|
children: [
|
|
@@ -12,13 +12,13 @@ function p() {
|
|
|
12
12
|
className: "flex items-center justify-between",
|
|
13
13
|
children: [/* @__PURE__ */ o("div", { children: [/* @__PURE__ */ a("h1", {
|
|
14
14
|
className: "text-2xl font-semibold",
|
|
15
|
-
children: "Client Management"
|
|
15
|
+
children: /* @__PURE__ */ a(m, { children: "Client Management" })
|
|
16
16
|
}), /* @__PURE__ */ o("p", {
|
|
17
17
|
className: "text-sm text-text-secondary",
|
|
18
18
|
children: [
|
|
19
|
-
|
|
19
|
+
h.length,
|
|
20
20
|
" clients · $",
|
|
21
|
-
(
|
|
21
|
+
(g / 1e6).toFixed(1),
|
|
22
22
|
"M revenue"
|
|
23
23
|
]
|
|
24
24
|
})] }), /* @__PURE__ */ o(c, {
|
|
@@ -29,40 +29,52 @@ function p() {
|
|
|
29
29
|
/* @__PURE__ */ o("div", {
|
|
30
30
|
className: "grid gap-4 md:grid-cols-3",
|
|
31
31
|
children: [
|
|
32
|
-
/* @__PURE__ */ o(
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
32
|
+
/* @__PURE__ */ o(p, {
|
|
33
|
+
treatment: "metric",
|
|
34
|
+
className: "border-border-seam",
|
|
35
|
+
children: [/* @__PURE__ */ o(d, {
|
|
36
|
+
className: "flex flex-row items-center justify-between space-y-0 pb-2",
|
|
37
|
+
children: [/* @__PURE__ */ a(f, {
|
|
38
|
+
className: "text-sm font-medium",
|
|
39
|
+
children: "Active Clients"
|
|
40
|
+
}), /* @__PURE__ */ a(t, { className: "h-4 w-4 text-text-secondary" })]
|
|
41
|
+
}), /* @__PURE__ */ a(u, { children: /* @__PURE__ */ a("div", {
|
|
42
|
+
className: "text-2xl font-bold tabular-nums",
|
|
43
|
+
children: _.length
|
|
44
|
+
}) })]
|
|
45
|
+
}),
|
|
46
|
+
/* @__PURE__ */ o(p, {
|
|
47
|
+
treatment: "metric",
|
|
48
|
+
className: "border-border-seam",
|
|
49
|
+
children: [/* @__PURE__ */ o(d, {
|
|
50
|
+
className: "flex flex-row items-center justify-between space-y-0 pb-2",
|
|
51
|
+
children: [/* @__PURE__ */ a(f, {
|
|
52
|
+
className: "text-sm font-medium",
|
|
53
|
+
children: "Total Revenue"
|
|
54
|
+
}), /* @__PURE__ */ a(n, { className: "h-4 w-4 text-text-secondary" })]
|
|
55
|
+
}), /* @__PURE__ */ a(u, { children: /* @__PURE__ */ o("div", {
|
|
56
|
+
className: "text-2xl font-bold tabular-nums",
|
|
57
|
+
children: [
|
|
58
|
+
"$",
|
|
59
|
+
(g / 1e6).toFixed(1),
|
|
60
|
+
"M"
|
|
61
|
+
]
|
|
62
|
+
}) })]
|
|
63
|
+
}),
|
|
64
|
+
/* @__PURE__ */ o(p, {
|
|
65
|
+
treatment: "metric",
|
|
66
|
+
className: "border-border-seam",
|
|
67
|
+
children: [/* @__PURE__ */ o(d, {
|
|
68
|
+
className: "flex flex-row items-center justify-between space-y-0 pb-2",
|
|
69
|
+
children: [/* @__PURE__ */ a(f, {
|
|
70
|
+
className: "text-sm font-medium",
|
|
71
|
+
children: "Total Projects"
|
|
72
|
+
}), /* @__PURE__ */ a(r, { className: "h-4 w-4 text-text-secondary" })]
|
|
73
|
+
}), /* @__PURE__ */ a(u, { children: /* @__PURE__ */ a("div", {
|
|
74
|
+
className: "text-2xl font-bold tabular-nums",
|
|
75
|
+
children: h.reduce((e, t) => e + t.projects, 0)
|
|
76
|
+
}) })]
|
|
77
|
+
})
|
|
66
78
|
]
|
|
67
79
|
}),
|
|
68
80
|
/* @__PURE__ */ o(l, { children: [/* @__PURE__ */ a(d, { children: /* @__PURE__ */ a(f, { children: "Client Portfolio" }) }), /* @__PURE__ */ o(u, { children: [/* @__PURE__ */ o("div", {
|
|
@@ -85,7 +97,7 @@ function p() {
|
|
|
85
97
|
children: "Status"
|
|
86
98
|
})
|
|
87
99
|
]
|
|
88
|
-
}),
|
|
100
|
+
}), h.map((e) => /* @__PURE__ */ o("div", {
|
|
89
101
|
className: "grid grid-cols-7 gap-2 py-2 border-b last:border-0 text-sm",
|
|
90
102
|
children: [
|
|
91
103
|
/* @__PURE__ */ a("span", {
|
|
@@ -133,6 +145,6 @@ function p() {
|
|
|
133
145
|
});
|
|
134
146
|
}
|
|
135
147
|
//#endregion
|
|
136
|
-
export {
|
|
148
|
+
export { h as CompanyClientManagementPagePage };
|
|
137
149
|
|
|
138
150
|
//# sourceMappingURL=CompanyClientManagementPagePage.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"CompanyClientManagementPagePage.js","names":[],"sources":["../../../src/crewfoundry/pages/CompanyClientManagementPagePage.tsx"],"sourcesContent":["import {\n Badge,\n Button,\n Card,\n CardContent,\n CardDescription,\n CardHeader,\n CardTitle,\n} from '@burdenoff/fe-libs/ui';\nimport { Building2, DollarSign, FolderKanban, Plus } from 'lucide-react';\nimport { useCrewFoundryStore } from '../store/crewfoundryStore';\n\nexport function CompanyClientManagementPagePage() {\n const { clients } = useCrewFoundryStore();\n const totalRevenue = clients.reduce((s, c) => s + c.revenue, 0);\n const activeClients = clients.filter((c) => c.status === 'active');\n\n return (\n <div className=\"space-y-6 p-6\">\n <div className=\"flex items-center justify-between\">\n <div>\n <h1 className=\"text-2xl font-semibold\">Client Management</h1>\n <p className=\"text-sm text-text-secondary\">\n {clients.length} clients · ${(totalRevenue / 1000000).toFixed(1)}M revenue\n </p>\n </div>\n <Button size=\"sm\">\n <Plus className=\"h-4 w-4 mr-1\" />\n Add Client\n </Button>\n </div>\n <div className=\"grid gap-4 md:grid-cols-3\">\n <
|
|
1
|
+
{"version":3,"file":"CompanyClientManagementPagePage.js","names":[],"sources":["../../../src/crewfoundry/pages/CompanyClientManagementPagePage.tsx"],"sourcesContent":["import {\n Badge,\n Button,\n Card,\n CardContent,\n CardDescription,\n CardHeader,\n CardTitle,\n GlassCard,\n GradientText,\n} from '@burdenoff/fe-libs/ui';\nimport { Building2, DollarSign, FolderKanban, Plus } from 'lucide-react';\nimport { useCrewFoundryStore } from '../store/crewfoundryStore';\n\nexport function CompanyClientManagementPagePage() {\n const { clients } = useCrewFoundryStore();\n const totalRevenue = clients.reduce((s, c) => s + c.revenue, 0);\n const activeClients = clients.filter((c) => c.status === 'active');\n\n return (\n <div className=\"space-y-6 p-6\">\n <div className=\"flex items-center justify-between\">\n <div>\n <h1 className=\"text-2xl font-semibold\">\n <GradientText>Client Management</GradientText>\n </h1>\n <p className=\"text-sm text-text-secondary\">\n {clients.length} clients · ${(totalRevenue / 1000000).toFixed(1)}M revenue\n </p>\n </div>\n <Button size=\"sm\">\n <Plus className=\"h-4 w-4 mr-1\" />\n Add Client\n </Button>\n </div>\n <div className=\"grid gap-4 md:grid-cols-3\">\n <GlassCard treatment=\"metric\" className=\"border-border-seam\">\n <CardHeader className=\"flex flex-row items-center justify-between space-y-0 pb-2\">\n <CardTitle className=\"text-sm font-medium\">Active Clients</CardTitle>\n <Building2 className=\"h-4 w-4 text-text-secondary\" />\n </CardHeader>\n <CardContent>\n <div className=\"text-2xl font-bold tabular-nums\">{activeClients.length}</div>\n </CardContent>\n </GlassCard>\n <GlassCard treatment=\"metric\" className=\"border-border-seam\">\n <CardHeader className=\"flex flex-row items-center justify-between space-y-0 pb-2\">\n <CardTitle className=\"text-sm font-medium\">Total Revenue</CardTitle>\n <DollarSign className=\"h-4 w-4 text-text-secondary\" />\n </CardHeader>\n <CardContent>\n <div className=\"text-2xl font-bold tabular-nums\">\n ${(totalRevenue / 1000000).toFixed(1)}M\n </div>\n </CardContent>\n </GlassCard>\n <GlassCard treatment=\"metric\" className=\"border-border-seam\">\n <CardHeader className=\"flex flex-row items-center justify-between space-y-0 pb-2\">\n <CardTitle className=\"text-sm font-medium\">Total Projects</CardTitle>\n <FolderKanban className=\"h-4 w-4 text-text-secondary\" />\n </CardHeader>\n <CardContent>\n <div className=\"text-2xl font-bold tabular-nums\">\n {clients.reduce((s, c) => s + c.projects, 0)}\n </div>\n </CardContent>\n </GlassCard>\n </div>\n <Card>\n <CardHeader>\n <CardTitle>Client Portfolio</CardTitle>\n </CardHeader>\n <CardContent>\n <div className=\"grid grid-cols-7 gap-2 text-xs font-medium text-text-secondary border-b pb-2 mb-2\">\n <span>Client</span>\n <span>Industry</span>\n <span>Contact</span>\n <span className=\"text-right\">Revenue</span>\n <span className=\"text-right\">Projects</span>\n <span>Since</span>\n <span className=\"text-center\">Status</span>\n </div>\n {clients.map((c) => (\n <div key={c.id} className=\"grid grid-cols-7 gap-2 py-2 border-b last:border-0 text-sm\">\n <span className=\"font-medium\">{c.name}</span>\n <span className=\"text-text-secondary\">{c.industry}</span>\n <div>\n <p className=\"text-xs\">{c.contactPerson}</p>\n <p className=\"text-xs text-text-secondary\">{c.email}</p>\n </div>\n <span className=\"text-right\">${(c.revenue / 1000).toFixed(0)}K</span>\n <span className=\"text-right\">{c.projects}</span>\n <span className=\"text-text-secondary\">{c.since}</span>\n <div className=\"text-center\">\n <Badge\n variant={\n c.status === 'active'\n ? 'default'\n : c.status === 'prospect'\n ? 'secondary'\n : 'destructive'\n }\n className=\"text-[10px]\"\n >\n {c.status}\n </Badge>\n </div>\n </div>\n ))}\n </CardContent>\n </Card>\n </div>\n );\n}\n"],"mappings":"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"}
|