1
0
mirror of https://github.com/ianstormtaylor/slate.git synced 2025-09-02 19:52:32 +02:00

add start of image example

This commit is contained in:
Ian Storm Taylor
2016-06-28 18:26:56 -07:00
parent d5f0a55515
commit 78a902d7a0
9 changed files with 289 additions and 10 deletions

172
examples/images/index.js Normal file
View File

@@ -0,0 +1,172 @@
import Editor, { Mark, Raw } from '../..'
import React from 'react'
import ReactDOM from 'react-dom'
import state from './state.json'
import { Map } from 'immutable'
/**
* The images example.
*
* @type {Component} Images
*/
class Images extends React.Component {
state = {
state: Raw.deserialize(state)
};
/**
* Insert an image with `src` at the current selection.
*
* @param {String} src
*/
insertImage(src) {
let { state } = this.state
if (state.isExpanded) {
state = state
.transform()
.delete()
.apply()
}
const { anchorBlock, selection } = state
if (anchorBlock.text == '') {
state = state
.transform()
.setBlock('image', { src })
.apply()
}
else if (selection.isAtEndOf(anchorBlock)) {
state = state
.transform()
.splitBlock()
.setBlock('image', { src })
.apply()
}
else if (selection.isAtStartOf(anchorBlock)) {
state = state
.transform()
.splitBlock()
.moveToStartOfPreviousBlock()
.setBlock('image', { src })
.apply()
}
else {
state = state
.transform()
.splitBlock()
.splitBlock()
.moveToStartOfPreviousBlock()
.setBlock('image', { src })
.apply()
}
this.setState({ state })
}
/**
* On clicking the image button, prompt for an image and insert it.
*
* @param {Event} e
*/
onClickImage(e) {
e.preventDefault()
const src = window.prompt('Enter the URL of the image:')
if (!src) return
this.insertImage(src)
}
/**
* Render the app.
*
* @return {Element} element
*/
render() {
return (
<div>
{this.renderToolbar()}
{this.renderEditor()}
</div>
)
}
/**
* Render the toolbar.
*
* @return {Element} element
*/
renderToolbar() {
return (
<div className="menu toolbar-menu">
<span className="button" onMouseDown={e => this.onClickImage(e)}>
<span className="material-icons">image</span>
</span>
</div>
)
}
/**
* Render the editor.
*
* @return {Element} element
*/
renderEditor() {
return (
<div className="editor">
<Editor
state={this.state.state}
renderNode={node => this.renderNode(node)}
onChange={(state) => {
console.groupCollapsed('Change!')
console.log('Document:', state.document.toJS())
console.log('Selection:', state.selection.toJS())
console.log('Content:', Raw.serialize(state))
console.groupEnd()
this.setState({ state })
}}
/>
</div>
)
}
/**
* Render our custom `node`.
*
* @param {Node} node
* @return {Element} element
*/
renderNode(node) {
switch (node.type) {
case 'image': {
return (props) => {
const { data } = props.node
const src = data.get('src')
return <img src={src} />
}
}
case 'paragraph': {
return (props) => <p>{props.children}</p>
}
}
}
}
/**
* Export.
*/
export default Images

View File

@@ -0,0 +1,49 @@
{
"nodes": [
{
"kind": "block",
"type": "paragraph",
"nodes": [
{
"kind": "text",
"ranges": [
{
"text": "In addition to nodes that contain editable text, you can also create other types of nodes, like images or videos."
},
]
}
]
},
{
"kind": "block",
"type": "image",
"data": {
"src": "https://img.washingtonpost.com/wp-apps/imrs.php?src=https://img.washingtonpost.com/news/speaking-of-science/wp-content/uploads/sites/36/2015/10/as12-49-7278-1024x1024.jpg&w=1484"
},
"nodes": [
{
"kind": "text",
"ranges": [
{
"text": ""
}
]
}
]
},
{
"kind": "block",
"type": "paragraph",
"nodes": [
{
"kind": "text",
"ranges": [
{
"text": "This example shows images in action. It features two ways to add images. You can either add an image via the toolbar icon above, or if you want in on a little secret, copy an image URL to your keyboard and paste it anywhere in the editor!"
}
]
}
]
}
]
}