@wordpress/editor 12.9.0 → 12.12.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +6 -0
- package/build/components/document-outline/index.js +7 -9
- package/build/components/document-outline/index.js.map +1 -1
- package/build/components/editor-help/index.native.js.map +1 -1
- package/build/components/entities-saved-states/entity-record-item.js.map +1 -1
- package/build/components/entities-saved-states/index.js.map +1 -1
- package/build/components/error-boundary/index.js +3 -0
- package/build/components/error-boundary/index.js.map +1 -1
- package/build/components/global-keyboard-shortcuts/save-shortcut.js.map +1 -1
- package/build/components/index.js +61 -9
- package/build/components/index.js.map +1 -1
- package/build/components/local-autosave-monitor/index.js +24 -19
- package/build/components/local-autosave-monitor/index.js.map +1 -1
- package/build/components/page-attributes/order.js +3 -7
- package/build/components/page-attributes/order.js.map +1 -1
- package/build/components/page-attributes/parent.js +2 -2
- package/build/components/page-attributes/parent.js.map +1 -1
- package/build/components/post-author/select.js.map +1 -1
- package/build/components/post-comments/index.js.map +1 -1
- package/build/components/post-format/index.js +5 -8
- package/build/components/post-format/index.js.map +1 -1
- package/build/components/post-last-revision/check.js.map +1 -1
- package/build/components/post-last-revision/index.js.map +1 -1
- package/build/components/post-pending-status/check.js.map +1 -1
- package/build/components/post-pingbacks/index.js.map +1 -1
- package/build/components/post-publish-button/index.js +4 -2
- package/build/components/post-publish-button/index.js.map +1 -1
- package/build/components/post-publish-panel/index.js.map +1 -1
- package/build/components/post-publish-panel/maybe-category-panel.js +5 -5
- package/build/components/post-publish-panel/maybe-category-panel.js.map +1 -1
- package/build/components/post-publish-panel/maybe-post-format-panel.js.map +1 -1
- package/build/components/post-publish-panel/postpublish.js.map +1 -1
- package/build/components/post-publish-panel/prepublish.js.map +1 -1
- package/build/components/post-schedule/label.js +93 -13
- package/build/components/post-schedule/label.js.map +1 -1
- package/build/components/post-slug/index.js +8 -13
- package/build/components/post-slug/index.js.map +1 -1
- package/build/components/post-sticky/index.js.map +1 -1
- package/build/components/post-switch-to-draft-button/index.js.map +1 -1
- package/build/components/post-taxonomies/flat-term-selector.js +8 -4
- package/build/components/post-taxonomies/flat-term-selector.js.map +1 -1
- package/build/components/post-taxonomies/hierarchical-term-selector.js +1 -0
- package/build/components/post-taxonomies/hierarchical-term-selector.js.map +1 -1
- package/build/components/post-taxonomies/index.js +3 -1
- package/build/components/post-taxonomies/index.js.map +1 -1
- package/build/components/post-template/index.js +1 -2
- package/build/components/post-template/index.js.map +1 -1
- package/build/components/post-title/index.js.map +1 -1
- package/build/components/post-title/index.native.js.map +1 -1
- package/build/components/post-trash/check.js.map +1 -1
- package/build/components/post-url/check.js +54 -0
- package/build/components/post-url/check.js.map +1 -0
- package/build/components/post-url/index.js +115 -0
- package/build/components/post-url/index.js.map +1 -0
- package/build/components/post-url/label.js +30 -0
- package/build/components/post-url/label.js.map +1 -0
- package/build/components/post-visibility/index.js +10 -11
- package/build/components/post-visibility/index.js.map +1 -1
- package/build/components/post-visibility/label.js +5 -0
- package/build/components/post-visibility/label.js.map +1 -1
- package/build/components/provider/index.js.map +1 -1
- package/build/components/provider/index.native.js +0 -1
- package/build/components/provider/index.native.js.map +1 -1
- package/build/components/provider/use-block-editor-settings.js +3 -1
- package/build/components/provider/use-block-editor-settings.js.map +1 -1
- package/build/components/table-of-contents/panel.js +5 -1
- package/build/components/table-of-contents/panel.js.map +1 -1
- package/build/components/template-validation-notice/index.js.map +1 -1
- package/build/components/theme-support-check/index.js +1 -1
- package/build/components/theme-support-check/index.js.map +1 -1
- package/build/components/time-to-read/index.js +60 -0
- package/build/components/time-to-read/index.js.map +1 -0
- package/build/hooks/custom-sources-backwards-compatibility.js.map +1 -1
- package/build/store/actions.js +5 -1
- package/build/store/actions.js.map +1 -1
- package/build/store/reducer.js +1 -1
- package/build/store/reducer.js.map +1 -1
- package/build/store/selectors.js +2 -2
- package/build/store/selectors.js.map +1 -1
- package/build/utils/media-upload/index.js +4 -8
- package/build/utils/media-upload/index.js.map +1 -1
- package/build-module/components/document-outline/index.js +7 -8
- package/build-module/components/document-outline/index.js.map +1 -1
- package/build-module/components/editor-help/index.native.js.map +1 -1
- package/build-module/components/entities-saved-states/entity-record-item.js.map +1 -1
- package/build-module/components/entities-saved-states/index.js.map +1 -1
- package/build-module/components/error-boundary/index.js +2 -0
- package/build-module/components/error-boundary/index.js.map +1 -1
- package/build-module/components/global-keyboard-shortcuts/save-shortcut.js.map +1 -1
- package/build-module/components/index.js +7 -4
- package/build-module/components/index.js.map +1 -1
- package/build-module/components/local-autosave-monitor/index.js +24 -18
- package/build-module/components/local-autosave-monitor/index.js.map +1 -1
- package/build-module/components/page-attributes/order.js +3 -6
- package/build-module/components/page-attributes/order.js.map +1 -1
- package/build-module/components/page-attributes/parent.js +3 -3
- package/build-module/components/page-attributes/parent.js.map +1 -1
- package/build-module/components/post-author/select.js.map +1 -1
- package/build-module/components/post-comments/index.js.map +1 -1
- package/build-module/components/post-format/index.js +5 -8
- package/build-module/components/post-format/index.js.map +1 -1
- package/build-module/components/post-last-revision/check.js.map +1 -1
- package/build-module/components/post-last-revision/index.js.map +1 -1
- package/build-module/components/post-pending-status/check.js.map +1 -1
- package/build-module/components/post-pingbacks/index.js.map +1 -1
- package/build-module/components/post-publish-button/index.js +4 -1
- package/build-module/components/post-publish-button/index.js.map +1 -1
- package/build-module/components/post-publish-panel/index.js.map +1 -1
- package/build-module/components/post-publish-panel/maybe-category-panel.js +5 -5
- package/build-module/components/post-publish-panel/maybe-category-panel.js.map +1 -1
- package/build-module/components/post-publish-panel/maybe-post-format-panel.js.map +1 -1
- package/build-module/components/post-publish-panel/postpublish.js.map +1 -1
- package/build-module/components/post-publish-panel/prepublish.js.map +1 -1
- package/build-module/components/post-schedule/label.js +90 -13
- package/build-module/components/post-schedule/label.js.map +1 -1
- package/build-module/components/post-slug/index.js +8 -14
- package/build-module/components/post-slug/index.js.map +1 -1
- package/build-module/components/post-sticky/index.js.map +1 -1
- package/build-module/components/post-switch-to-draft-button/index.js.map +1 -1
- package/build-module/components/post-taxonomies/flat-term-selector.js +8 -6
- package/build-module/components/post-taxonomies/flat-term-selector.js.map +1 -1
- package/build-module/components/post-taxonomies/hierarchical-term-selector.js +1 -2
- package/build-module/components/post-taxonomies/hierarchical-term-selector.js.map +1 -1
- package/build-module/components/post-taxonomies/index.js +4 -1
- package/build-module/components/post-taxonomies/index.js.map +1 -1
- package/build-module/components/post-template/index.js +1 -2
- package/build-module/components/post-template/index.js.map +1 -1
- package/build-module/components/post-title/index.js.map +1 -1
- package/build-module/components/post-title/index.native.js.map +1 -1
- package/build-module/components/post-trash/check.js.map +1 -1
- package/build-module/components/post-url/check.js +44 -0
- package/build-module/components/post-url/check.js.map +1 -0
- package/build-module/components/post-url/index.js +102 -0
- package/build-module/components/post-url/index.js.map +1 -0
- package/build-module/components/post-url/label.js +18 -0
- package/build-module/components/post-url/label.js.map +1 -0
- package/build-module/components/post-visibility/index.js +12 -13
- package/build-module/components/post-visibility/index.js.map +1 -1
- package/build-module/components/post-visibility/label.js +3 -0
- package/build-module/components/post-visibility/label.js.map +1 -1
- package/build-module/components/provider/index.js.map +1 -1
- package/build-module/components/provider/index.native.js +0 -1
- package/build-module/components/provider/index.native.js.map +1 -1
- package/build-module/components/provider/use-block-editor-settings.js +4 -2
- package/build-module/components/provider/use-block-editor-settings.js.map +1 -1
- package/build-module/components/table-of-contents/panel.js +4 -1
- package/build-module/components/table-of-contents/panel.js.map +1 -1
- package/build-module/components/template-validation-notice/index.js.map +1 -1
- package/build-module/components/theme-support-check/index.js +2 -2
- package/build-module/components/theme-support-check/index.js.map +1 -1
- package/build-module/components/time-to-read/index.js +50 -0
- package/build-module/components/time-to-read/index.js.map +1 -0
- package/build-module/hooks/custom-sources-backwards-compatibility.js.map +1 -1
- package/build-module/store/actions.js +5 -1
- package/build-module/store/actions.js.map +1 -1
- package/build-module/store/reducer.js +2 -2
- package/build-module/store/reducer.js.map +1 -1
- package/build-module/store/selectors.js +3 -3
- package/build-module/store/selectors.js.map +1 -1
- package/build-module/utils/media-upload/index.js +3 -5
- package/build-module/utils/media-upload/index.js.map +1 -1
- package/build-style/style-rtl.css +12 -30
- package/build-style/style.css +15 -29
- package/package.json +28 -28
- package/src/components/document-outline/index.js +9 -8
- package/src/components/editor-help/index.native.js +6 -6
- package/src/components/entities-saved-states/entity-record-item.js +6 -6
- package/src/components/entities-saved-states/index.js +6 -9
- package/src/components/error-boundary/index.js +3 -0
- package/src/components/global-keyboard-shortcuts/save-shortcut.js +2 -3
- package/src/components/index.js +13 -4
- package/src/components/local-autosave-monitor/index.js +39 -38
- package/src/components/page-attributes/order.js +1 -9
- package/src/components/page-attributes/parent.js +6 -10
- package/src/components/post-author/select.js +2 -3
- package/src/components/post-comments/index.js +4 -3
- package/src/components/post-format/index.js +15 -22
- package/src/components/post-format/style.scss +2 -17
- package/src/components/post-last-revision/check.js +2 -4
- package/src/components/post-last-revision/index.js +2 -4
- package/src/components/post-pending-status/check.js +2 -5
- package/src/components/post-pingbacks/index.js +2 -3
- package/src/components/post-publish-button/index.js +7 -8
- package/src/components/post-publish-panel/index.js +2 -3
- package/src/components/post-publish-panel/maybe-category-panel.js +7 -5
- package/src/components/post-publish-panel/maybe-post-format-panel.js +2 -3
- package/src/components/post-publish-panel/postpublish.js +2 -5
- package/src/components/post-publish-panel/prepublish.js +2 -3
- package/src/components/post-publish-panel/test/__snapshots__/index.js.snap +1 -1
- package/src/components/post-schedule/label.js +111 -17
- package/src/components/post-schedule/test/label.js +127 -15
- package/src/components/post-slug/index.js +9 -16
- package/src/components/post-slug/test/index.js +7 -6
- package/src/components/post-sticky/index.js +2 -3
- package/src/components/post-switch-to-draft-button/index.js +2 -5
- package/src/components/post-taxonomies/flat-term-selector.js +10 -13
- package/src/components/post-taxonomies/hierarchical-term-selector.js +5 -7
- package/src/components/post-taxonomies/index.js +3 -1
- package/src/components/post-template/index.js +1 -1
- package/src/components/post-title/index.js +21 -31
- package/src/components/post-title/index.native.js +10 -16
- package/src/components/post-title/style.scss +1 -1
- package/src/components/post-trash/check.js +2 -3
- package/src/components/post-url/check.js +38 -0
- package/src/components/post-url/index.js +122 -0
- package/src/components/post-url/label.js +22 -0
- package/src/components/post-url/style.scss +16 -0
- package/src/components/post-visibility/index.js +11 -17
- package/src/components/post-visibility/label.js +4 -0
- package/src/components/post-visibility/style.scss +0 -17
- package/src/components/provider/index.js +2 -3
- package/src/components/provider/index.native.js +12 -17
- package/src/components/provider/use-block-editor-settings.js +4 -8
- package/src/components/table-of-contents/panel.js +7 -2
- package/src/components/template-validation-notice/index.js +2 -3
- package/src/components/theme-support-check/index.js +2 -2
- package/src/components/time-to-read/index.js +59 -0
- package/src/hooks/custom-sources-backwards-compatibility.js +45 -44
- package/src/store/actions.js +213 -190
- package/src/store/reducer.js +2 -2
- package/src/store/selectors.js +17 -25
- package/src/store/test/selectors.js +10 -13
- package/src/style.scss +1 -0
- package/src/utils/media-upload/index.js +2 -5
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
/**
|
|
2
2
|
* External dependencies
|
|
3
3
|
*/
|
|
4
|
-
import {
|
|
4
|
+
import { get, some } from 'lodash';
|
|
5
5
|
import classnames from 'classnames';
|
|
6
6
|
|
|
7
7
|
/**
|
|
@@ -19,15 +19,16 @@ import { __ } from '@wordpress/i18n';
|
|
|
19
19
|
import PublishButtonLabel from './label';
|
|
20
20
|
import { store as editorStore } from '../../store';
|
|
21
21
|
|
|
22
|
+
const noop = () => {};
|
|
23
|
+
|
|
22
24
|
export class PostPublishButton extends Component {
|
|
23
25
|
constructor( props ) {
|
|
24
26
|
super( props );
|
|
25
27
|
this.buttonNode = createRef();
|
|
26
28
|
|
|
27
29
|
this.createOnClick = this.createOnClick.bind( this );
|
|
28
|
-
this.closeEntitiesSavedStates =
|
|
29
|
-
this
|
|
30
|
-
);
|
|
30
|
+
this.closeEntitiesSavedStates =
|
|
31
|
+
this.closeEntitiesSavedStates.bind( this );
|
|
31
32
|
|
|
32
33
|
this.state = {
|
|
33
34
|
entitiesSavedStatesCallback: false,
|
|
@@ -41,10 +42,8 @@ export class PostPublishButton extends Component {
|
|
|
41
42
|
|
|
42
43
|
createOnClick( callback ) {
|
|
43
44
|
return ( ...args ) => {
|
|
44
|
-
const {
|
|
45
|
-
|
|
46
|
-
setEntitiesSavedStatesCallback,
|
|
47
|
-
} = this.props;
|
|
45
|
+
const { hasNonPostEntityChanges, setEntitiesSavedStatesCallback } =
|
|
46
|
+
this.props;
|
|
48
47
|
// If a post with non-post entities is published, but the user
|
|
49
48
|
// elects to not save changes to the non-post entities, those
|
|
50
49
|
// entities will still be dirty when the Publish button is clicked.
|
|
@@ -167,9 +167,8 @@ export default compose( [
|
|
|
167
167
|
};
|
|
168
168
|
} ),
|
|
169
169
|
withDispatch( ( dispatch, { isPublishSidebarEnabled } ) => {
|
|
170
|
-
const { disablePublishSidebar, enablePublishSidebar } =
|
|
171
|
-
editorStore
|
|
172
|
-
);
|
|
170
|
+
const { disablePublishSidebar, enablePublishSidebar } =
|
|
171
|
+
dispatch( editorStore );
|
|
173
172
|
return {
|
|
174
173
|
onTogglePublishSidebar: () => {
|
|
175
174
|
if ( isPublishSidebarEnabled ) {
|
|
@@ -21,15 +21,17 @@ import { store as editorStore } from '../../store';
|
|
|
21
21
|
function MaybeCategoryPanel() {
|
|
22
22
|
const hasNoCategory = useSelect( ( select ) => {
|
|
23
23
|
const postType = select( editorStore ).getCurrentPostType();
|
|
24
|
-
const categoriesTaxonomy =
|
|
25
|
-
'category'
|
|
26
|
-
)
|
|
27
|
-
|
|
24
|
+
const categoriesTaxonomy =
|
|
25
|
+
select( coreStore ).getTaxonomy( 'category' );
|
|
26
|
+
const defaultCategoryId = select( coreStore ).getEntityRecord(
|
|
27
|
+
'root',
|
|
28
|
+
'site'
|
|
29
|
+
)?.default_category;
|
|
28
30
|
const defaultCategory = select( coreStore ).getEntityRecords(
|
|
29
31
|
'taxonomy',
|
|
30
32
|
'category',
|
|
31
33
|
{
|
|
32
|
-
|
|
34
|
+
id: defaultCategoryId,
|
|
33
35
|
}
|
|
34
36
|
)?.[ 0 ];
|
|
35
37
|
const postTypeSupportsCategories =
|
|
@@ -39,9 +39,8 @@ const PostFormatSuggestion = ( {
|
|
|
39
39
|
|
|
40
40
|
export default function PostFormatPanel() {
|
|
41
41
|
const { currentPostFormat, suggestion } = useSelect( ( select ) => {
|
|
42
|
-
const { getEditedPostAttribute, getSuggestedPostFormat } =
|
|
43
|
-
editorStore
|
|
44
|
-
);
|
|
42
|
+
const { getEditedPostAttribute, getSuggestedPostFormat } =
|
|
43
|
+
select( editorStore );
|
|
45
44
|
const supportedFormats = get(
|
|
46
45
|
select( coreStore ).getThemeSupports(),
|
|
47
46
|
[ 'formats' ],
|
|
@@ -163,11 +163,8 @@ class PostPublishPanelPostpublish extends Component {
|
|
|
163
163
|
}
|
|
164
164
|
|
|
165
165
|
export default withSelect( ( select ) => {
|
|
166
|
-
const {
|
|
167
|
-
|
|
168
|
-
getCurrentPost,
|
|
169
|
-
isCurrentPostScheduled,
|
|
170
|
-
} = select( editorStore );
|
|
166
|
+
const { getEditedPostAttribute, getCurrentPost, isCurrentPostScheduled } =
|
|
167
|
+
select( editorStore );
|
|
171
168
|
const { getPostType } = select( coreStore );
|
|
172
169
|
|
|
173
170
|
return {
|
|
@@ -35,9 +35,8 @@ function PostPublishPanelPrepublish( { children } ) {
|
|
|
35
35
|
siteTitle,
|
|
36
36
|
siteHome,
|
|
37
37
|
} = useSelect( ( select ) => {
|
|
38
|
-
const { getCurrentPost, isEditedPostBeingScheduled } =
|
|
39
|
-
editorStore
|
|
40
|
-
);
|
|
38
|
+
const { getCurrentPost, isEditedPostBeingScheduled } =
|
|
39
|
+
select( editorStore );
|
|
41
40
|
const { getEntityRecord, isResolving } = select( coreStore );
|
|
42
41
|
const siteData =
|
|
43
42
|
getEntityRecord( 'root', '__unstableBase', undefined ) || {};
|
|
@@ -184,7 +184,7 @@ exports[`PostPublishPanel should render the spinner if the post is being saved 1
|
|
|
184
184
|
<div
|
|
185
185
|
className="editor-post-publish-panel__content"
|
|
186
186
|
>
|
|
187
|
-
<
|
|
187
|
+
<ForwardRef(UnforwardedSpinner) />
|
|
188
188
|
</div>
|
|
189
189
|
<div
|
|
190
190
|
className="editor-post-publish-panel__footer"
|
|
@@ -1,28 +1,122 @@
|
|
|
1
1
|
/**
|
|
2
2
|
* WordPress dependencies
|
|
3
3
|
*/
|
|
4
|
-
import { __ } from '@wordpress/i18n';
|
|
5
|
-
import {
|
|
6
|
-
import {
|
|
4
|
+
import { __, _x, sprintf, isRTL } from '@wordpress/i18n';
|
|
5
|
+
import { __experimentalGetSettings, getDate, dateI18n } from '@wordpress/date';
|
|
6
|
+
import { useSelect } from '@wordpress/data';
|
|
7
7
|
|
|
8
8
|
/**
|
|
9
9
|
* Internal dependencies
|
|
10
10
|
*/
|
|
11
11
|
import { store as editorStore } from '../../store';
|
|
12
12
|
|
|
13
|
-
export function PostScheduleLabel(
|
|
14
|
-
|
|
15
|
-
return date && ! isFloating
|
|
16
|
-
? format(
|
|
17
|
-
`${ settings.formats.date } ${ settings.formats.time }`,
|
|
18
|
-
date
|
|
19
|
-
)
|
|
20
|
-
: __( 'Immediately' );
|
|
13
|
+
export default function PostScheduleLabel( props ) {
|
|
14
|
+
return usePostScheduleLabel( props );
|
|
21
15
|
}
|
|
22
16
|
|
|
23
|
-
export
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
} )
|
|
17
|
+
export function usePostScheduleLabel( { full = false } = {} ) {
|
|
18
|
+
const { date, isFloating } = useSelect(
|
|
19
|
+
( select ) => ( {
|
|
20
|
+
date: select( editorStore ).getEditedPostAttribute( 'date' ),
|
|
21
|
+
isFloating: select( editorStore ).isEditedPostDateFloating(),
|
|
22
|
+
} ),
|
|
23
|
+
[]
|
|
24
|
+
);
|
|
25
|
+
|
|
26
|
+
return full
|
|
27
|
+
? getFullPostScheduleLabel( date )
|
|
28
|
+
: getPostScheduleLabel( date, { isFloating } );
|
|
29
|
+
}
|
|
30
|
+
|
|
31
|
+
export function getFullPostScheduleLabel( dateAttribute ) {
|
|
32
|
+
const date = getDate( dateAttribute );
|
|
33
|
+
|
|
34
|
+
const timezoneAbbreviation = getTimezoneAbbreviation();
|
|
35
|
+
const formattedDate = dateI18n(
|
|
36
|
+
// translators: If using a space between 'g:i' and 'a', use a non-breaking sapce.
|
|
37
|
+
_x( 'F j, Y g:i\xa0a', 'post schedule full date format' ),
|
|
38
|
+
date
|
|
39
|
+
);
|
|
40
|
+
return isRTL()
|
|
41
|
+
? `${ timezoneAbbreviation } ${ formattedDate }`
|
|
42
|
+
: `${ formattedDate } ${ timezoneAbbreviation }`;
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
export function getPostScheduleLabel(
|
|
46
|
+
dateAttribute,
|
|
47
|
+
{ isFloating = false, now = new Date() } = {}
|
|
48
|
+
) {
|
|
49
|
+
if ( ! dateAttribute || isFloating ) {
|
|
50
|
+
return __( 'Immediately' );
|
|
51
|
+
}
|
|
52
|
+
|
|
53
|
+
// If the user timezone does not equal the site timezone then using words
|
|
54
|
+
// like 'tomorrow' is confusing, so show the full date.
|
|
55
|
+
if ( ! isTimezoneSameAsSiteTimezone( now ) ) {
|
|
56
|
+
return getFullPostScheduleLabel( dateAttribute );
|
|
57
|
+
}
|
|
58
|
+
|
|
59
|
+
const date = getDate( dateAttribute );
|
|
60
|
+
|
|
61
|
+
if ( isSameDay( date, now ) ) {
|
|
62
|
+
return sprintf(
|
|
63
|
+
// translators: %s: Time of day the post is scheduled for.
|
|
64
|
+
__( 'Today at %s' ),
|
|
65
|
+
// translators: If using a space between 'g:i' and 'a', use a non-breaking sapce.
|
|
66
|
+
dateI18n( _x( 'g:i\xa0a', 'post schedule time format' ), date )
|
|
67
|
+
);
|
|
68
|
+
}
|
|
69
|
+
|
|
70
|
+
const tomorrow = new Date( now );
|
|
71
|
+
tomorrow.setDate( tomorrow.getDate() + 1 );
|
|
72
|
+
|
|
73
|
+
if ( isSameDay( date, tomorrow ) ) {
|
|
74
|
+
return sprintf(
|
|
75
|
+
// translators: %s: Time of day the post is scheduled for.
|
|
76
|
+
__( 'Tomorrow at %s' ),
|
|
77
|
+
// translators: If using a space between 'g:i' and 'a', use a non-breaking sapce.
|
|
78
|
+
dateI18n( _x( 'g:i\xa0a', 'post schedule time format' ), date )
|
|
79
|
+
);
|
|
80
|
+
}
|
|
81
|
+
|
|
82
|
+
if ( date.getFullYear() === now.getFullYear() ) {
|
|
83
|
+
return dateI18n(
|
|
84
|
+
// translators: If using a space between 'g:i' and 'a', use a non-breaking sapce.
|
|
85
|
+
_x( 'F j g:i\xa0a', 'post schedule date format without year' ),
|
|
86
|
+
date
|
|
87
|
+
);
|
|
88
|
+
}
|
|
89
|
+
|
|
90
|
+
return dateI18n(
|
|
91
|
+
// translators: Use a non-breaking space between 'g:i' and 'a' if appropriate.
|
|
92
|
+
_x( 'F j, Y g:i\xa0a', 'post schedule full date format' ),
|
|
93
|
+
date
|
|
94
|
+
);
|
|
95
|
+
}
|
|
96
|
+
|
|
97
|
+
function getTimezoneAbbreviation() {
|
|
98
|
+
const { timezone } = __experimentalGetSettings();
|
|
99
|
+
|
|
100
|
+
if ( timezone.abbr && isNaN( Number( timezone.abbr ) ) ) {
|
|
101
|
+
return timezone.abbr;
|
|
102
|
+
}
|
|
103
|
+
|
|
104
|
+
const symbol = timezone.offset < 0 ? '' : '+';
|
|
105
|
+
return `UTC${ symbol }${ timezone.offset }`;
|
|
106
|
+
}
|
|
107
|
+
|
|
108
|
+
function isTimezoneSameAsSiteTimezone( date ) {
|
|
109
|
+
const { timezone } = __experimentalGetSettings();
|
|
110
|
+
|
|
111
|
+
const siteOffset = Number( timezone.offset );
|
|
112
|
+
const dateOffset = -1 * ( date.getTimezoneOffset() / 60 );
|
|
113
|
+
return siteOffset === dateOffset;
|
|
114
|
+
}
|
|
115
|
+
|
|
116
|
+
function isSameDay( left, right ) {
|
|
117
|
+
return (
|
|
118
|
+
left.getDate() === right.getDate() &&
|
|
119
|
+
left.getMonth() === right.getMonth() &&
|
|
120
|
+
left.getFullYear() === right.getFullYear()
|
|
121
|
+
);
|
|
122
|
+
}
|
|
@@ -1,32 +1,144 @@
|
|
|
1
1
|
/**
|
|
2
|
-
*
|
|
2
|
+
* WordPress dependencies
|
|
3
3
|
*/
|
|
4
|
-
import {
|
|
4
|
+
import { __experimentalGetSettings, setSettings } from '@wordpress/date';
|
|
5
5
|
|
|
6
6
|
/**
|
|
7
7
|
* Internal dependencies
|
|
8
8
|
*/
|
|
9
|
-
import {
|
|
9
|
+
import { getFullPostScheduleLabel, getPostScheduleLabel } from '../label';
|
|
10
10
|
|
|
11
|
-
describe( '
|
|
11
|
+
describe( 'getFullPostScheduleLabel', () => {
|
|
12
|
+
it( 'should show a date', () => {
|
|
13
|
+
const label = getFullPostScheduleLabel( '2022-04-28T15:30:00' );
|
|
14
|
+
expect( label ).toBe( 'April 28, 2022 3:30\xa0pm UTC+0' ); // Unused, for backwards compatibility.
|
|
15
|
+
} );
|
|
16
|
+
|
|
17
|
+
it( "should show site's timezone abbr", () => {
|
|
18
|
+
const settings = __experimentalGetSettings();
|
|
19
|
+
|
|
20
|
+
setSettings( {
|
|
21
|
+
...settings,
|
|
22
|
+
timezone: { offset: 10, string: 'Australia/Sydney', abbr: 'AEST' },
|
|
23
|
+
} );
|
|
24
|
+
|
|
25
|
+
const label = getFullPostScheduleLabel( '2022-04-28T15:30:00' );
|
|
26
|
+
expect( label ).toBe( 'April 28, 2022 3:30\xa0pm AEST' );
|
|
27
|
+
|
|
28
|
+
setSettings( settings );
|
|
29
|
+
} );
|
|
30
|
+
|
|
31
|
+
it( "should show site's timezone offset", () => {
|
|
32
|
+
const settings = __experimentalGetSettings();
|
|
33
|
+
|
|
34
|
+
setSettings( {
|
|
35
|
+
...settings,
|
|
36
|
+
timezone: { offset: 10 },
|
|
37
|
+
} );
|
|
38
|
+
|
|
39
|
+
const label = getFullPostScheduleLabel( '2022-04-28T15:30:00' );
|
|
40
|
+
expect( label ).toBe( 'April 28, 2022 3:30\xa0pm UTC+10' );
|
|
41
|
+
|
|
42
|
+
setSettings( settings );
|
|
43
|
+
} );
|
|
44
|
+
} );
|
|
45
|
+
|
|
46
|
+
describe( 'getPostScheduleLabel', () => {
|
|
12
47
|
it( 'should show the post will be published immediately if no publish date is set', () => {
|
|
13
|
-
const
|
|
14
|
-
expect(
|
|
48
|
+
const label = getPostScheduleLabel( undefined );
|
|
49
|
+
expect( label ).toBe( 'Immediately' );
|
|
15
50
|
} );
|
|
16
51
|
|
|
17
52
|
it( 'should show the post will be published immediately if it has a floating date', () => {
|
|
18
|
-
const
|
|
19
|
-
|
|
20
|
-
|
|
53
|
+
const label = getPostScheduleLabel( '2022-04-28T15:30:00', {
|
|
54
|
+
isFloating: true,
|
|
55
|
+
} );
|
|
56
|
+
expect( label ).toBe( 'Immediately' );
|
|
57
|
+
} );
|
|
58
|
+
|
|
59
|
+
it( "should show full date if user timezone does not equal site's timezone", () => {
|
|
60
|
+
const now = new Date( '2022-04-28T13:00:00.000Z' );
|
|
61
|
+
jest.spyOn( now, 'getTimezoneOffset' ).mockImplementationOnce(
|
|
62
|
+
() => 10 * -60 // UTC+10
|
|
21
63
|
);
|
|
22
|
-
|
|
64
|
+
|
|
65
|
+
const label = getPostScheduleLabel( '2022-04-28T15:30:00', { now } );
|
|
66
|
+
expect( label ).toBe( 'April 28, 2022 3:30\xa0pm UTC+0' );
|
|
23
67
|
} );
|
|
24
68
|
|
|
25
|
-
it(
|
|
26
|
-
const
|
|
27
|
-
|
|
28
|
-
|
|
69
|
+
it( "should show today if date is same day as now and user timezone equals site's timezone", () => {
|
|
70
|
+
const settings = __experimentalGetSettings();
|
|
71
|
+
|
|
72
|
+
setSettings( {
|
|
73
|
+
...settings,
|
|
74
|
+
timezone: { offset: 10 },
|
|
75
|
+
} );
|
|
76
|
+
|
|
77
|
+
const now = new Date( '2022-04-28T03:00:00.000Z' );
|
|
78
|
+
jest.spyOn( now, 'getTimezoneOffset' ).mockImplementationOnce(
|
|
79
|
+
() => 10 * -60 // UTC+10
|
|
29
80
|
);
|
|
30
|
-
|
|
81
|
+
|
|
82
|
+
const label = getPostScheduleLabel( '2022-04-28T15:30:00', { now } );
|
|
83
|
+
expect( label ).toBe( 'Today at 3:30\xa0pm' );
|
|
84
|
+
|
|
85
|
+
setSettings( settings );
|
|
86
|
+
} );
|
|
87
|
+
|
|
88
|
+
it( "should show tomorrow if date is same day as now + 1 day and user timezone equals site's timezone", () => {
|
|
89
|
+
const settings = __experimentalGetSettings();
|
|
90
|
+
|
|
91
|
+
setSettings( {
|
|
92
|
+
...settings,
|
|
93
|
+
timezone: { offset: 10 },
|
|
94
|
+
} );
|
|
95
|
+
|
|
96
|
+
const now = new Date( '2022-04-28T03:00:00.000Z' );
|
|
97
|
+
jest.spyOn( now, 'getTimezoneOffset' ).mockImplementationOnce(
|
|
98
|
+
() => 10 * -60 // UTC+10
|
|
99
|
+
);
|
|
100
|
+
|
|
101
|
+
const label = getPostScheduleLabel( '2022-04-29T15:30:00', { now } );
|
|
102
|
+
expect( label ).toBe( 'Tomorrow at 3:30\xa0pm' );
|
|
103
|
+
|
|
104
|
+
setSettings( settings );
|
|
105
|
+
} );
|
|
106
|
+
|
|
107
|
+
it( "should hide year if date is same year as now and user timezone equals site's timezone", () => {
|
|
108
|
+
const settings = __experimentalGetSettings();
|
|
109
|
+
|
|
110
|
+
setSettings( {
|
|
111
|
+
...settings,
|
|
112
|
+
timezone: { offset: 10 },
|
|
113
|
+
} );
|
|
114
|
+
|
|
115
|
+
const now = new Date( '2022-04-28T03:00:00.000Z' );
|
|
116
|
+
jest.spyOn( now, 'getTimezoneOffset' ).mockImplementationOnce(
|
|
117
|
+
() => 10 * -60 // UTC+10
|
|
118
|
+
);
|
|
119
|
+
|
|
120
|
+
const label = getPostScheduleLabel( '2022-12-25T15:30:00', { now } );
|
|
121
|
+
expect( label ).toBe( 'December 25 3:30\xa0pm' );
|
|
122
|
+
|
|
123
|
+
setSettings( settings );
|
|
124
|
+
} );
|
|
125
|
+
|
|
126
|
+
it( "should show year if date is not same year as now and user timezone equals site's timezone", () => {
|
|
127
|
+
const settings = __experimentalGetSettings();
|
|
128
|
+
|
|
129
|
+
setSettings( {
|
|
130
|
+
...settings,
|
|
131
|
+
timezone: { offset: 10 },
|
|
132
|
+
} );
|
|
133
|
+
|
|
134
|
+
const now = new Date( '2022-04-28T03:00:00.000Z' );
|
|
135
|
+
jest.spyOn( now, 'getTimezoneOffset' ).mockImplementationOnce(
|
|
136
|
+
() => 10 * -60 // UTC+10
|
|
137
|
+
);
|
|
138
|
+
|
|
139
|
+
const label = getPostScheduleLabel( '2023-04-28T15:30:00', { now } );
|
|
140
|
+
expect( label ).toBe( 'April 28, 2023 3:30\xa0pm' );
|
|
141
|
+
|
|
142
|
+
setSettings( settings );
|
|
31
143
|
} );
|
|
32
144
|
} );
|
|
@@ -4,8 +4,9 @@
|
|
|
4
4
|
import { withDispatch, withSelect } from '@wordpress/data';
|
|
5
5
|
import { Component } from '@wordpress/element';
|
|
6
6
|
import { __ } from '@wordpress/i18n';
|
|
7
|
-
import {
|
|
7
|
+
import { compose } from '@wordpress/compose';
|
|
8
8
|
import { safeDecodeURIComponent, cleanForSlug } from '@wordpress/url';
|
|
9
|
+
import { TextControl } from '@wordpress/components';
|
|
9
10
|
|
|
10
11
|
/**
|
|
11
12
|
* Internal dependencies
|
|
@@ -41,25 +42,19 @@ export class PostSlug extends Component {
|
|
|
41
42
|
}
|
|
42
43
|
|
|
43
44
|
render() {
|
|
44
|
-
const { instanceId } = this.props;
|
|
45
45
|
const { editedSlug } = this.state;
|
|
46
|
-
|
|
47
|
-
const inputId = 'editor-post-slug-' + instanceId;
|
|
48
|
-
|
|
49
46
|
return (
|
|
50
47
|
<PostSlugCheck>
|
|
51
|
-
<
|
|
52
|
-
|
|
48
|
+
<TextControl
|
|
49
|
+
label={ __( 'Slug' ) }
|
|
53
50
|
autoComplete="off"
|
|
54
51
|
spellCheck="false"
|
|
55
|
-
type="text"
|
|
56
|
-
id={ inputId }
|
|
57
52
|
value={ editedSlug }
|
|
58
|
-
onChange={ (
|
|
59
|
-
this.setState( { editedSlug:
|
|
53
|
+
onChange={ ( slug ) =>
|
|
54
|
+
this.setState( { editedSlug: slug } )
|
|
60
55
|
}
|
|
61
56
|
onBlur={ this.setSlug }
|
|
62
|
-
className="editor-post-
|
|
57
|
+
className="editor-post-slug"
|
|
63
58
|
/>
|
|
64
59
|
</PostSlugCheck>
|
|
65
60
|
);
|
|
@@ -68,9 +63,8 @@ export class PostSlug extends Component {
|
|
|
68
63
|
|
|
69
64
|
export default compose( [
|
|
70
65
|
withSelect( ( select ) => {
|
|
71
|
-
const { getCurrentPost, getEditedPostAttribute } =
|
|
72
|
-
editorStore
|
|
73
|
-
);
|
|
66
|
+
const { getCurrentPost, getEditedPostAttribute } =
|
|
67
|
+
select( editorStore );
|
|
74
68
|
|
|
75
69
|
const { id } = getCurrentPost();
|
|
76
70
|
return {
|
|
@@ -87,5 +81,4 @@ export default compose( [
|
|
|
87
81
|
},
|
|
88
82
|
};
|
|
89
83
|
} ),
|
|
90
|
-
withInstanceId,
|
|
91
84
|
] )( PostSlug );
|
|
@@ -3,6 +3,11 @@
|
|
|
3
3
|
*/
|
|
4
4
|
import { shallow } from 'enzyme';
|
|
5
5
|
|
|
6
|
+
/**
|
|
7
|
+
* WordPress dependencies
|
|
8
|
+
*/
|
|
9
|
+
import { TextControl } from '@wordpress/components';
|
|
10
|
+
|
|
6
11
|
/**
|
|
7
12
|
* Internal dependencies
|
|
8
13
|
*/
|
|
@@ -13,11 +18,7 @@ describe( 'PostSlug', () => {
|
|
|
13
18
|
it( 'should update internal slug', () => {
|
|
14
19
|
const wrapper = shallow( <PostSlug postSlug="index" /> );
|
|
15
20
|
|
|
16
|
-
wrapper.find( '
|
|
17
|
-
target: {
|
|
18
|
-
value: 'single',
|
|
19
|
-
},
|
|
20
|
-
} );
|
|
21
|
+
wrapper.find( TextControl ).prop( 'onChange' )( 'single' );
|
|
21
22
|
|
|
22
23
|
expect( wrapper.state().editedSlug ).toEqual( 'single' );
|
|
23
24
|
} );
|
|
@@ -28,7 +29,7 @@ describe( 'PostSlug', () => {
|
|
|
28
29
|
<PostSlug postSlug="index" onUpdateSlug={ onUpdateSlug } />
|
|
29
30
|
);
|
|
30
31
|
|
|
31
|
-
wrapper.find(
|
|
32
|
+
wrapper.find( TextControl ).prop( 'onBlur' )( {
|
|
32
33
|
target: {
|
|
33
34
|
value: 'single',
|
|
34
35
|
},
|
|
@@ -27,9 +27,8 @@ export function PostSticky( { onUpdateSticky, postSticky = false } ) {
|
|
|
27
27
|
export default compose( [
|
|
28
28
|
withSelect( ( select ) => {
|
|
29
29
|
return {
|
|
30
|
-
postSticky:
|
|
31
|
-
'sticky'
|
|
32
|
-
),
|
|
30
|
+
postSticky:
|
|
31
|
+
select( editorStore ).getEditedPostAttribute( 'sticky' ),
|
|
33
32
|
};
|
|
34
33
|
} ),
|
|
35
34
|
withDispatch( ( dispatch ) => {
|
|
@@ -65,11 +65,8 @@ function PostSwitchToDraftButton( {
|
|
|
65
65
|
|
|
66
66
|
export default compose( [
|
|
67
67
|
withSelect( ( select ) => {
|
|
68
|
-
const {
|
|
69
|
-
|
|
70
|
-
isCurrentPostPublished,
|
|
71
|
-
isCurrentPostScheduled,
|
|
72
|
-
} = select( editorStore );
|
|
68
|
+
const { isSavingPost, isCurrentPostPublished, isCurrentPostScheduled } =
|
|
69
|
+
select( editorStore );
|
|
73
70
|
return {
|
|
74
71
|
isSaving: isSavingPost(),
|
|
75
72
|
isPublished: isCurrentPostPublished(),
|
|
@@ -55,11 +55,11 @@ const termNamesToIds = ( names, terms ) => {
|
|
|
55
55
|
};
|
|
56
56
|
|
|
57
57
|
// Tries to create a term or fetch it if it already exists.
|
|
58
|
-
function findOrCreateTerm( termName, restBase ) {
|
|
58
|
+
function findOrCreateTerm( termName, restBase, namespace ) {
|
|
59
59
|
const escapedTermName = escapeString( termName );
|
|
60
60
|
|
|
61
61
|
return apiFetch( {
|
|
62
|
-
path:
|
|
62
|
+
path: `/${ namespace }/${ restBase }`,
|
|
63
63
|
method: 'POST',
|
|
64
64
|
data: { name: escapedTermName },
|
|
65
65
|
} )
|
|
@@ -68,7 +68,7 @@ function findOrCreateTerm( termName, restBase ) {
|
|
|
68
68
|
if ( errorCode === 'term_exists' ) {
|
|
69
69
|
// If the terms exist, fetch it instead of creating a new one.
|
|
70
70
|
const addRequest = apiFetch( {
|
|
71
|
-
path: addQueryArgs(
|
|
71
|
+
path: addQueryArgs( `/${ namespace }/${ restBase }`, {
|
|
72
72
|
...DEFAULT_QUERY,
|
|
73
73
|
search: escapedTermName,
|
|
74
74
|
} ),
|
|
@@ -86,7 +86,7 @@ function findOrCreateTerm( termName, restBase ) {
|
|
|
86
86
|
.then( unescapeTerm );
|
|
87
87
|
}
|
|
88
88
|
|
|
89
|
-
function FlatTermSelector( { slug } ) {
|
|
89
|
+
export function FlatTermSelector( { slug } ) {
|
|
90
90
|
const [ values, setValues ] = useState( [] );
|
|
91
91
|
const [ search, setSearch ] = useState( '' );
|
|
92
92
|
const debouncedSearch = useDebounce( setSearch, 500 );
|
|
@@ -100,14 +100,10 @@ function FlatTermSelector( { slug } ) {
|
|
|
100
100
|
hasResolvedTerms,
|
|
101
101
|
} = useSelect(
|
|
102
102
|
( select ) => {
|
|
103
|
-
const { getCurrentPost, getEditedPostAttribute } =
|
|
104
|
-
editorStore
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
getEntityRecords,
|
|
108
|
-
getTaxonomy,
|
|
109
|
-
hasFinishedResolution,
|
|
110
|
-
} = select( coreStore );
|
|
103
|
+
const { getCurrentPost, getEditedPostAttribute } =
|
|
104
|
+
select( editorStore );
|
|
105
|
+
const { getEntityRecords, getTaxonomy, hasFinishedResolution } =
|
|
106
|
+
select( coreStore );
|
|
111
107
|
const post = getCurrentPost();
|
|
112
108
|
const _taxonomy = getTaxonomy( slug );
|
|
113
109
|
const _termIds = _taxonomy
|
|
@@ -228,9 +224,10 @@ function FlatTermSelector( { slug } ) {
|
|
|
228
224
|
return;
|
|
229
225
|
}
|
|
230
226
|
|
|
227
|
+
const namespace = taxonomy?.rest_namespace ?? 'wp/v2';
|
|
231
228
|
Promise.all(
|
|
232
229
|
newTermNames.map( ( termName ) =>
|
|
233
|
-
findOrCreateTerm( termName, taxonomy.rest_base )
|
|
230
|
+
findOrCreateTerm( termName, taxonomy.rest_base, namespace )
|
|
234
231
|
)
|
|
235
232
|
).then( ( newTerms ) => {
|
|
236
233
|
const newAvailableTerms = availableTerms.concat( newTerms );
|
|
@@ -152,7 +152,7 @@ export function getFilterMatcher( filterValue ) {
|
|
|
152
152
|
* @param {string} props.slug Taxonomy slug.
|
|
153
153
|
* @return {WPElement} Hierarchical term selector component.
|
|
154
154
|
*/
|
|
155
|
-
function HierarchicalTermSelector( { slug } ) {
|
|
155
|
+
export function HierarchicalTermSelector( { slug } ) {
|
|
156
156
|
const [ adding, setAdding ] = useState( false );
|
|
157
157
|
const [ formName, setFormName ] = useState( '' );
|
|
158
158
|
/**
|
|
@@ -173,12 +173,10 @@ function HierarchicalTermSelector( { slug } ) {
|
|
|
173
173
|
taxonomy,
|
|
174
174
|
} = useSelect(
|
|
175
175
|
( select ) => {
|
|
176
|
-
const { getCurrentPost, getEditedPostAttribute } =
|
|
177
|
-
editorStore
|
|
178
|
-
|
|
179
|
-
|
|
180
|
-
coreStore
|
|
181
|
-
);
|
|
176
|
+
const { getCurrentPost, getEditedPostAttribute } =
|
|
177
|
+
select( editorStore );
|
|
178
|
+
const { getTaxonomy, getEntityRecords, isResolving } =
|
|
179
|
+
select( coreStore );
|
|
182
180
|
const _taxonomy = getTaxonomy( slug );
|
|
183
181
|
|
|
184
182
|
return {
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
/**
|
|
2
2
|
* External dependencies
|
|
3
3
|
*/
|
|
4
|
-
import { filter,
|
|
4
|
+
import { filter, includes } from 'lodash';
|
|
5
5
|
|
|
6
6
|
/**
|
|
7
7
|
* WordPress dependencies
|
|
@@ -18,6 +18,8 @@ import HierarchicalTermSelector from './hierarchical-term-selector';
|
|
|
18
18
|
import FlatTermSelector from './flat-term-selector';
|
|
19
19
|
import { store as editorStore } from '../../store';
|
|
20
20
|
|
|
21
|
+
const identity = ( x ) => x;
|
|
22
|
+
|
|
21
23
|
export function PostTaxonomies( {
|
|
22
24
|
postType,
|
|
23
25
|
taxonomies,
|
|
@@ -16,7 +16,7 @@ import { store as coreStore } from '@wordpress/core-data';
|
|
|
16
16
|
*/
|
|
17
17
|
import { store as editorStore } from '../../store';
|
|
18
18
|
|
|
19
|
-
export function PostTemplate(
|
|
19
|
+
export function PostTemplate() {
|
|
20
20
|
const { availableTemplates, selectedTemplate, isViewable } = useSelect(
|
|
21
21
|
( select ) => {
|
|
22
22
|
const {
|