MDL-42434 mod_chat: display the whole help text
[moodle.git] / mod / chat / gui_ajax / module.js
CommitLineData
2daed78a
PS
1/*
2 * NOTE: the /mod/chat/gui_header_js/ is not a real plugin,
3 * ideally this code should be in /mod/chat/module.js
4 */
5
6/**
7 * @namespace M.mod_chat_ajax
8 */
9M.mod_chat_ajax = M.mod_chat_ajax || {};
10
579a4976 11/**
2daed78a
PS
12 * Init ajax based Chat UI.
13 * @namespace M.mod_chat_ajax
14 * @function
15 * @param {YUI} Y
16 * @param {Object} cfg configuration data
579a4976 17 */
2daed78a
PS
18M.mod_chat_ajax.init = function(Y, cfg) {
19
20 var gui_ajax = {
579a4976 21
c52b4db5
AD
22 // Properties.
23 api : M.cfg.wwwroot + '/mod/chat/chat_ajax.php?sesskey=' + M.cfg.sesskey, // The path to the ajax callback script.
24 cfg : {}, // A configuration variable.
25 interval : null, // The interval object for refreshes.
26 layout : null, // A reference to the layout used in this module.
27 messages : [], // An array of messages.
28 scrollable : true, // True is scrolling should occur.
29 thememenu : null, // A reference to the menu for changing themes.
579a4976
SH
30
31 // Elements
32 messageinput : null,
33 sendbutton : null,
34 messagebox : null,
35
2daed78a 36 init : function(cfg) {
579a4976
SH
37 this.cfg = cfg;
38 this.cfg.req_count = this.cfg.req_count || 0;
e9c599cb
AD
39 participantswidth = 180;
40 if (Y.one('#input-message').get('docWidth') < 640) {
41 participantswidth = 120;
42 }
69ccc32d 43 this.layout = new Y.YUI2.widget.Layout({
579a4976 44 units : [
e9c599cb
AD
45 {position: 'right', width: participantswidth, resize: true, gutter: '1px', scroll: true, body: 'chat-userlist', animate: false},
46 {position: 'bottom', height: 42, resize: false, body: 'chat-input-area', gutter: '1px', collapse: false, resize: false},
47 {position: 'center', body: 'chat-messages', gutter: '0px', scroll: true}
579a4976
SH
48 ]
49 });
50
51 this.layout.on('render', function() {
7d2975c1
DC
52 var unit = this.getUnitByPosition('right');
53 if (unit) {
54 unit.on('close', function() {
55 closeLeft();
56 });
57 }
579a4976
SH
58 }, this.layout);
59 this.layout.render();
60
c52b4db5 61 // Gather the general elements.
579a4976
SH
62 this.messageinput = Y.one('#input-message');
63 this.sendbutton = Y.one('#button-send');
64 this.messagebox = Y.one('#chat-messages');
65
c52b4db5 66 // Set aria attributes to messagebox and chat-userlist.
02a011ea
RT
67 this.messagebox.set('role', 'log');
68 this.messagebox.set('aria-live', 'polite');
69 var userlist = Y.one('#chat-userlist');
70 userlist.set('aria-live', 'polite');
71 userlist.set('aria-relevant', 'all');
72
c52b4db5 73 // Attach the default events for this module.
579a4976 74 this.sendbutton.on('click', this.send, this);
2daed78a
PS
75 this.messagebox.on('mouseenter', function() {
76 this.scrollable = false;
77 }, this);
78 this.messagebox.on('mouseleave', function() {
79 this.scrollable = true;
80 }, this);
579a4976 81
c52b4db5 82 // Send the message when the enter key is pressed.
579a4976
SH
83 Y.on('key', this.send, this.messageinput, 'press:13', this);
84
85 document.title = this.cfg.chatroom_name;
86
c52b4db5 87 // Prepare and execute the first AJAX request of information.
579a4976
SH
88 Y.io(this.api,{
89 method : 'POST',
90 data : build_querystring({
91 action : 'init',
92 chat_init : 1,
93 chat_sid : this.cfg.sid,
332fdda5 94 chat_theme : this.cfg.theme
579a4976
SH
95 }),
96 on : {
97 success : function(tid, outcome) {
5be94998 98 this.messageinput.removeAttribute('disabled');
579a4976 99 this.messageinput.set('value', '');
c67a139c 100 this.messageinput.focus();
579a4976
SH
101 try {
102 var data = Y.JSON.parse(outcome.responseText);
103 } catch (ex) {
104 return;
105 }
106 this.update_users(data.users);
107 }
108 },
109 context : this
110 });
111
c67a139c
DC
112 var scope = this;
113 this.interval = setInterval(function() {
114 scope.update_messages();
579a4976
SH
115 }, this.cfg.timer, this);
116
c52b4db5 117 // Create and initalise theme changing menu.
69ccc32d 118 this.thememenu = new Y.YUI2.widget.Menu('basicmenu', {xy:[0,0]});
579a4976 119 this.thememenu.addItems([
332fdda5
FR
120 {text: M.util.get_string('bubble', 'mod_chat'), url: this.cfg.chaturl + '&chat_theme=bubble'},
121 {text: M.util.get_string('compact', 'mod_chat'), url: this.cfg.chaturl + '&chat_theme=compact'},
122 {text: M.util.get_string('coursetheme', 'mod_chat'), url: this.cfg.chaturl + '&chat_theme=course_theme'}
579a4976
SH
123 ]);
124 this.thememenu.render(document.body);
c52b4db5
AD
125 Y.one('#choosetheme').on('click', function(e) {
126 this.moveTo((e.pageX - 20), (e.pageY - 20));
579a4976
SH
127 this.show();
128 }, this.thememenu);
887efbd9
SA
129
130 // Set the data-placement for the help-icon to display all the content.
131 this.helpicon = Y.one('#button-send + a');
132 this.dataset = this.helpicon.get('dataset');
133 this.dataset.placement = 'top';
134 this.helpicon.set('dataset', this.dataset);
579a4976
SH
135 },
136
137 append_message : function(key, message, row) {
c52b4db5
AD
138 var item = Y.Node.create('<li id="mdl-chat-entry-' + key + '">' + message.message + '</li>');
139 item.addClass((message.mymessage) ? 'mdl-chat-my-entry' : 'mdl-chat-entry');
579a4976
SH
140 Y.one('#messages-list').append(item);
141 if (message.type && message.type == 'beep') {
efe26818
DW
142 var audioElement = document.createElement('audio');
143 audioElement.setAttribute('src', '../beep.mp3');
144 audioElement.play();
579a4976
SH
145 }
146 },
147
148 send : function(e, beep) {
b12c3878 149 if((this.messageinput.get('value') != '') || (typeof beep != 'undefined')) {
64e7aa4d 150 this.sendbutton.set('value', M.util.get_string('sending', 'chat'));
b12c3878 151 var data = {
152 chat_message : (!beep) ? this.messageinput.get('value') : '',
153 chat_sid : this.cfg.sid,
332fdda5 154 chat_theme : this.cfg.theme
b12c3878 155 };
156 if (beep) {
157 data.beep = beep
158 }
159 data.action = 'chat';
160
161 Y.io(this.api, {
162 method : 'POST',
163 data : build_querystring(data),
164 on : {
165 success : this.send_callback
166 },
167 context : this
168 });
2daed78a 169 }
579a4976
SH
170 },
171
172 send_callback : function(tid, outcome, args) {
529817c8
DC
173 try {
174 var data = Y.JSON.parse(outcome.responseText);
175 } catch (ex) {
176 return;
579a4976 177 }
64e7aa4d 178 this.sendbutton.set('value', M.util.get_string('send', 'chat'));
529817c8 179 this.messageinput.set('value', '');
579a4976
SH
180 clearInterval(this.interval);
181 this.update_messages();
58f3f058
DC
182 var scope = this;
183 this.interval = setInterval(function() {
184 scope.update_messages();
579a4976
SH
185 }, this.cfg.timer, this);
186 },
187
e8a4928d 188 talkto: function (e, name) {
c52b4db5 189 this.messageinput.set('value', "To " + name + ": ");
579a4976
SH
190 this.messageinput.focus();
191 },
192
193 update_messages : function() {
194 this.cfg.req_count++;
467902f2 195 Y.io(this.api, {
579a4976
SH
196 method : 'POST',
197 data : build_querystring({
467902f2 198 action: 'update',
579a4976
SH
199 chat_lastrow : this.cfg.chat_lastrow || false,
200 chat_lasttime : this.cfg.chat_lasttime,
201 chat_sid : this.cfg.sid,
332fdda5 202 chat_theme : this.cfg.theme
579a4976
SH
203 }),
204 on : {
205 success : this.update_messages_callback
206 },
207 context : this
208 });
209 },
210
211 update_messages_callback : function(tid, outcome) {
212 try {
213 var data = Y.JSON.parse(outcome.responseText);
214 } catch (ex) {
215 return;
216 }
217 if (data.error) {
a8e3b008
DC
218 clearInterval(this.interval);
219 alert(data.error);
220 window.location = this.cfg.home;
579a4976
SH
221 }
222 this.cfg.chat_lasttime = data.lasttime;
223 this.cfg.chat_lastrow = data.lastrow;
c52b4db5 224 // Update messages.
579a4976 225 for (var key in data.msgs){
2daed78a 226 if (!M.util.in_array(key, this.messages)) {
579a4976
SH
227 this.messages.push(key);
228 this.append_message(key, data.msgs[key], data.lastrow);
229 }
230 }
c52b4db5 231 // Update users.
579a4976
SH
232 this.update_users(data.users);
233 // Scroll to the bottom of the message list
234 if (this.scrollable) {
c52b4db5 235 Y.Node.getDOMNode(this.messagebox).parentNode.scrollTop += 500;
579a4976
SH
236 }
237 this.messageinput.focus();
238 },
239
240 update_users : function(users) {
2daed78a 241 if (!users) {
579a4976
SH
242 return;
243 }
244 var list = Y.one('#users-list');
245 list.get('children').remove();
246 for (var i in users) {
c52b4db5 247 var li = Y.Node.create('<li><table><tr><td>' + users[i].picture + '</td><td></td></tr></table></li>');
579a4976 248 if (users[i].id == this.cfg.userid) {
c52b4db5 249 li.all('td').item(1).append(Y.Node.create('<strong><a target="_blank" href="' + users[i].url + '">' + users[i].name + '</a></strong>'));
579a4976 250 } else {
c52b4db5 251 li.all('td').item(1).append(Y.Node.create('<div><a target="_blank" href="' + users[i].url + '">' + users[i].name + '</a></div>'));
64e7aa4d 252 var talk = Y.Node.create('<a href="###">' + M.util.get_string('talk', 'chat') + '</a>');
e8a4928d 253 talk.on('click', this.talkto, this, users[i].name);
64e7aa4d 254 var beep = Y.Node.create('<a href="###">' + M.util.get_string('beep', 'chat') + '</a>');
e8a4928d 255 beep.on('click', this.send, this, users[i].id);
9d3b8b24 256 li.all('td').item(1).append(Y.Node.create('<div></div>').append(talk).append('&nbsp;').append(beep));
579a4976
SH
257 }
258 list.append(li);
259 }
260 }
2daed78a
PS
261
262 };
263
264 gui_ajax.init(cfg);
265};