FCP Defined
First Contentful Paint (FCP) measures the time it takes for the browser to render the first piece of content you see on a webpage. This can be text, images (background images), SVG elements, etc.
💡 Don’t confuse FCP with LCP, which measures how fast the main content (largest) becomes visible.
- This is classified as a notable metric. It’s not an official Core Web Vitals metric. Only LCP, INP, and CLS are official metrics that you must pass or fail.
- Why is FCP Important? FCP is probably one of the most important metrics in terms of the user experience, as it will help improve perceived performance (how fast a site feels). It provides feedback for the user: “Is it loading?”
What is a Good FCP?
According to Google, they want you to have your FCP under 1.8 seconds.
Just like with LCP, they use the 75th percentile to determine where you stand. 75% of the visits/crawls need to meet the “good” threshold for you to get that classification.
You really want to aim for lower than 1.8 seconds because Google uses throttled 4G for mobile when crawling your site. They are purposely measuring your site using a slow connection to ensure users across the board have a good experience, not just those on a fast connection.
How to Measure FCP
There are many different tools you can use to measure FCP. A few favorites are PageSpeed Insights (PSI), GTmetrix, and DebugBear.
WebPageTest can also be super handy as it lets you adjust the filmstrip thumbnail intervals. Meaning, you can really narrow down to the first visual element where FCP comes into play.
And, of course, I like to use the “FCP tab” in the PageSpeed Insights report:
I always recommend testing at least three times due to factors like cache, network latency, etc., which can influence FCP. Never rely on one data point.
PSI and Real-User Data
It’s important to understand the difference between lab data and real-user data. Lab data is at the bottom of the report under the “Diagnose performance issues” section, while the top section contains real-user data. It’s collected over an average of 28 days as users hit your site and are recorded for Core Web Vitals. But remember, it’s always delayed (example).
Also, pay attention to this tab to see if there is enough data for your individual URL. Otherwise, the origin (average) of your site is shown.
Server Response Time (TTFB)
One of the most important factors to improve FCP is having low TTFB (server response time). To improve this:
- Use a high-quality hosting provider (powerful servers, scaling, networking, DNS, etc.).
- Have a cache solution in place (server-level, plugin).
- Reduce HTML size with a lightweight theme: GeneratePress, Kadence/Kadence Blocks, or Bricks.
- Use the latest version of PHP (or one behind). PHP 8.3 is ~10% faster than 8.1 (source).
- When enabling cache on a server in the same geographical location: FCP decrease of 43.09%.
- Utilize edge cache if you’re serving global visitors (Cloudflare).
- Without edge cache: FCP increase of 111.04%.
Check out our previous presentation on TTFB, which discusses everything above. If you skip this part, you will most likely struggle to achieve lower FCP.
Enable Text Compression
Compression is method of reducing the size of data without losing any information. Think of it like image optimization/compression, but for HTML and CSS/JS.
Hosting providers, CDNs (Cloudflare), and cache plugins typically should add compression headers automatically for GZIP or Brotli (latest method). However, I still see this missing all the time, many times due to a misconfiguration with hosting or cache.
If you see this warning, make it a top priority to fix, as compression has a huge impact on performance. In this example, there is a 86.02% savings on a single file just by enabling compression.
Use a third-party tool like GiftOfSpeed to verify it. I’ve seen instances where some assets are compressed and others aren’t. It’s not always an all or nothing problem.
JS and CSS Minification
Next, we’re going to dive into some things you can do to improve FCP in Perfmatters. The first is to enable JS and CSS minification. This is the process of removing unnecessary characters from your code (whitespace, comments, shortening function and variable names, etc.), along with additional markup cleanup.
We have a JS and CSS minification feature in our Perfmatters plugin. Files with .min.js or .min.css are automatically skipped, so this feature is pretty lightweight/fast. We also have exclusions and filters for fine-tuning things
Reduce Unused CSS
Next, we have unused CSS. Many themes and plugins simply load their entire stylesheets everywhere. Because of this, you’ll have a lot of unused code.
You can clean this up using the Remove Unused CSS feature in our Perfmatters plugin. We have exclusions and filters for fine-tuning things.
In our testing, we’ve seen an average decrease in FCP of 15%. 🔥
Reduce Unused JS
Next, we have unused JS. Like with unused CSS, many themes and plugins simply load their JS everywhere. Same with third-party scripts. Because of this, you’ll have a lot of unused code.
You can use the Delay JavaScript feature in our Perfmatters plugin. Delay scripts not needed right away on user interaction. We have exclusions and filters for fine-tuning things.
Eliminate Render-Blocking Resources
The next thing you can do is to fix any render-blocking resources. Most CSS and JS is naturally render- blocking. There are a couple of ways you can fix this. Note: jQuery usually can’t be optimized.
First off, using the Remove Unused CSS and Delay JS features will automatically fix the render-blocking issues on those assets. That’s why I recommend focusing on unused CSS and JS first.
Second, you can defer JavaScript in our Perfmatters plugin. JS is downloaded during HTML parsing and will execute after the page has finished loading. We have exclusions and filters for fine-tuning things.
Ensure Text Remains Visible During Webfont Load
Next is the ensure text remains visible during webfont load warning. Modern browsers wait until the font has fully downloaded to display it. This can create a flash, otherwise known as FOIT. That also means it could hold up FCP. To fix this, we recommend doing a few things (can be done in Perfmatters):
- First off, you should host your Google Fonts locally for faster performance.
- Second, you should add swap to your fonts. This means there is a temporary fallback to system fonts.
- Third, you should preload the fonts to minimize any CLS. Yes, sounds counter-intuitive, but it will force them to load as soon as possible.
- (Optional) Fourth, you can async your Google font CSS to fix the render-blocking issue. I recommend testing on and off due to CLS.
Avoid Chaining Critical Requests
Next is the avoid chaining critical requests warning. As Google states, “the greater the length of the chains and the larger the download sizes, the more significant the impact on page load performance.” This will impact FCP.
The good news is that the other things we’ve done, such as removing unused CSS, delaying JS, deferring JS, preloading local fonts, etc., will all reduce critical requests. So by the time you get to this point, you probably won’t have much left to do.
Avoid Enormous Network Payloads
Next is the avoid enormous network payloads warning. Essentially, this just means that any large resource (JS, CSS, image, font, etc.) is going to affect the performance of your site, and this can impact your FCP.
This is especially important for any assets that load above the fold. Every KB matters. A few common examples:
- Featured images or hero background images that aren’t sized or optimized properly.
- Oversized fonts. Many themes and plugins that don’t take performance into consideration might load an entire font icon library sitewide when only 1% of the library is being used (Font Awesome, Dashicons, etc.)
- Large external JS files.
Tip: I always recommend keeping individual images at 100 KB or less, especially for mobile. You can use an image optimization plugin like ShortPixel or Imagify. The free Squoosh tool from Google is also great for fine-tuning individual images. Use WebP/AVIF formats if needed.
Optimizing Fonts
Speaking of fonts, here are a few tricks and tools I recommend to optimize them.
Use Yellow Lab Tools to see how much of a font library is being used. For example, on this site, the client was using less than 1%.
Use a Font Awesome kit. This lets you collect all the icons you need in a kit and then deploy that across your site, instead of the all the icons.
Use a theme or page builder that allows you to add SVG icons individually. For example, in GenerateBlocks, you can just copy/paste SVG code from Font Awesome. Use SVGViewer tool’s “Optimize” feature to decrease SVG code size.
Use Google Webfonts Helper tool to download the smallest Google Fonts with mimimum charsets. I’ve seen users decrease font sizes by 76%. (Example: Montserrat down from 64.6 KB to 15 KB)
Defer Offscreen Images
You should always lazy loading your images, that will fix the defer offscreen images warning. Now, technically, FCP is related to things above the fold. However, lazy loading could still have an indirect impact on FCP, such as reducing unnecessary data transfer and even of course perceived performance.
We have extensive lazy loading options in our Perfmatters plugin and filters to fine-tune things.
- Exclude leading images
- Lazy load iframes and videos (YouTube preview thumbnail feature)
- Exclusions (individual and parent selectors)
- Threshold (viewport) settings
Properly Size Images
As with lazy loading images, properly size images can have an indirect impact on FCP, such as reducing unnecessary data transfer and even of course perceived performance.
WordPress actually crops your images in the media library automatically and uses srcset
for responsive images. So with many themes and page builders, you should be fine, or pretty close.
If you do see this warning a lot, I would check with your theme or page builder first to see if they have recommended sizes for the media library settings.
If you need to take it a step further, you could use a service like ShortPixel AI, EWWW, or Optimole to scale your images on the fly.
Disable Plugins or JS/CSS
Another way to improve FCP is to ensure that the scripts and CSS from plugins and themes aren’t loading where they shouldn’t.
The Script Manager in Perfmatters allows you to disable scripts on a per post/page basis or sitewide basis. And MU mode lets you disable entire plugins from running (MySQL queries, inline code, etc.)
This can be very powerful, but it is also a more advanced feature. For many users just starting out, we recommend starting with the other optimizations first (which are more automated) and then fine-tuning with the Script Manager at the end.
Trying to Improve Your Core Web Vitals?
This article is part of a larger series, called Vitality, where we tackle notable metrics and Core Web Vitals!
Speculative Loading Techniques
Not everything is about final page speed scores or tests. You always need to think about the user experience and perceived performance (how fast a site feels, quick to navigate, etc.). There are different speculative loading mechanisms you can use. And technically, this will help improve FCP for the user.
- Preconnect allows the browser to set up early connections before an HTTP request, eliminating round trip latency and saving time for users (DNS + TCP + TLS). This is great for third-party requests that might not already be delayed, or a CDN URL (cdn.domain.com). We have a preconnect feature in Perfmatters.
- Prefetch lets you automatically fetch most of the resources required to render a URL in the background after a user hovers over a link. This results in faster load times and navigation. We have our Instant Page feature in Perfmatters that enables this.
- Prerender goes a step further than prefetch, and actually renders the content ready to be shown after a user hovers over a link. This results in pretty much instant load times. The new and free Speculative Loading plugin from the WordPress performance team enables this for you. Highly recommend it!
Quick Summary of FCP
- Server response time (TTFB), including HTML doc size has a huge impact on FCP. The further the distance, the more it matters. Don’t skip this! See previous video on TTFB, caching, etc.
- Use lightweight theme (GeneratePress, Kadence, Bricks).
- Get FCP under 1.8 seconds or less. Remember, Google uses throttled 4G mobile connection.
- Make sure compression (GZIP or Brotli) is running on everything.
- Minify your JS and CSS.
- Remove unused CSS.
- Delay unused JS until it’s needed on user interaction.
- Defer JS to help eliminate render-blocking resources and avoid chaining critical requests.
- Host your fonts locally, add swap, and preload them.
- Decrease any large resources. Image optimization, fixing large font libraries, etc.
- Lazy load images and make sure they are properly sized.
- Disable JS/CSS and or entire plugins from loading where they shouldn’t with a tool like the Script Manager.
- Take advantage of speculative loading techniques.