From ab2c7a706d8f452a1585c577a0881426820dc2f5 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Tadeusz=20Miesi=C4=85c?= <tadeusz.miesiac@gmail.com>
Date: Thu, 12 Oct 2023 21:16:07 +0800
Subject: [PATCH] feat(results 2nd step): created dummy component for results

---
 Group.svg                                     |  4 ++
 src/assets/vectors/icons/Group.svg            |  5 ++
 .../Results/PinsList/PinsList.component.tsx   | 14 ++++
 .../Results/PinsList/PinsList.types.tsx       |  3 +
 .../PinsListItem/PinsListItem.component.tsx   | 13 ++++
 .../Results/PinsList/PinsListItem/index.ts    |  1 +
 .../Results/PinsList/index.ts                 |  1 +
 .../Results/Results.component.tsx             | 26 ++++++++
 .../SearchDrawerContent/Results/index.ts      |  1 +
 src/redux/store.ts                            |  1 +
 ...erHeadingBackwardButton.component.test.tsx | 65 +++++++++++++++++++
 .../DrawerHeadingBackwardButton.component.tsx | 53 +++++++++++++++
 .../DrawerHeadingBackwardButton/index.ts      |  1 +
 src/shared/Icon/Icon.component.tsx            |  2 +
 src/shared/Icon/Icons/PinOrance.tsx           | 20 ++++++
 src/types/iconTypes.ts                        |  3 +-
 src/utils/getReduxWrapperWithStore.tsx        | 61 +++++++++++++++++
 17 files changed, 273 insertions(+), 1 deletion(-)
 create mode 100644 Group.svg
 create mode 100644 src/assets/vectors/icons/Group.svg
 create mode 100644 src/components/Map/Drawer/SearchDrawerContent/Results/PinsList/PinsList.component.tsx
 create mode 100644 src/components/Map/Drawer/SearchDrawerContent/Results/PinsList/PinsList.types.tsx
 create mode 100644 src/components/Map/Drawer/SearchDrawerContent/Results/PinsList/PinsListItem/PinsListItem.component.tsx
 create mode 100644 src/components/Map/Drawer/SearchDrawerContent/Results/PinsList/PinsListItem/index.ts
 create mode 100644 src/components/Map/Drawer/SearchDrawerContent/Results/PinsList/index.ts
 create mode 100644 src/components/Map/Drawer/SearchDrawerContent/Results/Results.component.tsx
 create mode 100644 src/components/Map/Drawer/SearchDrawerContent/Results/index.ts
 create mode 100644 src/shared/DrawerHeadingBackwardButton/DrawerHeadingBackwardButton.component.test.tsx
 create mode 100644 src/shared/DrawerHeadingBackwardButton/DrawerHeadingBackwardButton.component.tsx
 create mode 100644 src/shared/DrawerHeadingBackwardButton/index.ts
 create mode 100644 src/shared/Icon/Icons/PinOrance.tsx
 create mode 100644 src/utils/getReduxWrapperWithStore.tsx

diff --git a/Group.svg b/Group.svg
new file mode 100644
index 00000000..6c9f4a0e
--- /dev/null
+++ b/Group.svg
@@ -0,0 +1,4 @@
+<svg width="18" height="24" viewBox="0 0 18 24" fill="none" xmlns="http://www.w3.org/2000/svg">
+<path d="M9 0C4.575 0 0 3.375 0 9C0 14.325 8.1 22.65 8.475 23.025C8.625 23.175 8.775 23.25 9 23.25C9.225 23.25 9.375 23.175 9.525 23.025C9.9 22.65 18 14.4 18 9C18 3.375 13.425 0 9 0ZM9 12C7.35 12 6 10.65 6 9C6 7.35 7.35 6 9 6C10.65 6 12 7.35 12 9C12 10.65 10.65 12 9 12Z" fill="#E17221"/>
+<circle cx="9.0002" cy="8.99922" r="4.8" fill="#E17221"/>
+</svg>
diff --git a/src/assets/vectors/icons/Group.svg b/src/assets/vectors/icons/Group.svg
new file mode 100644
index 00000000..6d6e49d3
--- /dev/null
+++ b/src/assets/vectors/icons/Group.svg
@@ -0,0 +1,5 @@
+<svg width="18" height="24" viewBox="0 0 18 24" fill="none" xmlns="http://www.w3.org/2000/svg">
+<path d="M9 0C4.575 0 0 3.375 0 9C0 14.325 8.1 22.65 8.475 23.025C8.625 23.175 8.775 23.25 9 23.25C9.225 23.25 9.375 23.175 9.525 23.025C9.9 22.65 18 14.4 18 9C18 3.375 13.425 0 9 0ZM9 12C7.35 12 6 10.65 6 9C6 7.35 7.35 6 9 6C10.65 6 12 7.35 12 9C12 10.65 10.65 12 9 12Z" fill="#E17221"/>
+<circle cx="9.0002" cy="8.99922" r="4.8" fill="#E17221"/>
+<path d="M8.846 15V7.344L7.22 8.322V7.332L8.846 6.36H9.74V15H8.846Z" fill="white"/>
+</svg>
diff --git a/src/components/Map/Drawer/SearchDrawerContent/Results/PinsList/PinsList.component.tsx b/src/components/Map/Drawer/SearchDrawerContent/Results/PinsList/PinsList.component.tsx
new file mode 100644
index 00000000..2678ebb1
--- /dev/null
+++ b/src/components/Map/Drawer/SearchDrawerContent/Results/PinsList/PinsList.component.tsx
@@ -0,0 +1,14 @@
+import { PinItem } from './PinsList.types';
+import { PinsListItem } from './PinsListItem';
+
+interface PinsListProps {
+  pinsList: PinItem[];
+}
+
+export const PinsList = ({ pinsList }: PinsListProps): JSX.Element => (
+  <ul className="px-6 py-2">
+    {pinsList.map(pin => (
+      <PinsListItem key={pin.name} name={pin.name} />
+    ))}
+  </ul>
+);
diff --git a/src/components/Map/Drawer/SearchDrawerContent/Results/PinsList/PinsList.types.tsx b/src/components/Map/Drawer/SearchDrawerContent/Results/PinsList/PinsList.types.tsx
new file mode 100644
index 00000000..ce02ca44
--- /dev/null
+++ b/src/components/Map/Drawer/SearchDrawerContent/Results/PinsList/PinsList.types.tsx
@@ -0,0 +1,3 @@
+export type PinItem = {
+  name: string;
+};
diff --git a/src/components/Map/Drawer/SearchDrawerContent/Results/PinsList/PinsListItem/PinsListItem.component.tsx b/src/components/Map/Drawer/SearchDrawerContent/Results/PinsList/PinsListItem/PinsListItem.component.tsx
new file mode 100644
index 00000000..754795e9
--- /dev/null
+++ b/src/components/Map/Drawer/SearchDrawerContent/Results/PinsList/PinsListItem/PinsListItem.component.tsx
@@ -0,0 +1,13 @@
+import { Icon } from '@/shared/Icon';
+
+interface PinsListItemProps {
+  name: string;
+}
+
+export const PinsListItem = ({ name }: PinsListItemProps): JSX.Element => (
+  <div className="flex flex-row justify-between pt-4">
+    <Icon name="pin-orange" className="mr-2 shrink-0" />
+    <p className="w-full text-left">{name}</p>
+    <Icon name="chevron-right" className="h-6 w-6 shrink-0" />
+  </div>
+);
diff --git a/src/components/Map/Drawer/SearchDrawerContent/Results/PinsList/PinsListItem/index.ts b/src/components/Map/Drawer/SearchDrawerContent/Results/PinsList/PinsListItem/index.ts
new file mode 100644
index 00000000..89b9aebc
--- /dev/null
+++ b/src/components/Map/Drawer/SearchDrawerContent/Results/PinsList/PinsListItem/index.ts
@@ -0,0 +1 @@
+export { PinsListItem } from './PinsListItem.component';
diff --git a/src/components/Map/Drawer/SearchDrawerContent/Results/PinsList/index.ts b/src/components/Map/Drawer/SearchDrawerContent/Results/PinsList/index.ts
new file mode 100644
index 00000000..c9d388b0
--- /dev/null
+++ b/src/components/Map/Drawer/SearchDrawerContent/Results/PinsList/index.ts
@@ -0,0 +1 @@
+export { PinsList } from './PinsList.component';
diff --git a/src/components/Map/Drawer/SearchDrawerContent/Results/Results.component.tsx b/src/components/Map/Drawer/SearchDrawerContent/Results/Results.component.tsx
new file mode 100644
index 00000000..c6f7edad
--- /dev/null
+++ b/src/components/Map/Drawer/SearchDrawerContent/Results/Results.component.tsx
@@ -0,0 +1,26 @@
+import { DrawerHeadingBackwardButton } from '@/shared/DrawerHeadingBackwardButton';
+import { PinsList } from './PinsList';
+
+const PINS_LIST = [
+  { name: 'Glyceraldehyde-3-phosphate dehydrogenase' },
+  { name: 'D-3-phosphoglycerate dehydrogenase' },
+  { name: 'Glutathione reductase, mitochondrial' },
+  { name: 'NADH dehydrogenase [ubiquinone] iron-sulfur protein 8, mitochondrial' },
+];
+
+export const Results = (): JSX.Element => {
+  const drugName = 'Aspirin';
+
+  const navigateToGroupedSearchResults = (): void => {};
+
+  return (
+    <div>
+      <DrawerHeadingBackwardButton
+        title="Drugs"
+        value={drugName}
+        backwardFunction={navigateToGroupedSearchResults}
+      />
+      <PinsList pinsList={PINS_LIST} />
+    </div>
+  );
+};
diff --git a/src/components/Map/Drawer/SearchDrawerContent/Results/index.ts b/src/components/Map/Drawer/SearchDrawerContent/Results/index.ts
new file mode 100644
index 00000000..0b2da8f8
--- /dev/null
+++ b/src/components/Map/Drawer/SearchDrawerContent/Results/index.ts
@@ -0,0 +1 @@
+export { Results } from './Results.component';
diff --git a/src/redux/store.ts b/src/redux/store.ts
index 1999d33f..f4251783 100644
--- a/src/redux/store.ts
+++ b/src/redux/store.ts
@@ -26,3 +26,4 @@ export const store = configureStore({
 export type RootState = ReturnType<typeof store.getState>;
 // Inferred type: {posts: PostsState, comments: CommentsState, users: UsersState}
 export type AppDispatch = typeof store.dispatch;
+export type StoreType = typeof store;
diff --git a/src/shared/DrawerHeadingBackwardButton/DrawerHeadingBackwardButton.component.test.tsx b/src/shared/DrawerHeadingBackwardButton/DrawerHeadingBackwardButton.component.test.tsx
new file mode 100644
index 00000000..c6ef266e
--- /dev/null
+++ b/src/shared/DrawerHeadingBackwardButton/DrawerHeadingBackwardButton.component.test.tsx
@@ -0,0 +1,65 @@
+import { StoreType } from '@/redux/store';
+import { InitialStoreState, getReduxWrapperWithStore } from '@/utils/getReduxWrapperWithStore';
+import { render, screen } from '@testing-library/react';
+import { DrawerHeadingBackwardButton } from './DrawerHeadingBackwardButton.component';
+
+const backwardFunction = jest.fn();
+
+const renderComponent = (
+  title: string,
+  value: string,
+  initialStoreState: InitialStoreState = {},
+): { store: StoreType } => {
+  const { Wrapper, store } = getReduxWrapperWithStore(initialStoreState);
+
+  return (
+    render(
+      <Wrapper>
+        <DrawerHeadingBackwardButton
+          title={title}
+          value={value}
+          backwardFunction={backwardFunction}
+        />
+      </Wrapper>,
+    ),
+    {
+      store,
+    }
+  );
+};
+
+describe('DrawerHeadingBackwardButton - component', () => {
+  beforeEach(() => {
+    backwardFunction.mockReset();
+  });
+
+  it('should render passed values', () => {
+    renderComponent('Title', 'value');
+
+    expect(screen.getByRole('back-button')).toBeInTheDocument();
+    expect(screen.getByText('Title:')).toBeInTheDocument();
+    expect(screen.getByText('value')).toBeInTheDocument();
+    expect(screen.getByRole('close-drawer-button')).toBeInTheDocument();
+  });
+
+  it('should call backward function on back button click', () => {
+    renderComponent('Title', 'value');
+
+    const backButton = screen.getByRole('back-button');
+    backButton.click();
+
+    expect(backwardFunction).toBeCalled();
+  });
+
+  it('should call class drawer on close button click', () => {
+    const { store } = renderComponent('Title', 'value', {
+      drawer: { open: true, drawerName: 'search' },
+    });
+    expect(store.getState().drawer.open).toBe(true);
+
+    const closeButton = screen.getByRole('close-drawer-button');
+    closeButton.click();
+
+    expect(store.getState().drawer.open).toBe(false);
+  });
+});
diff --git a/src/shared/DrawerHeadingBackwardButton/DrawerHeadingBackwardButton.component.tsx b/src/shared/DrawerHeadingBackwardButton/DrawerHeadingBackwardButton.component.tsx
new file mode 100644
index 00000000..d5b6394a
--- /dev/null
+++ b/src/shared/DrawerHeadingBackwardButton/DrawerHeadingBackwardButton.component.tsx
@@ -0,0 +1,53 @@
+import { useAppDispatch } from '@/redux/hooks/useAppDispatch';
+import { closeDrawer } from '@/redux/drawer/drawer.slice';
+import { IconButton } from '@/shared/IconButton';
+
+export const CLOSE_BUTTON_ROLE = 'close-drawer-button';
+export const BACK_BUTTON_ROLE = 'back-button';
+
+export interface DrawerHeadingBackwardButtonProps {
+  title: string;
+  value: string;
+  backwardFunction: () => void;
+}
+
+export const DrawerHeadingBackwardButton = ({
+  backwardFunction,
+  title,
+  value,
+}: DrawerHeadingBackwardButtonProps): JSX.Element => {
+  const dispatch = useAppDispatch();
+
+  const handleCloseDrawer = (): void => {
+    dispatch(closeDrawer());
+  };
+
+  const onBackwardClick = (): void => {
+    backwardFunction();
+  };
+
+  return (
+    <div className="flex items-center justify-between border-b border-b-divide pl-4 pr-5">
+      <div className="flex flex-row flex-nowrap items-center">
+        <IconButton
+          className="h-6 w-6 bg-white-pearl"
+          icon="chevron-left"
+          classNameIcon="fill-font-500 h-6 w-6"
+          onClick={onBackwardClick}
+          role={BACK_BUTTON_ROLE}
+        />
+        <div className="ml-2 py-8 text-xl">
+          <span className="font-normal">{title}: </span>
+          <span className="font-semibold">{value}</span>
+        </div>
+      </div>
+      <IconButton
+        className="bg-white-pearl"
+        classNameIcon="fill-font-500"
+        icon="close"
+        role={CLOSE_BUTTON_ROLE}
+        onClick={handleCloseDrawer}
+      />
+    </div>
+  );
+};
diff --git a/src/shared/DrawerHeadingBackwardButton/index.ts b/src/shared/DrawerHeadingBackwardButton/index.ts
new file mode 100644
index 00000000..b3fb4674
--- /dev/null
+++ b/src/shared/DrawerHeadingBackwardButton/index.ts
@@ -0,0 +1 @@
+export { DrawerHeadingBackwardButton } from './DrawerHeadingBackwardButton.component';
diff --git a/src/shared/Icon/Icon.component.tsx b/src/shared/Icon/Icon.component.tsx
index b23a3ad4..89943cae 100644
--- a/src/shared/Icon/Icon.component.tsx
+++ b/src/shared/Icon/Icon.component.tsx
@@ -12,6 +12,7 @@ import { PageIcon } from '@/shared/Icon/Icons/PageIcon';
 import { PluginIcon } from '@/shared/Icon/Icons/PluginIcon';
 import { PlusIcon } from '@/shared/Icon/Icons/PlusIcon';
 import { CloseIcon } from '@/shared/Icon/Icons/CloseIcon';
+import { PinOrange } from '@/shared/Icon/Icons/PinOrance';
 
 import type { IconTypes } from '@/types/iconTypes';
 
@@ -25,6 +26,7 @@ const icons = {
   'chevron-left': ChevronLeftIcon,
   'chevron-up': ChevronUpIcon,
   'chevron-down': ChevronDownIcon,
+  'pin-orange': PinOrange,
   plus: PlusIcon,
   arrow: ArrowIcon,
   dots: DotsIcon,
diff --git a/src/shared/Icon/Icons/PinOrance.tsx b/src/shared/Icon/Icons/PinOrance.tsx
new file mode 100644
index 00000000..d2adc98f
--- /dev/null
+++ b/src/shared/Icon/Icons/PinOrance.tsx
@@ -0,0 +1,20 @@
+interface PinOrangeProps {
+  className: string;
+}
+
+export const PinOrange = ({ className }: PinOrangeProps): JSX.Element => (
+  <svg
+    width="18"
+    height="24"
+    viewBox="0 0 18 24"
+    fill="none"
+    xmlns="http://www.w3.org/2000/svg"
+    className={className}
+  >
+    <path
+      d="M9 0C4.575 0 0 3.375 0 9C0 14.325 8.1 22.65 8.475 23.025C8.625 23.175 8.775 23.25 9 23.25C9.225 23.25 9.375 23.175 9.525 23.025C9.9 22.65 18 14.4 18 9C18 3.375 13.425 0 9 0ZM9 12C7.35 12 6 10.65 6 9C6 7.35 7.35 6 9 6C10.65 6 12 7.35 12 9C12 10.65 10.65 12 9 12Z"
+      fill="#E17221"
+    />
+    <circle cx="9.0002" cy="8.99922" r="4.8" fill="#E17221" />
+  </svg>
+);
diff --git a/src/types/iconTypes.ts b/src/types/iconTypes.ts
index 9b14f66b..f4db4670 100644
--- a/src/types/iconTypes.ts
+++ b/src/types/iconTypes.ts
@@ -12,4 +12,5 @@ export type IconTypes =
   | 'legend'
   | 'page'
   | 'plugin'
-  | 'close';
+  | 'close'
+  | 'pin-orange';
diff --git a/src/utils/getReduxWrapperWithStore.tsx b/src/utils/getReduxWrapperWithStore.tsx
new file mode 100644
index 00000000..1382f962
--- /dev/null
+++ b/src/utils/getReduxWrapperWithStore.tsx
@@ -0,0 +1,61 @@
+import { StoreType } from '@/redux/store';
+import { configureStore } from '@reduxjs/toolkit';
+import { Provider } from 'react-redux';
+import bioEntityContentsReducer from '@/redux/bioEntityContents/bioEntityContents.slice';
+import chemicalsReducer from '@/redux/chemicals/chemicals.slice';
+import drawerReducer from '@/redux/drawer/drawer.slice';
+import drugsReducer from '@/redux/drugs/drugs.slice';
+import mirnasReducer from '@/redux/mirnas/mirnas.slice';
+import projectReducer from '@/redux/project/project.slice';
+import searchReducer from '@/redux/search/search.slice';
+import modelsReducer from '@/redux/models/models.slice';
+import { SearchState } from '@/redux/search/search.types';
+import { ProjectState } from '@/redux/project/project.types';
+import { DrugsState } from '@/redux/drugs/drugs.types';
+import { MirnasState } from '@/redux/mirnas/mirnas.types';
+import { ChemicalsState } from '@/redux/chemicals/chemicals.types';
+import { BioEntityContentsState } from '@/redux/bioEntityContents/bioEntityContents.types';
+import { DrawerState } from '@/redux/drawer/drawer.types';
+
+interface WrapperProps {
+  children: React.ReactNode;
+}
+
+export type InitialStoreState = {
+  search?: SearchState;
+  project?: ProjectState;
+  drugs?: DrugsState;
+  mirnas?: MirnasState;
+  chemicals?: ChemicalsState;
+  bioEntityContents?: BioEntityContentsState;
+  drawer?: DrawerState;
+};
+
+type GetReduxWrapperUsingSliceReducer = (initialState?: InitialStoreState) => {
+  Wrapper: ({ children }: WrapperProps) => JSX.Element;
+  store: StoreType;
+};
+
+export const getReduxWrapperWithStore: GetReduxWrapperUsingSliceReducer = (
+  preloadedState: InitialStoreState = {},
+) => {
+  const testStore = configureStore({
+    reducer: {
+      search: searchReducer,
+      project: projectReducer,
+      drugs: drugsReducer,
+      mirnas: mirnasReducer,
+      chemicals: chemicalsReducer,
+      bioEntityContents: bioEntityContentsReducer,
+      drawer: drawerReducer,
+      models: modelsReducer,
+    },
+    preloadedState,
+  });
+
+  const Wrapper = ({ children }: WrapperProps): JSX.Element => (
+    <Provider store={testStore}>{children}</Provider>
+  );
+
+  return { Wrapper, store: testStore };
+};
-- 
GitLab