diff --git a/.gitignore b/.gitignore index e1c51b2641..889a02f347 100644 --- a/.gitignore +++ b/.gitignore @@ -45,3 +45,6 @@ size-plugin.json !.yarn/releases !.yarn/sdks !.yarn/versions + +.yalc +yalc.lock \ No newline at end of file diff --git a/packages/site/package.json b/packages/site/package.json index 53871fd7cd..bb29130f1b 100644 --- a/packages/site/package.json +++ b/packages/site/package.json @@ -7,13 +7,17 @@ "generate:content": "patternfly-doc-core convert-to-mdx ../documentation-site/patternfly-docs/content/", "dev": "patternfly-doc-core start", "build": "patternfly-doc-core build", + "preview": "npx wrangler pages dev ./dist", "serve": "patternfly-doc-core serve", "sync": "patternfly-doc-core sync", + "deploy": "npx wrangler pages deploy ./dist", "init:docs": "patternfly-doc-core init" }, "dependencies": { - "@patternfly/patternfly-doc-core": "^1.9.0", - "astro": "^5.7.13" + "@patternfly/patternfly-doc-core": "latest", + "@patternfly/react-icons": "^6.2.2", + "astro": "^5.7.13", + "wrangler": "^4.20.0" }, "devDependencies": { "tsx": "^4.19.0" diff --git a/packages/site/pf-docs.config.mjs b/packages/site/pf-docs.config.mjs index 4e6576da21..fa8bdb072f 100644 --- a/packages/site/pf-docs.config.mjs +++ b/packages/site/pf-docs.config.mjs @@ -4,7 +4,7 @@ export const config = { // documentation core with a content identifier of 'content': { base: 'src/', - pattern: "**/*.{md,mdx}", + pattern: "**/*.md*", name: 'content' }, // diff --git a/packages/site/src/content/design-guidelines/charts/about/about.mdx b/packages/site/src/content/design-guidelines/charts/about/about.mdx new file mode 100644 index 0000000000..d301c71891 --- /dev/null +++ b/packages/site/src/content/design-guidelines/charts/about/about.mdx @@ -0,0 +1,79 @@ +--- +id: About charts +section: charts +sortValue: 1 +--- + +_Charts are only available in React_ + +A **chart** visualizes data in an application. The type of chart you use will depend on your use case and the type of data you need to display. + +## Elements +Chart with axis labels + +1. **Title:** Titles should be left-aligned and appear above your chart. +2. **Axis labels and scale values:** We recommend using tick marks to clearly mark scale values on the y-axis. The text for axis labels and scale values should be 12px font in standard text color. All scale values should be equally distributed across the axis and the axis label should fall outside the scale values, centered with the axis line. +3. **Legends:** We recommend using legends when charts include more than one variable and therefore use more than one color. When datasets are overlapping, an [interactive legend](#interactive-chart-legends) can be used. If space is not available to display names of horizontal and vertical axes, a legend must be added instead. The legend should list the colors that each variable obtains and the name of the variable. The text on the legend should be 14px size and standard text color. They can either be placed left-aligned to the right of the chart or centered below the chart. +4. **Chart tooltip:** A tooltip will appear on hover over certain elements of a chart, like bars in a bar chart or segments in a donut chart. [Chart tooltips](/charts/tooltips) should display the specific values related to the element the user is hovering over. + +## Chart types +Image displaying what chart types to use when + +- [Area chart](/charts/area-chart/design-guidelines): Use to show (potentially multiple) trends over a continuous scale (usually time). +- [Bar chart](/charts/bar-chart/design-guidelines): Use to show and compare categories and their respective data point/value. Bar charts can be plotted vertically or horizontally. The axis that labels the bar is the category, the axis that marks the end point of the bar displays the data points/values. + - [Stacked bar chart](/charts/stack-chart/design-guidelines): Use to show and compare categorical data of more than one variable. Can be plotted vertically or horizontally. + - Vertical bar charts (category on the horizontal x axis): Use to show a progression of the categories (or sequential variables). The most common bar chart. + - Horizontal bar charts (category on the vertical y axis): Use to show nominal variables. Allows for more space for category labeling. +- [Bullet chart](/charts/bullet-chart/design-guidelines): Use as an extension to the bar chart to measure data with thresholds and static ranges. +- [Donut chart](/charts/donut-chart/design-guidelines): Use to show the relationship of a set of values to a whole or to show progress completion as a percentage. Donut charts are best used to display data with a small number of categories (example: 2-5 categories). Use the middle of the chart to highlight a data point. + - [Donut utilization](/charts/donut-utilization-chart/design-guidelines): Use to show utilization for an object as a percentage. + - [Donut utilization with threshold](/charts/donut-utilization-chart/design-guidelines#donut-chart---utilization-with-threshold): Use to show utilization for an object as a percentage in relation to threshold values. +- [Line chart](/charts/line-chart/design-guidelines): Use to compare several data sets or to show data changes over a period of time. Line charts work best when small changes exist within the data. +- [Pie chart](/charts/pie-chart/design-guidelines): Use to show percentages or proportional data. Can be used to show up to five or more data points. +- [Sparkline](/charts/sparkline-chart/design-guidelines): Use to show how values change over time for multiple sets of data. Sparkline charts offer an alternative to the line chart when multiple lines need to be plotted. Axis values are not labeled, but a tooltip can be used to display the value at a given point. + +## Charts in cards +If a chart lives in a card, the title of that chart will be placed on the header of that card instead of the chart. The rest of the chart guidelines should be followed for the chart itself. + +Chart on a card + +Sparkline on a card + +## Brush and zoom +The brush and zoom properties allow for magnification of an area, bar, line, or stack chart. If desired, more advanced features can be added through [Victory](https://formidable.com/open-source/victory/guides/brush-and-zoom/). + +### Example + +Brush and zoom + +1. **Window:** Click and drag to create a window around the section of the chart that you want to zoom in on. +2. **Magnified chart:** The portion selected will appear above the full chart view. + +## Interactive chart legends +For charts that graph more than one data set, use interactive legends to highlight or isolate certain data sets. This would work well for [line](#line-chart), [area](#area-chart), or [stacked](#stacked-bar-charts) charts, where data sets can overlap. + +### Example +On hover + +Interactive legend on hover + +1. **Legend:** When a user hovers over a legend label, opacity lowers for all other legend labels. +2. **Chart:** Data corresponding to the hovered legend label is highlighted since opacity lowers for all other data sets, too. + +On click + +Interactive legend hidden + +1. **Legend:** When a user clicks on a legend label, it becomes disabled and the color swatch is replaced with an eye-slashed icon. +2. **Chart:** Data corresponding to the clicked legend label is hidden from view. + +## Develop with charts + +Default styles in the [@patternfly/react-charts package](https://www.npmjs.com/package/@patternfly/react-charts) are aligned with our light theme. Charts work with PatternFly's light theme by default—you don't need to import anything else. + +To support dark-themed charts, you must: +1. Import the [@patternfly/patternfly package](https://www.npmjs.com/package/@patternfly/patternfly), so that you can use our global tokens. +1. Import the stylesheet that contains dark theme styles by adding this line before importing your main application component: `import '@patternfly/patternfly/patternfly-charts.css';` + - Once you import this file, you'll have access to [all chart variables](https://www.npmjs.com/package/@patternfly/patternfly?activeTab=code). Beyond dark theme, you could use these variables to match the style of other UI elements to your chart styles. + +To display the list of all available chart tokens, filter for "charts" in [the PatternFly design tokens table](/tokens/all-patternfly-tokens). \ No newline at end of file diff --git a/packages/site/src/content/design-guidelines/charts/about/img/axis-labels.png b/packages/site/src/content/design-guidelines/charts/about/img/axis-labels.png new file mode 100644 index 0000000000..452bff7669 Binary files /dev/null and b/packages/site/src/content/design-guidelines/charts/about/img/axis-labels.png differ diff --git a/packages/site/src/content/design-guidelines/charts/about/img/brush-and-zoom.png b/packages/site/src/content/design-guidelines/charts/about/img/brush-and-zoom.png new file mode 100644 index 0000000000..2bafc49489 Binary files /dev/null and b/packages/site/src/content/design-guidelines/charts/about/img/brush-and-zoom.png differ diff --git a/packages/site/src/content/design-guidelines/charts/about/img/chart-legend.png b/packages/site/src/content/design-guidelines/charts/about/img/chart-legend.png new file mode 100644 index 0000000000..c676e37b7b Binary files /dev/null and b/packages/site/src/content/design-guidelines/charts/about/img/chart-legend.png differ diff --git a/packages/site/src/content/design-guidelines/charts/about/img/chart-on-a-card.png b/packages/site/src/content/design-guidelines/charts/about/img/chart-on-a-card.png new file mode 100644 index 0000000000..9bc02a4ef3 Binary files /dev/null and b/packages/site/src/content/design-guidelines/charts/about/img/chart-on-a-card.png differ diff --git a/packages/site/src/content/design-guidelines/charts/about/img/interaction-legend-hide.png b/packages/site/src/content/design-guidelines/charts/about/img/interaction-legend-hide.png new file mode 100644 index 0000000000..e0fd4be744 Binary files /dev/null and b/packages/site/src/content/design-guidelines/charts/about/img/interaction-legend-hide.png differ diff --git a/packages/site/src/content/design-guidelines/charts/about/img/interaction-legend-hover.png b/packages/site/src/content/design-guidelines/charts/about/img/interaction-legend-hover.png new file mode 100644 index 0000000000..7c007f1f2a Binary files /dev/null and b/packages/site/src/content/design-guidelines/charts/about/img/interaction-legend-hover.png differ diff --git a/packages/site/src/content/design-guidelines/charts/about/img/sparkline-card.png b/packages/site/src/content/design-guidelines/charts/about/img/sparkline-card.png new file mode 100644 index 0000000000..6c97506c7a Binary files /dev/null and b/packages/site/src/content/design-guidelines/charts/about/img/sparkline-card.png differ diff --git a/packages/site/src/content/design-guidelines/charts/area-chart/area-chart.mdx b/packages/site/src/content/design-guidelines/charts/area-chart/area-chart.mdx new file mode 100644 index 0000000000..c54626aea9 --- /dev/null +++ b/packages/site/src/content/design-guidelines/charts/area-chart/area-chart.mdx @@ -0,0 +1,16 @@ +--- +id: Area chart +section: charts +--- +An **area chart** is used to provide metrics for a single data point. While similar to a line chart in both form and function, it offers an area fill for visual emphasis. The area fill below the line also functions to indicate cumulative data. + +## Usage +The most common use case for area charts is to show trending over a continuous scale (usually time). Use this chart type when you need to provide more visual emphasis than a simple [line chart](/charts/line-chart) offers. + +You may stack area charts to compare more than one continuous data sets. Stacking area charts will put more emphasis on the difference between each visualized data set. + +### Example +Area chart  + +1. **Data area fill:** The area fill is presented below the data line. Data area fills use colors that conform with the [colors for charts](/charts/colors-for-charts). +2. **Chart tooltip:** Use the chart tooltip to drill into the data related to any data point provided on your area chart. \ No newline at end of file diff --git a/packages/site/src/content/design-guidelines/charts/area-chart/img/area-chart.png b/packages/site/src/content/design-guidelines/charts/area-chart/img/area-chart.png new file mode 100644 index 0000000000..bc989f6c66 Binary files /dev/null and b/packages/site/src/content/design-guidelines/charts/area-chart/img/area-chart.png differ diff --git a/packages/site/src/content/design-guidelines/charts/bar-chart/bar-chart.mdx b/packages/site/src/content/design-guidelines/charts/bar-chart/bar-chart.mdx new file mode 100644 index 0000000000..00116463bf --- /dev/null +++ b/packages/site/src/content/design-guidelines/charts/bar-chart/bar-chart.mdx @@ -0,0 +1,23 @@ +--- +id: Bar chart +section: charts +--- +A **bar chart** is used to easily display two variables, one on the horizontal x-axis and one on the vertical y-axis. They are helpful to visualize and compare categorical data. + +## Usage +Bar charts are a great way to show and compare categorical data. Unlike donut or pie charts that differentiate by angle area, bar charts differentiate by length. Because of this clearer differentiation, we recommend using bar charts over donut or pie charts in most cases. + +If you want to show continuous data over time, you may consider using a [line chart](/charts/line-chart) instead. If you wish to show the percentage utilization ratio between used and available, you should check out the [donut utilization chart](/charts/donut-utilization-chart). + +## Horizontal vs. vertical bar charts + +The orientation of bar charts is dependent on the data and space at hand. Any bar chart should be able to be displayed in either direction if applicable. + +#### Example +Horizontal bar chart + +
+ +Vertical bar chart + +A bar's height represents its value. All bars should be the same width, and the spacing between them should be equal, mimicking the spacing between axis values. For fill color recommendations, see [colors for charts](/charts/colors-for-charts). diff --git a/packages/site/src/content/design-guidelines/charts/bar-chart/img/horizontal-bar-chart.png b/packages/site/src/content/design-guidelines/charts/bar-chart/img/horizontal-bar-chart.png new file mode 100644 index 0000000000..90b7be669e Binary files /dev/null and b/packages/site/src/content/design-guidelines/charts/bar-chart/img/horizontal-bar-chart.png differ diff --git a/packages/site/src/content/design-guidelines/charts/bar-chart/img/vertical-bar-chart.png b/packages/site/src/content/design-guidelines/charts/bar-chart/img/vertical-bar-chart.png new file mode 100644 index 0000000000..2309f5f567 Binary files /dev/null and b/packages/site/src/content/design-guidelines/charts/bar-chart/img/vertical-bar-chart.png differ diff --git a/packages/site/src/content/design-guidelines/charts/bullet-chart/bullet-chart.mdx b/packages/site/src/content/design-guidelines/charts/bullet-chart/bullet-chart.mdx new file mode 100644 index 0000000000..c18ab79415 --- /dev/null +++ b/packages/site/src/content/design-guidelines/charts/bullet-chart/bullet-chart.mdx @@ -0,0 +1,13 @@ +--- +id: Bullet chart +section: charts +--- +A **bullet chart** can be thought of as an extension to a bar chart that measures a dynamic value with thresholds and target values. While similar to [donut utilization charts](/charts/donut-utilization-chart), bullet charts can show underages and overages of data (below 0% and above 100%), visualize horizontally or vertically, and pack large amounts of information into a compact space. + +## Usage +Bullet charts are most often used to measure sets of performance data or utilization. They can be used for similar use cases as [donut utilization with threshhold charts](/charts/donut-utilization-chart#donut-utilization-threshold-examples). For example, a user can use a bullet chart to measure values of a set compared to the whole, while also illustrating related thresholds, target values, and underages or overages. + +When deciding which chart to use, consider the type of data you are dealing with and the importance of tracking underages or overages in that data. Also consider the amount of space you have to visualize the data and its surrounding information. Bullet charts consolidate data and therefore take up less space than donut charts. They fit very well within text-dense areas, since they can be horizontally or visually illustrated. Bullet charts can also measure data by percentages or integer values; donut charts cannot. + +### Example +Bullet chart \ No newline at end of file diff --git a/packages/site/src/content/design-guidelines/charts/bullet-chart/img/bullet-chart.png b/packages/site/src/content/design-guidelines/charts/bullet-chart/img/bullet-chart.png new file mode 100644 index 0000000000..ff1d783f6a Binary files /dev/null and b/packages/site/src/content/design-guidelines/charts/bullet-chart/img/bullet-chart.png differ diff --git a/packages/site/src/content/design-guidelines/charts/donut-chart/donut-chart.mdx b/packages/site/src/content/design-guidelines/charts/donut-chart/donut-chart.mdx new file mode 100644 index 0000000000..1f2132fc6b --- /dev/null +++ b/packages/site/src/content/design-guidelines/charts/donut-chart/donut-chart.mdx @@ -0,0 +1,25 @@ +--- +id: Donut chart +section: charts +--- +A **donut chart** represents relative amounts that must add up to 100%. + +## Usage +In donut charts, you can choose to use percentages or integer values to compare parts to the whole. When deciding which to use, consider the information that is most important to your user and what makes the most sense for your use case. For example, if a user knows they have 123 farm animals and they’re interested in knowing how many of those animals are cows, it probably makes more sense to use an integer value. If that same user is interested in knowing how much storage space they have left in their grain silo, a percentage might be better. + +Do not try to represent more than six categories in a donut chart. We recommend using the [colors for charts](/charts/colors-for-charts) guidelines to represent your data when thresholds are not present. + +The most common use cases for donut charts are: +- Showing the relationship of a set of values to a whole. +- Showing utilization for an object as a percentage (with or without thresholds). + +If you need to compare one category to another, consider using a [bar chart](/charts/bar-chart). + +### Example +Donut chart + +1. **Segment fill:** We recommend using [colors for charts](/charts/colors-for-charts) for different items within the donut chart. +2. **Segment padding:** Always provide 3px of padding between segments. +3. **Chart tooltip:** A tooltip will appear upon hover that states the name of the segment and corresponding value. For example, if the segment represents "Bugs," and the value being represented is 25, your chart tooltip would state, "Bugs: 25." +4. **Label:** When a donut chart is contained within a dashboard card, a label defines what the chart represents. The label may also represent the total value of the data set. If this optional representation is chosen, it should follow the format of **[total numeric value] + [data set label]** (example: "100 Issues"). The total numeric value should be rounded to two decimal places or less (14 characters max) and should be styled using 24px font in standard text color. The data set label cannot contain more than 24 characters and should be styled using 14px font in secondary text color. Center them within the donut and style as shown. If the label exceeds the max character count, place it outside of the donut and leave the center empty. +5. **Legend:** In order to be compliant with accessibility guidelines, a legend is necessary. Each variable on the legend should report their current value. \ No newline at end of file diff --git a/packages/site/src/content/design-guidelines/charts/donut-chart/img/donut-chart.png b/packages/site/src/content/design-guidelines/charts/donut-chart/img/donut-chart.png new file mode 100644 index 0000000000..097a74ea4a Binary files /dev/null and b/packages/site/src/content/design-guidelines/charts/donut-chart/img/donut-chart.png differ diff --git a/packages/site/src/content/design-guidelines/charts/donut-utilization-chart/donut-utilization-chart.mdx b/packages/site/src/content/design-guidelines/charts/donut-utilization-chart/donut-utilization-chart.mdx new file mode 100644 index 0000000000..727c9102cb --- /dev/null +++ b/packages/site/src/content/design-guidelines/charts/donut-utilization-chart/donut-utilization-chart.mdx @@ -0,0 +1,32 @@ +--- +id: Donut utilization chart +section: charts +--- +A **donut utlization chart** is a donut chart used specifically to show utilization metrics. + +## Usage +### Donut chart - Utilization +Donut utilization + +Donut utilization hover + +Donut utilization 2 + +1. **Unused segment fill:** The unused area of the donut chart will always remain at #EDEDED. +2. **Used segment fill:** We recommend using #0066cc for the used area of the donut chart. See [colors for charts](/charts/colors-for-charts) for other recommended color options. +3. **Utilization label:** Both percentages and whole numbers can be used to represent the utilization. +4. **Chart tooltip:** Since this is a utilization donut chart, the tooltip will display the percentage of data utilized. Chart tooltips only appear on hover over the utilization segment of the chart. We recommend stating the segment name and the utilization value being captured. For example, if the user is tracking GBps utilization, the chart tooltip would state "GBps utilization: 75%." + +### Donut chart - Utilization with threshold +Donut utilization with threshold + +1. **Threshold segment fill:** The outer segments of the chart are static and represent the thresholds for your use case. The example diagrams show utilization thresholds for a database and are used to let users know when they move from a safe zone into a danger zone. For threshold segments, use incremental shades of grey starting at #EDEDED then to #D2D2D2 then to #BBBBBB. Provide 3px of padding between each segment. +2. **Utilization segment fill:** This dynamic chart is a concentric circle within the donut thresholds and will represent the data set. For this chart, we recommend using the following colors: + - #0066cc before the data set has hit a threshold + - #F0AB00 once the data set has hit the warning threshold + - #C9190B once the data set has hit the danger threshold +3. **Legend:** The utilization segment color swatch will change in accordance to the chart. + +Donut utilization with threshold hover + +4. **Chart tooltip:** Chart tooltips appear on hover for both threshold segments and utilization segments. We recommend stating the threshold name, the segment name, and the value being represented. For example, if the threshold being met is "Danger," and the segment represents "Storage capacity," and the value being represented is 92%, your chart tooltip would state, "Danger: Storage capacity: 92%." We recommend stating the threshold name "at" the percentage the threshold begins, so a threshold name might read, "Warning at 60%." diff --git a/packages/site/src/content/design-guidelines/charts/donut-utilization-chart/img/donut-utilization-2.png b/packages/site/src/content/design-guidelines/charts/donut-utilization-chart/img/donut-utilization-2.png new file mode 100644 index 0000000000..9eeee8c1e8 Binary files /dev/null and b/packages/site/src/content/design-guidelines/charts/donut-utilization-chart/img/donut-utilization-2.png differ diff --git a/packages/site/src/content/design-guidelines/charts/donut-utilization-chart/img/donut-utilization-hover.png b/packages/site/src/content/design-guidelines/charts/donut-utilization-chart/img/donut-utilization-hover.png new file mode 100644 index 0000000000..8a31c00403 Binary files /dev/null and b/packages/site/src/content/design-guidelines/charts/donut-utilization-chart/img/donut-utilization-hover.png differ diff --git a/packages/site/src/content/design-guidelines/charts/donut-utilization-chart/img/donut-utilization-with-threshold-hover.png b/packages/site/src/content/design-guidelines/charts/donut-utilization-chart/img/donut-utilization-with-threshold-hover.png new file mode 100644 index 0000000000..93429771bd Binary files /dev/null and b/packages/site/src/content/design-guidelines/charts/donut-utilization-chart/img/donut-utilization-with-threshold-hover.png differ diff --git a/packages/site/src/content/design-guidelines/charts/donut-utilization-chart/img/donut-utilization-with-threshold.png b/packages/site/src/content/design-guidelines/charts/donut-utilization-chart/img/donut-utilization-with-threshold.png new file mode 100644 index 0000000000..33d32c335a Binary files /dev/null and b/packages/site/src/content/design-guidelines/charts/donut-utilization-chart/img/donut-utilization-with-threshold.png differ diff --git a/packages/site/src/content/design-guidelines/charts/donut-utilization-chart/img/donut-utilization.png b/packages/site/src/content/design-guidelines/charts/donut-utilization-chart/img/donut-utilization.png new file mode 100644 index 0000000000..55129e0dee Binary files /dev/null and b/packages/site/src/content/design-guidelines/charts/donut-utilization-chart/img/donut-utilization.png differ diff --git a/packages/site/src/content/design-guidelines/charts/legend-chart/legend-chart.mdx b/packages/site/src/content/design-guidelines/charts/legend-chart/legend-chart.mdx new file mode 100644 index 0000000000..83f9951e78 --- /dev/null +++ b/packages/site/src/content/design-guidelines/charts/legend-chart/legend-chart.mdx @@ -0,0 +1,6 @@ +--- +id: Legends +section: charts +--- + +A **legend chart** is a chart with a legend next to it, showing the different data entries or values being represented, often by category. A legend can be added to any chart type. \ No newline at end of file diff --git a/packages/site/src/content/design-guidelines/charts/line-chart/img/line-chart.png b/packages/site/src/content/design-guidelines/charts/line-chart/img/line-chart.png new file mode 100644 index 0000000000..88249bbbfa Binary files /dev/null and b/packages/site/src/content/design-guidelines/charts/line-chart/img/line-chart.png differ diff --git a/packages/site/src/content/design-guidelines/charts/line-chart/line-chart.mdx b/packages/site/src/content/design-guidelines/charts/line-chart/line-chart.mdx new file mode 100644 index 0000000000..da40ed1f78 --- /dev/null +++ b/packages/site/src/content/design-guidelines/charts/line-chart/line-chart.mdx @@ -0,0 +1,15 @@ +--- +id: Line chart +section: charts +--- +A **line chart** plots a series of discrete data samples to show continuous data and trend information. Sample values on the line can be measured and extracted. + +## Usage +The most common use case for line charts is to compare several data sets over a period of time. They can be used to project trends into the past or future. A best fit line is created and extended in both directions to do so, but the validity of the projection is not certain. If you want to show and compare categorical data, you may consider using a [bar chart](/charts/bar-chart). + +Multiple lines on the same chart allow the user to visualize relationships between varying data sets, such as correlated events, similarities or unexpected differences. We recommend displaying no more than 6 lines on a single graph to avoid confusion. + +### Example +Line chart + +Line charts can optionally represent data points as dots on the line. If so, the same interaction that occurs when hovering over one in an [area chart](/charts/area-chart) will occur in line charts. For line colors, we recommend consulting [colors for charts](/charts/colors-for-charts). \ No newline at end of file diff --git a/packages/site/src/content/design-guidelines/charts/pie-chart/img/pie-chart.png b/packages/site/src/content/design-guidelines/charts/pie-chart/img/pie-chart.png new file mode 100644 index 0000000000..494788d56e Binary files /dev/null and b/packages/site/src/content/design-guidelines/charts/pie-chart/img/pie-chart.png differ diff --git a/packages/site/src/content/design-guidelines/charts/pie-chart/pie-chart.mdx b/packages/site/src/content/design-guidelines/charts/pie-chart/pie-chart.mdx new file mode 100644 index 0000000000..a0236e7056 --- /dev/null +++ b/packages/site/src/content/design-guidelines/charts/pie-chart/pie-chart.mdx @@ -0,0 +1,16 @@ +--- +id: Pie chart +section: charts +--- +A **pie chart** is commonly used to show percentages or proportional data. + +## Usage +Choose a pie chart when you need to compare a set of values to a whole. For example, you might choose a pie chart when visualizing the number of sales made by a team of five people; each segment of the chart represents one salesperson’s performance in the context of the rest of the team. The sum of all of the segments of the chart must equal 100%, and the data points should be mutually exclusive. It is recommended that there are no more than six segments per single pie chart. + +A pie chart may be the wrong choice when you need to compare categories to one another, because it can be difficult to distinguish small differences between segments. If you wish to compare values to each other, a [bar chart](/charts/bar-chart) may be a more effective pattern. + +### Example +Pie chart + +1. **Pie chart fill:** We recommend fill colors based on the [colors for charts](/charts/colors-for-charts). +2. **Legend:** Each variable on the legend should report their current value. diff --git a/packages/site/src/content/design-guidelines/charts/scatter-chart/scatter-chart.mdx b/packages/site/src/content/design-guidelines/charts/scatter-chart/scatter-chart.mdx new file mode 100644 index 0000000000..fe165394a7 --- /dev/null +++ b/packages/site/src/content/design-guidelines/charts/scatter-chart/scatter-chart.mdx @@ -0,0 +1,5 @@ +--- +id: Scatter chart +section: charts +--- + A **scatter chart** uses dots to represent values in a chart. These dots can be added to area and line charts to outline specific interactive points along a line. \ No newline at end of file diff --git a/packages/site/src/content/design-guidelines/charts/sparkline-chart/img/sparkline.png b/packages/site/src/content/design-guidelines/charts/sparkline-chart/img/sparkline.png new file mode 100644 index 0000000000..bce898a8e4 Binary files /dev/null and b/packages/site/src/content/design-guidelines/charts/sparkline-chart/img/sparkline.png differ diff --git a/packages/site/src/content/design-guidelines/charts/sparkline-chart/sparkline-chart.mdx b/packages/site/src/content/design-guidelines/charts/sparkline-chart/sparkline-chart.mdx new file mode 100644 index 0000000000..d6049d5fd5 --- /dev/null +++ b/packages/site/src/content/design-guidelines/charts/sparkline-chart/sparkline-chart.mdx @@ -0,0 +1,14 @@ +--- +id: Sparkline chart +section: charts +--- + +A **sparkline** is a small chart that helps users analyze data and understand trends and patterns. + +## Usage +Sparklines are commonly used in tables, reports, and dashboards. A common use case is displaying utilization in an environment over time. Sparklines help to show trends in a series of values or to highlight maximum and minimum values. We recommend using sparklines alone without an axis and placing the name of the item being visualized underneath the chart. + +### Example +Sparkline + +We recommend showing sparklines without an x or y-axis. Depending on space, a label can be placed underneath or to the left of the sparkline naming its visualized item. diff --git a/packages/site/src/content/design-guidelines/charts/stacked-chart/img/horizontal-stacked-bar-chart.png b/packages/site/src/content/design-guidelines/charts/stacked-chart/img/horizontal-stacked-bar-chart.png new file mode 100644 index 0000000000..55e669538a Binary files /dev/null and b/packages/site/src/content/design-guidelines/charts/stacked-chart/img/horizontal-stacked-bar-chart.png differ diff --git a/packages/site/src/content/design-guidelines/charts/stacked-chart/img/vertical-stacked-bar-chart.png b/packages/site/src/content/design-guidelines/charts/stacked-chart/img/vertical-stacked-bar-chart.png new file mode 100644 index 0000000000..bc3c84b339 Binary files /dev/null and b/packages/site/src/content/design-guidelines/charts/stacked-chart/img/vertical-stacked-bar-chart.png differ diff --git a/packages/site/src/content/design-guidelines/charts/stacked-chart/stacked-chart.mdx b/packages/site/src/content/design-guidelines/charts/stacked-chart/stacked-chart.mdx new file mode 100644 index 0000000000..5a7f2e9e97 --- /dev/null +++ b/packages/site/src/content/design-guidelines/charts/stacked-chart/stacked-chart.mdx @@ -0,0 +1,17 @@ +--- +id: Stack chart +section: charts +--- +A **stacked bar chart** describes totals while allowing a degree of internal breakdown of its data. Stacked bar charts can be illustrated vertically and horizontally depending on available space and the described data. + +## Usage +An advantageous feature of stacked bar charts is the ability to reorder the stacked bars without changing the chart's overall total. + +#### Example +Horizontal stacked bar chart + +
+ +Vertical stacked bar chart + +The first series name is represented by the topmost stacked bar, and the last series name is represented by the bottommost stacked bar. For recommendations on series colors, see [colors for charts](/charts/colors-for-charts). diff --git a/packages/site/src/content/design-guidelines/charts/themed-charts/themed-charts.mdx b/packages/site/src/content/design-guidelines/charts/themed-charts/themed-charts.mdx new file mode 100644 index 0000000000..2c765a4668 --- /dev/null +++ b/packages/site/src/content/design-guidelines/charts/themed-charts/themed-charts.mdx @@ -0,0 +1,5 @@ +--- +id: Themes +section: charts +--- +A **themed chart** is a chart with different theme and color treatments applied to it. Themed charts can help visually distinguish between different categories and data collection points plotted on the graph. \ No newline at end of file diff --git a/packages/site/src/content/design-guidelines/charts/threshold-chart/threshold-chart.mdx b/packages/site/src/content/design-guidelines/charts/threshold-chart/threshold-chart.mdx new file mode 100644 index 0000000000..467decbe8c --- /dev/null +++ b/packages/site/src/content/design-guidelines/charts/threshold-chart/threshold-chart.mdx @@ -0,0 +1,5 @@ +--- +id: Threshold chart +section: charts +--- +A **threshold chart** can be used to visually specify a threshold for certain variables on the chart. \ No newline at end of file diff --git a/packages/site/src/content/design-guidelines/charts/tooltip-chart/img/chart-tooltip.png b/packages/site/src/content/design-guidelines/charts/tooltip-chart/img/chart-tooltip.png new file mode 100644 index 0000000000..d296a5735a Binary files /dev/null and b/packages/site/src/content/design-guidelines/charts/tooltip-chart/img/chart-tooltip.png differ diff --git a/packages/site/src/content/design-guidelines/charts/tooltip-chart/tooltip-chart.mdx b/packages/site/src/content/design-guidelines/charts/tooltip-chart/tooltip-chart.mdx new file mode 100644 index 0000000000..10a4cf2234 --- /dev/null +++ b/packages/site/src/content/design-guidelines/charts/tooltip-chart/tooltip-chart.mdx @@ -0,0 +1,17 @@ +--- +id: Tooltips +section: charts +--- + +A **tooltip chart** is a chart with tooltips that appear when users hover over items within it. + +## Usage +For charts that have more than one data set graphed, a complex chart tooltip can be used to give more detail to a specific point in the multiple data series. This works well for [line](/charts/line-chart), [area](/charts/area-chart), or [stacked](/charts/stack-chart) charts, where data sets may intersect over a period of time. + +## Example +On hover, the tooltip shows all the corresponding data points that match a point along the x-axis. Tooltip content could also include any additional information that might be important to the user. + +Example of tooltip in line chart + + + diff --git a/packages/site/src/content/design-guidelines/components/components.css b/packages/site/src/content/design-guidelines/components/components.css new file mode 100644 index 0000000000..02498d8393 --- /dev/null +++ b/packages/site/src/content/design-guidelines/components/components.css @@ -0,0 +1,6 @@ +.ws-docs-content-img { + text-align: center; + margin-inline: auto; + width: 100%; + max-width: 700px; +} diff --git a/packages/site/src/content/design-guidelines/content/about.mdx b/packages/site/src/content/design-guidelines/content/about.mdx new file mode 100644 index 0000000000..5384fe7cd0 --- /dev/null +++ b/packages/site/src/content/design-guidelines/content/about.mdx @@ -0,0 +1,38 @@ +--- +id: About UX writing +section: UX writing +sortValue: 1 + +--- +The words in a user interface (UI), commonly referred to as "UX copy" or "microcopy," are just as important as the visual design and layout. UX copy is an essential element of design that can be used strategically to drive better UX decisions and guide users to succeed. + +Our UX writing guidelines provide a place for UX professionals like you to learn about designing with words. + +Anyone involved in UX—researchers, designers, developers, content strategists, and more—can use this guide for building better product experiences with content design and strategy. + +## Style guide goal + +As a PatternFly community, our goal with this style guide is to help UX professionals: +- Create clarity and consistency across products and applications. +- Make products sound more conversational and human. +- Use written content to create unified, on-brand experiences for all users. + +With that said, we recognize that the PatternFly way is not the *only* way. This guide isn’t meant to: +- Overrule another style guide. +- Provide a complete list of all writing rules across all channels. +- Serve as hard requirements that everyone must follow. + +## Additional resources + +We provide thorough guidance across our UX writing guidelines, but you may find the following supplementary resources to also be useful. + +- For component-specific microcopy guidance, see the component's [design guidelines](/components/about-modal/design-guidelines). +- For microcopy guidance that’s not included in this guide, see [IBM Carbon’s UX content guidelines](https://www.carbondesignsystem.com/guidelines/content/overview). +- For Red Hat product terminology and documentation standards, see [Red Hat's supplementary style guide for Red Hat product documentation](https://redhat-documentation.github.io/supplementary-style-guide/#introduction). +- For additional terminology guidance, use [Merriam-Webster’s online dictionary](https://www.merriam-webster.com/). + +If you're writing for Red Hat products and find conflicting information in these resources, default to PatternFly's guidance. + +## Contribute + +In true Flyer fashion, we keep this style guide open. Contribute your ideas through [GitHub](https://github.com/orgs/patternfly/discussions). diff --git a/packages/site/src/content/design-guidelines/content/brand-voice-and-tone.mdx b/packages/site/src/content/design-guidelines/content/brand-voice-and-tone.mdx new file mode 100644 index 0000000000..567bbab640 --- /dev/null +++ b/packages/site/src/content/design-guidelines/content/brand-voice-and-tone.mdx @@ -0,0 +1,113 @@ +--- +id: Brand voice and tone +section: UX writing +--- + +In a business context, brand is the identity of a company that people recognize based on an emotional and psychological connection, as well as factual information. +It is important to recognize that, while you can guide users through your products, and influence their experience, you cannot fully control the way users perceive your brand. A large part of your brand identity is shaped by your users’ perception. + +What you can do to encourage a brand identity is carefully and intentionally choose the words you use. All of your UX copy should align with your company’s brand to contribute to a consistent and authentic experience across every content channel users interact with. + +To keep your UX copy on-brand, consider style, voice, and tone: + +- **Style** is the way you use grammar, punctuation, and syntax. It’s influenced by how your words work together and what effect your writing has on the user. + +- **Voice** is the personality that’s reflected in your writing. For example, your content's voice may be "helpful." + +- **Tone** encompasses the user’s emotions that need to be accounted for and the resulting approach you must take. It is important to choose a tone that's appropriate for the context of your content. For example, your content's tone may be "casual" or "professional." + +## Voice + +Let’s consider how we use the Red Hat brand voice in our UX copy. If Red Hat were a person, they would be: + +- Helpful but humble (not arrogant). +- Authentic but adaptable (not stubborn). +- Open but ordered (not chaotic). +- Brave but balanced (not reckless). + +### Voice traits +To reflect the Red Hat voice in our products' UX copy, we consider UX voice traits. Each voice trait is an extension of the Red Hat voice. + +
+ +| **Red Hat voice traits** | **UX voice traits** | +|----------------------------------------|---------------------| +| Helpful but humble (not arrogant) | Friendly | +| Authentic but adaptable (not stubborn) | Approachable | +| Open but ordered (not chaotic) | Collaborative | +| Brave but balanced (not reckless) | Inventive | + +
+ +When crafting your brand voice, align your voice traits to any company or team values that you have. + +You can’t *tell* your users what your voice is. You need to *show* them who you are in your writing. To do this, consider utilizing "Don't and Do” charts. For example, Red Hat's UX copy voice charts look like: + +#### Voice trait: Friendly + +**Description**: Our #1 focus is the user. We make them feel welcome and create a sense of belonging and understanding. + +
+ +| **Don't** | **Do** | +|--------|-----------| +| Don’t include fluff or long sentences that run on and on. | Do be clear and concise for users of all skills and abilities. +| | Do write how you speak, but add extra polish. || +| | Do focus on comprehension and use plain language. || + +
+ +#### Voice trait: Approachable + +**Description**: People are comfortable engaging with us. We’re open to listening and changing our ways when better ideas come along. + +
+ +| **Don't** | **Do** | +|--------|-----------| +| Don’t use jargon, idioms, bizspeak, or formal language.| Do say what you mean. | +| | Do be direct and transparent with descriptive, specific language. | + +
+ +#### Voice trait: Collaborative + +**Description**: We embody Red Hat’s open source mission with our collaborative working style and our sense of community. + +
+ +| **Don't** | **Do** | +|--------|-----------| + | Don’t rely on inside jokes, colloquial expressions, culture-specific examples, or other alienating language to get your point across.| Do deliver content in a way that includes everyone. | +| Don’t use “I” too much. Make the user the star of every story you tell.| Do use “you” and the active voice to put emphasis on the user and the power in their hands. | + +
+ +#### Voice trait: Inventive + +**Description**: We have a fearless edge, challenging the assumption that UX is for a niche group of techies. We’re also not afraid to share our ideas and welcome new ones. + +
+ +| **Don't** | **Do** | +|--------|-----------| +| Don’t belittle others or make jokes at their expense. We can laugh at ourselves but not at our users. | Do deliver concepts and ideas with an air of confident simplicity. | +| Don’t use others as examples of what not to do.| Do add real-world, global-friendly examples.| + +
+ +If you’re contributing content (such as website copy or documentation) to PatternFly, keep Red Hat's voice traits in mind. If you’re adopting PatternFly as part of another organization, you should go through a similar process to document the attributes of your own brand voice. + +## Tone +Unlike voice, tone can change. To determine tone, ask yourself the following questions: + +- What does the user need at this time? +- What is the user thinking? +- How is the user feeling? + +The tone you use is based on the answers to those questions. PatternFly’s tone typically varies between casual, professional, informative, and supportive, depending on context. For example: + +- You’re writing a blog post about a PatternFly event—exciting! Your tone is **casual**. +- You’re writing a social media post addressing a product delay or failure—not exciting. Your tone is **professional**. +- You’re writing an email to inform a user of an overdue payment. Your tone is **informative** and **professional**. +- You’re guiding a user through a new interface. Your tone is **informative** and **supportive**. diff --git a/packages/site/src/content/design-guidelines/content/capitalization.mdx b/packages/site/src/content/design-guidelines/content/capitalization.mdx new file mode 100644 index 0000000000..72817a5cfe --- /dev/null +++ b/packages/site/src/content/design-guidelines/content/capitalization.mdx @@ -0,0 +1,71 @@ +--- +id: Capitalization +section: UX writing +--- + +# Capitalization guidelines + +Consistent capitalization adds clarity and creates unity across product UIs. PatternFly recommends writing in sentence case for all titles, headings, subtitles, or subheadings. **Sentence case** capitalizes only the first letter of the first word. The only exceptions to this are proper nouns, product names, acronyms, and initialisms, all of which should be capitalized. + +For example: “When you use PatternFly’s design resources, you get helpful tips and best practices.” + +**Above all else, your main goal should be consistency.** You may need to use different capitalization standards depending on what you're designing, but be sure to keep the capitalization within your product area consistent. + +## Red Hat product UIs + +When you write for a product, make sure you adhere to the following capitalization patterns. + +- Default to sentence case across all UI elements, including navigation items, page titles, buttons, and so on. + +
A side navigation menu, expanded to show capitalization styles.
+ +- Keep capitalization for custom resources the same as the capitalization style used during creation. + - For example, if a custom resource name was created with all lowercase letters, don't change any of the letters to uppercase when referencing this resource. +- Capitalize product feature names when they’re used as proper nouns or when they refer to a capitalized UI term (like a navigation item). Write them in lowercase when they’re used to describe generic concepts. For example: + +
+ + | **Feature name** | **UI text** | **Reasoning** | + |------------------|--------------|------------------| + | Compliance | “Check your system **compliance** using Red Hat Insights **Compliance**.” | The first “compliance” is lowercase since it refers to a concept. The second “compliance” refers to a specific feature offered on cloud.redhat.com, so it is capitalized. | + | Sources | “Add a *source* by going to **Settings > *Sources*.**” "Check the *Sources* table for status."

Button text: "Add *source*" | “Sources” is only capitalized when it directly refers to a subsection, feature, or location in the UI. "Source" is lowercase in the button text because button labels should always be in sentence case. | +
+ +### Capitalization in breadcrumb trails + +It is common for page titles to appear as an item in a breadcrumb trail. Match the capitalization of the original page title in the corresponding breadcrumb item even when the item does not use sentence case, or when a breadcrumb trail contains mixed capitalization standards. + +
A breadcrumb trail with mixed capitalization styles due to page title formatting.
+ +Sometimes, user-named items will appear in a breadcrumb trail. If a custom resource name (for example, "customResource-name") is included in the breadcrumb trail, you should match the capitalization of the users' original entry. + +

A breadcrumb trail with mixed capitalization styles due to custom resource naming.

+ +### Tools outside your product portfolio + +If you’re referencing tools that aren't part of your company’s product portfolio, write the product names as they appear in the respective company’s documentation. + +For example, if you’re referencing a product in Amazon Web Services that Amazon capitalizes, then you should also capitalize it in your writing. + +## PatternFly website documentation + +There are additional capitalization guidelines that you should follow if you contribute to any PatternFly content, like documentation or microcopy. + +- Use sentence case for page titles, menu items, navigation items, headings, subtitles, and subheadings. + +- Capitalize proper nouns, product names, acronyms, and initialisms. For example: React, PatternFly, and HTML. + +Take the PatternFly website as an example, where all navigation items, button text, and headings are written in sentence case and all proper nouns are in title case: + +
A PatternFly website screenshot showing sentence case copy. +
+ +- Write all components in lowercase unless they start a sentence. + +- Format any code snippets according to the standards used for their language. + +For example, the following image from our component documentation uses lowercase for the component name ("card") and capitalizes code appropriately ("isCompact" and "isLarge"). + +
Component documentation showing sentence case copy and capitalization styling for code. +
+ diff --git a/packages/site/src/content/design-guidelines/content/error-messages.mdx b/packages/site/src/content/design-guidelines/content/error-messages.mdx new file mode 100644 index 0000000000..391abbffd2 --- /dev/null +++ b/packages/site/src/content/design-guidelines/content/error-messages.mdx @@ -0,0 +1,183 @@ +--- +id: Error messages +section: UX writing +--- + +## Error message structure + +A user typically sees an error message when they attempt to perform an action but cannot continue because something isn’t right. + +Make your error messages brief yet descriptive. A useful pattern to follow is to include a description, reason, and resolution: +- **Description**: What happened? + - For example, if the user's login failed. +- **Reason**: Why did it happen? + - For example, if an SSH key doesn't allow auto-login. +- **Resolution**: How can it be resolved? + - For example, a user may need to manually log in to the host. + +Combine your description, reason, and resolution with a title to create a strong error message. For example: + +- **Description**: _**Login failed**_ +- **Reason**: _The SSH key for auto-login is either not available, is unauthorized, or is password protected._ +- **Resolution**: _To manually log in to the host, click **Log in.**_ + +## Best practices for writing error messages + +Keep these best practices in mind when crafting error messages: + +#### Don’t blame users + +A user should never feel like the error is their fault. Avoid language like “You did something wrong.” Depending on your message, you may need to use the passive voice instead of the active voice so that you don't assign blame to the user. + +
+ +| **Before** | **After** | +|:-----------------:|:-----------------:| +| You did not provide your authentication credentials. | Authentication credentials weren't provided.| + +
+ +#### Give users a next step + +A user should never feel stuck. If they’re hit with an error, give them the information they need to continue with their task. + +
+ +| **Before** | **After** | +|:-------------:|:------------------:| +| Your list already has the maximum number of items. You are not able to continue customizing. | Your list has the maximum number of items. To continue customizing, remove an item.| + +
+ +#### Avoid jargon + +Error messages are frustrating enough without technical terms that users might not understand. Avoid jargon and use terms that are familiar to your users. + +
+ +| **Before** | **After** | +|:---------------:|:-----------------:| +| Error code 5959: Outdated version information. Task termination pending. | Your task is outdated. To keep it active, update its version.| + +
+ +#### Include the right amount of description + +Tell your user what is wrong. An error without an explanation can add to their frustration and prevent them from finding a solution. + +
+ +| **Before** | **After** | +|:-------------:|:----------------:| +| An error occurred. The email cannot be sent. | To send this email, turn on your email permissions in user settings.| + +
+ +However, don’t include too much information. The user doesn’t need to know exactly what is going on behind the scenes. Only give them information about what went wrong and what they can do next. + +
+ +| **Before** | **After** | +|:------------:|:------------:| +| Your information cannot be saved. Our system is currently designed to accommodate 1 record per user. The system memory is unable to store more at this time. | Only 1 record can be saved. To continue, remove one of your records.| + +
+ +#### Lead with the benefit + +When providing users with a resolution, start the sentence with their goal ("the benefit"), followed by what they need to do to continue. + +
+ +| **Before** | **After** | +|:-----------------:|:----------------:| +| Click **Log in** to manually log in. | To manually log in, click **Log in.**| + +
+ +## 404 error pages + +A **404 page** is an error page that a user lands on when the content they're trying to view either doesn’t exist or can’t be found. 404 pages are named after the type of error they communicate: “Error 404: Not found.” + +Write 404 pages with [error message best practices](/ux-writing/error-messages) in mind: Explain what a 404 error is, define how users can proceed, and provide the tools they need to get there. + +Effective 404 pages combine several elements to regroup, redirect, and empower lost users to reach their desired destination or find a new one. + +The PatternFly 404 page with added call outs to mark four main elements: Heading, next steps, suggested content, and a link to the home page. + +1. **Heading:** Communicates what a 404 error is in plain language that users can understand. Avoid including “404” or “404 error” unless it’s clearly defined after: “404: That page no longer exists.” Write 404 headings without end punctuation (no period), unless punctuated page headings align with your brand or product. + +1. **Next steps:** Defines how users can proceed, typically by inviting them to search the site, explore suggested content, or both. Always write the next steps in full sentences and punctuate accordingly. + +1. **Suggested content (optional):** Points users toward relevant pages such as onboarding information, reference guides, or FAQs. + +1. **Link to home page:** Provides a quick and easy way for users to navigate back to your site’s home page. + +## Best practices for 404 error content + +Consider your 404 page as a flight path instead of a dead end. Use clear, informative microcopy to point users in the right direction. To see an example, visit [PatternFly’s 404 page](/404/). + +To create effective 404 pages, follow these best practice guidelines: + +1. **Use understandable language.** Skip technical jargon by writing your 404 heading in plain and specific terms. + +
+ + | **Before** | **After** | + |:-----------:|:-----------:| + | Error 404: Not found| 404: That page no longer exists | + +
+ +1. **Avoid exclamations, colloquialisms, and excessive humor.** Write 404 headings to be informative and repeatable. When users land on a page more than once, jokes grow stale. Steer clear of extraneous words like “Uh oh!” or “Oops!”. + +
+ + | **Before** | **After** | + |:-----------:|:-----------:| + | Uh oh, spaghetti-o! We lost that one | We lost that page | + | Oops! We dropped the ball | We couldn't find that page | + | Huh, that's odd... | That page no longer exists | + +
+ +1. **Avoid assigning blame to the user.** If your brand doesn’t use first-person plural (“we”) pronouns, use “that page” or “this page” as your heading's subject instead. + +
+ + | **Before** | **After** | + |:-----------:|:-----------:| + | Your search came up empty | We can't find that page | + | The page you're trying to reach doesn't exist | That page no longer exists | + +
+ +1. **Turn error into opportunity.** Always provide a link back to your site’s home page, and include supplemental next steps below your heading to encourage users to explore options beyond just going back to where they came from. + +
+ + | **Before** | **After** | + |:-----------:|:-----------:| + | That page doesn't exist. | Another page might have what you need, so try searching PatternFly. | + +
+ +1. **Channel your brand voice.** Bland, impersonal error messages can be frustrating. Infuse your 404 page content with brand personality to support a more inviting site experience. + +
+ + | **Before** | **After** | + |:-----------:|:-----------:| + | **Error 404: Not found**
Requested URL not found on this server. Please try again. | **404: We couldn't find that page**
Another page might have what you need, so try searching PatternFly. | + +
+ +1. **Write for all audiences.** Be mindful of localization. Puns, wordplay, and cultural references may not localize for all users. Prioritize clarity over cleverness. + +
+ + | **Before** | **After** | + |:-----------:|:-----------:| + | **404: Not all who wander are lost...**
But this page is. Search again or find your way back home. | **404: We lost that page**
Let's find you a better one. Try a new search or return home. | + +
diff --git a/packages/site/src/content/design-guidelines/content/img/404-page.png b/packages/site/src/content/design-guidelines/content/img/404-page.png new file mode 100644 index 0000000000..68bb3af40f Binary files /dev/null and b/packages/site/src/content/design-guidelines/content/img/404-page.png differ diff --git a/packages/site/src/content/design-guidelines/content/img/Testing.png b/packages/site/src/content/design-guidelines/content/img/Testing.png new file mode 100644 index 0000000000..7cdfac952b Binary files /dev/null and b/packages/site/src/content/design-guidelines/content/img/Testing.png differ diff --git a/packages/site/src/content/design-guidelines/content/img/active.png b/packages/site/src/content/design-guidelines/content/img/active.png new file mode 100644 index 0000000000..18e28eefa2 Binary files /dev/null and b/packages/site/src/content/design-guidelines/content/img/active.png differ diff --git a/packages/site/src/content/design-guidelines/content/img/basic-breadcrumb.png b/packages/site/src/content/design-guidelines/content/img/basic-breadcrumb.png new file mode 100644 index 0000000000..d95cb33ea2 Binary files /dev/null and b/packages/site/src/content/design-guidelines/content/img/basic-breadcrumb.png differ diff --git a/packages/site/src/content/design-guidelines/content/img/breadcrumb-custom-item.png b/packages/site/src/content/design-guidelines/content/img/breadcrumb-custom-item.png new file mode 100644 index 0000000000..10df62fff9 Binary files /dev/null and b/packages/site/src/content/design-guidelines/content/img/breadcrumb-custom-item.png differ diff --git a/packages/site/src/content/design-guidelines/content/img/component-docs.png b/packages/site/src/content/design-guidelines/content/img/component-docs.png new file mode 100644 index 0000000000..0886c70489 Binary files /dev/null and b/packages/site/src/content/design-guidelines/content/img/component-docs.png differ diff --git a/packages/site/src/content/design-guidelines/content/img/component-example-text.png b/packages/site/src/content/design-guidelines/content/img/component-example-text.png new file mode 100644 index 0000000000..970220d398 Binary files /dev/null and b/packages/site/src/content/design-guidelines/content/img/component-example-text.png differ diff --git a/packages/site/src/content/design-guidelines/content/img/concise.png b/packages/site/src/content/design-guidelines/content/img/concise.png new file mode 100644 index 0000000000..4fd768618f Binary files /dev/null and b/packages/site/src/content/design-guidelines/content/img/concise.png differ diff --git a/packages/site/src/content/design-guidelines/content/img/conversational.png b/packages/site/src/content/design-guidelines/content/img/conversational.png new file mode 100644 index 0000000000..48fce043f2 Binary files /dev/null and b/packages/site/src/content/design-guidelines/content/img/conversational.png differ diff --git a/packages/site/src/content/design-guidelines/content/img/copydoc.png b/packages/site/src/content/design-guidelines/content/img/copydoc.png new file mode 100644 index 0000000000..f565f39f56 Binary files /dev/null and b/packages/site/src/content/design-guidelines/content/img/copydoc.png differ diff --git a/packages/site/src/content/design-guidelines/content/img/desguidelines1.png b/packages/site/src/content/design-guidelines/content/img/desguidelines1.png new file mode 100644 index 0000000000..127998f56d Binary files /dev/null and b/packages/site/src/content/design-guidelines/content/img/desguidelines1.png differ diff --git a/packages/site/src/content/design-guidelines/content/img/desguidelines2.png b/packages/site/src/content/design-guidelines/content/img/desguidelines2.png new file mode 100644 index 0000000000..6c283bd5ea Binary files /dev/null and b/packages/site/src/content/design-guidelines/content/img/desguidelines2.png differ diff --git a/packages/site/src/content/design-guidelines/content/img/desguidelines3.png b/packages/site/src/content/design-guidelines/content/img/desguidelines3.png new file mode 100644 index 0000000000..13deb62c18 Binary files /dev/null and b/packages/site/src/content/design-guidelines/content/img/desguidelines3.png differ diff --git a/packages/site/src/content/design-guidelines/content/img/elements-example.png b/packages/site/src/content/design-guidelines/content/img/elements-example.png new file mode 100644 index 0000000000..c2c8970b89 Binary files /dev/null and b/packages/site/src/content/design-guidelines/content/img/elements-example.png differ diff --git a/packages/site/src/content/design-guidelines/content/img/error.png b/packages/site/src/content/design-guidelines/content/img/error.png new file mode 100644 index 0000000000..90c9e34dc1 Binary files /dev/null and b/packages/site/src/content/design-guidelines/content/img/error.png differ diff --git a/packages/site/src/content/design-guidelines/content/img/longurl.png b/packages/site/src/content/design-guidelines/content/img/longurl.png new file mode 100644 index 0000000000..bb59957a0c Binary files /dev/null and b/packages/site/src/content/design-guidelines/content/img/longurl.png differ diff --git a/packages/site/src/content/design-guidelines/content/img/navigation-capitalization.png b/packages/site/src/content/design-guidelines/content/img/navigation-capitalization.png new file mode 100644 index 0000000000..9974ee85da Binary files /dev/null and b/packages/site/src/content/design-guidelines/content/img/navigation-capitalization.png differ diff --git a/packages/site/src/content/design-guidelines/content/img/pf-component-caps.png b/packages/site/src/content/design-guidelines/content/img/pf-component-caps.png new file mode 100644 index 0000000000..e3a5485c82 Binary files /dev/null and b/packages/site/src/content/design-guidelines/content/img/pf-component-caps.png differ diff --git a/packages/site/src/content/design-guidelines/content/img/pf-home-caps.png b/packages/site/src/content/design-guidelines/content/img/pf-home-caps.png new file mode 100644 index 0000000000..85ebf1b851 Binary files /dev/null and b/packages/site/src/content/design-guidelines/content/img/pf-home-caps.png differ diff --git a/packages/site/src/content/design-guidelines/content/img/simple-tense.png b/packages/site/src/content/design-guidelines/content/img/simple-tense.png new file mode 100644 index 0000000000..d04acc3b91 Binary files /dev/null and b/packages/site/src/content/design-guidelines/content/img/simple-tense.png differ diff --git a/packages/site/src/content/design-guidelines/content/img/sliderelements.png b/packages/site/src/content/design-guidelines/content/img/sliderelements.png new file mode 100644 index 0000000000..c5f28ea5e7 Binary files /dev/null and b/packages/site/src/content/design-guidelines/content/img/sliderelements.png differ diff --git a/packages/site/src/content/design-guidelines/content/img/submit-form.png b/packages/site/src/content/design-guidelines/content/img/submit-form.png new file mode 100644 index 0000000000..21b0b31c1a Binary files /dev/null and b/packages/site/src/content/design-guidelines/content/img/submit-form.png differ diff --git a/packages/site/src/content/design-guidelines/content/img/truncation1@2x.jpg b/packages/site/src/content/design-guidelines/content/img/truncation1@2x.jpg new file mode 100644 index 0000000000..0d9054dac0 Binary files /dev/null and b/packages/site/src/content/design-guidelines/content/img/truncation1@2x.jpg differ diff --git a/packages/site/src/content/design-guidelines/content/img/truncation2@2x.jpg b/packages/site/src/content/design-guidelines/content/img/truncation2@2x.jpg new file mode 100644 index 0000000000..12a6ead50d Binary files /dev/null and b/packages/site/src/content/design-guidelines/content/img/truncation2@2x.jpg differ diff --git a/packages/site/src/content/design-guidelines/content/img/truncation3@2x.jpg b/packages/site/src/content/design-guidelines/content/img/truncation3@2x.jpg new file mode 100644 index 0000000000..ebf6702401 Binary files /dev/null and b/packages/site/src/content/design-guidelines/content/img/truncation3@2x.jpg differ diff --git a/packages/site/src/content/design-guidelines/content/img/truncation4@2x.jpg b/packages/site/src/content/design-guidelines/content/img/truncation4@2x.jpg new file mode 100644 index 0000000000..812f08ea25 Binary files /dev/null and b/packages/site/src/content/design-guidelines/content/img/truncation4@2x.jpg differ diff --git a/packages/site/src/content/design-guidelines/content/img/truncation5@2x.jpg b/packages/site/src/content/design-guidelines/content/img/truncation5@2x.jpg new file mode 100644 index 0000000000..5d173e636b Binary files /dev/null and b/packages/site/src/content/design-guidelines/content/img/truncation5@2x.jpg differ diff --git a/packages/site/src/content/design-guidelines/content/img/truncation6@2x.jpg b/packages/site/src/content/design-guidelines/content/img/truncation6@2x.jpg new file mode 100644 index 0000000000..71c21bd8a1 Binary files /dev/null and b/packages/site/src/content/design-guidelines/content/img/truncation6@2x.jpg differ diff --git a/packages/site/src/content/design-guidelines/content/img/truncation7@2x.jpg b/packages/site/src/content/design-guidelines/content/img/truncation7@2x.jpg new file mode 100644 index 0000000000..8c7ec808c9 Binary files /dev/null and b/packages/site/src/content/design-guidelines/content/img/truncation7@2x.jpg differ diff --git a/packages/site/src/content/design-guidelines/content/img/truncation8@2x.jpg b/packages/site/src/content/design-guidelines/content/img/truncation8@2x.jpg new file mode 100644 index 0000000000..fdadd5e3c2 Binary files /dev/null and b/packages/site/src/content/design-guidelines/content/img/truncation8@2x.jpg differ diff --git a/packages/site/src/content/design-guidelines/content/img/truncation9@2x.jpg b/packages/site/src/content/design-guidelines/content/img/truncation9@2x.jpg new file mode 100644 index 0000000000..50e28902e6 Binary files /dev/null and b/packages/site/src/content/design-guidelines/content/img/truncation9@2x.jpg differ diff --git a/packages/site/src/content/design-guidelines/content/img/useful.png b/packages/site/src/content/design-guidelines/content/img/useful.png new file mode 100644 index 0000000000..7848c9b84c Binary files /dev/null and b/packages/site/src/content/design-guidelines/content/img/useful.png differ diff --git a/packages/site/src/content/design-guidelines/content/img/user-menu-example.png b/packages/site/src/content/design-guidelines/content/img/user-menu-example.png new file mode 100644 index 0000000000..d1e2541951 Binary files /dev/null and b/packages/site/src/content/design-guidelines/content/img/user-menu-example.png differ diff --git a/packages/site/src/content/design-guidelines/content/numerics.mdx b/packages/site/src/content/design-guidelines/content/numerics.mdx new file mode 100644 index 0000000000..ad36d4cc34 --- /dev/null +++ b/packages/site/src/content/design-guidelines/content/numerics.mdx @@ -0,0 +1,101 @@ +--- +id: Numerics +section: UX writing +--- + +## Font styling + +If needed, we offer a font modifier `.pf-v6-m-tabular-nums` that applies tabular styling to numerals. [Learn more about tabular font styling.](/design-foundations/typography#tabular-font-styling) + +## Date and time formats + +All date and time formats should be localizable, not hard-coded. When building localizable date and time formats, development teams should share the same library by using resources like [date-fns](https://date-fns.org/) or [Day.js](https://day.js.org/). + +PatternFly date and time formats follow the American standard. When localizing, use the appropriate format for the language locale and follow ISO standards. + +
+ +| **Element** | **Guideline** | **Example** | +|-------------|-------------|-------------| +| Date | Use Month DD, YYYY | September 17, 2020

Sep 17, 2020 | +| Date numeric value | When you represent the date as a numeric value or label, use MM-DD-YYYY. | 09-17-2020 | +| Time | Display time in either 12-hour or 24-hour (UTC) time. | 12-hour: 3:00 PM

With seconds: 3:30:11 PM

24-hour: 15:00 | +| 12-hour time notation | This time convention divides the 24 hours of the day into 2 periods of 12 hours, AM and PM.

12-hour time notation is the American standard. | 3:00 PM | +| 24-hour time notation | This time convention divides the day by 24 hours and runs from midnight to midnight. The hours are represented from 0 to 23. | 14:00 | +| Date and time | Include the timestamp, along with the timezone, after the date. | Thursday, January 21, 2019 9:38:11 PM EST

Thursday, 21 January 2019, 9:38:11 PM EST

07 Jan 2019, 23:33 UTC | +| Time zone | Display time in the user's time zone or in UTC.

Use UTC when spanning multiple time zones. | Maintenance begins today at 14:00 UTC (2 PM EST). | +| Day |Write out the full name of the day. If space is limited, use the day’s 3-letter abbreviation: | Monday, September 17, 2020

Mon, Sep 17, 2020 | +| Month | Write out the full name of the month. If space is limited, use the month’s 3-letter abbreviation. | September 17, 2020

Sep 17, 2020 | +| Duration | HH:MM:SS or HH:MM | 03:15:30

03:15

00:15 | +
+ +## Absolute or relative time + +Whether you use **absolute** or **relative** timestamps will depend on context. + +### Absolute time + +To represent the exact date and time that an event occurred, use an absolute timestamp. For example, "07 Jan 2020, 23:33 UTC". For more examples, reference the [table of date and time formats.](#date-and-time-formats) + +### Relative time + +To represent how long ago an event occurred, use a relative timestamp. When reporting relative time, align with the following language: + +
+ +| **Time frame** | **Guideline** | **Relative timestamp(s)** +|---------------------|------------------------|------------------------| +| Less than 1 minute ago | **Do not** display time in seconds or milliseconds. | Just now | +| Less than 1 hour ago | Display time in minutes, rounded to the nearest minute. | 1 minute ago

4 minutes ago | +| Less than 1 day ago | Display time in hours, rounded to the nearest hour. | 1 hour ago

4 hours ago | +| Less than 1 month ago| Display time in days. | 1 day ago

24 days ago | +| Less than 1 year ago | Display time in months, rounded to the nearest month. | 1 month ago

10 months ago | +| 1 or more years ago | Display time in years, rounded to the nearest year. | 1 year ago

5 years ago + +
+ +## Numbers and currency + +To allow users to more quickly scan through content, use numerals instead of written numbers. + +
+ +| **Before** | **After** | +|---------------------|------------------------| +| Your transaction will be complete in three business days. | Your transaction will be complete in 3 business days. | +| You have a credit of two dollars. | You have a credit of US$2.00. | + +
+ +### Digit grouping + +When grouping digits within large numbers, use the American notation standard. Separate thousands with a comma and separate cents with a decimal. For example: + +- 1,000,000,000 +- 1,000,000.00 + +### Currency + +When displaying currencies that only use the "$" symbol, add the first 2 letters of the ISO currency code. For example: + +- US$1,500 (United States) +- AU$1,500 (Australia) +- HK$1,500 (Hong Kong) +- CA$1,500 (Canada) + +For other currencies, use their 3-letter ISO code wherever possible. You can use national currency symbols, but keep in mind that some users may not be familiar with them. When in doubt, default to ISO. For example: + +- EUR 1,500 or £1,500 (British pound) +- GPB 1,500 or €1,500 (Euro) +- JPY 1,500 or ¥1,500 (Japanese Yen) + +Use a currency's ISO 3-digit numeric code when writing for computerized systems or for countries that don't use Latin scripts. + +| **Country** | **Currency** | **Alphabetic code** | **Numeric code** | +|----------------|----------|-----------------|--------------| +| United States | Dollar | USD | 840 | +| China | Yuan | CNY | 156 | +| European Union | Euro | EUR | 978 | +| United Kingdom | Pound | GBP | 826 | + +Generally, we don't provide currency conversions. \ No newline at end of file diff --git a/packages/site/src/content/design-guidelines/content/product-tours.mdx b/packages/site/src/content/design-guidelines/content/product-tours.mdx new file mode 100644 index 0000000000..194a6ea5d7 --- /dev/null +++ b/packages/site/src/content/design-guidelines/content/product-tours.mdx @@ -0,0 +1,39 @@ +--- +id: Product tours +section: UX writing +--- +A product tour, also referred to as an "onboarding flow", includes a series of dialog boxes or pop-ups that introduce users to a new tool or a redesigned tool. + +In product tours, your UX copy is never intended only to tell a user *how* something works. You need to convince them that using and learning about the product is worth their time. + +When writing a product tour, refer to the following best practice guidelines and their respective before/after example: + +1. **Focus on the user’s goals**: Emphasize what the user can do with the product. + +
+ + |**Before** | **After** | + |------------|-----------| + | We introduced a new feature for designing called Flyer Fact. Discover how it works by taking a tour to learn more.
**OK \| Cancel** | Create consistency and design faster with Flyer Fact.
**Start tour \| Not now** | + +
+ +1. **Be conversational**: Imagine that you’re sitting beside the user and walking them through the product. Avoid jargon and be casual. + +
+ + |**Before** | **After** | + |------------|-----------| + | There are three major areas of Flyer Fact: components, layouts, and documentation. These are for designers to utilize in order to build user experiences that serve the needs of their users. | Create accessible and intuitive interfaces with Flyer Fact’s components, layouts, and documentation. | + +
+ +1. **Empathize with the user**: Learning new things can be scary, so don’t stuff your onboarding flow with exclamation marks, and avoid telling the user how hard you worked on the new tool or how excited you are. Instead, understand that the user might be a little intimidated and focus on giving them information and guidance in a straightforward way. + +
+ + |**Before** | **After** | + |------------|-----------| + | We are so excited to announce the Flyer Fact redesign! We can’t wait to show you around. | Flyer Fact has a new look. Let’s explore what you can do. | + +
diff --git a/packages/site/src/content/design-guidelines/content/punctuation.mdx b/packages/site/src/content/design-guidelines/content/punctuation.mdx new file mode 100644 index 0000000000..ad3c104b31 --- /dev/null +++ b/packages/site/src/content/design-guidelines/content/punctuation.mdx @@ -0,0 +1,141 @@ +--- +id: Punctuation +section: UX writing +--- + +## Headings and titles +Headings and titles can include punctuation, but should not end in punctuation. For example: + +
+ +|**Before** | **After** | +|------------|-----------| +| Style, voice, and tone. | Style, voice, and tone | +| Getting started with PatternFly! | Getting started with PatternFly | + +
+ +The exception for this rule is a question mark, when it is contextually important. For example, in a confirmation dialog, it is important that users understand what action they are about to take. A valid heading may include a question mark, such as "Delete service account?". + +## Referring to text in the UI +When referring to an element or text in the UI, use bold text. Don't use quotation marks or italics -- those should be reserved for quotes and emphasis, respectively. For example: + +
+ +| **Before** | **After** | +|------------------------------------|--------------------------------------| +| Add user to the “Group title” team | Add user to the **Group title** team | + +
+ +## Parallel structure +All items in a list or series should be of the same part of speech. For example: + +
+ +|**Before** | **After** | +|------------|-----------| +| Remember these important tips: Write clearly; conduct research; spelling and grammar. | Remember these important tips: Write clearly; conduct research; use correct spelling and grammar. | + +
+ +## Ampersand (&) +For clarity, avoid using **ampersands** (&), and use "and" instead. + +## Buttons +Avoid using punctuation on **buttons**. + +Do not use punctuation to create icons on buttons (for example, do not use a plus sign "+"). Instead, refer to [PatternFly's icons page](/design-foundations/icons) for any icons you place on buttons. + +## Colon and semicolon +Use a **colon** to introduce a list or a series. You can also use it as a pause before introducing related information. For example: + +- "I enjoy the following hobbies: cooking, drawing, and traveling." +- "That leads me to my favorite hobby: running." + +Use a **semicolon** to connect two closely related independent clauses. You can also use a semicolon instead of a comma to separate long list items for extra clarity. For example: + +- "I love running in the morning; it wakes me up." +- "Every morning, I enjoy eating toast, bacon, and eggs; reading a book; and relaxing on the porch." + +**Note**: If you're tempted to use a semicolon in the UI, try breaking up the sentence and cutting down on your words instead. This often leads to content that is more readable and clear. + +## Commas +When a conjunction connects two independent clauses, a **comma** should precede it. Also put a comma before “and” if it’s the Oxford comma. For example: + +- "I like to run, and I like to swim" — A comma is needed before “and” because “and” connects two independent clauses. +- "I like to run and swim: — A comma is not needed before “and” because “and” does not connect two independent clauses. +- "I like to run, swim, and hike" — The Oxford comma is included before “and.” + +## Ellipses (...) +**Ellipses (...)** are commonly used when information is omitted. Use ellipses when you cannot fit all words onto a line or when you remove less relevant information (like in a quote). For example: + +
+ +|**Before** | **After** | +|---------------------|--------------------| +| They said, “For many reasons, I think the PatternFly community is great.” | They said, “...I think the PatternFly community is great.” | + +
+ +Ellipses can also be used in more creative contexts to signify someone’s thoughts or speech, like a pause for thinking. For example, "But I was just trying to...never mind, forget it." + +## Em dash, en dash, and hyphen + +### Em dash ( — ) +To add emphasis to a phrase or sentence following it, use an **em dash ( — )**. You can also use an em dash to provide additional information or specification in the middle of a sentence. For example: + +- "Good design is not about you—it’s about the user." +- "I like drinking something hot—coffee, tea, or cocoa—during my morning meetings." + +### En dash ( – ) +To separate numbers in a series, use an **en dash ( – )**. For example, "We plan on having 100–150 attendees." + +### Hyphen ( - ) +Use a **hyphen ( - )** if it's part of a term (such as "walk-through") or someone's name (such as "Mary-Jane"). + +You should also use a hyphen for a compound adjective that comes before the noun it modifies, but omit the hyphen if the first adjective ends in "-ly." For example: + +- "I like when my documentation is up to date." +- "I write up-to-date documentation." +- "He is a highly talented writer." +- "She is a high-quality job candidate." + +For most prefixes, you should *not* use a hyphen. For example: + +- Auto- (such as autopopulate; autoloading) +- Pre- (such as prerequisite) +- Re- (such as recreate) +- Sub- (such as submerge) + +An exception for this rule is when you add a modifier prefix like “non." In these cases, you should use a hyphen. For example, "non-Red Hatter." + +If you're unsure about the use of a hyphen, refer to [Merriam-Webster's online dictionary.](https://www.merriam-webster.com/) + +## Exclamation mark +Use **exclamation marks** sparingly. Don’t use one to generate excitement; only use an exclamation mark if the user is actually experiencing something exciting. You can also use an exclamation mark for something cautionary, like “Stop!” or “Watch out!” + +To more accurately capture human expression, use an exclamation mark after just a few words, not after a long sentence. For example: + +
+ +|**Before** | **After** | +|------------|-----------| +| Congratulations on creating an account! | Congratulations! You created an account. | + +
+ +## Parentheses +Use **parentheses** to offer more context to a term or phrase (such as a description or short example). + +Do not use parentheses to indicate a possible plural of something, like "account(s)." When a user can either select one thing or multiple things, use the plural form. + +## Quotation marks +Use double **quotation marks** (“Example”) for quotes and article titles. Use single quotation marks (‘Example’) for quotes or article titles within double quotation marks. + +While double quotation marks are the standard in American English, single quotation marks are usually the standard in British English. + +Double quotation marks and single quotation marks are sometimes used interchangeably across various publications. In some contexts, they can mean the same thing, but they are not always interchangeable. For instance, when you need to use nested quotation marks, single quotation marks should be used inside of double quotation marks. For example: + +- An article title within a dialogue: *Abi said, “I love the article Cat wrote. It’s called ‘Improving product design with an open source mindset,’ and it’s such a fun read.”* +- A quote within a dialogue: *“I like Cat’s article too, Abi. My coworker told me, ‘PatternFly has the best publication ever.’ That made me smile.”* \ No newline at end of file diff --git a/packages/site/src/content/design-guidelines/content/sentence-structure.mdx b/packages/site/src/content/design-guidelines/content/sentence-structure.mdx new file mode 100644 index 0000000000..055ec61c36 --- /dev/null +++ b/packages/site/src/content/design-guidelines/content/sentence-structure.mdx @@ -0,0 +1,44 @@ +--- +id: Sentence structure +section: UX writing +--- + +## Point of view + +Use the **second person** "you/your" whenever you can. This way, your focus is on the user, and the product interaction feels more like a conversation. + +Use the **first person** "I" when the user is agreeing to something. For example, a user can check a box reading, “I agree to the terms and conditions.” + +Try to avoid using **third person** "he/she/they/it." Third person sounds formal and disconnected from the user. + +
+ +|**Before** | **After** | +|------------|-----------| +| Users can simplify their designs with PatternFly. | Simplify your designs with PatternFly. | + +
+ +## Voice + +**Active voice** is when the subject of the sentence performs the action. **Passive voice** is when the subject of the sentence receives the action. + +Use an active voice whenever possible. It makes a sentence shorter and gets the point across faster. + +
+ +|**Before** | **After** | +|------------|-----------| +| The book is being read by Matt. | Matt is reading the book. | + +
+ +There are some occasions when passive voice is appropriate, like when you don’t wish to point out a subject or when you want to emphasize an action. Additionally, passive voice can help avoid assigning blame to a user, especially in error messages. + +
+ +|**Before** | **After** | +|------------|-----------| +| You entered the wrong password. | The password is incorrect. | + +
\ No newline at end of file diff --git a/packages/site/src/content/design-guidelines/content/terminology.mdx b/packages/site/src/content/design-guidelines/content/terminology.mdx new file mode 100644 index 0000000000..b10413306b --- /dev/null +++ b/packages/site/src/content/design-guidelines/content/terminology.mdx @@ -0,0 +1,82 @@ +--- +id: Terminology +section: UX writing +--- + +This resource overviews common UI terms and their usage. + +For Red Hat product terminology and documentation standards, see [Red Hat's supplementary style guide for product documentation](https://redhat-documentation.github.io/supplementary-style-guide/#introduction). + +**Note:** Do not precede UI terms with "please." It is extraneous and overly formal. + +
+ +| **Term** | **Usage** | **Opposite term** | **Notes** | +|------------------|-----------|-----|-----| +| **Add** (v.) | Use to describe adding an existing item to an existing list, group, view, or other container element. | *Remove* | If the object being added is not readily apparent from the context, consider adding a noun (like “Add user”). If you’re creating a new object, **do not use** *Add*. See *Create*. +| **Cancel** (v.) | Use to describe ending an action in progress or ending an action where changes could be lost (like in a form). | | Use *Canceling* instead of *Cancelling*. Use *Canceled* instead of *Cancelled*.| +| **Change** | **Do not use**. See *Edit*. +| **Click** (v.) | Use to prompt the user to click a button, radio button, link, or any other item that isn't part of a list, group, view, or other container element.| | **Do not use** interchangeably with *Select*.| +| **Close** (v.) | Use to describe shutting an open window (like a message dialog). | *Open* | **Do not use** interchangeably with *Cancel* or *Quit*. | +| **Collapse** (v.)| Use to describe minimizing a container element (like a list or message) so that it’s partially visible. | *Expand* | +| **Continue** (v.) | Use to describe proceeding with an action or process that is in progress. | +| **Copy** (v.) | Use to describe the action of creating a reproduction of an object (like a file or text). This may be used in reference to the keyboard action (Ctrl/cmd + c). | | Do not use interchangeably with *Duplicate*. +| **Create** (v.) | Use to describe creating something new. | *Delete* | If the object being created is not readily apparent from the context, consider adding a noun (like “Create user”). *New* or *Add* are not recommended for this use case. See *Add* for usage guidelines. +| **Delete** (v.) | Use to describe completely removing an object. Delete is a destructive action. | *Create* | *Erase* and *Remove* are not recommended for this use case. See *Remove* for usage guidelines. +| **Deselect** (v.) | Use to prompt the user to deselect an item from a list, group, view, or other container element. | *Select* +| **Download** (v.) | Use to describe copying a file from a server or site directly to your system in a file format. | *Upload* | +| **Duplicate** (v.) |Use to describe creating a copy of an object (like a file or configuration). The duplicate item may be edited upon or after creation. | | Do not use interchangeably with *Copy*. +| **Edit** (v.) | Use to describe making changes to an object (like a file, configuration, or policy). | | *Modify* and *Change* are not recommended for this use case.| +| **Expand** (v.) | Use to describe expanding a container element (like a list or message) to show all its contents. | *Collapse* +| **Export** (v.) | Use to describe packing the contents (like a project or spreadsheet) from a website or application to a file format (like .pdf or .xslx) to your system. | *Import* | Do not use interchangeably with *Download*. +| **Export** (v.) | Use to describe packing the contents (like a project or spreadsheet) from a website or application to a file format (like .pdf or .xslx) to your system. | *Import* | Do not use interchangeably with *Download*. +| **Filter** (v.) | Use to describe the action of narrowing a set of search results to show only items meeting a certain criteria. Filtering is mostly associated with views like tables, lists, and card grids and assumes that a search has previously been performed to return an initial results list. +| **Hide** (v.) | Use to describe hiding something that is displayed in the interface. | *Show* +| **Home page** (n.) | Use to describe the main page of a website. | | Write *Home page* as two words, not one. +| **Import** (v.) |Use to describe loading a copy of an object (like a file, image, or format) to your system, software, or application for use or processing. | *Export* | Do not use interchangeably with *Upload* or *Add*. +| **Log in** (v.) | Use to describe logging in. | *Log out *| Use *log in to,* not *log into.* +| **Login** (adj.) | Use to describe something related to the act of logging in to an application, like a login page. | | The noun *Login* can also be used as an alternative for *Username*, but *Username* is recommended. | +| **Log out** (v.) | Use to describe logging out. | *Log in* +| **Modify** | **Do not use.** See *Edit*. +| **New** | **Do not use.** See *Add* or *Create*. +| **OK** (adj.) | Use to collect confirmation or understanding from the user. | | Do not use *Okay,* *O.K.,* *Ok,* or *ok* in the UI. +| **Open** (v.) | Use to describe launching something (like system preferences).| *Close* +| **Quit** (v.) | Use to describe exiting an application. +| **Please** (adv.) | **Do not use** | Do not precede UI terms with "please". It is extraneous and overly formal. | +| **Remove** (v.) | Use to describe removing an item from a list, group, view, or other container element without completely deleting it. Also see *Add* and *Delete*. | *Add* | If what you’re removing is not readily apparent from the context, consider adding a noun (like “Remove file”). +| **Save** (v.) | Use to describe preserving changes made by the user. | *Cancel* +| **Search** (v.) | Use to decribe the action of querying a data set to return a results list. Searching will always be applied against some criteria and may be narrow or broad. +| **Select** (v.) | Use to prompt the user to select an item from a list, group, view, or other container element. | *Deselect* | Do not use *Choose* for this use case. +| **Set up** (v.) | Use to describe setting up an arrangement (like a system, process, or environment). | | *Set up* is two words as a verb and one word as a noun. See *Setup*. +| **Setup** (n.) | Use to describe the setup of something (like a system, process, or environment). | | *Setup* is one word as a noun and two words as a verb. See *Set up*. +| **Show** (v.) | Use to describe displaying something that is hidden in the interface. | *Hide* | Do not use interchangeably with *View* or *Expand*. +| **Sign up** (v.) | Use to describe signing up for a web account, application, service, or event. | | *Sign up* is two words as a verb and one word as an adjective or noun. See *Signup*. +| **Signup** (adj.) | Use to describe something related to the act of signing up for a web account, application, service, or event, like a signup page. | | The noun *Signup* can also be used to refer to a user signup submission (for example, "We need more signups for this event."). +| **View** (v.) | Use to describe accessing another page to see details. (n.) Use to represent an arrangement of data in the interface (like a list view). | | Do not use interchangeably with *Show* or *Expand*. +| **Upload** (v.) | Use to describe loading a copy of a file to a server.| | Do not use interchangeably with *Import*. +| **Username** (n.) | Usually a unique ID (like ssmith123). +| **Utilize** (v.) | **Do not use.** Opt for the less formal version, *Use*. + +
+ +## Abbreviations and acronyms +Use abbreviations that users are familiar with, and write out uncommon abbreviations. Only use an abbreviation that has already been established and *never* make up an abbreviation or acronym yourself to help keep consistency in your products. Make sure that your abbreviations are consistent, always abbreviate units of measurement, and, when referring to a product, default to how the company refers to it themselves. + +
+ +| **Abbreviation** | **Usage** | +|------------------|-----------| +| **CSS** | Stands for *Cascading Style Sheets*. Write *CSS* in all caps. | +| **e.g.**, **i.e.**, and **etc.** | Use sparingly. These terms aren’t easily understood by everyone, especially users whose native language is not rooted in Latin. Write out their meaning instead: | +| **HTML** | Stands for *Hypertext Markup Language*. Write *HTML* in all caps. | +| **JS** | Stands for *JavaScript*. Write *JS* in all caps. | +| **K8** | Stands for *Kubernetes*. | +| **KVM** | Refers to a kernel-based virtual machine. Write *KVM* in all caps. | +| **sysadmin** | Avoid using abbreviations like *sysadmin* and *SysAdmin* because they’re too informal and not always easily understood. *System* should be singular (not *Systems administrator*) because it can include both a single system and multiple systems, similar to a *brain surgeon*, who works on more than one brain.

Taken from Red Hat Corporate Style Guide. | +| **U.S.** | As a noun, use *United States* unless there are space constraints. As an adjective, use *U.S.* (for example, *U.S. soldier*). As part of an organization, use *U.S.*

Taken from Red Hat Corporate Style Guide. | +| **URL** | Stands for *Uniform Resource Locator*. Write *URL* in all caps. | +| **VM** | Refers to a virtual machine. OK to abbreviate as long as you've spelled it out once in the first occurrence and as long as *VM* won't be confused with other terms that share that acronym.

Taken from Red Hat Corporate Style Guide. | +| **N/A** | Refers to *data not applicable*, meaning there is no relevant, matching, or applicable data.

For example, when a filter returns no results, when a data source is empty, or when no data source is connected.| +| **--** | Refers to *data unavailable*, meaning the data exists and fits the criteria, but is not currently available to display.

For example, when a data source is connected, but data can't be fetched due to permission restrictions or errors.| + +
\ No newline at end of file diff --git a/packages/site/src/content/design-guidelines/content/tooltips.mdx b/packages/site/src/content/design-guidelines/content/tooltips.mdx new file mode 100644 index 0000000000..7e3e9fc507 --- /dev/null +++ b/packages/site/src/content/design-guidelines/content/tooltips.mdx @@ -0,0 +1,82 @@ +--- +id: Tooltips +section: UX writing +--- + +import ArrowCircleUpIcon from '@patternfly/react-icons/dist/esm/icons/arrow-circle-up-icon'; +import BellIcon from '@patternfly/react-icons/dist/esm/icons/bell-icon'; +import CogIcon from '@patternfly/react-icons/dist/esm/icons/cog-icon'; +import CopyIcon from '@patternfly/react-icons/dist/esm/icons/copy-icon'; +import DownloadIcon from '@patternfly/react-icons/dist/esm/icons/download-icon'; +import EllipsisVIcon from '@patternfly/react-icons/dist/esm/icons/ellipsis-v-icon'; +import PencilAltIcon from '@patternfly/react-icons/dist/esm/icons/pencil-alt-icon'; +import SearchIcon from '@patternfly/react-icons/dist/esm/icons/search-icon'; +import SearchMinusIcon from '@patternfly/react-icons/dist/esm/icons/search-minus-icon'; +import SearchPlusIcon from '@patternfly/react-icons/dist/esm/icons/search-plus-icon'; +import SyncAltIcon from '@patternfly/react-icons/dist/esm/icons/sync-alt-icon'; +import TrashIcon from '@patternfly/react-icons/dist/esm/icons/trash-icon'; +import ExportIcon from '@patternfly/react-icons/dist/esm/icons/export-icon'; +import TaskIcon from '@patternfly/react-icons/dist/esm/icons/task-icon'; +import QuestionCircleIcon from '@patternfly/react-icons/dist/esm/icons/question-circle-icon'; +import { Button, Icon, Tooltip, Split, SplitItem } from '@patternfly/react-core' + +A **tooltip** is a message box that is shown when a UI element, like a button or an icon, is in a hover state. They contain short descriptions that offer additional information to help users better understand elements within a UI. + + + + + +When writing tooltips, follow these general recommendations: + +
+ +| **Don't** | **Do** | +|----------------------------------------|---------------------| +| Don't repeat information that is already available in the UI. | Do write content that is succinct, clear, and effective. | +| Don't use tooltips for critical information. | Do use tooltips for additional, non-essential information. | +| Don't end sentence fragments in a period. | Do end full sentences in a period. | +| Don’t place tooltips on question-circle icons (). Instead, use a [popover](/components/popover). | Do follow [our tooltip development accessibility guidelines](/components/tooltip/accessibility) to ensure that tooltip content is available to all users.| + +
+ +You can find additional guidance in [the tooltip design guidelines.](/components/tooltip/design-guidelines) + +## Icon tooltips +Icons allow you to save space in a UI and provide users with another recognition method. + +It's often important to place tooltips on icons, especially when they aren't accompanied by a text label. This helps ensure that your users can hover over an icon to understand the action that it is linked to. When you use a tooltip with an icon, limit the content to 1 or 2 words that identify the icon accurately and clearly. + +For example: + + + + + + + + + + + + + +In PatternFly, there are commonly used icons that hold universal meanings. These should always use the same tooltip description, as shown in the following table: + +|**Icon** | **Name** | **Tooltip content** | **Note** | +|------------|-----------|-----------|---- | +| | fa-arrow-circle-up | Upgrade | +| | fa-bell | Notifications | +| | fa-cog | Settings | +| | fa-copy | Copy | +| | fa-download | Download | +| | fa-ellipsis-v | More options | +| | fa-pencil-alt | Edit | +| | fa-search | Search | +| | fa-search-minus | Search minus | +| | fa-search-plus | Search plus | +| | fa-sync-alt | Sync, Refresh, or Running | Choose the best fit for your scenario.| +| | fa-trash | Delete | +| | pficon-export | Export | +| | pficon-task | Tasks | + +You can learn more about the usage of these icons in our [design foundations.](/design-foundations/icons) diff --git a/packages/site/src/content/design-guidelines/content/truncation.mdx b/packages/site/src/content/design-guidelines/content/truncation.mdx new file mode 100644 index 0000000000..1694e7dff9 --- /dev/null +++ b/packages/site/src/content/design-guidelines/content/truncation.mdx @@ -0,0 +1,43 @@ +--- +id: Truncation +section: UX writing +--- + +**Truncate**, or shorten, your content whenever a string overflows the container and you don't want multiple lines of text. Typically, this is done by utilizing ellipses (...). + +For example, use truncation when a URL overflows its container: + +image showing long url truncation + +## Where to truncate +Whether you should truncate strings at the beginning, end, or in the middle requires a bit of research. + +If your product has a default truncation scheme, such as a setting for how to truncate host names, you should follow that practice. + +If the product doesn't have a default truncation scheme, think about how the product's users tend to name objects. Is it more likely that the unique part of the name will be at the beginning or end of the string? Based on the answer, you should either truncate at the end of the string (abcdef...) or in the middle of the string (abc...ghi). To decide on a method, ask yourself: *Which part of the string is more likely to differentiate the item?* + +If users are able to customize settings regarding truncation, then you should match their chosen preference: + +image showing user selected truncation options + +## Truncation guidelines and best practices + +When considering when and how to truncate, follow these guidelines: + +- Indicate truncated text with an ellipsis (…). If the text is part of a link, the ellipsis should also be part of the link. + +- Leave no fewer than 4 characters when truncating text. Leave enough characters to give a fair idea of what the string says + - For example, don't truncate “demo1.internal-el6.satellite” to “de…”, since that doesn't properly convey the meaning of the full string. + +- In any string within a container, if there is not sufficient room for the full spelling or hyphenated word, consider abbreviating the text. + +- Avoid abbreviations or truncated text in navigation items (all levels of navigation in the masthead and left navigation). + +- Ensure that there is at least one method for the user to view the entire string. We recommend using a tooltip (useful for fewer than 150 characters or so). You could also use expandable rows or overlays. + +- Avoid truncation directly before or after punctuation whenever possible. It’s tricky to differentiate whether the punctuation is part of the ellipsis or part of the name + - For example, don't truncate “demo1.internal-el6.satellite” to “demo1…”, because it's unclear that there's a period in addition to the ellipses. + +- If a table column is resizable, the truncated text should adjust accordingly. + +- Do not truncate text in column headings. \ No newline at end of file diff --git a/packages/site/src/content/design-guidelines/content/units-and-symbols.mdx b/packages/site/src/content/design-guidelines/content/units-and-symbols.mdx new file mode 100644 index 0000000000..086072b9b4 --- /dev/null +++ b/packages/site/src/content/design-guidelines/content/units-and-symbols.mdx @@ -0,0 +1,127 @@ +--- +id: Units and symbols +section: UX writing +--- + +# Communicating measurements + +Use consistent formatting, terminology, and symbols when displaying units of measurement in your UI, including: + +- Currency. +- Data bandwidth. +- Data storage. +- Time. + +When displaying quantitative values for measurements in your UI, use the [International System of Units](https://www.nist.gov/pml/owm/metric-si/si-units) (SI unit) so that your content can be understood by global users. The following table outlines the base units and symbols you should use to describe different quantitative values: + +
+ +| **Measurement** | **Unit** | **Symbol** | +| --- | --- | ---| +| Length | Meter | m +| Mass | Kilogram | kg +| Electric current | Ampere | A +| Thermodynamic temperature | Kelvin | K +| Amount of substance | Mole | mol +| Luminous intensity | Candela | cd + +
+ +## Currency + +Wherever possible, display currency in three-letter code according to [ISO Standard 4217](https://www.iso.org/iso-4217-currency-codes.html). See our [numerics](/ux-writing/numerics#numbers-and-currency) guidelines for more information about writing currency. + +## Data bandwidth + +Bandwidth is the amount of data transferred from one point to another within a network in a specified amount of time. + +Data transfer is primarily measured in two ways: + +- **Megabits/second (Mbps)**: Specifies download and upload speeds on the internet +- **Megabytes/second (MBps)**: Specifies the quantity of data or file size transferred over time + +Data transfer rates can be measured in binary or metric units. Always align this unit with the scale you use to measure data size. + +| **Binary unit** | **Symbol** | +|-----------------|------------| +| 1 mebibyte/second | MiBps | +| 1 gibibyte/second | GiBps | +| 1 tebibyte/second | TiBps | + +| **Metric unit** | **Symbol** | +|-----------------|------------| +| 1 megabyte/second | MBps | +| 1 gigabyte/second | GBps | +| 1 terabyte/second | TBps | + +**Note**: Pay special attention to the letter case when writing symbols for bits (b) and bytes (B). Eight bits (b) make up one byte (B), so using the wrong symbol will change your meaning. + +## Data storage + +Computer storage and memory are typically measured in bytes. Bytes can be shown in **binary units** (gibibytes) or **decimal/metric units**(gigabytes). + +To remain consistent and reduce confusion, use binary units to express amounts of digital information. This practice aligns with most computing and open source software. + +
+ +| **Binary unit** | **Symbol** | **Value** | +|-----------------|------------|------------------| +| 1 kibibyte | KiB | 1024 | +| 1 mebibyte | MiB | 10242 | +| 1 gibibyte | GiB | 10243 | +| 1 tebibyte | TiB | 10244 | + +
+ +
+ +| **Metric unit** | **Symbol** | **Value** | +|-----------------|------------|------------------| +| 1 kilobyte | KB | 1000 | +| 1 megabyte | MB | 10002 | +| 1 gigabyte | GB | 10003 | +| 1 terabyte | TB | 10004 | + +
+ +## Time + +Whenever possible, write the full name of each time unit. + +For example, write "6 minutes" instead of "6 min." + +If space is limited, use symbols to communicate the same units of time in less space: + +
+ +| **Unit** | **Symbol**| +| --- | --- | +| Millisecond | ms +| Second | s +| Minute | min +| Hour | hr + +
+ +Avoid using symbols for days, weeks, months, and years. + +## Best practices for writing units of measurement + +Follow these general best practices for writing units of measurement: + +
+ +| **Best practice** | **Examples** | +|------------------------|--------------------------| +| Use consistent units, and avoid mixing them. | Write *10 to 75 seconds* instead of *10 seconds to 1.25 minutes*. | +| Include a space between numbers and units, except for percentages. | Add a space to *75 kg* but not to *75%*. | +| Display the full name of each unit unless space is limited. | Write *6 seconds ago* instead of *6s ago.* | +| Don't make unit symbols plural. | Write *60 cm*, not *60 cms*. | Don't punctuate unit symbols unless they end a sentence. *60 cm doesn't end this sentence, so "cm" isn't followed by a period.* | +| Write SI unit symbols in lowercase. If a symbol is named after a person or proper noun, then capitalize its first letter. | Write *W* for watt.

Write *Hz* for hertz. | +| Don't mix symbols or apply mathematical operations to unit names. | Write *kg/m3* instead of *kilogram/m3*.

Write *kg · m-3* instead of *kilogram/cubic meter*.

Use *kilogram per cubic meter* instead of *kg/cubic meter*, *kilogram per meter3*, or *kg per m3*. | +| Use parentheses to display a secondary unit of measure. | *10°C (50°F)* | +| Clearly express units for two or more related quantities. If necessary, you can include the unit after each numeral. | Write *6 to 8 inches* or *6 inches to 8 inches*. | +| Use symbols to display derived units of measure (units formed using a calculation). | *38 mph, 27 ft/s2* | +| For derived units of measure, use the symbol that represents its word form, since it will be more familiar to your users. | Use *Hz* for Hertz instead of the derivation *cycles per second (cycles/second)*. + +
\ No newline at end of file diff --git a/packages/site/src/content/design-guidelines/content/ux-writing-best-practices.mdx b/packages/site/src/content/design-guidelines/content/ux-writing-best-practices.mdx new file mode 100644 index 0000000000..e9912318e1 --- /dev/null +++ b/packages/site/src/content/design-guidelines/content/ux-writing-best-practices.mdx @@ -0,0 +1,103 @@ +--- +id: UX writing best practices +section: UX writing +--- + +Treat words as part of your design, not something to be added at the end. UX copy needs to be rooted in user information and context so that it can contribute to an effective, intuitive, and human-centric product experience. + +By making writing part of your design process, you’ll also be able to uncover design issues at the very beginning. If a design is too difficult to explain with words, then it might still need some work. By the time you create high-fidelity mockups, you’ll already have a few rounds of content feedback under your belt and can focus on refinement. Work across teams to fine-tune your copy and align your words with voice and tone standards. + +This guide details the best practices that you should follow when writing for UX. + +## Know your users +Before you write, understand who you're writing for. Getting to know your users’ needs and experiences can inform you on what words will resonate with them. + +To understand your users, create user personas (or use the ones your team already has) and reference them as you work. If your team is in the process of gathering information about users, there are a few ways you can get involved: + +- Ask to sit in on any interviews and listen. +- Make notes about specific words being used, standards being referenced, or concepts that keep coming up. +- Do your own research into your users’ domain by reading popular blogs, forums, or documentation. + +## Focus on goals and tasks +Consider what your user is trying to accomplish (the **goal**) and the steps they’ll take to get there (the **tasks**). By understanding the entire user journey, you can provide the right content to the right user in the right place at the right time. + +Frame each task as a conversation. Imagine you are sitting in a room with your user, and write out the conversation you might have to help them accomplish their task. This activity can help you: + +- Write in a natural and conversational way, which can inform and improve the content you use in the interface. +- Anticipate questions the user might have along the way. +- Anticipate information you need to collect from your user. +- Identify gaps in your knowledge or understanding. + +## Understand the context +Users carry around a lot of baggage, so it’s important to know where they’re coming from—literally, personally, and emotionally. + +- **Literally**: Take a look at the application or feature you’re building and figure out the potential paths your user could have taken to arrive in this spot. Are they coming from a Google search? Another page in the application? An email? + + Use that context to plan for the information they need to see in order to get themselves oriented. This might mean you should create a strong header with some intro text, a clear call to action, a breadcrumb bar, or all of the above. + +- **Personally**: Consider where the user is coming from personally. What terminology are they expecting to see? Will they be familiar with all the information you’re giving them? Is it possible they might need additional information or links to documentation? + + Use that context to choose the right terminology and prioritize your content. + +- **Emotionally**: Consider how your user is likely to be feeling in the situation you’re designing for. Is this situation stressful (paying a bill)? Frustrating (account creation error)? + + Empathize with them, and be sure to use an appropriate tone. + +## Sound like a person +Jargon, bizpeak, and formal language make you sound more like a brochure than a human. Users need to relate to your brand and like you before they can trust you. Talk with them as people using familiar, conversational words. + +
+ +|**Before** | **After** | +|------------|-----------| +| Utilizing the open source phenomenon allows you to leverage collaborative communications. | Open source is great for collaboration. | + +
+ +## Be clear and concise +Dr. Seuss said it best: “So the writer who breeds more words than he needs, is making a chore for the reader who reads.” Use plain language, and don’t use more words than you need. Chunk content into short, related sections, and avoid long paragraphs or strings of text. + +
+ +|**Before** | **After** | +|------------|-----------| +| Make the decision to send a notification to your administrator. | Notify your administrator. | + +
+ +## Be consistent +Stick with the same terminology to describe actions and objects across the entire user experience. Using two terms interchangeably—even when they mean the same thing—can confuse users. + +
+ +|**Before** | **After** | +|------------|-----------| +| Log in to your account only. Never sign in to your friend’s account. | Log in to your account only. Never log in to your friend’s account. | + +
+ +## Align with your brand +Make sure your UX copy reflects your brand voice (as we outline in [our brand voice and tone guide](/ux-writing/brand-voice-and-tone)). UX copy is not just for adding clarity and guiding users through the interface. You’re also creating an experience with your words, making a product interaction sound, feel, and look like a human conversation. + + +## Lead with the benefit +Users want to know why they should do something. What’s in it for them? They typically focus on the beginning of a sentence, so make your instruction worth it by starting with the outcome—in other words, the benefit. + +
+ +|**Before** | **After** | +|------------|-----------| +| Install this extension to learn more about email. | To learn more about email, install this extension. | + +
+ +## Use positive, action-oriented language +Focus on what the user needs to do in order to complete the task or reach their goal. Give directions that show users that they can do what they're hoping to. + +
+ +|**Before** | **After** | +|------------|-----------| +| Your user settings do not allow you to access this file. | To access this file, adjust your user settings. | + +
\ No newline at end of file diff --git a/packages/site/src/content/design-guidelines/content/writing-for-all-audiences.mdx b/packages/site/src/content/design-guidelines/content/writing-for-all-audiences.mdx new file mode 100644 index 0000000000..3bcbf05caa --- /dev/null +++ b/packages/site/src/content/design-guidelines/content/writing-for-all-audiences.mdx @@ -0,0 +1,84 @@ +--- +id: Writing for all audiences +section: UX writing +--- + +By following accessibility and global writing best practices, you’ll be better equipped to create product experiences for users of all abilities and backgrounds. + +## Writing for all abilities +When designing interfaces, consider all users’ abilities, including physical and cognitive. Use words that are clear, concise, and consistent. Refer to the [Web Content Accessibility Guidelines (WCAG)](https://www.w3.org/TR/WCAG21/) for accessibility compliance information. + +To create accessible content, refer to the following best practices: + +- Use plain language and short sentences. + +- Use common contractions (for example, "it’s” and "you’re") in areas that sound most natural to you. Contractions help make your UI more accessible, and they’re great for maintaining a casual voice and tone. + +- Don't identify items by color only. Color identifiers don’t help users who are colorblind. For example: + +
+ blue PatternFly primary button reading Submit form +
+ +
+ + | **Before** | **After** | + |--------|-----------| + | Click the blue button. | Click **Submit form**. | + +
+ +- Write for responsive design. If your application is accessible by multiple devices, such as a tablet, laptop, television, and smartphone, then consider that on some devices you may slide or tap the screen, while on others you may select options by clicking or pressing. + +- Use proper heading levels (H1, H2) to articulate the page content’s organization. Headings are useful in identifying content changes, and machine translation recognizes each heading level as a new segment, which is important with text-laden pages. + - Headings are ranked hierarchically from H1 through H6, with H1 headings representing the most important idea on a page. + +- Consistently describe UI elements in tooltips and product documentation. For example, for a kebab icon the tooltip text might be "More options". In product documentation, you would then say "Click **More options**". + +- Label UI elements (buttons, icons, menus) consistently and descriptively to clearly represent the element’s function. + +## Writing for localization and translation + +Accessibility is closely related to localization and translation. The more accessible your words are, the easier it is to translate them. Keep the following additional guidelines in mind when writing for global users: + +- Translated text can be a drastically different length than the source text. Collaborate with UX designers to ensure that the text you use can appear 50% shorter or 50% longer with no negative impact on design. + +- Character width is affected by double-byte characters. + +- Avoid describing objects with human characteristics, for example “the computer knows when you log on.” + +- Avoid idioms, jargon, or regional metaphors, such as “on the ball.” They don’t make sense in all languages. + +- Avoid culture-specific or location-specific references and examples. They won’t resonate with all users. + +- Avoid vague terms like “stuff” or “kind of.” These terms can be translated incorrectly. + +- Use humor sparingly. It generally doesn’t translate well. + +## Writing for screen readers + +Include text for screen readers. Screen readers are most useful when the words represent what is visually shown on the screen. When writing text that is visible only to a screen reader, such as an aria-label that describes an icon button, reference the following guidelines: + +- Avoid redundancy. Screen readers announce the component or element as well as the associated property and state when the HTML is defined correctly. For example, a search button is announced to a user as a combination of the label and the component. Label the button as "Search", not "Search button." This way, it will be announced as "Search button" (rather than "Search search button"). + +- Make sure that labels for elements like buttons or links make sense when pulled out of context. Use descriptive hyperlinks instead of raw links or vague linked text, such as “Click here.” + +- When you define an aria-label for an element that also has associated visible text in the UI, ensure the aria-label begins with the same text that is displayed in the UI to avoid confusing screen reader users who have vision. + +- Avoid unnecessary capitalization. + +- Avoid leet speak, which uses numbers or special characters in place of letters (for example, "a11y" for accessibility). + +## Using accessible and global-friendly graphics + +The graphics that you use in your UI should meet accessibility and localization standard by following these best practices: + +- Verify that you have rights to use graphics without infringing on copyrights. + +- Include alt text for images that provide additional meaning or content to the page. If the image is decorative or if the alt text would be duplicated by adjacent text, then use an empty alt attribute instead, `alt=""`. An empty alt attribute communicates to screen readers that the image provides no additional content and can be ignored. + +- Select a text-free image and use callouts to caption the image. When localizing content, graphics containing text may require translation, and translating a static image requires graphic editing. Callouts are easier to localize. + + + + diff --git a/packages/site/src/content/design-guidelines/content/writing-patternfly-design-guidelines.mdx b/packages/site/src/content/design-guidelines/content/writing-patternfly-design-guidelines.mdx new file mode 100644 index 0000000000..1c363e865b --- /dev/null +++ b/packages/site/src/content/design-guidelines/content/writing-patternfly-design-guidelines.mdx @@ -0,0 +1,131 @@ +--- +id: Writing PatternFly design guidelines +section: UX writing +--- + +This guide provides instructions for writing clear and consistent design documentation for PatternFly. PatternFly's design guidelines provide users with information regarding the design, usage, behavior, and more of PatternFly's elements and components. + +To learn how to contribute design guidelines, see our [contribution guide](https://github.com/patternfly/patternfly-org/wiki/Contributing-to-patternfly-org-for-designers). + +## Design guidelines sections +When creating guidelines, refer to the following template to ensure that information is presented in a consistent order and within sections that are consistently named and structured. Sections may be omitted, but if they are present, you must use the specified section headings and heading levels. + +### Elements (H2) +Display an image of the component containing numbered annotation tags for each major part of the component's visual design. Include specific icons, headers, fields, symbols, and anything else included in the component's structure. Following the image, list all the parts you tagged, aligning with the number displayed in the respective annotation tag. In this list, provide a description of each one. + +For example: + +A screenshot of the slider component's element section with 8 elements outlined. + +### Usage (H2) +Explain how the component is used, when to use it, and why it should be used. Include explanations of problems it could help solve and address its advantages over similar components. Include images for visual examples. + +Additional sub-sections to include: + +#### When to use (H3) +#### When not to use (H3) +#### When to use X vs. Y (H3) +#### Examples of incorrect usage (H3) + +### Behavior (H2) +Explain how the component functions and break down how its elements interact with each other to achieve its purpose. It may be helpful to include additional images or animations to demonstrate how the component works. + +### Variations (H2) +Showcase different forms of your component and include explanations indicating when to use each one. + +Additional sub-sections to include: +#### When to use X variation vs. when to use Y variation (H3) + +### Spacing (H2) +Introduce spacing requirements for components and their content. For more information regarding proper spacing, refer to our [spacing guidelines.](/design-foundations/spacers) + +### Placement (H2) +Provide details on where components should be located in a UI and in relation to other components. + +### Content considerations (H2) +Showcase the different content that could be included within your component. Here is where you can also give additional tips and tricks the user may want to know. Content guidance includes: + +- Editorial guidelines for labeling and message text. +- Length restrictions and what to do when text overflows. +- Localization considerations. + +### Accessibility (H2) +Each component that has an accessibility tab should include the following sentence within this section: + +"For information regarding accessibility, visit the [component name] accessibility tab." + +Then, link the component's accessibility tab to the words "accessibility tab." + +## Formatting + +The following best practices should inform the way that you format the content in your design documentation. + +### Capitalization + +Our [capitalization style guidelines](/ux-writing/capitalization/) outline best practices for capitalization across PatternFly. + +Always write headings in sentence case. Write component names in lowercase. + +For example, "Usage guidelines for card views" + +### Bolds and italics + +**Bold** component names when you first introduce them. + +For example, "A **card** is a square or rectangle container of related information." + +*Italicize* words for emphasis, but do so sparingly. + +### Lists + +Lists help organize lengthy, complex content into shorter, scannable sections. Use lists to introduce use cases, exceptions, and procedures. + +When building lists, follow these best practices: + +- Use bullets by default. Only use numbers if the order of items is important, like in a callout list. +- Introduce your list with a clause or phrase that describes the information it shares. +- Start each item with a capital letter. +- End list items with a period if they're sentences, or if they form a full sentence when combined with the clause/phrase that introduces the list. +- Maintain parallel structure. Start every list item with the same part of speech. (For example, each item of this list starts with a verb.) + +## Images + +Design documentation includes images to contextualize elements in a UI and demonstrate them in action. All images should include alt text for accessibility. + +### Annotations + +Annotations highlight specific areas in an image. Follow these best practices when using annotations: + +- Use numbered callouts to call out multiple areas in your image, then use a corresponding numbered list to explain each one. For example: + + ![Two callouts highlight multiple items on a toolbar.](./img/desguidelines2.png) + + **1. Items in view:** Allows the user to select the item count (number of listed items) per page, as seen in full pagination + + **2. Compact pager:** Supplies the user with page-back and page-next controls only + +- Avoid using a callout to highlight a single item, unless you're pointing out a small part of a large view, or the item isn't clearly shown in your image. Use a blank, unnumbered callout to mark the area, then bold it in your explanation. For example: + + ![#A single callout highlights the login button on a large screen.](./img/desguidelines3.png) + + Always write your **login button** as two words: "Log in." + +## Style, voice, and tone + +PatternFly's documentation is friendly and instructional. Learn more about voice in our [brand voice and tone section](/ux-writing/brand-voice-and-tone/). + +When writing design guidelines, use: + +- Present tense. +- Second-person point of view ("you"). +- Active voice, unless you're using passive voice for emphasis. +- Direct language and sentence structure. +- Full words to introduce examples, instead of their abbreviations ("for example" instead of "e.g."), as seen on our [terms list](/ux-writing/terminology/). +- Descriptive language instead of directional language (up, down, left, right) to refer to elements in your document. +- Descriptive hyperlinks (not "click here"). + +If you're linking to other PatternFly pages, use relative URLs instead of full URLs. + +- **Relative URL:** /components/tooltip/design-guidelines + +- **Full URL:** https://www.patternfly.org/components/tooltip/design-guidelines diff --git a/packages/site/src/content/design-guidelines/styles/colors-for-charts/colors-for-charts.css b/packages/site/src/content/design-guidelines/styles/colors-for-charts/colors-for-charts.css new file mode 100644 index 0000000000..27b6c196ca --- /dev/null +++ b/packages/site/src/content/design-guidelines/styles/colors-for-charts/colors-for-charts.css @@ -0,0 +1,25 @@ +.ws-colors-grid { + --pf-v6-l-grid--m-gutter--GridGap: var(--pf-t--global--spacer--lg); +} + +.ws-content-chart-colors { + height: 44px; + width: 44px; + border-radius: 50%; +} + +.ws-content-chart-colors-gallery--information>* { + font-size: 12px +} + +.ws-content-chart-colors-gallery--information>*>code { + font-size: 10px!important +} + +.ws-chart-colors-gridtext { + max-width: 680px; +} + +.pf-v6-c-divider.ws-chart-colors-divider { + margin-top: var(--pf-v6-c-content--h2--MarginTop); +} diff --git a/packages/site/src/content/design-guidelines/styles/colors-for-charts/colors-for-charts.mdx b/packages/site/src/content/design-guidelines/styles/colors-for-charts/colors-for-charts.mdx new file mode 100644 index 0000000000..f8f753748d --- /dev/null +++ b/packages/site/src/content/design-guidelines/styles/colors-for-charts/colors-for-charts.mdx @@ -0,0 +1,120 @@ +--- +id: Colors for charts +section: charts +hideSource: true +sortValue: 2 +--- + +import { Alert, Grid, GridItem, Divider } from '@patternfly/react-core'; +import ColorsGrid from './colors-grid'; +import './colors-for-charts.css'; + +import '../../components/components.css'; + +**Note:** Our charts use separate design tokens from our standard library. To view a list of all chart tokens, apply the "chart" category filter to [the PatternFly design tokens table](/tokens/all-patternfly-tokens). + +## Color palettes + +To create well-designed charts, you typically need to use multiple colors to best communicate your data. Our chart color options are all pulled from [standard PatternFly color palettes](/design-foundations/charts), but the amount of hues within each color family are more limited to ensure that your chart colors are distinct enough from each other. Your data will determine the number of colors and the type of colors you will need. + + + +## Usage + +Our chart color system is completely customizable. Once you choose your base colors and the total number of colors you need, the system will sort them correctly. + +The system will first use each base color from the families you selected. Once all base colors have been used, the system alternates between choosing the lightest and darkest values of each family. The color picking system will continue to alternate between the remaining lightest and darkest colors of each family until it has reached the total number of colors you selected. + +No matter which base colors you select, this process will remain the same. + +### Example palette + +If you select 4 color families—blue, teal, green, and yellow color—your chart could look like this: + +
+![Chart color palette for a bar chart that uses hues across 4 color families.](./img/example-palette.svg) +
+ +1. Base colors: `--pf-t-chart-color-[colorname]-300` +1. Lightest: `--pf-t-chart-color-[colorname]-100` +1. Darkest: `--pf-t-chart-color-[colorname]-500` +1. Second-lightest: `--pf-t-chart-color-[colorname]-200` +1. Second-darkest: `--pf-t-chart-color-[colorname]-400` + +### Figma color scales + +To simplify the process of selecting hues for your design, we offer premade color scales in Figma for each color family. These color scales arrange a family's hues based off our recommendations, so you can use colors in the order that they appear within a color scale. + +
+![Color scale options within Figma.](./img/figma-colorscale.svg) +
+ +### Best practices + +When selecting colors for your chart, adhere to these general rules: + +1. Within a color family, use the base color first. Then use the other lighter and darker hues. +1. Some families have predetermined uses: + - **Blue:** Use to show success. + - **Red-orange:** Use to show failure. Do not use this family unless you're communicating failure. + - **Other colors:** Use for neutral purposes or categories. + +
+![Pie chart measuring completion versus failure.](./img/success-and-failure.svg) +
+ +1. Use **patterns** to deemphasize a section of a chart. + - To best highlight chart sections that utilize solid colors, only use patterns for a single chart portion or type of portion. For example, you could use a pattern on your "success" portions to help "failure" portions stand out. + - Do not use patterns for every section of a chart. + +1. When using certain hues of red-orange and green together in a single chart, they might not always pass accessibility requirements. To improve your chart's accessibility in these cases, add a pattern to the section that you want to deemphasize. + +## Variations + +### Few chart variables +When working with *7 or fewer variables*, align each variable to an available base color. + +For example, the following chart displays sales data per product over a period of time: + +
+![Simple bar chart with few data points.](./img/few-variables.svg) +
+ +### Many chart variables +If the set of data includes *more than 7 variables*, apply a multichromatic order system that includes all of the colors in the color system. + +For example, the following chart displays the cost of living expenses over a period of time: + +
+![Complex bar chart with many data points.](./img/many-variables.svg) +
+ +### Nested or grouped chart variables +If your dataset includes grouped variables, align each group to a color family. When you select multiple color families, your chart will automatically arrange the order of colors as follows: blue, green, teal, purple, yellow, orange, red orange, and then black. If there are more than 6 groups, this order would restart and continue to cycle. + +For example, the following chart includes quarterly sales data that is broken down by geographical locations: + +
+![Bar chart with multiple bars nested within each data point.](./img/nested-variables.svg) +
+ +### Monochromatic charts + +To create a monochromatic effect in your chart, you can also apply a color order system within 1 color family. This effect is particularly helpful for charts with nested variables. + +
+![Nested bar chart with a different color family per data point.](./img/monochromatic.svg) +
+ +Within a family, the color order follows the same pattern used when combining multiple families. The chart palette begins with the base hue, then uses the lightest, darkest, second lightest, and second darkest hues. Regardless of color family, hues will always follow this order. + +
+![Design tokens used within a nested bar chart.](./img/monochromatic-annotated.svg) +
+ +As design tokens, this order looks like: +1. Base hue: `--pf-t-chart-color-[colorname]-300` +1. Lightest hue: `--pf-t-chart-color-[colorname]-100` +1. Darkest hue: `--pf-t-chart-color-[colorname]-500` +1. Second-lightest hue: `--pf-t-chart-color-[colorname]-200` +1. Second-darkest hue: `--pf-t-chart-color-[colorname]-400` \ No newline at end of file diff --git a/packages/site/src/content/design-guidelines/styles/colors-for-charts/colors-grid.jsx b/packages/site/src/content/design-guidelines/styles/colors-for-charts/colors-grid.jsx new file mode 100644 index 0000000000..a9d0210a38 --- /dev/null +++ b/packages/site/src/content/design-guidelines/styles/colors-for-charts/colors-grid.jsx @@ -0,0 +1,83 @@ +import React from 'react'; +import { Grid, GridItem, Flex, FlexItem, Content } from '@patternfly/react-core'; +import '@patternfly/patternfly/patternfly-charts.css'; + +const colorFamilies = [ + 'Red-orange', + 'Orange', + 'Yellow', + 'Teal', + 'Green', + 'Blue', + 'Purple', + 'Black', +]; + +const ColorEntry = ({color, idx, computedStyles}) => { + const varName = `--pf-v6-chart-color-${color.replace(' ', '-').toLowerCase()}-${idx}00`; + const varValue = computedStyles?.getPropertyValue + ? computedStyles.getPropertyValue(varName).toUpperCase() + : ''; + return ( + + +
+
+ + + {varValue} + {varName} + + +
+ ); +}; + +const ColorFamily = ({color, computedStyles}) => { + const entries = []; + for (let i = 1; i < 6; i++) { + entries.push(); + } + + return ( + + {color} family + + {entries} + + + ); +}; + +const ColorsGrid = () => { + let [computedStyles, setComputedStyles] = React.useState(); + + const updateComputedStyles = mutationList => { + for (const mutation of mutationList) { + if ( + mutation.type === "attributes" && + mutation.attributeName === 'class' + ) { + setComputedStyles(getComputedStyle(document.documentElement)); + } + } + } + + React.useEffect(() => { + const getInitialRootStyles = () => typeof window !== "undefined" && window.getComputedStyle && getComputedStyle(document.documentElement); + setComputedStyles(getInitialRootStyles); + const observer = new MutationObserver(updateComputedStyles); + observer.observe(document.documentElement, {attributes: true}); + return () => observer.disconnect(); + }, []); + + return ( + + {colorFamilies.map(color => ( + + ))} + + ) +}; + +export default ColorsGrid; diff --git a/packages/site/src/content/design-guidelines/styles/colors-for-charts/img/example-palette.svg b/packages/site/src/content/design-guidelines/styles/colors-for-charts/img/example-palette.svg new file mode 100644 index 0000000000..36e57e7ba1 --- /dev/null +++ b/packages/site/src/content/design-guidelines/styles/colors-for-charts/img/example-palette.svg @@ -0,0 +1,64 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/packages/site/src/content/design-guidelines/styles/colors-for-charts/img/few-variables.svg b/packages/site/src/content/design-guidelines/styles/colors-for-charts/img/few-variables.svg new file mode 100644 index 0000000000..ab4cc94eec --- /dev/null +++ b/packages/site/src/content/design-guidelines/styles/colors-for-charts/img/few-variables.svg @@ -0,0 +1,46 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/packages/site/src/content/design-guidelines/styles/colors-for-charts/img/figma-colorscale.svg b/packages/site/src/content/design-guidelines/styles/colors-for-charts/img/figma-colorscale.svg new file mode 100644 index 0000000000..9cf1fa5f7b --- /dev/null +++ b/packages/site/src/content/design-guidelines/styles/colors-for-charts/img/figma-colorscale.svg @@ -0,0 +1,10 @@ + + + + + + + + + + diff --git a/packages/site/src/content/design-guidelines/styles/colors-for-charts/img/many-variables.svg b/packages/site/src/content/design-guidelines/styles/colors-for-charts/img/many-variables.svg new file mode 100644 index 0000000000..d46e7e04da --- /dev/null +++ b/packages/site/src/content/design-guidelines/styles/colors-for-charts/img/many-variables.svg @@ -0,0 +1,57 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/packages/site/src/content/design-guidelines/styles/colors-for-charts/img/monochromatic-annotated.svg b/packages/site/src/content/design-guidelines/styles/colors-for-charts/img/monochromatic-annotated.svg new file mode 100644 index 0000000000..9a6d94894f --- /dev/null +++ b/packages/site/src/content/design-guidelines/styles/colors-for-charts/img/monochromatic-annotated.svg @@ -0,0 +1,62 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/packages/site/src/content/design-guidelines/styles/colors-for-charts/img/monochromatic.svg b/packages/site/src/content/design-guidelines/styles/colors-for-charts/img/monochromatic.svg new file mode 100644 index 0000000000..e14a061a86 --- /dev/null +++ b/packages/site/src/content/design-guidelines/styles/colors-for-charts/img/monochromatic.svg @@ -0,0 +1,60 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/packages/site/src/content/design-guidelines/styles/colors-for-charts/img/nested-variables.svg b/packages/site/src/content/design-guidelines/styles/colors-for-charts/img/nested-variables.svg new file mode 100644 index 0000000000..c9c5f4e175 --- /dev/null +++ b/packages/site/src/content/design-guidelines/styles/colors-for-charts/img/nested-variables.svg @@ -0,0 +1,63 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/packages/site/src/content/design-guidelines/styles/colors-for-charts/img/success-and-failure.svg b/packages/site/src/content/design-guidelines/styles/colors-for-charts/img/success-and-failure.svg new file mode 100644 index 0000000000..1a74c2a091 --- /dev/null +++ b/packages/site/src/content/design-guidelines/styles/colors-for-charts/img/success-and-failure.svg @@ -0,0 +1,20 @@ + + + + + + + + + + + + + + + + + + + + diff --git a/packages/site/src/content/design-guidelines/styles/colors/ColorFamily.jsx b/packages/site/src/content/design-guidelines/styles/colors/ColorFamily.jsx new file mode 100644 index 0000000000..fe7666bd3a --- /dev/null +++ b/packages/site/src/content/design-guidelines/styles/colors/ColorFamily.jsx @@ -0,0 +1,88 @@ +import React from 'react'; +import tokens from '@patternfly/react-tokens/dist/esm/patternfly_variables'; +import AngleRightIcon from '@patternfly/react-icons/dist/esm/icons/angle-right-icon'; +import { css } from '@patternfly/react-styles'; +import { normalizeColor, getContrastRatio } from './helpers'; +import { Accordion, AccordionItem, AccordionContent, AccordionToggle, Content, ContentVariants, Title } from '@patternfly/react-core'; + +const palettePrefix = '--pf-t--color--'; + +export function ColorFamily({ + title, + family +}) { + const [expanded, setExpanded] = React.useState([]); + const rootTokens = tokens[':root']; + const familyTokens = Object.values(rootTokens).filter(token => token.name.includes(`${palettePrefix}${family}--`)); + + if (family === 'gray') { + const whiteToken = rootTokens.t_color_white; + familyTokens.unshift(whiteToken); + const blackToken = rootTokens.t_color_black; + familyTokens.push(blackToken); + } + + const expand = name => { + if (expanded.includes(name)) { + setExpanded(expanded.filter(token => token !== name)); + } else { + setExpanded(expanded.concat(name)); + } + }; + + return ( + + {title} + + {familyTokens.map(token => { + const isExpanded = expanded.includes(token.name); + const itemStyle = { + '--pf-v6-c-accordion__toggle--BackgroundColor': `var(${token.name})`, + '--pf-v6-c-accordion__toggle--hover--BackgroundColor': `var(${token.name})`, + fontSize: 'var(--pf-t--global--font--size--md)' + }; + if (getContrastRatio(token.value, '#151515') > 4.5) { + itemStyle['--pf-v6-c-accordion__toggle-text--Color'] = '#151515'; + } + else if (getContrastRatio(token.value, '#151515') <= 4.5) { + itemStyle['--pf-v6-c-accordion__toggle-text--Color'] = '#FFFFFF'; + } + + const tokenList = Object.values(rootTokens) + .filter(t => t.value === token.value && !/\d/.test(t.name)) // only show semantic tokens (without digits at the end) + .map(t => t.name) + .sort(); + + return ( + + expand(token.name)} + id={token.value.replace('#', 'color-')} + style={{ + backgroundColor: `${token.value} !important`, + color: itemStyle['--pf-v6-c-accordion__toggle-text--Color'] + }} + > + #{normalizeColor(token.value.toUpperCase())} + + + {tokenList?.length > 0 ? ( + <> + Semantic tokens<span className='pf-v6-screen-reader'>for {token.value.toUpperCase()}</span> + + {tokenList.map(tokenName => + {tokenName} + )} + + + ) : ( + No semantic tokens<span className='pf-v6-screen-reader'>for {token.value.toUpperCase()}</span> + )} + + + ); + })} + + + ); +} diff --git a/packages/site/src/content/design-guidelines/styles/colors/ColorSwatch.css b/packages/site/src/content/design-guidelines/styles/colors/ColorSwatch.css new file mode 100644 index 0000000000..be88aee3ca --- /dev/null +++ b/packages/site/src/content/design-guidelines/styles/colors/ColorSwatch.css @@ -0,0 +1,5 @@ +.ws-color-swatch > svg { + flex: 0 0 44px; + margin-right: var(--pf-t--global--spacer--md); + border-radius: 50%; +} diff --git a/packages/site/src/content/design-guidelines/styles/colors/ColorSwatch.jsx b/packages/site/src/content/design-guidelines/styles/colors/ColorSwatch.jsx new file mode 100644 index 0000000000..531520fa6b --- /dev/null +++ b/packages/site/src/content/design-guidelines/styles/colors/ColorSwatch.jsx @@ -0,0 +1,79 @@ +import React from 'react'; +import tokens from '@patternfly/react-tokens/dist/esm/patternfly_variables'; +import { Popover, Stack, StackItem, Split, SplitItem, Title, Button } from '@patternfly/react-core'; +import { normalizeColor, tokenName } from './helpers'; +import './ColorSwatch.css'; + +export function ColorSwatch({ + label, + color, + caption, + children +}) { + const token = tokens[":root"][tokenName(color)]; + const popoverContent = ( + + + Token + + {color} + + + {token && ( + + + {'Hex value'} + + + {`#${normalizeColor(token.value)}`} + + + )} + + Usage +

{children}

+
+
+ ); + + return ( + + + All tokens} + hasAutoWidth + > + + + + + + {label || token && `#${normalizeColor(token.value)}`} {caption && `(${caption})`} + + + {color} + + + + ); +} diff --git a/packages/site/src/content/design-guidelines/styles/colors/colors.mdx b/packages/site/src/content/design-guidelines/styles/colors/colors.mdx new file mode 100644 index 0000000000..9352ac4d4b --- /dev/null +++ b/packages/site/src/content/design-guidelines/styles/colors/colors.mdx @@ -0,0 +1,223 @@ +--- +id: Colors +section: design-foundations +--- +import { Alert, Grid, GridItem, Banner, Button, Stack } from '@patternfly/react-core'; +import { Table, Caption, Thead, Tr, Th, Tbody, Td } from '@patternfly/react-table'; +import ArrowRightIcon from '@patternfly/react-icons/dist/esm/icons/arrow-right-icon'; +import { ColorSwatch } from './ColorSwatch'; +import { ColorFamily } from './ColorFamily'; + +# PatternFly's palette + +Our color palettes align with Red Hat's brand colors and are designed to reinforce content and support effective communication across different UI needs. Colors are applied to PatternFly elements using [semantic design tokens.](/tokens/about-tokens) This guide offers guidance for color use in some of the most common scenarios, but it does not cover all tokens. Additional color usage information is included in our tokens documentation. + +
+ +
+ +Each example contains a descriptive label, a semantic token, and a color swatch circle. If you select a color swatch circle, you can see more details, including a hex code and usage information. Color swatches will automatically update to match light or dark theme colors, based on your browser settings. + +## Brand colors + +Brand colors are used to identify your brand, and are the colors most frequently used across your UI. Our brand color, "PatternFly blue", is used across all components. There are different brand tokens depending on the use case, like icon tokens, text tokens, global color tokens, and so on. + + + + + + Use to reinforce your brand. Often indicates a default or active state. + + + Use for branded elements that are in a hover/focus state. + + + Use for branded text elements. + + + + + PatternFly blue colors + + + +## Background colors + +Background colors are used throughout components and, occasionally, for certain screens. + + + + + + Use as the primary background color for UI content such as cards, page sections, and other content areas. + + + Use as the hover color for primary-colored backgrounds. + + + Use as the secondary color for UI content. Also use for UI shell backgrounds, like navigation and mastheads. + + + Use as the hover color for secondary-colored backgrounds. + + + + + PatternFly background colors + + + + +## Text and icon colors + +Text and icon colors overlap, because they can be used inline with each other. Note that there are different tokens for standalone icons, inline icons, and standalone text. For more details view our [icons](/design-foundations/icons) and [typography](/design-foundations/typography) guidelines. + +Text and icons can also display status information, which is covered in the [status and state colors section.](#status-and-state-colors) + + + + + + Use as the primary color for standard text, like heading/body copy. Icons paired with regular text should inherit this color or should use --global--icon--color--regular. + + + Use as a secondary text color for text in an element that requires less emphasis, like descriptions or inactive tab labels. + + + Use as the default color for icons in icon buttons and/or when paired with regular-colored text. + + + Use as the default text color for links. + + + + + PatternFly text and icon colors + + + +## Status and state colors + +Status and state colors are indicators that communicate data and actions to users through the UI. PatternFly's status colors cover default, danger, success, information, and warning statuses, as well as disabled states. + +### Danger + + + + + + Use as the default color for icons that convey danger, like in alerts or banners. + + + Use as the default color for text that communicates a danger status. + + + Use as the hover color for any element that conveys a danger status. + + + + + PatternFly danger colors + + + +### Warning + + + + + + Use as the default color for icons that convey a warning status, like in alerts or banners. + + + Use as the default color for text that communicates a warning status. + + + Use as the hover color for any element that conveys a warning status. + + + + + PatternFly warning colors + + + +### Disabled + + + + + Use as the color for icons that show in disabled icon buttons and/or when paired with disabled-color text + + + Use as the color of text on disabled elements, like disabled menu items. + + + Use as the background color for disabled components. + + + + + PatternFly disabled colors + + + +## Nonstatus colors + + + + + + Use as the default border color for any element that does not convey status and that you always want to be teal, like color-coded labels. + + + Use as the default background color for any element that does not convey status and that you always will want to be purple, like color-coded labels and banners. + + + Use as the hover state color for any element that uses the nonstatus green background color. + + + + + PatternFly nonstatus colors + + + +## Contrast ratios + +[Our goal](/accessibility/patternflys-accessibility/) is for PatternFly to meet [level AA requirements in the Web Content Accessibility Guidelines 2.1](https://www.w3.org/WAI/standards-guidelines/wcag/new-in-21/). To achieve level AA accessibility, your UI contrast ratios must be at or above 4.5:1 for normal text, 3:1 for large text, and 3:1 for graphics and other UI components. Additionally, on hover, link text color should have ample contrast from both the background color and the default state link color. + +To check the contrast between background and text colors, use a WCAG AA-compliance tool. + +## Color families +Our color palettes are organized into "families" that contain different shades of the same hue. In the following families, you can expand each color to see related tokens. + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/packages/site/src/content/design-guidelines/styles/colors/helpers.js b/packages/site/src/content/design-guidelines/styles/colors/helpers.js new file mode 100644 index 0000000000..220c75e032 --- /dev/null +++ b/packages/site/src/content/design-guidelines/styles/colors/helpers.js @@ -0,0 +1,35 @@ +export function normalizeColor(color) { + color = color.toUpperCase(); + if (color.startsWith('#')) { + const hex = color.substr(1); + return hex.length === 3 ? hex.split('').map(char => char.repeat(2)).join('') : hex; + } +} + +function normalizeLuminance(val) { + val = parseInt(val, 16) / 255; + return val <= 0.03928 ? val / 12.92 : Math.pow((val + 0.055) / 1.055, 2.4); +} + +function getRelativeLuminance(color) { + // https://www.w3.org/TR/WCAG21/relative-luminance.xml + const r = normalizeLuminance(color.substr(0, 2)); + const g = normalizeLuminance(color.substr(2, 2)); + const b = normalizeLuminance(color.substr(4, 2)); + return (0.2126 * r) + (0.7152 * g) + (0.0722 * b); +} + +export function getContrastRatio(c1, c2) { + // https://www.w3.org/TR/WCAG21/#dfn-contrast-ratio + c1 = normalizeColor(c1); + c2 = normalizeColor(c2); + + const l1 = getRelativeLuminance(c1); + const l2 = getRelativeLuminance(c2); + + return (l1 + 0.05) / (l2 + 0.05); +} + +export function tokenName(cssVar) { + return cssVar.substr(8).replace(/-+/g, '_'); +} diff --git a/packages/site/src/content/design-guidelines/styles/colors/img/background-colors.png b/packages/site/src/content/design-guidelines/styles/colors/img/background-colors.png new file mode 100644 index 0000000000..26a4ad8982 Binary files /dev/null and b/packages/site/src/content/design-guidelines/styles/colors/img/background-colors.png differ diff --git a/packages/site/src/content/design-guidelines/styles/colors/img/brand-colors.png b/packages/site/src/content/design-guidelines/styles/colors/img/brand-colors.png new file mode 100644 index 0000000000..176af265a0 Binary files /dev/null and b/packages/site/src/content/design-guidelines/styles/colors/img/brand-colors.png differ diff --git a/packages/site/src/content/design-guidelines/styles/colors/img/danger-colors.png b/packages/site/src/content/design-guidelines/styles/colors/img/danger-colors.png new file mode 100644 index 0000000000..37a9365d1d Binary files /dev/null and b/packages/site/src/content/design-guidelines/styles/colors/img/danger-colors.png differ diff --git a/packages/site/src/content/design-guidelines/styles/colors/img/disabled-colors.png b/packages/site/src/content/design-guidelines/styles/colors/img/disabled-colors.png new file mode 100644 index 0000000000..fd8601d000 Binary files /dev/null and b/packages/site/src/content/design-guidelines/styles/colors/img/disabled-colors.png differ diff --git a/packages/site/src/content/design-guidelines/styles/colors/img/nonstatus-colors.png b/packages/site/src/content/design-guidelines/styles/colors/img/nonstatus-colors.png new file mode 100644 index 0000000000..248346cfed Binary files /dev/null and b/packages/site/src/content/design-guidelines/styles/colors/img/nonstatus-colors.png differ diff --git a/packages/site/src/content/design-guidelines/styles/colors/img/primary-colors.png b/packages/site/src/content/design-guidelines/styles/colors/img/primary-colors.png new file mode 100644 index 0000000000..5763e89362 Binary files /dev/null and b/packages/site/src/content/design-guidelines/styles/colors/img/primary-colors.png differ diff --git a/packages/site/src/content/design-guidelines/styles/colors/img/success-colors.png b/packages/site/src/content/design-guidelines/styles/colors/img/success-colors.png new file mode 100644 index 0000000000..73bc83a343 Binary files /dev/null and b/packages/site/src/content/design-guidelines/styles/colors/img/success-colors.png differ diff --git a/packages/site/src/content/design-guidelines/styles/colors/img/text-icon-colors.png b/packages/site/src/content/design-guidelines/styles/colors/img/text-icon-colors.png new file mode 100644 index 0000000000..fcf6780702 Binary files /dev/null and b/packages/site/src/content/design-guidelines/styles/colors/img/text-icon-colors.png differ diff --git a/packages/site/src/content/design-guidelines/styles/colors/img/warning-colors.png b/packages/site/src/content/design-guidelines/styles/colors/img/warning-colors.png new file mode 100644 index 0000000000..73bc83a343 Binary files /dev/null and b/packages/site/src/content/design-guidelines/styles/colors/img/warning-colors.png differ diff --git a/packages/site/src/content/design-guidelines/styles/motion/motion.mdx b/packages/site/src/content/design-guidelines/styles/motion/motion.mdx new file mode 100644 index 0000000000..f6ec009e10 --- /dev/null +++ b/packages/site/src/content/design-guidelines/styles/motion/motion.mdx @@ -0,0 +1,164 @@ +--- +id: Motion +section: design-foundations +--- + +import { Alert, AlertActionLink, Card, CardHeader, CardTitle, CardBody, CardFooter, Grid, GridItem} from '@patternfly/react-core'; +import ExternalLinkAltIcon from '@patternfly/react-icons/dist/esm/icons/external-link-alt-icon'; + + + View the project roadmap + +} +> +

+We are still working on adding motion to all PatternFly components. As we progress, we will release batches of updated components, which will adhere to the principles and guidelines outlined on this page. +

+
+
+ +Like color or typography, **motion** can create a strong foundation that helps connect the complex elements within your designs. By carefully incorporating motion into the design of a UI, you can create products that are more clear, engaging, and expressive. Effective motion design should be intentional, and should be used to help guide users through their experiences more efficiently. + +This guide outlines the principles that drive motion design in PatternFly and describes the different types of motion that are supported in our design system. + +## Principles +These principles guide the use of motion in PatternFly, to ensure consistency and alignment with our [brand voice and tone](https://www.patternfly.org/ux-writing/brand-voice-and-tone). + +
+ + + + + + Intentional + + Motion should be intentionally designed in ways that help your users reach their goals. Animations should be quick and simple to focus your users’ attention only on what’s important, without distracting. + + + + + + Consistent + + Motion should be applied consistently to ensure that you’re sticking to the best design practices. Consistent animations provide a sense of familiarity to users throughout their journey and connect cross-product experiences. + + + + + + Engaging + + To draw your users in and keep them interested, motion should be expressive and approachable. Animations should celebrate the big moments in our users’ journeys and add character to common interactions. + + + + + + Inclusive + + + Motion should contribute to experiences that offer all of your users a sense of belonging. Animations should always be optional and should respect your users’ motion preferences. + + + + + +## Motion in PatternFly + +PatternFly components support motion in the form of **micro animations**, which are small, unobtrusive, and often understated. These animations serve specific purposes within a UI, and are designed to be subtle and complementary. + +Animations are largely built into PatternFly components, but there may be instances where you need to use our motion tokens to enable an animation in your specific scenarios. Wherever PatternFly provides animation, reduced motion support (based on users' browser settings) is provided. + +If you want to implement additional motion, or if you'd like to customize the default PatternFly behavior, [follow these practices.](#custom-motion) + +### Types of animations +There are 5 different types of animations used in PatternFly: +1. **Hover:** Shown when a user hovers over an element to inform them that the item can be clicked. +1. **Click:** Shown when a user clicks an element, in order to provide immediate feedback that confirms user actions. +1. **Loading:** Loading animations, like spinners or progress bars, which keep users informed about the loading process in order to reduce frustration. +1. **Errors/validation:** Shown when an error occurs during a validation process, in order to draw attention to error messages and guide users as they resolve issues. +1. **Change:** Smooth transitions between different screens or sections of an application or website that enhance user flow and engagement. + +### Anatomy of an animation +An animation is composed of 4 elements: triggers, duration, easing, and properties. + +1. **Triggers:** The event that causes the animation to happen. These can be: + - User-initiated. For example, a gesture or click. + - System-initiated. For example, after a certain amount of time. + +1. **Duration:** Describes how long animations should be. + - Shorter durations are used for simpler effects and smaller animations. For example, fading or color changing. + - Longer durations are used for more complex effects and larger-scale animations. For example, page transitions or objects that slide in and out of the screen. Optimal timing can change based on viewport size. + +1. **Easing:** Describes how an element transitions over time. + +1. **Properties:** The characteristics of the element being transitioned. Animations may have multiple properties, including: + - Fade in/out + - Scale + - Rotate + - Color transitions + - Slide in/out + - Expand/collapse + +## Developing and designing with motion + +### Figma +In Figma, you can find annotations and prototype videos for each animation... + +### Motion tokens + +PatternFly component animations are created using design tokens that cover the different elements of an animation, including duration, delay, and timing. Like we do with color tokens, we implement motion by using semantic tokens, which are built off of base tokens. Motion tokens begin with `-pf-t--global--motion--` + +You can [search for motion tokens here.](/tokens/all-patternfly-tokens) + +If you aren't familiar with our token system, [refer to this overview](/tokens/about-tokens). + +#### Duration +Duration tokens specify the length of time that different animation should take to complete. There are predefined duration tokens based on the type of animation, shown in the following table; + +| **Animation** | **Description** | **Tokens** | +| --- | --- | --- | +| Slide-out | Moves an element out of the viewport. | `-pf--t--global--motion--duration--slide-out--short`

`-pf--t--global--motion--duration--slide-out--default`

`-pf--t--global--motion--duration--slide-out--long` | +| Slide-in | Moves an element into the viewport from offscreen. | `-pf--t--global--motion--duration--slide-in--short`

`-pf--t--global--motion--duration--slide-in--default`

`-pf--t--global--motion--duration--slide-in--long` | +| Fade | Applies a gradual transition to an element. | `--pf-t--global--motion--duration--fade--short`

`--pf-t--global--motion--duration--fade--default`

`--pf-t--global--motion--duration--fade--long` | +| Icon | Applies transitions to icons. | `--pf-t--global--motion--duration--icon--short`

`--pf-t--global--motion--duration--icon--default`

`--pf-t--global--motion--duration--icon--long` | +
+ +#### Delay +Delay tokens specify the length of time that should pass before an animation begins. Delay options include none, short, default, and long. + +| **Token** | **Value** | +| --- | --- | +| `--pf-t--global--motion--delay--none` | 0ms | +| `--pf-t--global--motion--delay--short` | 50ms | +| `--pf-t--global--motion--delay--default` | 100ms | +| `--pf-t--global--motion--delay--long` | 7000ms | +
+ +#### Timing +Timing-function tokens specify the easing path that an animation takes. These paths are defined by [cubic Bezier curves,](https://developer.mozilla.org/en-US/docs/Web/CSS/easing-function#cubic_b%C3%A9zier_easing_functionyar) which define the start and end points of a curve, as well as its initial and final times and states. + +The available options for timing are described in the following table: + +| **Timing function** | **Description** | **Token** | **Value** | +| --- | --- | --- | --- | +| Accelerate | Specifies that the animation starts slowly and accelerates gradually until the end. Equivalent to an "ease-in" transition. | `--pf-t--global--motion--timing-function--accelerate` | cubic-bezier(.4, 0, .7, .2) +| Default | Use default to specify that the animation starts slow, speeds up and slows down at the end. Equivalent to an "ease-in-out" transition.| `--pf-t--global--motion--timing-function--default` | cubic-bezier(.4, 0, .2, 1) +| Decelerate | Use decelerate to specify that the animation starts quickly and decelerates gradually until the end. Equivalent to an "ease-out" transition. | `--pf-t--global--motion--timing-function--decelerate` | cubic-bezier(0, 0, .2, 1) + +### Motion patterns + +A **motion pattern** is a combination of tokens and properties that work together to solve common animation needs. These patterns help ensure that the behavior of a type of animation is consistent across similar use cases—even if different components are involved. + +For example, an "action fade" pattern may dictate how animation is applied when a user selects an action. This pattern specifies the timing and duration of the fade, so that the animation is the same across different action components. In this example, we would want users to see the same hover/click animation whether they're interacting with an action button, an action menu, and so on. + +### Custom motion + +For some scenarios, like creating a new [PatternFly extension](/extensions/about-extensions), you may need to customize motion that doesn't already exist in PatternFly components. When you're creating a new animation behavior, make sure that: +- There is no existing support for the animation. +- The animation adheres to our motion principles and respects users' [`prefers-reduced-motion` settings.](https://developer.mozilla.org/en-US/docs/Web/CSS/@media/prefers-reduced-motion) +- Your implementation uses appropriate semantic tokens. \ No newline at end of file diff --git a/packages/site/src/content/design-guidelines/styles/spacers/auto-layout-spacers.png b/packages/site/src/content/design-guidelines/styles/spacers/auto-layout-spacers.png new file mode 100644 index 0000000000..d1dae92fb2 Binary files /dev/null and b/packages/site/src/content/design-guidelines/styles/spacers/auto-layout-spacers.png differ diff --git a/packages/site/src/content/design-guidelines/styles/spacers/complex-text-spacing.png b/packages/site/src/content/design-guidelines/styles/spacers/complex-text-spacing.png new file mode 100644 index 0000000000..23f284ffe4 Binary files /dev/null and b/packages/site/src/content/design-guidelines/styles/spacers/complex-text-spacing.png differ diff --git a/packages/site/src/content/design-guidelines/styles/spacers/heading-body-spacing.png b/packages/site/src/content/design-guidelines/styles/spacers/heading-body-spacing.png new file mode 100644 index 0000000000..66aadd9f95 Binary files /dev/null and b/packages/site/src/content/design-guidelines/styles/spacers/heading-body-spacing.png differ diff --git a/packages/site/src/content/design-guidelines/styles/spacers/icon-spacing.png b/packages/site/src/content/design-guidelines/styles/spacers/icon-spacing.png new file mode 100644 index 0000000000..f80053cfd6 Binary files /dev/null and b/packages/site/src/content/design-guidelines/styles/spacers/icon-spacing.png differ diff --git a/packages/site/src/content/design-guidelines/styles/spacers/spacers.css b/packages/site/src/content/design-guidelines/styles/spacers/spacers.css new file mode 100644 index 0000000000..dfa795c337 --- /dev/null +++ b/packages/site/src/content/design-guidelines/styles/spacers/spacers.css @@ -0,0 +1,71 @@ + +.content-inner-div { + margin-left: var(--pf-t--global--spacer--xs); +} + +.ws-content-spacerTitle { + font-weight: var(--pf-t--global--font--weight--heading); + font-size: var(--pf-t--global--font--size--heading--md); +} + +.ws-content-p { + font-size: var(--pf-t--global--font--size--lg); +} + +.ws-content-spacer4 { + background-color: var(--pf-t--color--orange--50); + width: var(--pf-t--global--spacer--xs); + height: var(--pf-t--global--spacer--3xl); +} + +.ws-content-spacer8 { + background-color: var(--pf-t--color--green--30); + width: var(--pf-t--global--spacer--sm); + height: var(--pf-t--global--spacer--3xl); +} + +.ws-content-spacer16 { + background-color: var(--pf-t--color--green--60); + width: var(--pf-t--global--spacer--md); + height: var(--pf-t--global--spacer--3xl); +} + +.ws-content-spacer24 { + background-color: var(--pf-t--color--blue--50); + width: var(--pf-t--global--spacer--lg); + height: var(--pf-t--global--spacer--3xl); +} + +.ws-content-spacer32 { + background-color: var(--pf-t--color--purple--50); + width: var(--pf-t--global--spacer--xl); + height: var(--pf-t--global--spacer--3xl); +} + +.ws-content-spacer48 { + background-color: var(--pf-t--color--yellow--50); + width: var(--pf-t--global--spacer--2xl); + height: var(--pf-t--global--spacer--3xl); +} + +.ws-content-spacer64 { + background-color: var(--pf-t--color--red-orange--50); + width: var(--pf-t--global--spacer--3xl); + height: var(--pf-t--global--spacer--3xl); +} + +.ws-content-spacer80 { + background-color: var(--pf-t--color--red--50); + width: var(--pf-t--global--spacer--4xl); + height: var(--pf-t--global--spacer--3xl); +} + +.ws-content-border { + margin: 0; + padding: 0; + border: var(--pf-t--global--border--width--regular) solid var(--pf-t--global--border--color--nonstatus--blue--default); +} + +.ws-content-p + .ws-content-border { + margin-top: var(--pf-t--global--spacer--lg); +} diff --git a/packages/site/src/content/design-guidelines/styles/spacers/spacers.mdx b/packages/site/src/content/design-guidelines/styles/spacers/spacers.mdx new file mode 100644 index 0000000000..663f0e5eed --- /dev/null +++ b/packages/site/src/content/design-guidelines/styles/spacers/spacers.mdx @@ -0,0 +1,69 @@ +--- +id: Spacers +section: design-foundations +--- +import './spacers.css'; + + +PatternFly designs use **spacers** to define fixed amounts of space between UI elements. They help you create designs that are visually balanced and consistent. Spacers are built into PatternFly components, and are also available as tokens for you to use within Figma's auto layout system: + +![Spacer tokens displayed as options in a Figma layout menu](./auto-layout-spacers.png) + +## Spacer sizing + +Like the rest of our dimension tokens, spacers use rem sizing, rather than pixels. Rems are relative units that adjust size based on a webpage's HTML document root element size. For example, if the root size is 10px, a rem size of 1.5 would be 15px. + +PatternFly's default root element size is 16px. If you change this default size, note that the following table will no longer show accurate pixel measurements (though the rem values will stay the same). +## PatternFly spacers + +Our spacers include the following sizes: + +| **Spacer** | **Token** | **Size** | **Example** | +| :-:| :-: | :-: | :-: | +| xs | `--pf-t--global--spacer--xs` | .25rem (4px) |
| +| sm | `--pf-t--global--spacer--sm` | .5rem (8px) |
| +| md | `--pf-t--global--spacer--md` | 1rem (16px) |
| +| lg | `--pf-t--global--spacer--lg` | 1.5rem (24px) |
| +| xl | `--pf-t--global--spacer--xl` | 2rem (32px) |
| +| 2xl | `--pf-t--global--spacer--2xl` | 3rem (48px) |
| +| 3xl | `--pf-t--global--spacer--3xl` | 4rem (64px) |
| + | 4xl | `--pf-t--global--spacer--4xl` | 5rem (80px) |
+ +### Spacer tokens + +Our spacer tokens are based on the values in the previous table, but there are certain use cases that align with more specific tokens. When using spacers in these scenarios, always use these more specific semantic tokens, rather than a global spacer token. +- **Action spacers:** Used to set horizontal and vertical padding within actions, like buttons. + - Action spacer tokens begin with `--pf-t--global--spacer--action--` +- **Control spacers:** Used to set horizontal and vertical padding within controls, like menu toggles and text inputs. + - Control spacer tokens begin with `--pf-t--global--spacer--control--` +- **Gap spacers:** Used to set space between elements or groups of elements, like gaps between multiple actions, gaps between items in a group, gaps between controls, and so on. + - Gap spacer tokens begin with `--pf-t--global--spacer--gap` + +You can search for spacer tokens in [our list of all tokens.](/tokens/all-patternfly-tokens) +## Considering line height and padding + +There are additional considerations to keep in mind when adapting spacers to different line heights and padding, which are common with PatternFly components and text content. + +### Using spacers with components + +Some components like icons, buttons, and input fields, have a fixed amount of padding built in. Remember to account for this extra space when laying the content out on your page. You may not have as much horizontal or vertical room as you think. + +For example, padding around this vertical ellipsis (or "kebab") icon increases the amount of space that it takes up in a component: + +![A vertical ellipsis icon with an extra small spacer symbol.](./icon-spacing.png) + +When laying out your design, make sure to account for this extra padding. +### Using spacers with text + +When spacing out text-based content, use the standard [global spacer tokens.](/design-foundations/spacers#patternfly-spacers) + +You should consider line height to ensure that you’re leaving the right amount of vertical space between each line of text: + +![A medium spacer placed between a heading and body text.](./heading-body-spacing.png) + +You also need to use different spacer sizes depending on the type of text you’re using. For example, you’ll need to provide a 16px spacer between a title and body copy, but only an 8px spacer between items in a bulleted or numbered list. + +![Different-sized spacers placed between heading, body, and list text](./complex-text-spacing.png) + +For more information about line height and text spacing, read our [typography guidelines.](/design-foundations/typography) + diff --git a/packages/site/src/content/design-guidelines/styles/typography/line-height.png b/packages/site/src/content/design-guidelines/styles/typography/line-height.png new file mode 100644 index 0000000000..4676223686 Binary files /dev/null and b/packages/site/src/content/design-guidelines/styles/typography/line-height.png differ diff --git a/packages/site/src/content/design-guidelines/styles/typography/typography.mdx b/packages/site/src/content/design-guidelines/styles/typography/typography.mdx new file mode 100644 index 0000000000..8493a5b5b6 --- /dev/null +++ b/packages/site/src/content/design-guidelines/styles/typography/typography.mdx @@ -0,0 +1,105 @@ +--- +id: Typography +section: design-foundations +--- + +import { Content as PFContent, ContentVariants, Title } from '@patternfly/react-core'; +import correct from './typography_correct_spacing.png'; +import incorrect from './typography_incorrect_spacing.png'; + +You can use **typography** to create visual hierarchy in a UI. By creating a consistent and logical hierarchy, users can more quickly scan and understand information on a page. + +This page outlines PatternFly's typography principles and standards, including token values and usage information. + +You can place text content on a page using the content or title component: +- **[Content component:](/components/content)** Used to create formatted blocks of text content. Content accepts all general HTML text formatting tags, including heading, paragraph, and list styles. +- **[Title component:](/components/title)** Used specifically for headings or title text in components. Title is flexible and allows you to set the size of the text and heading level independently. + +## PatternFly fonts + +We use 3 fonts in PatternFly: +- **Red Hat Display:** Used for larger text, such as headings. +- **Red Hat Text:** Used for smaller text, subheadings, and body text. More readable for long-form text. +- **Red Hat Mono:** A tabular font used to format text as code. [Read more about our use of tabular font styling.](#tabular-font-styling) + +[Download PatternFly's fonts from GitHub.](https://github.com/RedHatOfficial/RedHatFont) + +### Font sizing: rem vs pixel + +Font size tokens use rems, rather than pixels. Rems are relative units that adjust font size based on a webpage's HTML document root element size. For example, if the root size is 10px, a rem size of 1.5 would be 15px. + +PatternFly's default root element size is 16px. If you change this default size, note that the following tables will no longer show accurate pixel measurements (though the rem values will stay the same). + +## Headings + +All headings use Red Hat Display bold. + +| Example | Tokens | Size | Line height | Usage | +| --- | --- | --- | --- | --- | +| Aa | --pf-t--global--font--size--heading--h1 | 1.5rem (24px) | 1.3 | Super hero headings
H1
Page titles | +| Aa | --pf-t--global--font--size--heading--h2 | 1.25rem (20px) | 1.3 | Hero headings
H2 | +| Aa | --pf-t--global--font--size--heading--h3 | 1.125rem (18px) | 1.3 | H3 | +| Aa | --pf-t--global--font--size--heading--h4
--pf-t--global--font--size--heading--h5
--pf-t--global--font--size--heading--h6 |1rem (16px) | 1.3 | H4
H5
H6 | + +### Customizing heading levels +The [title component](/components/title) allows you to customize the visual hierarchy of text on your page, while keeping the semantic hierarchy consistent with expectations for accessibility. + +The following table shows the default mapping of PatternFly heading levels to text size: + +| Heading level | Default size | +|----|-----------| +| H1 | 2xl (1.5rem, 24px)| +| H2 | xl (1.25rem, 20px) | +| H3 | lg (1.125rem, 18px) | +| H4 | md (1 rem, 16px) | +| H5 | md (1 rem, 16px) | +| H6 | md (1 rem, 16px) | + +If you use the title component, you can change the text size of your heading levels to customize beyond this default behavior. + +For example, you may decide that the default size of 20px for secondary headings is too large and you want to decrease the size from 20px (xl) to 18px (lg). Instead of making your secondary headings H3’s to set the size, you should use the title component to keep them as H2 headings and change the `size` property from `xl` to `lg`. + +Example: + + This is a default "xl" H2. +``` Aa ``` + + This is a customized "lg" H2. +``` Aa ``` + +Make sure that you maintain good visual hierarchy and mapping between heading levels and text sizes. In most cases, H1 should always be your largest heading and subheadings should get progressively smaller as you move down the hierarchy. Rare exceptions to this rule do occur, but should only be used to highlight critical data. For example, there might be scenarios where card titles use a text size that is larger than the H1 page title. + +Refer to the [title component examples](/components/title#custom-sizes) to understand the range of customization options. + +## Body text + +All body text uses Red Hat Text. + +| Example | Tokens | Size | Line height | Usage | +| --- | --- | --- | --- | --- | +|

Aa

| --pf-t--global--font--size--body--lg | 1rem (16px) | 1.5 | Use for larger body text, like in xl empty states. | +| Aa | --pf-t--global--font--size--body--default | 0.875rem (14px) | 1.5 | Use for standard body text. | +| Aa | --pf-t--global--font--size--body--sm | 0.75rem (12px) | 1.5 | User for smaller body text, like helper text. | + +## Tabular font styling + +The primary fonts used in PatternFly (Red Hat Display and Red Hat Text) are proportional fonts, which typically offer better readability for standard blocks of text. When numerals are placed within long text bodies, as part of the text, it is best to use a proportional font. + +Sometimes, numerals benefit from the use of a tabular font instead. **Tabular fonts** apply uniform width and spacing to helps maintain proper alignment of numbers. This can be particularly helpful when numbers are dynamically changing on screen, to prevent rough and jumpy movement. + +Tabular font styling is used in a couple of PatternFly components, including slider and progress, but we also offer a modifier that allows you to apply tabular styling on your own: `.pf-v6-m-tabular-nums`, which sets `font-variant-numeric: tabular-nums;` + +## Line height and spacing +The line height of your text impacts how you should use [spacers](/design-foundations/spacers) in your design. + +Your overall line height can be calculated by multiplying the font's built-in line height by the text size. + +For example, if your font has a line height of 1.5 and a size of 16px, the final height of a line of text would be 24px (16px * 1.5 = 24px). In this example, you would consider the final line height of 24px when creating designs. + +![Correct and incorrect text spacing examples.](./line-height.png) + +## Line length + +Line length measures the number of characters in a single line of text, including spaces. To increase readability and contribute to well-balanced spacing on a screen, use line lengths between 20 and 100 characters. + +Lines that are too long can be difficult to follow, while lines that only include a few words per line can use space inefficiently. \ No newline at end of file diff --git a/packages/site/src/content/design-guidelines/styles/typography/typography_correct_spacing.png b/packages/site/src/content/design-guidelines/styles/typography/typography_correct_spacing.png new file mode 100644 index 0000000000..bc0835b80b Binary files /dev/null and b/packages/site/src/content/design-guidelines/styles/typography/typography_correct_spacing.png differ diff --git a/packages/site/src/content/design-guidelines/styles/typography/typography_incorrect_spacing.png b/packages/site/src/content/design-guidelines/styles/typography/typography_incorrect_spacing.png new file mode 100644 index 0000000000..cf11b53fc1 Binary files /dev/null and b/packages/site/src/content/design-guidelines/styles/typography/typography_incorrect_spacing.png differ diff --git a/packages/site/src/content/design-guidelines/usage-and-behavior/bulk-selection/bulk-selection.mdx b/packages/site/src/content/design-guidelines/usage-and-behavior/bulk-selection/bulk-selection.mdx new file mode 100644 index 0000000000..6981a6d30c --- /dev/null +++ b/packages/site/src/content/design-guidelines/usage-and-behavior/bulk-selection/bulk-selection.mdx @@ -0,0 +1,49 @@ +--- +id: Bulk selection +section: patterns +--- + +## Bulk selection +Use a bulk selection pattern when you want to select or deselect multiple items in a content view (list, table, or card grid). The bulk selector uses a [Split button](/components/menus/menu-toggle#split-button-toggle-with-checkbox) component to control selection from the [Toolbar](/components/toolbar). Besides controlling selection, the bulk selector reflects the selection status of the related component (partially selected, all items selected, or no items selected). + +## Bulk selector +The bulk selector is created using a Split button and is always located as the leftmost item in a toolbar. + +Bulk selector + +**1. Bulk selector:** The bulk selector uses a split button to combine a selection checkbox with a dropdown menu. + +**2. Checkbox:** The state of the checkbox reflects the current selection state of the list, table, or card grid. + +Bulk Selector Checkbox States + +**3. Items selected:** This text always reflects the total number of items selected. If pagination is in use, it will reflect the items selected across all pages. + +**4. Menu:** at a minimum the menu will include: +* Select none - to clear selections across all pages. +* Select page - to select all items on the current page (when pagination is in use). +* Select all - to select all items across pages. + +Additional menu items can be added to select items that match some predetermined filter criteria, such as “Red Cars or Blue Cars” / “Running VMs”, etc. + +## Usage +### Bulk selection from the toolbar +The example below shows a bulk selector placed in a toolbar above a table using pagination. + +Bulk selection from toolbar + +There are 50 total items in this dataset spread across 10 pages (5 items per page), but only the first page has been selected and therefore partial selection is reflected in the checkbox. The user may select (or deselect) additional items either through the use of the bulk selection checkbox, the bulk selection menu, or by clicking on the checkbox at the front of a row. The selected items count will update whenever selection is changed. + +### Bulk selection and global actions +Bulk selection is often used to select multiple items and perform an action on them. Note that after an action is completed, the selection state remains as is until the user changes the selection. + +### Integrated bulk selection for tables +Tables are unique to other view in that they include integrated bulk selection by default. Below is an example of a PatternFly table component with integrated bulk selection in the header row. + +Integrated bulk selection in a table + +**1. Bulk selection checkbox:** A checkbox in the header row of a table will select (or deselect) all items in the table or all items on the current page if pagination is in use. + +In PatternFly we recommend that integrated bulk selection only be used in cases where a table is placed in a page without a toolbar. Whenever a toolbar is present, we recommend using the toolbar to control bulk selection. This will provide for better visibility on the count of selected items, lead to better consistency between view types, and allow for more variety of selection options. + +Note: To hide integrated bulk selection and enable selection control from the toolbar in the PatternFly React Table component, set the canSelectAll prop to ‘false’. diff --git a/packages/site/src/content/design-guidelines/usage-and-behavior/bulk-selection/img/bulk-select-checkbox.png b/packages/site/src/content/design-guidelines/usage-and-behavior/bulk-selection/img/bulk-select-checkbox.png new file mode 100644 index 0000000000..09ac40db28 Binary files /dev/null and b/packages/site/src/content/design-guidelines/usage-and-behavior/bulk-selection/img/bulk-select-checkbox.png differ diff --git a/packages/site/src/content/design-guidelines/usage-and-behavior/bulk-selection/img/bulk-selection-example.png b/packages/site/src/content/design-guidelines/usage-and-behavior/bulk-selection/img/bulk-selection-example.png new file mode 100644 index 0000000000..a36b84be29 Binary files /dev/null and b/packages/site/src/content/design-guidelines/usage-and-behavior/bulk-selection/img/bulk-selection-example.png differ diff --git a/packages/site/src/content/design-guidelines/usage-and-behavior/bulk-selection/img/bulk-selection-no-toolbar.png b/packages/site/src/content/design-guidelines/usage-and-behavior/bulk-selection/img/bulk-selection-no-toolbar.png new file mode 100644 index 0000000000..d00d77c596 Binary files /dev/null and b/packages/site/src/content/design-guidelines/usage-and-behavior/bulk-selection/img/bulk-selection-no-toolbar.png differ diff --git a/packages/site/src/content/design-guidelines/usage-and-behavior/bulk-selection/img/bulk-selector.png b/packages/site/src/content/design-guidelines/usage-and-behavior/bulk-selection/img/bulk-selector.png new file mode 100644 index 0000000000..00ea1ca32e Binary files /dev/null and b/packages/site/src/content/design-guidelines/usage-and-behavior/bulk-selection/img/bulk-selector.png differ diff --git a/packages/site/src/content/design-guidelines/usage-and-behavior/empty-state/img/access-denied.jpg b/packages/site/src/content/design-guidelines/usage-and-behavior/empty-state/img/access-denied.jpg new file mode 100644 index 0000000000..dfc08b65ca Binary files /dev/null and b/packages/site/src/content/design-guidelines/usage-and-behavior/empty-state/img/access-denied.jpg differ diff --git a/packages/site/src/content/design-guidelines/usage-and-behavior/empty-state/img/add.png b/packages/site/src/content/design-guidelines/usage-and-behavior/empty-state/img/add.png new file mode 100644 index 0000000000..339062bbd1 Binary files /dev/null and b/packages/site/src/content/design-guidelines/usage-and-behavior/empty-state/img/add.png differ diff --git a/packages/site/src/content/design-guidelines/usage-and-behavior/empty-state/img/level-of-detail.jpg b/packages/site/src/content/design-guidelines/usage-and-behavior/empty-state/img/level-of-detail.jpg new file mode 100644 index 0000000000..0a0ca3c47a Binary files /dev/null and b/packages/site/src/content/design-guidelines/usage-and-behavior/empty-state/img/level-of-detail.jpg differ diff --git a/packages/site/src/content/design-guidelines/usage-and-behavior/filters/filters.mdx b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/filters.mdx new file mode 100644 index 0000000000..a6adf7be58 --- /dev/null +++ b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/filters.mdx @@ -0,0 +1,404 @@ +--- +id: Filters +section: patterns +related: [ + 'Badge', + 'Label', + 'Label group', + 'Search input', + 'Options menu', + 'Select', + 'Toolbar' +] +--- + +import "../../components/components.css" + +**Filters** allow users to narrow down content from data in tables, data lists or card views, among many others. + +## Filter types + +Filters can contain 1 attribute or multiple attributes. PatternFly components can be combined in different ways to create more complex filtering experiences. These different filter types can be used in a toolbar or on their own. + +Filters consisting of single attributes include: +* [Text entry](#text-entry-filters) +* [Single select](#single-select) +* [Checkbox select](#checkbox-select) + +Filters consisting of multiple attributes include: +* [Attribute-value](#attribute-value-filter) +* [Filter group](#filter-group) +* [Toggle group](#toggle-group) +* [Faceted filter](#faceted-filter) + +## Filter features + +All types of filters can include any of the following attributes: +* [Filter labels](#filter-labels): A way for users to see their selections when the menu is closed. +* [Typeahead](#typeahead): A way for users to narrow down the list of options when looking for the value they want to select. +* [Badge count](#badge-count): Indication of how many selections were made within the menu. + +The following table outlines which features are supported for each filter type. Just because a feature is supported, does not mean it must be used in your filters. + +| **Filter type** | **Filter labels** | **Typeahead** | **Badge count** +| ----------------- | ------- | ------ | ------- | +| Text entry| Yes (only for attribute filters) | Yes | No | +| Single select | Yes (only for attribute filters) | Yes | No | +| Checkbox select | Yes | No (but you can have a search inside the menu) | Yes | +| Attribute-value | Yes | Yes (except for checkbox selects) | Yes (only for checkbox select) +| Filter group | Yes | Yes (only for single selects) | Yes (only for checkbox selects) | +| Toggle group | No | No | No| +| Faceted filter | Yes | Yes | Yes| + +### Filter labels + +When filters are applied, filter labels can be used to provide feedback to the user on what they are filtering on. + +
+![Filter label that shows an active filter based on the user's selection.](./img/filter-label.svg) +
+ +1. **Filter label:** Shows users what conditions they are filtering on. Can show boolean relationships between different attribute-value pairs. Individual filter labels can be removed by clicking the ‘x’ in each label, and entire filter groups can be removed using the group ‘x’. + +Follow these best practices for using filter labels: +* Filters between attribute categories should be combined with a boolean “AND” operator. +* Filters within a category are shown grouped together and should be combined with a boolean “OR” operator. + * **Example:** An item must be Stopped “OR” Down “AND” have Samsung “OR” Hewlett-Packard as a vendor. +* If the list is not otherwise sorted, items that satisfy a higher number of filters should be shown higher up the page. + * **Example:** Items that have both Samsung and Hewlett-Packard as vendors are listed before items that only have Samsung or Hewlett-Packard. +In this example, the result will be to show all items that have a status of stopped “OR” down “AND” are from vendor Samsung “OR” Hewlett-Packard “AND” match the keyword. + +#### When to use +Use filter labels when: +* The value of the applied filter is not shown on the control itself. +* There is more than 1 value for a given facet. +* There are boolean filter rules being applied. + +**Don’t use** filter labels when the current settings of the controls are sufficient to convey applied filters. + +### Typeahead +Adding typeahead capabilities to your filters is useful when there is a large number of items to select from the filter dropdown. Users can quickly find the value they would like to filter by typing in the field. + +
+![Before and after typeahead filtering in a menu.](./img/typeahead.svg) +
+ +Typeahead is supported in single selects, faceted filters that can handle 1 input. Users can scroll through the dropdown list or type in the box to find the desired option. + +#### When to use +Use a typeahead filter when: +* A dropdown list has a large number of options. In these cases, typeahead can help a user find their desired option in less time. +* Typeahead filters can be used in place of a textbox filter, in certain cases. For example, when filtering by name, using a typeahead filter will ensure that only valid filters surface. This will avoid the need to present an empty state when invalid values are entered. + +#### Behavior +A filter query is triggered whenever a new value is set by the user. The following are triggers applicable to the variations of the typeahead filter shown in the previous example. + +| Value selector                       | Trigger | +| -------------------------------------------| ------ | +| Search field                         | The user types in an input and/or presses the Enter key after typing in the input field. This action will create a filter for the first value shown in the filtered list. | +| Select lists                     | The user selects or deselects an item in the list. | + +### Badge count +Badges are used to indicate a count. In filters, badges can be used in the following ways: + +#### Badge in checkbox select +You can opt to use a badge in a checkbox select to indicate to the user how many items they have selected when the toggle is collapsed. + +
+![Badge in menu toggle that displays the number of items that have been selected as filter conditions.](./img/badge-count.svg) +
+ +## Variations for 1 attribute +There are various ways to allow users to filter down content. Single filtering methods include [text entry filters](#text-entry-filters), [single selects](#single-select) and [checkbox selects](#checkbox-select). + +### Text entry filters +A text entry filter provides the user with an input field to type in values that filter the view, whether or not their input is an exact match. The text entry filter uses the [search input](/components/search-input) component which can be used with or without a button. + +
+![1 basic search input field and 1 search input with a submit button.](./img/text-entry-filters.svg) +
+ +1. **Basic search input:** Filters automatically, as soon as the user starts typing. +2. **Search input with button:** Filters on enter, or clicks of the arrow button. + +Note, the placeholder text in your text entry filter should indicate what the user can filter on. If the inputted string is constrained to filter a **single column**, the placeholder text of the input field should read “Filter by _attribute name_”. If the inputted string filters **all columns**, the placeholder text of the input field should read “Filter” instead. + +#### Behavior +Although both basic filter components have the same end result, they differ in when the search is triggered. With search inputs, the data in the table automatically filters as the user types. With input groups, the user must press enter to apply the search, and start filtering data in the table. + +**Note:** With both basic filter components, the user can only filter by 1 input at a time. + +#### When to use +Use a text entry filter when you’d like to give users the ability to search values in unbound data. Using the _search input_ component is preferred, however, use the _input group_ component when you are worried about performance issues with querying a large data set after every stroke. + +#### Supported features +Text entry filters support [filter labels](#filter-labels), but do not support [typeahead](#typeahead) or [badges](#badge-count). + +Filter labels are supported for text entry filters, but in general, we recommend not showing a label to avoid redundancy, except for cases when text entry filters are used inside of [attribute-value filters](#attribute-value-filter). + +Since you can only search by 1 value at a time, the value will already be shown in the input field, as shown in the following image. + +
+![Search value shown in the search input field.](./img/search-value.svg) +
+ +### Single select +A single select provides the user with a fixed set of values from which they can only select 1 value. This filter type uses the [single select component](/components/select/react#single). + +If the single select filter is the only filter in the toolbar, it should have an “All options” menu item that's selected by default, acting as an equivalent of no filter selected. + +
+![Single select menu with 'all options' item selected.](./img/single-select-default.svg) +
+ +When a different menu item is selected, it should be displayed in the toggle. Selecting "All options" will reset any selected options. + +
+![Single select menu with specific item selected.](./img/single-select-selection-mode.svg) +
+ +#### Behavior +The user is presented with a list of values to choose from. A selected value is indicated with a blue checkmark to the right of the value. When a value is selected, the selection appears in the toggle. +When a user selects a different value, the initial selected value becomes unselected. The new value inherits the blue checkmark and is reflected in the toggle. + +#### When to use +Use a single select list when you’d like users to only select 1 option from a **predefined list** of options. + +#### Supported features +Typeahead functionality can be added to single selects, allowing users to input a search inside the toggle, filtering down from the list of menu options shown. This is especially useful for very long lists that would be inconvenient for the user to scroll through. typeahead is recommended for lists that are more than 10 items long. + +
+![Before and after typeahead filtering in a menu.](./img/typeahead-input.svg) +
+ +Stand alone single selects in a toolbar do not use badge counts or filter labels since only 1 selection can be made, and the selection will already be apparent in the toggle. + +### Checkbox select +A checkbox select provides the user with a fixed set of values from which they can select multiple values. This filter type uses the [checkbox select component](/components/menus/select#checkbox-select). + +
+![Before and after multiple items are selected from a checkbox select menu.](./img/checkbox-select-menus.svg) +
+ +#### Behavior +The user is presented with a list of values to choose from. From this list, users can select or deselect 1 or more values at a time, with selections indicated by a blue checkbox preceding the value. The dropdown should remain open as the user makes selections until they click away or manually close it. Selected values will appear as filter labels underneath the filter, allowing the user to see their selections even when the toggle is collapsed. + +#### When to use +Use a checkbox select for selecting multiple values from a predefined list. Multiple values will be combined using a logical “OR” operation. + +#### Supported features +Checkbox select supported features include [filter labels](#filter-labels), and optionally, [badges](#badge-count). + +
+![Badge in select menu toggle that shows the number of selected items.](./img/checkbox-select.svg) +
+ +**Filter labels** are used as a way for users to view all their selections when the menu of selections is collapsed. + +**Badges** can be used in the checkbox select toggle to indicate how many selections have been made, although they are not required. + +Although **typeahead** is not supported for checkbox selects, you can add a search input inside the menu, right above the items the user can select from. This will allow the user to filter down the list of options. + +
+![Search field placed within a menu.](./img/typeahead-search.svg) +
+ +## Variations for multiple attributes +There are multiple ways of combining variations for single attribute filters into multiple attribute filters, including [attribute-value filters](#attribute-value-filter), [filter groups](#filter-group), [toggle groups](#toggle-group) and [faceted filters](#faceted-filter). + +### Attribute-value filter +The attribute-value filter gives users the ability to specify an attribute-value pair for filtering a data set. + +
+![Attribute selector with text entry field.](./img/attribute-a.svg) +
+ +
+![Attribute selector with a single select menu.](./img/attribute-b.svg) +
+ +
+![Attribute selector with a checkbox select menu.](./img/attribute-c.svg) +
+ +
+![Attribute selector with a date picker.](./img/attribute-d.svg) +
+ +The following elements make up an attribute-value (textbox) filter. +1. **Attribute selector:** A select list that allows the user to select the attribute that they want to filter against. +2. **Value selector:** A value selector that is used to pass a value to the filter. The value selector can be any data input component. Common components used for value selection include: + + a. A **text entry field** for entering a value from the keyboard. Use when you will enter the value as unbounded data (e.g. a name). When the text entry field is a basic search input, the value will appear as a label automatically, and the search will start being validated. When the text entry field is a search input with a button, the value will appear as a label and the search will be validated when the user presses the Enter key on their keyboard or the arrow button. + + b. A **single select** for selecting a value from a predefined list. This will work the same as a stand alone single select, however since any selection in an attribute filter will result in a label, there is no need to have an “All” option as part of your menu, as users can reset their filters via the filter labels. + + c. A **checkbox select** for selecting multiple values from a predefined list. Multiple values will be combined using a logical "OR" operation. + + d. A **date picker** for selecting a date range. Use when the value you want to filter on is expressed as a date and/or time stamp. + +#### Behavior +To use an attribute-filter, the user must first select an _attribute_ to filter on using the left toggle, followed by choosing the specific _values_ to filter on using the right toggle. Whatever is selected in the attribute toggle will determine what is shown in the value toggle. + +The value toggles behave as described in the [variations for 1 attribute](#variations-for-1-attribute) section. The only difference for multiple attributes is that as users make filter selections using the attribute filter, each selection will **always** show up as a label underneath the filters. + +When using the attribute filter, a filter query is triggered whenever the user sets a new value. The following are triggers applicable to the variations of the attribute-value filter shown above. + +| Value selector | Trigger | +| ---------------| ------ | +| Search field | The user starts typing (for search input), presses the Enter key, or clicks the Search button (for input groups). | +| Select lists | The user selects or deselects an item in the list. | +| Date picker | The user selects a new date and/or time. | + +#### When to use +Use an attribute-value filter when users have multiple attributes to filter on. This filter should be used over a faceted filter when the attributes use different selection formats (for example, attribute A uses a single select, but attribute B uses a checkbox select). + +#### Supported features +Attribute-value filter features include [filter labels](#filter-labels), [badges](#badge-count), and [typeahead](#typeahead). + +**Filter labels** are strongly recommended for attribute filters as a way for users to view all their selections when the user switches between attribute filters and when the menu of selections is collapsed. + +**Badges** can be used in a checkbox select value selector toggle to indicate how many selections have been made. + +**typeahead** allows the user to narrow down their search and is supported for all value selection types except checkbox selects. Although typeahead is **not supported** for checkbox selects, you can add a search input inside the menu, above the items the user can select from. + +### Filter group +A filter group is a set of filters that appear side by side in a toolbar. This filter type uses the [select list](/components/menus/select) component. + +**Filter group with only single selects** + +
+![Filter group with 2 single select menus.](./img/filter-group-single.svg) +
+ +1. When an option is selected, it is reflected in the toggle. +1. The default selection should be “All _attribute-name_” to indicate that no filter has been applied. This option also allows users to clear whatever filter they can have applied. + + +**Filter group with multiple selection types** + +
+![Filter group with multiple, mixed selection types.](./img/filter-group-multiple.svg) +
+ +Filter group with single select, checkbox select, and date picker. When there are no selections, the toggle should contain the attribute name. + +When selections are made, the behavior will depend on the selection type: +1. **Single select:** The selection will appear in the toggle. +1. **Checkbox selects:** The attribute name will remain in the toggle, with the addition of a badge containing the number of filters selected. +1. **Date pickers:** The selection will appear in the toggle. + +In all cases, selections should appear as filter labels underneath the filters. + +#### When to use +Use a filter group when you only have a handful of attributes that you want to show. Only use this filter when space allows; otherwise consider using an attribute-value or faceted filter instead. + +#### Behavior +Filter queries are applied when the user selects or deselects an item in the list or selects a date/time range. If the filter group is only made up of single selects, the selected filters will be shown inside each filter’s toggle. If the filter group contains multiple selects, the selected filters will be shown as filter labels underneath the filters. Additionally, you can also choose to display the selected number of items in each filter as a badge in their toggle. A clear filter action to the right of the filters will remove all applied filters. + +#### Supported features +Filter groups support [filter labels](#filter-labels), [badges](#badge-count), and [typeahead](#typeahead). + +**Filter labels** are recommended for filter groups that have 1 or more checkbox selects. If the filter group only consists of single selects, there is no need to add filter labels as the count will always be one. + +**Badges** can be used in a checkbox select toggle to indicate how many selections have been made for that attribute filter. + +**typeahead** allows the user to narrow down their search and is supported for all value selection types except checkbox selects. Although typeahead is **not supported** for checkbox selects, you can add a search input inside the menu, above the items the user can select from. + +### Toggle group +A toggle group filter allows users to select from a set of predefined different elements to filter something on. This filter uses the [toggle group component](/components/toggle-group). + +
+![Toggle group for a chart visual.](./img/toggle-filter.svg) +
+ +#### When to use +Use a toggle group filter when you have few filter options that you want users to filter from, without hiding the options in a select list. A common usage for toggle groups is for filtering a chart view, to include or remove a data point from view. + +#### Behavior +Information will be shown to the user based on the toggles they select. If something is selected, it means the information is being filtered on. + +#### Supported features +Toggle groups do not use or support filter labels, badges, or typeahead. + +### Faceted filter +Faceted filtering is useful when items can be described by categories according to multiple dimensions or facets. This filter usually uses the [grouped checkbox select list](/components/menus/select#grouped-checkbox-input) component. + +
+![Menu with 2 named groups of selectable items.](./img/faceted-filter.svg) +
+ +The following elements can be used in a faceted (checkbox) filter: +1. **Facets:** Different categories containing filter values, such as _Status_ or _Vendor_. +2. **Values:** What users might filter on. Each category is made up of checkbox selects, where each category can have multiple options selected. Never include 2 selection types within the same faceted filter. + +
+![Filter labels that display items selected from filter groups.](./img/faceted-filter-collapsed.svg) +
+ +1. **Facets:** When the options menu is collapsed, selected values are displayed as labels in named groups, which use the name of the facet as the group label. + +**Note:** Consider adding an “Other” option to attribute lists where items can not fall under any of the specified values. + +#### When to use +Use a faceted filter when: +* The user is browsing a set of items without robust knowledge of what is in the set. +* The important characteristics of the items to be filtered are mostly traits with a small and discrete set of choices like color, status, availability, or distributor rather than arbitrary text or numeric values such as name, date created, or amount of available space. +* The facets to filter from are all checkbox select + +**Do not use** a faceted filter when the important characteristics of the items are mostly open-ended values and/or have a mix of single and multiple select. Additionally, if space is limited, consider using an [attribute-value](#attribute-value-filter) filter instead. + +#### Behavior +New filters are applied or removed as the user selects or deselects values using checkboxes. A badge count can optionally be added to the toggle to indicate the number of selections made in the filter. Selections will appear as filter labels underneath the filter. Note that there is an "AND" relationship between facets, and an "OR" relationship between values. + +#### Supported features +Faceted filters support [filter labels](#s), [badges](#badge-count), and [typeahead](#typeahead). + +## Filter validation +If your filter has limitations, you can present an error state on your filter toggle to communicate these limitations to users. Examples of instances where you can want to use filter validation include: +* In cases where free-form text input validation is needed +* When there is a limit on how many filters a user can apply at a time +* When there is a limit on how many options can be selected for 1 attribute + +When using error validation in a filter, include a tooltip on hover with an explanation of what went wrong. + +
+![Filter with a danger icon that has an informative tooltip.](./img/filter-error.svg) +
+ +## Layout considerations +Filters can be included in a [toolbar](/components/toolbar) and are usually left aligned. There can be more than 1 filter used in a single toolbar, and in some cases, custom filters can make up a full toolbar. Filters can also be used alone outside of a toolbar. + +## Mobile considerations +In responsive views, filters can be hidden within the filter icon. On click, the toolbar will expand to reveal the filter. If there are multiple filter elements, they will be collapsed into a single faceted filter. Read more about toolbars in mobile views in [the toolbar design guidelines](/components/toolbar/design-guidelines#the-toolbar-on-mobile). + +
+![Toolbar action required to open a filtering menu on mobile.](./img/mobile-before.svg) +
+ +
+![Mobile view of a toolbar after applying a filter.](./img/mobile-after.svg) +
+ +## Examples +**Filter group in data list toolbar** + +
+![Filters applied to a data list.](./img/filter-group-data-list.svg) +
+ +**Attribute filter in table toolbar** + +
+![Attribute filter option for a table.](./img/attribute-filter-table.svg) +
+ +## Content + +### Filters +Filter placeholder text in input fields should read “Filter by [attribute name].” Write all placeholder text in sentence case. + +**Examples:** _Filter by status_, _Filter by vendor_ + +### Clearing filters +The option to clear all filters will be displayed after the last filter label. It should read “Clear filters” in sentence case. When clicked, it should remove all applied filters and collapse the toolbar back into a single row. \ No newline at end of file diff --git a/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/attribute-a.svg b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/attribute-a.svg new file mode 100644 index 0000000000..4c92579a7e --- /dev/null +++ b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/attribute-a.svg @@ -0,0 +1,23 @@ + + + + + + + + + + + + + + + + + + + + + + + diff --git a/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/attribute-b.svg b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/attribute-b.svg new file mode 100644 index 0000000000..120ff35ad4 --- /dev/null +++ b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/attribute-b.svg @@ -0,0 +1,57 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/attribute-c.svg b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/attribute-c.svg new file mode 100644 index 0000000000..d2e94a252e --- /dev/null +++ b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/attribute-c.svg @@ -0,0 +1,73 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/attribute-d.svg b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/attribute-d.svg new file mode 100644 index 0000000000..e95047db5a --- /dev/null +++ b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/attribute-d.svg @@ -0,0 +1,36 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/attribute-filter-table.svg b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/attribute-filter-table.svg new file mode 100644 index 0000000000..2e2575a372 --- /dev/null +++ b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/attribute-filter-table.svg @@ -0,0 +1,101 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/badge-count.svg b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/badge-count.svg new file mode 100644 index 0000000000..4a33f91edf --- /dev/null +++ b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/badge-count.svg @@ -0,0 +1,36 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/checkbox-select-menus.svg b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/checkbox-select-menus.svg new file mode 100644 index 0000000000..f0a2469642 --- /dev/null +++ b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/checkbox-select-menus.svg @@ -0,0 +1,96 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/checkbox-select.svg b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/checkbox-select.svg new file mode 100644 index 0000000000..4b0d2d396a --- /dev/null +++ b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/checkbox-select.svg @@ -0,0 +1,70 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/faceted-filter-collapsed.svg b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/faceted-filter-collapsed.svg new file mode 100644 index 0000000000..d9a3fe468e --- /dev/null +++ b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/faceted-filter-collapsed.svg @@ -0,0 +1,49 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/faceted-filter.svg b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/faceted-filter.svg new file mode 100644 index 0000000000..015093a765 --- /dev/null +++ b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/faceted-filter.svg @@ -0,0 +1,93 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/filter-error.svg b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/filter-error.svg new file mode 100644 index 0000000000..1a3de0b756 --- /dev/null +++ b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/filter-error.svg @@ -0,0 +1,41 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/filter-group-data-list.svg b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/filter-group-data-list.svg new file mode 100644 index 0000000000..767a619693 --- /dev/null +++ b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/filter-group-data-list.svg @@ -0,0 +1,95 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/filter-group-multiple.svg b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/filter-group-multiple.svg new file mode 100644 index 0000000000..270621a0fd --- /dev/null +++ b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/filter-group-multiple.svg @@ -0,0 +1,104 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/filter-group-single.svg b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/filter-group-single.svg new file mode 100644 index 0000000000..92111efc08 --- /dev/null +++ b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/filter-group-single.svg @@ -0,0 +1,49 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/filter-label.svg b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/filter-label.svg new file mode 100644 index 0000000000..7771b81a2a --- /dev/null +++ b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/filter-label.svg @@ -0,0 +1,35 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/mobile-after.svg b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/mobile-after.svg new file mode 100644 index 0000000000..488abe8867 --- /dev/null +++ b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/mobile-after.svg @@ -0,0 +1,101 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/mobile-before.svg b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/mobile-before.svg new file mode 100644 index 0000000000..774a1b91e6 --- /dev/null +++ b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/mobile-before.svg @@ -0,0 +1,66 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/search-value.svg b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/search-value.svg new file mode 100644 index 0000000000..708fe89337 --- /dev/null +++ b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/search-value.svg @@ -0,0 +1,25 @@ + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/single-select-default.svg b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/single-select-default.svg new file mode 100644 index 0000000000..bf12803c86 --- /dev/null +++ b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/single-select-default.svg @@ -0,0 +1,38 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/single-select-selection-mode.svg b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/single-select-selection-mode.svg new file mode 100644 index 0000000000..26e4d43c6a --- /dev/null +++ b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/single-select-selection-mode.svg @@ -0,0 +1,38 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/text-entry-filters.svg b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/text-entry-filters.svg new file mode 100644 index 0000000000..ceefa7469a --- /dev/null +++ b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/text-entry-filters.svg @@ -0,0 +1,57 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/toggle-filter.svg b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/toggle-filter.svg new file mode 100644 index 0000000000..68e1d5b1de --- /dev/null +++ b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/toggle-filter.svg @@ -0,0 +1,64 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/typeahead-input.svg b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/typeahead-input.svg new file mode 100644 index 0000000000..f5e47714b9 --- /dev/null +++ b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/typeahead-input.svg @@ -0,0 +1,60 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/typeahead-search.svg b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/typeahead-search.svg new file mode 100644 index 0000000000..1fa1f39ed5 --- /dev/null +++ b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/typeahead-search.svg @@ -0,0 +1,75 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/typeahead.svg b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/typeahead.svg new file mode 100644 index 0000000000..1588255cbd --- /dev/null +++ b/packages/site/src/content/design-guidelines/usage-and-behavior/filters/img/typeahead.svg @@ -0,0 +1,61 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/packages/site/src/content/design-guidelines/usage-and-behavior/usage-and-behavior.mdx b/packages/site/src/content/design-guidelines/usage-and-behavior/usage-and-behavior.mdx new file mode 100644 index 0000000000..a0936eaabd --- /dev/null +++ b/packages/site/src/content/design-guidelines/usage-and-behavior/usage-and-behavior.mdx @@ -0,0 +1,139 @@ +--- +id: Usage and behavior +section: design-foundations +--- + +# PatternFly component usage and behavior guidelines + +As you design with PatternFly, you might encounter common use cases where multiple components could be used. These guidelines outline which component to use in these situations and shares where to find more detailed usage guidelines. + +## Displaying structured data +Structured data includes any information that is stored in a database or similar regular data structure. Most commonly, structure data is displayed in either a list or a table, where rows correspond to records in the database. To display this type of content, we recommend using the **[data list](/components/data-list)** and the **[table](/components/table)** components. + +- Tables are built from a standard tabular structure of rows and columns. + +- Data lists support any valid HTML layout inside of a row, which enables more formatting flexibility. + +Your use case dictates which of these components you should use: + +| **Use case** | **Recommended component** | +|----------| ---------- | +| You want to display data in a grid with column headings. | Table | +| Data does not easily fit into a grid or you want multiple lines of data in a row. | Data list | +| You want to display non-text information like images or charts. | Data list or table

**Note:** Tables support graphics within cells, but this approach is only recommended for use with small graphics. | +| All rows don’t have the same format. | Data list | + +## Providing contextual help on a page +Contextual help includes any on-screen elements intended to guide the user towards additional information that will help them complete a task. To display this type of content, we recommend using the **[tooltip](/components/tooltip)**, **[popover](/components/popover)**, and **[hint](/components/hint)** components. + +- Tooltips are shown when users hover over an element. + +- Popovers can be shown on hover or click, can contain any HTML content, and are persistent. + +- Hints are static elements that appear inline with other content on a page. + +Your use case dictates which of these components you should use: + +| **Use case** | **Recommended component** | +|------------------------ | -----------| +| You want to provide a short (no more than 1-2 lines) explanation of new or unfamiliar UI elements as a simple text string that is only shown “on-demand.” |Tooltip| +| You want to include formatted text and/or interactive elements in your message body. | Hint or popover | +| You want the information to persist until the user dismisses it. | Hint or popover | +|You want the information to be announced by a screen reader whenever the user tabs to an element.| Hint, popover, or tooltip

**Note:** By default, popovers are only triggered when the user clicks on an element. Therefore screen readers will not read popover text when tabbing through an interface. If a popover is triggered on hover (optional behavior), it will behave like a tooltip and its content will be announced whenever a keyboard user tabs to the trigger element. | +|You want to present additional information that might not be necessary or relevant to all users.| Hint or popover

**Note:** Hints can be used to convey information to advanced users (such as “pro-tips”). However, since a hint adds static content to a page, you should consider whether it’s important for this information to be shown at all times.| + +## Progressive disclosure +Progressive disclosure is the practice of showing and hiding information as needed, in order to simplify a user interface. To progressively disclose content, we recommend using the **[accordion](/components/accordion)**, **[expandable sections](/components/expandable-section)**, and **[expandable field groups](/components/forms/form/#field-groups)**. + +- Accordions allow content to be placed in stackable, expandable containers so that content can be hidden from view to simplify presentation and reduce the need for scrolling. + +- Expandable sections allow designers to hide a single block of content or settings behind a show/hide link. + +- Expandable field groups allow designers to group form elements into expandable containers. + +Your use case dictates which of these components you should use: + +| **Use case** | **Recommended component** | +| ------------------------ | ----------- | +| You want to group a list of actions, links, or other data into expandable groups. | Accordion | +|You want to hide advanced or seldomly used options within a form.| Expandable section or field group | +|You want to give the user the ability to show or hide chunks of information on a long scrolling page.| Expandable section | + +## Inputting data within forms +Data input controls allow users to input information into a form. Input may be bound or unbound. Bound input controls only allow users to input data within a defined range, such as the **[slider](/components/slider)** and **[number input](/components/number-input)** components. Unbound controls do not enforce constraints, such as the **[text input](/components/forms/text-input)** and **[text area](/components/forms/text-area)** components. + +Your use case dictates which of these components you should use: + +| **Use case** | **Recommended component** | +|------------------------ | -----------| +|You want to enter text from the keyboard. Possible values are alpha-numeric, unconstrained, or dependent on context.| Text area or text input

**Note:** If data will always be constrained to a single line, use a text input. Use a text area component for multi-line input.| +|You want to constrain the input of numeric data to a specified range.|Number input, slider, text input, or text area

**Note:** You can use a standard text input for this use case and validate the entered value, but using a number input or slider will be a more direct way to constrain the values that a user can input. | +|You want to optimize numeric data entry for direct manipulation by touch or using the mouse over the keyboard.|Number input or slider| +|It’s useful for users to visualize where numeric input falls within the range of possible values.| Slider | + +## Selecting between options on a form +There are a few components that you can use to allow users to select form options. Depending on the nature of options being presented, we recommend using the **[checkbox](/components/forms/checkbox)**, **[radio](/components/forms/radio)**, or **[switch](/components/switch)** components. + +- Checkboxes allow users to select one or more items from a list of options. + +- Radio buttons allow users to select from a set of mutually exclusive options. + +- Switches indicate the state of a binary setting or object (such as on/off, enabled/disabled). + +Your use case dictates which of these components you should use: + +| **Use case** | **Recommended component** | +|------------------------ | -----------| +|The user wants to select one or more items from a list of items. | Checkbox or switch

**Note:** Switches are sometimes used in place of checkboxes because they provide a larger touch target than a checkbox, which improves the mobile experience. | +| The user wants to select from a set of mutually exclusive options.| Radio | +|The user wants to enable an option or feature.| Checkbox, radio, or switch

**Note:** Checkboxes are often used to enable or disable software features, because they allow you to concisely display on/off settings.

**Note:** You can use 2 radio buttons to allow users to choose between options like on/off or enabled/disabled, however this approach uses more space and is only recommended when it’s important to make both labeled options visible at the same time.| + +## Displaying progress +It’s important to display progress for action that will take more than a few seconds to complete. Use the **[progress](/components/progress)** component to show users the percentage of completion for a process or task. Use the **[spinner](/components/spinner)** and **[skeleton](/components/skeleton)** components to just simply indicate activity while the user is waiting for an action to complete. + +Your use case dictates which of these components you should use: + +| **Use case** | **Recommended component** | +|------------------------ | -----------| +| The user is waiting for a process to complete, but the time left until completion is not known.| Spinner | +|The user is waiting for a process to complete, but the time left until completion is known.| Progress or spinner

**Note:** A progress component is the preferred recommendation when it is possible to estimate the time to completion or the percentage of the task that is done.| +| The user is progressing through a step-by-step task and you want to reflect where they are in the process.| Progress | +|The user is waiting for a page to load.| Progress, skeleton, or spinner

**Note:** Progress bars are not typically used during page loading, but could be used with the skeleton component if you want to provide the user with more information about time to completion.

**Note:** Spinners may be used to provide feedback on page loading when the details of the data are not known. | + +## Displaying object details in context +It is often necessary to display more details about an object listed in a summary view, such as a list or a table. This can be accomplished by drilling-down into a new page or presenting contextual details on the same page. To take these approaches, we recommend using the **[data list](/components/data-list)**, **[drawer](/components/drawer)**, **[table](/components/table)**, and **[popovers](/components/popover)** components. + +- Data lists and tables support expandable rows for displaying object details directly in the list or table. + +- Drawers can be used to create a side-by-side primary-detail view. + +- Popovers can be used to display details about an object in a list or table. + +Your use case dictates which of these components you should use: + +| **Use case** | **Recommended component** | +|------------------------ | -----------| +|You want to view details of multiple objects at the same time for comparison.| Data list or expandable table row | +|Your detailed data is best presented in a horizontal format.| Data list, drawer, expandable table row, or popover

**Note:** Drawers can be attached to either the left, right, or bottom edge of the parent container. To present horizontal data, use a bottom/horizontal drawer to create a top-bottom primary-detail view.| +|Your detailed data is best presented in a vertical format.| Drawer or popover| +|You have only a small amount of detailed data to show.|Data list, drawer, expandable table row, or popover

**Note:** Row expansions and drawers can accommodate any amount of information. Showing a small amount of data within a row expansion or drawer may waste space because each presentation type will consume the full width or height of its parent container. Popovers will adjust to the size and shape of their contents.| +|You don’t want to cover other information while displaying details.|Data list, drawer, or expandable table row

**Note:** Both inline and overlay drawers are available. If you don’t want to cover content on a page, we recommend the [inline drawer](/components/drawer#basic-inline) variation. | + +## Dropdown menus for actions and selections +To allow users to select between items in a menu, we recommend using the **[select](/components/menus/select)**, **[options](/components/menus/options-menu)**, or **[dropdown](/components/menus/dropdown)** menu components. + +- Select menus allow users to select one or more values from a list. + +- Options menus are similar to a select, but are more appropriate when users make selections from optional settings. + +- Dropdown menus allow you to expose a list of possible actions. + +Your use case dictates which of these components you should use: + +| **Use case** | **Recommended component** | +|------------------------ | -----------| +|You want to select a value or multiple values from a list.| Select | +|You want to select filter terms from a list.| Select | +|You want to make the selected value visible when the menu is closed.| Select | +|You want to select options from one or more lists (sorting options, for example).| Options menu | +|You want to expose a list of commands or actions in a limited space.| Dropdown | diff --git a/packages/site/src/content/developer-resources/PF-a11y.png b/packages/site/src/content/developer-resources/PF-a11y.png new file mode 100644 index 0000000000..4c786f7a2f Binary files /dev/null and b/packages/site/src/content/developer-resources/PF-a11y.png differ diff --git a/packages/site/src/content/developer-resources/Popover.png b/packages/site/src/content/developer-resources/Popover.png new file mode 100644 index 0000000000..3d87a9f1a2 Binary files /dev/null and b/packages/site/src/content/developer-resources/Popover.png differ diff --git a/packages/site/src/content/developer-resources/a11y-scores.jsx b/packages/site/src/content/developer-resources/a11y-scores.jsx new file mode 100644 index 0000000000..bb60cc9950 --- /dev/null +++ b/packages/site/src/content/developer-resources/a11y-scores.jsx @@ -0,0 +1,279 @@ +export const a11yScores = [ + { + 'November 11, 2024': [ + { + criteria: + 'Accessibility report generated using axe-core based tooling.', + status: '✅', + notes: ( + <> + + Q2 2024 report (November 11, 2024) + +

133 violations found

+ + ), + }, + { + criteria: 'Manual keyboard and screen reader testing conducted.', + status: '--', + notes: '', + }, + { + criteria: `Accessibility violations in product itemized and prioritized. Notes should indicate how violations + were identified - i.e. via generated report and/or manual testing.`, + status: '✅', + notes: ( + <> + + patternfly/patternfly-org issue #4374 + +

Errors identified via generated report.

+ + ), + }, + { + criteria: + 'Critical and major accessibility violations identified in item #3 resolved (%).', + status: '--', + notes:

133 violations remaining

, + }, + { + criteria: `Automated accessibility checks added to pull request or equivalent code acceptance criteria.`, + status: '--', + notes: '', + }, + { + criteria: + 'Manual keyboard and screen reader accessibility checks added to pull request or equivalent code acceptance criteria.', + status: '✅', + notes: `Accessibility devs identified and tagged on relevant PRs to manually review screen reader and keyboard interactions`, + }, + { + criteria: ( + <> + CI/CD Process established to track accessibility + violations/regressions. CI/CD process could be wired up to use{' '} + https://www.deque.com/axe/{' '} + or the patternfly-a11y tool (also built using axe) + + ), + status: '--', + notes: ( + <> + Report{' '} + + configuration + {' '} + created, needs to be hooked into CI/CD + + ), + }, + { + criteria: `Website built with PatternFly React components. Could note alternate design systems/component + libraries along with reference to their accessibility docs.`, + status: '✅', + notes: '', + }, + { + criteria: 'PatternFly React is up to date with the latest release', + status: '✅', + notes: `Current versions: + "@patternfly/patternfly": "6.0.0", + "@patternfly/react-core": "6.0.0"`, + }, + { + criteria: 'User testing conducted (Extra credit 🌟)', + status: '--', + notes: '', + }, + ], + }, + { + 'April 23, 2024': [ + { + criteria: + 'Accessibility report generated using axe-core based tooling.', + status: '✅', + notes: ( + <> + + Q2 2024 report (April 23, 2024) + +

24 violations found

+ + ), + }, + { + criteria: 'Manual keyboard and screen reader testing conducted.', + status: '--', + notes: '', + }, + { + criteria: `Accessibility violations in product itemized and prioritized. Notes should indicate how violations + were identified - i.e. via generated report and/or manual testing.`, + status: '✅', + notes: ( + <> + + patternfly/patternfly-org issue #3979 + +

Errors identified via generated report.

+ + ), + }, + { + criteria: + 'Critical and major accessibility violations identified in item #3 resolved (%).', + status: '--', + notes:

24 violations remaining

, + }, + { + criteria: `Automated accessibility checks added to pull request or equivalent code acceptance criteria.`, + status: '--', + notes: '', + }, + { + criteria: + 'Manual keyboard and screen reader accessibility checks added to pull request or equivalent code acceptance criteria.', + status: '✅', + notes: `Accessibility devs identified and tagged on relevant PRs to manually review screen reader and keyboard interactions`, + }, + { + criteria: ( + <> + CI/CD Process established to track accessibility + violations/regressions. CI/CD process could be wired up to use{' '} + https://www.deque.com/axe/{' '} + or the patternfly-a11y tool (also built using axe) + + ), + status: '--', + notes: ( + <> + Report{' '} + + configuration + {' '} + created, needs to be hooked into CI/CD + + ), + }, + { + criteria: `Website built with PatternFly React components. Could note alternate design systems/component + libraries along with reference to their accessibility docs.`, + status: '✅', + notes: '', + }, + { + criteria: 'PatternFly React is up to date with the latest release', + status: '✅', + notes: `Current versions: + "@patternfly/patternfly": "5.3.0", + "@patternfly/react-core": "5.3.0"`, + }, + { + criteria: 'User testing conducted (Extra credit 🌟)', + status: '--', + notes: '', + }, + ], + }, + { + 'Nov 21, 2022': [ + { + criteria: + 'Preliminary accessibility report generated using axe-core based tooling.', + status: '✅', + notes: ( + <> + + Initial report (May 16th, 2022) + +

1066 violations found

+ + ), + }, + { + criteria: 'Manual keyboard and screen reader testing conducted.', + status: '--', + notes: '', + }, + { + criteria: `Accessibility violations in product itemized and prioritized. Notes should indicate how violations + were identified - i.e. via generated report and/or manual testing.`, + status: '✅', + notes: ( + <> + + patternfly/patternfly-org issue #2920 + +

Will be updated once keyboard/screen reader testing conducted

+ + ), + }, + { + criteria: + 'Critical and major accessibility violations identified in item #3 resolved (%).', + status: '96%', + notes: ( + <> + + Latest generated report (Nov 21, 2022) + +

44 violations remaining

+ + ), + }, + { + criteria: `Automated accessibility checks added to pull request or equivalent code acceptance criteria.`, + status: '--', + notes: '', + }, + { + criteria: + 'Manual keyboard and screen reader accessibility checks added to pull request or equivalent code acceptance criteria.', + status: '✅', + notes: `Accessibility devs identified and tagged on relevant PRs to manually review screen reader and keyboard interactions`, + }, + { + criteria: ( + <> + CI/CD Process established to track accessibility + violations/regressions. CI/CD process could be wired up to use{' '} + https://www.deque.com/axe/{' '} + or the patternfly-a11y tool (also built using axe) + + ), + status: '--', + notes: ( + <> + Report{' '} + + configuration + {' '} + created, needs to be hooked into CI/CD + + ), + }, + { + criteria: `Website built with PatternFly React components. Could note alternate design systems/component + libraries along with reference to their accessibility docs.`, + status: '✅', + notes: '', + }, + { + criteria: 'PatternFly React is up to date with the latest release', + status: '✅', + notes: `Current versions: + "@patternfly/patternfly": ">=4.185.1", + "@patternfly/react-core": ">=4.202.16"`, + }, + { + criteria: 'User testing conducted (Extra credit 🌟)', + status: '--', + notes: '', + }, + ], + }, +]; diff --git a/packages/site/src/content/developer-resources/about-accessibility.mdx b/packages/site/src/content/developer-resources/about-accessibility.mdx new file mode 100644 index 0000000000..eccf5a4565 --- /dev/null +++ b/packages/site/src/content/developer-resources/about-accessibility.mdx @@ -0,0 +1,95 @@ +--- +id: About accessibility +section: accessibility +--- + +# Accessibility fundamentals + +Accessibility is a foundation of PatternFly, so if you contribute to PatternFly or use it for your products you should first familiarize yourself with our accessibility guidelines and recommendations. + +No user should feel left behind when using your product. The goal of accessible design is to remove barriers and create inclusive product experiences that work for everyone, regardless of ability. This is best achieved when accessibility is considered early in the design and development process, but it's never too late to start prioritizing accessibility. + +There’s always room to improve accessibility. That’s why our guidelines will continually evolve. Your feedback can help support PatternFly's accessibility, so we welcome you to contribute to our documentation or [get involved in our GitHub discussions](https://github.com/orgs/patternfly/discussions). + +## Assistive technologies + +A core consideration for accessibility practices is the assistive technologies that people may use to access your product. While there are many kinds of assistive technologies, PatternFly focuses primarily on accommodating users of keyboards and screen readers. + +### Keyboard +Some users can’t use a mouse and rely on other methods of navigation instead, like a keyboard. A keyboard allows users to navigate through UI elements in the order that they appear on the page, typically using the Tab key. Keyboard users should be able to do anything that mouse users can, including viewing text that is shown upon hover or in popups. + +### Screen readers +When a user has impaired vision (temporary or permanent) that prevents them from viewing a screen, they can use a screen reader that reads visible and non-visible content aloud. Non-visible content includes hidden text, like tooltips, and alternative text (alt text) for icons, images, and links. + +## Understanding users’ needs +Great user experiences don’t just happen. They’re designed, tested, and refined with users in mind. To develop inclusive products, it’s important to understand the varying needs of all users and consider the assistive tools and methods that they use. + +This section provides information to help you better understand and address some of the needs of [users with diverse abilities](https://www.a11yproject.com/posts/accessibility-is-blind-people/). It is important to note that some users might fall into multiple groups, and some might use tools created for a different group. + +### Motor control +Users with reduced motor control often use a keyboard or computer mouse to access content. Some users may also have difficulty keeping a mouse steady when trying to interact with content. + +To design for users with reduced motor control, remember that: + +- Users who rely on a keyboard need elements that are keyboard accessible and highly visible when in focus. +- Users who rely on a mouse or touch need target areas that are large enough to be easily clicked and selected. + +### Vision + +#### No vision +Users with no vision rely on screen readers to access web sites and applications. These users often navigate a page by observing specific elements, like headers, links, or form elements. + +To design for users with no vision: + +- Use [semantic elements](www.w3schools.com/html/html5_semantic_elements.asp). +- Write labels that are meaningful when pulled out of context. + +#### Low vision +Users with low vision can have different needs depending on the nature of their visual impairment, such as difficulty with color differentiation, blurriness, or lack of vision in central or peripheral areas. + +To design for users with low vision: + +- Interfaces should not rely on color alone to communicate information. +- Palettes must have sufficient contrast. +- Layouts should be responsive to font size increases. + +### Cognitive processing +Users who have difficulty processing information benefit from well-written content. + +To design for users with cognitive processing issues: + +- Write content that is clear, concise, and easy to scan. +- Consider visual hierarchy and chunk content into short, related sections. +- Avoid long paragraphs. + +### Accessibility spectrum + +While there are a few main accessibility needs, it is not an exhaustive list. Often the “Persona Spectrum”, coined by Microsoft [(Download the Inclusive Guidebook as a PDF)](https://download.microsoft.com/download/b/0/d/b0d4bf87-09ce-4417-8f28-d60703d672ed/inclusive_toolkit_manual_final.pdf), can be used to understand related mismatches and motivations across a spectrum of permanent, temporary, and situational scenarios. + +While accessibility tends to focus on those with permanent disabilities, everyone benefits from accessible products: + +- Accessible content supports better comprehension across language fluency and literacy levels. +- Alternative text (alt text) makes images accessible to users with low bandwidth connections or older technologies that can’t load the images. +- Closed captioning benefits those in crowded areas, those learning how to read, and those learning a new language. + +Accessibility takes **all users** into account. + + +An accessibility spectrum showing examples of the situational, temporary, and permanent situations for different impairments. + +## Experience parity +We believe that all abilities should be treated equally. There should be parity in the experience of all users—one user group shouldn't be prioritized over the other. +To help you achieve this, consider these guidelines: + +- Content should be optimized for all input types: touch, mouse, and keyboard. + - Don’t optimize the experience for one input type at the expense of another. + - Contents that are mouse-accessible should also be accessible using touch or a keyboard. + - Don’t show interactive elements on hover. + - Interactive elements that display in a pop-up must also display on click, touch, or enter-key events. + +- Screen reader content should match visibly rendered content (refer to the [first note for `aria-hidden` state](https://www.w3.org/TR/wai-aria/#aria-hidden)). + +- There should be parity between hover and focus events. Any information that’s available on hover for the mouse user should be available on keyboard focus. + - Make content that appears on hover available to a screen reader by using `aria-describedby` (refer to [Tooltips & Toggletips example from Inclusive Components](https://inclusive-components.design/tooltips-toggletips/)). + +When building accessible user experiences, solving for one can extend to many. Humans are diverse and unique, and designing for accessibility takes that into consideration to create truly inclusive products. diff --git a/packages/site/src/content/developer-resources/accessibility-datalist.jsx b/packages/site/src/content/developer-resources/accessibility-datalist.jsx new file mode 100644 index 0000000000..e1fb4da68a --- /dev/null +++ b/packages/site/src/content/developer-resources/accessibility-datalist.jsx @@ -0,0 +1,328 @@ +import React from 'react'; +import { + DataList, + DataListItem, + DataListItemRow, + DataListCell, + DataListToggle, + DataListContent, + DataListItemCells, +} from '@patternfly/react-core'; + +export class AccessibilityDatalist extends React.Component { + constructor(props) { + super(props); + this.state = { + expanded: [], + isOpen1: false, + isOpen2: false, + isOpen3: false, + isOpen4: false, + isOpen5: false, + isOpen6: false, + allExpanded: false + }; + + this.onToggleAll = () => { + this.setState( + { + allExpanded: !this.state.allExpanded + }, + () => { + if (this.state.allExpanded) { + this.setState({ + expanded: ['ex-toggle1', 'ex-toggle2', 'ex-toggle3', 'ex-toggle4', 'ex-toggle5', 'ex-toggle6'] + }); + } else { + this.setState({ + expanded: [] + }); + } + } + ); + }; + this.onSelect1 = event => { + this.setState(prevState => ({ + isOpen1: !prevState.isOpen1 + })); + }; + + this.onSelect2 = event => { + this.setState(prevState => ({ + isOpen2: !prevState.isOpen2 + })); + }; + + this.onSelect3 = event => { + this.setState(prevState => ({ + isOpen3: !prevState.isOpen3 + })); + }; + + this.onSelect4 = event => { + this.setState(prevState => ({ + isOpen4: !prevState.isOpen4 + })); + }; + + this.onSelect5 = event => { + this.setState(prevState => ({ + isOpen5: !prevState.isOpen5 + })); + }; + + this.onSelect6 = event => { + this.setState(prevState => ({ + isOpen6: !prevState.isOpen6 + })); + }; + } + + render() { + const toggle = id => { + const expanded = this.state.expanded; + const index = expanded.indexOf(id); + const newExpanded = + index >= 0 ? [...expanded.slice(0, index), ...expanded.slice(index + 1, expanded.length)] : [...expanded, id]; + this.setState(() => ({ expanded: newExpanded })); + }; + return ( + + + + + toggle('ex-toggle1')} + isExpanded={this.state.expanded.includes('ex-toggle1')} + id="ex-toggle1" + aria-controls="ex-expand1" + /> + + , + +
Skip to main links
+
, + + WCAG 2.4.1 + , + + development + + ]} + /> +
+ +

+ A mechanism should be available to bypass blocks of content that are repeated on multiple web pages. +
+
+ When keyboard-only users interact with your site, they use the tab key to jump from link to link. If your UI has many links in your page header or in a menu, they must tab through those every time they come to a new page just to get to the main content. Providing a "skip to main content" link allows them to easily bypass this hassle. +

+ +
+
+ + + toggle('ex-toggle2')} + isExpanded={this.state.expanded.includes('ex-toggle2')} + id="ex-toggle2" + aria-controls="ex-expand2" + /> + + , + +
Page titles
+
, + + WCAG 2.4.2 + , + + development + + ]} + /> +
+ +

+ Use descriptive titles to help users find content, orient themselves within it, and navigate through it. +
+
+ Users can more quickly identify the content they need when accurate, descriptive titles appear in site maps or lists of search results. The title of each web page should: +
+ - Identify the subject of the web page. +
+ - Make sense when read out of context. For example, when read by a screen reader, in a site map, or in a list of search results. +
+ - Be concise. +

+
+
+ + + toggle('ex-toggle3')} + isExpanded={this.state.expanded.includes('ex-toggle3')} + id="ex-toggle3" + aria-controls="ex-expand3" + /> + + , + +
Links
+
, + + WCAG 2.4.4 + , + + design, development + + ]} + /> +
+ +

+ If more than one link has the same label, it should also have the same URL. +
+
+ Screen reader users can access the list of links that are on a page, which pulls the links out of context. If you have links with different URLs but the same label, then add additional text to provide context to screen reader users. +

+
+
+ + + toggle('ex-toggle4')} + isExpanded={this.state.expanded.includes('ex-toggle4')} + id="ex-toggle4" + aria-controls="ex-expand4" + /> + + , + +
Landmarks
+
, + + ARIA11 + , + + design, development + + ]} + /> +
+ +

+ Use landmark roles to clearly identify regions that communicate page structure. +
+
+ Landmark roles programmatically identify sections of a page. If more than one landmark role occurs in the page, use aria-label to differentiate the landmark elements. + Landmarks help assistive-technology users orient themselves to a page and help them navigate easily to various page sections. Whenever a landmark role is used more than once, provide a name using aria-label or aria-labelledby to provide context for that landmark. ( ARIA6, ARIA16) +
+
+ Note: While toolbar is not a landmark role, the same rule applies. +

+
+
+ + + toggle('ex-toggle5')} + isExpanded={this.state.expanded.includes('ex-toggle5')} + id="ex-toggle5" + aria-controls="ex-expand" + /> + + , + +
Headings
+
, + + WCAG 2.4.10 + , + + design, development + + ]} + /> +
+ +

+ Heading text should be descriptive. +
+
+ Appropriate heading levels should be used to communicate the outline and structure of the page. For example, a common practice is to use a single h1 for the primary headline or logo on a page, h2s to designate major sections, and h3's for supporting subsections. +

+
+
+ + + toggle('ex-toggle6')} + isExpanded={this.state.expanded.includes('ex-toggle6')} + id="ex-toggle6" + aria-controls="ex-expand" + /> + + , + +
Contents
+
, + + , + + design + + ]} + /> +
+ +

+ Content should be meaningful, clear, and concise. +
+
+ Use simple language and formatting, as appropriate for the context. +

+
+
+
+
+ ); + } +} diff --git a/packages/site/src/content/developer-resources/accessibility-design.mdx b/packages/site/src/content/developer-resources/accessibility-design.mdx new file mode 100644 index 0000000000..c9bf515783 --- /dev/null +++ b/packages/site/src/content/developer-resources/accessibility-design.mdx @@ -0,0 +1,47 @@ +--- +id: Design for accessibility +section: accessibility +--- + +import { Card, CardBody, Grid, GridItem } from '@patternfly/react-core'; + +As described in our [accessibility guidelines](/accessibility/about-accessibility), users may interact with your product through a variety of assistive technologies. In addition to [developing for accessibility](/accessibility/develop-for-accessibility), you must also incorporate it into your product's visual design. + +## Color and contrast + +Color and contrast go hand-in-hand for visual design accessibility. + +For example, you should consider contrast when using colors commonly affected by color perception deficiency (such as those described in ["Overview of Low Vision" by W3C](https://www.w3.org/WAI/GL/low-vision-a11y-tf/wiki/Overview_of_Low_Vision#Color_Perception)). Different colors in a UI should be distinguishable for users across the color perception deficiency spectrum, typically by ensuring that each color has a different contrast weight. + +Designing with contrast in mind also benefits users with light sensitivity. + +PatternFly components use [our color palettes](/design-foundations/colors) to pass color contrast tests. As long as you follow our recommendations, any UI built with PatternFly components should have proper contrast between colors, making them distinguishable for users with different types of color perception and light sensitivity. + +It's important not to solely rely on color for conveying information. Even though PatternFly components pass color contrast tests, they also use icons to further help with identification, which can be especially helpful for users with a form of color blindness. + +Two sets of alert components being compared, one displayed as normal and the other displayed with red-green color blindness emulated. + +If you go beyond our recommendations to combine PatternFly colors in other ways, please be sure to check your color contrast with a contrast checker. When you alter the colors and/or icons used in PatternFly components, know that they may no longer be accessible for all users. + +A set of alert components displayed with red-green color blindness emulated. These alert components are not clear or distinguishable, because they use poor color contrast and irrelevant icons. + +## Content + +The text in your UI should also be accessible to users with low vision. For example, links should be descriptive and concise, essential content should not be hidden in the UI, and text should scale appropriately as the UI window is resized or magnified. + +To help simplify and strengthen the way that users process content, it is important to carefully consider your text size, font, letter spacing, margins, and spacing. PatternFly supports accessibility in these areas through our [typography](/design-foundations/typography) and [spacing](/design-foundations/spacers) guidelines. + +## Understanding low vision + +In addition to following the previous recommendations, it is helpful to develop an understanding of low-vision users, so that their needs are a key concern as you design. + +**Low vision** refers to any visual impairment that impedes a person’s ability to perform everyday tasks, which cannot be corrected with glasses, contacts, medicine, or surgery. + +There are 4 types of limitations as a result of low vision. + +1. **Visual acuity**: A measure of a person's visual sharpness, with 20/20 being the standard. +1. **Field of vision**: The area of vision that people can see clearly when their eyes are in a fixed position. Some users have a restricted field of vision, such as central or peripheral field loss. +1. **Color perception**: How people see colors. Some of your users may have deficiencies in color perception that affects their ability to see certain colors. This is commonly called "color blindness", but many people with color perception deficiencies can still see most colors. +1. **Contrast and light sensitivity**: The way that people perceive luminance (the contrast of foreground and background). + +We do our best to make PatternFly accessible for low-vision users by default, but it is important that you consciously design with these needs in mind to ensure that your final design has proper color, contrast, and content accessibility. diff --git a/packages/site/src/content/developer-resources/accessibility-development.mdx b/packages/site/src/content/developer-resources/accessibility-development.mdx new file mode 100644 index 0000000000..28d48dcd7d --- /dev/null +++ b/packages/site/src/content/developer-resources/accessibility-development.mdx @@ -0,0 +1,151 @@ +--- +id: Develop for accessibility +section: accessibility +--- +import { AccessibilityDatalist } from './accessibility-datalist'; + +PatternFly provides accessible components, but **we can't guarantee that your products will be accessible**. In order to ensure that your product is accessible, you will need to take additional steps during development, as described in the following guidelines and techniques. + +## Prioritizing accessibility during development + +As you develop your product, you should keep accessibility top of mind, by asking yourself a few questions: + +- **Can all users discover and perceive elements?**: If you can see or click on an element, then all users should be able to locate and navigate to it. This should include those that use a keyboard or other assistive technology, such as a screen reader. + +- **Can all users interact with elements?**: It should be easy for users to use an element once it's in focus. They should be able to interact with elements and initiate actions via keyboard (like pressing Enter to initiate a button action) and screen readers. + +- **Can all users understand elements?**: It should be clear what actions elements can perform. For example, buttons should have visible text that would be clear out of context of the page. If not, it should have an `aria-label` or accessible name. + +## Development techniques + +These are some of the items outside the scope of PatternFly that you should prioritize to ensure accessibility: + + + +### UI element accessibility techniques + +The [WCAG 2.0 techniques](https://www.w3.org/TR/WCAG20-TECHS/Overview.html#contents) provide examples on how to meet accessibility guidelines. The following techniques are standard across PatternFly for specific patterns. + +#### Labeling with ARIA + +For sighted users, the context and visual appearance of an element can help users understand its purpose. But this isn’t always the case. For example, the X, often used in the top-right corner of pop-ups to indicate the control for closing, might not be clear to those using assistive technology: + +Popover example of close button + +ARIA supplements HTML so that common application interactions and features can be passed to assistive technologies when there is not a native mechanism. This is typically done by including an `aria-label` that provides descriptive context to assistive technologies. **Only use labels when they are necessary to make an element accessible.** ARIA is meant to add context when there *isn’t* visible text, not to override or reiterate what’s already there. Make sure that your labels are useful and not redundant. + +Note that ARIA can only affect the semantics of an element; it has no effect on its behavior. For example, while you can make an element hidden to screen readers with `aria-hidden=”true”`, that does not hide the element from focus. + +#### Form fields + +Use [explicit linking](https://www.w3.org/TR/WCAG20-TECHS/H44.html) between `label` and form input elements (such as `input`, `textarea`, or `select`) when both are present. [This "H44" guidelines](//www.w3.org/TR/WCAG20-TECHS/H44.html) provides an accessible name to screen readers and makes the label clickable to increase the overall clickable area of the form element. + +When a `label` element cannot accompany a form input element, provide one using using `aria-label` or `aria-labelledby`, as outline by the ["ARIA14" guidelines](//www.w3.org/TR/WCAG20-TECHS/ARIA14.html). + +In a single-field form, the submit button label can serve as the field label for sighted users, [following the "G167" guidelines](//www.w3.org/TR/WCAG20-TECHS/general.html#G167). For assistive devices, use `aria-labelledby`. + +#### Icons + +To render icons as something that assistive devices can ignore, pass `aria-hidden='true'` to all icons, either to the icon element or a parent element of the icon. + +##### **Decorative and semantic icons** + +There are 2 main categories of accessible icons: +- **Decorative icons**, which can be removed without affecting the page's information. +- **Semantic icons**, which provide information that isn't present on the page. For example, these can represent status, indicate an alert message type, or replace text as button labels. The meaning of a semantic icon must be provided in alternative ways to the user. Additionally, you should follow these guidelines: + - Add a label for the icon in tooltip text that displays on hover and focus. + - For interactive elements (like `` and ` + ``` + +##### **Non-interactive icons** + +For **non-interactive icons**, include `.pf-v5-screen-reader` text near the icon. Depending on the component, this text might not be a direct sibling to the icon element. + +For example, in the alert component, the icon label text is adjacent to the message: + + ``` + { +
+ +
+

+ {{#> screen-reader}}Success:{{/screen-reader}} Success alert title +

+
+
+ } + ``` + +#### Images + +All images should have alt text so that assistive technology can provide an image description. When an image contains words that are important to understanding the content, the alt text should include those words. This allows the alt text to communicate the same message as the image itself. + +**Note**: Alt text does not necessarily describe the visual characteristics of the image itself. It just needs to convey the same meaning as the image. + +The exception to this practice is when images are primarily for presentation purposes and are not essential pieces of content. To signify that an image should be skipped by a screen reader, set the value of the alt attribute to an empty string: `alt=””`. + +#### Trapping focus + +The recommended interaction pattern for components like the modal or popover is to trap focus within the component's modal element when it becomes visible. + +For keyboard-only users who use the tab key to navigate the interface, trapped focus means that focus cannot be shifted outside of the modal when using the tab key. Instead, when focus leaves the last focusable item, it should move to the first focusable item of the modal. + +For screen reader users, the other contents on the page should be hidden from the screen reader. + +Based on the [screen reader / browser combinations](/accessibility/testing-your-accessibility) we use for testing, we recommend applying `aria-hidden="true"` to the parent wrapping element of the page contents. The modal element of the component must not be a descendent of this element, and should be included as a sibling to this element. + +#### Scrollable elements + +Any elements with horizontal or vertical scroll need to be accessible via keyboard. + +Parent elements should be able to capture browser focus and be scrolled using the arrow keys. Some browsers will automatically make scrollable elements focusable to ensure keyboard accessibility, as long as they have a non-negative `tabindex`. It may be necessary to ensure that every container with overflow content which can grow larger than its parent's height to have `tabindex=0`. + +When `tabIndex` is added, you should either add `role='region'` and an `aria-label` that describes the scrollable element, or an `aria-labelledby` to a descriptive and accessibly named heading. + +Some screen reader users navigate page elements via an element list or rotor menu, and the default label for these scrollable elements will be driven by whatever text content exists inside the container. This generated label may not be suitable to describe the region's purpose, and would likely be better described with a simple `aria-label`. + +For example: +```html noLive +
+
+

Content

+
+
+``` + +## Screen reader considerations + +Just as front-end developers use their browser to see how their changes look, you should use a screen reader to see how your accessibility looks. You can use a screen reader that is available in your operating system, like VoiceOver for Mac, or you could download an open-source screen reader like [NVDA](https://www.nvaccess.org/download/) if you have a PC. + +To test PatternFly, we target the following screen readers: + +- JAWS with Chrome, Windows ([JAWS keyboard shortcuts](//dequeuniversity.com/screenreaders/jaws-keyboard-shortcuts)) +- Voiceover with Safari, Mac ([Voiceover keyboard shortcuts](//dequeuniversity.com/screenreaders/voiceover-keyboard-shortcuts)) +- NVDA with Firefox, Windows ([NVDA keyboard shortcuts](//dequeuniversity.com/screenreaders/nvda-keyboard-shortcuts)) + +Generally, screen readers access the Document Object Model (DOM) and use browser Application Programming Interfaces (APIs) to get the information they need. In this way, a screen reader knows what to say when a set of list items begins and ends, and can typically announce how many items are in the list in advance. A screen reader can also traverse a page using heading navigation to speak the heading level. + +There are a few aspects that can affect how screen readers communicate information, which you should consider when building and testing your product: + +- **Semantic HTML**: Semantics refers to the meaning of a piece of code. A semantic element clearly describes its meaning to both the browser and the developer. For example, `
` and `` are non-semantic elements because they don't describe their contents. On the other hand, `
` and `` are semantic elements, because they clearly define their contents. Screen readers expect semantic HTML when traversing the DOM, so non-semantic elements (that aren't customized to be made accessible) are highly likely to be inaccessible. ARIA and other accessible attributes are meant to extend the functionality and meaning of native semantics, but at the core, your HTML should be semantic. + +- **Headings**: A user with vision can scan a page to quickly understand its information architecture. Visually impaired users have other methods of achieving this, such as using heading levels to determine the flow of information. Headings that vary in size for design purposes, rather than functionality, will likely confuse these users. A clear flow of sequential heading sizes based on headings and subheadings is significantly clearer to all users. + +- **Accessible names for all elements**: When an element doesn't have visual text, or when further explanation is necessary, a screen reader will not know what an item is or does. For example, if you have an icon `
+ + + + {columnNames.map(columnName => ( + + ))} + + + + {reportData.map((row, idx) => ( + + {columnNames.map(columnName => ( + + ))} + + ))} + +
Report generated {reportDate}
+ {capitalize(columnName)} +
+ {row[columnName]} +
+ ); +}; diff --git a/packages/site/src/content/developer-resources/accessibility-scorecard.mdx b/packages/site/src/content/developer-resources/accessibility-scorecard.mdx new file mode 100644 index 0000000000..a985b85405 --- /dev/null +++ b/packages/site/src/content/developer-resources/accessibility-scorecard.mdx @@ -0,0 +1,19 @@ +--- +id: Accessibility scorecard +section: accessibility +--- +import { AccessibilityScorecard } from './accessibility-scorecard'; + +## Scoring your accessibility + +To support the proper assessment of accessibility measures, we've created a scorecard that outlines the ways that we recommend testing your UI and assessing how well it meets accessibility expectations. A completed scorecard can help you communicate the accessibility of your UI to stakeholders by clearly identifying how it meets important criteria. + +Scoring your accessibility shouldn't be a one-time thing. It's something that you should do routinely to assess your product as it evolves. + +An accessibility scorecard offers a higher-level overview of the current state of your product's accessibility, but it is **not intended to replace a full accessibility audit**, as described by our [accessibility testing guide](/accessibility/testing-your-accessibility). An accessibility audit is a vital part of creating your accessibility scorecard. + +## PatternFly.org accessibility scorecard + +The following example demonstrates what a completed scorecard may look like by assessing the PatternFly.org website documentation. + + diff --git a/packages/site/src/content/developer-resources/accessibility-testing.mdx b/packages/site/src/content/developer-resources/accessibility-testing.mdx new file mode 100644 index 0000000000..c0da98662e --- /dev/null +++ b/packages/site/src/content/developer-resources/accessibility-testing.mdx @@ -0,0 +1,112 @@ +--- +id: Testing your accessibility +section: accessibility +--- +import { Checkbox } from '@patternfly/react-core'; + +# Testing your product's accessibility + +This guide contains instructions and recommendations that you can use to robustly test your product's accessibility, in order to identify accessibility issues and opportunities for improvement. + +**Keep in mind that this guide will not cover every scenario.** + +## Standard testing procedures + +Many accessibility issues can be found by doing a few standard checks. + +### Validate your HTML + +Good accessibility practices start with structural, semantic HTML. When a screen reader (or any sort of assistive technology) scans a web page, it gets information about the Document Object Model (DOM), or the HTML structure of the page. No styles or JavaScript will be read by a screen reader. + +Screen readers (like Voice Over (VO), NVDA, or JAWS) don't just turn text into speech. They also use information in the HTML to list all of the headings on a page, give extra navigation controls to data tables, announce how many items are in a list, and more. This makes semantic HTML essential. + +You can use an HTML validation tool to test your product, such as [W3C’s markup validation service](https://validator.w3.org/). + +### Check for accessibility violations with an audit tool + +When using PatternFly, we recommend checking for accessibility violations locally via aXe: The Accessibility Engine (using [aXe DevTools](https://www.deque.com/axe/devtools/), the [Chrome extension](https://chrome.google.com/webstore/detail/axe-devtools-web-accessib/lhdoppojpmngadmnindnejefpokejbdd), or the [Firefox extension](https://addons.mozilla.org/en-US/firefox/addon/axe-devtools/)). If you want to test prior to deployment, you can integrate aXe with [Cypress](https://www.cypress.io/). + +#### Bulk testing with the patternfly-ally script + +We offer the [patternfly-a11y script](https://github.com/patternfly/patternfly-a11y) for bulk testing, which reports any aXe accessibility violations from a set of pages. You can adapt this script to your needs by creating a configuration file that includes authentication, waits for specific items to finish loading (like a loading spinner), or addresses other items relevant to your use case. As a report, this script will deliver an [accessibility report via surge](http://a11y-os.surge.sh/). + +Before using this script, your UI should be built in the CI workflow. Once built, create a job to run the script against that build. The script assumes that a web server is running and serving your product somewhere that the script can reach (for example, in `localhost:8000`). + +### Test keyboard accessibility + +The keyboard is an essential accessibility tool, so it is necessary to ensure that the following requirements are met: + +- All functionality is keyboard accessible. +- Elements in the HTML and in the layout follow a logical order. +- Elements with focus are clearly visible. + +### Test without styles + +Screen readers cannot access style information, so you should disable styles for your product to test that your information architecture is effective and that elements have adequate text labels. + +The [WAVE browser extension from WebAIM](https://wave.webaim.org/) allows you to disable styles if this isn't available in the browser you are using. + +### Test with a screen reader + +You can test with any screen reader that is available in your operating system. In PatternFly, we target: + - [JAWS](https://www.freedomscientific.com/products/software/jaws/) with Chrome, Windows ([JAWS keyboard shortcuts](//dequeuniversity.com/screenreaders/jaws-keyboard-shortcuts)). + - [VoiceOver](https://support.apple.com/guide/voiceover/welcome/mac) with Safari, Mac ([VoiceOver keyboard shortcuts](//dequeuniversity.com/screenreaders/voiceover-keyboard-shortcuts)). + - [NVDA](https://www.nvaccess.org/download/) with Firefox, Windows ([NVDA keyboard shortcuts](//dequeuniversity.com/screenreaders/nvda-keyboard-shortcuts)). + +### Check color contrast + +Your UI's colors should pass the following contrast checks to ensure that users across the vision spectrum can understand your product: + - Text color against background color ([Understanding WCAG 1.4.3](//www.w3.org/WAI/WCAG21/Understanding/contrast-minimum.html)) + - Text color against link color ([Technique G183](//www.w3.org/TR/WCAG20-TECHS/G183.html)) + - Visible boundaries of buttons and form elements against adjacent background color ([Understanding WCAG 1.4.11](//www.w3.org/WAI/WCAG21/Understanding/non-text-contrast.html)) + +## Accessibility testing checklist + +To keep track of your testing efforts, we recommend referencing the following checklist. + +This checklist includes some of the main areas that the PatternFly team checks for to ensure that a UI meets consistent accessibility standards. To evaluate your specific implementation, we recommend checking these same areas in your product. + +### Broad accessibility criteria + + + + + + + +Keyboard navigation via the tab key can discover all information.} description={If content should be hidden from other assistive technology like a screen reader, aria-hidden="true" should be passed instead.} id="general-criteria-4" /> + + } id="general-criteria-5" /> + +### Structural accessibility criteria + + Structure: The visual information architecture maps to the various rotor menus that exist by default.} body={<> + + + + +} id="accessibility-points-7" /> +
+ Labels: } body={<>Link labels are descriptive, informative, and unique (unless they have the same URL). id="accessibility-points-8a"/> + + Buttons and form controls:} description={ +
  • All form controls have clear and descriptive labels.
  • +
  • Expandable buttons display the expandable control and utilize aria-expanded to indicate that a button is expandable. aria-expanded should always have a boolean value if a button is meant to be expandable.
  • +
    + } + id="general-criteria-8b" /> + + Form inputs have a label (even if it's not visible).} id="general-criteria-8c" /> + + Icons have some kind of text for screen readers (even if it's not visible.)} id="general-criteria-8d" /> + + Images have proper alt text.} description={The exception to this practice is when images are primarily for presentation purposes and are not essential pieces of content. To signify that an image should be skipped by a screen reader, set the value of the alt attribute to an empty string: alt=""} id="general-criteria-8e" /> + + Landmark regions should have labels when there is more than one type of landmark, and they are not the same (such as navigation, main, form, etc.). Section element shouldn’t be used unless it has a label.} id="general-criteria-8f" /> + + Tables and table content is clearly described. WebAIM has additional guidance on
    creating accessible tables.} id="general-criteria-8g" /> + + ARIA labels provide descriptive details to screen reader users, without reiterating or overriding the text that is already there. If there is visible text then there doesn’t need to be an ARIA label. } id="general-criteria-8h" /> + +} id="general-criteria-8" /> diff --git a/packages/site/src/content/developer-resources/ally-color-example.png b/packages/site/src/content/developer-resources/ally-color-example.png new file mode 100644 index 0000000000..edccd63d71 Binary files /dev/null and b/packages/site/src/content/developer-resources/ally-color-example.png differ diff --git a/packages/site/src/content/developer-resources/ally-contrast-example.png b/packages/site/src/content/developer-resources/ally-contrast-example.png new file mode 100644 index 0000000000..bbcdb752ba Binary files /dev/null and b/packages/site/src/content/developer-resources/ally-contrast-example.png differ diff --git a/packages/site/src/content/developer-resources/cli-guidelines.mdx b/packages/site/src/content/developer-resources/cli-guidelines.mdx new file mode 100644 index 0000000000..ee1c0bf24a --- /dev/null +++ b/packages/site/src/content/developer-resources/cli-guidelines.mdx @@ -0,0 +1,163 @@ +--- +id: CLI handbook +title: Command-line interface handbook +source: overview +section: developer-resources +--- + +# Designing for command-line interfaces + +Our CLI handbook offers best practices for designing consistent, usable, and developer-friendly command-line interfaces (CLIs). It supports developers building CLI tools and designers collaborating on technical products. These guidelines are particularly helpful for environments where CLI tools are the primary or critical part of the user experience, emphasizing clarity, structure, and user-centered design across command syntax, help documentation, error messaging, and interactive behaviors. + +## Accessibility considerations + +While CLIs don't have visual UI elements, many [accessibility principles](/accessibility/about-accessibility/) still apply. + +Accessibility matters in CLI design just as much as it does in graphical interfaces. Clear, inclusive output ensures all users can successfully interact with the tool—including those using screen readers or alternative input devices. + +To ensure a CLI's accessibility, adhere to the following additional color, content, and testing practices. + +### Color + +
    + +| **Don't** | **Do** | +| --- | --- | +| Don’t convey meaning through color alone. | Do use text alongside color-based cues. For example, “Success” and “Error” labels. | +| | Do use text alongside red/green indicators, to make the information accessible to colorblind users. | + +
    + +### Content + +
    + +| **Don't** | **Do** | +| --- | --- | +| Don't use vague terms like “it failed”.| Do be direct and transparent with descriptive, specific language. | +| Don’t assume users can infer meaning from context alone.| Do use descriptive text for prompts and feedback. | +| Don't use prompt flows that require visual scanning without clear text guidance. | Do ensure all commands and prompts are keyboard-accessible and non-interactive-safe.

    Do use flags like `--non-interactive` for scripting or assistive tech users. | +| Don't use overly styled ASCII tables, long walls of text, or dynamic animations. | Do use plain, structured output that screen readers can parse.

    Do use clean, labeled output with headings, bullet points, or clear separators. | +
    + +### Testing + +
    + +| **Don't** | **Do** | +| --- | --- | +| Don't assume that your design is accessible. | Do test with screen readers and colorblind simulators to reveal subtle issues in contrast, clarity, and verbosity. | +
    + +### Example + +Accessible: + +```plaintext +✅ Deployment successful. +Run `tool status` to check environment health. +``` + +Less accessible: + +```plaintext +✅ You did it! +``` + +## CLI inputs + +To write effectively for CLIs, it is important to understand the different elements of CLI inputs: +1. **[Command name:](#command-names)** Identifies the action a command will perform and the subject that the action applies to. +1. **[Arguments:](#arguments)** Additional details used alongside the command name, which users select to specify the way that a command is applied. +1. **[Flags:](#flags)** Named parameters that modify the behavior of the command. + +### Commands + +A command describes the action triggered by the CLI. + +Command names should consistently use a verb-noun structure: +- **Verb:** The action performed. +- **Noun:** The resource or object affected. + +This structure mirrors how people think about tasks, making commands more intuitive and discoverable. The verb-noun format also aligns with widely-used CLIs like `git`, `kubectl`, and `docker`. In contrast, noun-verb structures can be harder to parse and don't scale well. + +#### Example + +In the following code block, `create project`, `delete environment`, and `scale deployment` are all commands. + +```bash +tool create project +tool delete environment +tool scale deployment +``` + +### Arguments + +Arguments are non-flag values following a command, typically unique identifiers like file paths or project names. + +A command requires an argument in order to execute. While multiple arguments can be used, their order matters. Fewer arguments are preferable to support easier recall and avoid confusion. + +#### Example + +In the following code block, `delete project` and `deploy environment` are commands, while `my-app` and `production` are arguments that represent the object being acted on. + +```bash +tool delete project my-app +tool deploy environment production +``` + +### Flags + +Flags are named parameters, prefixed with 2 hyphens (--), that modify the behavior of a command. They allow users to specify command modifiers, options, or other non-essential configuration. Flags can be added in any order. + +#### Example + +In the following code block, `--env`, `--force`, `--role`, and `--email` are flags. + +```bash +tool deploy --env staging --force +tool create user --role admin --email user@Examples:.com +``` + +#### Long-form and short-form + +There are 2 forms for flags: + +1. **Long-form flags:** More descriptive and clear. + + ```bash + tool deploy app --enable-autoscaling + tool configure user --assign-admin-privileges + tool update cluster --set-min-replicas 3 + ``` +1. **Short-form flags:** More concise, with 1-2 letters. + + - Reserve for frequently-used options. This benefits experienced users who prefer speed and situations with limited space. + - When possible, pair with long-form equivalents for better clarity and discoverability. + + ```bash + tool --help # Long-form + tool -h # Short-form (Help) + + tool --verbose # Long-form + tool -v # Short-form (Verbose) + + tool --config path/to/file + tool -c path/to/file # Short-form (Config file path) + ``` + +#### Types of flags + +1. **Boolean flags:** Represent on/off or true/false options. + + - Set a sensible default. + - Don’t require explicit values unless necessary. For example, allow `--force` rather than `--force=true`. + + ```bash + tool deploy --dry-run # Runs without executing + tool delete --force # Skips confirmation prompt + ``` + +2. **Help flags:** Provide help documentation that explains a command's purpose, its arguments/flags, and usage examples. + + - Offer both long `--help` and short `-h` options. \ No newline at end of file diff --git a/packages/site/src/content/developer-resources/cli-writing.mdx b/packages/site/src/content/developer-resources/cli-writing.mdx new file mode 100644 index 0000000000..d9c2fde04f --- /dev/null +++ b/packages/site/src/content/developer-resources/cli-writing.mdx @@ -0,0 +1,274 @@ +--- +id: CLI handbook +title: Command-line interface handbook +source: writing-guidelines +section: developer-resources +--- + +## CLI outputs + +CLI output messages typically fall into one of 3 categories: + +| Category | Usage | Example | +| --- | --- | --- | +| Success | Completed actions. | `✅ Dataset uploaded successfully.` | +| Warning | Completed actions that require review. | `⚠️ Model trained, but validation accuracy is low.` | +| Error | Failed actions. | `❌ Error: Cannot connect to remote service. Check your network connection or try again with --offline mode.` | + +### Success messages + +To build trust, reinforce that a command worked as intended, and guide users toward their next step, clearly communicate successful actions. + +#### Example + +```plaintext +✅ Project "my-app" deployed successfully. + +Next steps: +- Run `tool status my-app` to check deployment health +- Run `tool logs my-app` to view runtime output +``` + +### Error messages + +When errors occur, explain what happened, why, and how to fix it. + +Expanding on our [UI error writing guidelines](/ux-writing/error-messages), CLI errors should: +- Use plain language, avoiding internal jargon. +- Offer suggestions and actionable next steps. +- Conclude with the most important information. This is the opposite of content design for products with GUIs. +- By default, provide a clean message. Full stack traces or internal logs should only be exposed via debug flags (like `--debug` or `--trace`). + +#### Examples + +1. Generic failure with correction: + ```plaintext + ❌ Error: Cannot connect to remote service. + Check your network connection or try again with `--offline` mode. + ``` + +1. File permission issue: + ```plaintext + ❌ Error: Unable to write to file.txt + You may need to change the file’s permissions or run the command with elevated privileges. + ``` + +1. Command syntax error: + ```plaintext + ❌ Error: Unrecognized flag --versoin + Did you mean: --version ? + ``` + +### Output patterns + +#### Formatting + +To ensure that output is readable: +1. Structure large outputs: + - Use spacing, dividers, indentation, or table/column formats to break up large blocks and avoid unstructured text. + - Ensure consistent headers or labels for repeated information (like results or summaries). +2. Manage lists effectively: + - Structure lists for easy scanning—including software versions, resources, or deployment options. + - Display the most relevant or default item first (like the current version) and clearly label it with "Yes" or "*". + - [Paginate](#pagination) lists that exceed 5–7 items. + +#### Version listing + +When listing version information: +- Arrange versions top-down from newest to oldest. +- Clearly mark the current default. +- Display upgrade paths beside each item. + +##### Example + +```plaintext +Available Versions +- +VERSION DEFAULT AVAILABLE UPGRADES +1.4.3 Yes 1.4.4, 1.4.5, 1.5.0 +1.3.9 1.4.0, 1.4.1 +1.3.8 1.3.9 +``` + +#### Pagination + +Paginate long lists into 5–7 item pages, prompting users to continue with `--more`, `--page`, by pressing the **Enter** key. + +##### Example + +```bash +tool versions list --limit 5 +tool resources list --page 2 +``` + +#### Sorting and filtering + +To help users make sense of large CLI outputs, provide sorting and filtering options: +Default to sorting by relevance or recency.- +- Offer flags like `--sort`, `--filter`, or `--status` for flexible control. +- Ensure the default view serves most users without requiring flags for basic usability. + +## Help documentation + +CLIs must provide accessible in-application help. To ensure its relevance, write from a new user's perspective: would they immediately know what to do? + +Effective help documentation is: +- Brief yet meaningful. +- Clear, avoiding unexplained jargon or acronyms. +- Consistent across all commands. +- Referenced in [interactive prompts](#interactive-mode) (via `--help`) if supported. + +### Writing help output + +Structure help output consistently with these elements: +- **Description:** Plain language explanation of the command’s function. +- **Usage:** Command syntax, including required arguments and flags. +- **Examples:** At least 1 clear, real-world usage scenario. +- **Flags:** List of available options with brief, actionable descriptions. +- **Documentation link (optional):** For further details. + +#### Example + +```bash +Usage: + tool deploy [flags] + +Description: + Deploys the specified project to your active environment. + +Examples: + tool deploy my-app --env staging + +Flags: + -e, --env string Environment to deploy to + -f, --force Force deployment even if conflicts exist + -h, --help Show help for the deploy command + +For more information, visit: https://Examples:.com/docs/deploy +``` + +### Documenting flags +Well-documented flags improve discoverability, reduce user error, and make it easier for contributors and users to understand the CLI’s capabilities. + +Document flags clearly in: +- A command's `--help` output. +- Official CLI documentation or reference guides. +- Interactive prompt hints (if applicable). + +#### Best practices +- Use descriptive names that clearly indicate the flag’s purpose. Avoid ambiguous names like `--flag1`. +- Document the input type (such as string, boolean, or int). +- Show any default value. +- Mention if the flag is optional or required. + +Flag documentation should generally follow this format: + +```plaintext +--flag-name Description of what this flag does (default: value) +``` + +##### Example + +```plaintext +Flags: + -n, --name string Name of the project to create + -e, --env string Target environment (e.g., staging, prod) + -f, --force Skip confirmation prompts (default: false) + -o, --output string Output format: json, yaml, or table (default: table) + -h, --help Show help for this command +``` + +For boolean flags that act as switches (true/false): +- Typically default to `false`. +- Don't require an explicit value (for example, use `--force`, not `--force=true`). +- Clearly state what enabling the flag does. +- When possible, explain the flag's effect or common use cases: + + ```plaintext + --dry-run Simulate the command without making changes. Useful for validation or preview. + --watch Continuously stream status updates until completion. + ``` + +## Interactive mode + +Interactive mode guides users step-by-step with prompts, commonly for setup wizards, configuration flows, or complex inputs not suited for single commands. + +### When to use interactive mode + +User interactive mode for: +- Setup or initialization wizards. +- Optional configuration flows. +- Profile or environment selection. + +### When not to use interactive mode + +Do not use interactive mode for: +- Simple one-off tasks. +- Repetitive actions, such as run, delete, status. +- Automated commands, such as in CI/CD pipelines. +- Essential inputs that could be passed as flags. + +### Writing interactive prompts + +When designing interactive prompts, prioritize flags for essential inputs and use prompts primarily for optional choices or guided multi-step processes. + +Key considerations include: + +#### Default values +Choose defaults based on common use cases or sensible fallbacks. + +- Make defaults obvious—don't hide them in help text or assume user knowledge. +- Visually indicate defaults clearly (such as `[default]`, `(default)` or `(Y/n)`/`(y/N)`). +- If using a list, ensure a first-item default is genuinely the most common choice. +- Explain that pressing **Enter** accepts the default (if the input is left blank). +- Confirm (log or echo) the selected value after the prompt, even if it was the default. + +#### Clarity + +Ensure prompts are as clear as possible. + +- Phrase prompts as questions. + - For example: "Enable autoscaling? (Y/n)" +- Clearly state if responding to a prompt is optional. +- Offer inline help where useful. + - For example: "Output directory [? for help]" +- Avoid chaining an excessive number of prompts. +- Include optional next steps when appropriate (like view status, open logs). +- Avoid silent success unless explicitly requested (like in `--quiet` mode). + +#### User control + +Empower users with control over their CLI experience. + +- Consider using a `--guided` flag to let users intentionally trigger multi-step interactive flows. +- Let users bypass prompts with a `--non-interactive` or `--yes` flag. +- Allow users to cancel or exit flows early with **Ctrl+C** or a similar command. + +### Example + +```plaintext +Welcome! Let's configure your project. + +Project name: my-app +Language (js, py, go) [py]: +Use Docker? (y/N): y + +✅ Project "my-app" configured successfully. +``` + +```plaintext +Choose deployment region: +[1] US East (N. Virginia) +[2] US West (Oregon) (default) +[3] Europe (Frankfurt) + +Enable telemetry? (y/N) +``` + +```plaintext +Select output format (default = 'json') [Use arrows to move, type to filter, ? for help]: +``` + + + + diff --git a/packages/site/src/content/developer-resources/dark-theme-handbook.mdx b/packages/site/src/content/developer-resources/dark-theme-handbook.mdx new file mode 100644 index 0000000000..0badffb58e --- /dev/null +++ b/packages/site/src/content/developer-resources/dark-theme-handbook.mdx @@ -0,0 +1,61 @@ +--- +id: Dark theme handbook +title: PatternFly dark theme handbook +section: developer-resources +--- + +## Enabling dark theme + +Dark theme styles ship with PatternFly CSS by default. To enable dark theme, add the class `pf-[version]-theme-dark` (for example, `pf-v6-theme-dark`) to your application's `` tag. This class can be added dynamically to toggle dark theme on and off in your application. + +Dark theme can also be applied based on the browser’s `prefers-color-scheme` media query. When using this method, we recommend using JavaScript to detect the media query and apply the `pf-[version]-theme-dark` class. This allows you to manipulate a single class in order to toggle dark theme based on user preference. [Adam Argyle wrote a great article](https://web.dev/building-a-theme-switch-component/#javascript) on using JavaScript to manage dark theme preference, using the `prefers-color-scheme` media query alongside a manual button that toggles dark theme. + +[Our token resources](https://github.com/patternfly/patternfly/tree/v6/src/patternfly/base/tokens) include styles for both light and dark themes. When dark theme is enabled, your product will automatically pull dark theme tokens in order to adapt visual styles appropriately. + +The only features which will require additional work in order to support dark theme are charts and images. + +### Charts + +To use charts with dark themes, refer to our guidance for [developing with charts](/charts/about-charts#develop-with-charts). + +### Images + +To create images that adapt to light and dark themes, there are a few approaches you can take: + +- Use inline SVG's with fill colors set to [PatternFly color tokens](/tokens/all-patternfly-tokens), which inherently adapt to light and dark themes. +- Create images with colors that work well with both light and dark themes. These colors should meet [WCAG AA contrast requirements](https://webaim.org/resources/contrastchecker/). +- Utilize background color, border color, border-radius, and padding/spacing to create a container that can hold dynamic/user-supplied images. +- Write CSS and dynamically swap between 2 image variations: + + ``` + + + + + ``` + +## Best practices + +To make it easier to support light and dark theming in your application, we recommend following these best practices during design and development: + +* **Use PatternFly components without customizations.** Most problems with dark theming are due to the use of custom styles, overrides to PatternFly styles, and non-PatternFly components. To ensure consistent styling and behavior when switching themes, try to use PatternFly components as they are. + +* **Use tokens and component variables to define any overrides.** + * For example, to override a primary button’s background color, declare `.pf-[version]-c-button { --pf-[version]-c-button--m-primary--BackgroundColor: [color token]; }` instead of `.pf-[version]-c-button.pf-m-primary { background-color: [color token]; }`. + +* **Use tokens in custom styles.** + * For example, use `background-color: var(--pf-t--[version]--global--background--color--primary--default)` for a primary background instead of `background-color: #fff` or `background-color: white`. Values like `#fff` and `white` will not change between light and dark theme, but tokens will. + +* **Always use the most relevant semantic token for your use case.** If there isn't a semantic token for your scenario, then you can use a base token. Never use a palette token directly in your code. + * For example, `--pf-t--[version]--global--text--color--link--default`, `--pf-t--[version]--color--blue--20`, and `#b9dafc` are all the same in PatternFly's default light theme. When you create something custom, where the color should match the application’s link text color, any of these values will work. However, in a different theme, these token values may not always be the same color. + +* **Use SVG files or icon fonts for icons, and use tokens for icon colors.** To easily manipulate icon colors between light and dark theme, SVG files and icon fonts can be changed via CSS by using the `fill` and `color` properties. When using semantic tokens, like `--pf-t--[version]--global--color--status--info--default`, colors will automatically adjust between light and dark theme. If images must be used, we advise you to use colors that work well in both light and dark themes and/or hide and show the appropriate images based on the presence of the dark theme body class. \ No newline at end of file diff --git a/packages/site/src/content/developer-resources/patternfly-accessibility.mdx b/packages/site/src/content/developer-resources/patternfly-accessibility.mdx new file mode 100644 index 0000000000..6d7789d6d7 --- /dev/null +++ b/packages/site/src/content/developer-resources/patternfly-accessibility.mdx @@ -0,0 +1,37 @@ +--- +id: PatternFly's accessibility +section: accessibility +--- + +## Component accessibility + +We do our best to build accessibility into PatternFly's components to take some of the accessibility work off your hands. + +As PatternFly is updated and enhanced, we maintain accessibility through a combination of automated and manual testing. We use [aXe: The Accessibility Engine](https://www.deque.com/axe/) to ensure that all components pass an accessibility audit before they’re added to PatternFly. + +We also regularly audit keyboard accessibility with both manual testing and integration tests. We aim to provide full support for VoiceOver as our main screen reader, but we still test our components through NVDA and JAWS. As part of our manual audit, every component is run through VoiceOver to make sure they’ll be as accessible as possible in your products. + +## Accessibility standards + +Our goal is to meet [level AA in the Web Content Accessibility Guidelines 2.1](https://www.w3.org/WAI/WCAG21/quickref/?currentsidebar=%23col_customize&levels=aaa). If you use or contribute to PatternFly, the following accessibility guidelines are some that you can expect PatternFly to adhere to: + +| Guideline | Link | Applies to | Tested | +| --- | --- | --- | --- | +| Semantic HTML structures are used to accurately communicate the purpose and relationship of UI elements. | [WCAG 1.3.1](//www.w3.org/WAI/WCAG21/quickref#info-and-relationships) | `design` `html` `css` | Automated testing with aXe and manual testing | +|Color is not the only method of communication. Providing meaning with color is supplementary to providing meaning with text. | [WCAG 1.4.1](//www.w3.org/WAI/WCAG21/quickref#use-of-color) | `design` `html` `css` | Manual testing and aXe used | +| Colors used provide sufficient contrast | [WCAG 1.4.3](//www.w3.org/WAI/WCAG21/quickref#contrast-minimum) and [1.4.11](//www.w3.org/WAI/WCAG21/quickref#non-text-contrast) | `css` | Automated testing with aXe | +| Font sizes can scale up to 200% without loss of content or functionality, and up to 400% without needing to scroll in more than one direction. | [WCAG 1.4.4](//www.w3.org/WAI/WCAG21/quickref#resize-text) and [1.4.10](//www.w3.org/WAI/WCAG21/quickref#reflow) | `css` | Manual testing | +| Styles that affect text spacing (line height, space between paragraphs, letter spacing, and word spacing) can be increased without loss of content or functionality. | [WCAG 1.4.12](//www.w3.org/WAI/WCAG21/quickref#text-spacing) | `css` | Manual testing and aXe used | +| Contents that appear on hover and focus are dismissible, hoverable, and persistent. | [WCAG 1.4.13](//www.w3.org/WAI/WCAG21/quickref#content-on-hover-or-focus) | `html` `css` `js` | Manual testing | +| All functionality is keyboard accessible. | [WCAG 2.1.1](//www.w3.org/WAI/WCAG21/quickref#keyboard) and [2.1.2](//www.w3.org/WAI/WCAG21/quickref#no-keyboard-trap) | `html` | Manual testing | +| Elements in the HTML and in the layout follow a logical order. | [WCAG 1.3.2](//www.w3.org/WAI/WCAG21/quickref#meaningful-sequence) and [2.4.3](//www.w3.org/WAI/WCAG21/quickref#focus-order) | `design` `html` `css` | Manual testing | +| Elements with focus are clearly visible. | [WCAG 2.4.7](//www.w3.org/WAI/WCAG21/quickref#focus-visible) | `css` | Manual testing | +| Flashing content does not flash more than three times in any one-second period, or the flash is below the general flash and red flash thresholds. | [WCAG 2.3.1](//www.w3.org/WAI/WCAG21/quickref/?showtechniques=231#three-flashes-or-below-threshold) | `css` | Manual testing| +| Functionality that uses complex gestures can also be operated with a single pointer without a path-based gesture. | [WCAG 2.5.1](//www.w3.org/WAI/WCAG21/quickref#pointer-gestures) | `design` | Manual testing | +| Pointer events can be canceled. | [WCAG 2.5.2](//www.w3.org/WAI/WCAG21/quickref#pointer-cancellation) | `js` | Manual testing | +| Visible labels of UI components are either the same as the accessible name or used in the beginning of the accessible name. | [WCAG 2.5.3](//www.w3.org/WAI/WCAG21/quickref#label-in-name) | `html` | Automated testing with aXe and manual testing | +| The target area for clickable elements is at least 44 by 44 [CSS pixels](//www.w3.org/TR/WCAG21#dfn-css-pixels). | [WCAG 2.5.5 (AAA)](//www.w3.org/WAI/WCAG21/quickref#target-size)* | `css` | Manual testing | +| An accessible name is provided for all elements. | [WCAG 4.1.2](//www.w3.org/WAI/WCAG21/quickref#name-role-value) | `design` `html` | Automated testing with aXe and manual testing with VoiceOver +| Status messages can be programmatically determined through role or properties. | [WCAG 4.1.3](//www.w3.org/WAI/WCAG21/quickref#status-messages) | `html` | Manual testing | + +*WCAG 2.5.5 is included for reference only. This guideline suggests a size that is larger than what PatternFly requires. \ No newline at end of file diff --git a/packages/site/src/content/developer-resources/rtl-handbook.mdx b/packages/site/src/content/developer-resources/rtl-handbook.mdx new file mode 100644 index 0000000000..d7bf1ff4c2 --- /dev/null +++ b/packages/site/src/content/developer-resources/rtl-handbook.mdx @@ -0,0 +1,47 @@ +--- +id: Right-to-left handbook +title: PatternFly right-to-left handbook +section: developer-resources + +--- + +To allow for internationalization of your product's content, it is important to implement bidirectional language support by developing for both right-to-left (RTL) and left-to-right (LTR) languages. + +The default browser behavior displays content following LTR formatting. In order to support RTL languages like Arabic and Hebrew, you will need to explicitly add RTL support. To support RTL languages the browser uses `dir="RTL"` and `lang="{language code}"` to lay out the page appropriately for the selected language. Setting `dir="RTL"` causes the browser to reverse and lay out the contents from right to left. The W3C provides [information about internationalization and the bidirectional algorithm](https://www.w3.org/International/techniques/authoring-html#direction). + +## Support in PatternFly + +### Components + +PatternFly components have been written to use [logical properties](https://developer.mozilla.org/en-US/docs/Web/CSS/CSS_logical_properties_and_values) - `block-start`, `inline-end`, `block-end`, and `inline-start` - rather than `top`, `right`, `bottom`, and `left`. This allows styles like margin and padding to be correctly laid out in both LTR and RTL. However, to avoid a sweeping breaking change, PatternFly variable names still use `top`, `bottom`, `left`, and `right`. + +**Note:** An exception to this support is with any components using popper.js, like tooltips and popovers. For now, the popper position and placement will need to be managed manually when used on pages with RTL content. + +### Charts + +To support RTL across PatternFly charts, we've added a new `legendDirection` property to the +``, ``, ``, ``, and `` components. This property allows you to adjust the direction of chart legend labels. When in RTL, the value of this property should be set to "rtl". + +Additionally, when in RTL, ensure that the `` representing a chart's x-axis uses the `invertAxis` property to flip the axis. + +**Note:** When using self-defined custom legends and label components, RTL support must be handled manually as `legendDirection` does not apply to custom implementations. + +### Icons +PatternFly components have also been written to reverse directional icons that are part of the component. For example, the caret indicating expansion of various components is properly reversed. + +Care should be taken to handle icons appropriately for RTL. Some icons you may have in your interface will not be mirrored automatically. [Sometimes an icon should be reversed in RTL](https://m2.material.io/design/usability/bidirectionality.html#mirroring-elements) (for example, when indicating a direction such as an expansion caret), and sometimes it should not be reversed (such as a logo, or an icon indicating time). When an icon *should* be reversed, but isn't reversed automatically, you you can use one of the methods mentioned in the [RTL helpers](#patternfly-rtl-helpers) section. + +## PatternFly RTL helpers + +The preferred approach for defining the browser's writing direction is to use the `dir` HTML attribute, preferably on the `` tag: `` or ``. If you are unable to use this attribute for any reason, you can instead set the CSS `direction` property with our `.pf-v6-m-dir-ltr` or `.pf-v6-m-dir-rtl` helpers. These approaches can apply to the whole document or individual elements, and can be nested. + +To adjust the of direction of icons that aren't automatically mirrored for RTL and LTR, you can use the `.pf-v6-m-mirror-inline-rtl` class or the `shouldMirrorRTL` property of the `` React component. + +To get the inverse of a number, dimension, or percentage, you can multiply by the variable `--pf-v6-global--inverse--multiplier`, which will have a value of 1 in LTR and -1 in RTL. + +## Best practices and resources +- There are [many nuances to how content is laid out through LTR and RTL](https://ltr.wtf/explained/bidiintro.html#the-good-the-bad-and-the-ugly), so it isn't always obvious what the correct result should be. Testing your site with native speakers is always recommended. +- The W3C's guide for [inline markup and bidirectional text in HTML](https://www.w3.org/International/articles/inline-bidi-markup/) explains how to write HTML within a paragraph or other inline content. +- The W3C's guide for [structural markup and right-to-left text in HTML](https://www.w3.org/International/articles/inline-bidi-markup/) covers ways of handling text direction at the document level and for elements. +- Material Design summarizes [which UI elements should be reversed in an RTL layout](https://m2.material.io/design/usability/bidirectionality.html#mirroring-layout). +- For a comprehensive discussion on RTL styling, refer to the [RTL Styling 101](https://rtlstyling.com/posts/rtl-styling) guide. diff --git a/packages/site/src/content/get-started/contribute.md b/packages/site/src/content/get-started/contribute.mdx similarity index 97% rename from packages/site/src/content/get-started/contribute.md rename to packages/site/src/content/get-started/contribute.mdx index 0a909b5964..cfb07aa170 100644 --- a/packages/site/src/content/get-started/contribute.md +++ b/packages/site/src/content/get-started/contribute.mdx @@ -3,7 +3,6 @@ id: Contribute title: Contribute to PatternFly section: get-started --- - ## Community contributions Thank you for your interest in contributing to PatternFly! We depend on community contributions to help our design system grow and evolve. We encourage everyone, regardless of background, to get involved. Common contributions include (but aren't limited to): @@ -50,10 +49,10 @@ Be sure to view our detailed contribution instructions for both of these reposit If you believe that you've come across a PatternFly bug, alert our team, so that we can resolve the issue. To report a bug, follow these steps: 1. View the documentation for the feature, to confirm that the behavior is not functioning as intended. -1. Search open issues in the [patternfly](https://github.com/patternfly/patternfly/issues) and [patternfly-react](https://github.com/patternfly/patternfly-react/issues) repositories to see if a related issue already exists. +2. Search open issues in the [patternfly](https://github.com/patternfly/patternfly/issues) and [patternfly-react](https://github.com/patternfly/patternfly-react/issues) repositories to see if a related issue already exists. - If the bug is present in only the React implementation of PatternFly, [create a bug issue in patternfly-react.](https://github.com/patternfly/patternfly-react/issues) - If the bug can be seen on both the React and HTML/CSS side, [create a bug issue in patternfly](https://github.com/patternfly/patternfly/issues). -1. Be sure to mention which project the bug was noticed in and if there is a deadline that the fix is needed for. +3. Be sure to mention which project the bug was noticed in and if there is a deadline that the fix is needed for. ## Documentation diff --git a/packages/site/src/content/get-started/release-notes.md b/packages/site/src/content/get-started/release-notes.md deleted file mode 100644 index 6f4d50892d..0000000000 --- a/packages/site/src/content/get-started/release-notes.md +++ /dev/null @@ -1,19 +0,0 @@ ---- -id: Upgrade -source: release-notes -title: PatternFly 6 upgrade -section: get-started ---- - -## PatternFly 6 React breaking changes - -import { ReleaseNotesTable } from './release-notes-table.js'; - -This resource organizes the PatternFly 5 to PatternFly 6 change log in a table that allows for searching, filtering, and sorting. -Note that this table does not contain a completely comprehensive list of changes, as it does not include information about dependency bumps and documentation updates. - -Comprehensive PatternFly 6 release notes can be found on GitHub, in [@patternfly/patternfly](https://github.com/patternfly/patternfly/releases) and [@patternfly/react-core](https://github.com/patternfly/patternfly-react/releases). - -A summary of the changes from PatternFly 6 can be found in our [release highlights](/get-started/release-highlights/). - - diff --git a/packages/site/src/content/get-started/upgrade.mdx b/packages/site/src/content/get-started/upgrade.mdx deleted file mode 100644 index 518f1ba05e..0000000000 --- a/packages/site/src/content/get-started/upgrade.mdx +++ /dev/null @@ -1,203 +0,0 @@ ---- -id: Upgrade -source: upgrade-guide -title: Upgrade to PatternFly 6 -section: get-started ---- -import { Alert, Button, Divider } from '@patternfly/react-core'; -import ArrowRightIcon from '@patternfly/react-icons/dist/esm/icons/arrow-right-icon'; - - To ensure your product is ready for PatternFly 6, [complete the PatternFly 5 upgrade process](https://v5-archive.patternfly.org/get-started/upgrade) first to address any necessary changes from our previous release. - -PatternFly 6 introduces the exciting new features and functionality outlined [our release highlights](/get-started/release-highlights). For a detailed breakdown on the work that went into this release, you can view [the PatternFly 6 major release notes](/get-started/upgrade/release-notes). - -In the following sections, this upgrade guide outlines steps required to migrate your codebase to PatternFly 6 and additional resources to support your journey: - -1. [Notable changes](#notable-changes): Significant changes you should be aware of before starting your upgrade. -1. [Upgrade steps](#how-to-upgrade): Step-by-step instructions for upgrading. -1. [Help resources](#get-help): Easy-access links to get help from the PatternFly team. - - - -## Notable changes - -Before you upgrade, familiarize yourself with these significant changes. While some are handled by codemods, some changes *could* require manual intervention and should be kept in mind as you upgrade. - -### Components - -1. [Chip](/components/chip): Replaced with [label](/components/label). -1. [Tile](/components/tile): Replaced with [card](/components/card). -1. [Text](https://v5-archive.patternfly.org/components/text): Renamed to ["content"](/components/content). -1. [Expandable section](/components/expandable-section): Removed `isActive`. -1. [Empty state](/components/empty-state): Refactored. - - This refactoring is not *entirely* handled by codemods. Depending on your implementation, your empty states could also require manual updates. For more details, search "empty state" in the [release notes table](/get-started/upgrade/release-notes). - -### Charts - -To support multiple chart libraries, Victory-based charts have moved to a "victory" directory in [@patternfly/react-charts](https://www.npmjs.com/package/@patternfly/react-charts). Your import paths will need to align with this change. - -- **Old path:** `import { Area } from '@patternfly/react-charts';` -- **New path:** `import { Area } from '@patternfly/react-charts/victory';` - -Victory is now an optional peer dependency, allowing future chart libraries to be installed without including Victory dependencies and vice versa. - -To install Victory packages, you can either: -- Install the single "victory" package to cover all features. -- Install specific packages, based on your product's features (such as "victory-core" or "victory-tooltip"). - - - -## How to upgrade - -Your upgrade process will require you to complete these steps: - -1. Update your dependencies to use PatternFly 6 instead of PatternFly 5. -1. [Run our codemods suite](#1.-run-our-codemods-suite). -1. [Remove all CSS overrides](#2.-remove-all-css-overrides). -1. [Review and update variable and class names](#3.-review-and-update-variable-and-class-names). -1. [Update any pixel-based logic for your breakpoints](#4.-update-any-pixel-based-logic-for-breakpoints). - -### 1. Run our codemods suite - -**Note:** Do this _before_ making any manual changes to your codebase. Waiting until after will lead to even more manual intervention and cleanup. - -We offer a suite of PatternFly codemods to simplify and streamline your upgrade process. Instead of having you manually locate errors across your codebase, our codemods can quickly identify and fix major issues. Some changes will still require manual intervention, but our codemods can automatically fix many issues and flag any that require manual work. - -To run [our codemods](https://github.com/patternfly/pf-codemods/), follow these steps: - -1. First, make sure that you have updated your dependencies to use PatternFly 6 instead of PatternFly 5. This is not handled by codemods. - -1. Run this command, adding in the path to your product's source code: - - `npx @patternfly/pf-codemods@latest --v6` - - * You should see an output similar to running `lint`, including a list of warnings and errors and a total count of each: - - ![Example codemod output.](./img/codemod-output.png) - - * If your results don’t look like this, [reach out to the PatternFly team](#get-help) before continuing. - -2. Make note of any flagged issues. - -3. Add the `--fix` flag to the end of your original command and run it again. - -4. Make note of the changes applied to your codebase. - -5. Note any errors that were not automatically fixed (some may simply be warnings) and manually repair critical issues. - -6. Build your product. - -7. To ensure that all issues are flagged and addressed, complete steps 1-6 multiple times. Once everything looks correct, continue to [step 2](#2-remove-all-css-overrides). - -8. You will likely need to make updates to [React tokens](https://www.patternfly.org/tokens/develop-with-tokens/#react-tokens) in your product, discussed in step 3. - -### 2. Remove all CSS overrides - -The new design token system in PatternFly 6 changes variable names across PatternFly. Any existing CSS overrides will be targeting outdated styles and will no longer work, so they must be updated or removed. - -Once you've completed the standard codemods in step 1: -1. Temporarily remove your overrides and see how things look. - - Since there isn't a PatternFly 6 equivalent for every PatternFly 5 style, some of your previous overrides will likely have no effect and can be removed. -1. Completely remove CSS overrides as much as possible, so that your product upgrade experience will be smoother for future releases. -1. If you need to keep any CSS customizations, continue to [step 3](#3.-review-and-update-variable-and-class-names). - -### 3. Review and update variable and class names - -A number of variables have been removed or added—primarily due to logical direction changes, refactoring, or deprecation. For more context, we've put together these lists: -- [Removed variables](https://docs.google.com/spreadsheets/d/e/2PACX-1vQqeH7ThYi0jkhYEB8B2SXa7x8AaY5T9ajG6o-Ogz3p7YVp0OuTulb_L3DYLDrHlY4zUE3IBiup6tkN/pubhtml?gid=1160160856&single=true) -- [Added variables](https://docs.google.com/spreadsheets/d/e/2PACX-1vQqeH7ThYi0jkhYEB8B2SXa7x8AaY5T9ajG6o-Ogz3p7YVp0OuTulb_L3DYLDrHlY4zUE3IBiup6tkN/pubhtml?gid=268831450&single=true). - -Wherever you have custom CSS overrides that reference PatternFly class names or CSS variables, carefully review them and make updates to ensure that they align with [our new design tokens](/tokens/all-patternfly-tokens). - -To assist with naming updates, we offer 3 codemods: -1. [class-name-updater](https://github.com/patternfly/pf-codemods/tree/main/packages/class-name-updater): Automatically identifies and renames classes to align with changes in PatternFly 6. -1. [tokens-update](https://github.com/patternfly/pf-codemods?tab=readme-ov-file#tokens-update): Updates global CSS variables in your React code, including React tokens. -1. [css-vars-updater](https://github.com/patternfly/pf-codemods/tree/main/packages/css-vars-updater): Updates CSS variables in non-React files, including .css, .scss, .md, or another file type that you specify. - -The following guidance outlines the steps to run these codemods. - -#### Run class-name-updater -For more details, refer to [the class-name-updater README](https://github.com/patternfly/pf-codemods/tree/main/packages/class-name-updater). - -This codemod highlights places in your codebase that may require you to make adjustments and specifically replaces `pf-v5` prefixes with `pf-v6`. It performs a simple "find and replace", so it could inadvertently identify code that resembles a PatternFly class name. Keep an eye out for this to avoid any unintentional changes. - -When using this codemod, make sure to add: -- The `--v6` option, since you are upgrading to PatternFly 6. This codemod targets v5 of PatternFly by default. -- The `--fix` flag to allow the codemod to fix issues where possible. - -#### Run tokens-update -For more details, refer to [the tokens-update example in the pf-codemods README](https://github.com/patternfly/pf-codemods?tab=readme-ov-file#tokens-update). - -This codemod updates global color variables in .js and .tsx files to a temporary hot pink color to visibly mark the places where you need to manually replace tokens (`--pf-t--temp--dev--tbd`, or `t_temp_dev_tbd` when using [React tokens](/tokens/develop-with-tokens#react-tokens)). For other global variables (like spacers, font size, or box shadows), it will attempt to provide an auto-fix to match the same or closest value. - -This codemod works both for CSS variables and React tokens. For example: -- A CSS variable: `--pf-v5-global--FontSize--lg` becomes `--pf-t--global--font--size--lg` -- A React token: `global_FontSize_lg` becomes `t_global_font_size_lg` - -##### Manual React token updates -Codemods will sometimes be unable to fix *all* tokens imported by `@patternfly/react-tokens` because there is often no 1:1 match for a PatternFly 5 and PatternFly 6 React token. - -If you continually receive errors that tokens in your code don’t exist, despite re-running codemods, it doesn't necessarily mean that codemods didn't work. It could mean your React tokens point to old global variables. If so, you must locate outdated tokens and replace them with the [PatternFly 6 React token](/tokens/develop-with-tokens#react-tokens) that best fits your use case. - -Example: -- PatternFly 5 token: `global_link_Color_hover` -- PatternFly 6 token: `t_global_color_nonstatus_green_clicked` - -While these tokens have different uses, this example is meant to show how the general syntax changed, which is what leads to errors with your code. - -#### Run css-vars-updater - -For more details, refer to[ the css-vars-updater README](https://github.com/patternfly/pf-codemods/tree/main/packages/css-vars-updater). - -This codemod automatically identifies PatternFly 5 CSS variables that need to be updated after the introduction of [design tokens in PatternFly 6](https://www.patternfly.org/tokens/about-tokens/). It will help you update these CSS variables in non-React files, including .css, .scss, .md, or another file type that you choose. - -### 4. Update any pixel-based logic for breakpoints - -PatternFly 6 uses rem units for global breakpoint [design tokens](/tokens/all-tokens), rather than pixels. - -If you have previously implemented any breakpoint logic based on a pixel value, you will need to account for the fact that PatternFly 6 breakpoint tokens use rems. To find the rem equivalent, divide your pixel value by 16 or refer to this table: - -| Breakpoint | Design token | Pixel value (previous) | Rem value (new) | -| --- | --- | --- | --- | -| xs |`--pf-t--global--breakpoint--xs` | 0px | 0rem -| sm |`--pf-t--global--breakpoint--sm` | 576px | 36rem -| md |`--pf-t--global--breakpoint--md` | 768px | 48rem -| lg |`--pf-t--global--breakpoint--lg` | 992px | 62rem -| xl |`--pf-t--global--breakpoint--xl` | 1200px | 75rem -| 2xl |`--pf-t--global--breakpoint--2xl` | 1450px | 90.625rem - -### Potential test failures - -#### Button - -1. *Cannot find aria-disabled* - - **Cause:** We changed button's `isDisabled` prop to assign a value for `disabled`, but none for `aria-disabled`. The exception to this is when the `component` prop is passed anything other than "button" as a value. Additionally, `aria-disabled` will now only render when true. - - **Fix:** Remove tests that look for `aria-disabled` in buttons when the expectation is either: - - For `aria-disabled` to be false. - - For `aria-disabled` to match `isDisabled` when `component="button"`. - -1. *Cannot find button attributes when using byText* - - **Cause:** We added a wrapping `div` around button text. The RTL `byText` query returns that wrapper instead of the button element itself, where button's attributes live. - - **Fix:** Instead of `byText`, use `byRole` and pass the button text to `name`. This returns the top-level button element. - -#### Select - -1. *Cannot find role* (When using React Testing Library) - - **Cause:** The React Testing Library query can't find the menu options if the Popper menu is set to `aria-disabled` after a selection is made. This error only seems to occur in unit tests—not browsers. - - **Fix:** Pass in the `{hidden: true}` option or change select's `appendTo` to `inline`. - - - -## Get help - -If you need support as you upgrade, the PatternFly team is here to help! Since this upgrade includes significant visual changes, please contact us with questions about styles or concerns with your UI. We'll always do our best to answer your questions, double-check your work, and connect you with the right people quickly. - - - - - -**Note:** If you use a custom solution to replicate PatternFly styling (without using PatternFly components), then your product will need to be re-skinned. This may be a large undertaking, so we encourage you to get help from the PatternFly team. diff --git a/packages/site/src/helpers/capitalize.js b/packages/site/src/helpers/capitalize.js new file mode 100644 index 0000000000..53509ae7c7 --- /dev/null +++ b/packages/site/src/helpers/capitalize.js @@ -0,0 +1,3 @@ +export function capitalize(input) { + return input[0].toUpperCase() + input.substring(1); +} diff --git a/packages/site/wrangler.jsonc b/packages/site/wrangler.jsonc new file mode 100644 index 0000000000..781f316e3c --- /dev/null +++ b/packages/site/wrangler.jsonc @@ -0,0 +1,14 @@ +{ + "$schema": "node_modules/wrangler/config-schema.json", + "name": "patternfly-org", + "main": "./dist/_worker.js/index.js", + "compatibility_date": "2025-06-17", + "compatibility_flags": ["nodejs_compat"], + "assets": { + "binding": "ASSETS", + "directory": "./dist" + }, + "observability": { + "enabled": true + } + } diff --git a/yarn.lock b/yarn.lock index 0a8c3b5e78..a9a453acf7 100644 --- a/yarn.lock +++ b/yarn.lock @@ -31,6 +31,22 @@ __metadata: languageName: node linkType: hard +"@astrojs/cloudflare@npm:^12.5.4": + version: 12.6.0 + resolution: "@astrojs/cloudflare@npm:12.6.0" + dependencies: + "@astrojs/internal-helpers": "npm:0.6.1" + "@astrojs/underscore-redirects": "npm:1.0.0" + "@cloudflare/workers-types": "npm:^4.20250507.0" + tinyglobby: "npm:^0.2.13" + vite: "npm:^6.3.5" + wrangler: "npm:^4.14.1" + peerDependencies: + astro: ^5.0.0 + checksum: 10c0/a77f2ea556499e6a3e701ae98341c1703bc0c5eb5bf46ea4a83f01a38781cde4ec00f2c758215da45e8ad8150c9f3ede55ead6c83e51fbf56b21ff4a18ff5f11 + languageName: node + linkType: hard + "@astrojs/compiler@npm:^2.10.3, @astrojs/compiler@npm:^2.11.0": version: 2.12.0 resolution: "@astrojs/compiler@npm:2.12.0" @@ -38,6 +54,13 @@ __metadata: languageName: node linkType: hard +"@astrojs/compiler@npm:^2.12.2": + version: 2.12.2 + resolution: "@astrojs/compiler@npm:2.12.2" + checksum: 10c0/3e63055117010247a9fa6d2c8de1263b3e6f3c089bb6b3cddea76bf3eea6b62b77359c89950e6d048d860874a79521ca2c0cc734af1ee59c7568e01e76a4df10 + languageName: node + linkType: hard + "@astrojs/internal-helpers@npm:0.6.1": version: 0.6.1 resolution: "@astrojs/internal-helpers@npm:0.6.1" @@ -139,7 +162,7 @@ __metadata: languageName: node linkType: hard -"@astrojs/mdx@npm:^4.2.6": +"@astrojs/mdx@npm:^4.3.0": version: 4.3.0 resolution: "@astrojs/mdx@npm:4.3.0" dependencies: @@ -162,7 +185,7 @@ __metadata: languageName: node linkType: hard -"@astrojs/node@npm:^9.1.3": +"@astrojs/node@npm:^9.2.2": version: 9.2.2 resolution: "@astrojs/node@npm:9.2.2" dependencies: @@ -193,7 +216,7 @@ __metadata: languageName: node linkType: hard -"@astrojs/react@npm:^4.2.1": +"@astrojs/react@npm:^4.3.0": version: 4.3.0 resolution: "@astrojs/react@npm:4.3.0" dependencies: @@ -239,6 +262,13 @@ __metadata: languageName: node linkType: hard +"@astrojs/underscore-redirects@npm:1.0.0": + version: 1.0.0 + resolution: "@astrojs/underscore-redirects@npm:1.0.0" + checksum: 10c0/f2554e1ae0d605b1eca54ffb67269eff6ff58fcdaf34ecd9ba0c0f6751c9e0fdb806c896b6b4e1adb47e291f18d7b7b4dc554334a45c231d5d1da25d73524e8a + languageName: node + linkType: hard + "@astrojs/yaml2ts@npm:^0.2.2": version: 0.2.2 resolution: "@astrojs/yaml2ts@npm:0.2.2" @@ -1965,6 +1995,79 @@ __metadata: languageName: node linkType: hard +"@cloudflare/kv-asset-handler@npm:0.4.0": + version: 0.4.0 + resolution: "@cloudflare/kv-asset-handler@npm:0.4.0" + dependencies: + mime: "npm:^3.0.0" + checksum: 10c0/54273c796d9815294599d7958a1a4e342f5519a03cc24c9501cf24d8721de9dbb8c53262941acb0e058bd9e952f807e3e1caa3ae242a0eabc26b1d2caa9a26f6 + languageName: node + linkType: hard + +"@cloudflare/unenv-preset@npm:2.3.3": + version: 2.3.3 + resolution: "@cloudflare/unenv-preset@npm:2.3.3" + peerDependencies: + unenv: 2.0.0-rc.17 + workerd: ^1.20250508.0 + peerDependenciesMeta: + workerd: + optional: true + checksum: 10c0/2bd12ce921d5da7df74fa24bea016dab8c17cc65c5f5a1b39a985ba687bcd39885fbbffb90297135a311bcfb054422241b9988224bd2fc9a0f3eb0730d3cf402 + languageName: node + linkType: hard + +"@cloudflare/workerd-darwin-64@npm:1.20250617.0": + version: 1.20250617.0 + resolution: "@cloudflare/workerd-darwin-64@npm:1.20250617.0" + conditions: os=darwin & cpu=x64 + languageName: node + linkType: hard + +"@cloudflare/workerd-darwin-arm64@npm:1.20250617.0": + version: 1.20250617.0 + resolution: "@cloudflare/workerd-darwin-arm64@npm:1.20250617.0" + conditions: os=darwin & cpu=arm64 + languageName: node + linkType: hard + +"@cloudflare/workerd-linux-64@npm:1.20250617.0": + version: 1.20250617.0 + resolution: "@cloudflare/workerd-linux-64@npm:1.20250617.0" + conditions: os=linux & cpu=x64 + languageName: node + linkType: hard + +"@cloudflare/workerd-linux-arm64@npm:1.20250617.0": + version: 1.20250617.0 + resolution: "@cloudflare/workerd-linux-arm64@npm:1.20250617.0" + conditions: os=linux & cpu=arm64 + languageName: node + linkType: hard + +"@cloudflare/workerd-windows-64@npm:1.20250617.0": + version: 1.20250617.0 + resolution: "@cloudflare/workerd-windows-64@npm:1.20250617.0" + conditions: os=win32 & cpu=x64 + languageName: node + linkType: hard + +"@cloudflare/workers-types@npm:^4.20250507.0": + version: 4.20250701.0 + resolution: "@cloudflare/workers-types@npm:4.20250701.0" + checksum: 10c0/7d61a7415d5911a63f99f83fcdfe6108e631b7e1587602ad3af99fa7c705a3cf4966687d5ced7d582d54b7ad93402f0c7eb01554d693e0cdc5cd7fec79295793 + languageName: node + linkType: hard + +"@cspotcode/source-map-support@npm:0.8.1": + version: 0.8.1 + resolution: "@cspotcode/source-map-support@npm:0.8.1" + dependencies: + "@jridgewell/trace-mapping": "npm:0.3.9" + checksum: 10c0/05c5368c13b662ee4c122c7bfbe5dc0b613416672a829f3e78bc49a357a197e0218d6e74e7c66cfcd04e15a179acab080bd3c69658c9fbefd0e1ccd950a07fc6 + languageName: node + linkType: hard + "@dagrejs/dagre@npm:1.1.2": version: 1.1.2 resolution: "@dagrejs/dagre@npm:1.1.2" @@ -2308,6 +2411,13 @@ __metadata: languageName: node linkType: hard +"@fastify/busboy@npm:^2.0.0": + version: 2.1.1 + resolution: "@fastify/busboy@npm:2.1.1" + checksum: 10c0/6f8027a8cba7f8f7b736718b013f5a38c0476eea67034c94a0d3c375e2b114366ad4419e6a6fa7ffc2ef9c6d3e0435d76dd584a7a1cbac23962fda7650b579e3 + languageName: node + linkType: hard + "@gar/promisify@npm:^1.1.3": version: 1.1.3 resolution: "@gar/promisify@npm:1.1.3" @@ -2547,7 +2657,7 @@ __metadata: languageName: node linkType: hard -"@jridgewell/resolve-uri@npm:^3.1.0": +"@jridgewell/resolve-uri@npm:^3.0.3, @jridgewell/resolve-uri@npm:^3.1.0": version: 3.1.2 resolution: "@jridgewell/resolve-uri@npm:3.1.2" checksum: 10c0/d502e6fb516b35032331406d4e962c21fe77cdf1cbdb49c6142bcbd9e30507094b18972778a6e27cbad756209cfe34b1a27729e6fa08a2eb92b33943f680cf1e @@ -2585,6 +2695,16 @@ __metadata: languageName: node linkType: hard +"@jridgewell/trace-mapping@npm:0.3.9": + version: 0.3.9 + resolution: "@jridgewell/trace-mapping@npm:0.3.9" + dependencies: + "@jridgewell/resolve-uri": "npm:^3.0.3" + "@jridgewell/sourcemap-codec": "npm:^1.4.10" + checksum: 10c0/fa425b606d7c7ee5bfa6a31a7b050dd5814b4082f318e0e4190f991902181b4330f43f4805db1dd4f2433fd0ed9cc7a7b9c2683f1deeab1df1b0a98b1e24055b + languageName: node + linkType: hard + "@jridgewell/trace-mapping@npm:^0.3.20, @jridgewell/trace-mapping@npm:^0.3.24, @jridgewell/trace-mapping@npm:^0.3.25": version: 0.3.25 resolution: "@jridgewell/trace-mapping@npm:0.3.25" @@ -3748,14 +3868,15 @@ __metadata: languageName: node linkType: hard -"@patternfly/patternfly-doc-core@npm:^1.9.0": - version: 1.9.0 - resolution: "@patternfly/patternfly-doc-core@npm:1.9.0" +"@patternfly/patternfly-doc-core@npm:latest": + version: 1.11.1 + resolution: "@patternfly/patternfly-doc-core@npm:1.11.1" dependencies: "@astrojs/check": "npm:^0.9.4" - "@astrojs/mdx": "npm:^4.2.6" - "@astrojs/node": "npm:^9.1.3" - "@astrojs/react": "npm:^4.2.1" + "@astrojs/cloudflare": "npm:^12.5.4" + "@astrojs/mdx": "npm:^4.3.0" + "@astrojs/node": "npm:^9.2.2" + "@astrojs/react": "npm:^4.3.0" "@nanostores/react": "npm:^0.8.0" "@patternfly/ast-helpers": "npm:1.4.0-alpha.190" "@patternfly/patternfly": "npm:^6.0.0" @@ -3767,7 +3888,7 @@ __metadata: "@patternfly/react-tokens": "npm:^6.0.0" "@types/react": "npm:^18.3.12" "@types/react-dom": "npm:^18.3.1" - astro: "npm:^5.4.1" + astro: "npm:^5.9.3" change-case: "npm:5.4.4" commander: "npm:^13.1.0" glob: "npm:^11.0.1" @@ -3780,7 +3901,7 @@ __metadata: typescript: "npm:^5.6.3" bin: patternfly-doc-core: dist/cli/cli.js - checksum: 10c0/a44348dc3955c28cbe14ee5b1a779d50d368d411feac9457de2b930fe850976166f87961b14e8782640180bdb347929b8c3c7ea9433ee2eb414a31e0a0f8a74c + checksum: 10c0/91297eeace5c043b6b764b6fb21739e12bf558260b8804ebbeae617176d76ae34ba13f1cdaeb56b20c1ef3f6fded80622cf9acc7f1d3c0f9f99524aac97c31fd languageName: node linkType: hard @@ -6105,13 +6226,22 @@ __metadata: languageName: node linkType: hard -"acorn-walk@npm:^8.0.0": +"acorn-walk@npm:8.3.2, acorn-walk@npm:^8.0.0": version: 8.3.2 resolution: "acorn-walk@npm:8.3.2" checksum: 10c0/7e2a8dad5480df7f872569b9dccff2f3da7e65f5353686b1d6032ab9f4ddf6e3a2cb83a9b52cf50b1497fd522154dda92f0abf7153290cc79cd14721ff121e52 languageName: node linkType: hard +"acorn@npm:8.14.0": + version: 8.14.0 + resolution: "acorn@npm:8.14.0" + bin: + acorn: bin/acorn + checksum: 10c0/6d4ee461a7734b2f48836ee0fbb752903606e576cc100eb49340295129ca0b452f3ba91ddd4424a1d4406a98adfb2ebb6bd0ff4c49d7a0930c10e462719bbfd7 + languageName: node + linkType: hard + "acorn@npm:^8.0.0, acorn@npm:^8.14.1": version: 8.14.1 resolution: "acorn@npm:8.14.1" @@ -6508,6 +6638,15 @@ __metadata: languageName: node linkType: hard +"as-table@npm:^1.0.36": + version: 1.0.55 + resolution: "as-table@npm:1.0.55" + dependencies: + printable-characters: "npm:^1.0.42" + checksum: 10c0/8c5693a84621fe53c62fcad6b779dc55c5caf4d43b8e67077964baea4a337769ef53f590d7395c806805b4ef1a391b614ba9acdee19b2ca4309ddedaf13894e6 + languageName: node + linkType: hard + "asn1@npm:~0.2.3": version: 0.2.6 resolution: "asn1@npm:0.2.6" @@ -6560,14 +6699,14 @@ __metadata: languageName: node linkType: hard -"astro@npm:^5.4.1": - version: 5.8.1 - resolution: "astro@npm:5.8.1" +"astro@npm:^5.7.13": + version: 5.7.13 + resolution: "astro@npm:5.7.13" dependencies: "@astrojs/compiler": "npm:^2.11.0" "@astrojs/internal-helpers": "npm:0.6.1" - "@astrojs/markdown-remark": "npm:6.3.2" - "@astrojs/telemetry": "npm:3.3.0" + "@astrojs/markdown-remark": "npm:6.3.1" + "@astrojs/telemetry": "npm:3.2.1" "@capsizecss/unpack": "npm:^2.4.0" "@oslojs/encoding": "npm:^1.1.0" "@rollup/pluginutils": "npm:^5.1.4" @@ -6594,7 +6733,6 @@ __metadata: github-slugger: "npm:^2.0.0" html-escaper: "npm:3.0.3" http-cache-semantics: "npm:^4.1.1" - import-meta-resolve: "npm:^4.1.0" js-yaml: "npm:^4.1.0" kleur: "npm:^4.1.5" magic-string: "npm:^0.30.17" @@ -6631,18 +6769,18 @@ __metadata: optional: true bin: astro: astro.js - checksum: 10c0/8425d9f7e09266cf841ac0ea6e77dd4038074b66eb3ab7aa2ac0f10b5ff15920b9d3f7fbf5288cdc9478a26420a4ce8983493de585df546245648a4c26247e02 + checksum: 10c0/4a057967d5d30a6fb85710912386a0d3cdf0ffececaa966685a38f0d5f10de66ba4db796eb4dc585f290ed322ded09f50b6e237ac7110022ec562a98193a4265 languageName: node linkType: hard -"astro@npm:^5.7.13": - version: 5.7.13 - resolution: "astro@npm:5.7.13" +"astro@npm:^5.9.3": + version: 5.10.2 + resolution: "astro@npm:5.10.2" dependencies: - "@astrojs/compiler": "npm:^2.11.0" + "@astrojs/compiler": "npm:^2.12.2" "@astrojs/internal-helpers": "npm:0.6.1" - "@astrojs/markdown-remark": "npm:6.3.1" - "@astrojs/telemetry": "npm:3.2.1" + "@astrojs/markdown-remark": "npm:6.3.2" + "@astrojs/telemetry": "npm:3.3.0" "@capsizecss/unpack": "npm:^2.4.0" "@oslojs/encoding": "npm:^1.1.0" "@rollup/pluginutils": "npm:^5.1.4" @@ -6669,6 +6807,7 @@ __metadata: github-slugger: "npm:^2.0.0" html-escaper: "npm:3.0.3" http-cache-semantics: "npm:^4.1.1" + import-meta-resolve: "npm:^4.1.0" js-yaml: "npm:^4.1.0" kleur: "npm:^4.1.5" magic-string: "npm:^0.30.17" @@ -6705,7 +6844,7 @@ __metadata: optional: true bin: astro: astro.js - checksum: 10c0/4a057967d5d30a6fb85710912386a0d3cdf0ffececaa966685a38f0d5f10de66ba4db796eb4dc585f290ed322ded09f50b6e237ac7110022ec562a98193a4265 + checksum: 10c0/99b2ee606b39615a00e71a240d95b9fdfd96c59393b0541017fd677ee553288e233d95971fe2e2771548c320d1c0c62e3cc344d2c5035117f5af8177ebe0162d languageName: node linkType: hard @@ -7039,6 +7178,13 @@ __metadata: languageName: node linkType: hard +"blake3-wasm@npm:2.1.5": + version: 2.1.5 + resolution: "blake3-wasm@npm:2.1.5" + checksum: 10c0/5dc729d8e3a9d1d7ab016b36cdda264a327ada0239716df48435163e11d2bf6df25d6e421655a1f52649098ae49555268a654729b7d02768f77c571ab37ef814 + languageName: node + linkType: hard + "blob-to-buffer@npm:^1.2.8": version: 1.2.9 resolution: "blob-to-buffer@npm:1.2.9" @@ -8458,6 +8604,13 @@ __metadata: languageName: node linkType: hard +"cookie@npm:^0.7.1": + version: 0.7.2 + resolution: "cookie@npm:0.7.2" + checksum: 10c0/9596e8ccdbf1a3a88ae02cf5ee80c1c50959423e1022e4e60b91dd87c622af1da309253d8abdb258fb5e3eacb4f08e579dc58b4897b8087574eee0fd35dfa5d2 + languageName: node + linkType: hard + "cookie@npm:^1.0.2": version: 1.0.2 resolution: "cookie@npm:1.0.2" @@ -9124,6 +9277,13 @@ __metadata: languageName: node linkType: hard +"data-uri-to-buffer@npm:^2.0.0": + version: 2.0.2 + resolution: "data-uri-to-buffer@npm:2.0.2" + checksum: 10c0/341b6191ed65fa453e97a6d44db06082121ebc2ef3e6e096dfb6a1ebbc75e8be39d4199a5b4dba0f0efc43f2a3b2bcc276d85cf1407eba880eb09ebf17c3c31e + languageName: node + linkType: hard + "data-uri-to-buffer@npm:^6.0.2": version: 6.0.2 resolution: "data-uri-to-buffer@npm:6.0.2" @@ -10016,7 +10176,7 @@ __metadata: languageName: node linkType: hard -"esbuild@npm:^0.25.0, esbuild@npm:~0.25.0": +"esbuild@npm:0.25.4, esbuild@npm:^0.25.0, esbuild@npm:~0.25.0": version: 0.25.4 resolution: "esbuild@npm:0.25.4" dependencies: @@ -10357,6 +10517,13 @@ __metadata: languageName: node linkType: hard +"exit-hook@npm:2.2.1": + version: 2.2.1 + resolution: "exit-hook@npm:2.2.1" + checksum: 10c0/0803726d1b60aade6afd10c73e5a7e1bf256ac9bee78362a88e91a4f735e8c67899f2853ddc613072c05af07bbb067a9978a740e614db1aeef167d50c6dc5c09 + languageName: node + linkType: hard + "expand-template@npm:^2.0.3": version: 2.0.3 resolution: "expand-template@npm:2.0.3" @@ -10419,6 +10586,13 @@ __metadata: languageName: node linkType: hard +"exsolve@npm:^1.0.4": + version: 1.0.7 + resolution: "exsolve@npm:1.0.7" + checksum: 10c0/4479369d0bd84bb7e0b4f5d9bc18d26a89b6dbbbccd73f9d383d14892ef78ddbe159e01781055342f83dc00ebe90044036daf17ddf55cc21e2cac6609aa15631 + languageName: node + linkType: hard + "extend-shallow@npm:^2.0.1": version: 2.0.1 resolution: "extend-shallow@npm:2.0.1" @@ -11244,6 +11418,16 @@ __metadata: languageName: node linkType: hard +"get-source@npm:^2.0.12": + version: 2.0.12 + resolution: "get-source@npm:2.0.12" + dependencies: + data-uri-to-buffer: "npm:^2.0.0" + source-map: "npm:^0.6.1" + checksum: 10c0/b1db46d28902344fd9407e1f0ed0b8f3a85cb4650f85ba8cee9c0b422fc75118172f12f735706e2c6e034617b13a2fbc5266e7fab617ecb184f0cee074b9dd3e + languageName: node + linkType: hard + "get-stream@npm:6.0.0": version: 6.0.0 resolution: "get-stream@npm:6.0.0" @@ -11440,7 +11624,7 @@ __metadata: languageName: node linkType: hard -"glob-to-regexp@npm:^0.4.1": +"glob-to-regexp@npm:0.4.1, glob-to-regexp@npm:^0.4.1": version: 0.4.1 resolution: "glob-to-regexp@npm:0.4.1" checksum: 10c0/0486925072d7a916f052842772b61c3e86247f0a80cc0deb9b5a3e8a1a9faad5b04fb6f58986a09f34d3e96cd2a22a24b7e9882fb1cf904c31e9a310de96c429 @@ -15303,6 +15487,15 @@ __metadata: languageName: node linkType: hard +"mime@npm:^3.0.0": + version: 3.0.0 + resolution: "mime@npm:3.0.0" + bin: + mime: cli.js + checksum: 10c0/402e792a8df1b2cc41cb77f0dcc46472b7944b7ec29cb5bbcd398624b6b97096728f1239766d3fdeb20551dd8d94738344c195a6ea10c4f906eb0356323b0531 + languageName: node + linkType: hard + "mimer@npm:^0.3.2": version: 0.3.2 resolution: "mimer@npm:0.3.2" @@ -15351,6 +15544,28 @@ __metadata: languageName: node linkType: hard +"miniflare@npm:4.20250617.4": + version: 4.20250617.4 + resolution: "miniflare@npm:4.20250617.4" + dependencies: + "@cspotcode/source-map-support": "npm:0.8.1" + acorn: "npm:8.14.0" + acorn-walk: "npm:8.3.2" + exit-hook: "npm:2.2.1" + glob-to-regexp: "npm:0.4.1" + sharp: "npm:^0.33.5" + stoppable: "npm:1.1.0" + undici: "npm:^5.28.5" + workerd: "npm:1.20250617.0" + ws: "npm:8.18.0" + youch: "npm:3.3.4" + zod: "npm:3.22.3" + bin: + miniflare: bootstrap.js + checksum: 10c0/4ac2036c111b4f502a76f1cc8e463caf052bf5c754a9dc0129dc71c8088e7ff0e12f1bec6d548cbf2cd2ca73a9f89f0fe3887119cfd5295d6690b6d32ac1549a + languageName: node + linkType: hard + "minimalistic-assert@npm:^1.0.0": version: 1.0.1 resolution: "minimalistic-assert@npm:1.0.1" @@ -15845,6 +16060,15 @@ __metadata: languageName: node linkType: hard +"mustache@npm:^4.2.0": + version: 4.2.0 + resolution: "mustache@npm:4.2.0" + bin: + mustache: bin/mustache + checksum: 10c0/1f8197e8a19e63645a786581d58c41df7853da26702dbc005193e2437c98ca49b255345c173d50c08fe4b4dbb363e53cb655ecc570791f8deb09887248dd34a2 + languageName: node + linkType: hard + "mute-stream@npm:0.0.7": version: 0.0.7 resolution: "mute-stream@npm:0.0.7" @@ -16616,7 +16840,7 @@ __metadata: languageName: node linkType: hard -"ohash@npm:^2.0.0": +"ohash@npm:^2.0.0, ohash@npm:^2.0.11": version: 2.0.11 resolution: "ohash@npm:2.0.11" checksum: 10c0/d07c8d79cc26da082c1a7c8d5b56c399dd4ed3b2bd069fcae6bae78c99a9bcc3ad813b1e1f49ca2f335292846d689c6141a762cf078727d2302a33d414e69c79 @@ -17403,6 +17627,13 @@ __metadata: languageName: node linkType: hard +"path-to-regexp@npm:6.3.0": + version: 6.3.0 + resolution: "path-to-regexp@npm:6.3.0" + checksum: 10c0/73b67f4638b41cde56254e6354e46ae3a2ebc08279583f6af3d96fe4664fc75788f74ed0d18ca44fa4a98491b69434f9eee73b97bb5314bd1b5adb700f5c18d6 + languageName: node + linkType: hard + "path-type@npm:^3.0.0": version: 3.0.0 resolution: "path-type@npm:3.0.0" @@ -17419,6 +17650,13 @@ __metadata: languageName: node linkType: hard +"pathe@npm:^2.0.3": + version: 2.0.3 + resolution: "pathe@npm:2.0.3" + checksum: 10c0/c118dc5a8b5c4166011b2b70608762e260085180bb9e33e80a50dcdb1e78c010b1624f4280c492c92b05fc276715a4c357d1f9edc570f8f1b3d90b6839ebaca1 + languageName: node + linkType: hard + "patternfly-org-workspace@workspace:.": version: 0.0.0-use.local resolution: "patternfly-org-workspace@workspace:." @@ -17797,6 +18035,13 @@ __metadata: languageName: node linkType: hard +"printable-characters@npm:^1.0.42": + version: 1.0.42 + resolution: "printable-characters@npm:1.0.42" + checksum: 10c0/7c94d94c6041a37c385af770c7402ad5a2e8a3429ca4d2505a9f19fde39bac9a8fd1edfbfa02f1eae5b4b0f3536b6b8ee6c84621f7c0fcb41476b2df6ee20e4b + languageName: node + linkType: hard + "prismjs@npm:^1.27.0": version: 1.29.0 resolution: "prismjs@npm:1.29.0" @@ -19969,7 +20214,7 @@ __metadata: languageName: node linkType: hard -"sharp@npm:^0.33.3": +"sharp@npm:^0.33.3, sharp@npm:^0.33.5": version: 0.33.5 resolution: "sharp@npm:0.33.5" dependencies: @@ -20203,9 +20448,11 @@ __metadata: version: 0.0.0-use.local resolution: "site@workspace:packages/site" dependencies: - "@patternfly/patternfly-doc-core": "npm:^1.9.0" + "@patternfly/patternfly-doc-core": "npm:latest" + "@patternfly/react-icons": "npm:^6.2.2" astro: "npm:^5.7.13" tsx: "npm:^4.19.0" + wrangler: "npm:^4.20.0" languageName: unknown linkType: soft @@ -20554,6 +20801,16 @@ __metadata: languageName: node linkType: hard +"stacktracey@npm:^2.1.8": + version: 2.1.8 + resolution: "stacktracey@npm:2.1.8" + dependencies: + as-table: "npm:^1.0.36" + get-source: "npm:^2.0.12" + checksum: 10c0/e17357d0a532d303138899b910ab660572009a1f4cde1cbf73b99416957a2378e6e1c791b3c31b043cf7c5f37647da1dd114e66c9203f23c65b34f783665405b + languageName: node + linkType: hard + "state-local@npm:^1.0.6": version: 1.0.7 resolution: "state-local@npm:1.0.7" @@ -20582,6 +20839,13 @@ __metadata: languageName: node linkType: hard +"stoppable@npm:1.1.0": + version: 1.1.0 + resolution: "stoppable@npm:1.1.0" + checksum: 10c0/ba91b65e6442bf6f01ce837a727ece597a977ed92a05cb9aea6bf446c5e0dcbccc28f31b793afa8aedd8f34baaf3335398d35f903938d5493f7fbe386a1e090e + languageName: node + linkType: hard + "stream-each@npm:^1.1.0": version: 1.2.3 resolution: "stream-each@npm:1.2.3" @@ -21707,6 +21971,28 @@ __metadata: languageName: node linkType: hard +"undici@npm:^5.28.5": + version: 5.29.0 + resolution: "undici@npm:5.29.0" + dependencies: + "@fastify/busboy": "npm:^2.0.0" + checksum: 10c0/e4e4d631ca54ee0ad82d2e90e7798fa00a106e27e6c880687e445cc2f13b4bc87c5eba2a88c266c3eecffb18f26e227b778412da74a23acc374fca7caccec49b + languageName: node + linkType: hard + +"unenv@npm:2.0.0-rc.17": + version: 2.0.0-rc.17 + resolution: "unenv@npm:2.0.0-rc.17" + dependencies: + defu: "npm:^6.1.4" + exsolve: "npm:^1.0.4" + ohash: "npm:^2.0.11" + pathe: "npm:^2.0.3" + ufo: "npm:^1.6.1" + checksum: 10c0/029ae051cf2f79d3946976b32010a6aaaa87c8783a01dc088046247e34cb40962e19d96b465df5728e6ed262da89df342c1db1d05c2c28851825a74b93b90039 + languageName: node + linkType: hard + "unfetch@npm:^3.1.1": version: 3.1.2 resolution: "unfetch@npm:3.1.2" @@ -23615,6 +23901,60 @@ __metadata: languageName: node linkType: hard +"workerd@npm:1.20250617.0": + version: 1.20250617.0 + resolution: "workerd@npm:1.20250617.0" + dependencies: + "@cloudflare/workerd-darwin-64": "npm:1.20250617.0" + "@cloudflare/workerd-darwin-arm64": "npm:1.20250617.0" + "@cloudflare/workerd-linux-64": "npm:1.20250617.0" + "@cloudflare/workerd-linux-arm64": "npm:1.20250617.0" + "@cloudflare/workerd-windows-64": "npm:1.20250617.0" + dependenciesMeta: + "@cloudflare/workerd-darwin-64": + optional: true + "@cloudflare/workerd-darwin-arm64": + optional: true + "@cloudflare/workerd-linux-64": + optional: true + "@cloudflare/workerd-linux-arm64": + optional: true + "@cloudflare/workerd-windows-64": + optional: true + bin: + workerd: bin/workerd + checksum: 10c0/3f3342840a4d439232f86d88019601071f18470c37582a2b7de1273346785aa090d0259e674be1f4d59f898d38d5b6d276da2cc4625de1609e0966e9405bdf7a + languageName: node + linkType: hard + +"wrangler@npm:^4.14.1, wrangler@npm:^4.20.0": + version: 4.22.0 + resolution: "wrangler@npm:4.22.0" + dependencies: + "@cloudflare/kv-asset-handler": "npm:0.4.0" + "@cloudflare/unenv-preset": "npm:2.3.3" + blake3-wasm: "npm:2.1.5" + esbuild: "npm:0.25.4" + fsevents: "npm:~2.3.2" + miniflare: "npm:4.20250617.4" + path-to-regexp: "npm:6.3.0" + unenv: "npm:2.0.0-rc.17" + workerd: "npm:1.20250617.0" + peerDependencies: + "@cloudflare/workers-types": ^4.20250617.0 + dependenciesMeta: + fsevents: + optional: true + peerDependenciesMeta: + "@cloudflare/workers-types": + optional: true + bin: + wrangler: bin/wrangler.js + wrangler2: bin/wrangler.js + checksum: 10c0/a1d5deab6f600d1e3807c94ca5f0fbe1884a34d76ec0d2880c1fb2f9125a3b4e8607502bf8c06cc6ef960ea85d93a587f00a36b5e4e479b8daffd3f5237e053c + languageName: node + linkType: hard + "wrap-ansi-cjs@npm:wrap-ansi@^7.0.0, wrap-ansi@npm:^7.0.0": version: 7.0.0 resolution: "wrap-ansi@npm:7.0.0" @@ -23722,33 +24062,33 @@ __metadata: languageName: node linkType: hard -"ws@npm:^7.3.1": - version: 7.5.9 - resolution: "ws@npm:7.5.9" +"ws@npm:8.18.0, ws@npm:^8.18.0": + version: 8.18.0 + resolution: "ws@npm:8.18.0" peerDependencies: bufferutil: ^4.0.1 - utf-8-validate: ^5.0.2 + utf-8-validate: ">=5.0.2" peerDependenciesMeta: bufferutil: optional: true utf-8-validate: optional: true - checksum: 10c0/aec4ef4eb65821a7dde7b44790f8699cfafb7978c9b080f6d7a98a7f8fc0ce674c027073a78574c94786ba7112cc90fa2cc94fc224ceba4d4b1030cff9662494 + checksum: 10c0/25eb33aff17edcb90721ed6b0eb250976328533ad3cd1a28a274bd263682e7296a6591ff1436d6cbc50fa67463158b062f9d1122013b361cec99a05f84680e06 languageName: node linkType: hard -"ws@npm:^8.18.0": - version: 8.18.0 - resolution: "ws@npm:8.18.0" +"ws@npm:^7.3.1": + version: 7.5.9 + resolution: "ws@npm:7.5.9" peerDependencies: bufferutil: ^4.0.1 - utf-8-validate: ">=5.0.2" + utf-8-validate: ^5.0.2 peerDependenciesMeta: bufferutil: optional: true utf-8-validate: optional: true - checksum: 10c0/25eb33aff17edcb90721ed6b0eb250976328533ad3cd1a28a274bd263682e7296a6591ff1436d6cbc50fa67463158b062f9d1122013b361cec99a05f84680e06 + checksum: 10c0/aec4ef4eb65821a7dde7b44790f8699cfafb7978c9b080f6d7a98a7f8fc0ce674c027073a78574c94786ba7112cc90fa2cc94fc224ceba4d4b1030cff9662494 languageName: node linkType: hard @@ -23999,6 +24339,17 @@ __metadata: languageName: node linkType: hard +"youch@npm:3.3.4": + version: 3.3.4 + resolution: "youch@npm:3.3.4" + dependencies: + cookie: "npm:^0.7.1" + mustache: "npm:^4.2.0" + stacktracey: "npm:^2.1.8" + checksum: 10c0/ab573c7dccebdaf2d6b084d262d5bfb22ad5c049fb1ad3e2d6a840af851042dd3a8a072665c5a5ee73c75bbc1618fbc08f1371ac896e54556bced0ddf996b026 + languageName: node + linkType: hard + "zod-to-json-schema@npm:^3.24.5": version: 3.24.5 resolution: "zod-to-json-schema@npm:3.24.5" @@ -24018,6 +24369,13 @@ __metadata: languageName: node linkType: hard +"zod@npm:3.22.3": + version: 3.22.3 + resolution: "zod@npm:3.22.3" + checksum: 10c0/cb4b24aed7dec98552eb9042e88cbd645455bf2830e5704174d2da96f554dabad4630e3b4f6623e1b6562b9eaa43535a37b7f2011f29b8d8e9eabe1ddf3b656b + languageName: node + linkType: hard + "zod@npm:3.23.8": version: 3.23.8 resolution: "zod@npm:3.23.8"