diff --git a/apps/website/pages/components/image/usage.tsx b/apps/website/pages/components/image/usage.tsx
new file mode 100644
index 000000000..622c520f7
--- /dev/null
+++ b/apps/website/pages/components/image/usage.tsx
@@ -0,0 +1,21 @@
+import Head from "next/head";
+import type { ReactElement } from "react";
+import ImagePageLayout from "../../../screens/components/image/ImagePageLayout";
+import ImageUsagePage from "../../../screens/components/image/usage/ImageUsagePage";
+
+const Usage = () => {
+ return (
+ <>
+
+ Image Usage — Halstack Design System
+
+
+ >
+ );
+};
+
+Usage.getLayout = function getLayout(page: ReactElement) {
+ return {page};
+};
+
+export default Usage;
diff --git a/apps/website/screens/common/MainContent.tsx b/apps/website/screens/common/MainContent.tsx
index 05ea75e0b..0eb6b6eb4 100644
--- a/apps/website/screens/common/MainContent.tsx
+++ b/apps/website/screens/common/MainContent.tsx
@@ -1,29 +1,26 @@
import { useToast } from "@dxc-technology/halstack-react";
-import { ReactNode, useMemo, useState, useEffect } from "react";
+import { ReactNode, useState, useEffect } from "react";
import styled from "styled-components";
import { responsiveSizes } from "./variables";
const MainContainer = styled.div`
- margin: 80px 0;
+ margin: 80px auto;
max-width: 1124px;
- margin-inline: max(5%, 50% - 1124px/2);
+ padding: 0 5%;
@media (max-width: ${responsiveSizes.laptop}px) {
margin: 80px 32px;
}
`;
+const pathVersion =
+ process.env.NEXT_PUBLIC_SITE_VERSION === "next" || process.env.NODE_ENV === "development"
+ ? 0
+ : parseInt(process.env.NEXT_PUBLIC_SITE_VERSION?.split(".")[0], 10);
+
const MainContent = ({ children }: { children: ReactNode }) => {
const toast = useToast();
- const pathVersion = useMemo(
- () =>
- process.env.NEXT_PUBLIC_SITE_VERSION === "next" || process.env.NODE_ENV === "development"
- ? 0
- : parseInt(process.env.NEXT_PUBLIC_SITE_VERSION?.split(".")[0], 10),
-
- []
- );
- const [latestRelease, setLatestRelease] = useState(null);
+ const [latestRelease, setLatestRelease] = useState(null);
useEffect(() => {
(async () => {
@@ -39,7 +36,7 @@ const MainContent = ({ children }: { children: ReactNode }) => {
}, []);
useEffect(() => {
- if (latestRelease > pathVersion) {
+ if (pathVersion && latestRelease && latestRelease > pathVersion) {
toast.info({
message: `Halstack ${latestRelease} is now available!`,
action: {
@@ -54,7 +51,7 @@ const MainContent = ({ children }: { children: ReactNode }) => {
},
});
}
- }, [latestRelease, pathVersion, toast]);
+ }, [latestRelease, toast]);
return {children};
};
diff --git a/apps/website/screens/common/componentsList.json b/apps/website/screens/common/componentsList.json
index 36e361338..aea357ea2 100644
--- a/apps/website/screens/common/componentsList.json
+++ b/apps/website/screens/common/componentsList.json
@@ -29,7 +29,7 @@
{
"label": "Container",
"path": "/components/container",
- "status": "new"
+ "status": "stable"
},
{
"label": "Contextual Menu",
@@ -63,7 +63,7 @@
{ "label": "Grid", "path": "/components/grid", "status": "stable" },
{ "label": "Header", "path": "/components/header", "status": "stable" },
{ "label": "Heading", "path": "/components/heading", "status": "stable" },
- { "label": "Image", "path": "/components/image", "status": "experimental" },
+ { "label": "Image", "path": "/components/image", "status": "stable" },
{ "label": "Inset", "path": "/components/inset", "status": "stable" },
{ "label": "Link", "path": "/components/link", "status": "stable" },
{ "label": "Nav Tabs", "path": "/components/nav-tabs", "status": "stable" },
diff --git a/apps/website/screens/components/flex/usage/FlexUsagePage.tsx b/apps/website/screens/components/flex/usage/FlexUsagePage.tsx
index 17a25d71a..7fbcd8da6 100644
--- a/apps/website/screens/components/flex/usage/FlexUsagePage.tsx
+++ b/apps/website/screens/components/flex/usage/FlexUsagePage.tsx
@@ -5,6 +5,27 @@ import QuickNavContainer from "@/common/QuickNavContainer";
import QuickNavContainerLayout from "@/common/QuickNavContainerLayout";
const sections = [
+ {
+ title: "Overview",
+ content: (
+ <>
+
+ The Flex component is designed to provide a more efficient way to organize, align, and distribute space among
+ items within a container, even when their size is unknown or dynamic (hence the term 'flex').
+
+
+ By leveraging the capabilities of the Flex component, developers can create more flexible and responsive
+ layouts that adapt to different screen sizes and device types. This powerful tool enables the creation of
+ complex structures that can be easily adjusted to accommodate various content types and user interactions.
+
+
+ In the sections that follow, we'll explore the core concepts and best practices for using the Flex component.
+ By understanding these principles, you can optimize the layout of your application, enhance the user experience,
+ and create more engaging and visually appealing interfaces.
+
+ >
+ ),
+ },
{
title: "Axes",
content: (
diff --git a/apps/website/screens/components/image/ImagePageLayout.tsx b/apps/website/screens/components/image/ImagePageLayout.tsx
index 968e6ba23..5bbfd4322 100644
--- a/apps/website/screens/components/image/ImagePageLayout.tsx
+++ b/apps/website/screens/components/image/ImagePageLayout.tsx
@@ -4,7 +4,10 @@ import TabsPageHeading from "@/common/TabsPageLayout";
import ComponentHeading from "@/common/ComponentHeading";
const ImagePageHeading = ({ children }: { children: React.ReactNode }) => {
- const tabs = [{ label: "Code", path: "/components/image" }];
+ const tabs = [
+ { label: "Code", path: "/components/image" },
+ { label: "Usage", path: "/components/image/usage" },
+ ];
return (
diff --git a/apps/website/screens/components/image/usage/ImageUsagePage.tsx b/apps/website/screens/components/image/usage/ImageUsagePage.tsx
new file mode 100644
index 000000000..410789c41
--- /dev/null
+++ b/apps/website/screens/components/image/usage/ImageUsagePage.tsx
@@ -0,0 +1,156 @@
+import { DxcImage, DxcParagraph, DxcFlex, DxcBulletedList } from "@dxc-technology/halstack-react";
+import Code from "@/common/Code";
+import DocFooter from "@/common/DocFooter";
+import QuickNavContainer from "@/common/QuickNavContainer";
+import QuickNavContainerLayout from "@/common/QuickNavContainerLayout";
+
+const sections = [
+ {
+ title: "Overview",
+ content: (
+ <>
+
+ The Image component serves as a versatile tool for efficiently loading and displaying visual content across
+ diverse contexts within your application. This powerful component is designed to optimize performance while
+ enhancing the overall user experience. By leveraging its capabilities, developers can seamlessly integrate
+ images into their projects, ensuring smooth rendering and responsive behavior.
+
+
+ To maximize the potential of the Image component and create visually appealing, high-performing applications,
+ it's crucial to adhere to certain best practices and usage guidelines. These recommendations encompass various
+ aspects of image implementation, from technical considerations to user-centric design principles. By following
+ these guidelines, you can ensure that your images not only load quickly and efficiently but also contribute
+ positively to the user's interaction with your application.
+
+
+ In the sections that follow, we'll delve into a comprehensive set of best practices and usage guidelines.
+ These insights will help you optimize performance, enhance accessibility, and create a more engaging visual
+ experience for your users across different devices and contexts.
+
+ >
+ ),
+ },
+ {
+ title: "Accessibility",
+ content: (
+ <>
+
+ The Image component should always include an alt
property to describe the content of the image.
+ This is important for users who rely on screen readers to understand the content of the page. The alt text
+ should be a short description of the image content.
+
+
+ If an image is purely decorative, use an empty value (alt=""
) to indicate this to screen readers,
+ preventing unnecessary noise. Also, include captions when the image is an integral part of the content,
+ providing users with additional context.
+
+ >
+ ),
+ },
+ {
+ title: "Aspect ratio and cropping",
+ content: (
+
+
+ Preserve aspect ratio. The aspect ratio of an image should generally be preserved, unless
+ explicitly specified otherwise by the design.
+
+
+ Avoid distortion. When resizing images, avoid stretching or squashing them to prevent
+ distortion. Instead, use object-fit
to set how the image is displayed or control the dimensions
+ through the container.
+
+
+ Thumbnails and zoom. When displaying thumbnails or zoomed images, ensure that the image is
+ cropped appropriately to focus on the most relevant content.
+
+
+ ),
+ },
+ {
+ title: "Considerations for background images",
+ content: (
+
+
+ Image as content vs. background. If the image is essential content, use the Image component.
+ For decorative backgrounds, consider using CSS background images to keep content and design separate.
+
+
+ Contrast and readability. Ensure sufficient contrast between background images and overlaid
+ text. This may require applying filters or overlays to the image.
+
+
+ ),
+ },
+ {
+ title: "Responsiveness",
+ content: (
+
+ An image should always adapt fluidly to the size of its container, ensuring that it maintains its aspect ratio
+ unless otherwise specified. To achieve this, it's important to define the width and height properties to ensure
+ images are loaded with known dimensions, which helps maintain layout stability and reduces cumulative layout
+ shifts. When designing for multiple devices, leveraging responsive image techniques, such as the{" "}
+ srcset
and
+ sizes
props, ensures that the appropriate resolution is served based on the user's screen size and
+ the layout's space allocation. This not only improves performance but also optimizes the experience across
+ different viewports.
+
+ ),
+ },
+ {
+ title: "Best practices",
+ content: (
+
+
+ Use high-quality images. Always use high-resolution images to deliver a crisp and clear
+ display, especially on high-density (retina) screens. This ensures a professional look and prevents
+ pixelation.
+
+
+ Optimize images. Compress and optimize images for the web to minimize file sizes. Reducing
+ load times and bandwidth consumption is crucial for performance, especially on mobile devices.
+
+
+ Leverage modern formats. Whenever possible, use newer image formats like WebP for improved
+ compression without sacrificing quality. Be sure to provide fallback formats for browsers that don't support
+ them.
+
+
+ Allow lazy loading. Implement lazy loading (loading="lazy"
) for images that
+ appear later on the page (below the fold). This helps speed up initial page loads and improve overall
+ performance.
+
+
+ Use responsive image techniques. Make use of srcset
and sizes
props
+ to serve images that adapt to different screen resolutions and sizes, ensuring the best display quality across
+ devices.
+
+
+ Avoid using images for text content. Text embedded within images reduces accessibility and
+ harms SEO. Always use HTML text to ensure readability by screen readers and search engines.
+
+
+ Limit decorative images. Avoid overloading pages with unnecessary decorative images. This not
+ only reduces performance but can also distract users from the main content.
+
+
+ Avoid images for icons. Use scalable vector graphics (SVGs) instead of images for icons. SVGs
+ offer better performance, scalability, and accessibility across various screen sizes.
+
+
+ ),
+ },
+];
+
+const ImageUsagePage = () => {
+ return (
+
+
+
+
+
+
+ );
+};
+
+export default ImageUsagePage;
diff --git a/apps/website/screens/components/tabs/usage/TabsUsagePage.tsx b/apps/website/screens/components/tabs/usage/TabsUsagePage.tsx
index 6d019c0a2..7f73ab74b 100644
--- a/apps/website/screens/components/tabs/usage/TabsUsagePage.tsx
+++ b/apps/website/screens/components/tabs/usage/TabsUsagePage.tsx
@@ -4,7 +4,6 @@ import QuickNavContainer from "@/common/QuickNavContainer";
import QuickNavContainerLayout from "@/common/QuickNavContainerLayout";
import Figure from "@/common/Figure";
import DocFooter from "@/common/DocFooter";
-import tabsUsage from "./examples/usage";
import defaultUsage from "./examples/default";
import scrollableUsage from "./examples/scrollable";
import contentUsageTabImage from "./images/tabs_content.png";
@@ -27,7 +26,6 @@ const sections = [
Tabs organize and allow navigation between groups of content that are related and at the same level of
hierarchy.
-
>
),
},
diff --git a/apps/website/screens/components/tabs/usage/examples/usage.ts b/apps/website/screens/components/tabs/usage/examples/usage.ts
deleted file mode 100644
index 0ab590747..000000000
--- a/apps/website/screens/components/tabs/usage/examples/usage.ts
+++ /dev/null
@@ -1,65 +0,0 @@
-import { DxcTabs, DxcInset } from "@dxc-technology/halstack-react";
-
-const code = `() => {
- return (
-
-
-
-
-
-
-
-
-
-
-
-
- )} active>
- <>>
-
-
-
-
-
- )}>
- <>>
-
-
-
-
-
- )}>
- <>>
-
-
-
- );
-}`;
-
-const scope = {
- DxcTabs,
- DxcInset,
-};
-
-export default { code, scope };
diff --git a/packages/lib/src/link/Link.tsx b/packages/lib/src/link/Link.tsx
index 396a1b0e9..44e1e05fe 100644
--- a/packages/lib/src/link/Link.tsx
+++ b/packages/lib/src/link/Link.tsx
@@ -7,7 +7,7 @@ import { LinkProps } from "./types";
const LinkContent = memo(
({ iconPosition, icon, inheritColor, children }: LinkProps): JSX.Element => (
-
+
{iconPosition === "after" && children}
{icon && (