From dc3c4e9a98a5ed3a1f26a7a7ef9b52ed11fbb56a Mon Sep 17 00:00:00 2001 From: Menshikov Alexander Date: Sat, 2 Jul 2016 15:30:59 +0300 Subject: [PATCH 1/4] Link plugin backend (#64) * Server meta-getter * Add url and url-text parsing * Url parsing * Add timeouts * Add user-agent field --- server/index.php | 96 ++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 96 insertions(+) create mode 100644 server/index.php diff --git a/server/index.php b/server/index.php new file mode 100644 index 00000000..4e803f04 --- /dev/null +++ b/server/index.php @@ -0,0 +1,96 @@ +loadHTML($html); + $nodes = $doc->getElementsByTagName('title'); + + $title = $nodes->item(0)->nodeValue; + $description = ""; + $keywords = ""; + $image = ""; + + $metas = $doc->getElementsByTagName('meta'); + + for ($i = 0; $i < $metas->length; $i++) + { + $meta = $metas->item($i); + if($meta->getAttribute('name') == 'description') + $description = $meta->getAttribute('content'); + if($meta->getAttribute('name') == 'keywords') + $keywords = $meta->getAttribute('content'); + if($meta->getAttribute('property')=='og:image'){ + $image = $meta->getAttribute('content'); + } + } + + return [ + 'image' => $image, + 'title' => $title, + 'description' => $description + ]; +} + +$url = get_url(); + +$url_params = parse_url($url); + +if (!$url) +{ + exit(0); +} + +$html = file_get_contents_curl($url); + +$result = get_meta_from_html($html); + +$result = array_merge( + + get_meta_from_html($html), + + array( + 'linkUrl' => $url, + 'linkText' => $url_params["host"] . $url_params["path"], + ) + +); + +echo json_encode($result); + +?> \ No newline at end of file From a70a9831ebc9f6fb0ca4bbb78c5df199c29c31eb Mon Sep 17 00:00:00 2001 From: Menshikov Alexander Date: Sat, 2 Jul 2016 15:36:47 +0300 Subject: [PATCH 2/4] Link plugin frontend (#63) * Implement link download by enter press * Change promise structure * Fix promises fetch * Server meta-getter * Change keyEnterCode to ENTER_KEY * Add url and url-text parsing * Attached loader * Loader gif * Remove a fish :D --- example.html | 7 +- .../ceditor-tool-link.css | 8 ++ .../ceditor-tool-link.js | 79 +++++++++++++----- plugins/ceditor-tool-link/loading.gif | Bin 0 -> 329 bytes server/index.php | 1 - 5 files changed, 68 insertions(+), 27 deletions(-) rename plugins/{ => ceditor-tool-link}/ceditor-tool-link.css (90%) rename plugins/{ => ceditor-tool-link}/ceditor-tool-link.js (73%) create mode 100644 plugins/ceditor-tool-link/loading.gif diff --git a/example.html b/example.html index f3165bf3..99bc0800 100644 --- a/example.html +++ b/example.html @@ -20,6 +20,7 @@ font-size: 2em; } + @@ -265,8 +266,8 @@ - - + + - \ No newline at end of file + diff --git a/plugins/ceditor-tool-link.css b/plugins/ceditor-tool-link/ceditor-tool-link.css similarity index 90% rename from plugins/ceditor-tool-link.css rename to plugins/ceditor-tool-link/ceditor-tool-link.css index 330dc089..f771837e 100644 --- a/plugins/ceditor-tool-link.css +++ b/plugins/ceditor-tool-link/ceditor-tool-link.css @@ -11,6 +11,7 @@ outline: none; border: 0; width: 100%; + background: transparent; } .tool-link-panel { @@ -57,3 +58,10 @@ text-decoration: none; color: rgba(165,156,86,.8); } + +.tool-link-loader { + + background: url("loading.gif") !important; + opacity: 0.1; + +} \ No newline at end of file diff --git a/plugins/ceditor-tool-link.js b/plugins/ceditor-tool-link/ceditor-tool-link.js similarity index 73% rename from plugins/ceditor-tool-link.js rename to plugins/ceditor-tool-link/ceditor-tool-link.js index c4c26b12..78012cf3 100644 --- a/plugins/ceditor-tool-link.js +++ b/plugins/ceditor-tool-link/ceditor-tool-link.js @@ -8,13 +8,16 @@ var linkTool = { defaultText : 'Insert link here ...', + ENTER_KEY : 13, + currentBlock : null, currentInput : null, elementClasses : { link : "tool-link-link", image : "tool-link-image", title : "tool-link-title", - description : "tool-link-description" + description : "tool-link-description", + loader : "tool-link-loader" }, /** @@ -36,6 +39,8 @@ var linkTool = { tag.addEventListener('paste', linkTool.blockPasteCallback, false); + tag.addEventListener('keydown', linkTool.blockKeyDownCallback, false); + return wrapper; }, @@ -82,19 +87,47 @@ var linkTool = { blockPasteCallback : function (event) { - clipboardData = event.clipboardData || window.clipboardData; + var clipboardData = event.clipboardData || window.clipboardData, + pastedData = clipboardData.getData('Text'), + block = event.target.parentNode; - pastedData = clipboardData.getData('Text'); + linkTool.renderLink(pastedData, block); - var block = event.target.parentNode; + event.stopPropagation(); + + }, + + blockKeyDownCallback : function (event) { + + if (event.keyCode == linkTool.ENTER_KEY) { + + var inputTag = event.target, + block = inputTag.parentNode, + url = inputTag.value; + + linkTool.renderLink(url, block); + + event.preventDefault(); + + } + + }, + + renderLink : function (url, block) { Promise.resolve() .then(function () { - return linkTool.urlify(pastedData) + return linkTool.urlify(url) }) - .then(fetch('http://ajax.ru/link')) + .then(function (url) { + + /* Show loader gif **/ + block.classList.add(linkTool.elementClasses.loader); + + return fetch('/server/?url=' + encodeURI(url)); + }) .then(function (response) { @@ -105,13 +138,7 @@ var linkTool = { } else { - return { - 'linkUrl' : 'http://yandex.ru', - 'linkText' : 'yandex.ru', - 'image' : 'https://yastatic.net/morda-logo/i/apple-touch-icon/ru-76x76.png', - 'title' : 'Яндекс', - 'description' : 'Сайт, поисковик, проч.' - }; + return Error("Invalid response status: %o", response); } @@ -122,6 +149,10 @@ var linkTool = { }) .catch(function(error) { + + /* Hide loader gif **/ + block.classList.remove(linkTool.elementClasses.loader); + cEditor.core.log('Error while doing things with link paste: %o', 'error', error); }); @@ -137,7 +168,7 @@ var linkTool = { return links[0]; } - return null; + return Promise.reject(Error("Url is not matched")); }, @@ -155,6 +186,8 @@ var linkTool = { currentBlock.appendChild(previewBlock); + currentBlock.classList.remove(linkTool.elementClasses.loader); + } }; @@ -164,7 +197,7 @@ linkTool.ui = { make : function (json) { var wrapper = this.wrapper(), - siteImage = this.image(json.image), + siteImage = this.image(json.image, linkTool.elementClasses.image), siteTitle = this.title(json.title), siteDescription = this.description(json.description), siteLink = this.link(json.linkUrl, json.linkText); @@ -190,15 +223,15 @@ linkTool.ui = { input : function () { - var inpitTag = document.createElement('input'); + var inputTag = document.createElement('input'); - inpitTag.classList += "ceditor-tool-link-input"; + inputTag.classList += "ceditor-tool-link-input"; - inpitTag.placeholder = linkTool.defaultText; + inputTag.placeholder = linkTool.defaultText; - inpitTag.contentEditable = false; + inputTag.contentEditable = false; - return inpitTag; + return inputTag; }, @@ -212,11 +245,11 @@ linkTool.ui = { }, - image : function (imageSrc) { + image : function (imageSrc, imageClass) { var imageTag = document.createElement('img'); - imageTag.classList += linkTool.elementClasses.image; + imageTag.classList += imageClass; imageTag.setAttribute('src', imageSrc); @@ -260,7 +293,7 @@ linkTool.ui = { descriptionTag.innerHTML = descriptionText; return descriptionTag; - } + }, }; diff --git a/plugins/ceditor-tool-link/loading.gif b/plugins/ceditor-tool-link/loading.gif new file mode 100644 index 0000000000000000000000000000000000000000..72ea7ccb5321d5384d70437cfaac73011237901e GIT binary patch literal 329 zcmZ?wbhEHb9b#5NV>2k zBC~b@b~P=nNfWAe-b%_i6tS^-1y(h@EsB~1TqDA_h@fkxG$bHgvj}VxE1JLgr!*!^ ILUxTc0Q$^Q5C8xG literal 0 HcmV?d00001 diff --git a/server/index.php b/server/index.php index 4e803f04..c70ec8a5 100644 --- a/server/index.php +++ b/server/index.php @@ -12,7 +12,6 @@ function file_get_contents_curl($url) curl_setopt($ch, CURLOPT_TIMEOUT, 10); curl_setopt($ch,CURLOPT_USERAGENT,'Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/51.0.2704.103 Safari/537.36'); - $data = curl_exec($ch); curl_close($ch); From 10c025a502d4c5765a9fc4f47a64fe352dfc4540 Mon Sep 17 00:00:00 2001 From: Menshikov Alexander Date: Sat, 2 Jul 2016 16:39:08 +0300 Subject: [PATCH 3/4] Add error background (#66) --- plugins/ceditor-tool-link/ceditor-tool-link.css | 16 ++++++++++++++++ plugins/ceditor-tool-link/ceditor-tool-link.js | 17 +++++++++++++---- 2 files changed, 29 insertions(+), 4 deletions(-) diff --git a/plugins/ceditor-tool-link/ceditor-tool-link.css b/plugins/ceditor-tool-link/ceditor-tool-link.css index f771837e..6ef9e80f 100644 --- a/plugins/ceditor-tool-link/ceditor-tool-link.css +++ b/plugins/ceditor-tool-link/ceditor-tool-link.css @@ -12,6 +12,9 @@ border: 0; width: 100%; background: transparent; + font-size: 1em; + padding: 12px; + transition: background 200ms; } .tool-link-panel { @@ -64,4 +67,17 @@ background: url("loading.gif") !important; opacity: 0.1; +} + +.tool-link-error { + + /*background: repeating-linear-gradient(*/ + /*45deg,*/ + /*#bc320e,*/ + /*#606dbc 10px,*/ + /*#465298 10px,*/ + /*#465298 20px*/ + /*);*/ + background: rgba(255, 0, 0, 0.9); + } \ No newline at end of file diff --git a/plugins/ceditor-tool-link/ceditor-tool-link.js b/plugins/ceditor-tool-link/ceditor-tool-link.js index 78012cf3..568fb829 100644 --- a/plugins/ceditor-tool-link/ceditor-tool-link.js +++ b/plugins/ceditor-tool-link/ceditor-tool-link.js @@ -17,7 +17,8 @@ var linkTool = { image : "tool-link-image", title : "tool-link-title", description : "tool-link-description", - loader : "tool-link-loader" + loader : "tool-link-loader", + error : "tool-link-error" }, /** @@ -99,11 +100,17 @@ var linkTool = { blockKeyDownCallback : function (event) { + var inputTag = event.target, + block = inputTag.parentNode; + + if (block.classList.contains(linkTool.elementClasses.error)) + { + block.classList.remove(linkTool.elementClasses.error) + } + if (event.keyCode == linkTool.ENTER_KEY) { - var inputTag = event.target, - block = inputTag.parentNode, - url = inputTag.value; + var url = inputTag.value; linkTool.renderLink(url, block); @@ -153,6 +160,8 @@ var linkTool = { /* Hide loader gif **/ block.classList.remove(linkTool.elementClasses.loader); + block.classList.add(linkTool.elementClasses.error); + cEditor.core.log('Error while doing things with link paste: %o', 'error', error); }); From b25ba148cc83d03f14678ff36c49ab973dcce5c4 Mon Sep 17 00:00:00 2001 From: Peter Savchenko Date: Sat, 2 Jul 2016 17:36:36 +0300 Subject: [PATCH 4/4] arrow up and left buttons callback update --- codex-editor.js | 68 ++++++++++++++++++++++++++++++------------------- example.html | 2 +- 2 files changed, 43 insertions(+), 27 deletions(-) diff --git a/codex-editor.js b/codex-editor.js index 144ccf60..0cbbcfa9 100644 --- a/codex-editor.js +++ b/codex-editor.js @@ -722,6 +722,13 @@ cEditor.callback = { return false; } + /** + * LEFT or UP not at the beginning + */ + if ( selection.anchorOffset !== 0) { + return false; + } + /** Saving caret after keydown event happend */ cEditor.caret.save(); @@ -732,37 +739,43 @@ cEditor.callback = { } /** - * Find deepest child node - * Iterate child nodes and find First DEEPEST node - * We need it to check caret positon (it must be at the begining) + * Do nothing if caret is not at the beginning of first child */ - focusedNodeHolder = focusedNodeHolder || focusedNode; + var caretInFirstChild = false, + caretAtTheBeginning = false; - if (focusedNodeHolder.childNodes.length !== 0) { + var editableElement = focusedNode.querySelector('[contenteditable]'), + firstChild, + deepestTextnode; - var focusedTextNode = ''; - - if (focusedNodeHolder.childNodes){ - /** Looking from the first child */ - focusedTextNode = cEditor.content.getDeepestTextNodeFromPosition(focusedNodeHolder, 0); - } - } - /** - * When we click "UP" or "LEFT", caret behaviour is as default. - * We should check caret position before we transmit/switch the block. - */ - if ( selection.anchorOffset !== 0) { - return false; - } - - /** - * We can't switch block till caret is not at the begining of first node and has zero offset - */ - if ( (cEditor.caret.offset !== 0 || cEditor.caret.focusedNodeIndex !== 0) && focusedNodeHolder.childNodes.length !== 0 ) { + if (!editableElement) { + cEditor.core.log('Can not find editable element in current block: %o', 'warn', focusedNode); return; } - cEditor.caret.setToPreviousBlock(block); + firstChild = editableElement.childNodes[0]; + + if (cEditor.core.isDomNode(firstChild)) { + + deepestTextnode = cEditor.content.getDeepestTextNodeFromPosition(firstChild, 0); + + } else { + + deepestTextnode = firstChild; + + } + + caretInFirstChild = selection.anchorNode == deepestTextnode; + caretAtTheBeginning = cEditor.caret.offset === 0; + + console.log("каретка в первом узле: %o", caretInFirstChild); + console.log("каретка в начале первого узла: %o", caretAtTheBeginning); + + if ( caretInFirstChild && caretAtTheBeginning ) { + + cEditor.caret.setToPreviousBlock(focusedNode); + + } }, @@ -1290,7 +1303,7 @@ cEditor.caret = { console.log("nextBlock: %o", nextBlock); - nextBlockEditableElement = nextBlock.querySelector('[contenteditable], [contenteditable="true"]'); + nextBlockEditableElement = nextBlock.querySelector('[contenteditable]'); console.log("nextBlockEditableElement: %o", nextBlockEditableElement); @@ -1304,6 +1317,9 @@ cEditor.caret = { cEditor.content.workingNodeChanged(block.nextSibling); }, + /** + * @todo передалать на prevBlock.querySelector('[contenteditable]') по аналогии с setToNextBlock + */ setToPreviousBlock : function(block) { if ( !block.previousSibling ) { diff --git a/example.html b/example.html index 99bc0800..d6403fee 100644 --- a/example.html +++ b/example.html @@ -166,7 +166,7 @@ link : { 'linkUrl' : 'http://google.com', 'linkText' : 'google.com', - 'image' : 'http://i1.kym-cdn.com/photos/images/facebook/000/002/110/longcat.jpg', + 'image' : 'http://2.bp.blogspot.com/-7bZ5EziliZQ/VynIS9F7OAI/AAAAAAAASQ0/BJFntXCAntstZe6hQuo5KTrhi5Dyz9yHgCK4B/s1600/googlelogo_color_200x200.png', 'title' : 'Google', 'description' : 'Поисковик, поисковик, проч.' }