Documents
Focal Point Picker in Strapi Media Library
Focal Point Picker in Strapi Media Library
Type
Document
Status
Published
Created
Feb 4, 2026
Updated
Feb 4, 2026
Updated by
Dosu Bot

Focal Point Picker in Strapi Media Library#

Introduction#

The focal point picker is a powerful feature in Strapi's Media Library that enables content editors to specify which part of an image should remain visible when the image is cropped or resized across different contexts. Introduced in January 2026 and released with Strapi v5.35.0, this feature addresses a critical workflow challenge for responsive web design.

The Problem#

Modern websites display the same image across multiple breakpoints and placements—hero banners, card thumbnails, social media previews, and mobile layouts. Without focal point control, automated cropping often cuts off the most important part of an image, forcing content editors to upload multiple pre-cropped variants. This approach creates significant overhead as media libraries grow.

The Solution#

The focal point picker allows editors to mark the most important area of an image with a single click. Frontend applications can then use these coordinates to ensure the subject remains visible regardless of how the image is cropped or resized. This results in a single source image that works intelligently across all use cases.

Backend Architecture#

Database Schema#

The focal point feature adds a new field to the file content type without requiring database migration. The focalPoint field is stored as a JSON object in the database, making it flexible and backwards-compatible with existing images.

Field Specification:

  • Type: json (not configurable)
  • Nullability: Optional field that can be null
  • Migration: None required—existing installations automatically support focal points

TypeScript Type Definitions#

The FocalPoint interface provides type safety across the entire codebase:

export interface FocalPoint {
  x: number;
  y: number;
}

Coordinate System:

  • Range: Both x and y values are percentages from 0 to 100
  • Resolution-Independent: Percentages work across any image size
  • Default: Center point (50, 50) when not specified
  • Integration: Included as optional field in File type: focalPoint?: FocalPoint | null

Validation#

Strapi enforces consistent validation rules across all API layers to ensure data integrity.

Validation Schema (applies to both Admin API and Content API):

const focalPointSchema = yup
  .object({
    x: yup.number().min(0).max(100).required(),
    y: yup.number().min(0).max(100).required(),
  })
  .nullable()
  .default(null);

Validation Rules:

  • Both x and y coordinates are required when focal point is set
  • Values must be numbers between 0 and 100 (inclusive)
  • The entire focal point object can be null (for images without a focal point)

Service Layer Integration#

The upload service handles focal point persistence throughout the file lifecycle:

File Creation:

  • formatFileInfo includes focalPoint from fileInfo when creating file entities

File Updates:

  • updateFileInfo updates the focal point field, preserving the existing value if not provided in the update

Shared Type Contracts#

The shared contracts file ensures type consistency between frontend and backend:

API Endpoints:
The focal point feature requires no new API endpoints. It integrates seamlessly into existing upload and update workflows, with focal point data passed alongside other file metadata.

Frontend UI Components#

The focal point picker UI is built with React components that provide an intuitive, interactive experience for content editors.

Component Architecture#

EditAssetContent#

The EditAssetContent component serves as the parent container for the focal point feature:

PreviewBox#

The PreviewBox component provides the core interactive focal point picker:

Entry Point:

  • PinMap icon button in the toolbar (top right) activates focal point mode
  • Only visible for image assets—conditionally rendered based on MIME type

Interaction:

Visual Feedback:

  • Renders a visual focal point marker at the selected position
  • Shows a semi-transparent preview marker that follows the mouse cursor
  • Provides real-time feedback before the user confirms their selection

FocalPointActions#

The FocalPointActions component presents a contextual action bar when focal point mode is active:

Action Buttons:

  • Cancel (Cross icon): Discards changes and exits focal point mode without saving
  • Reset (ArrowsCounterClockwise icon): Returns focal point to center (50%, 50%)
  • Save (Check icon): Confirms and applies the focal point selection

Coordinate Display:

  • Shows live coordinate badges with current focal point percentages
  • Updates in real-time as the user moves the focal point

Visual Components#

FocalPointAim and FocalPointHalo are styled components that render the focal point marker:

  • FocalPointAim: Center dot indicating the exact focal point
  • FocalPointHalo: Surrounding circle providing visual context
  • Positioning: Uses CSS positioning based on percentage coordinates for precise placement

API Integration Hook#

The useEditAsset hook handles communication with the backend:

  • Data Transmission: Includes focalPoint in the fileInfo payload when posting updates
  • Endpoint: Posts to /{pluginId}?id={asset.id} using existing file update workflow
  • Error Handling: Provides error feedback if validation or submission fails

User Guide#

This section provides step-by-step instructions for content editors working with the focal point picker.

Setting a Focal Point#

To add a focal point to an image in the Media Library, follow this workflow:

  1. Navigate to Media Library: Open the Media Library from the Strapi admin panel
  2. Select an Image: Click on any image to open the edit dialog
  3. Enter Focal Point Mode: Click the crosshair/pin icon in the toolbar (located in the top right of the preview area)
  4. Position the Focal Point: Click anywhere on the image to set the focal point
    • A marker appears at the clicked position
    • A semi-transparent preview marker follows your mouse cursor before you click
    • The cursor changes to a crosshair to indicate focal point mode is active
    • Current coordinates display in a badge showing percentage values
  5. Adjust as Needed: Click a different location to reposition the focal point
  6. Reset (Optional): Click the reset button (circular arrow icon) to return the focal point to the center (50%, 50%)
  7. Confirm Selection: Click the check icon to save your focal point
  8. Save Changes: Click the "Finish" button to persist all changes to the asset

Previewing a Focal Point#

The EditAssetContent component provides multiple ways to preview focal points:

  • Coordinate Display: Focal point coordinates appear in the file details section
  • Visual Marker: A marker shows the exact position on the image preview
  • Hover Preview: Before clicking, a semi-transparent marker follows your cursor to show where the focal point will be placed

Resetting a Focal Point#

To reset a focal point to the default center position:

  1. Enter focal point mode by clicking the crosshair/pin icon
  2. Click the reset button (circular arrows icon) in the action bar
  3. The focal point immediately returns to center (50%, 50%) in the preview
  4. You can still cancel or adjust the position before saving
  5. Click the check icon to confirm, then "Finish" to persist the reset

Note: The reset action is visible immediately in the preview but requires explicit saving to persist to the database.

Use Cases and Benefits#

The Challenge#

Based on community feedback, content teams face a common challenge: the same image must work across numerous breakpoints and placements—hero banners, card thumbnails, social media previews (OG images), and mobile versus desktop layouts. Without focal point control, automated cropping frequently cuts off the most important part of an image. This forces editors to upload multiple pre-cropped variants, creating a workflow blocker as content libraries grow.

Responsive Image Cropping Scenarios#

The primary use case for focal points is enabling intelligent image cropping across different aspect ratios. Common scenarios include:

Hero Images: The same image displayed at different heights on mobile (short viewport) versus desktop (tall viewport), where the focal point ensures the subject remains centered.

Thumbnail Generation: Creating smaller preview images where the important subject must stay visible even when the image is cropped to a square or different aspect ratio.

Card Layouts: Magazine-style or grid layouts with varying image dimensions where each card shows a different crop of the source image.

Social Media Previews: OG images with fixed aspect ratios (e.g., 1.91:1 for Facebook, 2:1 for Twitter) that automatically crop to show the focal point.

Responsive Art Direction: Different crops for different contexts without maintaining separate image files.

Benefits#

Single Source Image: Use one high-quality image for all contexts instead of managing multiple pre-cropped versions.

Subject Always Visible: The focal point ensures the most important part of the image remains in view regardless of aspect ratio or display size.

Reduced Content Management: Editors set the focal point once rather than creating and uploading multiple image variants.

Consistent Quality: All crops derive from the same source image, ensuring consistent quality and avoiding compression artifacts from re-uploading.

Developer Integration Guide#

This section provides practical examples for frontend developers to leverage focal point data in their applications.

Retrieving Focal Point Data#

Focal point data is automatically included in standard file entity API responses from Strapi. When you query for media files through the REST or GraphQL API, the response includes:

{
  "id": 1,
  "name": "example.jpg",
  "url": "/uploads/example.jpg",
  "focalPoint": {
    "x": 65,
    "y": 30
  },
  "alternativeText": "Product showcase",
  "caption": "New product line 2026"
}

CSS Implementation#

The focal point coordinates are designed for direct use with CSS object-position, making implementation straightforward.

Basic CSS Example#

img {
  object-fit: cover;
  object-position: 65% 30%; /* Using focalPoint.x and focalPoint.y */
}

The object-fit: cover property ensures the image fills its container, while object-position specifies which part of the image to keep visible.

React/JSX Implementation#

<img
  src={image.url}
  style={{
    objectFit: 'cover',
    objectPosition: `${image.focalPoint.x}% ${image.focalPoint.y}%`
  }}
  alt={image.alternativeText}
/>

Handling Missing Focal Points#

Always provide a fallback for images without focal points:

const focalPoint = image.focalPoint || { x: 50, y: 50 };
const objectPosition = `${focalPoint.x}% ${focalPoint.y}%`;

This defaults to the center (50%, 50%) for backwards compatibility with existing images.

Responsive Design Patterns#

Using CSS Custom Properties#

CSS custom properties allow you to dynamically set focal points:

// Set CSS custom properties
const style = {
  '--focal-x': `${image.focalPoint.x}%`,
  '--focal-y': `${image.focalPoint.y}%`
};
.hero-image {
  object-fit: cover;
  object-position: var(--focal-x) var(--focal-y);
  height: 300px;
}

@media (min-width: 768px) {
  .hero-image {
    height: 500px;
  }
}

@media (min-width: 1200px) {
  .hero-image {
    height: 700px;
  }
}

The focal point remains consistent across all breakpoints, but the crop adapts to different aspect ratios.

Background Images#

For CSS background images, use background-position:

.hero-section {
  background-image: url('/uploads/hero.jpg');
  background-size: cover;
  background-position: 65% 30%; /* From focal point data */
  height: 400px;
}
// Dynamic background positioning
const sectionStyle = {
  backgroundImage: `url(${image.url})`,
  backgroundSize: 'cover',
  backgroundPosition: `${image.focalPoint.x}% ${image.focalPoint.y}%`
};

Integration with Image CDNs#

Focal point coordinates can be passed to image transformation services for server-side cropping.

Cloudinary Example#

// Convert focal point to Cloudinary gravity parameter
const cloudinaryUrl = `https://res.cloudinary.com/demo/image/upload/c_fill,w_400,h_300,g_xy_center,x_${image.focalPoint.x * 0.01},y_${image.focalPoint.y * 0.01}/${image.name}`;

Imgix Example#

// Imgix focal point crop
const imgixUrl = `${image.url}?fit=crop&crop=focalpoint&fp-x=${image.focalPoint.x / 100}&fp-y=${image.focalPoint.y / 100}&w=800&h=600`;

Custom Transformation Services#

For custom image processing pipelines, the percentage-based coordinates can be easily converted to pixel values:

function focalPointToPixels(focalPoint, imageWidth, imageHeight) {
  return {
    x: Math.round((focalPoint.x / 100) * imageWidth),
    y: Math.round((focalPoint.y / 100) * imageHeight)
  };
}

const pixelCoords = focalPointToPixels(
  image.focalPoint, 
  2000, // original width
  1500 // original height
);
// Returns: { x: 1300, y: 450 }

Framework-Specific Examples#

Next.js Image Component#

import Image from 'next/image';

export function HeroImage({ image }) {
  const focalPoint = image.focalPoint || { x: 50, y: 50 };

  return (
    <div style={{ position: 'relative', width: '100%', height: '500px' }}>
      <Image
        src={image.url}
        alt={image.alternativeText}
        fill
        style={{
          objectFit: 'cover',
          objectPosition: `${focalPoint.x}% ${focalPoint.y}%`
        }}
      />
    </div>
  );
}

Vue.js Component#

<template>
  <img
    :src="image.url"
    :alt="image.alternativeText"
    :style="imageStyle"
    class="responsive-image"
  />
</template>

<script>
export default {
  props: ['image'],
  computed: {
    imageStyle() {
      const focalPoint = this.image.focalPoint || { x: 50, y: 50 };
      return {
        objectFit: 'cover',
        objectPosition: `${focalPoint.x}% ${focalPoint.y}%`
      };
    }
  }
}
</script>

Svelte Component#

<script>
  export let image;

  $: focalPoint = image.focalPoint || { x: 50, y: 50 };
  $: objectPosition = `${focalPoint.x}% ${focalPoint.y}%`;
</script>

<img
  src={image.url}
  alt={image.alternativeText}
  style="object-fit: cover; object-position: {objectPosition};"
/>

Technical Reference#

Data Format#

The focal point feature uses a percentage-based coordinate system (0-100) that is resolution-independent. This design choice ensures focal points work correctly across images of any size without recalculation.

Storage: JSON field in the database provides flexibility for future enhancements while maintaining a simple data structure.

Nullability: The field is nullable, ensuring backwards compatibility with existing images that don't have focal points set.

Validation Rules#

Strapi enforces consistent validation across admin API, content API, and frontend:

  • Both x and y coordinates are required when a focal point is set
  • Values must be numbers between 0 and 100 (inclusive)
  • The entire focal point object can be null

This three-tier validation approach (database, backend API, frontend) prevents invalid data from entering the system.

Asset Type Restrictions#

The focal point picker is only available for image assets. The UI conditionally renders based on MIME type, ensuring the feature appears only for appropriate file types.

Not Applicable To:

  • Video files
  • PDF documents
  • Audio files
  • Other non-image file types

Backwards Compatibility#

The focal point feature was designed with backwards compatibility as a priority:

Existing Images: Images uploaded before the feature was introduced continue to work without modification. The optional field defaults to null.

Default Behavior: When no focal point is set, images default to center positioning (50%, 50%), matching typical image display behavior.

API Responses: No breaking changes to existing API responses. The focalPoint field is simply added to file entities.

Migration: No database migration required. The feature works immediately upon upgrading to Strapi v5.35.0 or later.

Development History#

The focal point picker has an interesting history rooted in community feedback:

Origins: Feature requested since at least 2019 as part of discussions about Media Library enhancements.

RFC Process: An RFC was submitted over 2 years before implementation, demonstrating the lengthy contribution process for core features.

Community-Driven: The feature emerged from community needs and was ultimately delivered through community contribution.

Roadmap Context: Part of a broader Media Library enhancement roadmap that has evolved over several years.

Release: Officially released in Strapi v5.35.0 (February 4, 2026), fulfilling years of community requests for intelligent image cropping capabilities.