NOTICE: By continued use of this site you understand and agree to the binding Terms of Service and Privacy Policy.
// ==UserScript== // @name Ponycrush Smileybar // @namespace rainer-juergensen.de // @author Bastler // @version 0.0.2.3 // @description Adds a Smileybar to Ponycrush.com // @include https://ponycrush.com/* // @icon https://ponycrush.com/_/img/emotes/rainbowlaugh.png // @grant none // @license MIT // @run-at document-idle // ==/UserScript== /* * List of known smileys. Just add new ones here and they will get a button. */ var smileys = [{ code: " :D ", url: "https://ponycrush.com/_/img/emotes/pinkiehappy.png" }, { code: " :) ", url: "https://ponycrush.com/_/img/emotes/twilightsmile.png" }, { code: " ;) ", url: "https://ponycrush.com/_/img/emotes/raritywink.png" }, { code: " :P ", url: "https://ponycrush.com/_/img/emotes/rainbowwild.png" }, { code: " :lol: ", url: "https://ponycrush.com/_/img/emotes/rainbowlaugh.png" }, { code: " :insane: ", url: "https://ponycrush.com/_/img/emotes/pinkiecrazy.png" }, { code: " :blush: ", url: "https://ponycrush.com/_/img/emotes/twilightblush.png" }, //{code: " <3 ", url:"https://ponycrush.com/_/img/emotes/heart.png"}, { code: " :O ", url: "https://ponycrush.com/_/img/emotes/pinkiegasp.png" }, { code: " :smug: ", url: "https://ponycrush.com/_/img/emotes/ajsmug.png" }, { code: " :I ", url: "https://ponycrush.com/_/img/emotes/ajbemused.png" }, { code: " :/ ", url: "https://ponycrush.com/_/img/emotes/applejackunsure.png" }, { code: " :( ", url: "https://ponycrush.com/_/img/emotes/fluttersad.png" }, { code: " x( ", url: "https://ponycrush.com/_/img/emotes/twilightangry2.png" }, { code: " :V ", url: "https://ponycrush.com/_/img/emotes/pacman.png" }, { code: " :B ", url: "https://ponycrush.com/_/img/emotes/twistnerd.png" }, { code: " :awkward: ", url: "https://ponycrush.com/_/img/emotes/awkward.png" }, { code: " :awyeah: ", url: "https://ponycrush.com/_/img/emotes/awyeah.png" }, { code: " :blush2: ", url: "https://ponycrush.com/_/img/emotes/blush.png" }, { code: " :derp: ", url: "https://ponycrush.com/_/img/emotes/derp.png" }, { code: " :drool: ", url: "https://ponycrush.com/_/img/emotes/drool.png" }, { code: " :hmmph: ", url: "https://ponycrush.com/_/img/emotes/hmmph.png" }, { code: " :notamused: ", url: "https://ponycrush.com/_/img/emotes/notamused.png" }, { code: " :really: ", url: "https://ponycrush.com/_/img/emotes/really.png" }, { code: " :sad: ", url: "https://ponycrush.com/_/img/emotes/sad.png" }, { code: " :omg: ", url: "https://ponycrush.com/_/img/emotes/shocked.png" }, { code: " :smile: ", url: "https://ponycrush.com/_/img/emotes/smile.png" }, { code: " :stop: ", url: "https://ponycrush.com/_/img/emotes/stop.png" }, { code: " :tired: ", url: "https://ponycrush.com/_/img/emotes/tired.png" }, { code: " :wtf: ", url: "https://ponycrush.com/_/img/emotes/wtf.png" }, { code: " :yikes: ", url: "https://ponycrush.com/_/img/emotes/yikes.png" } ]; /* * This adds a insertAtCaret function to Input and TextArea elements. * Source: http://stackoverflow.com/a/19961519 */ HTMLInputElement.prototype.insertAtCaret = HTMLTextAreaElement.prototype.insertAtCaret = function (text) { text = text || ''; this.focus(); if (document.selection) { // IE var sel = document.selection.createRange(); sel.text = text; } else if (this.selectionStart || this.selectionStart === 0) { // Others var startPos = this.selectionStart; var endPos = this.selectionEnd; this.value = this.value.substring(0, startPos) + text + this.value.substring(endPos, this.value.length); this.selectionStart = startPos + text.length; this.selectionEnd = startPos + text.length; } else { this.value += text; } }; /* * This adds a insertAtCaret function to divs (for PMs/Discussions). * Source: http://stackoverflow.com/a/6691294 */ HTMLDivElement.prototype.insertAtCaret = function (html) { var sel, range; this.focus(); if (window.getSelection) { // IE9 and non-IE sel = window.getSelection(); if (sel.getRangeAt && sel.rangeCount) { range = sel.getRangeAt(0); range.deleteContents(); // Range.createContextualFragment() would be useful here but is // only relatively recently standardized and is not supported in // some browsers (IE9, for one) var el = document.createElement("div"); el.innerHTML = html; var frag = document.createDocumentFragment(), node, lastNode; while ((node = el.firstChild)) { lastNode = frag.appendChild(node); } range.insertNode(frag); // Preserve the selection if (lastNode) { range = range.cloneRange(); range.setStartAfter(lastNode); range.collapse(true); sel.removeAllRanges(); sel.addRange(range); } } } else if (document.selection && document.selection.type != "Control") { // IE < 9 document.selection.createRange().pasteHTML(html); } } /* * This function creates a function, * which adds sContent at the current caret to oTarget. */ function addSmiley(sContent, oTarget) { return function () { oTarget.insertAtCaret(sContent); } } /* * Creates the smileybar for the specific Input or TextArea (oTarget). */ function createSmileyBar(oTarget) { let oOut = document.createElement("DIV"); let iLen = smileys.length; let i; oOut.classList.add("btn-group"); for (i = 0; i < iLen; ++i) { let oButton = document.createElement("BUTTON"); let oImg = document.createElement("IMG"); oButton.title = smileys[i].code; oButton.classList.add("btn", "btn-default", "btn-sm", "btn-small"); oButton.tabIndex = "-1"; oButton.type = "button"; oButton.addEventListener("click", addSmiley(smileys[i].code, oTarget)); oImg.title = smileys[i].code; oImg.alt = smileys[i].code; oImg.classList.add("emote"); oImg.src = smileys[i].url; oButton.appendChild(oImg); oOut.appendChild(oButton); } return oOut; } /* * Adds smileybars to the website. */ function initTextArea() { //Discussions and PMs let oInputs = document.querySelectorAll(".note-editable"); let iAreLen = oInputs.length; for (let i = 0; i < iAreLen; ++i) { let oInput = oInputs[i]; let oBar = createSmileyBar(oInput); let oPanel = oInput.previousElementSibling.previousElementSibling; oPanel.appendChild(oBar); } //Horse Feed Main Input oInputs = document.querySelectorAll(".panel-body textarea"); iAreLen = oInputs.length; for (let i = 0; i < iAreLen; ++i) { let oInput = oInputs[i]; let oBar = createSmileyBar(oInput); let oSpacer = document.createElement("DIV"); oSpacer.classList.add("panel-body"); oSpacer.style.padding = "5px 5px 0 5px"; oSpacer.appendChild(oBar); let oBottomPanel = oInput.nextElementSibling; oBottomPanel.insertBefore(oSpacer, oBottomPanel.firstChild); } //Horse Feed Reply Input let oFeed = document.getElementsByClassName("wall-scroll"); if (oFeed.length > 0) { let observer = new MutationObserver(function (mutations) { mutations.forEach(function (mutation) { if (mutation.addedNodes !== undefined) { let iLen = mutation.addedNodes.length; for (let i = 0; i < iLen; ++i) { let note = mutation.addedNodes[i]; if (note.nodeType == Node.ELEMENT_NODE && note.className == "wall-item-replyform") { let oInput = note.firstChild.firstChild; let oBar = createSmileyBar(oInput); let oDiv = oInput.nextSibling; oBar.classList.add("text-left"); note.firstChild.insertBefore(oBar, oDiv); } } } }); }); observer.observe(oFeed[0], { childList: true, subtree: true }); } } initTextArea();