@ably/ui 17.8.0-dev.08f9f76c → 17.8.0-dev.7634f24d
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/core/Header.js.map +1 -1
- package/package.json +1 -1
package/core/Header.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../../src/core/Header.tsx"],"sourcesContent":["import React, { useState, useEffect, useRef, ReactNode, useMemo } from \"react\";\nimport Icon from \"./Icon\";\nimport cn from \"./utils/cn\";\nimport Logo from \"./Logo\";\nimport {\n componentMaxHeight,\n HEADER_BOTTOM_MARGIN,\n HEADER_HEIGHT,\n} from \"./utils/heights\";\nimport { HeaderLinks } from \"./Header/HeaderLinks\";\nimport { throttle } from \"es-toolkit/compat\";\nimport { Theme } from \"./styles/colors/types\";\nimport { COLLAPSE_TRIGGER_DISTANCE } from \"./Notice/component\";\n\nexport type ThemedScrollpoint = {\n id: string;\n className: string;\n};\n\n/**\n * Represents the state of the user session in the header.\n */\nexport type HeaderSessionState = {\n /**\n * Indicates if the user is signed in.\n */\n signedIn: boolean;\n\n /**\n * Information required to log out the user.\n */\n logOut: {\n /**\n * Token used for logging out.\n */\n token: string;\n\n /**\n * URL to log out the user.\n */\n href: string;\n };\n\n /**\n * Name of the user's account.\n */\n accountName: string;\n};\n\n/**\n * Props for the Header component.\n */\nexport type HeaderProps = {\n /**\n * Optional classnames to add to the header\n */\n className?: string;\n /**\n * Indicates if the notice banner is visible.\n */\n isNoticeVisible?: boolean;\n /**\n * Height of the notice banner in pixels.\n */\n noticeHeight?: number;\n /**\n * Optional search bar element.\n */\n searchBar?: ReactNode;\n\n /**\n * Optional search button element.\n */\n searchButton?: ReactNode;\n\n /**\n * URL for the logo link.\n */\n logoHref?: string;\n\n /**\n * Array of header links.\n */\n headerLinks?: {\n /**\n * URL for the link.\n */\n href: string;\n\n /**\n * Label for the link.\n */\n label: string;\n\n /**\n * Indicates if the link should open in a new tab.\n */\n external?: boolean;\n }[];\n\n /**\n * Optional classname for styling the header links container.\n */\n headerLinksClassName?: string;\n\n /**\n * Optional classname for styling the header center container.\n */\n headerCenterClassName?: string;\n\n /**\n * Optional desktop navigation element.\n */\n nav?: ReactNode;\n\n /**\n * Optional mobile navigation element.\n */\n mobileNav?: ReactNode;\n\n /**\n * State of the user session.\n */\n sessionState?: HeaderSessionState;\n\n /**\n * Array of themed scrollpoints. The header will change its appearance based on the scrollpoint in view.\n */\n themedScrollpoints?: ThemedScrollpoint[];\n\n /**\n * Visibility setting for the search button.\n * - \"all\": Visible on all devices.\n * - \"desktop\": Visible only on desktop devices.\n * - \"mobile\": Visible only on mobile devices.\n */\n searchButtonVisibility?: \"all\" | \"desktop\" | \"mobile\";\n\n /**\n * Optional location object to detect location changes.\n */\n location?: Location;\n\n /**\n * Optional badge text to display on the logo.\n */\n logoBadge?: string;\n};\n\nconst FLEXIBLE_DESKTOP_CLASSES = \"hidden md:flex flex-1 items-center h-full\";\n\n/**\n * Maximum width before the menu expanded into full width\n */\nconst MAX_MOBILE_MENU_WIDTH = \"560px\";\n\nconst Header: React.FC<HeaderProps> = ({\n className,\n isNoticeVisible = false,\n noticeHeight = 0,\n searchBar,\n searchButton,\n logoHref,\n headerLinks,\n headerLinksClassName,\n headerCenterClassName,\n nav,\n mobileNav,\n sessionState,\n themedScrollpoints = [],\n searchButtonVisibility = \"all\",\n location,\n logoBadge,\n}) => {\n const [showMenu, setShowMenu] = useState(false);\n const [fadingOut, setFadingOut] = useState(false);\n const [bannerVisible, setBannerVisible] = useState(isNoticeVisible);\n const menuRef = useRef<HTMLDivElement>(null);\n const [scrollpointClasses, setScrollpointClasses] = useState<string>(\n themedScrollpoints.length > 0 ? themedScrollpoints[0].className : \"\",\n );\n\n const headerProps = useMemo(\n () => ({\n style: {\n height: HEADER_HEIGHT,\n top: bannerVisible ? `${noticeHeight}px` : \"0\",\n },\n className: cn(\n \"fixed left-0 top-0 w-full z-50 bg-neutral-000 dark:bg-neutral-1300 border-b border-neutral-300 dark:border-neutral-1000 transition-colors px-6 lg:px-16\",\n scrollpointClasses,\n {\n \"md:top-auto\": bannerVisible,\n },\n ),\n }),\n [bannerVisible, noticeHeight, scrollpointClasses],\n );\n\n const closeMenu = () => {\n setFadingOut(true);\n\n setTimeout(() => {\n setShowMenu(false);\n setFadingOut(false);\n }, 150);\n };\n\n useEffect(() => {\n const handleNoticeClose = () => {\n setBannerVisible(false);\n };\n\n document.addEventListener(\"notice-closed\", handleNoticeClose);\n return () =>\n document.removeEventListener(\"notice-closed\", handleNoticeClose);\n }, []);\n\n useEffect(() => {\n const handleScroll = () => {\n setBannerVisible(\n window.scrollY <= COLLAPSE_TRIGGER_DISTANCE && isNoticeVisible,\n );\n for (const scrollpoint of themedScrollpoints) {\n const element = document.getElementById(scrollpoint.id);\n if (element) {\n const rect = element.getBoundingClientRect();\n if (rect.top <= HEADER_HEIGHT && rect.bottom >= HEADER_HEIGHT) {\n setScrollpointClasses(scrollpoint.className);\n return;\n }\n }\n }\n };\n\n const throttledHandleScroll = throttle(handleScroll, 150);\n\n handleScroll();\n\n window.addEventListener(\"scroll\", throttledHandleScroll);\n return () => window.removeEventListener(\"scroll\", throttledHandleScroll);\n }, [themedScrollpoints, isNoticeVisible]);\n\n useEffect(() => {\n const handleResize = () => {\n if (window.innerWidth >= 1040) {\n setShowMenu(false);\n }\n };\n window.addEventListener(\"resize\", handleResize);\n return () => window.removeEventListener(\"resize\", handleResize);\n }, []);\n\n useEffect(() => {\n if (showMenu) {\n document.body.classList.add(\"overflow-hidden\");\n } else {\n document.body.classList.remove(\"overflow-hidden\");\n }\n\n // Cleanup on unmount\n return () => {\n document.body.classList.remove(\"overflow-hidden\");\n };\n }, [showMenu]);\n\n // Close menu when location changes\n useEffect(() => {\n if (location && showMenu) {\n closeMenu();\n }\n }, [location, showMenu]);\n\n const wrappedSearchButton = useMemo(\n () =>\n searchButton ? (\n <div className=\"text-neutral-1300 dark:text-neutral-000 flex items-center\">\n {searchButton}\n </div>\n ) : null,\n [searchButton],\n );\n\n return (\n <>\n <header role=\"banner\" {...headerProps}>\n <div className={cn(\"flex items-center h-full\", className)}>\n <nav className=\"flex flex-1 h-full items-center\">\n {([\"light\", \"dark\"] as Theme[]).map((theme) => (\n <Logo\n key={theme}\n href={logoHref}\n theme={theme}\n badge={logoBadge}\n additionalLinkAttrs={{\n className: cn(\"h-full focus-base rounded mr-4 lg:mr-8\", {\n \"flex dark:hidden\": theme === \"light\",\n \"hidden dark:flex\": theme === \"dark\",\n }),\n }}\n />\n ))}\n <div className={FLEXIBLE_DESKTOP_CLASSES}>{nav}</div>\n </nav>\n <div className=\"flex md:hidden flex-1 items-center justify-end gap-6 h-full\">\n {searchButtonVisibility !== \"desktop\" ? wrappedSearchButton : null}\n <button\n className=\"cursor-pointer focus-base rounded flex items-center p-0\"\n onClick={() => setShowMenu(!showMenu)}\n aria-expanded={showMenu}\n aria-controls=\"mobile-menu\"\n aria-label=\"Toggle menu\"\n >\n <Icon\n name={\n showMenu\n ? \"icon-gui-x-mark-outline\"\n : \"icon-gui-bars-3-outline\"\n }\n additionalCSS=\"text-neutral-1300 dark:text-neutral-000\"\n size=\"1.5rem\"\n />\n </button>\n </div>\n {searchBar ? (\n <div\n className={cn(\n FLEXIBLE_DESKTOP_CLASSES,\n \"justify-center\",\n headerCenterClassName,\n )}\n >\n {searchBar}\n </div>\n ) : null}\n <HeaderLinks\n className={cn(FLEXIBLE_DESKTOP_CLASSES, headerLinksClassName)}\n headerLinks={headerLinks}\n sessionState={sessionState}\n searchButton={wrappedSearchButton}\n searchButtonVisibility={searchButtonVisibility}\n />\n </div>\n </header>\n {showMenu ? (\n <>\n <div\n className={cn(\n \"fixed inset-0 bg-neutral-1300 dark:bg-neutral-1300 z-40\",\n {\n \"animate-[fade-in-ten-percent_150ms_ease-in-out_forwards]\":\n !fadingOut,\n \"animate-[fade-out-ten-percent_150ms_ease-in-out_forwards]\":\n fadingOut,\n },\n )}\n onClick={closeMenu}\n onKeyDown={(e) => e.key === \"Escape\" && closeMenu()}\n role=\"presentation\"\n />\n <div\n id=\"mobile-menu\"\n className=\"md:hidden fixed flex flex-col top-[4.75rem] overflow-y-hidden mx-3 right-0 w-[calc(100%-24px)] bg-neutral-000 dark:bg-neutral-1300 rounded-2xl ui-shadow-lg-medium z-50\"\n style={{\n maxWidth: MAX_MOBILE_MENU_WIDTH,\n maxHeight: componentMaxHeight(\n HEADER_HEIGHT,\n HEADER_BOTTOM_MARGIN,\n ),\n }}\n ref={menuRef}\n role=\"navigation\"\n >\n {mobileNav}\n <HeaderLinks\n headerLinks={headerLinks}\n sessionState={sessionState}\n />\n </div>\n </>\n ) : null}\n </>\n );\n};\n\nexport default Header;\n"],"names":["React","useState","useEffect","useRef","useMemo","Icon","cn","Logo","componentMaxHeight","HEADER_BOTTOM_MARGIN","HEADER_HEIGHT","HeaderLinks","throttle","COLLAPSE_TRIGGER_DISTANCE","FLEXIBLE_DESKTOP_CLASSES","MAX_MOBILE_MENU_WIDTH","Header","className","isNoticeVisible","noticeHeight","searchBar","searchButton","logoHref","headerLinks","headerLinksClassName","headerCenterClassName","nav","mobileNav","sessionState","themedScrollpoints","searchButtonVisibility","location","logoBadge","showMenu","setShowMenu","fadingOut","setFadingOut","bannerVisible","setBannerVisible","menuRef","scrollpointClasses","setScrollpointClasses","length","headerProps","style","height","top","closeMenu","setTimeout","handleNoticeClose","document","addEventListener","removeEventListener","handleScroll","window","scrollY","scrollpoint","element","getElementById","id","rect","getBoundingClientRect","bottom","throttledHandleScroll","handleResize","innerWidth","body","classList","add","remove","wrappedSearchButton","div","header","role","map","theme","key","href","badge","additionalLinkAttrs","button","onClick","aria-expanded","aria-controls","aria-label","name","additionalCSS","size","onKeyDown","e","maxWidth","maxHeight","ref"],"mappings":"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"}
|
|
1
|
+
{"version":3,"sources":["../../src/core/Header.tsx"],"sourcesContent":["import React, { useState, useEffect, useRef, ReactNode, useMemo } from \"react\";\nimport Icon from \"./Icon\";\nimport cn from \"./utils/cn\";\nimport Logo from \"./Logo\";\nimport {\n componentMaxHeight,\n HEADER_BOTTOM_MARGIN,\n HEADER_HEIGHT,\n} from \"./utils/heights\";\nimport { HeaderLinks } from \"./Header/HeaderLinks\";\nimport { throttle } from \"es-toolkit/compat\";\nimport { Theme } from \"./styles/colors/types\";\nimport { COLLAPSE_TRIGGER_DISTANCE } from \"./Notice/component\";\n\nexport type ThemedScrollpoint = {\n id: string;\n className: string;\n};\n\n/**\n * Represents the state of the user session in the header.\n */\nexport type HeaderSessionState = {\n /**\n * Indicates if the user is signed in.\n */\n signedIn: boolean;\n\n /**\n * Information required to log out the user.\n */\n logOut: {\n /**\n * Token used for logging out.\n */\n token: string;\n\n /**\n * URL to log out the user.\n */\n href: string;\n };\n\n /**\n * Name of the user's account.\n */\n accountName: string;\n};\n\n/**\n * Props for the Header component.\n */\nexport type HeaderProps = {\n /**\n * Optional classnames to add to the header\n */\n className?: string;\n /**\n * Indicates if the notice banner is visible.\n */\n isNoticeVisible?: boolean;\n /**\n * Height of the notice banner in pixels.\n */\n noticeHeight?: number;\n /**\n * Optional search bar element.\n */\n searchBar?: ReactNode;\n\n /**\n * Optional search button element.\n */\n searchButton?: ReactNode;\n\n /**\n * URL for the logo link.\n */\n logoHref?: string;\n\n /**\n * Array of header links.\n */\n headerLinks?: {\n /**\n * URL for the link.\n */\n href: string;\n\n /**\n * Label for the link.\n */\n label: string;\n\n /**\n * Indicates if the link should open in a new tab.\n */\n external?: boolean;\n }[];\n\n /**\n * Optional classname for styling the header links container.\n */\n headerLinksClassName?: string;\n\n /**\n * Optional classname for styling the header center container.\n */\n headerCenterClassName?: string;\n\n /**\n * Optional desktop navigation element.\n */\n nav?: ReactNode;\n\n /**\n * Optional mobile navigation element.\n */\n mobileNav?: ReactNode;\n\n /**\n * State of the user session.\n */\n sessionState?: HeaderSessionState;\n\n /**\n * Array of themed scrollpoints. The header will change its appearance based on the scrollpoint in view.\n */\n themedScrollpoints?: ThemedScrollpoint[];\n\n /**\n * Visibility setting for the search button.\n * - \"all\": Visible on all devices.\n * - \"desktop\": Visible only on desktop devices.\n * - \"mobile\": Visible only on mobile devices.\n */\n searchButtonVisibility?: \"all\" | \"desktop\" | \"mobile\";\n\n /**\n * Optional location object to detect location changes.\n */\n location?: Location;\n\n /**\n * Optional badge text to display on the logo.\n */\n logoBadge?: string;\n};\n\nconst FLEXIBLE_DESKTOP_CLASSES = \"hidden md:flex flex-1 items-center h-full\";\n\n/**\n * Maximum width before the menu expanded into full width\n */\nconst MAX_MOBILE_MENU_WIDTH = \"560px\";\n\nconst Header: React.FC<HeaderProps> = ({\n className,\n isNoticeVisible = false,\n noticeHeight = 0,\n searchBar,\n searchButton,\n logoHref,\n headerLinks,\n headerLinksClassName,\n headerCenterClassName,\n nav,\n mobileNav,\n sessionState,\n themedScrollpoints = [],\n searchButtonVisibility = \"all\",\n location,\n logoBadge,\n}) => {\n const [showMenu, setShowMenu] = useState(false);\n const [fadingOut, setFadingOut] = useState(false);\n const [bannerVisible, setBannerVisible] = useState(isNoticeVisible);\n const menuRef = useRef<HTMLDivElement>(null);\n const [scrollpointClasses, setScrollpointClasses] = useState<string>(\n themedScrollpoints.length > 0 ? themedScrollpoints[0].className : \"\",\n );\n\n const headerProps = useMemo(() => ({\n style: {\n height: HEADER_HEIGHT,\n top: bannerVisible ? `${noticeHeight}px` : \"0\",\n },\n className: cn(\n \"fixed left-0 top-0 w-full z-50 bg-neutral-000 dark:bg-neutral-1300 border-b border-neutral-300 dark:border-neutral-1000 transition-colors px-6 lg:px-16\",\n scrollpointClasses,\n {\n \"md:top-auto\": bannerVisible,\n },\n ),\n }), [bannerVisible, noticeHeight, scrollpointClasses]);\n\n const closeMenu = () => {\n setFadingOut(true);\n\n setTimeout(() => {\n setShowMenu(false);\n setFadingOut(false);\n }, 150);\n };\n\n useEffect(() => {\n const handleNoticeClose = () => {\n setBannerVisible(false);\n };\n\n document.addEventListener(\"notice-closed\", handleNoticeClose);\n return () =>\n document.removeEventListener(\"notice-closed\", handleNoticeClose);\n }, []);\n\n useEffect(() => {\n const handleScroll = () => {\n setBannerVisible(\n window.scrollY <= COLLAPSE_TRIGGER_DISTANCE && isNoticeVisible,\n );\n for (const scrollpoint of themedScrollpoints) {\n const element = document.getElementById(scrollpoint.id);\n if (element) {\n const rect = element.getBoundingClientRect();\n if (rect.top <= HEADER_HEIGHT && rect.bottom >= HEADER_HEIGHT) {\n setScrollpointClasses(scrollpoint.className);\n return;\n }\n }\n }\n };\n\n const throttledHandleScroll = throttle(handleScroll, 150);\n\n handleScroll();\n\n window.addEventListener(\"scroll\", throttledHandleScroll);\n return () => window.removeEventListener(\"scroll\", throttledHandleScroll);\n }, [themedScrollpoints, isNoticeVisible]);\n\n useEffect(() => {\n const handleResize = () => {\n if (window.innerWidth >= 1040) {\n setShowMenu(false);\n }\n };\n window.addEventListener(\"resize\", handleResize);\n return () => window.removeEventListener(\"resize\", handleResize);\n }, []);\n\n useEffect(() => {\n if (showMenu) {\n document.body.classList.add(\"overflow-hidden\");\n } else {\n document.body.classList.remove(\"overflow-hidden\");\n }\n\n // Cleanup on unmount\n return () => {\n document.body.classList.remove(\"overflow-hidden\");\n };\n }, [showMenu]);\n\n // Close menu when location changes\n useEffect(() => {\n if (location && showMenu) {\n closeMenu();\n }\n }, [location, showMenu]);\n\n const wrappedSearchButton = useMemo(\n () =>\n searchButton ? (\n <div className=\"text-neutral-1300 dark:text-neutral-000 flex items-center\">\n {searchButton}\n </div>\n ) : null,\n [searchButton],\n );\n\n return (\n <>\n <header role=\"banner\" {...headerProps}>\n <div className={cn(\"flex items-center h-full\", className)}>\n <nav className=\"flex flex-1 h-full items-center\">\n {([\"light\", \"dark\"] as Theme[]).map((theme) => (\n <Logo\n key={theme}\n href={logoHref}\n theme={theme}\n badge={logoBadge}\n additionalLinkAttrs={{\n className: cn(\"h-full focus-base rounded mr-4 lg:mr-8\", {\n \"flex dark:hidden\": theme === \"light\",\n \"hidden dark:flex\": theme === \"dark\",\n }),\n }}\n />\n ))}\n <div className={FLEXIBLE_DESKTOP_CLASSES}>{nav}</div>\n </nav>\n <div className=\"flex md:hidden flex-1 items-center justify-end gap-6 h-full\">\n {searchButtonVisibility !== \"desktop\" ? wrappedSearchButton : null}\n <button\n className=\"cursor-pointer focus-base rounded flex items-center p-0\"\n onClick={() => setShowMenu(!showMenu)}\n aria-expanded={showMenu}\n aria-controls=\"mobile-menu\"\n aria-label=\"Toggle menu\"\n >\n <Icon\n name={\n showMenu\n ? \"icon-gui-x-mark-outline\"\n : \"icon-gui-bars-3-outline\"\n }\n additionalCSS=\"text-neutral-1300 dark:text-neutral-000\"\n size=\"1.5rem\"\n />\n </button>\n </div>\n {searchBar ? (\n <div\n className={cn(\n FLEXIBLE_DESKTOP_CLASSES,\n \"justify-center\",\n headerCenterClassName,\n )}\n >\n {searchBar}\n </div>\n ) : null}\n <HeaderLinks\n className={cn(FLEXIBLE_DESKTOP_CLASSES, headerLinksClassName)}\n headerLinks={headerLinks}\n sessionState={sessionState}\n searchButton={wrappedSearchButton}\n searchButtonVisibility={searchButtonVisibility}\n />\n </div>\n </header>\n {showMenu ? (\n <>\n <div\n className={cn(\n \"fixed inset-0 bg-neutral-1300 dark:bg-neutral-1300 z-40\",\n {\n \"animate-[fade-in-ten-percent_150ms_ease-in-out_forwards]\":\n !fadingOut,\n \"animate-[fade-out-ten-percent_150ms_ease-in-out_forwards]\":\n fadingOut,\n },\n )}\n onClick={closeMenu}\n onKeyDown={(e) => e.key === \"Escape\" && closeMenu()}\n role=\"presentation\"\n />\n <div\n id=\"mobile-menu\"\n className=\"md:hidden fixed flex flex-col top-[4.75rem] overflow-y-hidden mx-3 right-0 w-[calc(100%-24px)] bg-neutral-000 dark:bg-neutral-1300 rounded-2xl ui-shadow-lg-medium z-50\"\n style={{\n maxWidth: MAX_MOBILE_MENU_WIDTH,\n maxHeight: componentMaxHeight(\n HEADER_HEIGHT,\n HEADER_BOTTOM_MARGIN,\n ),\n }}\n ref={menuRef}\n role=\"navigation\"\n >\n {mobileNav}\n <HeaderLinks\n headerLinks={headerLinks}\n sessionState={sessionState}\n />\n </div>\n </>\n ) : null}\n </>\n );\n};\n\nexport default Header;\n"],"names":["React","useState","useEffect","useRef","useMemo","Icon","cn","Logo","componentMaxHeight","HEADER_BOTTOM_MARGIN","HEADER_HEIGHT","HeaderLinks","throttle","COLLAPSE_TRIGGER_DISTANCE","FLEXIBLE_DESKTOP_CLASSES","MAX_MOBILE_MENU_WIDTH","Header","className","isNoticeVisible","noticeHeight","searchBar","searchButton","logoHref","headerLinks","headerLinksClassName","headerCenterClassName","nav","mobileNav","sessionState","themedScrollpoints","searchButtonVisibility","location","logoBadge","showMenu","setShowMenu","fadingOut","setFadingOut","bannerVisible","setBannerVisible","menuRef","scrollpointClasses","setScrollpointClasses","length","headerProps","style","height","top","closeMenu","setTimeout","handleNoticeClose","document","addEventListener","removeEventListener","handleScroll","window","scrollY","scrollpoint","element","getElementById","id","rect","getBoundingClientRect","bottom","throttledHandleScroll","handleResize","innerWidth","body","classList","add","remove","wrappedSearchButton","div","header","role","map","theme","key","href","badge","additionalLinkAttrs","button","onClick","aria-expanded","aria-controls","aria-label","name","additionalCSS","size","onKeyDown","e","maxWidth","maxHeight","ref"],"mappings":"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"}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@ably/ui",
|
|
3
|
-
"version": "17.8.0-dev.
|
|
3
|
+
"version": "17.8.0-dev.7634f24d",
|
|
4
4
|
"description": "Home of the Ably design system library ([design.ably.com](https://design.ably.com)). It provides a showcase, development/test environment and a publishing pipeline for different distributables.",
|
|
5
5
|
"repository": {
|
|
6
6
|
"type": "git",
|