Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Refactor FocalPointPicker to function component #39168

Merged
merged 10 commits into from
Aug 25, 2022

Conversation

stokesman
Copy link
Contributor

@stokesman stokesman commented Mar 2, 2022

Part of #22890.

When starting on this I first looked for some small things that could be simplified and put them in the first commit since they would be hard to spot within the rewrite as a function component. Once I got into the rewrite, I found more things to simplify:

Testing Instructions

Make sure the FocalPointPicker works as expected. Especially in the Media & Text block and Cover blocks.

Screenshots

Types of changes

Refactor

Checklist:

  • My code is tested.
  • My code follows the WordPress code style.
  • My code follows the accessibility standards.
  • I've tested my changes with keyboard and screen readers.
  • My code has proper inline documentation.
  • I've included developer documentation if appropriate.
  • I've updated all React Native files affected by any refactorings/renamings in this PR (please manually search all *.native.js files for terms that need renaming or removal).
  • I've updated related schemas if appropriate.

@stokesman stokesman added [Type] Code Quality Issues or PRs that relate to code quality [Package] Components /packages/components labels Mar 2, 2022
@github-actions
Copy link

github-actions bot commented Mar 2, 2022

Size Change: -834 B (0%)

Total Size: 1.24 MB

Filename Size Change
build/components/index.min.js 197 kB -834 B (0%)
ℹ️ View Unchanged
Filename Size
build/a11y/index.min.js 982 B
build/annotations/index.min.js 2.76 kB
build/api-fetch/index.min.js 2.26 kB
build/autop/index.min.js 2.14 kB
build/blob/index.min.js 475 B
build/block-directory/index.min.js 7.06 kB
build/block-directory/style-rtl.css 990 B
build/block-directory/style.css 991 B
build/block-editor/default-editor-styles-rtl.css 378 B
build/block-editor/default-editor-styles.css 378 B
build/block-editor/index.min.js 159 kB
build/block-editor/style-rtl.css 15.1 kB
build/block-editor/style.css 15 kB
build/block-library/blocks/archives/editor-rtl.css 61 B
build/block-library/blocks/archives/editor.css 60 B
build/block-library/blocks/archives/style-rtl.css 65 B
build/block-library/blocks/archives/style.css 65 B
build/block-library/blocks/audio/editor-rtl.css 150 B
build/block-library/blocks/audio/editor.css 150 B
build/block-library/blocks/audio/style-rtl.css 122 B
build/block-library/blocks/audio/style.css 122 B
build/block-library/blocks/audio/theme-rtl.css 110 B
build/block-library/blocks/audio/theme.css 110 B
build/block-library/blocks/avatar/editor-rtl.css 116 B
build/block-library/blocks/avatar/editor.css 116 B
build/block-library/blocks/avatar/style-rtl.css 59 B
build/block-library/blocks/avatar/style.css 59 B
build/block-library/blocks/block/editor-rtl.css 161 B
build/block-library/blocks/block/editor.css 161 B
build/block-library/blocks/button/editor-rtl.css 441 B
build/block-library/blocks/button/editor.css 441 B
build/block-library/blocks/button/style-rtl.css 505 B
build/block-library/blocks/button/style.css 505 B
build/block-library/blocks/buttons/editor-rtl.css 292 B
build/block-library/blocks/buttons/editor.css 292 B
build/block-library/blocks/buttons/style-rtl.css 275 B
build/block-library/blocks/buttons/style.css 275 B
build/block-library/blocks/calendar/style-rtl.css 207 B
build/block-library/blocks/calendar/style.css 207 B
build/block-library/blocks/categories/editor-rtl.css 84 B
build/block-library/blocks/categories/editor.css 83 B
build/block-library/blocks/categories/style-rtl.css 79 B
build/block-library/blocks/categories/style.css 79 B
build/block-library/blocks/code/style-rtl.css 103 B
build/block-library/blocks/code/style.css 103 B
build/block-library/blocks/code/theme-rtl.css 124 B
build/block-library/blocks/code/theme.css 124 B
build/block-library/blocks/columns/editor-rtl.css 108 B
build/block-library/blocks/columns/editor.css 108 B
build/block-library/blocks/columns/style-rtl.css 406 B
build/block-library/blocks/columns/style.css 406 B
build/block-library/blocks/comment-author-avatar/editor-rtl.css 125 B
build/block-library/blocks/comment-author-avatar/editor.css 125 B
build/block-library/blocks/comment-content/style-rtl.css 92 B
build/block-library/blocks/comment-content/style.css 92 B
build/block-library/blocks/comment-template/style-rtl.css 187 B
build/block-library/blocks/comment-template/style.css 185 B
build/block-library/blocks/comments-pagination-numbers/editor-rtl.css 123 B
build/block-library/blocks/comments-pagination-numbers/editor.css 121 B
build/block-library/blocks/comments-pagination/editor-rtl.css 222 B
build/block-library/blocks/comments-pagination/editor.css 209 B
build/block-library/blocks/comments-pagination/style-rtl.css 235 B
build/block-library/blocks/comments-pagination/style.css 231 B
build/block-library/blocks/comments-title/editor-rtl.css 75 B
build/block-library/blocks/comments-title/editor.css 75 B
build/block-library/blocks/comments/editor-rtl.css 834 B
build/block-library/blocks/comments/editor.css 832 B
build/block-library/blocks/comments/style-rtl.css 632 B
build/block-library/blocks/comments/style.css 630 B
build/block-library/blocks/cover/editor-rtl.css 615 B
build/block-library/blocks/cover/editor.css 616 B
build/block-library/blocks/cover/style-rtl.css 1.55 kB
build/block-library/blocks/cover/style.css 1.55 kB
build/block-library/blocks/embed/editor-rtl.css 293 B
build/block-library/blocks/embed/editor.css 293 B
build/block-library/blocks/embed/style-rtl.css 410 B
build/block-library/blocks/embed/style.css 410 B
build/block-library/blocks/embed/theme-rtl.css 110 B
build/block-library/blocks/embed/theme.css 110 B
build/block-library/blocks/file/editor-rtl.css 300 B
build/block-library/blocks/file/editor.css 300 B
build/block-library/blocks/file/style-rtl.css 253 B
build/block-library/blocks/file/style.css 254 B
build/block-library/blocks/file/view.min.js 346 B
build/block-library/blocks/freeform/editor-rtl.css 2.44 kB
build/block-library/blocks/freeform/editor.css 2.44 kB
build/block-library/blocks/gallery/editor-rtl.css 948 B
build/block-library/blocks/gallery/editor.css 950 B
build/block-library/blocks/gallery/style-rtl.css 1.53 kB
build/block-library/blocks/gallery/style.css 1.53 kB
build/block-library/blocks/gallery/theme-rtl.css 108 B
build/block-library/blocks/gallery/theme.css 108 B
build/block-library/blocks/group/editor-rtl.css 412 B
build/block-library/blocks/group/editor.css 412 B
build/block-library/blocks/group/style-rtl.css 57 B
build/block-library/blocks/group/style.css 57 B
build/block-library/blocks/group/theme-rtl.css 78 B
build/block-library/blocks/group/theme.css 78 B
build/block-library/blocks/heading/style-rtl.css 76 B
build/block-library/blocks/heading/style.css 76 B
build/block-library/blocks/html/editor-rtl.css 327 B
build/block-library/blocks/html/editor.css 329 B
build/block-library/blocks/image/editor-rtl.css 876 B
build/block-library/blocks/image/editor.css 873 B
build/block-library/blocks/image/style-rtl.css 627 B
build/block-library/blocks/image/style.css 630 B
build/block-library/blocks/image/theme-rtl.css 110 B
build/block-library/blocks/image/theme.css 110 B
build/block-library/blocks/latest-comments/style-rtl.css 284 B
build/block-library/blocks/latest-comments/style.css 284 B
build/block-library/blocks/latest-posts/editor-rtl.css 213 B
build/block-library/blocks/latest-posts/editor.css 212 B
build/block-library/blocks/latest-posts/style-rtl.css 463 B
build/block-library/blocks/latest-posts/style.css 462 B
build/block-library/blocks/list/style-rtl.css 88 B
build/block-library/blocks/list/style.css 88 B
build/block-library/blocks/media-text/editor-rtl.css 266 B
build/block-library/blocks/media-text/editor.css 263 B
build/block-library/blocks/media-text/style-rtl.css 507 B
build/block-library/blocks/media-text/style.css 505 B
build/block-library/blocks/more/editor-rtl.css 431 B
build/block-library/blocks/more/editor.css 431 B
build/block-library/blocks/navigation-link/editor-rtl.css 705 B
build/block-library/blocks/navigation-link/editor.css 703 B
build/block-library/blocks/navigation-link/style-rtl.css 115 B
build/block-library/blocks/navigation-link/style.css 115 B
build/block-library/blocks/navigation-submenu/editor-rtl.css 296 B
build/block-library/blocks/navigation-submenu/editor.css 295 B
build/block-library/blocks/navigation-submenu/view.min.js 423 B
build/block-library/blocks/navigation/editor-rtl.css 2.05 kB
build/block-library/blocks/navigation/editor.css 2.06 kB
build/block-library/blocks/navigation/style-rtl.css 1.98 kB
build/block-library/blocks/navigation/style.css 1.97 kB
build/block-library/blocks/navigation/view-modal.min.js 2.78 kB
build/block-library/blocks/navigation/view.min.js 443 B
build/block-library/blocks/nextpage/editor-rtl.css 395 B
build/block-library/blocks/nextpage/editor.css 395 B
build/block-library/blocks/page-list/editor-rtl.css 363 B
build/block-library/blocks/page-list/editor.css 363 B
build/block-library/blocks/page-list/style-rtl.css 175 B
build/block-library/blocks/page-list/style.css 175 B
build/block-library/blocks/paragraph/editor-rtl.css 174 B
build/block-library/blocks/paragraph/editor.css 174 B
build/block-library/blocks/paragraph/style-rtl.css 260 B
build/block-library/blocks/paragraph/style.css 260 B
build/block-library/blocks/post-author/style-rtl.css 175 B
build/block-library/blocks/post-author/style.css 176 B
build/block-library/blocks/post-comments-form/editor-rtl.css 96 B
build/block-library/blocks/post-comments-form/editor.css 96 B
build/block-library/blocks/post-comments-form/style-rtl.css 493 B
build/block-library/blocks/post-comments-form/style.css 493 B
build/block-library/blocks/post-date/style-rtl.css 61 B
build/block-library/blocks/post-date/style.css 61 B
build/block-library/blocks/post-excerpt/editor-rtl.css 73 B
build/block-library/blocks/post-excerpt/editor.css 73 B
build/block-library/blocks/post-excerpt/style-rtl.css 69 B
build/block-library/blocks/post-excerpt/style.css 69 B
build/block-library/blocks/post-featured-image/editor-rtl.css 507 B
build/block-library/blocks/post-featured-image/editor.css 505 B
build/block-library/blocks/post-featured-image/style-rtl.css 166 B
build/block-library/blocks/post-featured-image/style.css 166 B
build/block-library/blocks/post-template/editor-rtl.css 99 B
build/block-library/blocks/post-template/editor.css 98 B
build/block-library/blocks/post-template/style-rtl.css 282 B
build/block-library/blocks/post-template/style.css 282 B
build/block-library/blocks/post-terms/style-rtl.css 73 B
build/block-library/blocks/post-terms/style.css 73 B
build/block-library/blocks/post-title/style-rtl.css 100 B
build/block-library/blocks/post-title/style.css 100 B
build/block-library/blocks/preformatted/style-rtl.css 103 B
build/block-library/blocks/preformatted/style.css 103 B
build/block-library/blocks/pullquote/editor-rtl.css 135 B
build/block-library/blocks/pullquote/editor.css 135 B
build/block-library/blocks/pullquote/style-rtl.css 326 B
build/block-library/blocks/pullquote/style.css 325 B
build/block-library/blocks/pullquote/theme-rtl.css 167 B
build/block-library/blocks/pullquote/theme.css 167 B
build/block-library/blocks/query-pagination-numbers/editor-rtl.css 122 B
build/block-library/blocks/query-pagination-numbers/editor.css 121 B
build/block-library/blocks/query-pagination/editor-rtl.css 221 B
build/block-library/blocks/query-pagination/editor.css 211 B
build/block-library/blocks/query-pagination/style-rtl.css 282 B
build/block-library/blocks/query-pagination/style.css 278 B
build/block-library/blocks/query-title/style-rtl.css 63 B
build/block-library/blocks/query-title/style.css 63 B
build/block-library/blocks/query/editor-rtl.css 439 B
build/block-library/blocks/query/editor.css 439 B
build/block-library/blocks/quote/style-rtl.css 213 B
build/block-library/blocks/quote/style.css 213 B
build/block-library/blocks/quote/theme-rtl.css 223 B
build/block-library/blocks/quote/theme.css 226 B
build/block-library/blocks/read-more/style-rtl.css 132 B
build/block-library/blocks/read-more/style.css 132 B
build/block-library/blocks/rss/editor-rtl.css 202 B
build/block-library/blocks/rss/editor.css 204 B
build/block-library/blocks/rss/style-rtl.css 289 B
build/block-library/blocks/rss/style.css 288 B
build/block-library/blocks/search/editor-rtl.css 165 B
build/block-library/blocks/search/editor.css 165 B
build/block-library/blocks/search/style-rtl.css 396 B
build/block-library/blocks/search/style.css 393 B
build/block-library/blocks/search/theme-rtl.css 114 B
build/block-library/blocks/search/theme.css 114 B
build/block-library/blocks/separator/editor-rtl.css 146 B
build/block-library/blocks/separator/editor.css 146 B
build/block-library/blocks/separator/style-rtl.css 233 B
build/block-library/blocks/separator/style.css 233 B
build/block-library/blocks/separator/theme-rtl.css 194 B
build/block-library/blocks/separator/theme.css 194 B
build/block-library/blocks/shortcode/editor-rtl.css 464 B
build/block-library/blocks/shortcode/editor.css 464 B
build/block-library/blocks/site-logo/editor-rtl.css 455 B
build/block-library/blocks/site-logo/editor.css 455 B
build/block-library/blocks/site-logo/style-rtl.css 192 B
build/block-library/blocks/site-logo/style.css 192 B
build/block-library/blocks/site-tagline/editor-rtl.css 86 B
build/block-library/blocks/site-tagline/editor.css 86 B
build/block-library/blocks/site-title/editor-rtl.css 84 B
build/block-library/blocks/site-title/editor.css 84 B
build/block-library/blocks/social-link/editor-rtl.css 184 B
build/block-library/blocks/social-link/editor.css 184 B
build/block-library/blocks/social-links/editor-rtl.css 674 B
build/block-library/blocks/social-links/editor.css 673 B
build/block-library/blocks/social-links/style-rtl.css 1.39 kB
build/block-library/blocks/social-links/style.css 1.38 kB
build/block-library/blocks/spacer/editor-rtl.css 322 B
build/block-library/blocks/spacer/editor.css 322 B
build/block-library/blocks/spacer/style-rtl.css 48 B
build/block-library/blocks/spacer/style.css 48 B
build/block-library/blocks/table/editor-rtl.css 494 B
build/block-library/blocks/table/editor.css 494 B
build/block-library/blocks/table/style-rtl.css 611 B
build/block-library/blocks/table/style.css 609 B
build/block-library/blocks/table/theme-rtl.css 175 B
build/block-library/blocks/table/theme.css 175 B
build/block-library/blocks/tag-cloud/style-rtl.css 239 B
build/block-library/blocks/tag-cloud/style.css 239 B
build/block-library/blocks/template-part/editor-rtl.css 235 B
build/block-library/blocks/template-part/editor.css 235 B
build/block-library/blocks/template-part/theme-rtl.css 101 B
build/block-library/blocks/template-part/theme.css 101 B
build/block-library/blocks/text-columns/editor-rtl.css 95 B
build/block-library/blocks/text-columns/editor.css 95 B
build/block-library/blocks/text-columns/style-rtl.css 166 B
build/block-library/blocks/text-columns/style.css 166 B
build/block-library/blocks/verse/style-rtl.css 87 B
build/block-library/blocks/verse/style.css 87 B
build/block-library/blocks/video/editor-rtl.css 561 B
build/block-library/blocks/video/editor.css 563 B
build/block-library/blocks/video/style-rtl.css 174 B
build/block-library/blocks/video/style.css 174 B
build/block-library/blocks/video/theme-rtl.css 110 B
build/block-library/blocks/video/theme.css 110 B
build/block-library/common-rtl.css 1.01 kB
build/block-library/common.css 1 kB
build/block-library/editor-elements-rtl.css 75 B
build/block-library/editor-elements.css 75 B
build/block-library/editor-rtl.css 11 kB
build/block-library/editor.css 11 kB
build/block-library/elements-rtl.css 54 B
build/block-library/elements.css 54 B
build/block-library/index.min.js 185 kB
build/block-library/reset-rtl.css 478 B
build/block-library/reset.css 478 B
build/block-library/style-rtl.css 11.8 kB
build/block-library/style.css 11.8 kB
build/block-library/theme-rtl.css 695 B
build/block-library/theme.css 700 B
build/block-serialization-default-parser/index.min.js 1.11 kB
build/block-serialization-spec-parser/index.min.js 2.83 kB
build/blocks/index.min.js 49.6 kB
build/components/style-rtl.css 11.6 kB
build/components/style.css 11.6 kB
build/compose/index.min.js 12 kB
build/core-data/index.min.js 15.5 kB
build/customize-widgets/index.min.js 11.3 kB
build/customize-widgets/style-rtl.css 1.38 kB
build/customize-widgets/style.css 1.38 kB
build/data-controls/index.min.js 653 B
build/data/index.min.js 8.05 kB
build/date/index.min.js 32 kB
build/deprecated/index.min.js 507 B
build/dom-ready/index.min.js 324 B
build/dom/index.min.js 4.69 kB
build/edit-navigation/index.min.js 16 kB
build/edit-navigation/style-rtl.css 4 kB
build/edit-navigation/style.css 4.01 kB
build/edit-post/classic-rtl.css 546 B
build/edit-post/classic.css 547 B
build/edit-post/index.min.js 30.5 kB
build/edit-post/style-rtl.css 6.94 kB
build/edit-post/style.css 6.94 kB
build/edit-site/index.min.js 57.4 kB
build/edit-site/style-rtl.css 8.22 kB
build/edit-site/style.css 8.2 kB
build/edit-widgets/index.min.js 16.5 kB
build/edit-widgets/style-rtl.css 4.35 kB
build/edit-widgets/style.css 4.35 kB
build/editor/index.min.js 41.5 kB
build/editor/style-rtl.css 3.66 kB
build/editor/style.css 3.65 kB
build/element/index.min.js 4.68 kB
build/escape-html/index.min.js 537 B
build/format-library/index.min.js 6.75 kB
build/format-library/style-rtl.css 571 B
build/format-library/style.css 571 B
build/hooks/index.min.js 1.64 kB
build/html-entities/index.min.js 448 B
build/i18n/index.min.js 3.77 kB
build/is-shallow-equal/index.min.js 527 B
build/keyboard-shortcuts/index.min.js 1.78 kB
build/keycodes/index.min.js 1.81 kB
build/list-reusable-blocks/index.min.js 1.74 kB
build/list-reusable-blocks/style-rtl.css 835 B
build/list-reusable-blocks/style.css 835 B
build/media-utils/index.min.js 2.93 kB
build/notices/index.min.js 953 B
build/nux/index.min.js 2.05 kB
build/nux/style-rtl.css 732 B
build/nux/style.css 728 B
build/plugins/index.min.js 1.94 kB
build/preferences-persistence/index.min.js 2.22 kB
build/preferences/index.min.js 1.3 kB
build/primitives/index.min.js 933 B
build/priority-queue/index.min.js 612 B
build/react-i18n/index.min.js 696 B
build/react-refresh-entry/index.min.js 8.44 kB
build/react-refresh-runtime/index.min.js 7.31 kB
build/redux-routine/index.min.js 2.74 kB
build/reusable-blocks/index.min.js 2.21 kB
build/reusable-blocks/style-rtl.css 256 B
build/reusable-blocks/style.css 256 B
build/rich-text/index.min.js 11.2 kB
build/server-side-render/index.min.js 1.61 kB
build/shortcode/index.min.js 1.53 kB
build/token-list/index.min.js 644 B
build/url/index.min.js 3.61 kB
build/vendors/react-dom.min.js 38.5 kB
build/vendors/react.min.js 4.34 kB
build/viewport/index.min.js 1.08 kB
build/warning/index.min.js 268 B
build/widgets/index.min.js 7.2 kB
build/widgets/style-rtl.css 1.18 kB
build/widgets/style.css 1.19 kB
build/wordcount/index.min.js 1.06 kB

compressed-size-action

@stokesman stokesman force-pushed the refactor/focal-point-picker-fn branch from 1313547 to b6d4df3 Compare March 2, 2022 17:42
@stokesman stokesman force-pushed the refactor/focal-point-picker-fn branch 2 times, most recently from 8163f00 to f38772b Compare March 16, 2022 22:00
Copy link
Contributor Author

@stokesman stokesman left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I've left some inline comments on some changes that are either stylistic or otherwise non-obvious.

Comment on lines -25 to +33
percentages = {
point = {
x: 0.5,
y: 0.5,
},
} ) {
const valueX = fractionToPercentage( percentages.x );
const valueY = fractionToPercentage( percentages.y );
const valueX = fractionToPercentage( point.x );
const valueY = fractionToPercentage( point.y );

const handleChange = ( value, axis ) => {
const num = parseInt( value, 10 );

if ( ! isNaN( num ) ) {
onChange( { ...percentages, [ axis ]: num / 100 } );
onChange( { ...point, [ axis ]: num / 100 } );
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is cosmetic but point just seems like a better name than percentages. It's an internal component so there's no concern of breakage.

Comment on lines -16 to +21
export default function FocalPoint( {
coordinates = { left: '50%', top: '50%' },
...props
} ) {
export default function FocalPoint( { left = '50%', top = '50%', ...props } ) {
const classes = classnames(
'components-focal-point-picker__icon_container'
);

const style = {
left: coordinates.left,
top: coordinates.top,
};
const style = { left, top };
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Cosmetic. The separate left and right props are a touch simpler. Less abstract seems a fine thing for an internal component.

Comment on lines 19 to 16
export default function FocalPointPickerGrid( {
bounds = {},
value,
...props
} ) {
export default function FocalPointPickerGrid( { bounds, value, ...props } ) {
Copy link
Contributor Author

@stokesman stokesman Mar 16, 2022

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

bounds is always supplied by the parent component and does not need to default.

Comment on lines -21 to +11
onLoad = noop,
onLoad,
Copy link
Contributor Author

@stokesman stokesman Mar 16, 2022

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

There is no need to default this. The parent component supplies it unconditionally.

packages/components/src/focal-point-picker/media.js Outdated Show resolved Hide resolved
packages/components/src/focal-point-picker/test/index.js Outdated Show resolved Hide resolved
Comment on lines 1 to 4
export const INITIAL_BOUNDS = {
top: 0,
left: 0,
bottom: 0,
right: 0,
width: 0,
height: 0,
width: 200,
height: 170,
};
Copy link
Contributor Author

@stokesman stokesman Jun 1, 2022

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The width and height values are extracted from the styles and the styles now pull them from here. The component was also no longer in need of all the other properties.

@stokesman stokesman force-pushed the refactor/focal-point-picker-fn branch 2 times, most recently from 8854204 to de2fd11 Compare July 7, 2022 17:37
@stokesman
Copy link
Contributor Author

@mirka and/or @ciampo, I've had this sitting for a good while and I'd appreciate your advice on it. Specifically whether you'd prefer to see this also converted to TypeScript in this same PR (like I noticed was recently done with FormTokenField).

@mirka
Copy link
Member

mirka commented Jul 8, 2022

Specifically whether you'd prefer to see this also converted to TypeScript in this same PR (like I noticed was recently done with FormTokenField).

What I took from my experience reviewing that PR was: It's probably easier to review if the FC and TS conversions are done in separate PRs 😄 I just didn't think it was worth codifying in the contributing guide because there are only a few class components left.

Is this ready for review, in that case?

@stokesman stokesman force-pushed the refactor/focal-point-picker-fn branch from a57bbef to 7aedf1f Compare July 12, 2022 14:32
@stokesman
Copy link
Contributor Author

Is this ready for review, in that case?

Now that I've linted with react-hooks/exhaustive-deps and added a couple commits to get it passing, I'll say yes.

@stokesman stokesman marked this pull request as ready for review July 12, 2022 15:47
Copy link
Contributor

@ciampo ciampo left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thank you @stokesman for working on this.

I had a look at the component on Storybook and found a few regressions:

  • the coordinates reset when the component loses focus (i.e. clicking outside of the interactive area)
  • the thirds grid in the "Video" example does not adapt to its container

With regards to the TS refactor, I would have probably worked on that first, in order to gain even more confidence when working on the follow-up refactor from class to functional component.

I would also like to express a personal preference for avoiding runtime changes as much as possible (ref optimizations, drag logic refactor, variable name changes...) during "refactor" PRs like this one, as they increase considerably the difficulty amount of time required to review the PR. Those are all great improvements, but I would personally prefer if they were applied in one or more follow-up PRs, keeping the original PR focused on the refactor from class to function component.

packages/components/src/focal-point-picker/index.js Outdated Show resolved Hide resolved
packages/components/src/focal-point-picker/index.js Outdated Show resolved Hide resolved
Comment on lines 224 to 107
if ( byTenths ) {
nextX = Math.round( nextX / 0.1 ) * 0.1;
nextY = Math.round( nextY / 0.1 ) * 0.1;
}
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

With this change, the values are not clamped anymore if byTenths is false — what's reason behind it? Why do are we moving away from roundClamp ? (reviewing this change in the context of the first "cleanup" commit in this PR)

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The values are clamped a few lines before this making the clamp of roundClamp redundant.

The larger story is one of yak-shaving. This PR got started when working on another PR (#34566) and wanting to modify roundClamp for a more specific purpose. I noticed the only other place it was used was this component, spotted the partial redundancy and figured it could be removed here to potentially free it up for the repurposing.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Makes sense. I'm going to keep this conversation open for extra visibility in case anyone else reviews this PR

packages/components/src/focal-point-picker/test/index.js Outdated Show resolved Hide resolved
packages/components/src/focal-point-picker/index.js Outdated Show resolved Hide resolved
@stokesman
Copy link
Contributor Author

  • the coordinates reset when the component loses focus (i.e. clicking outside of the interactive area)

🤦 That was introduced with 832ea2c and now fixed with 3d8d486

  • the thirds grid in the "Video" example does not adapt to its container

Great catch. Fixed it in 976b4b3. Sort of makes me think we may want a story with an intentionally 404'd media URL because otherwise we might have missed this. I don't believe a unit test could cover it because of jsdom and lack of element dimensions.

@ciampo ciampo requested review from mirka and chad1008 July 19, 2022 15:22
@ciampo ciampo added the [Type] Enhancement A suggestion for improvement. label Jul 19, 2022
Copy link
Contributor

@ciampo ciampo left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Most of my first round of feedback has been addressed, and the Storybook example seems to work as expected.

Given the fact that the code changes in this PR are not trivial, I've also tagged @mirka in case she wants to take a look as well before merging.

packages/components/src/focal-point-picker/test/index.js Outdated Show resolved Hide resolved
Comment on lines 224 to 107
if ( byTenths ) {
nextX = Math.round( nextX / 0.1 ) * 0.1;
nextY = Math.round( nextY / 0.1 ) * 0.1;
}
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Makes sense. I'm going to keep this conversation open for extra visibility in case anyone else reviews this PR

@ciampo
Copy link
Contributor

ciampo commented Jul 20, 2022

While giving this PR another round of testing, I discovered another bug (which is also present in trunk):

Basically, 0 coordinates are displayed as 50 in the UnitControl inputs (for both left and top coordinates)

Kapture.2022-07-20.at.12.03.38.mp4

@stokesman
Copy link
Contributor Author

stokesman commented Jul 21, 2022

I discovered another bug (which is also present in trunk)

Nice spotting that! Turns out it has the same cause as #42455. I tested by applying the changes from #42484 and it fixes it.

@ciampo
Copy link
Contributor

ciampo commented Jul 21, 2022

I discovered another bug (which is also present in trunk)

Nice spotting that! Turns out it has the same cause as #42455. I tested by applying the changes from #42484 and it fixes it.

Great timing! Let's prioritise #42484 — we can then rebase this PR after #42484 merged for a final round of testing

Copy link
Member

@mirka mirka left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't think I've gone as deep as Marco did, but I read through the code and nothing major is jumping out 👍

One happy find is that I think this PR fixes a bug in trunk where the indicator offset gets weird after scrolling:

CleanShot.2022-07-22.at.02.54.33.mp4

role="button"
tabIndex="-1"
>
<Grid bounds={ bounds } value={ `${ x }${ y }` } />
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

(Just a comment, not meant to address in this PR:) I found it a bit strange that a prop named value is being used basically as a re-rendering key. I wonder if it would be more straightforward (and efficient) if we simply passed isDragging instead of every changed value.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes, 💯 strange.

Your suggested solution seems great. It will require a little reworking of Grid but I'd expect it to be an all around improvement.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I thought of something that might block the suggestion. Right now Grid makes itself visible not just when dragging but also during any value changes (arrow keys while the drag area is focused or changes at the number inputs). There'd be no way to maintain that by merely using isDragging.

Maybe just changing the prop from value to key would be the way to go.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We could simplify the code by passing a showOverlay prop to the Grid component, moving the timeout logic to index.js

Click to expand
diff --git a/packages/components/src/focal-point-picker/grid.js b/packages/components/src/focal-point-picker/grid.js
index ecd6d6b7d9..ed6d8ae51d 100644
--- a/packages/components/src/focal-point-picker/grid.js
+++ b/packages/components/src/focal-point-picker/grid.js
@@ -1,8 +1,3 @@
-/**
- * WordPress dependencies
- */
-import { useState } from '@wordpress/element';
-
 /**
  * Internal dependencies
  */
@@ -11,21 +6,16 @@ import {
 	GridLineX,
 	GridLineY,
 } from './styles/focal-point-picker-style';
-import { useUpdateEffect } from '../utils/hooks';
-
-export default function FocalPointPickerGrid( { bounds, value, ...props } ) {
-	const animationProps = useRevealAnimation( value );
-	const style = {
-		width: bounds.width,
-		height: bounds.height,
-	};
 
+export default function FocalPointPickerGrid( { bounds, ...props } ) {
 	return (
 		<GridView
 			{ ...props }
-			{ ...animationProps }
 			className="components-focal-point-picker__grid"
-			style={ style }
+			style={ {
+				width: bounds.width,
+				height: bounds.height,
+			} }
 		>
 			<GridLineX style={ { top: '33%' } } />
 			<GridLineX style={ { top: '66%' } } />
@@ -34,25 +24,3 @@ export default function FocalPointPickerGrid( { bounds, value, ...props } ) {
 		</GridView>
 	);
 }
-
-/**
- * Custom hook that renders the "flash" animation whenever the value changes.
- *
- * @param {string} value Value of (box) side.
- */
-function useRevealAnimation( value ) {
-	const [ isActive, setIsActive ] = useState( false );
-
-	useUpdateEffect( () => {
-		setIsActive( true );
-		const timeout = window.setTimeout( () => {
-			setIsActive( false );
-		}, 600 );
-
-		return () => window.clearTimeout( timeout );
-	}, [ value ] );
-
-	return {
-		isActive,
-	};
-}
diff --git a/packages/components/src/focal-point-picker/index.js b/packages/components/src/focal-point-picker/index.js
index 09128c04b9..5c1f594641 100644
--- a/packages/components/src/focal-point-picker/index.js
+++ b/packages/components/src/focal-point-picker/index.js
@@ -27,6 +27,9 @@ import {
 	MediaContainer,
 } from './styles/focal-point-picker-style';
 import { INITIAL_BOUNDS } from './utils';
+import { useUpdateEffect } from '../utils/hooks';
+
+const GRID_OVERLAY_TIMEOUT = 600;
 
 export default function FocalPointPicker( {
 	autoPlay = true,
@@ -45,6 +48,7 @@ export default function FocalPointPicker( {
 	},
 } ) {
 	const [ point, setPoint ] = useState( valueProp );
+	const [ showGridOverlay, setShowGridOverlay ] = useState( false );
 
 	const { startDrag, endDrag, isDragging } = useDragging( {
 		onDragStart: ( event ) => {
@@ -146,6 +150,15 @@ export default function FocalPointPicker( {
 	const instanceId = useInstanceId( FocalPointPicker );
 	const id = `inspector-focal-point-picker-control-${ instanceId }`;
 
+	useUpdateEffect( () => {
+		setShowGridOverlay( true );
+		const timeout = window.setTimeout( () => {
+			setShowGridOverlay( false );
+		}, GRID_OVERLAY_TIMEOUT );
+
+		return () => window.clearTimeout( timeout );
+	}, [ x, y ] );
+
 	return (
 		<BaseControl
 			label={ label }
@@ -165,7 +178,7 @@ export default function FocalPointPicker( {
 					role="button"
 					tabIndex="-1"
 				>
-					<Grid bounds={ bounds } value={ `${ x }${ y }` } />
+					<Grid bounds={ bounds } showOverlay={ showGridOverlay } />
 					<Media
 						alt={ __( 'Media preview' ) }
 						autoPlay={ autoPlay }
diff --git a/packages/components/src/focal-point-picker/styles/focal-point-picker-style.js b/packages/components/src/focal-point-picker/styles/focal-point-picker-style.js
index 0687275c7f..58fa3eb5de 100644
--- a/packages/components/src/focal-point-picker/styles/focal-point-picker-style.js
+++ b/packages/components/src/focal-point-picker/styles/focal-point-picker-style.js
@@ -61,7 +61,6 @@ export const ControlWrapper = styled( Flex )`
 
 export const GridView = styled.div`
 	left: 50%;
-	opacity: 0;
 	overflow: hidden;
 	pointer-events: none;
 	position: absolute;
@@ -70,11 +69,7 @@ export const GridView = styled.div`
 	transition: opacity 120ms linear;
 	z-index: 1;
 
-	${ ( { isActive } ) =>
-		isActive &&
-		`
-		opacity: 1;
-	` }
+	opacity: ${ ( { showOverlay } ) => ( showOverlay ? 1 : 0 ) };
 `;
 
 export const GridLine = styled.div`

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Works for me! I applied it in 4f99530. I also tested again in Storybook and the Post Editor and found it works as expected.

packages/components/src/focal-point-picker/index.js Outdated Show resolved Hide resolved
@stokesman
Copy link
Contributor Author

stokesman commented Jul 28, 2022

One happy find is that I think this PR fixes a bug in trunk where the indicator offset gets weird after scrolling:

I vaguely remember encountering that and I definitely remember simplifying the logic to find the proper offset. Yet I also think that issue is only in Storybook for some reason. Maybe the iframe? So perhaps it could happen in the Site Editor as well (EDIT: probably not because I think only the canvas is in the iframe and not the inspector controls). I can't remember how much I looked into that.

@ciampo
Copy link
Contributor

ciampo commented Aug 16, 2022

Hey @stokesman , do you think you'll be able to finish the work on this one?

@stokesman stokesman force-pushed the refactor/focal-point-picker-fn branch 2 times, most recently from db440cd to e0015da Compare August 23, 2022 02:13
@stokesman
Copy link
Contributor Author

do you think you'll be able to finish the work on this one?

Eventually 😄 Though, where I'd left off there were no requested changes and it seemed like a changelog was all that was required. Since then a couple merges introduced conflicts and I've rebased and resolved those. I also added a commit regarding the conversation Lena started #39168 (comment).

@ciampo
Copy link
Contributor

ciampo commented Aug 23, 2022

Thank you, Mitchell! I gave another round of test in Storybook and the component is looking and behaving well!

Once #39168 (comment) is addressed and a CHANGELOG entry is added, we should be able to merge it!

@stokesman stokesman force-pushed the refactor/focal-point-picker-fn branch from e0015da to 3b88aa4 Compare August 25, 2022 02:40
Copy link
Contributor

@ciampo ciampo left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Great job! 🚀

@ciampo ciampo merged commit 9d72739 into trunk Aug 25, 2022
@ciampo ciampo deleted the refactor/focal-point-picker-fn branch August 25, 2022 09:09
@github-actions github-actions bot added this to the Gutenberg 14.1 milestone Aug 25, 2022
@stokesman
Copy link
Contributor Author

Thanks for testing and reviewing Marco and Lena 🙇

@cbravobernal cbravobernal removed the [Type] Enhancement A suggestion for improvement. label Sep 13, 2022
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
[Package] Components /packages/components [Type] Code Quality Issues or PRs that relate to code quality
Projects
None yet
Development

Successfully merging this pull request may close these issues.

4 participants