Skip to content

Instantly share code, notes, and snippets.

@djcowan
Last active August 27, 2024 00:20
Show Gist options
  • Save djcowan/e025418613cb7b854262084945fce403 to your computer and use it in GitHub Desktop.
Save djcowan/e025418613cb7b854262084945fce403 to your computer and use it in GitHub Desktop.
Wordpress Block Typescript
{
"$schema": "https://json.schemastore.org/tsconfig.json",
"compilerOptions": {
"forceConsistentCasingInFileNames": true,
"allowJs": true,
"checkJs": true,
"allowSyntheticDefaultImports": true,
"jsx": "preserve",
"target": "esnext",
"module": "esnext",
"lib": [ "DOM", "DOM.Iterable", "ESNext" ],
"declaration": true,
"declarationMap": true,
"composite": true,
"emitDeclarationOnly": true,
"isolatedModules": true,
"skipDefaultLibCheck": true,
/* Strict Type-Checking Options */
"strict": true,
/* Additional Checks */
"noImplicitReturns": true,
"noFallthroughCasesInSwitch": true,
/* Module Resolution Options */
"moduleResolution": "node",
/* This needs to be false so our types are possible to consume without setting this */
"esModuleInterop": false,
"resolveJsonModule": true,
"typeRoots": [ "./node_modules/@types" ],
"types": []
},
"include": ["./src", "experiments/focus-loss-edit-service"],
"exclude": [
"**/*.android.js",
"**/*.ios.js",
"**/*.native.js",
"**/benchmark",
"packages/*/build-*/**",
"packages/*/build/**",
"**/test/**",
"packages/**/react-native-*/**"
]
}
import { type BlockEditProps } from "@wordpress/blocks";
import clsx from "clsx";
import { __ } from "@wordpress/i18n";
import { useEffect, useRef } from "@wordpress/element";
import { InspectorControls, RichText, useBlockProps } from "@wordpress/block-editor";
import { __experimentalHStack as HStack, PanelBody, CheckboxControl, ToggleControl, } from "@wordpress/components";
export default function Edit( props: BlockEditProps<Record<string, any>> ): React.JSX.Element
{
const { attributes, setAttributes, clientId, } = props;
const {
sectionTag, label, title, placeholder, metadata, selector, sectionRef, sectionType, itemRef
} = attributes;
const timer = useRef( 0 );
useEffect( () =>
{
clearTimeout( timer.current );
timer.current = setTimeout( () =>
{
setAttributes( { metadata: { ...metadata, name: title } } );
}, 1000 );
}, [ title, ] );
const blockProps = useBlockProps( { className: clsx( selector, `is-section-${ sectionType }` ) });
const {children, ...innerBlocksProps } = useInnerBlocksProps( blockProps, {} );
return (
<>
<Card { ...blockProps } size={ "extraSmall" } data-ref={ sectionRef }>
<CardHeader className={ `${ selector }__header` }>
<RichText
tagName={ "h2" }
value={ title }
onChange={ ( newValue ) => setAttributes( { title: newValue } ) }
aria-label={ __( label, "namespace-domain" ) }
className={ `${ selector }__title` }
placeholder={ placeholder }
/>
</CardHeader>
<CardBody { ...innerBlocksProps } className={ `${ selector }__content` } data-ref={ itemRef }>
{ children as React.React.Node }
</CardBody>
</Card>
</>
);
}
import { RiLayoutTopLine as BlockIcon } from "@remixicon/react";
import { registerBlockType, type BlockConfiguration } from '@wordpress/blocks';
import "./style.scss";
import "./editor.scss";
import metadata from "./block.json";
import Edit from "./edit";
import Save from "./save";
import variations from "./variations";
registerBlockType( metadata as BlockConfiguration, {
edit: Edit,
save: Save,
icon: <BlockIcon />,
variations: variations,
} as Partial<BlockConfiguration> );
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment