Use domain of users email address for preview. Added css auto load and css Url support. Added possibility to translation chat widget.
This commit is contained in:
parent
7a231a0121
commit
069063b2c7
8 changed files with 284 additions and 187 deletions
|
@ -30,10 +30,10 @@ class App.ChannelChat extends App.Controller
|
||||||
|
|
||||||
apiOptions: [
|
apiOptions: [
|
||||||
{
|
{
|
||||||
name: 'channel'
|
name: 'chatId'
|
||||||
default: "'default'"
|
default: '1'
|
||||||
type: 'String'
|
type: 'Integer'
|
||||||
description: 'Name of the chat-channel.'
|
description: 'Identifier of the chat-topic.'
|
||||||
}
|
}
|
||||||
{
|
{
|
||||||
name: 'show'
|
name: 'show'
|
||||||
|
@ -54,18 +54,18 @@ class App.ChannelChat extends App.Controller
|
||||||
description: "If left empty, the host gets auto-detected - in this case %s. The auto-detection reads out the host from the <script> tag. If you don't include it via a <script> tag you need to specify the host."
|
description: "If left empty, the host gets auto-detected - in this case %s. The auto-detection reads out the host from the <script> tag. If you don't include it via a <script> tag you need to specify the host."
|
||||||
descriptionSubstitute: window.location.origin
|
descriptionSubstitute: window.location.origin
|
||||||
}
|
}
|
||||||
{
|
|
||||||
name: 'port'
|
|
||||||
default: 6042
|
|
||||||
type: 'Int'
|
|
||||||
description: ''
|
|
||||||
}
|
|
||||||
{
|
{
|
||||||
name: 'debug'
|
name: 'debug'
|
||||||
default: false
|
default: false
|
||||||
type: 'Boolean'
|
type: 'Boolean'
|
||||||
description: 'Enables console logging.'
|
description: 'Enables console logging.'
|
||||||
}
|
}
|
||||||
|
{
|
||||||
|
name: 'title'
|
||||||
|
default: "'<strong>Chat</strong> with us!'"
|
||||||
|
type: 'String'
|
||||||
|
description: 'Welcome Title shown on the closed chat. Can contain HTML.'
|
||||||
|
}
|
||||||
{
|
{
|
||||||
name: 'fontSize'
|
name: 'fontSize'
|
||||||
default: 'undefined'
|
default: 'undefined'
|
||||||
|
@ -91,18 +91,29 @@ class App.ChannelChat extends App.Controller
|
||||||
description: 'This class gets added to the button on initialization and gets removed once the chat connection got established.'
|
description: 'This class gets added to the button on initialization and gets removed once the chat connection got established.'
|
||||||
}
|
}
|
||||||
{
|
{
|
||||||
name: 'title'
|
name: 'cssAutoload'
|
||||||
default: "'<strong>Chat</strong> with us!'"
|
default: 'true'
|
||||||
|
type: 'boolean'
|
||||||
|
description: 'Automatically loads the chat.css file. If you want to use your own css, just set it to false.'
|
||||||
|
}
|
||||||
|
{
|
||||||
|
name: 'cssUrl'
|
||||||
|
default: 'undefined'
|
||||||
type: 'String'
|
type: 'String'
|
||||||
description: 'Welcome Title shown on the closed chat. Can contain HTML.'
|
description: 'Location of an external chat.css file.'
|
||||||
}
|
}
|
||||||
]
|
]
|
||||||
|
|
||||||
isOpen: true
|
isOpen: true
|
||||||
browserWidth: 1280
|
browserWidth: 1280
|
||||||
|
previewUrl: ''
|
||||||
|
|
||||||
constructor: ->
|
constructor: ->
|
||||||
super
|
super
|
||||||
|
|
||||||
|
if @Session.get('email')
|
||||||
|
@previewUrl = "www.#{@Session.get('email').replace(/^.+?\@/, '')}"
|
||||||
|
|
||||||
@load()
|
@load()
|
||||||
|
|
||||||
@widgetDesignerPermanentParams =
|
@widgetDesignerPermanentParams =
|
||||||
|
@ -133,6 +144,7 @@ class App.ChannelChat extends App.Controller
|
||||||
baseurl: window.location.origin
|
baseurl: window.location.origin
|
||||||
chats: chats
|
chats: chats
|
||||||
apiOptions: @apiOptions
|
apiOptions: @apiOptions
|
||||||
|
previewUrl: @previewUrl
|
||||||
)
|
)
|
||||||
|
|
||||||
@code.each (i, block) ->
|
@code.each (i, block) ->
|
||||||
|
@ -222,7 +234,7 @@ class App.ChannelChat extends App.Controller
|
||||||
renderDemoWebsite: (data) =>
|
renderDemoWebsite: (data) =>
|
||||||
imageSource = data['data_url']
|
imageSource = data['data_url']
|
||||||
|
|
||||||
if imageSource
|
if imageSource
|
||||||
@screenshot.attr 'src', imageSource
|
@screenshot.attr 'src', imageSource
|
||||||
@iframe.attr('src', '')
|
@iframe.attr('src', '')
|
||||||
@website.attr('data-mode', 'screenshot')
|
@website.attr('data-mode', 'screenshot')
|
||||||
|
@ -236,7 +248,7 @@ class App.ChannelChat extends App.Controller
|
||||||
palette = _.map palette, tinycolor
|
palette = _.map palette, tinycolor
|
||||||
|
|
||||||
# filter white
|
# filter white
|
||||||
palette = _.filter palette, (color) =>
|
palette = _.filter palette, (color) ->
|
||||||
color.getLuminance() < 0.85
|
color.getLuminance() < 0.85
|
||||||
|
|
||||||
htmlString = ''
|
htmlString = ''
|
||||||
|
@ -347,4 +359,4 @@ class App.ChannelChat extends App.Controller
|
||||||
@paramsBlock.each (i, block) ->
|
@paramsBlock.each (i, block) ->
|
||||||
hljs.highlightBlock block
|
hljs.highlightBlock block
|
||||||
|
|
||||||
App.Config.set( 'Chat Widget', { prio: 4000, name: 'Chat Widget', parent: '#channels', target: '#channels/chat', controller: App.ChannelChat, role: ['Admin'] }, 'NavBarAdmin' )
|
App.Config.set( 'Chat', { prio: 4000, name: 'Chat', parent: '#channels', target: '#channels/chat', controller: App.ChannelChat, role: ['Admin'] }, 'NavBarAdmin' )
|
||||||
|
|
|
@ -11,6 +11,7 @@
|
||||||
<table class="settings-list">
|
<table class="settings-list">
|
||||||
<thead>
|
<thead>
|
||||||
<tr>
|
<tr>
|
||||||
|
<th style="white-space: nowrap;"><%- @T('chatId') %></th>
|
||||||
<th style="white-space: nowrap;"><%- @T('Name') %></th>
|
<th style="white-space: nowrap;"><%- @T('Name') %></th>
|
||||||
<th style="white-space: nowrap;"><%- @T('Note') %></th>
|
<th style="white-space: nowrap;"><%- @T('Note') %></th>
|
||||||
<th style="white-space: nowrap;"><%- @T('Max. clients in waitlist') %></th>
|
<th style="white-space: nowrap;"><%- @T('Max. clients in waitlist') %></th>
|
||||||
|
@ -20,6 +21,10 @@
|
||||||
<tbody>
|
<tbody>
|
||||||
<% for chat in @chats: %>
|
<% for chat in @chats: %>
|
||||||
<tr data-id="<%= chat.id %>">
|
<tr data-id="<%= chat.id %>">
|
||||||
|
<td>
|
||||||
|
<label class="inline-label">
|
||||||
|
<%= chat.id %>
|
||||||
|
</label>
|
||||||
<td>
|
<td>
|
||||||
<label class="inline-label">
|
<label class="inline-label">
|
||||||
<a class="js-edit is-clickable"><%= chat.name %></a>
|
<a class="js-edit is-clickable"><%= chat.name %></a>
|
||||||
|
@ -40,7 +45,7 @@
|
||||||
</div>
|
</div>
|
||||||
<% end %>
|
<% end %>
|
||||||
<tr>
|
<tr>
|
||||||
<td colspan="4" class="settings-list-action-cell js-add">
|
<td colspan="5" class="settings-list-action-cell js-add">
|
||||||
<%- @Icon('plus-small') %> <%- @T('Add') %>
|
<%- @Icon('plus-small') %> <%- @T('Add') %>
|
||||||
</tbody>
|
</tbody>
|
||||||
</table>
|
</table>
|
||||||
|
@ -62,7 +67,7 @@
|
||||||
<div class="browser chat-demo js-browser">
|
<div class="browser chat-demo js-browser">
|
||||||
<form class="browser-head js-demo-head" novalidate>
|
<form class="browser-head js-demo-head" novalidate>
|
||||||
<div class="browser-input">
|
<div class="browser-input">
|
||||||
<input type="url" class="js-testurl-input" id="preview-iframe" placeholder="zammad.org">
|
<input type="url" class="js-testurl-input" id="preview-iframe" value="<%= @previewUrl %>" placeholder="www.zammad.org">
|
||||||
<div class="loading icon small muted"></div>
|
<div class="loading icon small muted"></div>
|
||||||
</div>
|
</div>
|
||||||
<input type="submit" class="btn" value="<%- @T('Load') %>">
|
<input type="submit" class="btn" value="<%- @T('Load') %>">
|
||||||
|
|
|
@ -14,6 +14,9 @@ do($ = window.jQuery, window) ->
|
||||||
host: ''
|
host: ''
|
||||||
debug: false
|
debug: false
|
||||||
flat: false
|
flat: false
|
||||||
|
lang: undefined,
|
||||||
|
cssAutoload: true,
|
||||||
|
cssUrl: undefined,
|
||||||
fontSize: undefined
|
fontSize: undefined
|
||||||
buttonClass: 'open-zammad-chat'
|
buttonClass: 'open-zammad-chat'
|
||||||
inactiveClass: 'is-inactive'
|
inactiveClass: 'is-inactive'
|
||||||
|
@ -31,30 +34,37 @@ do($ = window.jQuery, window) ->
|
||||||
state: 'offline'
|
state: 'offline'
|
||||||
initialQueueDelay: 10000
|
initialQueueDelay: 10000
|
||||||
wsReconnectEnable: true
|
wsReconnectEnable: true
|
||||||
strings:
|
translations:
|
||||||
'Online': 'Online'
|
de:
|
||||||
'Offline': 'Offline'
|
'<strong>Chat</strong> with us!': '<strong>Chat</strong> mit uns!'
|
||||||
'Connecting': 'Verbinden'
|
'Online': 'Online'
|
||||||
'Connection re-established': 'Verbindung wiederhergestellt'
|
'Online': 'Online'
|
||||||
'Today': 'Heute'
|
'Offline': 'Offline'
|
||||||
'Send': 'Senden'
|
'Connecting': 'Verbinden'
|
||||||
'Compose your message...': 'Ihre Nachricht...'
|
'Connection re-established': 'Verbindung wiederhergestellt'
|
||||||
'All colleges are busy.': 'Alle Kollegen sind belegt.'
|
'Today': 'Heute'
|
||||||
'You are on waiting list position <strong>%s</strong>.': 'Sie sind in der Warteliste an der Position <strong>%s</strong>.'
|
'Send': 'Senden'
|
||||||
'Start new conversation': 'Neue Konversation starten'
|
'Compose your message...': 'Ihre Nachricht...'
|
||||||
'Since you didn\'t respond in the last %s your conversation with <strong>%s</strong> got closed.': 'Da sie in den letzten %s nichts geschrieben haben wurde ihre Konversation mit <strong>%s</strong> geschlossen.'
|
'All colleges are busy.': 'Alle Kollegen sind belegt.'
|
||||||
'minutes': 'Minuten'
|
'You are on waiting list position <strong>%s</strong>.': 'Sie sind in der Warteliste an der Position <strong>%s</strong>.'
|
||||||
|
'Start new conversation': 'Neue Konversation starten'
|
||||||
|
'Since you didn\'t respond in the last %s your conversation with <strong>%s</strong> got closed.': 'Da sie in den letzten %s nichts geschrieben haben wurde ihre Konversation mit <strong>%s</strong> geschlossen.'
|
||||||
|
'minutes': 'Minuten'
|
||||||
sessionId: undefined
|
sessionId: undefined
|
||||||
|
|
||||||
T: (string, items...) =>
|
T: (string, items...) =>
|
||||||
if !@strings[string]
|
if @options.lang && @options.lang isnt 'en'
|
||||||
@log 'notice', "Translation needed for '#{string}'"
|
if !@translations[@options.lang]
|
||||||
translation = @strings[string] || string
|
@log 'notice', "Translation '#{@options.lang}' needed!"
|
||||||
|
else
|
||||||
|
translations = @translations[@options.lang]
|
||||||
|
if !translations[string]
|
||||||
|
@log 'notice', "Translation needed for '#{string}'"
|
||||||
|
string = translations[string] || string
|
||||||
if items
|
if items
|
||||||
for item in items
|
for item in items
|
||||||
translation = translation.replace(/%s/, item)
|
string = string.replace(/%s/, item)
|
||||||
|
string
|
||||||
translation
|
|
||||||
|
|
||||||
log: (level, string...) =>
|
log: (level, string...) =>
|
||||||
return if !@options.debug && level is 'debug'
|
return if !@options.debug && level is 'debug'
|
||||||
|
@ -80,12 +90,18 @@ do($ = window.jQuery, window) ->
|
||||||
@state = 'unsupported'
|
@state = 'unsupported'
|
||||||
@log 'notice', 'Chat: Browser not supported!'
|
@log 'notice', 'Chat: Browser not supported!'
|
||||||
return
|
return
|
||||||
|
|
||||||
if !@options.chatId
|
if !@options.chatId
|
||||||
@state = 'unsupported'
|
@state = 'unsupported'
|
||||||
@log 'error', 'Chat: need chatId as option!'
|
@log 'error', 'Chat: need chatId as option!'
|
||||||
return
|
return
|
||||||
|
|
||||||
|
# detect language
|
||||||
|
if !@options.lang
|
||||||
|
@options.lang = $('html').attr('lang')
|
||||||
|
if @options.lang
|
||||||
|
@options.lang = @options.lang.replace(/-.+?$/, '') # replace "-xx" of xx-xx
|
||||||
|
@log 'debug', "lang: #{@options.lang}"
|
||||||
|
|
||||||
@el = $(@view('chat')(
|
@el = $(@view('chat')(
|
||||||
title: @options.title
|
title: @options.title
|
||||||
))
|
))
|
||||||
|
@ -105,6 +121,8 @@ do($ = window.jQuery, window) ->
|
||||||
|
|
||||||
@wsConnect()
|
@wsConnect()
|
||||||
|
|
||||||
|
@loadCss()
|
||||||
|
|
||||||
checkForEnter: (event) =>
|
checkForEnter: (event) =>
|
||||||
if not event.shiftKey and event.keyCode is 13
|
if not event.shiftKey and event.keyCode is 13
|
||||||
event.preventDefault()
|
event.preventDefault()
|
||||||
|
@ -548,4 +566,21 @@ do($ = window.jQuery, window) ->
|
||||||
.attr('data-status', state)
|
.attr('data-status', state)
|
||||||
.text @T(capitalizedState)
|
.text @T(capitalizedState)
|
||||||
|
|
||||||
|
loadCss: ->
|
||||||
|
return if !@options.cssAutoload
|
||||||
|
url = @options.cssUrl
|
||||||
|
if !url
|
||||||
|
url = @options.host
|
||||||
|
.replace(/^wss/i, 'https')
|
||||||
|
.replace(/^ws/i, 'http')
|
||||||
|
.replace(/\/ws/i, '')
|
||||||
|
url += '/assets/chat/chat.css'
|
||||||
|
|
||||||
|
@log 'debug', "load css from '#{url}'"
|
||||||
|
styles = "@import url('#{url}');"
|
||||||
|
newSS = document.createElement('link')
|
||||||
|
newSS.rel = 'stylesheet'
|
||||||
|
newSS.href = 'data:text/css,' + escape(styles)
|
||||||
|
document.getElementsByTagName('head')[0].appendChild(newSS)
|
||||||
|
|
||||||
window.ZammadChat = ZammadChat
|
window.ZammadChat = ZammadChat
|
||||||
|
|
|
@ -1,64 +1,3 @@
|
||||||
if (!window.zammadChatTemplates) {
|
|
||||||
window.zammadChatTemplates = {};
|
|
||||||
}
|
|
||||||
window.zammadChatTemplates["agent"] = function (__obj) {
|
|
||||||
if (!__obj) __obj = {};
|
|
||||||
var __out = [], __capture = function(callback) {
|
|
||||||
var out = __out, result;
|
|
||||||
__out = [];
|
|
||||||
callback.call(this);
|
|
||||||
result = __out.join('');
|
|
||||||
__out = out;
|
|
||||||
return __safe(result);
|
|
||||||
}, __sanitize = function(value) {
|
|
||||||
if (value && value.ecoSafe) {
|
|
||||||
return value;
|
|
||||||
} else if (typeof value !== 'undefined' && value != null) {
|
|
||||||
return __escape(value);
|
|
||||||
} else {
|
|
||||||
return '';
|
|
||||||
}
|
|
||||||
}, __safe, __objSafe = __obj.safe, __escape = __obj.escape;
|
|
||||||
__safe = __obj.safe = function(value) {
|
|
||||||
if (value && value.ecoSafe) {
|
|
||||||
return value;
|
|
||||||
} else {
|
|
||||||
if (!(typeof value !== 'undefined' && value != null)) value = '';
|
|
||||||
var result = new String(value);
|
|
||||||
result.ecoSafe = true;
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
};
|
|
||||||
if (!__escape) {
|
|
||||||
__escape = __obj.escape = function(value) {
|
|
||||||
return ('' + value)
|
|
||||||
.replace(/&/g, '&')
|
|
||||||
.replace(/</g, '<')
|
|
||||||
.replace(/>/g, '>')
|
|
||||||
.replace(/"/g, '"');
|
|
||||||
};
|
|
||||||
}
|
|
||||||
(function() {
|
|
||||||
(function() {
|
|
||||||
if (this.agent.avatar) {
|
|
||||||
__out.push('\n<img class="zammad-chat-agent-avatar" src="');
|
|
||||||
__out.push(__sanitize(this.agent.avatar));
|
|
||||||
__out.push('">\n');
|
|
||||||
}
|
|
||||||
|
|
||||||
__out.push('\n<span class="zammad-chat-agent-sentence">\n <span class="zammad-chat-agent-name">');
|
|
||||||
|
|
||||||
__out.push(__sanitize(this.agent.name));
|
|
||||||
|
|
||||||
__out.push('</span>\n</span>');
|
|
||||||
|
|
||||||
}).call(this);
|
|
||||||
|
|
||||||
}).call(__obj);
|
|
||||||
__obj.safe = __objSafe, __obj.escape = __escape;
|
|
||||||
return __out.join('');
|
|
||||||
};
|
|
||||||
|
|
||||||
var bind = function(fn, me){ return function(){ return fn.apply(me, arguments); }; },
|
var bind = function(fn, me){ return function(){ return fn.apply(me, arguments); }; },
|
||||||
slice = [].slice;
|
slice = [].slice;
|
||||||
|
|
||||||
|
@ -75,6 +14,9 @@ var bind = function(fn, me){ return function(){ return fn.apply(me, arguments);
|
||||||
host: '',
|
host: '',
|
||||||
debug: false,
|
debug: false,
|
||||||
flat: false,
|
flat: false,
|
||||||
|
lang: void 0,
|
||||||
|
cssAutoload: true,
|
||||||
|
cssUrl: void 0,
|
||||||
fontSize: void 0,
|
fontSize: void 0,
|
||||||
buttonClass: 'open-zammad-chat',
|
buttonClass: 'open-zammad-chat',
|
||||||
inactiveClass: 'is-inactive',
|
inactiveClass: 'is-inactive',
|
||||||
|
@ -105,37 +47,48 @@ var bind = function(fn, me){ return function(){ return fn.apply(me, arguments);
|
||||||
|
|
||||||
ZammadChat.prototype.wsReconnectEnable = true;
|
ZammadChat.prototype.wsReconnectEnable = true;
|
||||||
|
|
||||||
ZammadChat.prototype.strings = {
|
ZammadChat.prototype.translations = {
|
||||||
'Online': 'Online',
|
de: {
|
||||||
'Offline': 'Offline',
|
'<strong>Chat</strong> with us!': '<strong>Chat</strong> mit uns!',
|
||||||
'Connecting': 'Verbinden',
|
'Online': 'Online',
|
||||||
'Connection re-established': 'Verbindung wiederhergestellt',
|
'Online': 'Online',
|
||||||
'Today': 'Heute',
|
'Offline': 'Offline',
|
||||||
'Send': 'Senden',
|
'Connecting': 'Verbinden',
|
||||||
'Compose your message...': 'Ihre Nachricht...',
|
'Connection re-established': 'Verbindung wiederhergestellt',
|
||||||
'All colleges are busy.': 'Alle Kollegen sind belegt.',
|
'Today': 'Heute',
|
||||||
'You are on waiting list position <strong>%s</strong>.': 'Sie sind in der Warteliste an der Position <strong>%s</strong>.',
|
'Send': 'Senden',
|
||||||
'Start new conversation': 'Neue Konversation starten',
|
'Compose your message...': 'Ihre Nachricht...',
|
||||||
'Since you didn\'t respond in the last %s your conversation with <strong>%s</strong> got closed.': 'Da sie in den letzten %s nichts geschrieben haben wurde ihre Konversation mit <strong>%s</strong> geschlossen.',
|
'All colleges are busy.': 'Alle Kollegen sind belegt.',
|
||||||
'minutes': 'Minuten'
|
'You are on waiting list position <strong>%s</strong>.': 'Sie sind in der Warteliste an der Position <strong>%s</strong>.',
|
||||||
|
'Start new conversation': 'Neue Konversation starten',
|
||||||
|
'Since you didn\'t respond in the last %s your conversation with <strong>%s</strong> got closed.': 'Da sie in den letzten %s nichts geschrieben haben wurde ihre Konversation mit <strong>%s</strong> geschlossen.',
|
||||||
|
'minutes': 'Minuten'
|
||||||
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
ZammadChat.prototype.sessionId = void 0;
|
ZammadChat.prototype.sessionId = void 0;
|
||||||
|
|
||||||
ZammadChat.prototype.T = function() {
|
ZammadChat.prototype.T = function() {
|
||||||
var i, item, items, len, string, translation;
|
var i, item, items, len, string, translations;
|
||||||
string = arguments[0], items = 2 <= arguments.length ? slice.call(arguments, 1) : [];
|
string = arguments[0], items = 2 <= arguments.length ? slice.call(arguments, 1) : [];
|
||||||
if (!this.strings[string]) {
|
if (this.options.lang && this.options.lang !== 'en') {
|
||||||
this.log('notice', "Translation needed for '" + string + "'");
|
if (!this.translations[this.options.lang]) {
|
||||||
|
this.log('notice', "Translation '" + this.options.lang + "' needed!");
|
||||||
|
} else {
|
||||||
|
translations = this.translations[this.options.lang];
|
||||||
|
if (!translations[string]) {
|
||||||
|
this.log('notice', "Translation needed for '" + string + "'");
|
||||||
|
}
|
||||||
|
string = translations[string] || string;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
translation = this.strings[string] || string;
|
|
||||||
if (items) {
|
if (items) {
|
||||||
for (i = 0, len = items.length; i < len; i++) {
|
for (i = 0, len = items.length; i < len; i++) {
|
||||||
item = items[i];
|
item = items[i];
|
||||||
translation = translation.replace(/%s/, item);
|
string = string.replace(/%s/, item);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return translation;
|
return string;
|
||||||
};
|
};
|
||||||
|
|
||||||
ZammadChat.prototype.log = function() {
|
ZammadChat.prototype.log = function() {
|
||||||
|
@ -205,6 +158,13 @@ var bind = function(fn, me){ return function(){ return fn.apply(me, arguments);
|
||||||
this.log('error', 'Chat: need chatId as option!');
|
this.log('error', 'Chat: need chatId as option!');
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
if (!this.options.lang) {
|
||||||
|
this.options.lang = $('html').attr('lang');
|
||||||
|
}
|
||||||
|
if (this.options.lang) {
|
||||||
|
this.options.lang = this.options.lang.replace(/-.+?$/, '');
|
||||||
|
this.log('debug', "lang: " + this.options.lang);
|
||||||
|
}
|
||||||
this.el = $(this.view('chat')({
|
this.el = $(this.view('chat')({
|
||||||
title: this.options.title
|
title: this.options.title
|
||||||
}));
|
}));
|
||||||
|
@ -219,6 +179,7 @@ var bind = function(fn, me){ return function(){ return fn.apply(me, arguments);
|
||||||
input: this.onInput
|
input: this.onInput
|
||||||
});
|
});
|
||||||
this.wsConnect();
|
this.wsConnect();
|
||||||
|
this.loadCss();
|
||||||
}
|
}
|
||||||
|
|
||||||
ZammadChat.prototype.checkForEnter = function(event) {
|
ZammadChat.prototype.checkForEnter = function(event) {
|
||||||
|
@ -730,12 +691,91 @@ var bind = function(fn, me){ return function(){ return fn.apply(me, arguments);
|
||||||
return this.el.find('.zammad-chat-agent-status').attr('data-status', state).text(this.T(capitalizedState));
|
return this.el.find('.zammad-chat-agent-status').attr('data-status', state).text(this.T(capitalizedState));
|
||||||
};
|
};
|
||||||
|
|
||||||
|
ZammadChat.prototype.loadCss = function() {
|
||||||
|
var newSS, styles, url;
|
||||||
|
if (!this.options.cssAutoload) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
url = this.options.cssUrl;
|
||||||
|
if (!url) {
|
||||||
|
url = this.options.host.replace(/^wss/i, 'https').replace(/^ws/i, 'http').replace(/\/ws/i, '');
|
||||||
|
url += '/assets/chat/chat.css';
|
||||||
|
}
|
||||||
|
this.log('debug', "load css from '" + url + "'");
|
||||||
|
styles = "@import url('" + url + "');";
|
||||||
|
newSS = document.createElement('link');
|
||||||
|
newSS.rel = 'stylesheet';
|
||||||
|
newSS.href = 'data:text/css,' + escape(styles);
|
||||||
|
return document.getElementsByTagName('head')[0].appendChild(newSS);
|
||||||
|
};
|
||||||
|
|
||||||
return ZammadChat;
|
return ZammadChat;
|
||||||
|
|
||||||
})();
|
})();
|
||||||
return window.ZammadChat = ZammadChat;
|
return window.ZammadChat = ZammadChat;
|
||||||
})(window.jQuery, window);
|
})(window.jQuery, window);
|
||||||
|
|
||||||
|
if (!window.zammadChatTemplates) {
|
||||||
|
window.zammadChatTemplates = {};
|
||||||
|
}
|
||||||
|
window.zammadChatTemplates["agent"] = function (__obj) {
|
||||||
|
if (!__obj) __obj = {};
|
||||||
|
var __out = [], __capture = function(callback) {
|
||||||
|
var out = __out, result;
|
||||||
|
__out = [];
|
||||||
|
callback.call(this);
|
||||||
|
result = __out.join('');
|
||||||
|
__out = out;
|
||||||
|
return __safe(result);
|
||||||
|
}, __sanitize = function(value) {
|
||||||
|
if (value && value.ecoSafe) {
|
||||||
|
return value;
|
||||||
|
} else if (typeof value !== 'undefined' && value != null) {
|
||||||
|
return __escape(value);
|
||||||
|
} else {
|
||||||
|
return '';
|
||||||
|
}
|
||||||
|
}, __safe, __objSafe = __obj.safe, __escape = __obj.escape;
|
||||||
|
__safe = __obj.safe = function(value) {
|
||||||
|
if (value && value.ecoSafe) {
|
||||||
|
return value;
|
||||||
|
} else {
|
||||||
|
if (!(typeof value !== 'undefined' && value != null)) value = '';
|
||||||
|
var result = new String(value);
|
||||||
|
result.ecoSafe = true;
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
if (!__escape) {
|
||||||
|
__escape = __obj.escape = function(value) {
|
||||||
|
return ('' + value)
|
||||||
|
.replace(/&/g, '&')
|
||||||
|
.replace(/</g, '<')
|
||||||
|
.replace(/>/g, '>')
|
||||||
|
.replace(/"/g, '"');
|
||||||
|
};
|
||||||
|
}
|
||||||
|
(function() {
|
||||||
|
(function() {
|
||||||
|
if (this.agent.avatar) {
|
||||||
|
__out.push('\n<img class="zammad-chat-agent-avatar" src="');
|
||||||
|
__out.push(__sanitize(this.agent.avatar));
|
||||||
|
__out.push('">\n');
|
||||||
|
}
|
||||||
|
|
||||||
|
__out.push('\n<span class="zammad-chat-agent-sentence">\n <span class="zammad-chat-agent-name">');
|
||||||
|
|
||||||
|
__out.push(__sanitize(this.agent.name));
|
||||||
|
|
||||||
|
__out.push('</span>\n</span>');
|
||||||
|
|
||||||
|
}).call(this);
|
||||||
|
|
||||||
|
}).call(__obj);
|
||||||
|
__obj.safe = __objSafe, __obj.escape = __escape;
|
||||||
|
return __out.join('');
|
||||||
|
};
|
||||||
|
|
||||||
/*!
|
/*!
|
||||||
* ----------------------------------------------------------------------------
|
* ----------------------------------------------------------------------------
|
||||||
* "THE BEER-WARE LICENSE" (Revision 42):
|
* "THE BEER-WARE LICENSE" (Revision 42):
|
||||||
|
@ -875,7 +915,7 @@ window.zammadChatTemplates["chat"] = function (__obj) {
|
||||||
|
|
||||||
__out.push('>\n <div class="zammad-chat-header-controls">\n <span class="zammad-chat-agent-status zammad-chat-is-hidden" data-status="online"></span>\n <span class="zammad-chat-header-icon">\n <svg class="zammad-chat-header-icon-open" viewBox="0 0 13 7"><path d="M10.807 7l1.4-1.428-5-4.9L6.5-.02l-.7.7-4.9 4.9 1.414 1.413L6.5 2.886 10.807 7z" fill-rule="evenodd"/></svg>\n <svg class="zammad-chat-header-icon-close js-chat-close" viewBox="0 0 13 13"><path d="m2.241.12l-2.121 2.121 4.243 4.243-4.243 4.243 2.121 2.121 4.243-4.243 4.243 4.243 2.121-2.121-4.243-4.243 4.243-4.243-2.121-2.121-4.243 4.243-4.243-4.243" fill-rule="evenodd"/></svg>\n </span>\n </div>\n <div class="zammad-chat-agent zammad-chat-is-hidden">\n </div>\n <div class="zammad-chat-welcome">\n <svg class="zammad-chat-icon" viewBox="0 0 24 24"><path d="M2 5C2 4 3 3 4 3h16c1 0 2 1 2 2v10C22 16 21 17 20 17H4C3 17 2 16 2 15V5zM12 17l6 4v-4h-6z" fill-rule="evenodd"/></svg>\n <span class="zammad-chat-welcome-text">');
|
__out.push('>\n <div class="zammad-chat-header-controls">\n <span class="zammad-chat-agent-status zammad-chat-is-hidden" data-status="online"></span>\n <span class="zammad-chat-header-icon">\n <svg class="zammad-chat-header-icon-open" viewBox="0 0 13 7"><path d="M10.807 7l1.4-1.428-5-4.9L6.5-.02l-.7.7-4.9 4.9 1.414 1.413L6.5 2.886 10.807 7z" fill-rule="evenodd"/></svg>\n <svg class="zammad-chat-header-icon-close js-chat-close" viewBox="0 0 13 13"><path d="m2.241.12l-2.121 2.121 4.243 4.243-4.243 4.243 2.121 2.121 4.243-4.243 4.243 4.243 2.121-2.121-4.243-4.243 4.243-4.243-2.121-2.121-4.243 4.243-4.243-4.243" fill-rule="evenodd"/></svg>\n </span>\n </div>\n <div class="zammad-chat-agent zammad-chat-is-hidden">\n </div>\n <div class="zammad-chat-welcome">\n <svg class="zammad-chat-icon" viewBox="0 0 24 24"><path d="M2 5C2 4 3 3 4 3h16c1 0 2 1 2 2v10C22 16 21 17 20 17H4C3 17 2 16 2 15V5zM12 17l6 4v-4h-6z" fill-rule="evenodd"/></svg>\n <span class="zammad-chat-welcome-text">');
|
||||||
|
|
||||||
__out.push(this.title);
|
__out.push(this.T(this.title));
|
||||||
|
|
||||||
__out.push('</span>\n </div>\n </div>\n <div class="zammad-chat-body"></div>\n <form class="zammad-chat-controls">\n <textarea class="zammad-chat-input" rows="1" placeholder="');
|
__out.push('</span>\n </div>\n </div>\n <div class="zammad-chat-body"></div>\n <form class="zammad-chat-controls">\n <textarea class="zammad-chat-input" rows="1" placeholder="');
|
||||||
|
|
||||||
|
|
2
public/assets/chat/chat.min.js
vendored
2
public/assets/chat/chat.min.js
vendored
File diff suppressed because one or more lines are too long
|
@ -1,7 +1,6 @@
|
||||||
<!doctype html>
|
<!doctype html>
|
||||||
<meta charset="utf-8">
|
<meta charset="utf-8">
|
||||||
<title>Zammad Chat</title>
|
<title>Zammad Chat</title>
|
||||||
<link rel="stylesheet" href="chat.css">
|
|
||||||
<meta name="viewport" content="width=device-width">
|
<meta name="viewport" content="width=device-width">
|
||||||
<script>document.write('<script src="http://' + (location.host || 'localhost').split(':')[0] + ':35738/livereload.js?snipver=1"></' + 'script>')</script>
|
<script>document.write('<script src="http://' + (location.host || 'localhost').split(':')[0] + ':35738/livereload.js?snipver=1"></' + 'script>')</script>
|
||||||
<style>
|
<style>
|
||||||
|
@ -140,6 +139,7 @@
|
||||||
var chat = new ZammadChat({
|
var chat = new ZammadChat({
|
||||||
chatId: 1,
|
chatId: 1,
|
||||||
host: 'ws://localhost:6042',
|
host: 'ws://localhost:6042',
|
||||||
|
cssUrl: 'http://localhost:3000/assets/chat/chat.css',
|
||||||
debug: true
|
debug: true
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|
|
@ -11,7 +11,7 @@
|
||||||
</div>
|
</div>
|
||||||
<div class="zammad-chat-welcome">
|
<div class="zammad-chat-welcome">
|
||||||
<svg class="zammad-chat-icon" viewBox="0 0 24 24"><path d="M2 5C2 4 3 3 4 3h16c1 0 2 1 2 2v10C22 16 21 17 20 17H4C3 17 2 16 2 15V5zM12 17l6 4v-4h-6z" fill-rule="evenodd"/></svg>
|
<svg class="zammad-chat-icon" viewBox="0 0 24 24"><path d="M2 5C2 4 3 3 4 3h16c1 0 2 1 2 2v10C22 16 21 17 20 17H4C3 17 2 16 2 15V5zM12 17l6 4v-4h-6z" fill-rule="evenodd"/></svg>
|
||||||
<span class="zammad-chat-welcome-text"><%- @title %></span>
|
<span class="zammad-chat-welcome-text"><%- @T(@title) %></span>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div class="zammad-chat-body"></div>
|
<div class="zammad-chat-body"></div>
|
||||||
|
|
|
@ -1,71 +1,73 @@
|
||||||
<!doctype html>
|
<!doctype html>
|
||||||
<meta charset="utf-8">
|
<html lang="de-de">
|
||||||
<title>Zammad Chat</title>
|
<head>
|
||||||
<link rel="stylesheet" href="chat.css">
|
<meta charset="utf-8">
|
||||||
<link rel="stylesheet" href="znuny.css">
|
<title>Zammad Chat</title>
|
||||||
<meta name="viewport" content="width=device-width">
|
<link rel="stylesheet" href="znuny.css">
|
||||||
<script>document.write('<script src="http://' + (location.host || 'localhost').split(':')[0] + ':35738/livereload.js?snipver=1"></' + 'script>')</script>
|
<meta name="viewport" content="width=device-width">
|
||||||
<style>
|
<script>document.write('<script src="http://' + (location.host || 'localhost').split(':')[0] + ':35738/livereload.js?snipver=1"></' + 'script>')</script>
|
||||||
body {
|
<style>
|
||||||
margin: 0;
|
body {
|
||||||
font-family: sans-serif;
|
margin: 0;
|
||||||
}
|
font-family: sans-serif;
|
||||||
|
|
||||||
.mockup {
|
|
||||||
vertical-align: bottom;
|
|
||||||
}
|
|
||||||
|
|
||||||
.settings {
|
|
||||||
position: fixed;
|
|
||||||
left: 20px;
|
|
||||||
top: 20px;
|
|
||||||
background: white;
|
|
||||||
font-size: 14px;
|
|
||||||
padding: 10px;
|
|
||||||
border-radius: 5px;
|
|
||||||
box-shadow: 0 3px 10px rgba(0,0,0,.3);
|
|
||||||
}
|
|
||||||
|
|
||||||
.settings input {
|
|
||||||
vertical-align: middle;
|
|
||||||
}
|
|
||||||
.settings input + input {
|
|
||||||
margin-right: 3px;
|
|
||||||
}
|
|
||||||
|
|
||||||
table td:first-child {
|
|
||||||
text-align: right;
|
|
||||||
padding-right: 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
td {
|
|
||||||
padding: 5px;
|
|
||||||
}
|
|
||||||
|
|
||||||
h2 {
|
|
||||||
font-size: 1em;
|
|
||||||
margin: 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
@media only screen and (max-width: 768px) {
|
|
||||||
.settings {
|
|
||||||
display: none;
|
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
.Box {
|
.mockup {
|
||||||
background: hsl(0,0%,91%);
|
vertical-align: bottom;
|
||||||
width: 26px;
|
}
|
||||||
height: 24px;
|
|
||||||
color: hsl(0,0%,47%);
|
|
||||||
float: left;
|
|
||||||
}
|
|
||||||
.Box.Active {
|
|
||||||
background: hsl(0,0%,36%);
|
|
||||||
color: white;
|
|
||||||
}
|
|
||||||
</style>
|
|
||||||
|
|
||||||
|
.settings {
|
||||||
|
position: fixed;
|
||||||
|
left: 20px;
|
||||||
|
top: 20px;
|
||||||
|
background: white;
|
||||||
|
font-size: 14px;
|
||||||
|
padding: 10px;
|
||||||
|
border-radius: 5px;
|
||||||
|
box-shadow: 0 3px 10px rgba(0,0,0,.3);
|
||||||
|
}
|
||||||
|
|
||||||
|
.settings input {
|
||||||
|
vertical-align: middle;
|
||||||
|
}
|
||||||
|
.settings input + input {
|
||||||
|
margin-right: 3px;
|
||||||
|
}
|
||||||
|
|
||||||
|
table td:first-child {
|
||||||
|
text-align: right;
|
||||||
|
padding-right: 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
td {
|
||||||
|
padding: 5px;
|
||||||
|
}
|
||||||
|
|
||||||
|
h2 {
|
||||||
|
font-size: 1em;
|
||||||
|
margin: 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
@media only screen and (max-width: 768px) {
|
||||||
|
.settings {
|
||||||
|
display: none;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
.Box {
|
||||||
|
background: hsl(0,0%,91%);
|
||||||
|
width: 26px;
|
||||||
|
height: 24px;
|
||||||
|
color: hsl(0,0%,47%);
|
||||||
|
float: left;
|
||||||
|
}
|
||||||
|
.Box.Active {
|
||||||
|
background: hsl(0,0%,36%);
|
||||||
|
color: white;
|
||||||
|
}
|
||||||
|
</style>
|
||||||
|
</head>
|
||||||
|
<body>
|
||||||
<img class="mockup" width="100%" src="znuny.png">
|
<img class="mockup" width="100%" src="znuny.png">
|
||||||
|
|
||||||
<div class="settings">
|
<div class="settings">
|
||||||
|
@ -107,6 +109,7 @@
|
||||||
var chat = new ZammadChat({
|
var chat = new ZammadChat({
|
||||||
chatId: 1,
|
chatId: 1,
|
||||||
host: 'ws://localhost:6042',
|
host: 'ws://localhost:6042',
|
||||||
|
cssUrl: 'http://localhost:3000/assets/chat/chat.css',
|
||||||
debug: true,
|
debug: true,
|
||||||
background: '#494d52',
|
background: '#494d52',
|
||||||
flat: true,
|
flat: true,
|
||||||
|
@ -144,4 +147,6 @@
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
</script>
|
</script>
|
||||||
|
</body>
|
||||||
|
</html>
|
Loading…
Reference in a new issue