Restyled message attachments

Added a size limit, added functionality to delete the attachments before sending in a more user-friendly way
This commit is contained in:
Emily Chao 2015-01-15 16:17:54 -10:00 committed by lilia
parent 9baafddb14
commit bb2b53035e
4 changed files with 225 additions and 12 deletions

View file

@ -33,6 +33,7 @@
</div>
<div id='contacts'></div>
</div>
<div id='file-modal'></div>
<script type='text/x-tmpl-mustache' id='new-group-update-form'>
<div>
<input type='text' name='name' class='name' placeholder='Group Name' value="{{ name }}">
@ -57,7 +58,7 @@
<form class='send'>
<input class='send-message' rows='6' type='textarea'>
<div class='attachments'>
<input type='file' name='files[]' multiple class='file-input'>
<input type='file' name='files[]' class='file-input'>
</div>
</form>
</div>
@ -113,7 +114,7 @@
<div class='message-composer'>
<input name='message' class='send-message' rows='6' type='textarea'>
<div class='attachments'>
<input type='file' name='files[]' multiple class='file-input'>
<input type='file' name='files[]' class='file-input'>
</div>
<input type='submit'>
</div>
@ -139,7 +140,7 @@
<div class='message-composer'>
<input class='send-message' rows='6' type='textarea'>
<div class='attachments'>
<input type='file' name='files[]' multiple class='file-input'>
<input type='file' name='files[]' class='file-input'>
</div>
<input type='submit'>
</div>
@ -154,6 +155,28 @@
</div>
</form>
</script>
<script type='text/x-tmpl-mustache' id='attachment-preview'>
<div class="imageAttachment">
<img src="{{ source }}" class="preview" />
<div class="close">x</div>
</div>
</script>
<script type='text/x-tmpl-mustache' id='file-size-modal'>
<div id="modal" class="modal-wrapper">
<div class="modal-content">
<div class="modal-container">
<div class="modal-banner">
<span>File Too Large</span>
<div class="modal-close"><a class="modal-close-button" href="#" title="Close">X</a></div>
</div>
<div class="modal-inner modal-padding">
<p>This file exceeds 420KB. Please attach a smaller file.</p>
<button id="closeModal"><a href="#">OK</a></button>
</div>
</div>
</div>
</div>
</script>
<script type="text/javascript" src="js/components.js"></script>
<script type="text/javascript" src="js/libtextsecure.js"></script>
@ -168,6 +191,7 @@
<script type="text/javascript" src="js/chromium.js"></script>
<script type="text/javascript" src="js/views/notifications.js"></script>
<script type="text/javascript" src="js/views/file_modal_view.js"></script>
<script type="text/javascript" src="js/views/file_input_view.js"></script>
<script type="text/javascript" src="js/views/list_view.js"></script>
<script type="text/javascript" src="js/views/new_group_update_view.js"></script>

View file

@ -22,25 +22,33 @@ var Whisper = Whisper || {};
className: 'file-input',
initialize: function() {
this.$input = this.$el.find('input[type=file]');
this.modal = new Whisper.ModalView({el: $('#file-modal')});
},
events: {
'change': 'previewImages'
'change': 'previewImages',
'click .close': 'deleteFiles'
},
addThumb: function(e) {
this.$el.append(
$('<img>').attr( "src", e.target.result ).addClass('preview')
);
var attachmentPreview = $('#attachment-preview').html();
Mustache.parse(attachmentPreview);
this.$el.append($(Mustache.render(attachmentPreview, {source: e.target.result})));
},
previewImages: function() {
this.$el.find('img').remove();
this.clearForm();
var files = this.$input.prop('files');
for (var i = 0; i < files.length; i++) {
var FR = new FileReader();
FR.onload = this.addThumb.bind(this);
FR.readAsDataURL(files[i]);
if ((files[i].size/1024).toFixed(4) >= 420) {
this.modal.open();
this.deleteFiles();
}
else {
FR.onload = this.addThumb.bind(this);
FR.readAsDataURL(files[i]);
}
}
},
@ -63,9 +71,18 @@ var Whisper = Whisper || {};
}.bind(this));
promises.push(p);
}
this.$el.find('img').remove();
this.clearForm();
return Promise.all(promises);
}
},
clearForm: function() {
this.$el.find('div.imageAttachment').remove();
},
deleteFiles: function() {
this.clearForm();
this.$input.wrap('<form>').parent('form').trigger('reset');
this.$input.unwrap();
}
});
})();

View file

@ -0,0 +1,47 @@
/* vim: ts=4:sw=4:expandtab
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
var Whisper = Whisper || {};
(function () {
'use strict';
Whisper.ModalView = Backbone.View.extend({
tagName: 'div',
className: 'file-overload-modal',
initialize: function() {
this.template = $('#file-size-modal').html();
Mustache.parse(this.template);
this.render();
},
render: function() {
this.$el.html($(Mustache.render(this.template)));
return this;
},
events: {
'click .modal-close': 'close',
'click #closeModal': 'close'
},
open: function() {
this.$el.find('#modal').show();
},
close: function() {
this.$el.find('#modal').hide();
}
});
})();

View file

@ -73,9 +73,37 @@ li.entry img {
margin-top: 5px;
}
div.imageAttachment {
height: 30px;
width: 30px;
float: left;
margin: 6px;
position: relative;
}
img.preview {
width: 30px;
height: 30px;
overflow: hidden;
position: relative;
}
.close {
font-family: sans-serif;
color: white;
position: absolute;
top: -10px;
left: 20px;
text-align: center;
cursor: default;
border-radius: 50%;
width: 20px;
height: 20px;
padding: 0px;
background: #666;
color: #fff;
text-align: center;
}
.bootstrap-tagsinput .tag {
@ -86,4 +114,101 @@ img.preview {
ul.country-list {
min-width: 197px !important;
}
div.attachments {
width: 95% !important;
}
input.file-input {
float: left !important;
}
.modal-wrapper {
position: fixed;
top: 0;
left: 0;
right: 0;
bottom: 0;
width: 100%;
z-index: 10000 !important;
display: none;
}
.modal-content {
position: absolute;
top: 0;
width: 100%;
height: 100%;
overflow: auto;
overflow-y: scroll;
}
.modal-container {
background-color: #FFFFFF;
width: 450px;
-webkit-box-shadow: 0 0 7px 0 #000000;
moz-box-shadow: 0 0 7px 0 #000000;
box-shadow: 0 0 7px 0 #000000;
display: block;
z-index: 10000 !important;
margin: 45px auto;
position: relative;
border: 1px solid #666;
}
.modal-banner {
background-color: #00badd;
color: #ffffff;
height: 45px;
line-height: 45px;
vertical-align: middle;
text-align: center;
font-wight: bold;
font-size: 1.5em;
position: relative;
}
.modal-banner span {
padding: 0 20px;
}
.modal-close {
position: absolute;
top: 0;
right: 12px;
bottom: 0;
}
.modal-close a.modal-close-button {
color: #FFFFFF;
text-decoration: none;
font-size: .8em;
}
.modal-inner {
overflow: hidden;
}
.modal-inner>p {
color: black !important;
}
.modal-padding {
padding: 16px 18px;
}
@media only screen and (max-width: 450px) {
.modal-container {
width: 100%;
margin: 0 auto;
}
.modal-banner {
height: 32px;
line-height: 32px;
vertical-align: middle;
text-align: center;
font-wight: bold;
font-size: 1em;
position: relative;
}
}