Skip to content

Commit

Permalink
Add theme reset section (#687)
Browse files Browse the repository at this point in the history
* add theme reset api endpoint

* add theme reset frontend

* add confirm dialog

* improve wording

Co-authored-by: Sarah Norris <[email protected]>

* undo unwanted change

---------

Co-authored-by: Sarah Norris <[email protected]>
  • Loading branch information
matiasbenedetto and mikachan authored Aug 1, 2024
1 parent 082be0b commit ee2392c
Show file tree
Hide file tree
Showing 5 changed files with 250 additions and 6 deletions.
38 changes: 38 additions & 0 deletions includes/class-create-block-theme-api.php
Original file line number Diff line number Diff line change
Expand Up @@ -144,6 +144,17 @@ public function register_rest_routes() {
},
),
);
register_rest_route(
'create-block-theme/v1',
'/reset-theme',
array(
'methods' => WP_REST_Server::EDITABLE,
'callback' => array( $this, 'rest_reset_theme' ),
'permission_callback' => function () {
return current_user_can( 'edit_theme_options' );
},
),
);
}

function rest_get_theme_data( $request ) {
Expand Down Expand Up @@ -371,6 +382,7 @@ function rest_save_theme( $request ) {
}
}
CBT_Theme_Templates::clear_user_templates_customizations();
CBT_Theme_Templates::clear_user_template_parts_customizations();
}

if ( isset( $options['saveStyle'] ) && true === $options['saveStyle'] ) {
Expand Down Expand Up @@ -410,6 +422,32 @@ function rest_get_font_families( $request ) {
);
}

/**
* Reset the theme to the default state.
*/
function rest_reset_theme( $request ) {
$options = $request->get_params();

if ( isset( $options['resetStyles'] ) && true === $options['resetStyles'] ) {
CBT_Theme_Styles::clear_user_styles_customizations();
}

if ( isset( $options['resetTemplates'] ) && true === $options['resetTemplates'] ) {
CBT_Theme_Templates::clear_user_templates_customizations();
}

if ( isset( $options['resetTemplateParts'] ) && true === $options['resetTemplateParts'] ) {
CBT_Theme_Templates::clear_user_template_parts_customizations();
}

return rest_ensure_response(
array(
'status' => 'SUCCESS',
'message' => __( 'Theme Reset.', 'create-block-theme' ),
)
);
}

private function sanitize_theme_data( $theme ) {
$sanitized_theme['name'] = sanitize_text_field( $theme['name'] );
$sanitized_theme['description'] = sanitize_text_field( $theme['description'] ?? '' );
Expand Down
15 changes: 10 additions & 5 deletions includes/create-theme/theme-templates.php
Original file line number Diff line number Diff line change
Expand Up @@ -106,17 +106,22 @@ public static function replace_template_namespace( $template, $new_slug ) {
* This will remove all user templates from the database.
*/
public static function clear_user_templates_customizations() {
//remove all user templates (they have been saved in the theme)
$templates = get_block_templates();
$template_parts = get_block_templates( array(), 'wp_template_part' );
foreach ( $template_parts as $template ) {
$templates = get_block_templates();
foreach ( $templates as $template ) {
if ( 'custom' !== $template->source ) {
continue;
}
wp_delete_post( $template->wp_id, true );
}
}

foreach ( $templates as $template ) {
/**
* Clear all user template-parts customizations.
* This will remove all user template-parts from the database.
*/
public static function clear_user_template_parts_customizations() {
$template_parts = get_block_templates( array(), 'wp_template_part' );
foreach ( $template_parts as $template ) {
if ( 'custom' !== $template->source ) {
continue;
}
Expand Down
160 changes: 160 additions & 0 deletions src/editor-sidebar/reset-theme.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,160 @@
/**
* WordPress dependencies
*/
import { __ } from '@wordpress/i18n';
import { useDispatch, useSelect } from '@wordpress/data';
import { store as noticesStore } from '@wordpress/notices';
import {
// eslint-disable-next-line @wordpress/no-unsafe-wp-apis
__experimentalConfirmDialog as ConfirmDialog,
// eslint-disable-next-line @wordpress/no-unsafe-wp-apis
__experimentalVStack as VStack,
PanelBody,
Button,
CheckboxControl,
} from '@wordpress/components';
import { trash } from '@wordpress/icons';
import { useState } from '@wordpress/element';
import { store as preferencesStore } from '@wordpress/preferences';

/**
* Internal dependencies
*/
import ScreenHeader from './screen-header';
import { resetTheme } from '../resolvers';

const PREFERENCE_SCOPE = 'create-block-theme';
const PREFERENCE_KEY = 'reset-theme';

function ResetTheme() {
const preferences = useSelect( ( select ) => {
const _preference = select( preferencesStore ).get(
PREFERENCE_SCOPE,
PREFERENCE_KEY
);
return {
resetStyles: _preference?.resetStyles ?? true,
resetTemplates: _preference?.resetTemplates ?? true,
resetTemplateParts: _preference?.resetTemplateParts ?? true,
};
}, [] );

const { set: setPreferences } = useDispatch( preferencesStore );
const { createErrorNotice } = useDispatch( noticesStore );
const [ isConfirmDialogOpen, setIsConfirmDialogOpen ] = useState( false );

const handleTogglePreference = ( key ) => {
setPreferences( PREFERENCE_SCOPE, PREFERENCE_KEY, {
...preferences,
[ key ]: ! preferences[ key ],
} );
};

const toggleConfirmDialog = () => {
setIsConfirmDialogOpen( ! isConfirmDialogOpen );
};

const handleResetTheme = async () => {
try {
await resetTheme( preferences );
toggleConfirmDialog();
// eslint-disable-next-line no-alert
window.alert(
__(
'Theme reset successfully. The editor will now reload.',
'create-block-theme'
)
);
window.location.reload();
} catch ( error ) {
createErrorNotice(
__(
'An error occurred while resetting the theme.',
'create-block-theme'
)
);
}
};

return (
<>
<ConfirmDialog
isOpen={ isConfirmDialogOpen }
confirmButtonText={ __( 'Reset', 'create-block-theme' ) }
onCancel={ toggleConfirmDialog }
onConfirm={ handleResetTheme }
size="medium"
>
{ __(
'Are you sure you want to reset the theme? This action cannot be undone.',
'create-block-theme'
) }
</ConfirmDialog>
<PanelBody>
<ScreenHeader
title={ __( 'Reset Theme', 'create-block-theme' ) }
/>
<VStack>
<CheckboxControl
label={ __(
'Reset theme styles',
'create-block-theme'
) }
help={ __(
'Reset customizations to theme styles and settings.',
'create-block-theme'
) }
checked={ preferences.resetStyles }
onChange={ () =>
handleTogglePreference( 'resetStyles' )
}
/>

<CheckboxControl
label={ __(
'Reset theme templates',
'create-block-theme'
) }
help={ __(
'Reset customizations to theme templates.',
'create-block-theme'
) }
checked={ preferences.resetTemplates }
onChange={ () =>
handleTogglePreference( 'resetTemplates' )
}
/>

<CheckboxControl
label={ __(
'Reset theme template-parts',
'create-block-theme'
) }
help={ __(
'Reset customizations to theme template-parts.',
'create-block-theme'
) }
checked={ preferences.resetTemplateParts }
onChange={ () =>
handleTogglePreference( 'resetTemplateParts' )
}
/>

<Button
text={ __( 'Reset Theme', 'create-block-theme' ) }
variant="primary"
icon={ trash }
disabled={
! preferences.resetStyles &&
! preferences.resetTemplates &&
! preferences.resetTemplateParts
}
onClick={ toggleConfirmDialog }
/>
</VStack>
</PanelBody>
</>
);
}

export default ResetTheme;
23 changes: 22 additions & 1 deletion src/plugin-sidebar.js
Original file line number Diff line number Diff line change
Expand Up @@ -39,6 +39,7 @@ import {
addCard,
blockMeta,
help,
trash,
} from '@wordpress/icons';

/**
Expand All @@ -52,8 +53,9 @@ import { ThemeMetadataEditorModal } from './editor-sidebar/metadata-editor-modal
import ScreenHeader from './editor-sidebar/screen-header';
import { downloadExportedTheme } from './resolvers';
import downloadFile from './utils/download-file';
import './plugin-styles.scss';
import AboutPlugin from './editor-sidebar/about';
import ResetTheme from './editor-sidebar/reset-theme';
import './plugin-styles.scss';

const CreateBlockThemePlugin = () => {
const [ isEditorOpen, setIsEditorOpen ] = useState( false );
Expand Down Expand Up @@ -190,6 +192,21 @@ const CreateBlockThemePlugin = () => {

<Divider />

<NavigatorButton path="/reset" icon={ trash }>
<Spacer />
<HStack>
<FlexItem>
{ __(
'Reset Theme',
'create-block-theme'
) }
</FlexItem>
<Icon icon={ chevronRight } />
</HStack>
</NavigatorButton>

<Divider />

<NavigatorButton
path="/about"
icon={ help }
Expand Down Expand Up @@ -299,6 +316,10 @@ const CreateBlockThemePlugin = () => {
<NavigatorScreen path="/about">
<AboutPlugin />
</NavigatorScreen>

<NavigatorScreen path="/reset">
<ResetTheme />
</NavigatorScreen>
</NavigatorProvider>
</PluginSidebar>

Expand Down
20 changes: 20 additions & 0 deletions src/resolvers.js
Original file line number Diff line number Diff line change
Expand Up @@ -144,3 +144,23 @@ export async function getFontFamilies() {
} );
return response.data;
}

export async function resetTheme( preferences ) {
return apiFetch( {
path: '/create-block-theme/v1/reset-theme',
method: 'PATCH',
data: preferences,
headers: {
'Content-Type': 'application/json',
},
} ).then( ( response ) => {
if ( 'SUCCESS' !== response?.status ) {
throw new Error(
`Failed to reset theme: ${
response?.message || response?.status
}`
);
}
return response;
} );
}

0 comments on commit ee2392c

Please sign in to comment.