Skip to content

Commit

Permalink
Improve design of abacard
Browse files Browse the repository at this point in the history
  • Loading branch information
falbru committed Jan 29, 2025
1 parent 10ea8f5 commit cec4e1e
Show file tree
Hide file tree
Showing 2 changed files with 67 additions and 36 deletions.
4 changes: 0 additions & 4 deletions app/components/UserValidator/Validator.module.css
Original file line number Diff line number Diff line change
@@ -1,9 +1,5 @@
@import url('~app/styles/variables.css');

.scannerModal {
text-align: center;
}

.scannerButton {
margin-bottom: var(--spacing-md);
}
99 changes: 67 additions & 32 deletions app/components/UserValidator/index.tsx
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import { Button, Flex, Icon, Modal } from '@webkom/lego-bricks';
import { get, debounce } from 'lodash';
import { ScanQrCode } from 'lucide-react';
import { useCallback, useRef, useState } from 'react';
import { Check, ScanQrCode, X } from 'lucide-react';
import { ReactNode, useCallback, useRef, useState } from 'react';
import { QrReader } from 'react-qr-reader';
import { useNavigate, useParams } from 'react-router-dom';
import { autocomplete } from 'app/actions/SearchActions';
Expand All @@ -16,6 +16,7 @@ import { useAppDispatch, useAppSelector } from 'app/store/hooks';
import styles from './Validator.module.css';
import type { SearchUser } from 'app/store/models/User';
import type { Required } from 'utility-types';
import TextWithIcon from 'app/components/TextWithIcon';

type UserWithUsername = Required<Partial<UserSearchResult>, 'username'>;

Expand All @@ -25,7 +26,9 @@ type Res = {

type ScanResult = {
message: string;
count: number;
icon: ReactNode;
color: string;
count?: number;
};

type Props = {
Expand Down Expand Up @@ -76,16 +79,19 @@ const Validator = ({ handleSelect, validateAbakusGroup }: Props) => {
* @param {string} result The newest scan
* @returns void
*/
const addScanResult = (result: string) => {
const addScanResult = (result: ScanResult) => {
setScanResults((prevScanResults) => {
if (
prevScanResults.length !== 0 &&
prevScanResults[0].message === result
prevScanResults[0].message === result.message
) {
prevScanResults[0].count++;
prevScanResults[0].count = (prevScanResults[0].count ?? 0) + 1;
return prevScanResults;
}
return [{ message: result, count: 1 }, ...prevScanResults].slice(0, 5);
return [
{ ...result, count: result.count ?? 1 },
...prevScanResults,
].slice(0, 5);
});
};

Expand All @@ -97,15 +103,15 @@ const Validator = ({ handleSelect, validateAbakusGroup }: Props) => {
* @returns void
*/
const displayResult = useCallback(
(result: string, success = false) => {
(result: ScanResult, success = false) => {
if (showScanner) {
addScanResult(result);
return;
}
if (success) {
showSuccessModal(result);
showSuccessModal(result.message);
} else {
dispatch(addToast({ message: result }));
dispatch(addToast({ message: result.message }));
}
},
[showScanner, dispatch],
Expand All @@ -125,29 +131,56 @@ const Validator = ({ handleSelect, validateAbakusGroup }: Props) => {
if (!validateAbakusGroup || (isUser(user) && user.isAbakusMember)) {
const sound = new window.Audio(goodSound);
sound.play();
if (validateAbakusGroup) {
displayResult(`${username} er Abakus-medlem`, true);
} else {
displayResult(`${username} ble registrert`, true);
}

displayResult(
{
message: validateAbakusGroup
? `${username} er Abakus-medlem`
: `${username} ble registrert`,
icon: <Check />,
color: 'var(--success-color)',
},
true,
);
} else {
displayResult(`${username} er ikke medlem av Abakus!`);
displayResult(
{
message: `${username} er ikke medlem av Abakus`,
icon: <X />,
color: 'var(--danger-color)',
},
false,
);
}
},
(err) => {
setIsLoading(false);
const payload = get(err, 'payload.response.jsonData');
if (payload && payload.errorCode === 'not_registered') {
displayResult(`${username} er ikke påmeldt arrangementet`);
} else if (payload && payload.errorCode === 'already_present') {
displayResult(`${username} er allerede registrert`);
} else if (payload && payload.detail === 'Not found.') {
displayResult(`Brukeren finnes ikke!\nBrukernavn: ${username}`);
} else {
displayResult(
`Det oppsto en uventet feil: ${JSON.stringify(payload || err)}`,
);
}

const errorMessages = {
not_registered: `${username} er ikke påmeldt arrangementet`,
already_present: `${username} er allerede registrert`,
unregistered: `${username} har meldt seg av`,
not_properly_registered: `${username} sin påmelding er i limbo. Ta kontakt med Webkom`,
waitlisted: `${username} er på venteliste`,
late_or_absent: `${username} har blitt registrert som ikke tilstede`,
missing_payment: `${username} har ikke betalt`,
no_user: `Brukeren finnes ikke! Brukernavn: ${username}`,
};

const errorMessage =
payload && payload.errorCode in errorMessages
? errorMessages[payload.errorCode]
: `Det oppsto en uventet feil: ${JSON.stringify(payload || err)}`;

displayResult(
{
message: errorMessage,
icon: <X />,
color: 'var(--danger-color)',
},
false,
);
},
)
.then(() => {
Expand Down Expand Up @@ -182,7 +215,6 @@ const Validator = ({ handleSelect, validateAbakusGroup }: Props) => {
</Flex>
</Modal>
<Modal
contentClassName={styles.scannerModal}
isOpen={showScanner}
onOpenChange={(open) => {
if (!open) {
Expand All @@ -208,10 +240,13 @@ const Validator = ({ handleSelect, validateAbakusGroup }: Props) => {
/>
<h3>Nylig scannede ABA-IDer</h3>
<Flex column justifyContent="center" gap={5}>
{scanResults.map(({ message, count }) => (
<span key={message + count}>
{message} (x{count})
</span>
{scanResults.map(({ message, color, icon, count }) => (
<div style={{ color }} key={message + count}>
<TextWithIcon
iconNode={icon}
content={`${message} (x${count ?? 1})`}
/>
</div>
))}
{scanResults.length === 0 && (
<span className="secondaryFontColor">
Expand Down

0 comments on commit cec4e1e

Please sign in to comment.