We’ve built a new WordPress base theme called One Base, and we’re now using it as the starting point for our websites. It brings together a lot of decisions about how we want to build, how clients should edit their content, and how much work a page should ask a browser to do.
The biggest change is moving further into Gutenberg and full site editing. Core blocks, patterns, templates and Global Styles now do more of the work. We still write custom functionality where a project needs it, but the starting point is the editing system WordPress already provides.
For me, a base theme has to work for two people: the developer building the site and the person looking after it once we’ve handed it over. Getting the second part right is as important as making the first build efficient.
Editing the page in context
I’ve spent years building WordPress sites with Advanced Custom Fields. It is still useful when content needs a specific structure. A relationship between records, a set of project details or a specialised component can benefit from carefully defined fields.
Ordinary page content is different. A client changing a heading or replacing an image should be able to see where that content sits. I want less of the process to involve editing a collection of fields, saving, opening another tab and trying to work out which part changed.
The WordPress Site Editor extends block editing to templates and shared parts of the site, including headers and footers. In One Base, those pieces sit alongside the same blocks used for page content. The controls become more familiar as someone uses the site.
That still needs a considered handover. Changing a paragraph on one page and changing a shared header have different consequences. Full site editing gives us the tools; we need to make the structure understandable and give each client the right level of access.
A consistent starting point for different designs
Standardising the base gives us a consistent way to organise blocks, build assets and assemble pages. We can spend more time on a project’s requirements because we’ve already made the routine decisions about where things belong and how they should behave.
We use theme.json for shared design settings such as colours, typography, spacing and content widths. Those settings help keep the editor and frontend aligned. A spacing scale is much easier to maintain when it has one defined source rather than a slightly different value in every section.
Patterns give clients a useful place to start. They can insert a prepared section and edit its native headings, images and text instead of constructing everything from an empty page. At the source level, our page patterns are composed from section-pattern references, so we can reuse an arrangement without maintaining several copies of its markup.
An ordinary inserted pattern becomes editable content on that page. It doesn’t automatically change everywhere when its source is updated. Where content should remain shared, we use the appropriate synced pattern or template part. That distinction matters when a client wants to make a local change.
The visual identity remains specific to the project. We’re standardising the mechanics underneath it: how we name components, register them, style them and maintain them. A common foundation should leave more room for good design.
Keeping content connected with WP_Query
A list of articles or case studies should come from the content itself. If a client publishes a new project, the relevant listing should pick it up according to its settings. They shouldn’t also have to recreate the project as a card on another page.
We build these listings around the native Query Loop block and WordPress’s WP_Query system. The query determines which records appear. The Post Template inside the loop controls how each result is displayed, with native pagination handling further pages.
Where we need extra behaviour, we extend that query. Our selection controls let an editor choose particular records in a specific order or show recent content. Visitor filters translate validated URL choices into query arguments. WordPress still retrieves the records and renders the results.
There are smaller improvements underneath this too. For loops containing our content cards, One Base prepares thumbnail data together using WordPress’s attachment cache. It also removes its internal tracking marker before the query runs, allowing the post list and pagination to reuse matching cached query results. Archive and search layouts can inherit the main query instead of unnecessarily creating another one.
Using WP_Query doesn’t make every query cheap. Large result sets and complicated custom-field filters still need care. The advantage is having one familiar system to inspect and improve, with content selection kept separate from its presentation.
Loading CSS for the page being viewed
Our CSS loading is deliberately split up. There is a shared global stylesheet for the foundation. Additional styles belong to the blocks and patterns that need them.
For core blocks, we register styles through wp_enqueue_block_style(). This uses WordPress’s block stylesheet system, which supports loading a block’s styles when it is used. Custom blocks declare their assets in block.json, keeping their styling and behaviour with the component.
Patterns have a small marker class. When WordPress renders a block containing that marker, our asset loader looks up the matching stylesheet and optional script. If the same pattern appears several times, its stable asset handle lets WordPress enqueue the file once. The marker survives when a pattern is inserted as ordinary blocks, so the styling keeps working after the content becomes independently editable.
The editor gets the pattern styles it needs to show available layouts. The public page loads the matching files for the patterns being rendered. A short article therefore doesn’t need the styles for every gallery, showcase or landing-page section in our catalogue.
This gives us a practical way to grow the library while keeping individual pages lean. It also makes the CSS easier to find when a section needs changing.
Performance comes from the details
Selective CSS is one part of the approach. JavaScript follows a similar principle: load the interaction where it is needed. A component can have its own frontend script without turning that behaviour into a requirement for every page on the site. Editor-only controls stay in the editor.
Images and fonts deserve just as much attention. WordPress attachment IDs let us work with responsive image sizes and appropriate thumbnails. We want the browser to receive an image suited to its display size, with dimensions that reserve its space, while keeping the original available when someone chooses to enlarge it.
Fonts need to be chosen and delivered carefully, and large media needs a reason to load immediately. A small preview should not require a full video download before someone asks to watch it. These choices can have a much bigger effect than shaving a few characters from a stylesheet.
This is how we approach high performance: reduce unnecessary transfers, avoid repeating server work and give the browser less to process before the page becomes useful. Hosting, compression, caching and third-party scripts remain part of that work. A lightweight theme can still be slowed down by an oversized image or an expensive external integration.
Moving to Gutenberg doesn’t guarantee a particular Lighthouse score. We need to test representative pages with real content and look at the individual results. Loading speed, interaction responsiveness and layout stability are the concerns covered by Core Web Vitals; lab testing helps us investigate them, while field data tells us what actual visitors experience.
A foundation we can keep improving
We’ve also kept content types and their business rules in separate modules. Case studies, services and testimonials have a purpose beyond the theme that displays them. Keeping that responsibility separate makes future design changes easier to reason about.
A shared base gives us a clearer route for improvements. When we resolve an accessibility issue, improve a query or refine a component’s behaviour, we have a known implementation to carry into future builds. Existing sites still need their own review and testing before receiving an update, but we have fewer different versions of the same problem to maintain.
What I expect from One Base is a better starting position: faster sites with less unnecessary code, a more familiar editing experience for clients, and a development process that is easier to keep consistent. The real measure will be what happens after launch. Can someone publish a useful page, update their content and understand the controls without needing us for every small change?
That is the part I’m most interested in getting right. The work on queries, assets and reusable patterns matters because it supports a website that stays useful to the people running it.