var React = require('react'); var Channel = require('./Channel'); var Mui = require('material-ui'); var FloatingActionButton = Mui.FloatingActionButton; var RightNav = require('./material-ui/right-nav.jsx'); var NUTELLA = require('nutella_lib'); var IdentitySelector = require('../identity-selector/main'); var Player = require('./Player'); var $ = require('jquery'); require('jquery-ui/draggable'); var Main = React.createClass({ componentDidMount: function() { var self = this; window.nutella = NUTELLA.init(self.props.params.broker, self.props.params.app_id, self.props.params.run_id, 'app', function(connected) { if(connected) { // Get current channels catalogue nutella.net.request('channels/retrieve', 'all', function (response) { self.handleUpdatedChannelsCatalogue(response); // TODO check that rid is within current available rids: if rids changed, catch error and ask for new one // If at startup info on id is already in state if(self.state.rid) { // Get current assigned channels (mapping) nutella.net.request('mapping/retrieve', 'all', function (response) { self.updateChannelsForRid(response, self.state.rid); }); } // Subscribe for future changes nutella.net.subscribe('mapping/updated', function (message, from) { self.updateChannelsForRid(message, self.state.rid); }); nutella.net.subscribe('currentConfig/switched', function (message, from) { self.handleActivitySwitch(message); }); nutella.net.subscribe('channels/updated', function (message, from) { nutella.net.request('mapping/retrieve', 'all', function (response) { self.handleUpdatedChannelsCatalogue(message, function() { self.updateChannelsForRid(response, self.state.rid); }); }); }); // Subscribe to teacher forced logout nutella.net.subscribe('logout/all', function (message, from) { self.handleLogout(); }); }); } }); }, /** * Manages the modal sidebar right after state change */ componentWillReceiveProps: function(nextProps) { var self = this; if(!this.state.rid) { this.refs.rightNav.open(); this.refs.rightNav.setState({ modal: true }); // Force update menu with resources nutella.net.request('mapping/retrieve', 'all', function (response) { self.handleUpdatedMapping(response); }); } else { this.refs.rightNav.setState({ modal: false }); } }, /** * Updates current available channels. * @param message list of channels * @param rid current identity */ updateChannelsForRid: function(message, rid) { var self = this; var myChannelsId = []; var myChannels = []; message.forEach(function (f) { for (var i in f.items) { var item = f.items[i]; if (item.name === rid) { myChannelsId = item.channels; break; } } }); for(var i=0; i); }, componentWillUnmount: function() { }, /** * Enables the tabs. */ handleTabsButton: function() { this.setState({tabs: true}); }, /** * Disables the tabs. */ handleOverlayTabs: function() { this.setState({tabs: false}); }, componentDidUpdate: function() { this.setupTabsButton(); }, setupTabsButton: function() { var fix = function() { $("
") .css({ top: 0, left: 0, width: window.innerWidth, height: window.innerHeight, position: "absolute", opacity: "0.001", zIndex: 1000 }) .appendTo("body"); }; var unfix = function() { $( ".ui-draggable-iframeFix" ).remove(); }; $(".tabs-button") .draggable({ containment: ".outer-div", start: function(event, ui) { fix(); }, stop: function(event, ui) { unfix(); } }) }, /** * Manages the transition between activities. * If old identity is still within the new available ones, then keeps it. * If not, it shows the identity-selector to pick the new one. */ handleActivitySwitch: function(mapping) { var ids = this.extractIdentitiesFromMapping(mapping); var id = this.state.rid; if(id) { if(ids.indexOf(id) !== -1) { this.updateChannelsForRid(mapping, this.state.rid); } else { this.setState({rid: null, modal: 'activity'}); } } else { this.setState({rid: null, modal: 'activity'}); } }, /** * Helper to extract identities from current mapping. * @param mapping * @returns {Array} */ extractIdentitiesFromMapping: function(mapping) { var ids = []; mapping.forEach(function (f) { for (var i in f.items) { if(f.items.hasOwnProperty(i) && f.items[i].name !== '') { ids.push(f.items[i].name); } } }); return ids; }, render: function() { if(!this.state.rid) { if(this.state.modal === 'activity') { return this.promptIdentitySelector('activity'); } return this.promptIdentitySelector('id'); } var self = this; var channels = []; for (var ch in this.state.channels) { if (this.state.channels.hasOwnProperty(ch)) { channels.push( ); } } var menuItems = []; this.state.mapping.forEach(function (f) { for (var i in f.items) { if(f.items.hasOwnProperty(i) && f.items[i].name !== '') { menuItems.push({ id: f.items[i].name, text: f.items[i].name, currentSelected: f.items[i].name === self.state.rid }); } } }); var backgroundMessageStyle = { position: 'fixed', left: '0', bottom: '50%', width: '100%', fontSize: '2.5vw', textAlign: 'center', color: '#9197a3', fontWeight: '300' }; var backgroundMessage = null; if(this.state.backgroundMessage) { backgroundMessage =

{this.state.backgroundMessage}

; } if(this.state.playing === null) { backgroundMessage =

{'Select a channel'}

; } var gridHeight = $('.grid').css('height'); var backgroundMessageTabsStyle = { position: 'fixed', left: '0', top: (parseInt(gridHeight) / 2) - 10, width: '100%', fontSize: '2.5vw', textAlign: 'center', color: 'rgba(255,255,255,0.8)', fontWeight: '300' }; var backgroundMessageTabs = null; if(this.state.backgroundMessageTabs) { backgroundMessageTabs =

{this.state.backgroundMessageTabs}

; } var canLogout = true; if(!this.state.rid) { canLogout = false; } var touchDivStyle = { width: '80px', height: '60px', position: 'fixed', bottom: 0, right: 0, zIndex: 250 }; var players = []; var ids = this.state.players; ids.forEach(function(id) { var p_id = self.state.playing; var playing = p_id === id; var player = ; players.push(player); }); var outerDivStyle = null; if(this.state.playing) { // prevent the scrolling only when there's a channel playing outerDivStyle = { position: 'relative', height: '100vh', overflow: 'hidden' }; } var buttonStyle = { zIndex: 110 }; var tabsButton =
; var overlayTabs = null; var tabsClass = ''; var overlayTabsStyle = { position: 'absolute', top: 0, left: 0, width: '100vw', height: '100vh', zIndex: 110 }; if(this.state.tabs) { overlayTabs =
; buttonStyle['opacity'] = 0; buttonStyle['pointerEvents'] = 'none'; } else { tabsClass = ' hidden-tabs'; } return (
{backgroundMessageTabs},{channels}
{tabsButton} {overlayTabs} {players} {backgroundMessage}
); } }); module.exports = Main;