From fa8dafcfd36798f891709e9a4e01f98f627e792a Mon Sep 17 00:00:00 2001
From: Jenny-Jiani <70129215+Jenny-Jiani@users.noreply.github.com>
Date: Wed, 30 Sep 2026 10:45:35 +0800
Subject: [PATCH 1/7] update camera-preview-renders-incorrectly-ios.md
---
...mera-preview-renders-incorrectly-ios-27.md | 102 +++++++++++++++++
.../camera-preview-renders-incorrectly-ios.md | 107 +-----------------
.../camera-preview-renders-incorrectly-ios.md | 10 +-
3 files changed, 114 insertions(+), 105 deletions(-)
create mode 100644 _includes/shared/camera-preview-renders-incorrectly-ios-27.md
diff --git a/_includes/shared/camera-preview-renders-incorrectly-ios-27.md b/_includes/shared/camera-preview-renders-incorrectly-ios-27.md
new file mode 100644
index 0000000..b56655f
--- /dev/null
+++ b/_includes/shared/camera-preview-renders-incorrectly-ios-27.md
@@ -0,0 +1,102 @@
+# Why does the camera preview render incorrectly on iOS 27?
+
+## Applicable Products
+
+This article applies to:
+
+- Dynamsoft Barcode Reader (DBR) JavaScript SDK (`dynamsoft-barcode-reader-bundle`) 11.6.3000 and earlier
+- Dynamsoft Capture Vision (DCV) JavaScript SDK (`dynamsoft-capture-vision-bundle`) 3.6.3000 and earlier
+
+## Summary
+
+On iOS 27, switching cameras or changing resolution can make the live camera preview render incorrectly. The exact behavior depends on the SDK version:
+
+| Version | Behavior |
+|---|---|
+| DBR 11.4 - 11.6.3000 (DCV 3.4 - 3.6.3000) | The preview renders distorted - squeezed or stretched instead of filling its container. Intermittent: the same switch can render correctly on one attempt and distorted on the next. |
+| DBR 11.2 and earlier (DCV 3.2 and earlier) | The preview isn't distorted, but it no longer fits its container - shown at the wrong zoom or size and not extending to the borders. |
+
+It's reproducible on Safari, Chrome, Edge, and Firefox - all iOS browsers share WebKit's camera implementation, so we suspect the issue originates there rather than in any Dynamsoft SDK. It does not occur on iOS 26.
+
+> [!NOTE]
+> Reported to Apple, but not confirmed as an Apple bug and still open as of iOS 27 RC. Details here may change if Apple ships a fix.
+
+
+
+
+ Expected
+
+
+
+ Distorted after switching cameras
+
+
+
+## Resolution
+
+### Recommended: upgrade
+
+Upgrade to `dynamsoft-barcode-reader-bundle` **11.6.3200+** or `dynamsoft-capture-vision-bundle` **3.6.3200+**, which include a built-in workaround.
+
+### If you can't upgrade yet
+
+Both workarounds below are temporary and version-specific - neither replaces upgrading.
+
+**DBR 11.4 - 11.6.3000 (DCV 3.4 - 3.6.3000)**
+
+The distortion requires `object-fit: fill` on the video element plus an ancestor using `display: flex` with `flex: 0 0 auto`, so overriding `object-fit` with `cover` on the `` element that [Dynamsoft Camera Enhancer](https://www.dynamsoft.com/camera-enhancer/docs/web/) renders avoids it:
+
+```css
+.dm-camera-core-container video {
+ object-fit: cover !important;
+}
+```
+
+`!important` is needed because the SDK sets `object-fit` inline. The JavaScript equivalent, via [`cameraView.getVideoElement()`](https://www.dynamsoft.com/camera-enhancer/docs/web/programming/javascript/api-reference/cameraview.html?product=dbr&lang=javascript#getvideoelement):
+
+```javascript
+let videoElement = cameraView.getVideoElement();
+videoElement?.style.setProperty('object-fit', 'cover', 'important');
+```
+
+> [!WARNING]
+> `cover` crops rather than stretches to preserve the aspect ratio - confirm that trade-off works for your UI.
+
+**DBR 11.2 and earlier (DCV 3.2 and earlier)**
+
+Reset the video element's dimensions whenever the camera or resolution changes, registering the handlers before `cameraEnhancer.open()`:
+
+```javascript
+const resetVideoWH = () => {
+ const videoEl = cameraEnhancer.getVideoEl();
+ videoEl.style.width = "";
+ videoEl.style.height = "";
+
+ requestAnimationFrame(() => {
+ requestAnimationFrame(() => {
+ videoEl.style.width = "100%";
+ videoEl.style.height = "100%";
+ });
+ });
+};
+cameraEnhancer.on("cameraChange", resetVideoWH);
+cameraEnhancer.on("resolutionChange", resetVideoWH);
+
+cameraView.createDrawingLayer(2); // layer ID depends on the product - see below
+
+// Normal startup routine, shown here only to indicate placement
+await cameraEnhancer.open();
+await cvRouter.startCapturing();
+```
+
+The `createDrawingLayer` call is part of the workaround. Pass the layer ID for your product:
+
+| Product | Layer ID |
+|---|---|
+| Dynamsoft Barcode Reader (DBR) | 2 |
+| Mobile Document Scanner (MDS - DDN layer) | 1 |
+| MRZ Scanner (DLR layer) | 3 |
+
+## Need more help?
+
+[Contact the Dynamsoft Support team](https://www.dynamsoft.com/contact/).
\ No newline at end of file
diff --git a/barcode-reader/web/camera/camera-preview-renders-incorrectly-ios.md b/barcode-reader/web/camera/camera-preview-renders-incorrectly-ios.md
index 4779519..1014006 100644
--- a/barcode-reader/web/camera/camera-preview-renders-incorrectly-ios.md
+++ b/barcode-reader/web/camera/camera-preview-renders-incorrectly-ios.md
@@ -1,110 +1,9 @@
---
layout: default-layout
-title: Why does the camera preview render incorrectly on iOS 27?
+title: Why Does the Barcode Reader's Camera Preview Render Incorrectly on iOS 27?
keywords: iOS 27, camera, preview, distorted, video, switching camera, changing resolution, Safari, Chrome, Edge, Firefox, WebKit, Dynamsoft Camera Enhancer, Dynamsoft Barcode Reader, Dynamsoft MRZ Scanner
-description: On iOS 27, switching cameras or changing resolution can make the live camera preview render distorted or fit its container incorrectly. Fixed in dynamsoft-barcode-reader-bundle 11.6.3200 and dynamsoft-capture-vision-bundle 3.6.3200; workarounds are available for earlier versions.
+description: On iOS 27, switching cameras or resolution can distort or misfit the MRZ Scanner's live camera preview - a WebKit-wide issue, not specific to Dynamsoft. See the fix in 11.6.3200+/3.6.3200+ and workarounds for older versions.
needAutoGenerateSidebar: false
---
-# Why does the camera preview render incorrectly on iOS 27?
-
-## Applicable Products
-
-This article applies to:
-
-- Dynamsoft Barcode Reader (DBR) JavaScript SDK (`dynamsoft-barcode-reader-bundle`) 11.6.3000 and earlier
-- Dynamsoft Capture Vision (DCV) JavaScript SDK (`dynamsoft-capture-vision-bundle`) 3.6.3000 and earlier
-
-## Summary
-
-On iOS 27, switching cameras or changing resolution can make the live camera preview render incorrectly. The exact behavior depends on the SDK version:
-
-| Version | Behavior |
-|---|---|
-| DBR 11.4 – 11.6.3000 (DCV 3.4 – 3.6.3000) | The preview renders distorted — squeezed or stretched instead of filling its container. Intermittent: the same switch can render correctly on one attempt and distorted on the next. |
-| DBR 11.2 and earlier (DCV 3.2 and earlier) | The preview isn't distorted, but it no longer fits its container — shown at the wrong zoom or size and not extending to the borders. |
-
-It's reproducible on Safari, Chrome, Edge, and Firefox — all iOS browsers share WebKit's camera implementation, so we suspect the issue originates there rather than in any Dynamsoft SDK. It does not occur on iOS 26.
-
-> [!NOTE]
-> Reported to Apple, but not confirmed as an Apple bug and still open as of iOS 27 RC. Details here may change if Apple ships a fix.
-
-
-
-
- Expected
-
-
-
- Distorted after switching cameras
-
-
-
-## Resolution
-
-### Recommended: upgrade
-
-Upgrade to `dynamsoft-barcode-reader-bundle` **11.6.3200+** or `dynamsoft-capture-vision-bundle` **3.6.3200+**, which include a built-in workaround.
-
-### If you can't upgrade yet
-
-Both workarounds below are temporary and version-specific — neither replaces upgrading.
-
-**DBR 11.4 – 11.6.3000 (DCV 3.4 – 3.6.3000)**
-
-The distortion requires `object-fit: fill` on the video element plus an ancestor using `display: flex` with `flex: 0 0 auto`, so overriding `object-fit` with `cover` on the `` element that [Dynamsoft Camera Enhancer](https://www.dynamsoft.com/camera-enhancer/docs/web/) renders avoids it:
-
-```css
-.dm-camera-core-container video {
- object-fit: cover !important;
-}
-```
-
-`!important` is needed because the SDK sets `object-fit` inline. The JavaScript equivalent, via [`cameraView.getVideoElement()`](https://www.dynamsoft.com/camera-enhancer/docs/web/programming/javascript/api-reference/cameraview.html?product=dbr&lang=javascript#getvideoelement):
-
-```javascript
-let videoElement = cameraView.getVideoElement();
-videoElement?.style.setProperty('object-fit', 'cover', 'important');
-```
-
-> [!WARNING]
-> `cover` crops rather than stretches to preserve the aspect ratio — confirm that trade-off works for your UI.
-
-**DBR 11.2 and earlier (DCV 3.2 and earlier)**
-
-Reset the video element's dimensions whenever the camera or resolution changes, registering the handlers before `cameraEnhancer.open()`:
-
-```javascript
-const resetVideoWH = () => {
- const videoEl = cameraEnhancer.getVideoEl();
- videoEl.style.width = "";
- videoEl.style.height = "";
-
- requestAnimationFrame(() => {
- requestAnimationFrame(() => {
- videoEl.style.width = "100%";
- videoEl.style.height = "100%";
- });
- });
-};
-cameraEnhancer.on("cameraChange", resetVideoWH);
-cameraEnhancer.on("resolutionChange", resetVideoWH);
-
-cameraView.createDrawingLayer(2); // layer ID depends on the product — see below
-
-// Normal startup routine, shown here only to indicate placement
-await cameraEnhancer.open();
-await cvRouter.startCapturing();
-```
-
-The `createDrawingLayer` call is part of the workaround. Pass the layer ID for your product:
-
-| Product | Layer ID |
-|---|---|
-| Dynamsoft Barcode Reader (DBR) | 2 |
-| Mobile Document Scanner (MDS — DDN layer) | 1 |
-| MRZ Scanner (DLR layer) | 3 |
-
-## Need more help?
-
-[Contact the Dynamsoft Support team](https://www.dynamsoft.com/contact/).
+{% include shared/camera-preview-renders-incorrectly-ios-27.md %}
diff --git a/mrz-scanner/general/camera-preview-renders-incorrectly-ios.md b/mrz-scanner/general/camera-preview-renders-incorrectly-ios.md
index 4904f82..c68e2c3 120000
--- a/mrz-scanner/general/camera-preview-renders-incorrectly-ios.md
+++ b/mrz-scanner/general/camera-preview-renders-incorrectly-ios.md
@@ -1 +1,9 @@
-../../barcode-reader/web/camera/camera-preview-renders-incorrectly-ios.md
\ No newline at end of file
+---
+layout: default-layout
+title: Why Does the MRZ Scanner's Camera Preview Render Incorrectly on iOS 27?
+keywords: iOS 27, camera, preview, distorted, video, switching camera, changing resolution, Safari, Chrome, Edge, Firefox, WebKit, Dynamsoft Camera Enhancer, Dynamsoft Barcode Reader, Dynamsoft MRZ Scanner
+description: iOS 27 can render the Barcode Reader's live camera preview distorted or out of alignment after switching cameras or resolution. Learn which SDK versions are affected and how to fix or work around it.
+needAutoGenerateSidebar: false
+---
+
+{% include shared/camera-preview-renders-incorrectly-ios-27.md %}
\ No newline at end of file
From 3506cf14db35ec2e1f69cbaab25ab6010eb8d880 Mon Sep 17 00:00:00 2001
From: Jenny-Jiani <70129215+Jenny-Jiani@users.noreply.github.com>
Date: Wed, 30 Sep 2026 11:01:24 +0800
Subject: [PATCH 2/7] Revert "update camera-preview-renders-incorrectly-ios.md"
This reverts commit fa8dafcfd36798f891709e9a4e01f98f627e792a.
---
.../general/camera-preview-renders-incorrectly-ios.md | 9 ---------
1 file changed, 9 deletions(-)
delete mode 120000 mrz-scanner/general/camera-preview-renders-incorrectly-ios.md
diff --git a/mrz-scanner/general/camera-preview-renders-incorrectly-ios.md b/mrz-scanner/general/camera-preview-renders-incorrectly-ios.md
deleted file mode 120000
index c68e2c3..0000000
--- a/mrz-scanner/general/camera-preview-renders-incorrectly-ios.md
+++ /dev/null
@@ -1,9 +0,0 @@
----
-layout: default-layout
-title: Why Does the MRZ Scanner's Camera Preview Render Incorrectly on iOS 27?
-keywords: iOS 27, camera, preview, distorted, video, switching camera, changing resolution, Safari, Chrome, Edge, Firefox, WebKit, Dynamsoft Camera Enhancer, Dynamsoft Barcode Reader, Dynamsoft MRZ Scanner
-description: iOS 27 can render the Barcode Reader's live camera preview distorted or out of alignment after switching cameras or resolution. Learn which SDK versions are affected and how to fix or work around it.
-needAutoGenerateSidebar: false
----
-
-{% include shared/camera-preview-renders-incorrectly-ios-27.md %}
\ No newline at end of file
From d85808c416c59fe51d97fe678dcaa727b3ad2480 Mon Sep 17 00:00:00 2001
From: Jenny-Jiani <70129215+Jenny-Jiani@users.noreply.github.com>
Date: Wed, 30 Sep 2026 11:07:33 +0800
Subject: [PATCH 3/7] Create camera-preview-renders-incorrectly-ios.md
---
.../general/camera-preview-renders-incorrectly-ios.md | 9 +++++++++
1 file changed, 9 insertions(+)
create mode 100644 mrz-scanner/general/camera-preview-renders-incorrectly-ios.md
diff --git a/mrz-scanner/general/camera-preview-renders-incorrectly-ios.md b/mrz-scanner/general/camera-preview-renders-incorrectly-ios.md
new file mode 100644
index 0000000..e76ddf6
--- /dev/null
+++ b/mrz-scanner/general/camera-preview-renders-incorrectly-ios.md
@@ -0,0 +1,9 @@
+---
+layout: default-layout
+title: Why Does the MRZ Scanner's Camera Preview Render Incorrectly on iOS 27?
+keywords: iOS 27, camera, preview, distorted, video, switching camera, changing resolution, Safari, Chrome, Edge, Firefox, WebKit, Dynamsoft Camera Enhancer, Dynamsoft Barcode Reader, Dynamsoft MRZ Scanner
+description: On iOS 27, switching cameras or resolution can distort or misfit the MRZ Scanner's live camera preview — a WebKit-wide issue, not specific to Dynamsoft. See the fix in 11.6.3200+/3.6.3200+ and workarounds for older versions.
+needAutoGenerateSidebar: false
+---
+
+{% include shared/camera-preview-renders-incorrectly-ios-27.md %}
From 26fa6333745a46a44414cd91028ab71f7f000a25 Mon Sep 17 00:00:00 2001
From: Jenny-Jiani <70129215+Jenny-Jiani@users.noreply.github.com>
Date: Wed, 30 Sep 2026 13:07:04 +0800
Subject: [PATCH 4/7] Rollback changes
This reverts commit d85808c416c59fe51d97fe678dcaa727b3ad2480.
---
...mera-preview-renders-incorrectly-ios-27.md | 102 -----------------
.../camera-preview-renders-incorrectly-ios.md | 107 +++++++++++++++++-
.../camera-preview-renders-incorrectly-ios.md | 10 +-
3 files changed, 105 insertions(+), 114 deletions(-)
delete mode 100644 _includes/shared/camera-preview-renders-incorrectly-ios-27.md
diff --git a/_includes/shared/camera-preview-renders-incorrectly-ios-27.md b/_includes/shared/camera-preview-renders-incorrectly-ios-27.md
deleted file mode 100644
index b56655f..0000000
--- a/_includes/shared/camera-preview-renders-incorrectly-ios-27.md
+++ /dev/null
@@ -1,102 +0,0 @@
-# Why does the camera preview render incorrectly on iOS 27?
-
-## Applicable Products
-
-This article applies to:
-
-- Dynamsoft Barcode Reader (DBR) JavaScript SDK (`dynamsoft-barcode-reader-bundle`) 11.6.3000 and earlier
-- Dynamsoft Capture Vision (DCV) JavaScript SDK (`dynamsoft-capture-vision-bundle`) 3.6.3000 and earlier
-
-## Summary
-
-On iOS 27, switching cameras or changing resolution can make the live camera preview render incorrectly. The exact behavior depends on the SDK version:
-
-| Version | Behavior |
-|---|---|
-| DBR 11.4 - 11.6.3000 (DCV 3.4 - 3.6.3000) | The preview renders distorted - squeezed or stretched instead of filling its container. Intermittent: the same switch can render correctly on one attempt and distorted on the next. |
-| DBR 11.2 and earlier (DCV 3.2 and earlier) | The preview isn't distorted, but it no longer fits its container - shown at the wrong zoom or size and not extending to the borders. |
-
-It's reproducible on Safari, Chrome, Edge, and Firefox - all iOS browsers share WebKit's camera implementation, so we suspect the issue originates there rather than in any Dynamsoft SDK. It does not occur on iOS 26.
-
-> [!NOTE]
-> Reported to Apple, but not confirmed as an Apple bug and still open as of iOS 27 RC. Details here may change if Apple ships a fix.
-
-
-
-
- Expected
-
-
-
- Distorted after switching cameras
-
-
-
-## Resolution
-
-### Recommended: upgrade
-
-Upgrade to `dynamsoft-barcode-reader-bundle` **11.6.3200+** or `dynamsoft-capture-vision-bundle` **3.6.3200+**, which include a built-in workaround.
-
-### If you can't upgrade yet
-
-Both workarounds below are temporary and version-specific - neither replaces upgrading.
-
-**DBR 11.4 - 11.6.3000 (DCV 3.4 - 3.6.3000)**
-
-The distortion requires `object-fit: fill` on the video element plus an ancestor using `display: flex` with `flex: 0 0 auto`, so overriding `object-fit` with `cover` on the `` element that [Dynamsoft Camera Enhancer](https://www.dynamsoft.com/camera-enhancer/docs/web/) renders avoids it:
-
-```css
-.dm-camera-core-container video {
- object-fit: cover !important;
-}
-```
-
-`!important` is needed because the SDK sets `object-fit` inline. The JavaScript equivalent, via [`cameraView.getVideoElement()`](https://www.dynamsoft.com/camera-enhancer/docs/web/programming/javascript/api-reference/cameraview.html?product=dbr&lang=javascript#getvideoelement):
-
-```javascript
-let videoElement = cameraView.getVideoElement();
-videoElement?.style.setProperty('object-fit', 'cover', 'important');
-```
-
-> [!WARNING]
-> `cover` crops rather than stretches to preserve the aspect ratio - confirm that trade-off works for your UI.
-
-**DBR 11.2 and earlier (DCV 3.2 and earlier)**
-
-Reset the video element's dimensions whenever the camera or resolution changes, registering the handlers before `cameraEnhancer.open()`:
-
-```javascript
-const resetVideoWH = () => {
- const videoEl = cameraEnhancer.getVideoEl();
- videoEl.style.width = "";
- videoEl.style.height = "";
-
- requestAnimationFrame(() => {
- requestAnimationFrame(() => {
- videoEl.style.width = "100%";
- videoEl.style.height = "100%";
- });
- });
-};
-cameraEnhancer.on("cameraChange", resetVideoWH);
-cameraEnhancer.on("resolutionChange", resetVideoWH);
-
-cameraView.createDrawingLayer(2); // layer ID depends on the product - see below
-
-// Normal startup routine, shown here only to indicate placement
-await cameraEnhancer.open();
-await cvRouter.startCapturing();
-```
-
-The `createDrawingLayer` call is part of the workaround. Pass the layer ID for your product:
-
-| Product | Layer ID |
-|---|---|
-| Dynamsoft Barcode Reader (DBR) | 2 |
-| Mobile Document Scanner (MDS - DDN layer) | 1 |
-| MRZ Scanner (DLR layer) | 3 |
-
-## Need more help?
-
-[Contact the Dynamsoft Support team](https://www.dynamsoft.com/contact/).
\ No newline at end of file
diff --git a/barcode-reader/web/camera/camera-preview-renders-incorrectly-ios.md b/barcode-reader/web/camera/camera-preview-renders-incorrectly-ios.md
index 1014006..4779519 100644
--- a/barcode-reader/web/camera/camera-preview-renders-incorrectly-ios.md
+++ b/barcode-reader/web/camera/camera-preview-renders-incorrectly-ios.md
@@ -1,9 +1,110 @@
---
layout: default-layout
-title: Why Does the Barcode Reader's Camera Preview Render Incorrectly on iOS 27?
+title: Why does the camera preview render incorrectly on iOS 27?
keywords: iOS 27, camera, preview, distorted, video, switching camera, changing resolution, Safari, Chrome, Edge, Firefox, WebKit, Dynamsoft Camera Enhancer, Dynamsoft Barcode Reader, Dynamsoft MRZ Scanner
-description: On iOS 27, switching cameras or resolution can distort or misfit the MRZ Scanner's live camera preview - a WebKit-wide issue, not specific to Dynamsoft. See the fix in 11.6.3200+/3.6.3200+ and workarounds for older versions.
+description: On iOS 27, switching cameras or changing resolution can make the live camera preview render distorted or fit its container incorrectly. Fixed in dynamsoft-barcode-reader-bundle 11.6.3200 and dynamsoft-capture-vision-bundle 3.6.3200; workarounds are available for earlier versions.
needAutoGenerateSidebar: false
---
-{% include shared/camera-preview-renders-incorrectly-ios-27.md %}
+# Why does the camera preview render incorrectly on iOS 27?
+
+## Applicable Products
+
+This article applies to:
+
+- Dynamsoft Barcode Reader (DBR) JavaScript SDK (`dynamsoft-barcode-reader-bundle`) 11.6.3000 and earlier
+- Dynamsoft Capture Vision (DCV) JavaScript SDK (`dynamsoft-capture-vision-bundle`) 3.6.3000 and earlier
+
+## Summary
+
+On iOS 27, switching cameras or changing resolution can make the live camera preview render incorrectly. The exact behavior depends on the SDK version:
+
+| Version | Behavior |
+|---|---|
+| DBR 11.4 – 11.6.3000 (DCV 3.4 – 3.6.3000) | The preview renders distorted — squeezed or stretched instead of filling its container. Intermittent: the same switch can render correctly on one attempt and distorted on the next. |
+| DBR 11.2 and earlier (DCV 3.2 and earlier) | The preview isn't distorted, but it no longer fits its container — shown at the wrong zoom or size and not extending to the borders. |
+
+It's reproducible on Safari, Chrome, Edge, and Firefox — all iOS browsers share WebKit's camera implementation, so we suspect the issue originates there rather than in any Dynamsoft SDK. It does not occur on iOS 26.
+
+> [!NOTE]
+> Reported to Apple, but not confirmed as an Apple bug and still open as of iOS 27 RC. Details here may change if Apple ships a fix.
+
+
+
+
+ Expected
+
+
+
+ Distorted after switching cameras
+
+
+
+## Resolution
+
+### Recommended: upgrade
+
+Upgrade to `dynamsoft-barcode-reader-bundle` **11.6.3200+** or `dynamsoft-capture-vision-bundle` **3.6.3200+**, which include a built-in workaround.
+
+### If you can't upgrade yet
+
+Both workarounds below are temporary and version-specific — neither replaces upgrading.
+
+**DBR 11.4 – 11.6.3000 (DCV 3.4 – 3.6.3000)**
+
+The distortion requires `object-fit: fill` on the video element plus an ancestor using `display: flex` with `flex: 0 0 auto`, so overriding `object-fit` with `cover` on the `` element that [Dynamsoft Camera Enhancer](https://www.dynamsoft.com/camera-enhancer/docs/web/) renders avoids it:
+
+```css
+.dm-camera-core-container video {
+ object-fit: cover !important;
+}
+```
+
+`!important` is needed because the SDK sets `object-fit` inline. The JavaScript equivalent, via [`cameraView.getVideoElement()`](https://www.dynamsoft.com/camera-enhancer/docs/web/programming/javascript/api-reference/cameraview.html?product=dbr&lang=javascript#getvideoelement):
+
+```javascript
+let videoElement = cameraView.getVideoElement();
+videoElement?.style.setProperty('object-fit', 'cover', 'important');
+```
+
+> [!WARNING]
+> `cover` crops rather than stretches to preserve the aspect ratio — confirm that trade-off works for your UI.
+
+**DBR 11.2 and earlier (DCV 3.2 and earlier)**
+
+Reset the video element's dimensions whenever the camera or resolution changes, registering the handlers before `cameraEnhancer.open()`:
+
+```javascript
+const resetVideoWH = () => {
+ const videoEl = cameraEnhancer.getVideoEl();
+ videoEl.style.width = "";
+ videoEl.style.height = "";
+
+ requestAnimationFrame(() => {
+ requestAnimationFrame(() => {
+ videoEl.style.width = "100%";
+ videoEl.style.height = "100%";
+ });
+ });
+};
+cameraEnhancer.on("cameraChange", resetVideoWH);
+cameraEnhancer.on("resolutionChange", resetVideoWH);
+
+cameraView.createDrawingLayer(2); // layer ID depends on the product — see below
+
+// Normal startup routine, shown here only to indicate placement
+await cameraEnhancer.open();
+await cvRouter.startCapturing();
+```
+
+The `createDrawingLayer` call is part of the workaround. Pass the layer ID for your product:
+
+| Product | Layer ID |
+|---|---|
+| Dynamsoft Barcode Reader (DBR) | 2 |
+| Mobile Document Scanner (MDS — DDN layer) | 1 |
+| MRZ Scanner (DLR layer) | 3 |
+
+## Need more help?
+
+[Contact the Dynamsoft Support team](https://www.dynamsoft.com/contact/).
diff --git a/mrz-scanner/general/camera-preview-renders-incorrectly-ios.md b/mrz-scanner/general/camera-preview-renders-incorrectly-ios.md
index e76ddf6..4904f82 100644
--- a/mrz-scanner/general/camera-preview-renders-incorrectly-ios.md
+++ b/mrz-scanner/general/camera-preview-renders-incorrectly-ios.md
@@ -1,9 +1 @@
----
-layout: default-layout
-title: Why Does the MRZ Scanner's Camera Preview Render Incorrectly on iOS 27?
-keywords: iOS 27, camera, preview, distorted, video, switching camera, changing resolution, Safari, Chrome, Edge, Firefox, WebKit, Dynamsoft Camera Enhancer, Dynamsoft Barcode Reader, Dynamsoft MRZ Scanner
-description: On iOS 27, switching cameras or resolution can distort or misfit the MRZ Scanner's live camera preview — a WebKit-wide issue, not specific to Dynamsoft. See the fix in 11.6.3200+/3.6.3200+ and workarounds for older versions.
-needAutoGenerateSidebar: false
----
-
-{% include shared/camera-preview-renders-incorrectly-ios-27.md %}
+../../barcode-reader/web/camera/camera-preview-renders-incorrectly-ios.md
\ No newline at end of file
From 5b1404d50e319518c1566a250ba3657e9d37934f Mon Sep 17 00:00:00 2001
From: Louie-Dynamsoft
Date: Tue, 29 Sep 2026 22:40:39 -0700
Subject: [PATCH 5/7] Add local Jekyll development scripts for FAQ (#67)
* Add local Jekyll development scripts for FAQ
* Keep archived FAQ pages out of local preview builds
---
.gitattributes | 1 +
.gitignore | 1 +
AGENTS.md | 6 ++
README.md | 16 ++++-
check_links.py | 1 +
scripts/dev.ps1 | 159 ++++++++++++++++++++++++++++++++++++++++++
scripts/dev.sh | 180 ++++++++++++++++++++++++++++++++++++++++++++++++
7 files changed, 363 insertions(+), 1 deletion(-)
create mode 100644 .gitattributes
create mode 100644 scripts/dev.ps1
create mode 100755 scripts/dev.sh
diff --git a/.gitattributes b/.gitattributes
new file mode 100644
index 0000000..0992525
--- /dev/null
+++ b/.gitattributes
@@ -0,0 +1 @@
+scripts/dev.sh text eol=lf
diff --git a/.gitignore b/.gitignore
index dc88a1b..55f042d 100644
--- a/.gitignore
+++ b/.gitignore
@@ -6,4 +6,5 @@ logs/
temp/*
!temp/keep.txt
.idea
+.dev/
# *.py
\ No newline at end of file
diff --git a/AGENTS.md b/AGENTS.md
index d7219cd..591c020 100644
--- a/AGENTS.md
+++ b/AGENTS.md
@@ -47,6 +47,12 @@ Directories named `archive` under `barcode-reader/{mobile,server,web}/` hold his
If you find yourself wanting to *add* content to an archive directory, it almost certainly belongs in the live directory instead.
+## Testing the local site
+
+The Jekyll layout comes from `Docs-Template-Repo`, not this repository. Install Git and Ruby/Bundler plus `rsync` (Bash) or `robocopy` (PowerShell). From the repo root, run `./scripts/dev.sh` or `./scripts/dev.ps1` to prepare `.dev/DocHome` and serve at `http://localhost:5555/faq/`. The scripts exclude archived FAQ directories and local worktrees from that merged workspace.
+
+For preparation without a server, use `./scripts/dev.sh --no-serve` or `./scripts/dev.ps1 -NoServe`; rerun the script without that flag to start the server. Use `--no-template-update` / `-NoTemplateUpdate` to reuse the cloned template. Rerun after editing FAQ source because the merged workspace is a copy, then check the changed page in the local site. `.dev/` is generated and Git-ignored; do not edit it as source.
+
## Before finishing
Run the link checker from the repo root and fix anything it flags in files you touched:
diff --git a/README.md b/README.md
index 1fc04f5..d37240b 100644
--- a/README.md
+++ b/README.md
@@ -10,10 +10,24 @@ See [`AGENTS.md`](AGENTS.md) for the FAQ article structure, frontmatter, linking
The site is built with Jekyll using a shared theme/layout maintained in [dynamsoft-docs/Docs-Template-Repo](https://github.com/dynamsoft-docs/Docs-Template-Repo), which this repo doesn't include locally. Pushes to `main` and `preview` trigger the CI workflows in `.github/workflows/main.yml`, which build and sync to production and the preview/testing environment respectively.
+For a local preview, install Git, Ruby/Bundler, and rsync (Bash) or robocopy (PowerShell), then run from the repository root:
+
+```bash
+./scripts/dev.sh
+```
+
+Or on Windows:
+
+```powershell
+./scripts/dev.ps1
+```
+
+The scripts clone the shared template's preview branch into `.dev/`, merge it with this FAQ source, install gems, and serve Jekyll at `http://localhost:5555/faq/`. The generated `.dev/` workspace is ignored by Git and omits archived FAQ content and local worktrees. Use `--no-serve` / `-NoServe` to prepare without serving, then rerun without that flag to serve; `--no-template-update` / `-NoTemplateUpdate` reuses the cloned template. Changes to FAQ files require rerunning the script to refresh the merged workspace.
+
## Checking links
`check_links.py` crawls the repo's Markdown files and reports broken links. Run it before submitting a change that touches links:
```bash
python check_links.py
-```
+```
\ No newline at end of file
diff --git a/check_links.py b/check_links.py
index ce54653..798579b 100644
--- a/check_links.py
+++ b/check_links.py
@@ -26,6 +26,7 @@ def find_md_files(root_dir):
for root, dirs, files in os.walk(root_dir):
if '.git' in dirs: dirs.remove('.git')
if '_site' in dirs: dirs.remove('_site')
+ if '.dev' in dirs: dirs.remove('.dev')
for file in files:
if file.endswith('.md'):
diff --git a/scripts/dev.ps1 b/scripts/dev.ps1
new file mode 100644
index 0000000..0d5abd5
--- /dev/null
+++ b/scripts/dev.ps1
@@ -0,0 +1,159 @@
+[CmdletBinding()]
+param(
+ [string]$TemplateRepoUrl = "https://github.com/dynamsoft-docs/Docs-Template-Repo.git",
+ [string]$TemplateBranch = "preview",
+ [int]$Port = 5555,
+ [string]$BindHost = "localhost",
+ [switch]$NoTemplateUpdate,
+ [switch]$NoServe
+)
+
+Set-StrictMode -Version Latest
+$ErrorActionPreference = "Stop"
+
+function Write-Step {
+ param([string]$Message)
+ Write-Host "==> $Message"
+}
+
+function Ensure-Command {
+ param([string]$Name)
+ if (-not (Get-Command $Name -ErrorAction SilentlyContinue)) {
+ throw "Required command '$Name' was not found in PATH."
+ }
+}
+
+function Invoke-Native {
+ param(
+ [Parameter(Mandatory = $true)]
+ [string]$FilePath,
+ [string[]]$Arguments = @()
+ )
+
+ & $FilePath @Arguments
+ $code = $LASTEXITCODE
+ if ($code -ne 0) {
+ $argText = ($Arguments -join " ")
+ throw "Command failed with exit code ${code}: $FilePath $argText"
+ }
+}
+
+function Invoke-Robocopy {
+ param(
+ [string]$Source,
+ [string]$Destination,
+ [string[]]$ExtraArgs
+ )
+
+ $baseArgs = @(
+ $Source,
+ $Destination,
+ "/R:2",
+ "/W:2",
+ "/NFL",
+ "/NDL",
+ "/NJH",
+ "/NJS",
+ "/NP"
+ )
+ $allArgs = $baseArgs + $ExtraArgs
+ & robocopy @allArgs | Out-Null
+ $code = $LASTEXITCODE
+ if ($code -ge 8) {
+ throw "robocopy failed with exit code $code. Source: $Source Destination: $Destination"
+ }
+}
+
+Ensure-Command "git"
+Ensure-Command "robocopy"
+Ensure-Command "bundle"
+
+$repoRoot = Split-Path -Parent $PSScriptRoot
+$devRoot = Join-Path $repoRoot ".dev"
+$templateRoot = Join-Path $devRoot "Docs-Template-Repo"
+$docHome = Join-Path $devRoot "DocHome"
+$bundlePath = Join-Path $devRoot "vendor\bundle"
+$bundleConfig = Join-Path $devRoot ".bundle"
+$bundleUserHome = Join-Path $devRoot ".bundle-user"
+$jekyllCache = Join-Path $devRoot ".jekyll-cache"
+$siteDir = Join-Path $devRoot "_site"
+
+Write-Step "Preparing local workspace in $devRoot"
+New-Item -ItemType Directory -Force -Path $devRoot | Out-Null
+
+if (-not (Test-Path $templateRoot)) {
+ Write-Step "Cloning template repo ($TemplateBranch)"
+ Invoke-Native -FilePath "git" -Arguments @("clone", "--depth", "1", "--branch", $TemplateBranch, $TemplateRepoUrl, $templateRoot)
+} elseif (-not $NoTemplateUpdate) {
+ Write-Step "Syncing template repo ($TemplateBranch)"
+ Invoke-Native -FilePath "git" -Arguments @("-C", $templateRoot, "fetch", "origin", $TemplateBranch, "--depth", "1")
+ Invoke-Native -FilePath "git" -Arguments @("-C", $templateRoot, "reset", "--hard")
+ Invoke-Native -FilePath "git" -Arguments @("-C", $templateRoot, "clean", "-fd")
+ Invoke-Native -FilePath "git" -Arguments @("-C", $templateRoot, "checkout", "-B", $TemplateBranch, "origin/$TemplateBranch")
+} else {
+ Write-Step "Skipping template update"
+}
+
+Write-Step "Rebuilding merged site workspace"
+if (Test-Path $docHome) {
+ Remove-Item -LiteralPath $docHome -Recurse -Force
+}
+New-Item -ItemType Directory -Force -Path $docHome | Out-Null
+Invoke-Robocopy -Source $repoRoot -Destination $docHome -ExtraArgs @(
+ "/MIR",
+ "/XD", ".git", ".dev", ".claude", ".vs", "node_modules", "_site", ".bundle", ".jekyll-cache", ".sass-cache", "vendor",
+ (Join-Path $repoRoot "barcode-reader\mobile\archive"),
+ (Join-Path $repoRoot "barcode-reader\server\archive"),
+ (Join-Path $repoRoot "barcode-reader\web\archive")
+)
+Invoke-Robocopy -Source $templateRoot -Destination $docHome -ExtraArgs @(
+ "/E",
+ "/XD", ".git", ".github", "_site", "node_modules"
+)
+
+Write-Step "Applying local assetsPath replacements"
+$search = "assetsPath = '/webres/wwwroot'"
+$replace = "assetsPath = 'https://www.dynamsoft.com/webres/wwwroot'"
+foreach ($dirName in @("_includes", "_layouts")) {
+ $dirPath = Join-Path $docHome $dirName
+ if (-not (Test-Path $dirPath)) {
+ continue
+ }
+
+ Get-ChildItem -Path $dirPath -Recurse -File | ForEach-Object {
+ $path = $_.FullName
+ try {
+ $content = [System.IO.File]::ReadAllText($path)
+ } catch {
+ return
+ }
+ if ($content.Contains($search)) {
+ $updated = $content.Replace($search, $replace)
+ [System.IO.File]::WriteAllText($path, $updated)
+ }
+ }
+}
+
+Write-Step "Configuring Bundler and Jekyll local paths"
+$env:BUNDLE_PATH = $bundlePath
+$env:BUNDLE_APP_CONFIG = $bundleConfig
+$env:BUNDLE_USER_HOME = $bundleUserHome
+$env:BUNDLE_USER_CACHE = Join-Path $bundleUserHome "cache"
+$env:JEKYLL_CACHE_DIR = $jekyllCache
+$env:JEKYLL_ENV = "development"
+New-Item -ItemType Directory -Force -Path $bundlePath, $bundleConfig, $bundleUserHome, $jekyllCache, $siteDir | Out-Null
+
+Push-Location $docHome
+try {
+ Write-Step "Installing Ruby dependencies"
+ Invoke-Native -FilePath "bundle" -Arguments @("install")
+
+ if ($NoServe) {
+ Write-Step "Workspace prepared. Run this script again without -NoServe to start Jekyll."
+ } else {
+ Write-Step "Starting Jekyll server on port $Port"
+ Invoke-Native -FilePath "bundle" -Arguments @("exec", "jekyll", "serve", "-P", "$Port", "--trace", "--host=$BindHost", "--livereload", "--destination", "$siteDir")
+ }
+} finally {
+ Pop-Location
+}
diff --git a/scripts/dev.sh b/scripts/dev.sh
new file mode 100755
index 0000000..6ba3f39
--- /dev/null
+++ b/scripts/dev.sh
@@ -0,0 +1,180 @@
+#!/usr/bin/env bash
+
+set -euo pipefail
+
+template_repo_url="https://github.com/dynamsoft-docs/Docs-Template-Repo.git"
+template_branch="preview"
+port="5555"
+bind_host="localhost"
+no_template_update="false"
+no_serve="false"
+
+write_step() {
+ echo "==> $1"
+}
+
+require_cmd() {
+ if ! command -v "$1" >/dev/null 2>&1; then
+ echo "Required command '$1' was not found in PATH." >&2
+ exit 1
+ fi
+}
+
+show_help() {
+ cat <<'EOF'
+Usage: ./scripts/dev.sh [options]
+
+Options:
+ --template-repo-url URL Template repository URL
+ --template-branch NAME Template branch (default: preview)
+ --port N Jekyll port (default: 5555)
+ --bind-host HOST Jekyll bind host (default: localhost)
+ --no-template-update Skip template fetch/pull
+ --no-serve Prepare workspace only (do not start Jekyll)
+ -h, --help Show this help message
+EOF
+}
+
+require_option_value() {
+ if [[ $# -lt 2 || -z "${2:-}" || "${2:-}" == --* ]]; then
+ echo "Missing value for option: $1" >&2
+ show_help
+ exit 1
+ fi
+}
+
+while [[ $# -gt 0 ]]; do
+ case "$1" in
+ --template-repo-url)
+ require_option_value "$@"
+ template_repo_url="$2"
+ shift 2
+ ;;
+ --template-branch)
+ require_option_value "$@"
+ template_branch="$2"
+ shift 2
+ ;;
+ --port)
+ require_option_value "$@"
+ port="$2"
+ shift 2
+ ;;
+ --bind-host)
+ require_option_value "$@"
+ bind_host="$2"
+ shift 2
+ ;;
+ --no-template-update)
+ no_template_update="true"
+ shift
+ ;;
+ --no-serve)
+ no_serve="true"
+ shift
+ ;;
+ -h|--help)
+ show_help
+ exit 0
+ ;;
+ *)
+ echo "Unknown option: $1" >&2
+ show_help
+ exit 1
+ ;;
+ esac
+done
+
+require_cmd git
+require_cmd rsync
+require_cmd bundle
+require_cmd find
+require_cmd sed
+
+script_dir="$(cd -- "$(dirname -- "${BASH_SOURCE[0]}")" && pwd)"
+repo_root="$(cd -- "$script_dir/.." && pwd)"
+dev_root="$repo_root/.dev"
+template_root="$dev_root/Docs-Template-Repo"
+doc_home="$dev_root/DocHome"
+bundle_path="$dev_root/vendor/bundle"
+bundle_config="$dev_root/.bundle"
+bundle_user_home="$dev_root/.bundle-user"
+jekyll_cache="$dev_root/.jekyll-cache"
+site_dir="$dev_root/_site"
+
+write_step "Preparing local workspace in $dev_root"
+mkdir -p "$dev_root"
+
+if [[ ! -d "$template_root/.git" ]]; then
+ write_step "Cloning template repo ($template_branch)"
+ git clone --depth 1 --branch "$template_branch" "$template_repo_url" "$template_root"
+elif [[ "$no_template_update" != "true" ]]; then
+ write_step "Syncing template repo ($template_branch)"
+ git -C "$template_root" fetch origin "$template_branch" --depth 1
+ git -C "$template_root" reset --hard
+ git -C "$template_root" clean -fd
+ git -C "$template_root" checkout -B "$template_branch" "origin/$template_branch"
+else
+ write_step "Skipping template update"
+fi
+
+write_step "Rebuilding merged site workspace"
+rm -rf "$doc_home"
+mkdir -p "$doc_home"
+rsync -a --delete \
+ --exclude '.git' \
+ --exclude '.dev' \
+ --exclude '.claude' \
+ --exclude '/barcode-reader/mobile/archive/' \
+ --exclude '/barcode-reader/server/archive/' \
+ --exclude '/barcode-reader/web/archive/' \
+ --exclude '.vs' \
+ --exclude 'node_modules' \
+ --exclude '_site' \
+ --exclude '.bundle' \
+ --exclude '.jekyll-cache' \
+ --exclude '.sass-cache' \
+ --exclude 'vendor' \
+ "$repo_root"/ "$doc_home"/
+rsync -a \
+ --exclude '.git' \
+ --exclude '.github' \
+ --exclude '_site' \
+ --exclude 'node_modules' \
+ "$template_root"/ "$doc_home"/
+
+write_step "Applying local assetsPath replacements"
+search="assetsPath = '/webres/wwwroot'"
+replace="assetsPath = 'https://www.dynamsoft.com/webres/wwwroot'"
+for dir_name in "_includes" "_layouts"; do
+ dir_path="$doc_home/$dir_name"
+ if [[ ! -d "$dir_path" ]]; then
+ continue
+ fi
+
+ while IFS= read -r -d '' file_path; do
+ sed -i.bak "s|$search|$replace|g" "$file_path"
+ rm -f -- "$file_path.bak"
+ done < <(find "$dir_path" -type f -print0)
+done
+
+write_step "Configuring Bundler and Jekyll local paths"
+export BUNDLE_PATH="$bundle_path"
+export BUNDLE_APP_CONFIG="$bundle_config"
+export BUNDLE_USER_HOME="$bundle_user_home"
+export BUNDLE_USER_CACHE="$bundle_user_home/cache"
+export JEKYLL_CACHE_DIR="$jekyll_cache"
+export JEKYLL_ENV="development"
+mkdir -p "$bundle_path" "$bundle_config" "$bundle_user_home" "$jekyll_cache" "$site_dir"
+
+pushd "$doc_home" >/dev/null
+write_step "Installing Ruby dependencies"
+bundle install
+
+if [[ "$no_serve" == "true" ]]; then
+ write_step "Workspace prepared. Run this script again without --no-serve to start Jekyll."
+else
+ write_step "Starting Jekyll server on port $port"
+ bundle exec jekyll serve -P "$port" --trace --host="$bind_host" --livereload --destination "$site_dir"
+fi
+popd >/dev/null
From f5e412a3d3b79241652d6456d0fe75c23ad642a6 Mon Sep 17 00:00:00 2001
From: Doby2333
Date: Wed, 30 Sep 2026 15:38:43 +0800
Subject: [PATCH 6/7] Restore MRZ camera preview metadata in shared FAQ
---
AGENTS.md | 2 +
README.md | 2 +-
.../camera-preview-renders-incorrectly-ios.md | 100 +++++++++++++++++
.../camera-preview-renders-incorrectly-ios.md | 101 +-----------------
.../camera-preview-renders-incorrectly-ios.md | 12 ++-
5 files changed, 115 insertions(+), 102 deletions(-)
create mode 100644 _includes/shared/camera-preview-renders-incorrectly-ios.md
diff --git a/AGENTS.md b/AGENTS.md
index 591c020..c7a673c 100644
--- a/AGENTS.md
+++ b/AGENTS.md
@@ -37,6 +37,8 @@ Rules:
- `mrz-scanner/general/` — MRZ Scanner FAQs
- `license/` — licensing FAQs shared across products
+For an answer published in more than one product section, keep each page’s own frontmatter and question H1, and put the common answer body in `_includes/shared/`. The iOS 27 camera-preview FAQ follows this pattern for Barcode Reader and MRZ Scanner; edit the shared include for answer changes.
+
## Archived content (`*/archive/*`)
Directories named `archive` under `barcode-reader/{mobile,server,web}/` hold historical, version-pinned content (e.g. `-v9.6.40`, `-v10.4.2000` snapshots). They are:
diff --git a/README.md b/README.md
index d37240b..7da79d1 100644
--- a/README.md
+++ b/README.md
@@ -22,7 +22,7 @@ Or on Windows:
./scripts/dev.ps1
```
-The scripts clone the shared template's preview branch into `.dev/`, merge it with this FAQ source, install gems, and serve Jekyll at `http://localhost:5555/faq/`. The generated `.dev/` workspace is ignored by Git and omits archived FAQ content and local worktrees. Use `--no-serve` / `-NoServe` to prepare without serving, then rerun without that flag to serve; `--no-template-update` / `-NoTemplateUpdate` reuses the cloned template. Changes to FAQ files require rerunning the script to refresh the merged workspace.
+The scripts clone the shared template's preview branch into `.dev/`, merge it with this FAQ source, install gems, and serve Jekyll at `http://localhost:5555/faq/`. The generated `.dev/` workspace is ignored by Git and omits archived FAQ content and local worktrees. Use `--no-serve` / `-NoServe` to prepare without serving, then rerun without that flag to serve; `--no-template-update` / `-NoTemplateUpdate` reuses the cloned template. Changes to FAQ files require rerunning the script to refresh the merged workspace. The Barcode Reader and MRZ Scanner iOS 27 camera-preview pages share their answer body in `_includes/shared/` while keeping separate page metadata.
## Checking links
diff --git a/_includes/shared/camera-preview-renders-incorrectly-ios.md b/_includes/shared/camera-preview-renders-incorrectly-ios.md
new file mode 100644
index 0000000..cd78030
--- /dev/null
+++ b/_includes/shared/camera-preview-renders-incorrectly-ios.md
@@ -0,0 +1,100 @@
+## Applicable Products
+
+This article applies to:
+
+- Dynamsoft Barcode Reader (DBR) JavaScript SDK (`dynamsoft-barcode-reader-bundle`) 11.6.3000 and earlier
+- Dynamsoft Capture Vision (DCV) JavaScript SDK (`dynamsoft-capture-vision-bundle`) 3.6.3000 and earlier
+
+## Summary
+
+On iOS 27, switching cameras or changing resolution can make the live camera preview render incorrectly. The exact behavior depends on the SDK version:
+
+| Version | Behavior |
+|---|---|
+| DBR 11.4 – 11.6.3000 (DCV 3.4 – 3.6.3000) | The preview renders distorted — squeezed or stretched instead of filling its container. Intermittent: the same switch can render correctly on one attempt and distorted on the next. |
+| DBR 11.2 and earlier (DCV 3.2 and earlier) | The preview isn't distorted, but it no longer fits its container — shown at the wrong zoom or size and not extending to the borders. |
+
+It's reproducible on Safari, Chrome, Edge, and Firefox — all iOS browsers share WebKit's camera implementation, so we suspect the issue originates there rather than in any Dynamsoft SDK. It does not occur on iOS 26.
+
+> [!NOTE]
+> Reported to Apple, but not confirmed as an Apple bug and still open as of iOS 27 RC. Details here may change if Apple ships a fix.
+
+
+
+
+ Expected
+
+
+
+ Distorted after switching cameras
+
+
+
+## Resolution
+
+### Recommended: upgrade
+
+Upgrade to `dynamsoft-barcode-reader-bundle` **11.6.3200+** or `dynamsoft-capture-vision-bundle` **3.6.3200+**, which include a built-in workaround.
+
+### If you can't upgrade yet
+
+Both workarounds below are temporary and version-specific — neither replaces upgrading.
+
+**DBR 11.4 – 11.6.3000 (DCV 3.4 – 3.6.3000)**
+
+The distortion requires `object-fit: fill` on the video element plus an ancestor using `display: flex` with `flex: 0 0 auto`, so overriding `object-fit` with `cover` on the `` element that [Dynamsoft Camera Enhancer](https://www.dynamsoft.com/camera-enhancer/docs/web/) renders avoids it:
+
+```css
+.dm-camera-core-container video {
+ object-fit: cover !important;
+}
+```
+
+`!important` is needed because the SDK sets `object-fit` inline. The JavaScript equivalent, via [`cameraView.getVideoElement()`](https://www.dynamsoft.com/camera-enhancer/docs/web/programming/javascript/api-reference/cameraview.html?product=dbr&lang=javascript#getvideoelement):
+
+```javascript
+let videoElement = cameraView.getVideoElement();
+videoElement?.style.setProperty('object-fit', 'cover', 'important');
+```
+
+> [!WARNING]
+> `cover` crops rather than stretches to preserve the aspect ratio — confirm that trade-off works for your UI.
+
+**DBR 11.2 and earlier (DCV 3.2 and earlier)**
+
+Reset the video element's dimensions whenever the camera or resolution changes, registering the handlers before `cameraEnhancer.open()`:
+
+```javascript
+const resetVideoWH = () => {
+ const videoEl = cameraEnhancer.getVideoEl();
+ videoEl.style.width = "";
+ videoEl.style.height = "";
+
+ requestAnimationFrame(() => {
+ requestAnimationFrame(() => {
+ videoEl.style.width = "100%";
+ videoEl.style.height = "100%";
+ });
+ });
+};
+cameraEnhancer.on("cameraChange", resetVideoWH);
+cameraEnhancer.on("resolutionChange", resetVideoWH);
+
+cameraView.createDrawingLayer(2); // layer ID depends on the product — see below
+
+// Normal startup routine, shown here only to indicate placement
+await cameraEnhancer.open();
+await cvRouter.startCapturing();
+```
+
+The `createDrawingLayer` call is part of the workaround. Pass the layer ID for your product:
+
+| Product | Layer ID |
+|---|---|
+| Dynamsoft Barcode Reader (DBR) | 2 |
+| Mobile Document Scanner (MDS — DDN layer) | 1 |
+| MRZ Scanner (DLR layer) | 3 |
+
+## Need more help?
+
+[Contact the Dynamsoft Support team](https://www.dynamsoft.com/contact/).
diff --git a/barcode-reader/web/camera/camera-preview-renders-incorrectly-ios.md b/barcode-reader/web/camera/camera-preview-renders-incorrectly-ios.md
index 4779519..07a3773 100644
--- a/barcode-reader/web/camera/camera-preview-renders-incorrectly-ios.md
+++ b/barcode-reader/web/camera/camera-preview-renders-incorrectly-ios.md
@@ -8,103 +8,4 @@ needAutoGenerateSidebar: false
# Why does the camera preview render incorrectly on iOS 27?
-## Applicable Products
-
-This article applies to:
-
-- Dynamsoft Barcode Reader (DBR) JavaScript SDK (`dynamsoft-barcode-reader-bundle`) 11.6.3000 and earlier
-- Dynamsoft Capture Vision (DCV) JavaScript SDK (`dynamsoft-capture-vision-bundle`) 3.6.3000 and earlier
-
-## Summary
-
-On iOS 27, switching cameras or changing resolution can make the live camera preview render incorrectly. The exact behavior depends on the SDK version:
-
-| Version | Behavior |
-|---|---|
-| DBR 11.4 – 11.6.3000 (DCV 3.4 – 3.6.3000) | The preview renders distorted — squeezed or stretched instead of filling its container. Intermittent: the same switch can render correctly on one attempt and distorted on the next. |
-| DBR 11.2 and earlier (DCV 3.2 and earlier) | The preview isn't distorted, but it no longer fits its container — shown at the wrong zoom or size and not extending to the borders. |
-
-It's reproducible on Safari, Chrome, Edge, and Firefox — all iOS browsers share WebKit's camera implementation, so we suspect the issue originates there rather than in any Dynamsoft SDK. It does not occur on iOS 26.
-
-> [!NOTE]
-> Reported to Apple, but not confirmed as an Apple bug and still open as of iOS 27 RC. Details here may change if Apple ships a fix.
-
-
-
-
- Expected
-
-
-
- Distorted after switching cameras
-
-
-
-## Resolution
-
-### Recommended: upgrade
-
-Upgrade to `dynamsoft-barcode-reader-bundle` **11.6.3200+** or `dynamsoft-capture-vision-bundle` **3.6.3200+**, which include a built-in workaround.
-
-### If you can't upgrade yet
-
-Both workarounds below are temporary and version-specific — neither replaces upgrading.
-
-**DBR 11.4 – 11.6.3000 (DCV 3.4 – 3.6.3000)**
-
-The distortion requires `object-fit: fill` on the video element plus an ancestor using `display: flex` with `flex: 0 0 auto`, so overriding `object-fit` with `cover` on the `` element that [Dynamsoft Camera Enhancer](https://www.dynamsoft.com/camera-enhancer/docs/web/) renders avoids it:
-
-```css
-.dm-camera-core-container video {
- object-fit: cover !important;
-}
-```
-
-`!important` is needed because the SDK sets `object-fit` inline. The JavaScript equivalent, via [`cameraView.getVideoElement()`](https://www.dynamsoft.com/camera-enhancer/docs/web/programming/javascript/api-reference/cameraview.html?product=dbr&lang=javascript#getvideoelement):
-
-```javascript
-let videoElement = cameraView.getVideoElement();
-videoElement?.style.setProperty('object-fit', 'cover', 'important');
-```
-
-> [!WARNING]
-> `cover` crops rather than stretches to preserve the aspect ratio — confirm that trade-off works for your UI.
-
-**DBR 11.2 and earlier (DCV 3.2 and earlier)**
-
-Reset the video element's dimensions whenever the camera or resolution changes, registering the handlers before `cameraEnhancer.open()`:
-
-```javascript
-const resetVideoWH = () => {
- const videoEl = cameraEnhancer.getVideoEl();
- videoEl.style.width = "";
- videoEl.style.height = "";
-
- requestAnimationFrame(() => {
- requestAnimationFrame(() => {
- videoEl.style.width = "100%";
- videoEl.style.height = "100%";
- });
- });
-};
-cameraEnhancer.on("cameraChange", resetVideoWH);
-cameraEnhancer.on("resolutionChange", resetVideoWH);
-
-cameraView.createDrawingLayer(2); // layer ID depends on the product — see below
-
-// Normal startup routine, shown here only to indicate placement
-await cameraEnhancer.open();
-await cvRouter.startCapturing();
-```
-
-The `createDrawingLayer` call is part of the workaround. Pass the layer ID for your product:
-
-| Product | Layer ID |
-|---|---|
-| Dynamsoft Barcode Reader (DBR) | 2 |
-| Mobile Document Scanner (MDS — DDN layer) | 1 |
-| MRZ Scanner (DLR layer) | 3 |
-
-## Need more help?
-
-[Contact the Dynamsoft Support team](https://www.dynamsoft.com/contact/).
+{% include shared/camera-preview-renders-incorrectly-ios.md %}
diff --git a/mrz-scanner/general/camera-preview-renders-incorrectly-ios.md b/mrz-scanner/general/camera-preview-renders-incorrectly-ios.md
index 4904f82..9f52bed 100644
--- a/mrz-scanner/general/camera-preview-renders-incorrectly-ios.md
+++ b/mrz-scanner/general/camera-preview-renders-incorrectly-ios.md
@@ -1 +1,11 @@
-../../barcode-reader/web/camera/camera-preview-renders-incorrectly-ios.md
\ No newline at end of file
+---
+layout: default-layout
+title: Why Does the MRZ Scanner's Camera Preview Render Incorrectly on iOS 27?
+keywords: iOS 27, camera, preview, distorted, video, switching camera, changing resolution, Safari, Chrome, Edge, Firefox, WebKit, Dynamsoft Camera Enhancer, Dynamsoft Barcode Reader, Dynamsoft MRZ Scanner
+description: On iOS 27, switching cameras or resolution can distort or misfit the MRZ Scanner's live camera preview — a WebKit-wide issue, not specific to Dynamsoft. See the fix in 11.6.3200+/3.6.3200+ and workarounds for older versions.
+needAutoGenerateSidebar: false
+---
+
+# Why does the camera preview render incorrectly on iOS 27?
+
+{% include shared/camera-preview-renders-incorrectly-ios.md %}
From 913add61d31aeaf1630872270ae75bb5d524efc9 Mon Sep 17 00:00:00 2001
From: Doby2333
Date: Wed, 30 Sep 2026 15:41:46 +0800
Subject: [PATCH 7/7] Revert "Restore MRZ camera preview metadata in shared
FAQ"
This reverts commit f5e412a3d3b79241652d6456d0fe75c23ad642a6.
---
AGENTS.md | 2 -
README.md | 2 +-
.../camera-preview-renders-incorrectly-ios.md | 100 -----------------
.../camera-preview-renders-incorrectly-ios.md | 101 +++++++++++++++++-
.../camera-preview-renders-incorrectly-ios.md | 12 +--
5 files changed, 102 insertions(+), 115 deletions(-)
delete mode 100644 _includes/shared/camera-preview-renders-incorrectly-ios.md
diff --git a/AGENTS.md b/AGENTS.md
index c7a673c..591c020 100644
--- a/AGENTS.md
+++ b/AGENTS.md
@@ -37,8 +37,6 @@ Rules:
- `mrz-scanner/general/` — MRZ Scanner FAQs
- `license/` — licensing FAQs shared across products
-For an answer published in more than one product section, keep each page’s own frontmatter and question H1, and put the common answer body in `_includes/shared/`. The iOS 27 camera-preview FAQ follows this pattern for Barcode Reader and MRZ Scanner; edit the shared include for answer changes.
-
## Archived content (`*/archive/*`)
Directories named `archive` under `barcode-reader/{mobile,server,web}/` hold historical, version-pinned content (e.g. `-v9.6.40`, `-v10.4.2000` snapshots). They are:
diff --git a/README.md b/README.md
index 7da79d1..d37240b 100644
--- a/README.md
+++ b/README.md
@@ -22,7 +22,7 @@ Or on Windows:
./scripts/dev.ps1
```
-The scripts clone the shared template's preview branch into `.dev/`, merge it with this FAQ source, install gems, and serve Jekyll at `http://localhost:5555/faq/`. The generated `.dev/` workspace is ignored by Git and omits archived FAQ content and local worktrees. Use `--no-serve` / `-NoServe` to prepare without serving, then rerun without that flag to serve; `--no-template-update` / `-NoTemplateUpdate` reuses the cloned template. Changes to FAQ files require rerunning the script to refresh the merged workspace. The Barcode Reader and MRZ Scanner iOS 27 camera-preview pages share their answer body in `_includes/shared/` while keeping separate page metadata.
+The scripts clone the shared template's preview branch into `.dev/`, merge it with this FAQ source, install gems, and serve Jekyll at `http://localhost:5555/faq/`. The generated `.dev/` workspace is ignored by Git and omits archived FAQ content and local worktrees. Use `--no-serve` / `-NoServe` to prepare without serving, then rerun without that flag to serve; `--no-template-update` / `-NoTemplateUpdate` reuses the cloned template. Changes to FAQ files require rerunning the script to refresh the merged workspace.
## Checking links
diff --git a/_includes/shared/camera-preview-renders-incorrectly-ios.md b/_includes/shared/camera-preview-renders-incorrectly-ios.md
deleted file mode 100644
index cd78030..0000000
--- a/_includes/shared/camera-preview-renders-incorrectly-ios.md
+++ /dev/null
@@ -1,100 +0,0 @@
-## Applicable Products
-
-This article applies to:
-
-- Dynamsoft Barcode Reader (DBR) JavaScript SDK (`dynamsoft-barcode-reader-bundle`) 11.6.3000 and earlier
-- Dynamsoft Capture Vision (DCV) JavaScript SDK (`dynamsoft-capture-vision-bundle`) 3.6.3000 and earlier
-
-## Summary
-
-On iOS 27, switching cameras or changing resolution can make the live camera preview render incorrectly. The exact behavior depends on the SDK version:
-
-| Version | Behavior |
-|---|---|
-| DBR 11.4 – 11.6.3000 (DCV 3.4 – 3.6.3000) | The preview renders distorted — squeezed or stretched instead of filling its container. Intermittent: the same switch can render correctly on one attempt and distorted on the next. |
-| DBR 11.2 and earlier (DCV 3.2 and earlier) | The preview isn't distorted, but it no longer fits its container — shown at the wrong zoom or size and not extending to the borders. |
-
-It's reproducible on Safari, Chrome, Edge, and Firefox — all iOS browsers share WebKit's camera implementation, so we suspect the issue originates there rather than in any Dynamsoft SDK. It does not occur on iOS 26.
-
-> [!NOTE]
-> Reported to Apple, but not confirmed as an Apple bug and still open as of iOS 27 RC. Details here may change if Apple ships a fix.
-
-
-
-
- Expected
-
-
-
- Distorted after switching cameras
-
-
-
-## Resolution
-
-### Recommended: upgrade
-
-Upgrade to `dynamsoft-barcode-reader-bundle` **11.6.3200+** or `dynamsoft-capture-vision-bundle` **3.6.3200+**, which include a built-in workaround.
-
-### If you can't upgrade yet
-
-Both workarounds below are temporary and version-specific — neither replaces upgrading.
-
-**DBR 11.4 – 11.6.3000 (DCV 3.4 – 3.6.3000)**
-
-The distortion requires `object-fit: fill` on the video element plus an ancestor using `display: flex` with `flex: 0 0 auto`, so overriding `object-fit` with `cover` on the `` element that [Dynamsoft Camera Enhancer](https://www.dynamsoft.com/camera-enhancer/docs/web/) renders avoids it:
-
-```css
-.dm-camera-core-container video {
- object-fit: cover !important;
-}
-```
-
-`!important` is needed because the SDK sets `object-fit` inline. The JavaScript equivalent, via [`cameraView.getVideoElement()`](https://www.dynamsoft.com/camera-enhancer/docs/web/programming/javascript/api-reference/cameraview.html?product=dbr&lang=javascript#getvideoelement):
-
-```javascript
-let videoElement = cameraView.getVideoElement();
-videoElement?.style.setProperty('object-fit', 'cover', 'important');
-```
-
-> [!WARNING]
-> `cover` crops rather than stretches to preserve the aspect ratio — confirm that trade-off works for your UI.
-
-**DBR 11.2 and earlier (DCV 3.2 and earlier)**
-
-Reset the video element's dimensions whenever the camera or resolution changes, registering the handlers before `cameraEnhancer.open()`:
-
-```javascript
-const resetVideoWH = () => {
- const videoEl = cameraEnhancer.getVideoEl();
- videoEl.style.width = "";
- videoEl.style.height = "";
-
- requestAnimationFrame(() => {
- requestAnimationFrame(() => {
- videoEl.style.width = "100%";
- videoEl.style.height = "100%";
- });
- });
-};
-cameraEnhancer.on("cameraChange", resetVideoWH);
-cameraEnhancer.on("resolutionChange", resetVideoWH);
-
-cameraView.createDrawingLayer(2); // layer ID depends on the product — see below
-
-// Normal startup routine, shown here only to indicate placement
-await cameraEnhancer.open();
-await cvRouter.startCapturing();
-```
-
-The `createDrawingLayer` call is part of the workaround. Pass the layer ID for your product:
-
-| Product | Layer ID |
-|---|---|
-| Dynamsoft Barcode Reader (DBR) | 2 |
-| Mobile Document Scanner (MDS — DDN layer) | 1 |
-| MRZ Scanner (DLR layer) | 3 |
-
-## Need more help?
-
-[Contact the Dynamsoft Support team](https://www.dynamsoft.com/contact/).
diff --git a/barcode-reader/web/camera/camera-preview-renders-incorrectly-ios.md b/barcode-reader/web/camera/camera-preview-renders-incorrectly-ios.md
index 07a3773..4779519 100644
--- a/barcode-reader/web/camera/camera-preview-renders-incorrectly-ios.md
+++ b/barcode-reader/web/camera/camera-preview-renders-incorrectly-ios.md
@@ -8,4 +8,103 @@ needAutoGenerateSidebar: false
# Why does the camera preview render incorrectly on iOS 27?
-{% include shared/camera-preview-renders-incorrectly-ios.md %}
+## Applicable Products
+
+This article applies to:
+
+- Dynamsoft Barcode Reader (DBR) JavaScript SDK (`dynamsoft-barcode-reader-bundle`) 11.6.3000 and earlier
+- Dynamsoft Capture Vision (DCV) JavaScript SDK (`dynamsoft-capture-vision-bundle`) 3.6.3000 and earlier
+
+## Summary
+
+On iOS 27, switching cameras or changing resolution can make the live camera preview render incorrectly. The exact behavior depends on the SDK version:
+
+| Version | Behavior |
+|---|---|
+| DBR 11.4 – 11.6.3000 (DCV 3.4 – 3.6.3000) | The preview renders distorted — squeezed or stretched instead of filling its container. Intermittent: the same switch can render correctly on one attempt and distorted on the next. |
+| DBR 11.2 and earlier (DCV 3.2 and earlier) | The preview isn't distorted, but it no longer fits its container — shown at the wrong zoom or size and not extending to the borders. |
+
+It's reproducible on Safari, Chrome, Edge, and Firefox — all iOS browsers share WebKit's camera implementation, so we suspect the issue originates there rather than in any Dynamsoft SDK. It does not occur on iOS 26.
+
+> [!NOTE]
+> Reported to Apple, but not confirmed as an Apple bug and still open as of iOS 27 RC. Details here may change if Apple ships a fix.
+
+
+
+
+ Expected
+
+
+
+ Distorted after switching cameras
+
+
+
+## Resolution
+
+### Recommended: upgrade
+
+Upgrade to `dynamsoft-barcode-reader-bundle` **11.6.3200+** or `dynamsoft-capture-vision-bundle` **3.6.3200+**, which include a built-in workaround.
+
+### If you can't upgrade yet
+
+Both workarounds below are temporary and version-specific — neither replaces upgrading.
+
+**DBR 11.4 – 11.6.3000 (DCV 3.4 – 3.6.3000)**
+
+The distortion requires `object-fit: fill` on the video element plus an ancestor using `display: flex` with `flex: 0 0 auto`, so overriding `object-fit` with `cover` on the `` element that [Dynamsoft Camera Enhancer](https://www.dynamsoft.com/camera-enhancer/docs/web/) renders avoids it:
+
+```css
+.dm-camera-core-container video {
+ object-fit: cover !important;
+}
+```
+
+`!important` is needed because the SDK sets `object-fit` inline. The JavaScript equivalent, via [`cameraView.getVideoElement()`](https://www.dynamsoft.com/camera-enhancer/docs/web/programming/javascript/api-reference/cameraview.html?product=dbr&lang=javascript#getvideoelement):
+
+```javascript
+let videoElement = cameraView.getVideoElement();
+videoElement?.style.setProperty('object-fit', 'cover', 'important');
+```
+
+> [!WARNING]
+> `cover` crops rather than stretches to preserve the aspect ratio — confirm that trade-off works for your UI.
+
+**DBR 11.2 and earlier (DCV 3.2 and earlier)**
+
+Reset the video element's dimensions whenever the camera or resolution changes, registering the handlers before `cameraEnhancer.open()`:
+
+```javascript
+const resetVideoWH = () => {
+ const videoEl = cameraEnhancer.getVideoEl();
+ videoEl.style.width = "";
+ videoEl.style.height = "";
+
+ requestAnimationFrame(() => {
+ requestAnimationFrame(() => {
+ videoEl.style.width = "100%";
+ videoEl.style.height = "100%";
+ });
+ });
+};
+cameraEnhancer.on("cameraChange", resetVideoWH);
+cameraEnhancer.on("resolutionChange", resetVideoWH);
+
+cameraView.createDrawingLayer(2); // layer ID depends on the product — see below
+
+// Normal startup routine, shown here only to indicate placement
+await cameraEnhancer.open();
+await cvRouter.startCapturing();
+```
+
+The `createDrawingLayer` call is part of the workaround. Pass the layer ID for your product:
+
+| Product | Layer ID |
+|---|---|
+| Dynamsoft Barcode Reader (DBR) | 2 |
+| Mobile Document Scanner (MDS — DDN layer) | 1 |
+| MRZ Scanner (DLR layer) | 3 |
+
+## Need more help?
+
+[Contact the Dynamsoft Support team](https://www.dynamsoft.com/contact/).
diff --git a/mrz-scanner/general/camera-preview-renders-incorrectly-ios.md b/mrz-scanner/general/camera-preview-renders-incorrectly-ios.md
index 9f52bed..4904f82 100644
--- a/mrz-scanner/general/camera-preview-renders-incorrectly-ios.md
+++ b/mrz-scanner/general/camera-preview-renders-incorrectly-ios.md
@@ -1,11 +1 @@
----
-layout: default-layout
-title: Why Does the MRZ Scanner's Camera Preview Render Incorrectly on iOS 27?
-keywords: iOS 27, camera, preview, distorted, video, switching camera, changing resolution, Safari, Chrome, Edge, Firefox, WebKit, Dynamsoft Camera Enhancer, Dynamsoft Barcode Reader, Dynamsoft MRZ Scanner
-description: On iOS 27, switching cameras or resolution can distort or misfit the MRZ Scanner's live camera preview — a WebKit-wide issue, not specific to Dynamsoft. See the fix in 11.6.3200+/3.6.3200+ and workarounds for older versions.
-needAutoGenerateSidebar: false
----
-
-# Why does the camera preview render incorrectly on iOS 27?
-
-{% include shared/camera-preview-renders-incorrectly-ios.md %}
+../../barcode-reader/web/camera/camera-preview-renders-incorrectly-ios.md
\ No newline at end of file