-
-
Save lawso017/44df47968be36222b874b8c4d94b779b to your computer and use it in GitHub Desktop.
window.addEventListener "trix-initialize", (e) => | |
Utility.TrixMentions.prepare($(e.target)) |
# Filter for use with https://github.com/jch/html-pipeline | |
# to extract mentioned user_ids | |
module HTML | |
class Pipeline | |
class TrixMentionFilter < Filter | |
attr_reader :mentioned_user_ids | |
def initialize(doc, context = nil, result = nil) | |
super doc, context, result | |
@mentioned_user_ids = [] | |
end | |
def call | |
process_attachments! do |attachment| | |
@mentioned_user_ids << attachment["user-id"].to_i | |
end | |
doc | |
end | |
def process_attachments! | |
doc.css("[data-trix-attachment]").each do |attachment_node| | |
attachment = JSON.parse(attachment_node.attribute('data-trix-attachment')) | |
next unless attachment["attachment-type"] == "trix-mention" | |
yield attachment | |
end | |
end | |
end | |
end | |
end |
window.Utility ||= {} | |
class Utility.TrixMentions | |
MENTIONS_PATH = "mentions-path" | |
MENTIONS_DIV_ID = "#trix-mentions-" | |
MENTIONS_INPUT_ID = MENTIONS_DIV_ID + "input-" | |
@prepare: ($trix) -> | |
mentionsDivForTrix = ($trix) -> | |
$(MENTIONS_DIV_ID + $trix.attr('trix-id')) | |
mentionsInputForTrix = ($trix) -> | |
$(MENTIONS_INPUT_ID + $trix.attr('trix-id')) | |
mentionsSelectizeForTrix = ($trix) -> | |
mentionsInputForTrix($trix).next('.selectize-control') | |
mentionsSelectizeDropdownForTrix = ($trix) -> | |
mentionsInputForTrix($trix).next('.selectize-dropdown') | |
createMentionsDivForTrix = ($trix) -> | |
$trix.after("<trix-mentions id='trix-mentions-"+ $trix.attr('trix-id') + "'><input id='trix-mentions-input-" + $trix.attr('trix-id') + "'></input></trix-mentions>") | |
initializeMentionsSelectize = ($trix) -> | |
$.getJSON $trix.data(MENTIONS_PATH), (result) -> | |
mentionsInputForTrix($trix).selectize | |
create: false | |
valueField: 'id' | |
labelField: 'name' | |
searchField: 'name' | |
sortField: 'name' | |
options: result.data | |
selectOnTab: true | |
onInitialize: -> | |
@.disable() | |
mentionsSelectizeForTrix($trix).css('left', -1000) | |
onItemAdd: (value, $item) -> | |
embed = "<span class='trix-mention'>@" + $item.text() + "</span>" | |
attachment = new Trix.Attachment | |
content: embed | |
'attachment-type': 'trix-mention' | |
'user-id': $item.data('value') | |
$trix[0].editor.setSelectedRange([$trix.data('last-position') - 1, $trix.data('last-position')]) | |
$trix[0].editor.deleteInDirection('forward') | |
$trix[0].editor.insertAttachment attachment | |
mentionsDivForTrix($trix).hide() | |
onBlur: -> | |
mentionsDivForTrix($trix).hide() | |
@.disable() | |
mentionsSelectizeForTrix($trix).css('left', -1000) | |
$trix.focus() | |
if @.items.length == 0 | |
$trix[0].editor.setSelectedRange([$trix.data('last-position') - 1, $trix.data('last-position')]) | |
$trix[0].editor.deleteInDirection('forward') | |
onDropdownClose: -> | |
mentionsDivForTrix($trix).hide() | |
onDropdownOpen: ($dropdown) -> | |
rect = $trix[0].editor.getClientRectAtPosition($trix[0].editor.getPosition()) | |
if rect != undefined | |
$dropdown.css('top', 34) | |
if rect.left + 200 > $trix.offset().left + $trix.width() | |
$dropdown.css('left', $trix.offset().left + $trix.width() - (rect.left + 210)) | |
onType: (str) -> | |
rect = $trix[0].editor.getClientRectAtPosition($trix[0].editor.getPosition()) | |
if rect.left + 200 > $trix.offset().left + $trix.width() | |
mentionsSelectizeDropdownForTrix($trix).css('left', $trix.offset().left + $trix.width() - (rect.left + 210)) | |
openMentionsSelectize = ($trix, editor) -> | |
$trix.data 'last-position', editor.getPosition() | |
mentionsInput = mentionsInputForTrix($trix) | |
mentionsSelectize = mentionsSelectizeForTrix($trix) | |
rect = editor.getClientRectAtPosition(editor.getPosition()) | |
mentionsSelectize.css('left', rect.left - 10) | |
mentionsSelectize.css('top', rect.top - 4) | |
mentionsInput[0].selectize.clear() | |
mentionsInput[0].selectize.enable() | |
mentionsDivForTrix($trix).show() | |
mentionsInput[0].selectize.focus() | |
if $trix.data(MENTIONS_PATH).length > 0 | |
createMentionsDivForTrix($trix) | |
initializeMentionsSelectize($trix) | |
$trix.on 'trix-change', -> | |
editor = @.editor | |
char = editor.getDocument().toString().charAt(editor.getPosition() - 1) | |
openMentionsSelectize($(@), editor) if char == '@' |
[data-trix-attachment] { | |
display: inline-block; | |
} | |
span.trix-mention + figcaption { | |
display: none; | |
} | |
trix-mentions { | |
.selectize-control { | |
position: fixed | |
} | |
.selectize-input { | |
border: none !important; | |
background: none !important; | |
box-shadow: none !important; | |
} | |
.selectize-control, .selectize-dropdown { | |
width: 200px !important; | |
z-index: 9999; | |
} | |
} |
I've spent the last couple hours trying to debug an error I'm getting and my JS skills just aren't there, especially with coffee thrown into the mix. Hopefully this will be an easy error on my part that you can direct me on how to resolve.
Line 82 of trix_mentions.js.coffee is what's triggering the error.
if $trix.data(MENTIONS_PATH).length > 0
Error as seen in Firefox:
TypeError: $trix.data(...) is undefined
Error as seen in Chrome:
Uncaught TypeError: Cannot read property 'length' of undefined
at Function.Utility.TrixMentions.TrixMentions.prepare (trix_mentions.self-857d9c9….js?body=1:105)
at mentionable_trix.self-9ca102d….js?body=1:4
at triggerEvent (trix.self-34b57b1….js?body=1:16)
at HTMLElement.notify (trix.self-34b57b1….js?body=1:21)
at trix.self-34b57b1….js?body=1:21
Utility.TrixMentions.TrixMentions.prepare @ trix_mentions.self-857d9c9….js?body=1:105
(anonymous) @ mentionable_trix.self-9ca102d….js?body=1:4
triggerEvent @ trix.self-34b57b1….js?body=1:16
notify @ trix.self-34b57b1….js?body=1:21
(anonymous) @ trix.self-34b57b1….js?body=1:21
I wasn't sure how I was supposed to set this up. I think all I need to configure is the path to my mentions, which I've done. Here is my config block:
MENTIONS_PATH = "/user/mentions?r"
MENTIONS_DIV_ID = "#trix-mentions-"
MENTIONS_INPUT_ID = MENTIONS_DIV_ID + "input-"
@lawso017, Any thoughts on how I should proceed? I'm running selectize.js 0.12.4 which appears to be the latest. Rails 5.1.2 on Ruby 2.4.1. Thanks!
@blimey85, the MENTIONS_PATH constant shouldn't need to be changed in your implementation. It's just defined as a constant to prevent typos in the code... we use the defined value "mentions-path" to identify the data attribute containing the path in the control.
In your case, you just need to ensure that your trix element has the data attribute:
data-mentions-path="/user/mentions?r"
defined.
@mitar, the autocomplete trigger is extremely primitive -- any time you hit "@", it's going to open the selectize control:
I expect you can expand the
if char == '@'
conditional to do a better evaluation of context and decide if you want to call openMentionsSelectize.