Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
49 commits
Select commit Hold shift + click to select a range
b0d346d
feat: Migrate the bold folder
im3dabasia Jun 23, 2026
c81beb7
feat: Migrate the code folder
im3dabasia Jun 23, 2026
b87fc46
feat: Migrate italic folder ot TS
im3dabasia Jun 23, 2026
06291ab
feat: Migrate keyboard package to TS
im3dabasia Jun 23, 2026
35c5fca
feat: Migrate language folder to TS
im3dabasia Jun 24, 2026
3827a0e
feat: Migrate nbsp folder to TS
im3dabasia Jun 24, 2026
536a44d
feat: Migrate strikethrough folder to TS
im3dabasia Jun 24, 2026
183de84
feat: Update RichTextFormat to include title
im3dabasia Jun 24, 2026
c68b791
feat: Migrate other folders to TS
im3dabasia Jun 25, 2026
384fa66
feat: Migrate image and math folders to TS
im3dabasia Jun 25, 2026
0ad4740
feat: Migrate link folder
im3dabasia Jun 29, 2026
794ed93
feat: Migrate link folder index.tsx
im3dabasia Jun 29, 2026
ae1f113
fix: Feedbacks from ai
im3dabasia Jun 30, 2026
31a133b
fix: Standardize the interface/types declaration in types.ts
im3dabasia Jun 30, 2026
735ff22
fix: linkFormat ts issue
im3dabasia Jun 30, 2026
e40146b
fix: Static lint failing errors
im3dabasia Jun 30, 2026
1a90f08
fix: Lint error with split()
im3dabasia Jun 30, 2026
7259a02
fix: CI errors
im3dabasia Jun 30, 2026
b76e065
fix: TS issues
im3dabasia Aug 19, 2026
6366cac
fix: Feedbacks related to ts-ignore and RichTextFormat
im3dabasia Aug 19, 2026
0d5a4e7
fix: Feedbacks for ReactNode in bold file
im3dabasia Aug 19, 2026
5459d36
fix: casting issue for linkFormat arg in applyFormat function
im3dabasia Aug 19, 2026
b33390c
fix: Remove unsafe alias
im3dabasia Aug 19, 2026
d06a6bc
fix: Avoid use of any in useAchor hook
im3dabasia Aug 19, 2026
f88357c
fix: any type in math
im3dabasia Aug 19, 2026
c137148
Merge branch 'trunk' into try/migrate-format-library-package
im3dabasia Aug 19, 2026
b005a2d
fix: tsconfig related changes
im3dabasia Aug 19, 2026
c78eac6
fix: Remove suppressions
im3dabasia Aug 19, 2026
c0cb642
Revert "fix: Remove suppressions"
im3dabasia Aug 19, 2026
a8e0a16
fix: Remove suppressions
im3dabasia Aug 19, 2026
7cbc258
Merge branch 'trunk' into try/migrate-format-library-package
im3dabasia Sep 1, 2026
1ecf45d
Merge branch 'trunk' into try/migrate-format-library-package
im3dabasia Sep 1, 2026
f0191cc
fix: regression in split in inline:216
im3dabasia Sep 1, 2026
17848bd
fix: split related regression bugs
im3dabasia Sep 1, 2026
ba8d3c0
fix: docs in registerFormatType
im3dabasia Sep 1, 2026
a4519e7
fix: 5 alais prop types FormatEditProps
im3dabasia Sep 1, 2026
f142995
fix: Reference LinkFormatAttributes in types.ts
im3dabasia Sep 1, 2026
4d6a260
fix: EditImageProps type and use InlineImageUIProps
im3dabasia Sep 1, 2026
1e0c73e
fix: types in partialRight, removed it and sorted walkToStart and wal…
im3dabasia Sep 1, 2026
51d6fe4
fix: Restore the doc comment for createLinkFormat function and LinkFo…
im3dabasia Sep 1, 2026
144e824
fix: Add CSSClassesSettingProps type and remove noised comments in CS…
im3dabasia Sep 1, 2026
930c87d
fix: Minor feedbacks related to type casting
im3dabasia Sep 1, 2026
be47383
fix: Add changelogs and update the type exportations in package.json
im3dabasia Sep 1, 2026
a7670d9
fix: Rename non tsx files to ts
im3dabasia Sep 1, 2026
5913bad
fix: Immediately show inlineui popover by removing latexToMathML
im3dabasia Sep 1, 2026
512db17
fix: Remove activeAttributes prop as it is unused in InlineColorUI
im3dabasia Sep 1, 2026
7e9e7bf
fix: Non blocking feedbacks
im3dabasia Sep 1, 2026
590f6f3
fix: Remove unused title in the applyFormat
im3dabasia Sep 1, 2026
2283510
fix: Add early return if splitValue is not passed
im3dabasia Sep 1, 2026
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 3 additions & 0 deletions packages/block-editor/src/components/link-control/index.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -88,11 +88,14 @@ import normalizeUrl from './normalize-url';
* @property {boolean=} forceIsEditingLink If passed as either `true` or `false`, controls the
* internal editing state of the component to respective
* show or not show the URL input field.
* @property {string=} searchInputPlaceholder Placeholder text for the search input.
* @property {WPLinkControlValue=} value Current link value.
* @property {WPLinkControlOnChangeProp=} onChange Value change handler, called with the updated value if
* the user selects a new link or updates settings.
* @property {Function=} onInputChange Callback fired when the search input value changes.
* Use this for observation only (e.g., to track search state).
* @property {Function=} onRemove Callback invoked when the link is removed.
* @property {Function=} onCancel Callback invoked when editing is cancelled.
* @property {string=} inputValue Initial value for the search input (uncontrolled).
* @property {boolean=} noDirectEntry Whether to allow turning a URL-like search query directly into a link.
* @property {boolean=} showSuggestions Whether to present suggestions when typing the URL.
Expand Down
1 change: 1 addition & 0 deletions packages/format-library/CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@
### Internal

- Use the `.jsx` extension for JavaScript source files that contain JSX ([#80990](https://github.com/WordPress/gutenberg/pull/80990)).
- Migrate the package to TypeScript ([#79486](https://github.com/WordPress/gutenberg/pull/79486)).

## 5.54.0 (2026-08-26)

Expand Down
2 changes: 2 additions & 0 deletions packages/format-library/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -34,12 +34,14 @@
"module": "build-module/index.mjs",
"exports": {
".": {
"types": "./build-types/index.d.ts",
"import": "./build-module/index.mjs",
"require": "./build/index.cjs"
},
"./package.json": "./package.json"
},
"wpScript": true,
"types": "build-types/index.d.ts",
"dependencies": {
"@wordpress/a11y": "file:../a11y",
"@wordpress/base-styles": "file:../base-styles",
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,8 +4,10 @@ import {
RichTextToolbarButton,
RichTextShortcut,
__unstableRichTextInputEvent,
// @ts-expect-error Block Editor not fully typed yet.
} from '@wordpress/block-editor';
import { formatBold } from '@wordpress/icons';
import type { FormatEditWithVisibilityProps } from '../types';

const name = 'core/bold';
const title = __( 'Bold' );
Expand All @@ -15,13 +17,19 @@ export const bold = {
title,
tagName: 'strong',
className: null,
edit( { isActive, value, onChange, onFocus, isVisible = true } ) {
edit( {
isActive,
value,
onChange,
onFocus,
isVisible = true,
}: FormatEditWithVisibilityProps ): React.ReactNode {
function onToggle() {
onChange( toggleFormat( value, { type: name, title } ) );
}

function onClick() {
onChange( toggleFormat( value, { type: name } ) );
onChange( toggleFormat( value, { type: name, title } ) );
onFocus();
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,8 +3,11 @@ import { toggleFormat, remove, applyFormat } from '@wordpress/rich-text';
import {
RichTextToolbarButton,
RichTextShortcut,
// @ts-expect-error Block Editor not fully typed yet.
} from '@wordpress/block-editor';
import { code as codeIcon } from '@wordpress/icons';
import type { RichTextValue } from '@wordpress/rich-text';
import type { FormatEditProps } from '../types';

const name = 'core/code';
const title = __( 'Inline code' );
Expand All @@ -14,7 +17,7 @@ export const code = {
title,
tagName: 'code',
className: null,
__unstableInputRule( value ) {
__unstableInputRule( value: RichTextValue ): RichTextValue {
const BACKTICK = '`';
const { start, text } = value;
const characterBefore = text[ start - 1 ];
Expand Down Expand Up @@ -46,7 +49,12 @@ export const code = {

return value;
},
edit( { value, onChange, onFocus, isActive } ) {
edit( {
value,
onChange,
onFocus,
isActive,
}: FormatEditProps ): React.ReactNode {
function onClick() {
onChange( toggleFormat( value, { type: name, title } ) );
onFocus();
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -13,8 +13,9 @@ import {
MediaUpload,
RichTextToolbarButton,
MediaUploadCheck,
// @ts-expect-error Block Editor not fully typed yet.
} from '@wordpress/block-editor';

import type { EditImageProps, InlineImageUIProps } from '../types';
const ALLOWED_MEDIA_TYPES = [ 'image' ];

const name = 'core/image';
Expand All @@ -23,10 +24,12 @@ const title = __( 'Inline image' );
/**
* Extracts the image ID from the className attribute.
*
* @param {Object} activeObjectAttributes The attributes of the active object.
* @return {number|undefined} The extracted image ID or undefined if not found.
* @param activeObjectAttributes The attributes of the active object.
* @return The extracted image ID or undefined if not found.
*/
function getCurrentImageId( activeObjectAttributes ) {
function getCurrentImageId(
activeObjectAttributes: EditImageProps[ 'activeObjectAttributes' ]
): number | undefined {
if ( ! activeObjectAttributes?.className ) {
return undefined;
}
Expand All @@ -53,13 +56,21 @@ export const image = {
edit: Edit,
};

function InlineUI( { value, onChange, activeObjectAttributes, contentRef } ) {
const { style, alt } = activeObjectAttributes;
function InlineUI( {
value,
onChange,
activeObjectAttributes,
contentRef,
}: InlineImageUIProps ) {
const style = activeObjectAttributes?.style;
const alt = activeObjectAttributes?.alt;

const width = style?.replace( /\D/g, '' );
const [ editedWidth, setEditedWidth ] = useState( width );
const [ editedAlt, setEditedAlt ] = useState( alt );
const hasChanged = editedWidth !== width || editedAlt !== alt;
const popoverAnchor = useAnchor( {
// eslint-disable-next-line react-hooks/refs
editableContentElement: contentRef.current,
settings: image,
} );
Expand All @@ -82,7 +93,7 @@ function InlineUI( { value, onChange, activeObjectAttributes, contentRef } ) {
style: editedWidth
? `width: ${ editedWidth }px;`
: '',
alt: editedAlt,
alt: editedAlt ?? '',
Comment thread
im3dabasia marked this conversation as resolved.
},
};

Expand All @@ -105,7 +116,7 @@ function InlineUI( { value, onChange, activeObjectAttributes, contentRef } ) {
/>
<WCTextareaControl
label={ __( 'Alternative text' ) }
value={ editedAlt }
value={ editedAlt ?? '' }
onChange={ ( newAlt ) => {
setEditedAlt( newAlt );
} }
Expand Down Expand Up @@ -153,13 +164,23 @@ function Edit( {
isObjectActive,
activeObjectAttributes,
contentRef,
} ) {
}: EditImageProps ) {
return (
<MediaUploadCheck>
<MediaUpload
allowedTypes={ ALLOWED_MEDIA_TYPES }
value={ getCurrentImageId( activeObjectAttributes ) }
onSelect={ ( { id, url, alt, width: imgWidth } ) => {
onSelect={ ( {
id,
url,
alt,
width: imgWidth,
}: {
id: number;
url: string;
alt: string;
width: number;
} ) => {
onChange(
insertObject( value, {
type: name,
Expand All @@ -176,7 +197,7 @@ function Edit( {
);
onFocus();
} }
render={ ( { open } ) => (
render={ ( { open }: { open: () => void } ) => (
<RichTextToolbarButton
icon={ inlineImage }
title={ isObjectActive ? __( 'Replace image' ) : title }
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,8 +4,10 @@ import {
RichTextToolbarButton,
RichTextShortcut,
__unstableRichTextInputEvent,
// @ts-expect-error Block Editor not fully typed yet.
} from '@wordpress/block-editor';
import { formatItalic } from '@wordpress/icons';
import type { FormatEditWithVisibilityProps } from '../types';

const name = 'core/italic';
const title = __( 'Italic' );
Expand All @@ -15,13 +17,19 @@ export const italic = {
title,
tagName: 'em',
className: null,
edit( { isActive, value, onChange, onFocus, isVisible = true } ) {
edit( {
isActive,
value,
onChange,
onFocus,
isVisible = true,
}: FormatEditWithVisibilityProps ) {
function onToggle() {
onChange( toggleFormat( value, { type: name, title } ) );
}

function onClick() {
onChange( toggleFormat( value, { type: name } ) );
onChange( toggleFormat( value, { type: name, title } ) );
onFocus();
}

Expand Down
Original file line number Diff line number Diff line change
@@ -1,7 +1,9 @@
import { __ } from '@wordpress/i18n';
import { toggleFormat } from '@wordpress/rich-text';
// @ts-expect-error Block Editor not fully typed yet.
import { RichTextToolbarButton } from '@wordpress/block-editor';
import { button } from '@wordpress/icons';
import type { FormatEditProps } from '../types';

const name = 'core/keyboard';
const title = __( 'Keyboard input' );
Expand All @@ -11,7 +13,7 @@ export const keyboard = {
title,
tagName: 'kbd',
className: null,
edit( { isActive, value, onChange, onFocus } ) {
edit( { isActive, value, onChange, onFocus }: FormatEditProps ) {
function onToggle() {
onChange( toggleFormat( value, { type: name, title } ) );
}
Expand Down
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import { __ } from '@wordpress/i18n';
// @ts-expect-error Block Editor not fully typed yet.
import { RichTextToolbarButton } from '@wordpress/block-editor';
import {
TextControl,
Expand All @@ -10,6 +11,11 @@ import { Stack } from '@wordpress/ui';
import { useState } from '@wordpress/element';
import { applyFormat, removeFormat, useAnchor } from '@wordpress/rich-text';
import { language as languageIcon } from '@wordpress/icons';
import type {
LanguageEditProps,
InlineLanguageUIProps,
LanguageFormat,
} from '../types';

const name = 'core/language';
const title = __( 'Language' );
Expand All @@ -24,9 +30,9 @@ export const language = {
dir: 'dir',
},
edit: Edit,
};
} satisfies LanguageFormat;

function Edit( { isActive, value, onChange, contentRef } ) {
function Edit( { isActive, value, onChange, contentRef }: LanguageEditProps ) {
const [ isPopoverVisible, setIsPopoverVisible ] = useState( false );
const togglePopover = () => {
setIsPopoverVisible( ( state ) => ! state );
Expand Down Expand Up @@ -60,14 +66,20 @@ function Edit( { isActive, value, onChange, contentRef } ) {
);
}

function InlineLanguageUI( { value, contentRef, onChange, onClose } ) {
function InlineLanguageUI( {
value,
contentRef,
onChange,
onClose,
}: InlineLanguageUIProps ) {
const popoverAnchor = useAnchor( {
// eslint-disable-next-line react-hooks/refs
editableContentElement: contentRef.current,
settings: language,
} );

const [ lang, setLang ] = useState( '' );
const [ dir, setDir ] = useState( 'ltr' );
const [ dir, setDir ] = useState< 'ltr' | 'rtl' >( 'ltr' );

return (
<Popover
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ import {
CheckboxControl,
} from '@wordpress/components';
import { Stack, VisuallyHidden } from '@wordpress/ui';
import type { CSSClassesSettingProps } from '../types';

/**
* CSSClassesSettingComponent
Expand All @@ -14,19 +15,23 @@ import { Stack, VisuallyHidden } from '@wordpress/ui';
* is shown when the toggle is enabled or when there is already a value. When
* toggled off and a value exists, it resets the value to an empty string.
*
* @param {Object} props - Component props.
* @param {Object} props.setting - Setting configuration object.
* @param {Object} props.value - Current link value object.
* @param {Function} props.onChange - Callback when value changes.
* @param props - Component props.
* @param props.setting - Setting configuration object.
* @param props.value - Current link value object.
* @param props.onChange - Callback when value changes.
*/
const CSSClassesSettingComponent = ( { setting, value, onChange } ) => {
const hasValue = value ? value?.cssClasses?.length > 0 : false;
const CSSClassesSettingComponent = ( {
setting,
value,
onChange,
}: CSSClassesSettingProps ) => {
const hasValue = !! value?.cssClasses?.length;
const [ isSettingActive, setIsSettingActive ] = useState( hasValue );
const instanceId = useInstanceId( CSSClassesSettingComponent );
const controlledRegionId = `css-classes-setting-${ instanceId }`;

// Sanitize user input: replace commas with spaces, collapse repeated spaces, and trim
const handleSettingChange = ( newValue ) => {
const handleSettingChange = ( newValue: string | undefined ) => {
const sanitizedValue =
typeof newValue === 'string'
? newValue.replace( /,/g, ' ' ).replace( /\s+/g, ' ' ).trim()
Expand Down
Loading
Loading