General Guide: See Global LCP Guide for universal concepts and fixes.
What is LCP?
Largest Contentful Paint measures when the largest content element becomes visible. Google recommends LCP under 2.5 seconds. Blogger's LCP is constrained by Google's shared hosting infrastructure, the XML template engine, and widget/gadget script loading.
Blogger-Specific LCP Causes
Blogger is fully hosted by Google with no server-side control. LCP problems come from:
- Unresized uploaded images -- Blogger stores original uploads; the XML template must request resized versions via URL parameters
- Widget/gadget bloat -- each gadget (Popular Posts, Blog Archive, Labels) loads its own JS and CSS synchronously
- XML template render-blocking -- Blogger's template engine inlines large CSS blocks and loads
widgets.jssynchronously - Third-party themes -- downloaded themes from sites like BTemplates or Flavor often bundle unoptimized CSS and JS
- Google-hosted shared infrastructure -- no CDN configuration or server tuning available
Fixes
1. Optimize Image URLs with Size Parameters
Blogger's image CDN (blogger.googleusercontent.com) supports on-the-fly resizing via URL parameters. Use this instead of serving full-size uploads:
<!-- BAD: Full-size original image -->
<img src="https://blogger.googleusercontent.com/img/abc123/s0/photo.jpg">
<!-- GOOD: Request 800px wide version -->
<img src="https://blogger.googleusercontent.com/img/abc123/w800/photo.jpg"
width="800" height="450" alt="Post image" loading="eager">
In your Blogger XML template, modify the post image output:
<!-- In your Blogger XML template, replace image rendering -->
<b:if cond='data:post.featuredImage'>
<img expr:src='data:post.featuredImage.isYouTube
? data:post.featuredImage.youtubeUrl
: resizeImage(data:post.featuredImage, 800, "800:450")'
width='800' height='450'
expr:alt='data:post.title'
loading='eager'/>
</b:if>
The resizeImage function is Blogger's built-in template function that appends the correct size parameters.
2. Remove Unused Widgets
Every Blogger widget loads its own JavaScript. Audit your layout at Layout > Edit:
Common heavy widgets to remove or replace:
- Popular Posts -- makes additional API calls; replace with static HTML links
- Blog Archive -- loads expandable tree widget JS
- Profile widget -- loads Google+ legacy scripts
- Follow by Email -- loads FeedBurner scripts (often broken since FeedBurner deprecation)
To remove a widget from the template XML directly:
<!-- Find and remove unused widget sections like: -->
<b:widget id='PopularPosts1' locked='false' title='Popular Posts' type='PopularPosts'>
<!-- Delete entire widget block -->
</b:widget>
3. Defer Template JavaScript
Blogger injects widgets.js synchronously. While you cannot remove it, you can defer your own scripts and reduce the JS competition:
<!-- In your Blogger template <head> section -->
<!-- Move all custom JS to bottom of body and add defer -->
<b:if cond='data:blog.pageType == "item"'>
<script defer='defer' src='https://yourcdn.com/post-enhancements.js'/>
</b:if>
<!-- Lazy-load comment system -->
<script>
//<![CDATA[
document.addEventListener('DOMContentLoaded', function() {
var observer = new IntersectionObserver(function(entries) {
if (entries[0].isIntersecting) {
// Load Disqus or other comment system only when scrolled to
var d = document.createElement('script');
d.src = '//yoursite.disqus.com/embed.js';
document.body.appendChild(d);
observer.disconnect();
}
});
var commentSection = document.getElementById('comments');
if (commentSection) observer.observe(commentSection);
});
//]]>
</script>
4. Inline Critical CSS and Async the Rest
Blogger templates often include large CSS blocks. Split them:
<!-- Inline only critical above-fold CSS -->
<b:skin><![CDATA[
/* CRITICAL ONLY: header, hero, first post card */
.header-wrapper { display: flex; align-items: center; height: 60px; }
.post-outer:first-child .post-thumbnail { width: 100%; aspect-ratio: 16/9; }
body { font-family: system-ui, sans-serif; margin: 0; }
]]></b:skin>
<!-- Load remaining CSS asynchronously -->
<link rel='preload' href='https://yourcdn.com/full-theme.css' as='style'
5. Preload Featured Image on Post Pages
<!-- Add to template <head> for post pages -->
<b:if cond='data:blog.pageType == "item"'>
<b:if cond='data:post.featuredImage'>
<link rel='preload' as='image'
expr:href='resizeImage(data:post.featuredImage, 1200, "16:9")'/>
</b:if>
</b:if>
Measuring LCP on Blogger
- PageSpeed Insights -- the primary tool since you have no server access
- Chrome DevTools Lighthouse -- test individual post pages, not just the homepage
- Test key page types: homepage (typically shows post list), individual post pages (show featured image + content), and label/archive pages
Blogger has no built-in performance monitoring. Use Google Search Console's Core Web Vitals report for field data across your published posts.
Analytics Script Impact
Blogger's built-in "Stats" tracking is lightweight. The main LCP risk comes from:
- Google AdSense --
adsbygoogle.jsis render-blocking and adds ~200ms to LCP; no way to defer it if you want ads - Third-party analytics (added manually to template) -- always use
asyncattribute - Social sharing widgets -- AddThis, ShareThis load heavy JS bundles; use native share links instead
<!-- GOOD: async analytics in Blogger template -->
<script async='async' src='https://www.googletagmanager.com/gtag/js?id=G-XXXXXX'/>