How to Customize QR Code Styles in EFQRCode: A Complete Guide to Module Shapes, Colors, and Icons

EFQRCode provides a style-centric architecture through the EFQRCodeStyle enum and parameter classes like EFStyleBasicParams, allowing you to customize module shapes, colors, center icons, and backdrops by configuring the corresponding parameter object and passing it to EFQRCodeGenerator.

EFQRCode is a Swift library for generating highly customizable QR codes. To customize QR code styles in EFQRCode, you work with a hierarchy of style-specific parameter classes located in the Source/Styles directory. This architecture lets you control everything from data module shapes to finder pattern styles using type-safe Swift enums and structs.

Understanding the EFQRCode Style Architecture

EFQRCode organizes styling logic into several key components defined in Source/Styles/EFQRCodeStyle.swift:

  • EFQRCodeStyle enum: Selects the style implementation (basic, bubble, 2.5D, etc.) and holds the corresponding parameter object.
  • EFStyleParams base class: Stores common parameters including an optional icon (EFStyleParamIcon) and backdrop (EFStyleParamBackdrop).
  • Style-specific parameter classes: Subclasses like EFStyleBasicParams, EFStyleBubbleParams, and EFStyle25DParams define per-style options such as alignment pattern shapes, timing pattern styles, and data module rendering modes.
  • EFQRCodeStyleBase subclasses: Implement the actual SVG rendering logic using the parameters above (e.g., EFQRCodeStyleBasic in Source/Styles/EFQRCodeStyleBasic.swift).

All styles share a copy-with API (copyWith(iconImage:watermarkImage:)) that returns a new style instance with requested modifications, enabling easy chaining of customizations.

Customizing the Basic Style

The basic style (EFQRCodeStyleBasic) is the most commonly used and offers granular control over every QR code element. Here is a complete implementation:

import EFQRCode

// 1️⃣ Create an icon (optional)
let icon = EFStyleParamIcon(
    image: .static(myIconCGImage),
    mode: .scaleAspectFill,
    alpha: 0.9,
    borderColor: CGColor.createWith(rgb: 0xffffff)!, // white border
    percentage: 0.25)

// 2️⃣ Configure the backdrop (optional)
let backdrop = EFStyleParamBackdrop(
    cornerRadius: 4,
    color: CGColor.createWith(rgb: 0xf0f0f0)!, // light gray background
    image: nil,
    quietzone: EFEdgeInsets(top: 1, left: 1, bottom: 1, right: 1))

// 3️⃣ Tune the basic-style parameters
let basicParams = EFStyleBasicParams(
    icon: icon,
    backdrop: backdrop,
    position: EFStyleBasicParamsPosition(
        style: .planets,          // planet-style finder patterns
        size: 1.2,
        color: CGColor.createWith(rgb: 0x000000)!),
    data: EFStyleBasicParamsData(
        style: .randomRound,      // random-sized circles for data modules
        scale: 0.9,
        color: CGColor.createWith(rgb: 0x000000)!),
    align: EFStyleBasicParamsAlign(
        style: .roundedRectangle,
        size: 0.8,
        color: CGColor.createWith(rgb: 0x000000)!),
    timing: EFStyleBasicParamsTiming(
        style: .round,
        size: 0.6,
        color: CGColor.createWith(rgb: 0x000000)!))

// 4️⃣ Build the style object
let style = EFQRCodeStyle.basic(params: basicParams)

// 5️⃣ Generate the QR code
let generator = EFQRCodeGenerator(
    content: "https://example.com",
    style: style)

let svgString = try generator.generateSVG()

Key configuration points:

  • EFStyleParamIcon: Controls the center logo image, scaling mode, opacity, border color, and size percentage (capped at 33% of the canvas).
  • EFStyleParamBackdrop: Sets the background color, corner radius, optional background image, and quiet-zone insets via EFEdgeInsets.
  • EFStyleBasicParamsPosition: Configures the three finder patterns (position detection) with styles like .planets, .dsj, .round, or .rectangle.
  • EFStyleBasicParamsData: Defines data module appearance with options like .randomRound, .round, or .rectangle.
  • EFStyleBasicParamsAlign: Controls alignment pattern shapes when the QR code version requires them.
  • EFStyleBasicParamsTiming: Styles the timing patterns (horizontal and vertical lines connecting finder patterns).

The rendering implementation in Source/Styles/EFQRCodeStyleBasic.swift processes these parameters by iterating over the QR code matrix and emitting SVG elements according to the selected enums.

Switching to Alternative Built-In Styles

EFQRCode provides several pre-built styles beyond the basic implementation. Each style uses the same architectural pattern but exposes different aesthetic parameters:

Bubble Style

let bubbleParams = EFStyleBubbleParams(
    icon: icon,
    backdrop: backdrop,
    outerColor: CGColor.createWith(rgb: 0x1e90ff)!,
    innerColor: CGColor.createWith(rgb: 0xffffff)!,
    bubbleRadius: 1.5,
    bubbleCount: 12)

let bubbleStyle = EFQRCodeStyle.bubble(params: bubbleParams)

Implementation: Source/Styles/EFQRCodeStyleBubble.swift

2.5D Style

let params25D = EFStyle25DParams(
    icon: icon,
    backdrop: backdrop,
    // 2.5D-specific parameters
    foregroundColor: CGColor.createWith(rgb: 0x000000)!,
    shadowColor: CGColor.createWith(rgb: 0x666666)!,
    shadowBlur: 2.0,
    extrusionDepth: 0.3)

let style25D = EFQRCodeStyle._25D(params: params25D)

Implementation: Source/Styles/EFQRCodeStyle25D.swift

Other Available Styles

Each style's parameter struct provides default values accessible via static properties (e.g., EFStyleBasicParams.default), allowing you to start from a working baseline and modify only specific fields.

Incremental Customization with copyWith

When you need to modify an existing style instance without reconstructing all parameters, use the copyWith method defined in EFQRCodeStyleBase (located in Source/Styles/EFQRCodeStyle.swift):

let alteredStyle = existingStyle.copyWith(
    iconImage: .static(newIconCGImage),   // replace only the icon
    watermarkImage: nil                   // remove or keep watermark
)

Each concrete style subclass forwards this call to its parameter class's copyWith implementation, preserving all other styling options while updating only the specified icon or watermark.

Key Source Files and Parameters

File Purpose Key Components
Source/Styles/EFQRCodeStyle.swift Central style enum and base classes EFQRCodeStyle, EFStyleParams, EFStyleParamIcon, EFStyleParamBackdrop, EFQRCodeStyleBase
Source/Styles/EFQRCodeStyleBasic.swift Basic style implementation EFStyleBasicParams, EFQRCodeStyleBasic, position/data/align/timing parameter structs
Source/Styles/EFQRCodeStyleBubble.swift Bubble aesthetic EFStyleBubbleParams, EFQRCodeStyleBubble
Source/Styles/EFQRCodeStyle25D.swift 2.5D extrusion effect EFStyle25DParams, EFQRCodeStyle25D
Source/Styles/EFQRCodeStyleDSJ.swift DSJ artistic style EFStyleDSJParams, EFQRCodeStyleDSJ
Source/Styles/EFQRCodeStyleImageFill.swift Image-filled modules EFStyleImageFillParams, EFQRCodeStyleImageFill
Source/Styles/EFQRCodeStyleLine.swift Line-based rendering EFStyleLineParams, EFQRCodeStyleLine
Source/EFQRCode+Generator.swift High-level generation API EFQRCodeGenerator, generateSVG()

Summary

  • EFQRCode uses a style-centric architecture centered on the EFQRCodeStyle enum and parameter classes like EFStyleBasicParams.
  • To customize QR code styles in EFQRCode, instantiate the appropriate parameter struct (e.g., EFStyleBasicParams), configure its nested components (EFStyleBasicParamsPosition, EFStyleBasicParamsData, etc.), and wrap it in EFQRCodeStyle.basic(params:).
  • All styles support center icons via EFStyleParamIcon and background customization via EFStyleParamBackdrop, including quiet-zone control through EFEdgeInsets.
  • Alternative aesthetics (bubble, 2.5D, DSJ, image-fill) follow the same pattern but expose different parameter structs in their respective EFQRCodeStyleXXX.swift files.
  • Use copyWith(iconImage:watermarkImage:) to modify existing style instances without rebuilding all parameters.

Frequently Asked Questions

How do I change the shape of individual QR code modules in EFQRCode?

To change data module shapes, use the data parameter within your style's parameter struct. For the basic style, set EFStyleBasicParamsData.style to .rectangle, .round, .roundedRectangle, or .randomRound. For example, .randomRound renders data modules as circles with randomized sizes, while .rectangle uses traditional square blocks. This configuration is processed by the rendering logic in Source/Styles/EFQRCodeStyleBasic.swift.

Can I add a logo or icon to the center of the QR code?

Yes, all EFQRCode styles support center icons through the EFStyleParamIcon class. Create an icon instance with your CGImage, specify the scaling mode (.scaleAspectFill or .scaleAspectFit), set the alpha transparency, border color, and size percentage (capped at 33% of the canvas). Pass this icon to your style's parameter struct (e.g., EFStyleBasicParams(icon: icon, ...)). The generator automatically overlays the icon while maintaining QR code readability.

What is the difference between the Basic, Bubble, and 2.5D styles?

The Basic style (EFQRCodeStyleBasic) offers granular control over individual QR components (position patterns, data modules, timing patterns) with configurable shapes and colors. The Bubble style (EFQRCodeStyleBubble) renders the QR code as a cluster of bubble-like circles with configurable outer/inner colors and bubble count, creating a softer aesthetic. The 2.5D style (EFQRCodeStyle25D) adds extrusion depth and shadow effects to modules, creating a three-dimensional appearance. Each style is implemented in its own file within Source/Styles/ and accepts a distinct parameter struct (e.g., EFStyleBubbleParams vs EFStyle25DParams).

How do I adjust the quiet zone (padding) around the QR code?

Control the quiet zone using the quietzone parameter within EFStyleParamBackdrop. Create an EFEdgeInsets instance specifying the top, left, bottom, and right margins in module units. For example, EFEdgeInsets(top: 1, left: 1, bottom: 1, right: 1) adds a one-module padding on all sides. Pass this backdrop configuration to your style parameters (e.g., EFStyleBasicParams(backdrop: backdrop, ...)). The rendering engine in EFQRCodeStyleBasic (or your selected style) applies these insets before drawing the QR matrix.

Have a question about this repo?

These articles cover the highlights, but your codebase questions are specific. Give your agent direct access to the source. Share this with your agent to get started:

Share the following with your agent to get started:
curl -s "https://instagit.com/install.md"

Works with
Claude Codex Cursor VS Code OpenClaw Any MCP Client

Maintain an open-source project? Get it listed too →