Conversation
…view
Layout and master content placeholders carry editor prompt boilerplate
("Click to add title", "单击此处添加正文") in their <p:txBody>. Real
Office never renders that text; it shows up only in edit mode. Open XML
SDK exposes the layout's <p:txBody> directly, and the previous renderer
forwarded it onto the slide whenever the placeholder slipped past the
type denylist.
Two issues with the old denylist approach:
1. ECMA-376 §19.3.1.36 says a <p:ph> with no `type` attribute defaults
to `obj`. Open XML SDK reports `Type.HasValue == false` for the
absent attribute, so the entire denylist branch was skipped — and a
layout body placeholder authored without an explicit type leaked its
prompt text onto the slide. This is the shape behind issue #79.
2. Picture/Chart/Table/Media placeholders weren't on the denylist
either, so their prompt text ("Click icon to add picture") leaked
the same way.
Fix: model the rule the way Apache POI does
(SlideShowExtractor.java:179-183, XSLFShape.java:369-370). Layout and
master placeholders never contribute text to the rendered slide — only
the four metadata slots (date/footer/header/slide number) carry
genuine layout-supplied content. Everything else is suppressed at the
text level but still renders chrome (fill / outline / geometry), so a
layout's themed placeholder background survives.
The ECMA default is now applied explicitly (`Type.HasValue == false`
=> Object) instead of relying on a side effect of the SDK's missing
HasValue.
Validated with a local functional test that injects a layout
placeholder with no `type` attribute and asserts the prompt text does
not appear in ViewAsHtml() while the layout-supplied footer text and
themed fill do.
Fixes #79
Supersedes #80
Co-Authored-By: pojian <lijianlin6868@gmail.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
<p:ph>with notypeattribute defaults toobj. Open XML SDK reportsType.HasValue == falsehere, which is the root cause behind PPTX HTML preview renders inherited placeholder prompt text #79 — the previous denylist never matched the very common "type-less body placeholder" shape and let its prompt text through.Fixes #79.
Supersedes #80 — same intent, narrower fix that aligns with how Apache POI handles inheritance (
SlideShowExtractor.java:179-183skips boiler-plate placeholder text on master sheets;XSLFShape.java:369-370handles the missing-type default).Why this differs from #80
#80 takes an allowlist approach (only render date/footer/header/slide-number), which:
<p:sp>for content placeholders — losing themed background fills and outlines that legitimate layouts carry.IsVisibleInheritedPlaceholderreturningfalsewhenType.HasValue == false. A future reader has to re-derive the ECMA default rule.skipIndicestype:check after the early continue as effectively dead code without explaining why.This PR splits text from chrome: a layout's placeholder still contributes its visual frame, only its
<p:txBody>is suppressed. The ECMA default is written as?? PlaceholderValues.Objectwith a comment pointing at the spec section.Test plan
Validated locally with a regression test that:
<p:sp>into every<p:spTree>in the slide layouts. Three variants:<p:ph idx="9999"/>— notypeattribute (the PPTX HTML preview renders inherited placeholder prompt text #79 trigger).<p:ph type="body" idx="1"/>(was previously caught by the denylist; verifies we didn't lose that case).<p:ph type="pic" idx="2"/>(previously leaked because Picture wasn't in the denylist).PowerPointHandler.ViewAsHtml()and asserts the prompt text is not in the rendered HTML.Footer-type placeholder's text does appear; aSlideNumber-type placeholder's text does appear; a Body-type placeholder with a themedsolidFillkeeps its fill in the rendered HTML even though its text is suppressed.All 6 cases pass. The 9 existing
HtmlPreviewBugTests_Round1tests also pass.dotnet build src/officecli/officecli.csprojcleandotnet test --filter HtmlPreviewBugTests_Round1— 9/9 pass