mirror of
https://github.com/xiaoqidun/ofdgo.git
synced 2026-10-29 08:46:55 +08:00
1 parent
6d782de471
commit
f5463b9479
17 files changed
+68
-46
No files matched your search
@@ -227,19 +227,19 @@
|
|||||||
<details id="objectGradientFields" hidden>
|
<details id="objectGradientFields" hidden>
|
||||||
<summary>渐变</summary>
|
<summary>渐变</summary>
|
||||||
<div class="form-pair">
|
<div class="form-pair">
|
||||||
<div class="form-row"><label for="gradientTarget">作用</label><select id="gradientTarget"><option value="fill">填充</option><option value="stroke">描边</option></select></div>
|
<div class="form-row"><label for="gradientTarget">应用</label><select id="gradientTarget"><option value="fill">填充</option><option value="stroke">描边</option></select></div>
|
||||||
<div class="form-row"><label for="gradientKind">类型</label><select id="gradientKind"><option value="keep">保持</option><option value="linear">线性</option><option value="radial">径向</option></select></div>
|
<div class="form-row"><label for="gradientKind">类型</label><select id="gradientKind"><option value="keep">保持</option><option value="linear">线性</option><option value="radial">径向</option></select></div>
|
||||||
</div>
|
</div>
|
||||||
<div id="gradientControls" hidden>
|
<div id="gradientControls" hidden>
|
||||||
<div class="form-row"><label for="gradientAngle">角度</label><div class="form-unit"><input id="gradientAngle" type="number" step="any" value="0"><span>°</span></div></div>
|
<div class="form-row"><label for="gradientAngle">角度</label><div class="form-unit"><input id="gradientAngle" type="number" step="any" value="0"><span>°</span></div></div>
|
||||||
<div class="gradient-stop-row gradient-stop-head"><span>颜色</span><span>位置%</span><span>透明%</span><span></span></div>
|
<div class="gradient-stop-row gradient-stop-head"><span>颜色</span><span>位置%</span><span>透明%</span><span></span></div>
|
||||||
<div id="gradientStops"></div>
|
<div id="gradientStops"></div>
|
||||||
<button id="gradientAdd" class="small-button" type="button" title="添加色标" aria-label="添加色标">+</button>
|
<button id="gradientAdd" class="icon-button" type="button" title="添加色标" aria-label="添加色标">+</button>
|
||||||
</div>
|
</div>
|
||||||
</details>
|
</details>
|
||||||
<details id="objectPatternFields" hidden>
|
<details id="objectPatternFields" hidden>
|
||||||
<summary>图案</summary>
|
<summary>图案</summary>
|
||||||
<div class="form-row"><label for="patternTarget">作用</label><select id="patternTarget"><option value="fill">填充</option><option value="stroke">描边</option></select></div>
|
<div class="form-row"><label for="patternTarget">应用</label><select id="patternTarget"><option value="fill">填充</option><option value="stroke">描边</option></select></div>
|
||||||
<div class="form-pair">
|
<div class="form-pair">
|
||||||
<div class="form-row"><label for="patternWidth">宽度</label><div class="form-unit"><input id="patternWidth" type="number" min="0" step="any"><span>mm</span></div></div>
|
<div class="form-row"><label for="patternWidth">宽度</label><div class="form-unit"><input id="patternWidth" type="number" min="0" step="any"><span>mm</span></div></div>
|
||||||
<div class="form-row"><label for="patternHeight">高度</label><div class="form-unit"><input id="patternHeight" type="number" min="0" step="any"><span>mm</span></div></div>
|
<div class="form-row"><label for="patternHeight">高度</label><div class="form-unit"><input id="patternHeight" type="number" min="0" step="any"><span>mm</span></div></div>
|
||||||
@@ -437,7 +437,7 @@
|
|||||||
<label class="form-row"><span>标题</span><input id="infoTitle" type="text" autofocus></label>
|
<label class="form-row"><span>标题</span><input id="infoTitle" type="text" autofocus></label>
|
||||||
<label class="form-row"><span>主题</span><input id="infoSubject" type="text"></label>
|
<label class="form-row"><span>主题</span><input id="infoSubject" type="text"></label>
|
||||||
<label class="form-row"><span>作者</span><input id="infoAuthor" type="text"></label>
|
<label class="form-row"><span>作者</span><input id="infoAuthor" type="text"></label>
|
||||||
<details class="info-custom"><summary>扩展</summary><div id="infoCustomRows"></div><button id="infoCustomAdd" class="small-button" type="button" title="添加字段" aria-label="添加字段">+</button></details>
|
<details class="info-custom"><summary>扩展</summary><div id="infoCustomRows"></div><button id="infoCustomAdd" class="icon-button" type="button" title="添加字段" aria-label="添加字段">+</button></details>
|
||||||
<div class="form-actions"><div id="infoStatus" class="form-status" role="status"></div><button id="infoCancel" class="button" type="button">取消</button><button class="button" type="submit">确定</button></div>
|
<div class="form-actions"><div id="infoStatus" class="form-status" role="status"></div><button id="infoCancel" class="button" type="button">取消</button><button class="button" type="submit">确定</button></div>
|
||||||
</form>
|
</form>
|
||||||
</dialog>
|
</dialog>
|
||||||
@@ -559,8 +559,8 @@
|
|||||||
<div class="form-row"><span>预览</span><div class="seal-position-options"><button id="signPick" class="button" type="button">定位</button><label><input id="signKeepRatio" type="checkbox" checked>等比</label></div></div>
|
<div class="form-row"><span>预览</span><div class="seal-position-options"><button id="signPick" class="button" type="button">定位</button><label><input id="signKeepRatio" type="checkbox" checked>等比</label></div></div>
|
||||||
<div class="form-row"><label for="signPlacement">位置</label><select id="signPlacement"><option value="normal">页面</option><option value="seam">骑缝</option></select></div>
|
<div class="form-row"><label for="signPlacement">位置</label><select id="signPlacement"><option value="normal">页面</option><option value="seam">骑缝</option></select></div>
|
||||||
<div class="form-row"><label for="signPages">页码</label><input id="signPages" type="text" autocomplete="off" spellcheck="false"></div>
|
<div class="form-row"><label for="signPages">页码</label><input id="signPages" type="text" autocomplete="off" spellcheck="false"></div>
|
||||||
<div class="form-row"><label for="signX">横坐标</label><div class="form-unit"><input id="signX" type="number" min="0" step="any" value="10" aria-label="横坐标(毫米)"><span>mm</span></div></div>
|
<div class="form-row"><label for="signX">横向</label><div class="form-unit"><input id="signX" type="number" min="0" step="any" value="10" aria-label="横坐标(毫米)"><span>mm</span></div></div>
|
||||||
<div class="form-row"><label for="signY">纵坐标</label><div class="form-unit"><input id="signY" type="number" min="0" step="any" value="10" aria-label="纵坐标(毫米)"><span>mm</span></div></div>
|
<div class="form-row"><label for="signY">纵向</label><div class="form-unit"><input id="signY" type="number" min="0" step="any" value="10" aria-label="纵坐标(毫米)"><span>mm</span></div></div>
|
||||||
<div class="form-row"><label for="signWidth">宽度</label><div class="form-unit"><input id="signWidth" type="number" min="0.01" step="any" value="40" aria-label="宽度(毫米)"><span>mm</span></div></div>
|
<div class="form-row"><label for="signWidth">宽度</label><div class="form-unit"><input id="signWidth" type="number" min="0.01" step="any" value="40" aria-label="宽度(毫米)"><span>mm</span></div></div>
|
||||||
<div class="form-row"><label for="signHeight">高度</label><div class="form-unit"><input id="signHeight" type="number" min="0.01" step="any" value="40" aria-label="高度(毫米)"><span>mm</span></div></div>
|
<div class="form-row"><label for="signHeight">高度</label><div class="form-unit"><input id="signHeight" type="number" min="0.01" step="any" value="40" aria-label="高度(毫米)"><span>mm</span></div></div>
|
||||||
</div>
|
</div>
|
||||||
@@ -788,7 +788,7 @@
|
|||||||
</section>
|
</section>
|
||||||
<section class="doc-font-panel" aria-labelledby="docFontPanelTitle">
|
<section class="doc-font-panel" aria-labelledby="docFontPanelTitle">
|
||||||
<div class="panel-row">
|
<div class="panel-row">
|
||||||
<div id="docFontPanelTitle" class="panel-title compact">OFD 字体</div>
|
<div id="docFontPanelTitle" class="panel-title compact">文档字体</div>
|
||||||
<span id="docFontSummary" class="count-pill">0</span>
|
<span id="docFontSummary" class="count-pill">0</span>
|
||||||
</div>
|
</div>
|
||||||
<div id="docFontList" class="doc-font-list"></div>
|
<div id="docFontList" class="doc-font-list"></div>
|
||||||
|
|||||||
+24
-6
@@ -1214,7 +1214,7 @@ button:not(:disabled):hover {
|
|||||||
}
|
}
|
||||||
|
|
||||||
.info-custom-row input,
|
.info-custom-row input,
|
||||||
.gradient-stop-row input,
|
.gradient-stop-row input[type="number"],
|
||||||
.structure-attribute > input,
|
.structure-attribute > input,
|
||||||
.form-row input[type="text"],
|
.form-row input[type="text"],
|
||||||
.form-row input[type="password"],
|
.form-row input[type="password"],
|
||||||
@@ -1260,8 +1260,8 @@ button:not(:disabled):hover {
|
|||||||
.info-custom-row {
|
.info-custom-row {
|
||||||
display: grid;
|
display: grid;
|
||||||
grid-template-columns: minmax(0, 1fr) minmax(0, 2fr) var(--control-height);
|
grid-template-columns: minmax(0, 1fr) minmax(0, 2fr) var(--control-height);
|
||||||
gap: 6px;
|
gap: 8px;
|
||||||
margin: 6px 0;
|
margin: 8px 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
#infoCustomRows > :first-child {
|
#infoCustomRows > :first-child {
|
||||||
@@ -1271,8 +1271,8 @@ button:not(:disabled):hover {
|
|||||||
.gradient-stop-row {
|
.gradient-stop-row {
|
||||||
display: grid;
|
display: grid;
|
||||||
grid-template-columns: 44px minmax(0, 1fr) minmax(0, 1fr) var(--control-height);
|
grid-template-columns: 44px minmax(0, 1fr) minmax(0, 1fr) var(--control-height);
|
||||||
gap: 6px;
|
gap: 8px;
|
||||||
margin: 6px 0;
|
margin: 8px 0;
|
||||||
align-items: center;
|
align-items: center;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1280,9 +1280,27 @@ button:not(:disabled):hover {
|
|||||||
font-size: 12px;
|
font-size: 12px;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.gradient-stop-head,
|
||||||
|
#gradientStops {
|
||||||
|
overflow-y: auto;
|
||||||
|
scrollbar-gutter: stable;
|
||||||
|
}
|
||||||
|
|
||||||
#gradientStops {
|
#gradientStops {
|
||||||
max-height: 180px;
|
max-height: 180px;
|
||||||
overflow-y: auto;
|
margin-bottom: 8px;
|
||||||
|
}
|
||||||
|
|
||||||
|
#gradientStops > :first-child {
|
||||||
|
margin-top: 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
#gradientStops > :last-child {
|
||||||
|
margin-bottom: 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
.gradient-stop-row .color-input {
|
||||||
|
width: 100%;
|
||||||
}
|
}
|
||||||
|
|
||||||
#infoCustomRows :focus-visible,
|
#infoCustomRows :focus-visible,
|
||||||
|
|||||||
@@ -887,7 +887,7 @@ function addCustomDataRow(field = {Name: "", Value: ""}, sourceIndex) {
|
|||||||
}
|
}
|
||||||
const remove = document.createElement("button");
|
const remove = document.createElement("button");
|
||||||
remove.type = "button";
|
remove.type = "button";
|
||||||
remove.className = "small-button";
|
remove.className = "icon-button";
|
||||||
remove.textContent = "×";
|
remove.textContent = "×";
|
||||||
remove.title = "删除字段";
|
remove.title = "删除字段";
|
||||||
remove.setAttribute("aria-label", "删除字段");
|
remove.setAttribute("aria-label", "删除字段");
|
||||||
@@ -2045,6 +2045,7 @@ function addGradientStop(position, color, transparency, source) {
|
|||||||
for (const [type, value, label] of [["color", color, "色标颜色"], ["number", position, "色标位置"], ["number", transparency, "色标透明度"]]) {
|
for (const [type, value, label] of [["color", color, "色标颜色"], ["number", position, "色标位置"], ["number", transparency, "色标透明度"]]) {
|
||||||
const input = document.createElement("input");
|
const input = document.createElement("input");
|
||||||
input.type = type;
|
input.type = type;
|
||||||
|
if (type === "color") input.className = "color-input";
|
||||||
input.value = value;
|
input.value = value;
|
||||||
input.disabled = el.gradientKind.value === "keep";
|
input.disabled = el.gradientKind.value === "keep";
|
||||||
input.setAttribute("aria-label", label);
|
input.setAttribute("aria-label", label);
|
||||||
@@ -2054,7 +2055,7 @@ function addGradientStop(position, color, transparency, source) {
|
|||||||
}
|
}
|
||||||
const remove = document.createElement("button");
|
const remove = document.createElement("button");
|
||||||
remove.type = "button";
|
remove.type = "button";
|
||||||
remove.className = "small-button";
|
remove.className = "icon-button";
|
||||||
remove.textContent = "×";
|
remove.textContent = "×";
|
||||||
remove.title = "删除色标";
|
remove.title = "删除色标";
|
||||||
remove.setAttribute("aria-label", "删除色标");
|
remove.setAttribute("aria-label", "删除色标");
|
||||||
@@ -5619,8 +5620,8 @@ function renderStyleResourceSettings(kind) {
|
|||||||
}
|
}
|
||||||
settingsField(content, "斜体", "Italic", value.Italic, "checkbox");
|
settingsField(content, "斜体", "Italic", value.Italic, "checkbox");
|
||||||
settingsSelect(content, "端点", "Cap", [["", "继承"], ["Butt", "平头"], ["Round", "圆头"], ["Square", "方头"]], value.Cap || "");
|
settingsSelect(content, "端点", "Cap", [["", "继承"], ["Butt", "平头"], ["Round", "圆头"], ["Square", "方头"]], value.Cap || "");
|
||||||
settingsSelect(content, "连接", "Join", [["", "继承"], ["Miter", "尖角"], ["Round", "圆角"], ["Bevel", "斜角"]], value.Join || "");
|
settingsSelect(content, "转角", "Join", [["", "继承"], ["Miter", "尖角"], ["Round", "圆角"], ["Bevel", "斜角"]], value.Join || "");
|
||||||
settingsField(content, "虚线", "DashPattern", value.DashPattern || "");
|
settingsField(content, "间隔", "DashPattern", value.DashPattern || "").title = "虚线间隔";
|
||||||
settingsField(content, "偏移", "DashOffset", value.DashOffset ?? "", "number", "mm");
|
settingsField(content, "偏移", "DashOffset", value.DashOffset ?? "", "number", "mm");
|
||||||
for (const [key, label] of [["FillColor", "填充"], ["StrokeColor", "描边"]]) {
|
for (const [key, label] of [["FillColor", "填充"], ["StrokeColor", "描边"]]) {
|
||||||
settingsSelect(content, label, key + "Mode", [["keep", "原有"], ["inherit", "继承"], ["solid", "颜色"]], "keep");
|
settingsSelect(content, label, key + "Mode", [["keep", "原有"], ["inherit", "继承"], ["solid", "颜色"]], "keep");
|
||||||
@@ -5641,7 +5642,7 @@ function renderStyleResourceSettings(kind) {
|
|||||||
if (kind === "ColorSpace") {
|
if (kind === "ColorSpace") {
|
||||||
settingsSelect(binding, "应用", "PaintTarget", [["fill", "填充"], ["stroke", "描边"]], "fill");
|
settingsSelect(binding, "应用", "PaintTarget", [["fill", "填充"], ["stroke", "描边"]], "fill");
|
||||||
settingsSelect(binding, "方式", "PaintMode", [["value", "分量"], ["index", "索引"]], "value");
|
settingsSelect(binding, "方式", "PaintMode", [["value", "分量"], ["index", "索引"]], "value");
|
||||||
settingsField(binding, "颜色值", "PaintValue", value.Type === "CMYK" ? `0 0 0 ${2 ** (value.BitsPerComponent || 8) - 1}` : value.Type === "GRAY" ? "0" : "0 0 0");
|
settingsField(binding, "色值", "PaintValue", value.Type === "CMYK" ? `0 0 0 ${2 ** (value.BitsPerComponent || 8) - 1}` : value.Type === "GRAY" ? "0" : "0 0 0");
|
||||||
}
|
}
|
||||||
const apply = settingsButton("应用", () => applyStyleResource(kind), !objects.value, "Apply", group.actions);
|
const apply = settingsButton("应用", () => applyStyleResource(kind), !objects.value, "Apply", group.actions);
|
||||||
const unbind = kind === "DrawParam" ? settingsButton("解绑", () => applyStyleResource(kind, true), !objects.value, "Unbind", group.actions) : null;
|
const unbind = kind === "DrawParam" ? settingsButton("解绑", () => applyStyleResource(kind, true), !objects.value, "Unbind", group.actions) : null;
|
||||||
@@ -5784,7 +5785,8 @@ function renderTemplateSettings() {
|
|||||||
settingsElements.Content.append(source);
|
settingsElements.Content.append(source);
|
||||||
}
|
}
|
||||||
settingsPages(source, "SourcePage", settings.page);
|
settingsPages(source, "SourcePage", settings.page);
|
||||||
document.querySelector("#settingsSourcePage").closest("label").firstElementChild.textContent = "来源页";
|
document.querySelector("#settingsSourcePage").closest("label").firstElementChild.textContent = "来源";
|
||||||
|
document.querySelector("#settingsSourcePage").setAttribute("aria-label", "来源页");
|
||||||
const write = async (operation, order = 0) => {
|
const write = async (operation, order = 0) => {
|
||||||
if (operation === "replace" && !window.confirm("替换模板内容?当前文档中引用此模板的页面将同步更新。")) return;
|
if (operation === "replace" && !window.confirm("替换模板内容?当前文档中引用此模板的页面将同步更新。")) return;
|
||||||
const selected = settings.selected;
|
const selected = settings.selected;
|
||||||
@@ -6626,7 +6628,7 @@ function updateSignPlacement() {
|
|||||||
input.disabled = !stamp;
|
input.disabled = !stamp;
|
||||||
input.required = stamp;
|
input.required = stamp;
|
||||||
}
|
}
|
||||||
document.querySelector('label[for="signX"]').textContent = el.signPlacement.value === "seam" ? "右侧内缩" : "横坐标";
|
document.querySelector('label[for="signX"]').textContent = el.signPlacement.value === "seam" ? "右侧内缩" : "横向";
|
||||||
el.signX.setAttribute("aria-label", el.signPlacement.value === "seam" ? "右侧内缩(毫米)" : "横坐标(毫米)");
|
el.signX.setAttribute("aria-label", el.signPlacement.value === "seam" ? "右侧内缩(毫米)" : "横坐标(毫米)");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -39,7 +39,7 @@ type OpenOptions struct {
|
|||||||
// FontFile 字体文件
|
// FontFile 字体文件
|
||||||
type FontFile = ofdgo.FontFile
|
type FontFile = ofdgo.FontFile
|
||||||
|
|
||||||
// FontInfo OFD字体信息
|
// FontInfo 文档字体信息
|
||||||
type FontInfo = ofdgo.FontInfo
|
type FontInfo = ofdgo.FontInfo
|
||||||
|
|
||||||
// Session WebUI文档会话
|
// Session WebUI文档会话
|
||||||
|
|||||||
+1
-1
@@ -17,7 +17,7 @@ package ofdgo
|
|||||||
// defaultPathLineWidth 为默认描边宽度,单位为毫米
|
// defaultPathLineWidth 为默认描边宽度,单位为毫米
|
||||||
const defaultPathLineWidth = 0.353
|
const defaultPathLineWidth = 0.353
|
||||||
|
|
||||||
// defaultMiterLimit 为默认尖角限制
|
// defaultMiterLimit 为默认尖角截断值
|
||||||
const defaultMiterLimit = 3.528
|
const defaultMiterLimit = 3.528
|
||||||
|
|
||||||
// mergeGraphicObjectAlpha 合并图形对象透明度
|
// mergeGraphicObjectAlpha 合并图形对象透明度
|
||||||
|
|||||||
@@ -109,7 +109,7 @@ func (e *Editor) AddColorSpace(space ColorSpace, profile []byte) (string, error)
|
|||||||
|
|
||||||
// GradientStops 解析当前文档的渐变分段,保留顺序并合并透明度
|
// GradientStops 解析当前文档的渐变分段,保留顺序并合并透明度
|
||||||
// 入参: segments 渐变分段, alpha 外层透明度
|
// 入参: segments 渐变分段, alpha 外层透明度
|
||||||
// 返回: []ColorStop 后端无关的色标, error 颜色解析错误
|
// 返回: []ColorStop 后端无关的渐变色标, error 颜色解析错误
|
||||||
func (e *Editor) GradientStops(segments []ShdSegment, alpha *int) ([]ColorStop, error) {
|
func (e *Editor) GradientStops(segments []ShdSegment, alpha *int) ([]ColorStop, error) {
|
||||||
positions := gradientPositions(segments)
|
positions := gradientPositions(segments)
|
||||||
stops := make([]ColorStop, len(segments))
|
stops := make([]ColorStop, len(segments))
|
||||||
|
|||||||
@@ -175,7 +175,7 @@ func (e *Editor) wrapCompositePath(renderer *Renderer, node *editorCompositeNode
|
|||||||
return e.vectorInstance(renderer, []*editorCompositeNode{node})
|
return e.vectorInstance(renderer, []*editorCompositeNode{node})
|
||||||
}
|
}
|
||||||
|
|
||||||
// isolateCompositeStyle 固定对象的绘制参数,避免目标容器改变颜色、虚线和线帽
|
// isolateCompositeStyle 固定对象的绘制参数,避免目标容器改变颜色、虚线和端点样式
|
||||||
// 入参: node 页面坐标中的对象节点
|
// 入参: node 页面坐标中的对象节点
|
||||||
// 返回: error 错误信息
|
// 返回: error 错误信息
|
||||||
func (e *Editor) isolateCompositeStyle(node *editorCompositeNode) error {
|
func (e *Editor) isolateCompositeStyle(node *editorCompositeNode) error {
|
||||||
|
|||||||
@@ -443,7 +443,7 @@ func resourceColorNode(node *editorXML) bool {
|
|||||||
|
|
||||||
// validateResourceColors 校验显式及默认颜色空间的既有颜色,防止位深或调色板更新使引用失效
|
// validateResourceColors 校验显式及默认颜色空间的既有颜色,防止位深或调色板更新使引用失效
|
||||||
// 入参: ctx 取消上下文, catalog 当前资源目录, space 替换后的颜色空间
|
// 入参: ctx 取消上下文, catalog 当前资源目录, space 替换后的颜色空间
|
||||||
// 返回: error 不兼容的颜色值或调色板索引
|
// 返回: error 不兼容的色值或调色板索引
|
||||||
func validateResourceColors(ctx context.Context, catalog *resourceCatalog, space ColorSpace) error {
|
func validateResourceColors(ctx context.Context, catalog *resourceCatalog, space ColorSpace) error {
|
||||||
doc, err := catalog.scan.reader.DocContext(ctx)
|
doc, err := catalog.scan.reader.DocContext(ctx)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
|||||||
@@ -24,6 +24,7 @@ import (
|
|||||||
|
|
||||||
// ObjectStyle 对象外观,nil字段保持原值,颜色的Alpha为nil时保留原颜色透明度
|
// ObjectStyle 对象外观,nil字段保持原值,颜色的Alpha为nil时保留原颜色透明度
|
||||||
// StyleObjects使用对象坐标毫米,StyleCompositeObjects的线宽、虚线长度及偏移使用页面毫米
|
// StyleObjects使用对象坐标毫米,StyleCompositeObjects的线宽、虚线长度及偏移使用页面毫米
|
||||||
|
// Cap为端点样式,Join为转角样式,MiterLimit为尖角截断值,DashPattern为虚线间隔序列
|
||||||
type ObjectStyle struct {
|
type ObjectStyle struct {
|
||||||
Alpha *int
|
Alpha *int
|
||||||
Fill *bool
|
Fill *bool
|
||||||
|
|||||||
+4
-4
@@ -35,7 +35,7 @@ const (
|
|||||||
FontStatusMissing = "missing"
|
FontStatusMissing = "missing"
|
||||||
)
|
)
|
||||||
|
|
||||||
// FontInfo OFD字体诊断信息,MatchedFace为实际匹配字体及原文件中的零起始索引,无法读取时为空
|
// FontInfo 文档字体诊断信息,MatchedFace为实际匹配字体及原文件中的零起始索引,无法读取时为空
|
||||||
type FontInfo struct {
|
type FontInfo struct {
|
||||||
ID string `json:"id"`
|
ID string `json:"id"`
|
||||||
FontName string `json:"fontName"`
|
FontName string `json:"fontName"`
|
||||||
@@ -141,7 +141,7 @@ func (r *Reader) fontDefinition(id string) *Font {
|
|||||||
return font
|
return font
|
||||||
}
|
}
|
||||||
|
|
||||||
// FontInfos 获取OFD字体诊断信息
|
// FontInfos 获取文档字体诊断信息
|
||||||
// 返回: []FontInfo 字体诊断列表, error 错误信息
|
// 返回: []FontInfo 字体诊断列表, error 错误信息
|
||||||
func (r *Renderer) FontInfos() ([]FontInfo, error) {
|
func (r *Renderer) FontInfos() ([]FontInfo, error) {
|
||||||
scanner, err := r.ScanFontInfos()
|
scanner, err := r.ScanFontInfos()
|
||||||
@@ -202,7 +202,7 @@ func (s *FontInfoScanner) Infos() ([]FontInfo, error) {
|
|||||||
return s.renderer.fontInfos(s.usage)
|
return s.renderer.fontInfos(s.usage)
|
||||||
}
|
}
|
||||||
|
|
||||||
// FontInfosFromPages 从页面内容获取OFD字体诊断信息
|
// FontInfosFromPages 从页面内容获取文档字体诊断信息
|
||||||
// 入参: pages 页面内容列表
|
// 入参: pages 页面内容列表
|
||||||
// 返回: []FontInfo 字体诊断列表, error 错误信息
|
// 返回: []FontInfo 字体诊断列表, error 错误信息
|
||||||
func (r *Renderer) FontInfosFromPages(pages []*PageContent) ([]FontInfo, error) {
|
func (r *Renderer) FontInfosFromPages(pages []*PageContent) ([]FontInfo, error) {
|
||||||
@@ -291,7 +291,7 @@ func (r *Renderer) fontInfoDocument() (*Document, error) {
|
|||||||
return doc, nil
|
return doc, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// fontInfos 获取OFD字体诊断信息
|
// fontInfos 获取文档字体诊断信息
|
||||||
// 入参: usage 字体使用次数
|
// 入参: usage 字体使用次数
|
||||||
// 返回: []FontInfo 字体诊断列表, error 错误信息
|
// 返回: []FontInfo 字体诊断列表, error 错误信息
|
||||||
func (r *Renderer) fontInfos(usage map[string]int) ([]FontInfo, error) {
|
func (r *Renderer) fontInfos(usage map[string]int) ([]FontInfo, error) {
|
||||||
|
|||||||
@@ -26,7 +26,7 @@ type geometryPolyline struct {
|
|||||||
direction Point
|
direction Point
|
||||||
}
|
}
|
||||||
|
|
||||||
// Stroke 将曲线、虚线及线帽连接转换为非零填充轮廓
|
// Stroke 按端点和转角样式将曲线、虚线转换为非零填充轮廓
|
||||||
// 曲线按Tolerance展开,默认误差为0.001毫米,重叠轮廓保持同向绕数
|
// 曲线按Tolerance展开,默认误差为0.001毫米,重叠轮廓保持同向绕数
|
||||||
// 结果未做布尔整理,按非零规则填充,区域运算需能处理重叠子路径的后端
|
// 结果未做布尔整理,按非零规则填充,区域运算需能处理重叠子路径的后端
|
||||||
// 入参: options 描边样式
|
// 入参: options 描边样式
|
||||||
@@ -283,7 +283,7 @@ func (line geometryPolyline) dash(pattern []float64, total, offset float64) ([]g
|
|||||||
|
|
||||||
// stroke 追加同向矩形、连接楔形及圆盘组成的非零填充区域
|
// stroke 追加同向矩形、连接楔形及圆盘组成的非零填充区域
|
||||||
// 入参: result 已有轮廓, options 描边样式
|
// 入参: result 已有轮廓, options 描边样式
|
||||||
// 返回: GeometryPath 填充轮廓, error 不支持的退化方形线帽
|
// 返回: GeometryPath 填充轮廓, error 不支持的退化方头端点
|
||||||
func (line geometryPolyline) stroke(result GeometryPath, options StrokeOptions) (GeometryPath, error) {
|
func (line geometryPolyline) stroke(result GeometryPath, options StrokeOptions) (GeometryPath, error) {
|
||||||
half := options.Width / 2
|
half := options.Width / 2
|
||||||
polygon := func(points ...Point) {
|
polygon := func(points ...Point) {
|
||||||
|
|||||||
+3
-3
@@ -37,7 +37,7 @@ func (r *Renderer) ResolveColor(value string, index *int, space string, alpha *i
|
|||||||
|
|
||||||
// GradientStops 解析OFD渐变分段的位置与透明度,返回独立数据并保留原分段顺序
|
// GradientStops 解析OFD渐变分段的位置与透明度,返回独立数据并保留原分段顺序
|
||||||
// 入参: segments 渐变分段, alpha 透明度
|
// 入参: segments 渐变分段, alpha 透明度
|
||||||
// 返回: []ColorStop 后端无关的渐变分段
|
// 返回: []ColorStop 后端无关的渐变色标
|
||||||
func (r *Renderer) GradientStops(segments []ShdSegment, alpha *int) []ColorStop {
|
func (r *Renderer) GradientStops(segments []ShdSegment, alpha *int) []ColorStop {
|
||||||
var gradient []ColorStop
|
var gradient []ColorStop
|
||||||
positions := gradientPositions(segments)
|
positions := gradientPositions(segments)
|
||||||
@@ -49,7 +49,7 @@ func (r *Renderer) GradientStops(segments []ShdSegment, alpha *int) []ColorStop
|
|||||||
}
|
}
|
||||||
|
|
||||||
// parseColorWithAlpha 解析带透明度的颜色
|
// parseColorWithAlpha 解析带透明度的颜色
|
||||||
// 入参: value 颜色值, index 调色板索引, space 颜色空间标识, alpha 透明度
|
// 入参: value 色值, index 调色板索引, space 颜色空间标识, alpha 透明度
|
||||||
// 返回: color.Color 颜色对象
|
// 返回: color.Color 颜色对象
|
||||||
func (r *Renderer) parseColorWithAlpha(value string, index *int, space string, alpha *int) color.Color {
|
func (r *Renderer) parseColorWithAlpha(value string, index *int, space string, alpha *int) color.Color {
|
||||||
kind, values := r.colorComponents(value, index, space)
|
kind, values := r.colorComponents(value, index, space)
|
||||||
@@ -89,7 +89,7 @@ func (r *Renderer) parseColorWithAlpha(value string, index *int, space string, a
|
|||||||
}
|
}
|
||||||
|
|
||||||
// colorComponents 读取颜色空间及归一化分量,保留源位深供渐变插值
|
// colorComponents 读取颜色空间及归一化分量,保留源位深供渐变插值
|
||||||
// 入参: value 颜色值, index 调色板索引, space 颜色空间标识
|
// 入参: value 色值, index 调色板索引, space 颜色空间标识
|
||||||
// 返回: string 颜色模型, [4]float64 单位分量
|
// 返回: string 颜色模型, [4]float64 单位分量
|
||||||
func (r *Renderer) colorComponents(value string, index *int, space string) (string, [4]float64) {
|
func (r *Renderer) colorComponents(value string, index *int, space string) (string, [4]float64) {
|
||||||
cs := r.colorDefinition(space)
|
cs := r.colorDefinition(space)
|
||||||
|
|||||||
@@ -207,7 +207,7 @@ func canvasNativeStroke(geometry GeometryBackend) bool {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// canvasStrokeOptions 转换Canvas描边样式,虚线由调用方传入
|
// canvasStrokeOptions 转换Canvas描边样式,虚线由调用方传入
|
||||||
// 入参: width 描边宽度, cap 线帽, join 连接, tolerance 展开误差
|
// 入参: width 线宽, cap 端点样式, join 转角样式, tolerance 展开误差
|
||||||
// 返回: StrokeOptions 公共描边样式
|
// 返回: StrokeOptions 公共描边样式
|
||||||
func canvasStrokeOptions(width float64, cap canvas.Capper, join canvas.Joiner, tolerance float64) StrokeOptions {
|
func canvasStrokeOptions(width float64, cap canvas.Capper, join canvas.Joiner, tolerance float64) StrokeOptions {
|
||||||
options := StrokeOptions{Width: width, Cap: "Butt", Join: "Miter", MiterLimit: defaultMiterLimit, Tolerance: tolerance}
|
options := StrokeOptions{Width: width, Cap: "Butt", Join: "Miter", MiterLimit: defaultMiterLimit, Tolerance: tolerance}
|
||||||
@@ -274,14 +274,14 @@ func canvasFillClip(clip *canvas.Path) bool {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// strokeCanvasPath 将文字和复杂画刷的描边交给配置的几何后端
|
// strokeCanvasPath 将文字和复杂画刷的描边交给配置的几何后端
|
||||||
// 入参: path Canvas路径, width 描边宽度, cap 线帽, join 连接
|
// 入参: path Canvas路径, width 线宽, cap 端点样式, join 转角样式
|
||||||
// 返回: *canvas.Path 描边轮廓
|
// 返回: *canvas.Path 描边轮廓
|
||||||
func (r *Renderer) strokeCanvasPath(path *canvas.Path, width float64, cap canvas.Capper, join canvas.Joiner) *canvas.Path {
|
func (r *Renderer) strokeCanvasPath(path *canvas.Path, width float64, cap canvas.Capper, join canvas.Joiner) *canvas.Path {
|
||||||
return r.strokeDashedCanvasPath(path, width, cap, join, 0, nil, false)
|
return r.strokeDashedCanvasPath(path, width, cap, join, 0, nil, false)
|
||||||
}
|
}
|
||||||
|
|
||||||
// strokeDashedCanvasPath 通过公共几何后端展开虚线和线帽,保留零长度绘制段
|
// strokeDashedCanvasPath 通过公共几何后端展开虚线和端点样式,保留零长度绘制段
|
||||||
// 入参: path 路径, width 线宽, cap 线帽, join 连接, offset 虚线偏移, dashes 虚线数组, fill 是否直接填充或凸窗口裁剪
|
// 入参: path 路径, width 线宽, cap 端点样式, join 转角样式, offset 虚线偏移, dashes 虚线间隔序列, fill 是否直接填充或凸窗口裁剪
|
||||||
// 返回: *canvas.Path 描边填充轮廓
|
// 返回: *canvas.Path 描边填充轮廓
|
||||||
func (r *Renderer) strokeDashedCanvasPath(path *canvas.Path, width float64, cap canvas.Capper, join canvas.Joiner, offset float64, dashes []float64, fill bool) *canvas.Path {
|
func (r *Renderer) strokeDashedCanvasPath(path *canvas.Path, width float64, cap canvas.Capper, join canvas.Joiner, offset float64, dashes []float64, fill bool) *canvas.Path {
|
||||||
geometry, err := r.Geometry()
|
geometry, err := r.Geometry()
|
||||||
|
|||||||
@@ -99,7 +99,7 @@ func (r *boundsRenderer) Size() (float64, float64) {
|
|||||||
return 0, 0
|
return 0, 0
|
||||||
}
|
}
|
||||||
|
|
||||||
// RenderPath 收集填充与描边范围,保持线帽、连接和虚线语义
|
// RenderPath 收集填充与描边范围,保持端点、转角和虚线语义
|
||||||
// 入参: path 路径, style 绘制样式, m 变换矩阵
|
// 入参: path 路径, style 绘制样式, m 变换矩阵
|
||||||
func (r *boundsRenderer) RenderPath(path *canvas.Path, style canvas.Style, m canvas.Matrix) {
|
func (r *boundsRenderer) RenderPath(path *canvas.Path, style canvas.Style, m canvas.Matrix) {
|
||||||
if style.HasFill() {
|
if style.HasFill() {
|
||||||
|
|||||||
@@ -49,8 +49,8 @@ func (r *Renderer) parseStrokePaint(strokeColor *StrokeColor, x, y, pageH float6
|
|||||||
}
|
}
|
||||||
|
|
||||||
// canvasGradient 将公共颜色节点转换为Canvas渐变
|
// canvasGradient 将公共颜色节点转换为Canvas渐变
|
||||||
// 入参: stops 渐变分段
|
// 入参: stops 渐变色标
|
||||||
// 返回: canvas.Grad 渐变分段
|
// 返回: canvas.Grad 渐变色标
|
||||||
func canvasGradient(stops []ColorStop) canvas.Grad {
|
func canvasGradient(stops []ColorStop) canvas.Grad {
|
||||||
var gradient canvas.Grad
|
var gradient canvas.Grad
|
||||||
for _, stop := range stops {
|
for _, stop := range stops {
|
||||||
|
|||||||
@@ -75,9 +75,9 @@ func (s *pathStyle) applyStrokeColor(r *Renderer, stroke *StrokeColor, bx, by, p
|
|||||||
s.strokePaint = r.parseStrokePaint(strokeColorNode, bx, by, pageH)
|
s.strokePaint = r.parseStrokePaint(strokeColorNode, bx, by, pageH)
|
||||||
}
|
}
|
||||||
|
|
||||||
// pathLineCap 转换线帽样式
|
// pathLineCap 转换端点样式
|
||||||
// 入参: cap 线帽名称, fallback 默认线帽
|
// 入参: cap 端点样式名称, fallback 默认端点样式
|
||||||
// 返回: canvas.Capper 线帽样式
|
// 返回: canvas.Capper 端点样式
|
||||||
func pathLineCap(cap string, fallback canvas.Capper) canvas.Capper {
|
func pathLineCap(cap string, fallback canvas.Capper) canvas.Capper {
|
||||||
switch cap {
|
switch cap {
|
||||||
case "Butt":
|
case "Butt":
|
||||||
@@ -90,8 +90,8 @@ func pathLineCap(cap string, fallback canvas.Capper) canvas.Capper {
|
|||||||
return fallback
|
return fallback
|
||||||
}
|
}
|
||||||
|
|
||||||
// applyLineJoin 应用线连接样式及尖角限制
|
// applyLineJoin 应用转角样式及尖角截断值
|
||||||
// 入参: join 线连接名称, limit 尖角限制, explicit 是否显式指定零截断值
|
// 入参: join 转角样式名称, limit 尖角截断值, explicit 是否显式指定零截断值
|
||||||
func (s *pathStyle) applyLineJoin(join string, limit float64, explicit bool) {
|
func (s *pathStyle) applyLineJoin(join string, limit float64, explicit bool) {
|
||||||
if limit > 0 || explicit {
|
if limit > 0 || explicit {
|
||||||
s.miterLimit = limit
|
s.miterLimit = limit
|
||||||
|
|||||||
@@ -84,6 +84,7 @@ type DrawParams struct {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// DrawParam 绘制参数
|
// DrawParam 绘制参数
|
||||||
|
// Cap为端点样式,Join为转角样式,MiterLimit为尖角截断值,DashPattern为虚线间隔序列
|
||||||
// MiterLimitSet为true时,零截断值覆盖继承值,否则零值表示未指定
|
// MiterLimitSet为true时,零截断值覆盖继承值,否则零值表示未指定
|
||||||
type DrawParam struct {
|
type DrawParam struct {
|
||||||
ID string `xml:"ID,attr"`
|
ID string `xml:"ID,attr"`
|
||||||
|
|||||||
Reference in new issue
Block a user