JSFiddle - React, Tailwind, and code Playground
HTML
<script src="https://code.jquery.com/jquery-2.1.3.min.js"></script>
<div class="col-md-12" data-bind="foreach: dropZones">
<div class="dropZone" data-bind="filedrop: { hover: hovering, drop: files }">
<div class="textPane" data-bind="visible: !hovering()">
<div class="buttonBar">
<img src="Content/images/cancel27.png" alt="Cancel" title="Cancel" />
<img src="Content/images/correctBox2.png" alt="Save" title="Save" />
</div>
<textarea maxlength="25000" data-bind="value: text" placeholder="Start typing here…"></textarea>
</div>
<div class="dropPane" data-bind="visible: hovering">Drop files here…</div>
</div>
</div>
<pre data-bind="text: ko.toJSON($root, null, 2)"></pre>
CSS
.dropZone {
position: relative;
margin-top: 20px;
height: 120px;
border: 2px dashed #bbb;
padding: 10px;
}
.textPane textarea {
box-sizing: border-box;
width: 100%;
}
.dropPane {
position: relative;
text-align: center;
z-index: -1;
line-height: 120px;
}
.buttonBar {
text-align: right;
}
.buttonBar img {
padding-left: 5px;
}
JavaScript
ko.bindingHandlers.filedrop = {
init: function (element, valueAccessor) {
var options = valueAccessor();
ko.utils.registerEventHandler(element, "dragenter", function (e) {
if (ko.isWriteableObservable(options.hover)) options.hover(true);
e.preventDefault();
});
ko.utils.registerEventHandler(element, "dragleave", function (e) {
if (ko.isWriteableObservable(options.hover)) options.hover(false);
e.preventDefault();
});
ko.utils.registerEventHandler(element, "dragover", function (e) {
e.preventDefault();
});
ko.utils.registerEventHandler(element, "drop", function (e) {
if (ko.isWriteableObservable(options.drop)) {
if (typeof options.drop.push === "function") {
console.log(e.dataTransfer.files);
options.drop.push.apply(options.drop, e.dataTransfer.files);
} else {
options.drop(e.dataTransfer.files);
console.log(e.dataTransfer.files);
}
}
if (ko.isWriteableObservable(options.hover)) options.hover(false);
e.preventDefault();
});
}
};
function DropZone() {
var self = this;
self.text = ko.observable();
self.files = ko.observableArray();
self.hovering = ko.observable(false);
self.filenames = ko.computed(function () {
return ko.utils.arrayMap(self.files(), function (element) {
return element.name;
});
});
}
function ViewModel() {
var self = this;
self.dropZones = ko.observableArray([
new DropZone()
]);
}
ko.applyBindings(new ViewModel());