Statistics
| Branch: | Tag: | Revision:

root / ui / static / snf / js / views.js @ 5dad72ea

History | View | Annotate | Download (9.5 kB)

1
;(function(root){
2
    
3
    // root
4
    var root = root;
5
    
6
    // setup namepsaces
7
    var snf = root.synnefo = root.synnefo || {};
8
    var models = snf.models = snf.models || {}
9
    var storage = snf.storage = snf.storage || {};
10
    var views = snf.views = snf.views || {}
11
    var util = snf.util = snf.util || {}
12

    
13
    // shortcuts
14
    var bb = root.Backbone;
15
    
16
    // logging
17
    var logger = new snf.logging.logger("SNF-VIEWS");
18
    var debug = _.bind(logger.debug, logger);
19
    
20
    // Base view object
21
    views.View = bb.View.extend({
22
        // the main element of the view
23
        // view delegates show, visible, hide etc to this element
24
        view_id: false,
25

    
26
        el: '#app',
27
        data_from: false,
28
        selectors: {},
29
        
30
        initialize: function() {
31
            this.log = new snf.logging.logger("SNF-VIEWS:" + this.view_id);
32
        },
33
    
34
        // is the view visible ?
35
        visible: function(){
36
            return $(this.el).is(":visible");
37
        },
38
        
39
        // hide view
40
        hide: function() {
41
            if (!this.visible()) { return this };
42
            return $(this.el).hide();
43
        },
44
        
45
        // show view
46
        show: function() {
47
            if (this.visible()) { return this };
48
            $(this.el).show();
49
            if (this.show_view) { this.show_view.apply(this, arguments)};
50
        },
51

    
52
        sel: function(id) {
53
            return this.$(this.selectors[id]);
54
        },
55

    
56
        // animations
57
        fadeIn: function(time, callback) {
58
            $(this.el).fadeIn(time, callback);
59
            return this.show();
60
        },
61

    
62
        fadeOut: function(time, callback) {
63
            $(this.el).fadeOut(time, callback);
64
            return this.hide();
65
        }
66
    });
67
    
68
    
69
    // overlays registry
70
    views._overlay_index = [];
71

    
72
    // overlay view helper
73
    views.Overlay = views.View.extend({
74
        view_id: 'overlay',
75
        tpl_selector: '#generic-overlay-tpl',
76
        css_class: 'overlay',
77
        oneInstance: true,
78
        fixed: false,
79

    
80
        
81
        initialize: function(options, selector) {
82
            this.defaults = {
83
                load: false,
84
                closeOnClick: false,
85
                mask: {
86
                    color: "#444",
87
                    loadSpeed: snf.config.overlay_speed || 0,
88
                    opacity: 0.7
89
                },
90
                speed: snf.config.overlay_speed || 200
91
            }
92
            
93
            this.tpl_selector = selector || this.tpl_selector;
94
            views.Overlay.__super__.initialize.apply(this);
95
            views._overlay_index.push(this);
96

    
97
            this.options = _.extend(this.defaults, options);
98
            this.options.clone = this.options.clone == undefined ? true : this.options.clonde;
99
            this.options.fixed = this.fixed;
100

    
101
            this.options.onOpen = this.options.onOpen || function() {};
102
            this.options.onClose = this.options.onClose || function() {};
103
            this.options.beforeOpen = this.options.beforeOpen || function() {};
104
            this.options.beforeClose = this.options.beforeClose || function() {};
105
            this.el = this.create_element();
106
            this.el.hide();
107
        
108
            var ajax_params = _.clone(this.options);
109

    
110
            ajax_params.onBeforeLoad = _.bind(this._beforeOpen, this);
111
            ajax_params.onLoad = _.bind(this._onOpen, this);
112
            ajax_params.onBeforeClose = _.bind(this._beforeClose, this);
113
            ajax_params.onClose = _.bind(this._onClose, this);
114
            ajax_params.oneInstance = this.oneInstance;
115
            // create overlay
116
            // TODO: does this return overlay object ?? (to avoid the next code line)
117
            $(this.el).overlay(ajax_params);
118

    
119
            this.overlay = $(this.el).overlay();
120
            this.append_css = this.options ? this.options.css_class ? this.options.css_class : "" : "";
121
            return this;
122
        },
123

    
124
        create_element: function() {
125
            var el = undefined;
126
            if (this.options.clone) {
127
                el = $(this.tpl_selector).clone();
128
            } else {
129
                el = $(this.tpl_selector);
130
            }
131
            
132
            // append content
133
            if (this.content_selector) {
134
                var content = $(this.content_selector).clone();
135
                content.addClass("content");
136
                
137
                if ($(el).find(".content").length) {
138
                    $(el).find(".content").replaceWith(content);
139
                }
140
                content.removeClass("hidden");
141
            }
142

    
143
            if (this.overlay_id) {
144
            }
145

    
146
            $(el).addClass("overlay");
147
            if (this.css_class) {
148
                $(el).addClass(this.css_class);
149
            }
150
            
151
            if (this.options.clone) {
152
                $("body").append(el);
153
            }
154

    
155
            return el;
156
        },
157

    
158
        set_title: function(title) {
159
            if (title || this.title) {
160
                $(this.el).find(".header .title").html(title || this.title)
161
            }
162
        },
163

    
164
        set_subtitle: function(subtitle) {
165
            if (subtitle || this.subtitle) {
166
                $(this.el).find(".header .subtitle").html(subtitle || this.subtitle)
167
            }
168
        },
169

    
170
        _beforeOpen: function() {
171
            if (this.append_css) {
172
                $(this.el).addClass(this.append_css);
173
            }
174

    
175
            this.set_title();
176
            this.set_subtitle();
177
            
178
            this.beforeOpen.apply(this, arguments);
179
            this.options.beforeOpen.apply(this, arguments);
180
        },
181

    
182
        _onOpen: function() {
183
            if ($(this.el).find(".closeme").length) {
184
                $(this.el).find(".closeme").click(_.bind(function(){
185
                    this.hide();
186
                }, this))
187
            }
188
            this.onOpen.apply(this, arguments);
189
            this.options.onOpen.apply(this, arguments);
190
        },
191

    
192
        _beforeClose: function() {
193
            this.beforeClose.apply(this, arguments);
194
            this.options.beforeClose.apply(this, arguments);
195
        },
196

    
197
        _onClose: function() {
198
            if (this.append_css) {
199
                $(this.el).removeClass(this.append_css);
200
            }
201
            this.onClose.apply(this, arguments);
202
            this.options.onClose.apply(this, arguments);
203
        },
204

    
205
        beforeOpen: function () {},
206
        onOpen: function () {},
207
        beforeClose: function () {},
208
        onClose: function () {},
209

    
210
        show: function() {
211
            // close opened overlays
212
            var hidden = false;
213
            _.each(views._overlay_index, function(ovr){
214
                if (ovr == this) { return };
215
                if (ovr.visible()) {
216
                    hidden = true;
217
                    ovr.hide();
218
                }
219
            })
220

    
221
            // do we need to wait for other overlays to close ???
222
            if (hidden) { delay = 300; } else { delay = 0; }
223
            window.setTimeout(_.bind(function(){ this.overlay.load() }, this), delay)
224
            return this;
225
        },
226

    
227
        hide: function() {
228
            if (!this.overlay.isOpened()) {
229
                // if its not opened events wont trigger
230
                this._onClose()
231
            } else {
232
                this.overlay.close();
233
            }
234
            return this;
235
        }
236
    });
237

    
238
    
239
    // overlay view helper
240
    views.VMOverlay = views.Overlay.extend({
241

    
242
        initialize: function() {
243
            views.VMOverlay.__super__.initialize.apply(this);
244
            this.vm = undefined;
245
            this.view_id_tpl = this.view_id;
246

    
247
            _.bindAll(this, "_handle_vm_change", "_handle_vm_remove");
248
        },
249

    
250
        set_vm: function(vm) {
251
            if (this.vm) { this.unbind_vm_handlers };
252
            this.vm = vm;
253
            this.view_id = this.view_id + "_" + vm.id;
254
            this.bind_vm_handlers();
255
        },
256

    
257
        bind_vm_handlers: function() {
258
            this.log.debug("binding handlers");
259
            this.vm.bind("change", this._handle_vm_change);
260
            storage.vms.bind("remove", this._handle_vm_remove);
261
        },
262
        
263
        unbind_vm_handlers: function() {
264
            this.log.debug("unbinding handlers", this.vm);
265
            if (!this.vm) { return };
266
            this.vm.unbind("change", this._handle_vm_change);
267
            storage.vms.unbind("remove", this._handle_vm_remove);
268
        },
269
        
270
        _update_vm_details: function() { 
271
            if (!this.vm) { console.error("invalid view state"); return }
272
            this.set_subtitle(this.vm.get("name") + snf.ui.helpers.vm_icon_tag(this.vm, "small"));
273

    
274
            var ico_path = snf.ui.helpers.os_icon_path(this.vm.get("OS"), "oslarge");
275
            this.$(".content").css({"background-image":"url(" + ico_path +")"})
276
            this.update_vm_details() 
277
        },
278

    
279
        update_vm_details: function() {},
280
        handle_vm_remove: function() {},
281
        handle_vm_change: function () {},
282
        
283
        _handle_vm_remove: function(vm, collection) {
284
            if (this.vm && vm.id == this.vm.id) {
285
                this.hide();
286
            }
287
            this.handle_vm_remove();
288
        },
289
        
290
        _handle_vm_change: function(vm) {
291
            this._update_vm_details();
292
            this.handle_vm_change(vm);
293
        },
294
        
295
        beforeClose: function() {
296
            this.unbind_vm_handlers();
297
            this.vm = undefined;
298
        },
299

    
300
        show: function(vm) {
301
            this.set_vm(vm);
302
            views.VMOverlay.__super__.show.apply(this, arguments);
303
            this._update_vm_details();
304
        }
305

    
306
    });
307

    
308
    snf.config.update_hidden_views = true;
309

    
310
})(this);