Flat selection design #231
Replies: 3 comments 4 replies
-
I think we can use ourselves data model to describe selection information . And we should use same data model in other features like copy / paste or comment . But it most like native browser selection , like : type selectionInfo = {
start: {blockId: string , offset: number},
end: {blockId: string , offset: number}
} It is easy for selection coordinating . If we list all selected blocks , it may change to a complex problem . And we should provide more pure functions and methods like : function getSelectedIdsBySelectionInfo(selectionInfo: selectionInfo): string[];
function getSelectedBlocksBySelectionInfo: (
selectionInfo: selectionInfo
) : Blocks[];
interface Selection {
getSelectedBlockIds: () => string[];
getSelectedBlocks: () => Blocks[];
} |
Beta Was this translation helpful? Give feedback.
-
This sounds very similar to how ProseMirror manages selections, except it seems like ProseMirror might be a bit easier to operate on since the rules are very consistent for the whole tree (e.g. every spot on the document inside or outside an element has a different position) & you can always easily determine if something is on the selection or outside it with greater than or less than comparisons. How does this design compare? Can you represent a selection of |
Beta Was this translation helpful? Give feedback.
-
Is this discussion specific only to quill? I think I'd benefit from a list of survive ways this has been approached and the pros and cons of the approach described, here. |
Beta Was this translation helpful? Give feedback.
-
Here we explain the basic design principles for working with native DOM selection in BlockSuite.
Natively, a DOM selection is composed with
anchorNode
andfocusNode
. This can be used for indexing a sub-tree. But for rich text editing, this API surface leaks many edge cases to be handled manually. For example, suppose we have 3 lines of text (3 paragraph blocks):And for a rich text editor, similar content can also be expressed in this way:
In both cases, we can perform a range selection from
2
to8
(23 456 78
get selected), but the resulting DOM range can be very different, which is challenging to work with.The proposed solution is to make our selection representation flat. To do this, Quill's
getSelection
API is a great fit. This{ index: number, length: number }
interface is excellent for updating our text model (code), whose result won't be affected by nested tags for rich text formatting.Also, BlockSuite is designed to support the co-existing of different rich text editor instances. For the example above, we have three Quill instances:
So based on this approach, when we select from
2
to8
, the flat selection should be modeled in this way:However, when the native DOM selection covers different quill instances, Quill's
getSelection
API doesn't work (returnsnull
). So we need to support our range selection representation by ourselves. We already havegetQuillIndexByNativeSelection
that provides the corresponding underlying capabilities. But we still need further engineering effort to get a reusable selection representation with handy APIs.cc @lawvs @DiamondThree @SaikaSakura @JimmFly @thorseraq
Beta Was this translation helpful? Give feedback.
All reactions