11import { Menu , MenuDivider , MenuItem , SubMenu } from '@szhsin/react-menu'
2- import { useCallback , useMemo } from 'react'
2+ import { memo , useCallback , useMemo } from 'react'
33import { AiOutlineCode } from 'react-icons/ai'
44import { BsBoxArrowInUpRight } from 'react-icons/bs'
5+ import { FiFilter } from 'react-icons/fi'
56import { GoGear } from 'react-icons/go'
67import { IoTrashBinOutline } from 'react-icons/io5'
78import { LiaSortSolid } from 'react-icons/lia'
89import { MdDateRange } from 'react-icons/md'
10+ import { useMediaQuery } from 'react-responsive'
911import { ref } from 'src/config'
1012import { useUserPreferences } from 'src/stores/preferences'
13+ import { useShallow } from 'zustand/shallow'
1114import { MY_LANGUAGES_OPTION } from '../config'
1215
1316type SortOption = { label : string ; value : string ; icon ?: React . ReactNode }
@@ -27,7 +30,7 @@ type CardSettingsProps = {
2730const DEFAULT_SORT_OPTIONS = [ { label : 'Newest' , value : 'published_at' , icon : < MdDateRange /> } ]
2831const SPECIAL_LABELS = [ 'global' , MY_LANGUAGES_OPTION . label . toLowerCase ( ) ]
2932
30- export const CardSettings = ( {
33+ const CardSettings = ( {
3134 id,
3235 url,
3336 sortBy,
@@ -38,30 +41,34 @@ export const CardSettings = ({
3841 customStartMenuItems,
3942 sortOptions,
4043} : CardSettingsProps ) => {
41- const userSelectedTags = useUserPreferences ( ( state ) => state . userSelectedTags )
42- const openLinksNewTab = useUserPreferences ( ( state ) => state . openLinksNewTab )
43- const removeCard = useUserPreferences ( ( state ) => state . removeCard )
44- const setCardSettings = useUserPreferences ( ( state ) => state . setCardSettings )
45- const cardSettings = useUserPreferences ( ( state ) => state . cardsSettings [ id ] )
44+ const { userSelectedTags, openLinksNewTab, removeCard, setCardSettings, cardSettings } =
45+ useUserPreferences (
46+ useShallow ( ( state ) => ( {
47+ userSelectedTags : state . userSelectedTags ,
48+ openLinksNewTab : state . openLinksNewTab ,
49+ removeCard : state . removeCard ,
50+ setCardSettings : state . setCardSettings ,
51+ cardSettings : state . cardsSettings ?. [ id ] ,
52+ } ) )
53+ )
4654
4755 const userTagsMemo = useMemo ( ( ) => {
48- const newTags = userSelectedTags . sort ( ( a , b ) => a . label . localeCompare ( b . label ) )
49- let tags = [ ...newTags ]
50- if ( globalTag ) {
51- tags = [ ...tags , globalTag ]
52- }
53-
54- tags = [ ...tags , MY_LANGUAGES_OPTION ]
56+ const tags = [ ...userSelectedTags ]
57+ . sort ( ( a , b ) => a . label . localeCompare ( b . label ) )
58+ . concat ( globalTag ? [ globalTag ] : [ ] )
59+ . concat ( MY_LANGUAGES_OPTION )
5560 return tags
5661 } , [ userSelectedTags , globalTag ] )
5762
58- const resolvedSortOptions =
59- typeof sortOptions === 'function'
63+ const resolvedSortOptions = useMemo ( ( ) => {
64+ return typeof sortOptions === 'function'
6065 ? sortOptions ( DEFAULT_SORT_OPTIONS )
6166 : sortOptions || DEFAULT_SORT_OPTIONS
67+ } , [ sortOptions ] )
6268
6369 const onOpenSourceUrlClicked = useCallback ( ( ) => {
64- let link = `${ url } ?${ ref } `
70+ if ( ! url ) return
71+ const link = `${ url } ?${ ref } `
6572 window . open ( link , openLinksNewTab ? '_blank' : '_self' )
6673 } , [ url , openLinksNewTab ] )
6774
@@ -70,9 +77,12 @@ export const CardSettings = ({
7077 [ userTagsMemo ]
7178 )
7279
80+ const isMobile = useMediaQuery ( { maxWidth : 767 } )
81+ const menuIcon = isMobile ? < FiFilter /> : < GoGear />
82+
7383 return (
7484 < Menu
75- menuButton = { < GoGear /> }
85+ menuButton = { menuIcon }
7686 theming = "dark"
7787 portal = { true }
7888 className = { `menuItem` }
@@ -144,3 +154,5 @@ export const CardSettings = ({
144154 </ Menu >
145155 )
146156}
157+
158+ export const MemoizedCardSettings = memo ( CardSettings )
0 commit comments