~ubuntu-branches/ubuntu/saucy/mumble-django/saucy-proposed

« back to all changes in this revision

Viewing changes to pyweb/mumble/media/js/channelviewer.js

  • Committer: Package Import Robot
  • Author(s): Michael Ziegler
  • Date: 2013-05-19 18:06:11 UTC
  • mfrom: (1.2.6)
  • Revision ID: package-import@ubuntu.com-20130519180611-flqpsk20fu2t6hq4
Tags: 2.9-1
* New upstream release.
* Drop DM-Upload-Allowed as it isn't used any longer.
* Update VCS-{SVN,Browser} tags.
* Update Django dependency to 1.5.
* Remove template patch for django-registration 0.8 (applied upstream).
* Remove the hunk that adds MessageMiddleware to settings.py (applied
  upstream).
* Disable the registration app for now (incompatible to Django 1.5).
* Remove dependency to python-simplejson.
* Adapt apache config to staticfiles change.

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
 
// kate: space-indent on; indent-width 4; replace-tabs on;
2
 
 
3
 
/**
4
 
 *  Copyright © 2010, Michael "Svedrin" Ziegler <diese-addy@funzt-halt.net>
5
 
 *
6
 
 *  Mumble-Django is free software; you can redistribute it and/or modify
7
 
 *  it under the terms of the GNU General Public License as published by
8
 
 *  the Free Software Foundation; either version 2 of the License, or
9
 
 *  (at your option) any later version.
10
 
 *
11
 
 *  This package is distributed in the hope that it will be useful,
12
 
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
13
 
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14
 
 *  GNU General Public License for more details.
15
 
 *
16
 
 *  Documentation for this channel viewer can be found here:
17
 
 *    http://mumble-django.org/docs/api/channelviewer.html
18
 
 */
19
 
 
20
 
Ext.namespace('Ext.ux');
21
 
 
22
 
if( typeof gettext == "undefined" ){
23
 
    // Cope with Django's jsi18n not being available by adding dummy gettext
24
 
    gettext = function( text ){
25
 
        return text;
26
 
    };
27
 
    gettext_noop = gettext;
28
 
}
29
 
 
30
 
Ext.ux.MumbleChannelNodeUI = Ext.extend(Ext.tree.TreeNodeUI, {
31
 
    renderElements : function(n, a, targetNode, bulkRender){
32
 
        Ext.ux.MumbleUserNodeUI.superclass.renderElements.call( this, n, a, targetNode, bulkRender );
33
 
        Ext.DomHelper.applyStyles( this.elNode, 'position: relative' );
34
 
        var tpl = new Ext.DomHelper.createTemplate(
35
 
            '<img style="position: absolute; top: 0px; right: {pos}px;" src="{imageurl}/{icon}.png"/>'
36
 
            );
37
 
        var icons = []
38
 
        if( a.chandata.description != "" ) icons.push( "comment_seen" );
39
 
        var pos = 8;
40
 
        for( var i = 0; i < icons.length; i++ ){
41
 
            tpl.append( this.elNode, {'imageurl': a.imageurl, 'icon': icons[i], 'pos': pos} );
42
 
            pos += 18
43
 
        }
44
 
    }
45
 
});
46
 
 
47
 
Ext.ux.MumbleUserNodeUI = Ext.extend(Ext.tree.TreeNodeUI, {
48
 
    renderElements : function(n, a, targetNode, bulkRender){
49
 
        Ext.ux.MumbleUserNodeUI.superclass.renderElements.call( this, n, a, targetNode, bulkRender );
50
 
        Ext.DomHelper.applyStyles( this.elNode, 'position: relative' );
51
 
        var tpl = new Ext.DomHelper.createTemplate(
52
 
            '<img style="position: absolute; top: 0px; right: {pos}px;" src="{imageurl}/{icon}.png"/>'
53
 
            );
54
 
        var icons = []
55
 
        if( a.userdata.userid != -1 )    icons.push( "authenticated" );
56
 
        if( a.userdata.selfDeaf )        icons.push( "deafened_self" );
57
 
        if( a.userdata.deaf )            icons.push( "deafened_server" );
58
 
        if( a.userdata.selfMute )        icons.push( "muted_self" );
59
 
        if( a.userdata.suppress )        icons.push( "muted_suppressed" );
60
 
        if( a.userdata.mute )            icons.push( "muted_server" );
61
 
        if( a.userdata.comment != "" )   icons.push( "comment_seen" );
62
 
        if( a.userdata.prioritySpeaker ) icons.push( "priority_speaker" );
63
 
        if( a.userdata.recording )       icons.push( "recording" );
64
 
        var pos = 8;
65
 
        for( var i = 0; i < icons.length; i++ ){
66
 
            tpl.append( this.elNode, {'imageurl': a.imageurl, 'icon': icons[i], 'pos': pos} );
67
 
            pos += 18
68
 
        }
69
 
    }
70
 
});
71
 
 
72
 
function cmp_channels( left, rite ){
73
 
    // Compare two channels, first by position, and if that equals, by name.
74
 
    if( typeof left.position != "undefined" && typeof rite.position != "undefined" ){
75
 
        byorder = left.position - rite.position;
76
 
        if( byorder != 0 )
77
 
            return byorder;
78
 
    }
79
 
    return left.name.localeCompare(rite.name);
80
 
}
81
 
 
82
 
function cmp_names( left, rite ){
83
 
    return left.name.localeCompare(rite.name);
84
 
}
85
 
 
86
 
Ext.ux.MumbleChannelViewer = function( config ){
87
 
    Ext.apply( this, config );
88
 
 
89
 
    Ext.applyIf( this, {
90
 
        title: gettext("Channel Viewer"),
91
 
        refreshInterval: 30000,
92
 
        idleInterval: 2,
93
 
        usersAboveChannels: false,
94
 
        autoScroll: true,
95
 
        enableDD:   false, // Users need to enable this explicitly
96
 
        root: {
97
 
            text: gettext("Loading..."),
98
 
            leaf: true
99
 
        },
100
 
        listeners: {}
101
 
    });
102
 
 
103
 
    Ext.applyIf( this.listeners, {
104
 
        dragdrop: function( tree, node, targetdd, ev ){
105
 
            if( typeof node.attributes.userdata != "undefined" )
106
 
                tree.fireEvent("moveUser", tree, node.attributes.userdata, targetdd.dragOverData.target.attributes.chandata);
107
 
            else if( typeof node.attributes.chandata != "undefined" )
108
 
                tree.fireEvent("moveChannel", tree, node.attributes.chandata, targetdd.dragOverData.target.attributes.chandata);
109
 
        }
110
 
    });
111
 
 
112
 
    Ext.applyIf( this, {
113
 
        // This stuff needs the above applied already
114
 
        bbar: [ gettext("Auto-Refresh")+':', {
115
 
                xtype:   "checkbox",
116
 
                ref:     "../cbAutoRefresh",
117
 
                scope:   this,
118
 
                handler: this.setAutoRefresh,
119
 
                checked: (this.refreshInterval > 0),
120
 
            }, {
121
 
                xtype:   "numberfield",
122
 
                width:   30,
123
 
                value:   this.refreshInterval / 1000,
124
 
                ref:     "../nfAutoRefreshInterval",
125
 
                scope: this,
126
 
                selectOnFocus: true,
127
 
                listeners: {
128
 
                    render: function(c) {
129
 
                        Ext.QuickTips.register({
130
 
                            target: c.getEl(),
131
 
                            text:   gettext('Enter the interval in seconds in which the channel viewer should refresh and hit Enter.')
132
 
                        });
133
 
                    },
134
 
                    specialkey: function( field, ev ){
135
 
                        if( ev.getKey() == ev.ENTER ){
136
 
                            this.scope.setAutoRefresh(); // lawl
137
 
                            this.blur();
138
 
                        }
139
 
                    }
140
 
                },
141
 
            }, gettext("Seconds"), '->', {
142
 
                xtype:   "button",
143
 
                text:    gettext("Refresh"),
144
 
                handler: this.refresh,
145
 
                scope:   this
146
 
            }]
147
 
    } );
148
 
 
149
 
    Ext.ux.MumbleChannelViewer.superclass.constructor.call( this );
150
 
 
151
 
    this.addEvents({
152
 
        'moveUser':    true,
153
 
        'moveChannel': true
154
 
    });
155
 
 
156
 
    this.autoRefreshId = 0;
157
 
    this.setAutoRefresh();
158
 
    if( this.refreshInterval == 0 )
159
 
        this.refresh();
160
 
}
161
 
 
162
 
Ext.extend( Ext.ux.MumbleChannelViewer, Ext.tree.TreePanel, {
163
 
    setAutoRefresh: function(){
164
 
        if( this.autoRefreshId != 0 ){
165
 
            clearTimeout( this.autoRefreshId );
166
 
        }
167
 
        if( this.cbAutoRefresh.getValue() ){
168
 
            this.refreshInterval = this.nfAutoRefreshInterval.getValue() * 1000;
169
 
            this.autoRefresh();
170
 
        }
171
 
        else{
172
 
            this.refreshInterval = 0;
173
 
        }
174
 
    },
175
 
 
176
 
    autoRefresh: function(){
177
 
        this.refresh();
178
 
        if( this.refreshInterval > 0 ){
179
 
            this.autoRefreshId = this.autoRefresh.defer( this.refreshInterval, this );
180
 
        }
181
 
    },
182
 
 
183
 
    refresh: function(){
184
 
        var conn = new Ext.data.Connection();
185
 
        conn.request({
186
 
            url:    this.source_url,
187
 
            scope:  this,
188
 
            success: function( resp, opt ){
189
 
                var respdata = Ext.decode( resp.responseText );
190
 
                var root = {
191
 
                    text: respdata.name,
192
 
                    nodeType: 'async',
193
 
                    id:   "mumbroot",
194
 
                    leaf: false,
195
 
                    icon: this.imageurl+'/mumble.16x16.png',
196
 
                    children: [],
197
 
                    chandata: respdata.root,
198
 
                    uiProvider: Ext.ux.MumbleChannelNodeUI,
199
 
                    imageurl: this.imageurl
200
 
                };
201
 
                tree = this;
202
 
                function populateNode( node, json ){
203
 
                    var subchan_users = 0;
204
 
                    var popChannels = function(){
205
 
                        json.channels.sort(cmp_channels);
206
 
                        for( var i = 0; i < json.channels.length; i++ ){
207
 
                            var child = {
208
 
                                text: json.channels[i].name,
209
 
                                id:   ("channel_" + json.channels[i].id),
210
 
                                nodeType: 'async',
211
 
                                allowDrag: true,
212
 
                                allowDrop: true,
213
 
                                draggable: true,
214
 
                                icon: tree.imageurl+'/channel.png',
215
 
                                children: [],
216
 
                                uiProvider: Ext.ux.MumbleChannelNodeUI,
217
 
                                chandata: json.channels[i],
218
 
                                imageurl: tree.imageurl
219
 
                            };
220
 
                            node.children.push( child );
221
 
                            subchan_users += populateNode( child, json.channels[i] );
222
 
                        }
223
 
                    }
224
 
                    var popUsers = function(){
225
 
                        json.users.sort(cmp_names);
226
 
                        for( var i = 0; i < json.users.length; i++ ){
227
 
                            var child = {
228
 
                                text: json.users[i].name,
229
 
                                id:   ("user_" + json.users[i].session),
230
 
                                nodeType: 'async',
231
 
                                leaf: true,
232
 
                                allowDrag: true,
233
 
                                draggable: true,
234
 
                                uiProvider: Ext.ux.MumbleUserNodeUI,
235
 
                                userdata: json.users[i],
236
 
                                imageurl: tree.imageurl
237
 
                            };
238
 
                            if( json.users[i].idlesecs <= tree.idleInterval )
239
 
                                child.icon = tree.imageurl+'/talking_on.png';
240
 
                            else
241
 
                                child.icon = tree.imageurl+'/talking_off.png';
242
 
                            node.leaf = false;
243
 
                            node.children.push( child );
244
 
                        }
245
 
                    }
246
 
                    if( tree.usersAboveChannels ){
247
 
                        popUsers();
248
 
                        popChannels();
249
 
                    }
250
 
                    else{
251
 
                        popChannels();
252
 
                        popUsers();
253
 
                    }
254
 
                    if( json.id == 0 || json.users.length > 0 || subchan_users )
255
 
                        node.expanded = true;
256
 
                    return subchan_users + json.users.length;
257
 
                }
258
 
                populateNode( root, respdata.root );
259
 
                this.setRootNode( root );
260
 
            },
261
 
            failure: function( resp, opt ){
262
 
                if( resp.isTimeout === true )
263
 
                    // Ignore, happens from time to time
264
 
                    return;
265
 
                if( this.refreshInterval > 0 )
266
 
                    this.cbAutoRefresh.setValue(false);
267
 
                Ext.Msg.show({
268
 
                    title: gettext("Update error"),
269
 
                    msg:   gettext("Querying the server failed, so the channel viewer has not been updated."),
270
 
                    icon:  Ext.MessageBox.ERROR,
271
 
                    buttons: Ext.MessageBox.OK
272
 
                    });
273
 
            },
274
 
        });
275
 
    },
276
 
} );
277
 
 
278
 
Ext.reg( 'mumblechannelviewer', Ext.ux.MumbleChannelViewer );