-
Notifications
You must be signed in to change notification settings - Fork 121
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Fix copy table related issues #169
base: main
Are you sure you want to change the base?
Changes from 10 commits
eea5f03
9fab6b9
d730e66
24df484
f80c512
425ae8d
0236599
c90c3c6
9a260a3
2e560ba
be5d856
294351f
b68d2ad
5e50c84
815d607
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,6 @@ | ||
--- | ||
'@editablejs/deserializer': patch | ||
'@editablejs/plugin-table': patch | ||
--- | ||
|
||
fix: fix issues about copy tables from other html page which may cause page collapse and wrong enter press respond and missing table header and missing last empty cell. |
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -4,7 +4,7 @@ | |
node_modules | ||
.pnp | ||
.pnp.js | ||
|
||
.history | ||
# testing | ||
coverage | ||
|
||
|
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,4 +1,4 @@ | ||
import { Editor, Descendant, Element, Text, DOMNode, isDOMText } from '@editablejs/models' | ||
import { DOMNode, Descendant, Editor, Element, Text, isDOMText } from '@editablejs/models' | ||
|
||
export interface HTMLDeserializerOptions { | ||
element?: Omit<Element, 'children'> | ||
|
@@ -79,6 +79,98 @@ export const HTMLDeserializer = { | |
for (const { transform, options } of transforms) { | ||
HTMLDeserializerEditor.with(transform, options) | ||
} | ||
|
||
|
||
// handle table cell merging | ||
// 对node的children进行遍历,寻找里面的children,判断children里是否有table,并对table做处理 | ||
// 如果有table,那么就对table里的cell进行遍历,判断cell的colspan和rowspan是否为1 | ||
// 如果不为1,那么就对cell的colspan和rowspan进行处理,使其都为1 | ||
// 如果为1,那么就不做处理 | ||
// 如果cell的colspan和rowspan都为1,那么就不做处理 | ||
const children = node.children; | ||
for (let i = 0; i < children.length; i++) { | ||
const child = children[i]; | ||
if (child.nodeName === 'TABLE') { | ||
let colCount = 0; | ||
for (let rowIndex = 0; rowIndex < child.rows.length; rowIndex++) { | ||
const row = child.rows[rowIndex]; | ||
// 计算第一行的列数,用colspan累加 | ||
if (rowIndex === 0) { | ||
for (let cellIndex = 0; cellIndex < row.cells.length; cellIndex++) { | ||
const cell = row.cells[cellIndex]; | ||
const colspan = cell.getAttribute('colspan') ?? 1 | ||
colCount += colspan - 0; | ||
} | ||
} | ||
|
||
|
||
for (let cellIndex = 0; cellIndex < row.cells.length; cellIndex++) { | ||
const cell = row.cells[cellIndex]; | ||
if (rowIndex === 0 && cell.nodeName === 'TH') { | ||
cell.style.fontWeight = '700'; | ||
} | ||
const colspan = cell.getAttribute('colspan') ?? 1 | ||
const rowspan = cell.getAttribute('rowspan') ?? 1 | ||
if (colspan > 1) { | ||
for (let i = 1; i < colspan; i++) { | ||
const newCell = document.createElement('TD') | ||
// 设置当前newCell的colspan和rowspan都为1 | ||
newCell.setAttribute('colspan', '1') | ||
newCell.setAttribute('rowspan', '1') | ||
// 设置当前newCell的文本为displaynone | ||
newCell.textContent = 'displaynone||||||' + rowIndex + '||||||' + cellIndex | ||
row.insertBefore(newCell, cell.nextSibling) | ||
} | ||
} | ||
if (rowspan > 1) { | ||
for (let i = 1; i < rowspan; i++) { | ||
// 获取当前行的下i行 | ||
const nextRow = child.rows[rowIndex + i] | ||
// 获取当前行的下i行的第cellIndex个cell | ||
for (let i = 0; i < colspan; i++) { | ||
const newCell = nextRow.insertCell(cellIndex); | ||
// 设置当前newCell的colspan和rowspan都为1 | ||
newCell.setAttribute('colspan', '1') | ||
newCell.setAttribute('rowspan', '1') | ||
// 设置当前newCell的文本为displaynone | ||
newCell.textContent = 'displaynone||||||' + rowIndex + '||||||' + cellIndex | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 这里太hack了,其实我没太看懂这里把合并行和列拉平的用意 There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 或者你那有好的思路,也可以参考下 There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
我提交了一版,整体包含了我的思路,我这儿没有测试数据。你可以先帮忙测试看看。 There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. |
||
} | ||
} | ||
} | ||
} | ||
let cellsLength = row.cells.length; | ||
if (cellsLength < colCount) { | ||
for (let i = 0; i < colCount - cellsLength; i++) { | ||
const newCell = row.insertCell(); | ||
// 设置当前newCell的colspan和rowspan都为1 | ||
newCell.setAttribute('colspan', '1') | ||
newCell.setAttribute('rowspan', '1') | ||
// 设置当前newCell的文本为空 | ||
newCell.textContent = ''; | ||
} | ||
} | ||
} | ||
} | ||
// 解析child的innerHTML,并循环遍历内部的所有strike,并增加style:text-decoration:line-through; | ||
if (child.innerHTML.indexOf('<strike') !== -1) { | ||
big-camel marked this conversation as resolved.
Show resolved
Hide resolved
|
||
const strikes = child.getElementsByTagName('strike'); | ||
for (let strike of strikes) { | ||
// 将当前的strike元素替换为span元素 | ||
const span = document.createElement('span'); | ||
span.innerHTML = strike.innerHTML; | ||
// 将 strike 元素的所有样式复制到 span 元素 | ||
for (let property of strike.style) { | ||
span.style.setProperty(property, strike.style.getPropertyValue(property)); | ||
} | ||
span.style.textDecoration = 'line-through'; | ||
// 将当前元素作为兄弟元素插入到strike后面 | ||
strike.insertAdjacentElement('afterend', span); | ||
} | ||
while (strikes.length > 0) { | ||
strikes[0].remove(); | ||
} | ||
} | ||
} | ||
|
||
return HTMLDeserializerEditor.transform(node, options) | ||
}, | ||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
那如果table里面还有嵌套的table呢?这里是只考虑了一层嵌套关系吗?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
对,满足现有需求够用了