diff --git a/docs/guides/changes.md b/docs/guides/changes.md
index eb768651d..9fcf35284 100644
--- a/docs/guides/changes.md
+++ b/docs/guides/changes.md
@@ -14,7 +14,7 @@ Changes in Slate are designed to prioritize expressiveness above almost all else
If you're building a powerful editor, it's going to be somewhat complex, and you're going to be writing code to perform all different kinds of programmatic changes. You'll be removing nodes, inserting fragments, moving the selection around, etc.
-And if the API for changes was verbose, or if required lots of in between steps to be continually performed, your code would balloon to be impossible to understand very quickly.
+And if the API for changes was verbose, or if it required lots of in between steps to be continually performed, your code would balloon to be impossible to understand very quickly.
To solve this, Slate has very expressive, chainable changes. Like this:
@@ -33,9 +33,9 @@ change
Hopefully from reading that you can discern that those changes result in... the entire document's content being selected and deleted, some text bring written, a word being bolded, and finally an image block and a paragraph block being added.
-Of course you're not usually going to chain that much.
+Of course you're not usually going to chain that much.
-Point is, you can get pretty expressive in just a few lines of code.
+Point is, you can get pretty expressive in just a few lines of code.
That way, when you're scanning to see what behaviors are being triggered, you can understand your code easily. You don't have to sit there and try to parse out a bunch of interim variables to figure out what you're trying to achieve.
@@ -89,7 +89,7 @@ function onKeyDown(event, change, editor) {
}
```
-Any change methods you call will be applied, and when the event handler stack is finished resolving, the editor will automatically update with those changes.
+Any change methods you call will be applied, and when the event handler stack is finished resolving, the editor will automatically update with those changes.
### 2. From Custom Node Components
@@ -107,8 +107,8 @@ class Image extends React.Component {
}
render() {
-
}
@@ -178,7 +178,7 @@ function insertImage(change, src) {
}
```
-Notice how rewriting that image inserting logic multiple times without having it encapsulated in a single function would get tedious. Now with those change functions define, you can reuse them!
+Notice how rewriting that image inserting logic multiple times without having it encapsulated in a single function would get tedious. Now with those change functions defined, you can reuse them!
But sadly you can't chain with those functions directly, since `change` objects don't actually know about them. Instead, you use the `.call()` method:
diff --git a/docs/guides/data-model.md b/docs/guides/data-model.md
index c2ab891fb..d4c9e81ab 100644
--- a/docs/guides/data-model.md
+++ b/docs/guides/data-model.md
@@ -6,7 +6,7 @@ Slate is based on an immutable data model that closely resembles the DOM. When y
## Mirror the DOM
-One of the main principles of Slate is that it tries to mirror the native DOM API's as much as possible.
+One of the main principles of Slate is that it tries to mirror the native DOM API's as much as possible.
If you think about it, this makes sense. Slate is kind of like a nicer implementation of `contenteditable`, which itself is built with the DOM. And people use the DOM to represent documents with rich-text-like structures all the time. Mirroring the DOM helps make the library familiar for new users, and it lets us reuse battle-tested patterns without having to reinvent them ourselves.
@@ -30,12 +30,12 @@ But for updating values, you'll need to use the [`Immutable.Record` API](https:/
Collections of Slate objects are represented as immutable `Lists`, `Sets`, `Stacks`, etc. Which means we get nice support for expressive methods like `filter`, `includes`, `take`, `skip`, `rest`, `last`, etc.
-If you haven't used Immutable.js before, there is definitely a learning curve. Before you give into Slate, you should check out the [Immutable.js docs](https://facebook.github.io/immutable-js/docs/#/). Once you get the hang of it won't slow you down at all, but it will take a few days to get used to, and you might write things a little "un-performantly" to start.
+If you haven't used Immutable.js before, there is definitely a learning curve. Before you give into Slate, you should check out the [Immutable.js docs](https://facebook.github.io/immutable-js/docs/#/). Once you get the hang of it, it won't slow you down at all, but it will take a few days to get used to, and you might write things a little "un-performantly" to start.
## The "Value"
-The top-level object in Slate—the object encapsulates the entire value of an Slate editor—is called a [`Value`](../reference/slate/value.md).
+The top-level object in Slate—the object encapsulates the entire value of an Slate editor—is called a [`Value`](../reference/slate/value.md).
It is made up of a document filled with content, and a selection representing the user's current cursor selection. It also has a history, to keep track of changes, and a few other more advanced properties like `decorations` and `data`.
@@ -48,7 +48,7 @@ Slate documents are nested and recursive. This means that a document has block n
Unlike the DOM though, Slate enforces a few more restrictions on its documents, to reduce the complexity involved in manipulating them, and to prevent "impossible" situations from arising. These restrictions are:
-- **Documents can only contain block nodes as direct children.** This restriction mirrors how rich-text editors work, with the top-most elements being blocks that can be split when pressing enter enter.
+- **Documents can only contain block nodes as direct children.** This restriction mirrors how rich-text editors work, with the top-most elements being blocks that can be split when pressing enter.
- **Blocks can only contain either other block nodes, or inlines and text nodes.** This is another "sane" restriction that allows you to avoid lots of boilerplate `if` statements in your code. Blocks either wrap other blocks, or contain actual content.
@@ -56,11 +56,11 @@ Unlike the DOM though, Slate enforces a few more restrictions on its documents,
- **Inlines can't contain no text.** Any inline node whose text is an empty string (`''`) will be automatically removed. This makes sense when you think about a user backspacing through an inline. When they delete that last character, they'd expect the inline to be removed. And when there are no characters, you can't really put your selection into the inline anymore. So Slate removes them from the document automatically, to simplify things.
-- **Text nodes can't be adjacent to other text nodes.** Any two adjacent text nodes will automatically be merged into one. This prevents ambiguous case where a cursor could be at the end of one text node or at the start of the next. However, you can have an inline node surrounded by two texts.
+- **Text nodes can't be adjacent to other text nodes.** Any two adjacent text nodes will automatically be merged into one. This prevents ambiguous cases where a cursor could be at the end of one text node or at the start of the next. However, you can have an inline node surrounded by two texts.
- **Blocks and inlines must always contain at least one text node.** This is to ensure that the user's cursor can always "enter" the nodes, and to make sure that ranges can be created referencing them.
-Slate enforces all of these restrictions for you automatically. Any time you [perform changes](./changes.md) to the document, Slate will check if the document is invalid, and if so it will return it to a "normalized" value.
+Slate enforces all of these restrictions for you automatically. Any time you [perform changes](./changes.md) to the document, Slate will check if the document is invalid, and if so it will return it to a "normalized" value.
> 🙃 Fun fact: normalizing is actually based on the DOM's [`Node.normalize()`](https://developer.mozilla.org/en-US/docs/Web/API/Node/normalize)!
@@ -71,7 +71,7 @@ In addition to documents, blocks and inlines, Slate introduces one other type of
Marks are how Slate represents formatting data that is attached to the characters in the text itself—things like **bold**, _italic_, `code`, or even more complex formatting like comments.
-Although you can change styling based on either inlines or marks, marks differ form inlines in that they don't affect the structure of the nodes in the document, they simply attach themselves to the characters.
+Although you can change styling based on either inlines or marks, marks differ from inlines in that they don't affect the structure of the nodes in the document, they simply attach themselves to the characters.
This makes marks easier to reason about and easier to manipulate. Because inlines involve editing the document's structure, you have to worry about things like splitting any existing nodes, what their order in the hierarchy is, etc. Marks on the other hand can be applied to characters no matter how the characters are nested in the document. If you can express it as a `Range`, you can add marks to it.
@@ -89,7 +89,7 @@ Because the elements don't properly close themselves. Instead you have to write
text
```
-And if you happened to another overlapping section of `` to that text, you might have to rearrange the closing tags again. Rendering marks in Slate is similar—you can't guarantee that even though a word has one mark applied that that mark will be contiguous, because it depends on how it overlaps with other marks.
+And if you happened to add another overlapping section of `` to that text, you might have to rearrange the closing tags again. Rendering marks in Slate is similar—you can't guarantee that even though a word has one mark applied that that mark will be contiguous, because it depends on how it overlaps with other marks.
That all sounds pretty complex, but you don't have to think about it much, as long as you use marks and inlines for their intended purposes...
@@ -101,7 +101,7 @@ That all sounds pretty complex, but you don't have to think about it much, as lo
Just like in the DOM, you can reference a part of the document using a `Range`. And there's one special range that Slate keeps track of called the "selection" that refers to the user's current cursor selection.
-Ranges are defined by an "anchor" and "focus" point. The anchor is where the range starts, and the focus is where it ends. And each point is a combination of an "key" referencing a specific node, and an "offset". This ends up looking like this:
+Ranges are defined by an "anchor" and "focus" point. The anchor is where the range starts, and the focus is where it ends. And each point is a combination of a "key" referencing a specific node, and an "offset". This ends up looking like this:
```js
const range = Range.create({
@@ -115,14 +115,14 @@ const range = Range.create({
The more readable `node-a` name is just pseudocode, because Slate uses auto-incrementing numerical strings by default—`'1', '2', '3', ...` But the important part is that every node has a unique `key` property, and a range references nodes by their keys.
-The terms "anchor" and "focus" are borrowed from the DOM, where they mean the same thing. The anchor is where a range starts, and the focus is where it ends. However, be careful because the anchor point doesnt't always _before_ the focus point in the document. Just like in the DOM, it depends on whether the range is backwards or forwards.
+The terms "anchor" and "focus" are borrowed from the DOM, where they mean the same thing. The anchor is where a range starts, and the focus is where it ends. However, be careful because the anchor point isn't always _before_ the focus point in the document. Just like in the DOM, it depends on whether the range is backwards or forwards.
Here's how MDN explains it:
> A user may make a selection from left to right (in document order) or right to left (reverse of document order). The anchor is where the user began the selection and the focus is where the user ends the selection. If you make a selection with a desktop mouse, the anchor is placed where you pressed the mouse button and the focus is placed where you released the mouse button. Anchor and focus should not be confused with the start and end positions of a selection, since anchor can be placed before the focus or vice versa, depending on the direction you made your selection.
> — [`Selection`, MDN](https://developer.mozilla.org/en-US/docs/Web/API/Selection)
-To make dealing with ranges easier though, they also provide "start" and "end" properties that take whether the range is forward or backward into account. The `startKey` and `startOffset` will always before the `endKey` and `endOffset` in the document.
+To make dealing with ranges easier though, they also provide "start" and "end" properties that take whether the range is forward or backward into account. The `startKey` and `startOffset` will always be before the `endKey` and `endOffset` in the document.
One important thing to note is that the anchor and focus points of ranges **always reference the "leaf-most" text nodes**. They never reference blocks or inlines, always their child text nodes. This makes dealing with ranges a _lot_ easier.
diff --git a/docs/guides/plugins.md b/docs/guides/plugins.md
index 261849286..55527dffd 100644
--- a/docs/guides/plugins.md
+++ b/docs/guides/plugins.md
@@ -1,9 +1,9 @@
# Plugins
-With Slate, _all_ of your editor's logic is controlled by "plugins".
+With Slate, _all_ of your editor's logic is controlled by "plugins".
-Plugins have complete control over the schema, the behaviors, and the rendering of the editor—they can add any kind of functionality they want. So much so that even the core logic of Slate is provided via two "core" plugins.
+Plugins have complete control over the schema, the behaviors, and the rendering of the editor—they can add any kind of functionality they want. So much so that even the core logic of Slate is provided via two "core" plugins.
Slate encourages you to break up code into small, reusable modules that can be shared with others, and easily reasoned about.
@@ -29,14 +29,14 @@ Here's a really simple plugin:
}
```
-It focuses the editor and selects everything when it is clicked, and it blurs the editor what esc is pressed.
+It focuses the editor and selects everything when it is clicked, and it blurs the editor when esc is pressed.
Notice how it's able to define a set of behaviors that work together to form a single "feature" in the editor. That's what makes Slate's plugins a powerful form of encapsulation.
## The Plugins "Stack"
-Slate's editor takes a list of plugins as one of its arguments. We refer to this list as the plugins "stack". It is very similar to "middleware" from Express or Koa.
+Slate's editor takes a list of plugins as one of its arguments. We refer to this list as the plugins "stack". It is very similar to "middleware" from Express or Koa.
```js
const plugins = [
@@ -49,7 +49,7 @@ const plugins = [
/>
```
-When the editor needs to handle a DOM event, or to decide what to render, it will loop through the plugins stack, invoking each plugin in turn. Plugins can choose to handle the request, in which case the editor will break out of the loop. Or they can ignore it, and they will be skipped as the editor proceeds to the next plugin in the stack.
+When the editor needs to handle a DOM event, or decide what to render, it will loop through the plugins stack, invoking each plugin in turn. Plugins can choose to handle the request, in which case the editor will break out of the loop. Or they can ignore it, and they will be skipped as the editor proceeds to the next plugin in the stack.
Because of this looping, plugins are **order-sensitive**! This is very important. The earlier in the stack, the more preference the plugin has, since it can react before the others after it. If two plugins both try to handle the same event, the earlier plugin will "win".
@@ -58,7 +58,7 @@ Because of this looping, plugins are **order-sensitive**! This is very important
If you put Slate on the page without adding any of your own plugins, it will still behave like you'd expect a rich-text editor to. That's because it has its own "core" logic. And that core logic is implemented with its own core plugins.
-The core plugins doesn't have any assumptions about your schema, or what types of formatting you want to allow. But they do define the common editing behaviors like splitting the current block when enter is pressed, or inserting a string of text when the user pastes from their clipboard.
+The core plugins doesn't have any assumptions about your schema, or what types of formatting you want to allow. But they do define common editing behaviors like splitting the current block when enter is pressed, or inserting a string of text when the user pastes from their clipboard.
These are behaviors that all rich-text editors exhibit, and that don't make sense for userland to have to re-invent for every new editor.
@@ -71,7 +71,7 @@ _To learn more, check out the [Core Plugin reference](../reference/slate-react/c
## The "Editor" Plugin
-If you've read through the [`` reference](../reference/slate-react/editor.md) you'll notice that the editor itself has handler like `onKeyDown`, `onClick`, etc. just like plugins.
+If you've read through the [`` reference](../reference/slate-react/editor.md) you'll notice that the editor itself has handlers like `onKeyDown`, `onClick`, etc. just like plugins.
```js
const plugins = [
@@ -138,7 +138,7 @@ const plugins = [
]
```
-These types of plugins are critical to keeping your code maintainable. And they're good candidates for open-sourcing for others to use. A few examples of plugins like this in the wild are [`slate-auto-replace`](https://github.com/ianstormtaylor/slate-auto-replace), [`slate-prism`](https://github.com/GitbookIO/slate-prism), [`slate-collapse-on-escape`](https://github.com/ianstormtaylor/slate-collapse-on-escape), etc.
+These types of plugins are critical to keeping your code maintainable. And they're good candidates for open-sourcing for others to use. A few examples of plugins like this in the wild are [`slate-auto-replace`](https://github.com/ianstormtaylor/slate-auto-replace), [`slate-prism`](https://github.com/GitbookIO/slate-prism), [`slate-collapse-on-escape`](https://github.com/ianstormtaylor/slate-collapse-on-escape), etc.
There's almost no piece of logic too small to abstract out and share, as long as it's reusable.
@@ -146,11 +146,11 @@ But hotkey binding logic by itself isn't a "feature". It's just a small helper t
### Feature Plugins
-Feature plugins are much larger in scope, and serve to define an entire series of behaviors that make up a single "feature" in your editor. They're not as concrete as util plugins, but they make reasoning about complex editors much simple.
+Feature plugins are much larger in scope, and serve to define an entire series of behaviors that make up a single "feature" in your editor. They're not as concrete as util plugins, but they make reasoning about complex editors much simpler.
For example, you maybe decide you want to allow **bold** formatting in your editor. To do that, you need a handful of different behaviors.
-You could just have a single, long `plugins.js` file that contained all of the plugins for all of the features in your editor. But figuring out what was going on in that file would get confusing very quickly.
+You could just have a single, long `plugins.js` file that contained all of the plugins for all of the features in your editor. But figuring out what was going on in that file would get confusing very quickly.
Instead, it can help to split up your plugins into features. So you might have a `bold.js`, `italic.js`, `images.js`, etc. Your bold plugin might look like...
@@ -223,7 +223,7 @@ That said, there might be another type of plugins that kind of straddle the line
These are plugins that bundle up a set of logic, similar to how a feature might, but in a way that is re-usable across codebases. Some examples of these would be [`slate-edit-code`](https://github.com/GitbookIO/slate-edit-code), [`slate-edit-list`](https://github.com/GitbookIO/slate-edit-list), [`slate-edit-table`](https://github.com/GitbookIO/slate-edit-table), etc.
-Framework plugins will often expose objects with `changes`, `helpers` and `plugins` instead of simple array. Or, they may choose to just augment a single returned plugin object with some of the other exports.
+Framework plugins will often expose objects with `changes`, `helpers` and `plugins` instead of a simple array. Or, they may choose to just augment a single returned plugin object with some of the other exports.
You'll often want to encapsulate framework plugins in your own feature plugins, but they can go a long way in terms of reducing your codebase size.
@@ -236,7 +236,7 @@ If you think of another good pattern, feel free to pull request it!
### Write Plugins as Functions
-You should always write plugins as functions that take `options`.
+You should always write plugins as functions that take `options`.
```js
function YourPlugin(options) {
@@ -272,7 +272,7 @@ function YourBoldPlugin(options) {
### Accept Change Functions
-It's common for a helper plugins to want to make some change based on an event that is triggered by the user. For example, when you want to write a plugin that adds a mark when a hotkey is pressed.
+It's common for helper plugins to want to make some change based on an event that is triggered by the user. For example, when you want to write a plugin that adds a mark when a hotkey is pressed.
If you write this in the naive way as taking a mark `type` string, users won't be able to add data associated with the mark in more complex cases. And if you accept a string or an object, what happens if the user wants to actually add two marks at once, or perform some other piece of logic. You'll have to keep adding esoteric options which make the plugin hard to maintain.
@@ -313,4 +313,3 @@ const plugins = [
})
]
```
-
diff --git a/docs/guides/rendering.md b/docs/guides/rendering.md
index 73dbac0dd..ae03d8ded 100644
--- a/docs/guides/rendering.md
+++ b/docs/guides/rendering.md
@@ -3,14 +3,14 @@
One of the best parts of Slate is that it's built with React, so it fits right into your existing application. It doesn't re-invent its own view layer that you have to learn. It tries to keep everything as React-y as possible.
-To that end, Slate gives you control over the rendering behavior of every node and mark in your document, any placeholders you want to render, and even the top-level editor itself.
+To that end, Slate gives you control over the rendering behavior of every node and mark in your document, any placeholders you want to render, and even the top-level editor itself.
You can define these behaviors by passing `props` into the editor, or you can define them in Slate plugins.
## Nodes & Marks
-Using custom components for the nodes and marks is the most common rendering need. Slate makes this easy to do, you just define a `renderNode` function.
+Using custom components for the nodes and marks is the most common rendering need. Slate makes this easy to do, you just define a `renderNode` function.
The function is called with the node's props, including `props.node` which is the node itself. You can use these to determine what to render. For example, you can render nodes using simple HTML elements:
@@ -29,9 +29,9 @@ function renderNode(props) {
}
```
-> 🤖 Be sure to mix in `props.attributes` and render `props.children` in your node components! The attributes required for utilities like Slate's `findDOMNode`, and the children are the actual text content of your nodes.
+> 🤖 Be sure to mix in `props.attributes` and render `props.children` in your node components! The attributes are required for utilities like Slate's `findDOMNode`, and the children are the actual text content of your nodes.
-Or course, you don't have to use simple HTML elements, you can use your own custom React components too:
+You don't have to use simple HTML elements, you can use your own custom React components too:
```js
function renderNode(props) {
@@ -99,7 +99,7 @@ function renderPlaceholder(props) {
if (node.text != '') return
return (
-
@@ -119,7 +119,7 @@ That will render a simple placeholder element inside all of the your `caption` b
## The Editor Itself
-Not only can you control the rendering behavior of the components inside the editor, but you can also control the rendering of the editor itself.
+Not only can you control the rendering behavior of the components inside the editor, but you can also control the rendering of the editor itself.
This sounds weird, but it can be pretty useful if you want to render additional top-level elements from inside a plugin. To do so, you use the `renderEditor` function:
@@ -143,6 +143,6 @@ function renderEditor(props) {
Here we're rendering a small word count number underneath all of the content of the editor. Whenever you change the content of the editor, `renderEditor` will be called, and the word count will be updated.
-This is very similar to how higher-order components work! Except it allows each plugin in Slate's plugin stack to add to wrap the editor's children.
+This is very similar to how higher-order components work! Except it allows each plugin in Slate's plugin stack to wrap the editor's children.
> 🤖 Be sure to remember to render `children` in your `renderEditor` functions, because that contains the editor's own elements!
diff --git a/docs/guides/schemas.md b/docs/guides/schemas.md
index abe7c9449..05a6ee7ff 100644
--- a/docs/guides/schemas.md
+++ b/docs/guides/schemas.md
@@ -39,7 +39,7 @@ const schema = {
> 🤖 Internally, Slate instantiates schemas as immutable `Schema` models, but you don't have to worry about that. In user-land schemas can always be defined as plain Javascript objects, and you can let Slate handle the rest.
-Hopefully just by reading this definition you'll understand what kinds of blocks are allowed in the document and what properties they can have—schemas are designed to prioritize legibility.
+Hopefully just by reading this definition you'll understand what kinds of blocks are allowed in the document and what properties they can have—schemas are designed to prioritize legibility.
This schema defines a document that only allows `paragraph` and `image` blocks. In the case of `paragraph` blocks, they can only contain text nodes. And in the case of `image` blocks, they are always void nodes with a `data.src` property that is a URL. Simple enough, right?
@@ -76,7 +76,7 @@ const schema = {
That's an example of defining your own custom `normalize` option for the document validation. If the invalid reason is `child_type_invalid`, it will set the child to be a `paragraph`.
-When Slate discovers and invalid child, it will first check to see if your custom normalizer handles that case, and if it does Slate won't do any of its default behavior. That way you can opt-in to customizing the normalization logic for specific cases, without having to re-implement all of the defaults yourself.
+When Slate discovers an invalid child, it will first check to see if your custom normalizer handles that case, and if it does Slate won't do any of its default behavior. That way you can opt-in to customizing the normalization logic for specific cases, without having to re-implement all of the defaults yourself.
This gives you the best of both worlds. You can write simple, terse, declarative validation rules that can be highly optimized. But you can still define fine-grained, imperative normalization logic for when invalid states occur.
@@ -89,7 +89,7 @@ Sometimes though, the declarative validation syntax isn't fine-grained enough to
> 🤖 Actually, under the covers the declarative schemas are all translated into `validateNode` functions too!
-When you define a `validateNode` function, you either return nothing if ths node's already valid, or you return a normalizer function that will make the node valid if it isn't. Here's an example:
+When you define a `validateNode` function, you either return nothing if the node's already valid, or you return a normalizer function that will make the node valid if it isn't. Here's an example:
```js
function validateNode(node) {