Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
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
18 changes: 18 additions & 0 deletions packages/block-library/src/navigation-link/editor.scss
Original file line number Diff line number Diff line change
Expand Up @@ -150,3 +150,21 @@
.navigation-link-control__error-text {
color: $alert-red;
}

.navigation-link-to__action-button {
grid-column: auto;
// When this is the last button AND in an odd position among its class
// siblings, it's unpaired — span the full grid row.
&:nth-last-child(1 of #{&}):nth-child(odd of #{&}) {
grid-column: 1 / -1;
}

// Artificially increase specificity to override `justify-content` styles.
// Not ideal, but it shouldn't be necessary once switching to the new `Button`
// component from `@wordpress/ui`.
&#{&}#{&} {
justify-content: center;
}

}

97 changes: 35 additions & 62 deletions packages/block-library/src/navigation-link/shared/controls.js
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,6 @@ import {
Button,
__experimentalToolsPanel as ToolsPanel,
__experimentalToolsPanelItem as ToolsPanelItem,
__experimentalHStack as HStack,
CheckboxControl,
TextControl,
TextareaControl,
Expand Down Expand Up @@ -150,19 +149,14 @@ export function Controls( {

// Check if URL is viewable (not hash link or other relative path like ./ or ../)
const isViewableUrl =
url &&
!! url &&
( ! isHashLink( url ) ||
( isRelativePath( url ) && ! url.startsWith( '/' ) ) );

// Construct full URL for viewing (prepend home URL for absolute paths starting with /)
const viewUrl =
isViewableUrl && url.startsWith( '/' ) && homeUrl ? homeUrl + url : url;

const entityTypeName = getEntityTypeName(
attributes.type,
attributes.kind
);

return (
<ToolsPanel
label={ __( 'Settings' ) }
Expand Down Expand Up @@ -220,61 +214,6 @@ export function Controls( {
help={ helpText ? helpText : undefined }
/>
</ToolsPanelItem>

{ url && (
<HStack
className="navigation-link-to__actions"
alignment="left"
justify="left"
style={ { gridColumn: '1 / -1' } }
>
{ hasUrlBinding &&
isBoundEntityAvailable &&
entityRecord?.id &&
attributes.kind === 'post-type' &&
onNavigateToEntityRecord && (
<Button
size="compact"
variant="secondary"
onClick={ () => {
onNavigateToEntityRecord( {
postId: entityRecord.id,
postType: attributes.type,
} );
} }
__next40pxDefaultSize
>
{ sprintf(
/* translators: %s: entity type (e.g., "page", "post", "category") */
__( 'Edit %s' ),
entityTypeName
) }
</Button>
) }
{ isViewableUrl && (
<Button
size="compact"
variant="secondary"
href={ viewUrl }
target="_blank"
icon={ external }
iconPosition="right"
__next40pxDefaultSize
>
{ sprintf(
/* translators: %s: entity type (e.g., "page", "post", "category") or "link" for external links */
__( 'View %s' ),
attributes.kind &&
attributes.type &&
attributes.kind !== 'custom'
? entityTypeName
: __( 'link' )
) }
</Button>
) }
</HStack>
) }

<ToolsPanelItem
hasValue={ () => !! opensInNewTab }
label={ __( 'Open in new tab' ) }
Expand All @@ -291,6 +230,40 @@ export function Controls( {
}
/>
</ToolsPanelItem>

{ !! url &&
hasUrlBinding &&
isBoundEntityAvailable &&
entityRecord?.id &&
attributes.kind === 'post-type' &&
onNavigateToEntityRecord && (
<Button
variant="secondary"
onClick={ () => {
onNavigateToEntityRecord( {
postId: entityRecord.id,
postType: attributes.type,
} );
} }
__next40pxDefaultSize
className="navigation-link-to__action-button"
>
{ __( 'Edit' ) }
</Button>
) }
{ isViewableUrl && (
<Button
variant="secondary"
href={ viewUrl }
target="_blank"
icon={ external }
iconPosition="right"
__next40pxDefaultSize
className="navigation-link-to__action-button"
>
{ __( 'View' ) }
</Button>
) }
</>
) }

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -237,7 +237,7 @@ describe( 'Controls', () => {

render( <Controls { ...propsWithExternalLink } /> );

expect( screen.getByText( 'View link' ) ).toBeVisible();
expect( screen.getByText( 'View' ) ).toBeVisible();
} );

it( 'shows "View page" for page links', () => {
Expand All @@ -253,7 +253,7 @@ describe( 'Controls', () => {

render( <Controls { ...propsWithPageLink } /> );

expect( screen.getByText( 'View page' ) ).toBeVisible();
expect( screen.getByText( 'View' ) ).toBeVisible();
} );

it( 'shows "View post" for post links', () => {
Expand All @@ -269,7 +269,7 @@ describe( 'Controls', () => {

render( <Controls { ...propsWithPostLink } /> );

expect( screen.getByText( 'View post' ) ).toBeVisible();
expect( screen.getByText( 'View' ) ).toBeVisible();
} );

it( 'shows "View category" for category links', () => {
Expand All @@ -285,7 +285,7 @@ describe( 'Controls', () => {

render( <Controls { ...propsWithCategoryLink } /> );

expect( screen.getByText( 'View category' ) ).toBeVisible();
expect( screen.getByText( 'View' ) ).toBeVisible();
} );

it( 'shows "View link" for custom type links', () => {
Expand All @@ -301,7 +301,7 @@ describe( 'Controls', () => {

render( <Controls { ...propsWithCustomLink } /> );

expect( screen.getByText( 'View link' ) ).toBeVisible();
expect( screen.getByText( 'View' ) ).toBeVisible();
} );
} );
} );
Loading