Skip to content

Commit

Permalink
features: allows filtering by tag in inventory panel
Browse files Browse the repository at this point in the history
  • Loading branch information
andresgnlez committed Jan 18, 2024
1 parent 4c0e849 commit a4fcf17
Show file tree
Hide file tree
Showing 9 changed files with 90 additions and 18 deletions.
11 changes: 8 additions & 3 deletions app/layout/project/sidebar/header/title/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -190,8 +190,13 @@ const EditableTitle = ({
<FieldRFF<FormFields['description']> name="description">
{({ input }) => (
<div className="relative w-full">
<div className="relative">
<div>
<div
className={cn({
relative: true,
'pb-4': input.value?.length,
})}
>
<>
<p className="invisible absolute left-0 top-0 font-heading text-sm font-normal text-white">
{input.value}
</p>
Expand All @@ -218,7 +223,7 @@ const EditableTitle = ({
}
}}
/>
</div>
</>
<p className="line-clamp-3 font-heading text-sm font-normal text-white">
{input.value}
</p>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@ const InventoryTable = ({
onToggleSeeOnMap,
onSelectRow,
onSelectAll,
onSelectTag,
ActionsComponent,
}: InventoryTable): JSX.Element => {
const noData = !loading && data?.length === 0;
Expand Down Expand Up @@ -77,6 +78,7 @@ const InventoryTable = ({
selectedIds={selectedIds}
onSelectRow={onSelectRow}
onToggleSeeOnMap={onToggleSeeOnMap}
onSelectTag={onSelectTag}
ActionsComponent={ActionsComponent}
/>
))}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ const RowItem = ({
selectedIds,
onSelectRow,
onToggleSeeOnMap,
onSelectTag,
ActionsComponent,
}: RowItem) => {
const { id, name, scenarios, tag, isVisibleOnMap, isCustom } = item;
Expand Down Expand Up @@ -60,9 +61,16 @@ const RowItem = ({
{tag && (
<td className="w-28 px-6 pb-2 pt-5 text-xs">
<div className="flex justify-center">
<span className="whitespace-nowrap rounded-full bg-yellow-700 bg-opacity-10 px-2 py-1 text-yellow-700">
<button
type="button"
className={cn({
'whitespace-nowrap rounded-full bg-yellow-600 px-2 py-1 text-gray-900': true,
'pointer-events-auto': !onSelectTag,
})}
onClick={() => onSelectTag?.(tag)}
>
{tag}
</span>
</button>
</div>
</td>
)}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ export type RowItem = {
selectedIds: string[];
onSelectRow: (evt: ChangeEvent<HTMLInputElement>) => void;
onToggleSeeOnMap: (id: string) => void;
onSelectTag?: (tag: DataItem['tag']) => void;
ActionsComponent: ({
item,
onDismissMenu,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -27,5 +27,6 @@ export type InventoryTable = {
onToggleSeeOnMap: (id: string) => void;
onSelectRow: (evt: ChangeEvent<HTMLInputElement>) => void;
onSelectAll: (evt: ChangeEvent<HTMLInputElement>) => void;
onSelectTag?: (tag: DataItem['tag']) => void;
ActionsComponent: ({ item }) => JSX.Element;
};
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { useCallback, useState, ChangeEvent, useEffect } from 'react';
import { useCallback, useState, ChangeEvent, useEffect, ComponentProps, useMemo } from 'react';

import { useRouter } from 'next/router';

Expand All @@ -9,12 +9,17 @@ import {
setLayerSettings,
} from 'store/slices/projects/[id]';

import Fuse from 'fuse.js';

import { useAllFeatures, useColorFeatures } from 'hooks/features';

import Icon from 'components/icon';
import ActionsMenu from 'layout/project/sidebar/project/inventory-panel/features/actions-menu';
import FeaturesBulkActionMenu from 'layout/project/sidebar/project/inventory-panel/features/bulk-action-menu';
import { Feature } from 'types/api/feature';

import CLOSE_SVG from 'svgs/ui/close.svg?sprite';

import InventoryTable, { type DataItem } from '../components/inventory-table';

const FEATURES_TABLE_COLUMNS = [
Expand All @@ -31,6 +36,7 @@ const FEATURES_TABLE_COLUMNS = [

const InventoryPanelFeatures = ({ noData: noDataMessage }: { noData: string }): JSX.Element => {
const dispatch = useAppDispatch();
const [selectedTag, setSelectedTag] = useState<string | null>(null);

const {
selectedFeatures: visibleFeatures,
Expand Down Expand Up @@ -166,12 +172,39 @@ const InventoryPanelFeatures = ({ noData: noDataMessage }: { noData: string }):
[dispatch, visibleFeatures, allFeaturesQuery.data, selectedContinuousFeatures]
);

const handleSelectTag = useCallback(
(tag: Parameters<ComponentProps<typeof InventoryTable>['onSelectTag']>[0]) => {
setSelectedTag(tag);
setSelectedFeaturesIds([]);
},
[]
);

const clearTag = useCallback(() => {
setSelectedTag(null);
}, []);

const displayBulkActions = selectedFeaturesIds.length > 0;

const data: DataItem[] = allFeaturesQuery.data?.map((feature) => ({
...feature,
isVisibleOnMap: layerSettings[feature.id]?.visibility ?? false,
}));
const data: DataItem[] = useMemo(() => {
let d = allFeaturesQuery.data?.map((feature) => ({
...feature,
isVisibleOnMap: layerSettings[feature.id]?.visibility ?? false,
}));

if (selectedTag) {
const fuse = new Fuse(d, {
keys: ['tag'],
threshold: 0.25,
});

d = fuse.search(selectedTag).map((f) => {
return f.item;
});
}

return d;
}, [allFeaturesQuery.data, layerSettings, selectedTag]);

useEffect(() => {
if (allFeaturesQuery.isRefetching) {
Expand All @@ -180,7 +213,29 @@ const InventoryPanelFeatures = ({ noData: noDataMessage }: { noData: string }):
}, [allFeaturesQuery.isRefetching]);

return (
<div className="flex flex-col space-y-6 overflow-hidden">
<div className="flex flex-col space-y-4 overflow-hidden">
{selectedTag && (
<span className="space-x-2 text-xs">
<span>Filtering by: </span>
<button
type="button"
className="inline-block rounded-2xl bg-yellow-500 bg-opacity-20 px-3 py-0.5 text-yellow-500 transition-colors hover:bg-yellow-600 hover:text-gray-900"
onClick={clearTag}
>
{selectedTag}
</button>
<button
type="button"
className="group inline-flex justify-center rounded-full border border-gray-700 p-1.5 transition-colors hover:border-white"
onClick={clearTag}
>
<Icon
icon={CLOSE_SVG}
className="inline-block h-2 w-2 text-white transition-colors group-hover:text-white"
/>
</button>
</span>
)}
<div className="h-full overflow-hidden">
<InventoryTable
loading={allFeaturesQuery.isFetching}
Expand All @@ -193,6 +248,7 @@ const InventoryPanelFeatures = ({ noData: noDataMessage }: { noData: string }):
onSelectAll={handleSelectAll}
onSelectRow={handleSelectFeature}
onToggleSeeOnMap={toggleSeeOnMap}
onSelectTag={handleSelectTag}
ActionsComponent={ActionsMenu}
/>
</div>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -62,7 +62,7 @@ const InventoryPanel = (): JSX.Element => {
} = panel;

return (
<Section className="relative flex flex-col space-y-2 overflow-hidden">
<Section className="relative flex flex-col space-y-4 overflow-hidden">
<header className="flex items-center justify-between">
<div className="space-y-1">
<span className="text-xs font-semibold text-blue-500">Inventory Panel</span>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -85,7 +85,6 @@ const TargetAndSPFFeatures = (): JSX.Element => {

const targetedFeatures = useMemo(() => {
let parsedData = [];
console.log({ featureValues });
selectedFeaturesQuery.data?.forEach((feature) => {
if (feature.splitFeaturesSelected?.length > 0) {
const featureMetadata = allFeaturesQuery.data?.find(({ id }) => id === feature.id);
Expand Down Expand Up @@ -457,24 +456,24 @@ const TargetAndSPFFeatures = (): JSX.Element => {
/>
{filters.type && (
<div className="flex items-center space-x-2 text-xs">
<span className=" space-x-3">
<span className="space-x-2">
<span>Filtering by: </span>
<button
type="button"
className="inline-block rounded-2xl bg-yellow-500/10 px-3 py-0.5 text-yellow-500 transition-colors hover:bg-yellow-500 hover:text-gray-900"
className="inline-block rounded-2xl bg-yellow-500 bg-opacity-20 px-3 py-0.5 text-yellow-500 transition-colors hover:bg-yellow-600 hover:text-gray-900"
onClick={() => handleTagFilter(null)}
>
{filters.type}
</button>
</span>
<button
type="button"
className="group inline-flex justify-center rounded-full border border-gray-400 p-1 transition-colors hover:border-transparent"
className="group inline-flex justify-center rounded-full border border-gray-700 p-1.5 transition-colors hover:border-white"
onClick={() => handleTagFilter(null)}
>
<Icon
icon={CLOSE_SVG}
className="inline-block h-2 w-2 text-gray-400 transition-colors group-hover:text-white"
className="inline-block h-2 w-2 text-white transition-colors group-hover:text-white"
/>
</button>
</div>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -95,7 +95,7 @@ const RowItem = ({
<div className="flex justify-center">
<button
type="button"
className="cursor-pointer whitespace-nowrap rounded-full bg-yellow-700 bg-opacity-10 px-2 py-1 text-yellow-700"
className="cursor-pointer whitespace-nowrap rounded-full bg-yellow-600 px-2 py-1 text-gray-900"
onClick={() => {
onClickTag(type);
}}
Expand Down

0 comments on commit a4fcf17

Please sign in to comment.