diff --git a/mail.css b/mail.css index 862b088..0a5b9ba 100644 --- a/mail.css +++ b/mail.css @@ -1668,6 +1668,7 @@ div text-overflow: ellipsis; word-wrap: break-word; overflow: hidden; + white-space: nowrap; } .compose .headers .attach .attach-list .name diff --git a/mail.js b/mail.js index f828765..718a866 100644 --- a/mail.js +++ b/mail.js @@ -130,6 +130,7 @@ var DropDownBase = { } if (top + this.refs.dd.offsetHeight > wh) top = wh-this.refs.dd.offsetHeight; + this.refs.dd.style.display = ''; this.setState({ visible: true, top: top, left: left, calloutLeft: calloutLeft }); this.refs.dd.focus(); this.onClose = onClose; @@ -782,6 +783,78 @@ var ComposeWindow = React.createClass({ { this.setState({ text: ev.target.value }); }, + attachKeyDown: function(ev) + { + if (ev.keyCode == 46) // delete + { + for (var i = this.state.attachments.length-1; i >= 0; i--) + if (this.state.attachments[i].selected) + this.state.attachments.splice(i, 1); + this.setState({ attachments: this.state.attachments }); + ev.stopPropagation(); + } + else if (ev.keyCode == 40 || ev.keyCode == 38) // down, up + { + var sel = null, dir = (ev.keyCode == 40 ? 1 : -1); + for (var i = 0; i < this.state.attachments.length; i++) + { + if (this.state.attachments[i].selected) + { + sel = i; + break; + } + } + if (sel !== null && (sel+dir) >= 0 && (sel+dir) < this.state.attachments.length) + { + sel += dir; + for (var i = 0; i < this.state.attachments.length; i++) + this.state.attachments[i].selected = (i == sel); + this.setState({ attachments: this.state.attachments }); + var item = this.refs['a'+sel]; + if (item.offsetTop + item.offsetHeight > this.refs.scroll.scrollTop + this.refs.scroll.offsetHeight) + this.refs.scroll.scrollTop = item.offsetTop + item.offsetHeight - this.refs.scroll.offsetHeight; + else if (item.offsetTop < this.refs.scroll.scrollTop+this.refs.title.offsetHeight) + this.refs.scroll.scrollTop = item.offsetTop-this.refs.title.offsetHeight; + ev.stopPropagation(); + ev.preventDefault(); // prevent scroll + } + } + }, + selectAttachment: function(ev) + { + var t = ev.target; + while (t && !t.getAttribute('data-i')) + t = t.parentNode; + if (t) + { + var ns = parseInt(t.getAttribute('data-i')); + if (ev.shiftKey && this.lastSel) + { + if (ns < this.lastSel) + { + for (var i = 0; i < this.state.attachments.length; i++) + this.state.attachments[i].selected = i >= ns && i <= this.lastSel; + } + else if (ns > this.lastSel) + { + for (var i = 0; i < this.state.attachments.length; i++) + this.state.attachments[i].selected = i >= this.lastSel && i <= ns; + } + } + else if (ev.ctrlKey) + { + this.state.attachments[ns].selected = true; + this.lastSel = ns; + } + else + { + this.lastSel = ns; + for (var i = 0; i < this.state.attachments.length; i++) + this.state.attachments[i].selected = (i == ns); + } + this.setState({ attachments: this.state.attachments }); + } + }, render: function() { return
@@ -823,9 +896,9 @@ var ComposeWindow = React.createClass({
-
-
+
Attachment @@ -833,7 +906,8 @@ var ComposeWindow = React.createClass({
Size
{this.state.attachments.map((a, i) => -
+
{a.name}
{formatBytes(a.size)}
@@ -966,7 +1040,7 @@ var MessageView = React.createClass({ render: function() { var msg = this.state.msg; - return