define(['taskbar'], function(taskbar) { var composer = { active: undefined, posts: {} }; function allowed() { if(!(parseInt(app.uid, 10) > 0 || parseInt(config.allowGuestPosting, 10) === 1)) { app.alert({ type: 'danger', timeout: 5000, alert_id: 'post_error', title: 'Please Log In to Post', message: 'Posting is currently restricted to registered members only, click here to log in', clickfn: function() { ajaxify.go('login'); } }); return false; } return true; } composer.newTopic = function(cid) { if(allowed()) { push({ cid: cid, title: '', body: '', modified: false }); } } composer.newReply = function(tid, title, text) { if(allowed()) { push({ tid: tid, title: title, body: text, modified: false }); } } composer.editPost = function(pid) { if(allowed()) { socket.emit('api:composer.push', { pid: pid }, function(threadData) { push({ pid: pid, title: threadData.title, body: threadData.body, modified: false }); }); } } function push(post) { var uuid = utils.generateUUID(); taskbar.push('composer', uuid, { title: post.title ? post.title : 'New Topic', icon: post.picture }); composer.posts[uuid] = post; composer.load(uuid); } composer.load = function(post_uuid) { if($('#cmp-uuid-' + post_uuid).length) { composer.activateReposition(post_uuid); } else { composer.createNewComposer(post_uuid); } } composer.createNewComposer = function(post_uuid) { templates.preload_template('composer', function() { var composerTemplate = templates['composer'].parse({}); composerTemplate = $(composerTemplate); composerTemplate.attr('id', 'cmp-uuid-' + post_uuid); $(document.body).append(composerTemplate); composer.activateReposition(post_uuid); var postContainer = $(composerTemplate[0]); if(config.allowFileUploads || config.imgurClientIDSet) initializeFileReader(post_uuid); var postData = composer.posts[post_uuid], titleEl = postContainer.find('.title'), bodyEl = postContainer.find('textarea'); if (parseInt(postData.tid) > 0) { titleEl.val('Replying to: ' + postData.title); titleEl.prop('readOnly', true); } else if (parseInt(postData.pid) > 0) { titleEl.val(postData.title); titleEl.prop('readOnly', true); socket.emit('api:composer.editCheck', postData.pid, function(editCheck) { if (editCheck.titleEditable) { postContainer.find('input').prop('readonly', false); } }); } else { titleEl.val(postData.title); titleEl.prop('readOnly', false); } bodyEl.val(postData.body); postContainer.on('change', 'input, textarea', function() { composer.posts[post_uuid].modified = true; }); function getUniqueUserslugs() { var postContainer = $('#post-container'); if(postContainer.length) { var elements = $('#post-container li[data-userslug]'); if(!elements.length) { return []; } var slugs = []; for(var i=0; i= 768) { postContainer.css('width', Math.floor(bodyRect.width * percentage) + 'px'); } else { postContainer.css('width', '100%'); } } if(config.imgurClientIDSet) { postContainer.find('.upload-instructions').removeClass('hide'); postContainer.find('.img-upload-btn').removeClass('hide'); } if(config.allowFileUploads) { postContainer.find('.file-upload-btn').removeClass('hide'); } postContainer.css('visibility', 'visible'); composer.focusElements(post_uuid); } composer.focusElements = function(post_uuid) { var postContainer = $('#cmp-uuid-' + post_uuid), postData = composer.posts[post_uuid], titleEl = postContainer.find('.title'), bodyEl = postContainer.find('textarea'); if ((parseInt(postData.tid) || parseInt(postData.pid)) > 0) { bodyEl.focus(); bodyEl.selectionStart = bodyEl.val().length; bodyEl.selectionEnd = bodyEl.val().length; } else if (parseInt(postData.cid) > 0) { titleEl.focus(); } } composer.post = function(post_uuid) { var postData = composer.posts[post_uuid], postContainer = $('#cmp-uuid-' + post_uuid), titleEl = postContainer.find('.title'), bodyEl = postContainer.find('textarea'); titleEl.val(titleEl.val().trim()); bodyEl.val(bodyEl.val().trim()); if(postData.uploadsInProgress && postData.uploadsInProgress.length) { return composerAlert('Still uploading', 'Please wait for uploads to complete.'); } else if (titleEl.val().length < parseInt(config.minimumTitleLength, 10)) { return composerAlert('Title too short', 'Please enter a longer title. At least ' + config.minimumTitleLength+ ' characters.'); } else if (titleEl.val().length > parseInt(config.maximumTitleLength, 10)) { return composerAlert('Title too long', 'Please enter a shorter title. Titles can\'t be longer than ' + config.maximumTitleLength + ' characters.'); } else if (bodyEl.val().length < parseInt(config.minimumPostLength, 10)) { return composerAlert('Content too short', 'Please enter a longer post. At least ' + config.minimumPostLength + ' characters.'); } // Still here? Let's post. if (parseInt(postData.cid) > 0) { socket.emit('api:topics.post', { 'title' : titleEl.val(), 'content' : bodyEl.val(), 'category_id' : postData.cid }); } else if (parseInt(postData.tid) > 0) { socket.emit('api:posts.reply', { 'topic_id' : postData.tid, 'content' : bodyEl.val() }); } else if (parseInt(postData.pid) > 0) { socket.emit('api:posts.edit', { pid: postData.pid, content: bodyEl.val(), title: titleEl.val() }); } composer.discard(post_uuid); } function composerAlert(title, message) { app.alert({ type: 'danger', timeout: 2000, title: title, message: message, alert_id: 'post_error' }); } composer.discard = function(post_uuid) { if (composer.posts[post_uuid]) { $('#cmp-uuid-' + post_uuid).remove(); delete composer.posts[post_uuid]; composer.active = undefined; taskbar.discard('composer', post_uuid); } } composer.minimize = function(post_uuid) { var postContainer = $('#cmp-uuid-' + post_uuid); postContainer.css('visibility', 'hidden'); composer.active = undefined; taskbar.minimize('composer', post_uuid); } function initializeFileReader(post_uuid) { if(jQuery.event.props.indexOf('dataTransfer') === -1) { jQuery.event.props.push('dataTransfer'); } var draggingDocument = false; if(window.FileReader) { var postContainer = $('#cmp-uuid-' + post_uuid), drop = postContainer.find('.imagedrop'), textarea = postContainer.find('textarea'); $(document).off('dragstart').on('dragstart', function(e) { draggingDocument = true; }).off('dragend').on('dragend', function(e) { draggingDocument = false; }); textarea.on('dragenter', function(e) { if(draggingDocument) { return; } drop.css('top', textarea.position().top + 'px'); drop.css('height', textarea.height()); drop.css('line-height', textarea.height() + 'px'); drop.show(); drop.on('dragleave', function(ev) { drop.hide(); drop.off('dragleave'); }); }); function cancel(e) { e.preventDefault(); return false; } drop.on('dragover', cancel); drop.on('dragenter', cancel); drop.on('drop', function(e) { e.preventDefault(); var dt = e.dataTransfer, files = dt.files; for (var i=0; i parseInt(config.maximumFileSize, 10) * 1024) { return composerAlert('File too big', 'Maximum allowed file size is ' + config.maximumFileSize + 'kbs'); } uploadFile('api:posts.uploadFile', post_uuid, fileData); } }); reader.readAsDataURL(file); } function uploadFile(method, post_uuid, img) { var linkStart = method === 'api:posts.uploadImage' ? '!' : '', postContainer = $('#cmp-uuid-' + post_uuid), textarea = postContainer.find('textarea'), text = textarea.val(), imgText = linkStart + '[' + img.name + '](uploading...)'; text += imgText; textarea.val(text + " "); if(!composer.posts[post_uuid].uploadsInProgress) { composer.posts[post_uuid].uploadsInProgress = []; } composer.posts[post_uuid].uploadsInProgress.push(1); socket.emit(method, img, function(err, data) { var currentText = textarea.val(); if(err) { textarea.val(currentText.replace(imgText, linkStart + '[' + img.name + '](upload error)')); return app.alertError(err.message); } textarea.val(currentText.replace(imgText, linkStart + '[' + data.name + '](' + data.url + ')')); composer.posts[post_uuid].uploadsInProgress.pop(); }); } return { newTopic: composer.newTopic, newReply: composer.newReply, editPost: composer.editPost, load: composer.load, minimize: composer.minimize }; });