The Core Challenge
WordPress outputs Gutenberg HTML. React Native cannot render HTML natively. This is the fundamental tension that every WordPress mobile app must solve, and how you solve it determines the quality of your entire app experience.
Most WordPress app solutions take the path of least resistance: they load the HTML into a WebView component. This works in the sense that the content appears on screen, but it is not native rendering. The text is drawn by a browser engine, not by React Native's native text components. The scroll physics are web-based, not native. And the user experience feels like a website wrapped in an app frame — because that is exactly what it is.
NativePress takes a fundamentally different approach. Instead of sending HTML to the app and letting a browser engine handle it, the plugin converts HTML to Markdown on the server, and the app renders that Markdown using native React Native components. Every heading, paragraph, image, link, and code block is a real native component.
The Data Flow Pipeline
Understanding the full pipeline helps explain why this architecture works so well. Here is the complete journey of a WordPress post from Gutenberg editor to native screen:
WordPress Gutenberg (HTML) → NativePress Plugin (league/html-to-markdown) → REST API { content_markdown: "..." } → Expo App (fetch) → Zustand Store → MarkdownRenderer (react-native-markdown-display) → Native iOS/Android UI
Each stage in this pipeline has a specific responsibility, and the clean separation between stages is what makes the system reliable and maintainable.
Stage 1: WordPress Gutenberg Output
When you write a post in WordPress using the Gutenberg block editor, the content is stored as HTML with special block comment markers. A typical paragraph block looks like this internally:
<!-- wp:paragraph --><p>Your text here.</p><!-- /wp:paragraph -->
These block comments are useful for WordPress but meaningless to a mobile app. They add noise to the payload and serve no rendering purpose. The NativePress plugin strips them out as part of the conversion process.
Stage 2: Server-Side Markdown Conversion
This is where the key transformation happens. The NativePress_Markdown class in the WordPress plugin takes the Gutenberg HTML output and converts it to clean Markdown using the league/html-to-markdown PHP library. The conversion process handles several important tasks:
- Strips Gutenberg block comments — removes all
<!-- wp:* -->markers that WordPress uses internally - Converts HTML elements to Markdown — headings become
## Heading, bold becomes**bold**, links become[text](url) - Handles figure and figcaption blocks — WordPress wraps images in
<figure>elements with optional captions. The plugin extracts the image URL and preserves the caption as Markdown text. - Preserves image URLs — all image URLs are kept as absolute paths so the app can load them directly from the WordPress media library
- Normalizes whitespace — removes excessive blank lines and ensures consistent spacing between elements
The result is a clean Markdown string that represents the post content without any HTML tags, block comments, or WordPress-specific markup.
Stage 3: REST API Delivery
The NativePress plugin exposes custom REST API endpoints under the /wp-json/nativepress/v1/ namespace. When the app requests a post, the response includes a content_markdown field alongside the standard metadata (title, author, date, featured image, categories).
All post responses go through a shared format_post() method in the NativePress_API class. This ensures consistent data shapes across all endpoints — whether you are fetching a single post, a paginated list, or search results.
The Markdown payload is significantly smaller than the equivalent HTML. A typical 1,500-word blog post might be 8KB of Gutenberg HTML but only 4KB of Markdown. This reduces bandwidth usage and speeds up content loading, especially on mobile networks.
Stage 4: App-Side Rendering
In the Expo React Native app, the Markdown string is passed to a MarkdownRenderer component that wraps the react-native-markdown-display library. This library parses the Markdown and maps each element to native React Native components:
| Markdown Element | Native Component | Benefit |
|---|---|---|
Headings (## H2) |
React Native Text |
Native font rendering |
| Paragraphs | React Native Text |
Native text selection |
Images () |
React Native Image |
Native caching, aspect ratios |
Links ([text](url)) |
expo-web-browser |
In-app browser, no context switch |
| Code blocks | Text with monospace font |
Proper syntax display |
| Lists | React Native View + Text |
Native layout engine |
| Blockquotes | Styled View wrapper |
Native border and background |
Why Markdown as the Intermediate Format
The choice of Markdown as the intermediate format between WordPress and the mobile app was deliberate. Several alternatives were considered and rejected:
- Raw HTML — requires a full HTML parser in the app, leads to WebView rendering, larger payload size
- Gutenberg block JSON — tightly coupled to WordPress internals, complex to parse, changes between WordPress versions
- Custom JSON format — would require maintaining a custom parser on both plugin and app sides, fragile to content changes
- Markdown — simple, well-specified, maps cleanly to native components, has mature parsing libraries on every platform, smaller payload than HTML
Markdown hits the sweet spot. It is expressive enough to represent all common WordPress content (headings, paragraphs, images, links, lists, blockquotes, code blocks) while being simple enough that a parser can reliably convert it to native components. And because the conversion happens on the server, the app never needs to deal with HTML parsing at all.
Handling Edge Cases
Not all WordPress content maps cleanly to Markdown. The NativePress plugin includes specific handling for several edge cases that commonly appear in WordPress posts:
Embedded Videos
YouTube and Vimeo embeds in WordPress use <iframe> elements, which have no Markdown equivalent. The plugin extracts the video URL from the iframe src attribute and converts it to a Markdown link with a video indicator. In the app, the MarkdownRenderer's custom rules detect these video links and can render a thumbnail with a play button that opens the video in expo-web-browser.
Code Blocks with Syntax Highlighting
WordPress code blocks include a language class (e.g., language-javascript). The Markdown conversion preserves this as a fenced code block with language annotation: ```javascript. The app-side renderer uses this annotation to apply appropriate monospace styling. Full syntax highlighting is possible with additional libraries, but the base implementation prioritizes readability and performance.
Nested Lists
Markdown supports nested lists through indentation, and the league/html-to-markdown library handles nested <ul> and <ol> elements correctly. The app-side renderer maps these to nested View components with increasing left padding.
Tables
WordPress Gutenberg tables are converted to Markdown pipe tables. The app-side renderer wraps tables in a horizontally scrollable container to handle wide tables on narrow screens. Column alignment is preserved from the original HTML.
Performance Wins
The performance advantages of native rendering over WebView are measurable and significant:
- Faster initial render: Native Text components render immediately. A WebView must initialize a browser engine, parse HTML, build a DOM, calculate layout, and then paint — adding 200 to 500ms of latency on typical devices.
- Smooth scrolling: Native ScrollView uses platform scroll physics (iOS bounce, Android overscroll glow). WebView scroll fights with the outer ScrollView, creating a jarring double-scroll experience.
- Image caching: Native Image components leverage the platform's image caching layer. In a WebView, image caching depends on the browser engine's HTTP cache, which is less reliable and harder to control.
- Memory efficiency: A WebView runs a full browser engine in memory. Native components use only the memory needed for the actual content. On older devices, this difference is significant.
- Smaller payload: Markdown is typically 40 to 60 percent smaller than the equivalent Gutenberg HTML, reducing download time and data usage.
Custom Render Rules
The react-native-markdown-display library allows custom render rules for any Markdown element. NativePress Dev includes customized rules for several components:
- Images: Custom rule that calculates aspect ratios, applies rounded corners, and uses progressive loading with a placeholder shimmer effect
- Links: Custom rule that opens external URLs in
expo-web-browser(an in-app browser) rather than ejecting the user to Safari or Chrome - Code blocks: Custom rule that applies a monospace font, dark background, and horizontal scrolling for long lines
- Blockquotes: Custom rule that adds a left border accent and subtle background color matching the app's theme
All custom rules respect the app's color scheme, automatically adapting to light and dark mode via useColorScheme() and CSS custom properties defined in the theme constants.
For Developers Who Want to Extend This
If you are a developer who wants to understand, modify, or extend the rendering pipeline, the NativePress Developer Edition gives you full source code access to both the WordPress plugin and the Expo app. You can add custom render rules for specific content types, modify the Markdown conversion logic, or integrate additional native components.
The architecture is deliberately modular. The plugin's Markdown class, the API's format_post method, and the app's MarkdownRenderer are all independent components that can be modified without affecting the rest of the system. For a broader look at the full stack, read the complete Expo React Native guide, or learn about the business case for native rendering.