Dropzonejs resort appended images - javascript

I have dropzone box and I've implemented sortable into it. As my form submits with html and not ajax I had to add hidden inputs where I push my selected images with dropzonejs therefore I could get them in back-end.
So far everything I explained above is working
Issue
As I mentioned I've implemented sortable functionality into dropzonejs and it does sort images in dropzone box, but not in my appended hidden input
In order to get sorted images in back-end I need to apply that sortable into my appended input as well.
Code
HTML
//Drop zone box
<div class="dropzone" id="my-awesome-dropzone" action="#">
<div class="fallback">
<input name="cimages[]" type="file" multiple />
</div>
<div class="clearfix"></div>
</div>
// append hidden input include selected images for back-end use
<div id="botofform"></div>
Script
Dropzone.autoDiscover = false;
var myDropzone = new Dropzone("#my-awesome-dropzone", {
headers: {
"X-CSRF-TOKEN": $("meta[name='csrf-token']").attr("content")
},
autoProcessQueue : false,
acceptedFiles: ".jpeg,.jpg,.png,.gif",
dictDefaultMessage: "Drag an image here to upload, or click to select one",
maxFiles: 15, // Maximum Number of Files
maxFilesize: 8, // MB
addRemoveLinks: true,
dictRemoveFile: 'Remove',
dictFileTooBig: 'Image is bigger than 8MB',
// append hidden input and add selected images
accept: function(file) {
let fileReader = new FileReader();
fileReader.readAsDataURL(file);
fileReader.onloadend = function() {
let content = fileReader.result;
$('#botofform').append('<input type="hidden" class="cimages" name="cimages[]" value="'+ content +'">');
file.previewElement.classList.add("dz-success");
}
file.previewElement.classList.add("dz-complete");
}
});
// reorder images in dropzone box (need to get this results into "$('#botofform').append" above)
$(function(){
$(".dropzone").sortable({
items:'.dz-preview',
cursor: 'move',
opacity: 0.5,
containment: '.dropzone',
distance: 20,
tolerance: 'pointer',
});
});
Question
How can I apply sortable results into my appended input?
How do I reduce $('#botofform') items (inputs) when an image gets removed by dropzonejs?

You can use data-attribute for both your div where image is added and input field .So, whenever new file is uploaded you can use setAttribute("data-id", count) here count can be any random number only make sure this value should be same for both input and div because this will help us to remove and sort inputs .
Now , for sorting inputs you can use stop event this will get called when sorting is stop .Inside this you can loop through dropzone div and then get attribute which we have added earlier using this attribute we can find the input and append same to botofform div.
Finally , for deleting files you can use remove files event this will get called whenever remove link is clicked so here you simply need to get that data-id which is added to div then use this attribute to remove input as well.
Demo Code :
var count;
var random;
Dropzone.autoDiscover = false;
var myDropzone = new Dropzone("#my-awesome-dropzone", {
headers: {
"X-CSRF-TOKEN": $("meta[name='csrf-token']").attr("content")
},
autoProcessQueue: false,
acceptedFiles: ".jpeg,.jpg,.png,.gif",
dictDefaultMessage: "Drag an image here to upload, or click to select one",
maxFiles: 15, // Maximum Number of Files
maxFilesize: 8, // MB
addRemoveLinks: true,
dictRemoveFile: 'Remove',
dictFileTooBig: 'Image is bigger than 8MB',
// append hidden input and add selected images
accept: function(file) {
let fileReader = new FileReader();
fileReader.readAsDataURL(file);
fileReader.onloadend = function() {
random = 1 + Math.floor(Math.random() * 1000);
count = $(".dz-complete").length + "_" + random;
let content = fileReader.result;
console.log(count)
//add dataid
$('#botofform').append('<input type="text" class="cimages" name="cimages[]" data-id = "' + count + '" value="' + content + '">');
file.previewElement.classList.add("dz-success");
file.previewElement.setAttribute("data-id", count);
}
file.previewElement.classList.add("dz-complete");
},
removedfile: function(file) {
console.log("inside remove --" + file.previewElement.getAttribute("data-id"))
var ids = file.previewElement.getAttribute("data-id") // get attr where file is been removed
$("#botofform input[data-id=" + ids + "]").remove() //remove input field as well
file.previewElement.remove(); //remove file
}
});
$(function() {
$(".dropzone").sortable({
items: '.dz-preview',
cursor: 'move',
opacity: 0.5,
containment: '.dropzone',
distance: 20,
tolerance: 'pointer',
stop: function(event, ui) {
//cloned div
var cloned = $('div#botofform').clone()
$('#botofform').html("") //empty it
//loop through dropzone..
$('.dropzone .dz-complete').each(function() {
var data_id = $(this).data('id') //get data-id
$(cloned).find("input[data-id=" + data_id + "]").clone().appendTo($('#botofform')) //find input which has that data-id and append same to bottmform
});
}
});
});
<link rel="stylesheet" href=" http://code.jquery.com/ui/1.9.1/themes/base/jquery-ui.css">
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/dropzone/4.3.0/dropzone.js"></script>
<script src="https://code.jquery.com/ui/1.12.1/jquery-ui.js"></script>
//Drop zone box
<div class="dropzone" id="my-awesome-dropzone" action="#">
<div class="fallback">
<input name="cimages[]" type="file" multiple />
</div>
<div class="clearfix"></div>
</div>
<div id="botofform"></div>

Related

Detecting open button in an upload dialog

Is there a way to detect if the open button in an upload dialog is clicked using javascript or query?
UPDATE :
I will show you my sample code:
<input type = "file" name = "imgUpload" id = "trngImgUpload" style = "display : none;" multiple>
<button class="btnTools" onclick = "trngOpenVidUploadDialog()" ><img src ="#Url.Content("~/Images/video_icon.jpg")" class ="img3"/></button>
<script>
function trngOpenVidUploadDialog() {
//$('#modalMatchingTypePairType').modal('hide');
//console.log(123);
$('#trngImgUpload').trigger("click");
};
$('input[type=file]').change(function () {
if (this.files) {
alert('changed');
var path = sendVidFile($('#trngImgUpload')[0].files[0], 1);
$('#page' + currId).append('<div class = "vidDR" id = "tTool' + (toolIdCounter) + '"><div class = "del"></div><embed autostart="false" class = "vid" src="' + path + '"></embed></div>');
$('.vidDR').resizable({
containment: '#page' + currId
}).draggable({
containment: '#page' + currId
});
$(".vidDR").click(function () {
alert(1);
});
$('#trngImgUpload').val("");
$('#tTool' + toolIdCounter).contextmenu(function () {
$(this).remove();
});
toolIdCounter++;
}
});
</script>
I already tried using change event but nothing happens. I don't know whats wrong in my code.
You cannot capture the action on the 'Open' button, however you can capture the action upon changes on the file input. E.g. when the user has selected a new file using the file input.
Example as follows:
// input on change event listener
$('#file-upload').on('change', function() {
alert('File Attached: ' + $('#file-upload').val());
});
<!-- jQuery -->
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script>
<!-- file upload input -->
<input type="file" id="file-upload">
Hope this helps.
No! That is not possible.
But if you want to have an eye on your input type=file then you might like to use change() event on the input.
Check the snippet:
$('input[type=file]').change(function() {
if (this.files) {
$('pre').html('Files selected. (open clicked.)');
}
});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<input type="file" name="imgUpload" id="trngImgUpload" style="display : none;" multiple>
<button class="btnTools" onclick="trngOpenVidUploadDialog()">
<img src="https://cdn3.iconfinder.com/data/icons/ilb/Perspective%20Button%20-%20Windows.png" class="img3" />
</button>
<script>
function trngOpenVidUploadDialog() {
//$('#modalMatchingTypePairType').modal('hide');
//console.log(123);
$('#trngImgUpload').trigger("click");
};
$('input[type=file]').change(function() {
if (this.files) {
alert('changed');
}
});
</script>

Adding form input fields dynamically

HTML FORM
<div class="module">
<div class="moduleTitle">Upload Photos</div>
<form id="upload" method="post" action="actions/upload.php" enctype="multipart/form-data">
<div id="drop">
Drop Here
<a>Browse</a>
<input type="file" name="upl" multiple />
</div>
<form onSubmit="addTags();return false;" id="tagAddForm">
<ul>
<!-- The file uploads will be shown here -->
</ul>
<input type="submit" name="login" value="Add Tags" class="submit" id="login"/>
</form>
</div>
</form>
Javascript File
$(function(){
var ul = $('#upload ul');
$('#drop a').click(function(){
// Simulate a click on the file input button
// to show the file browser dialog
$(this).parent().find('input').click();
});
// Initialize the jQuery File Upload plugin
$('#upload').fileupload({
// This element will accept file drag/drop uploading
dropZone: $('#drop'),
// This function is called when a file is added to the queue;
// either via the browse button, or via drag/drop:
add: function (e, data) {
var tpl = $('<li class="working uploaded"><input type="text" value="0" data-width="48" data-height="48"'+
' data-fgColor="#0788a5" data-readOnly="1" data-bgColor="#3e4043" /><p></p><span></span></li>');
// Append the file name and file size
tpl.find('p').text(data.files[0].name);
// Add the HTML to the UL element
data.context = tpl.appendTo(ul);
// Initialize the knob plugin
tpl.find('input').knob();
// Listen for clicks on the cancel icon
tpl.find('span').click(function(){
if(tpl.hasClass('working')){
jqXHR.abort();
}
tpl.fadeOut(function(){
tpl.remove();
});
});
// Automatically upload the file once it is added to the queue
var jqXHR = data.submit();
},
progress: function(e, data){
// Calculate the completion percentage of the upload
var progress = parseInt(data.loaded / data.total * 100, 10);
// Update the hidden input field and trigger a change
// so that the jQuery knob plugin knows to update the dial
data.context.find('input').val(progress).change();
if(progress == 100){
data.context.removeClass('working');
}
},
fail:function(e, data){
// Something has gone wrong!
data.context.addClass('error');
}
});
// Prevent the default action when a file is dropped on the window
$(document).on('drop dragover', function (e) {
e.preventDefault();
});
// Helper function that formats the file sizes
function formatFileSize(bytes) {
if (typeof bytes !== 'number') {
return '';
}
if (bytes >= 1000000000) {
return (bytes / 1000000000).toFixed(2) + ' GB';
}
if (bytes >= 1000000) {
return (bytes / 1000000).toFixed(2) + ' MB';
}
return (bytes / 1000).toFixed(2) + ' KB';
}
});
Here is a demo how you could dynamically generate (input/li)s based on an array of files.
//Create an empty container
var $elems = $();
//Cycle thru the files
$.each(data.files, function(idx, file) {
//Create an input with attrs
var $input = $("<input/>", {
'type': 'text',
'placeholder': 'separate tags with commas',
'name': file["name"]
});
//Create list element & append input
var $li = $("<li/>").append($input);
//Populate the container with the list item
$elems = $elems.add($li);
});
//Append all list items
$("#tagAddForm > UL").append($elems);
And a working demo with sample files that I defined for the demo.
Another one with option to display image thumbs based on the file name.

Custom upload for a generated form

I have a generated form which I can't add HTML directly to it.
This form has 2 upload boxes which needs to have a custom styling. I have managed to style the upload box, but upon testing the function which I need to be triggerd, doesn't trigger.
To clarify, here is my code and what I tried:
The html (that is autom being generated):
<div class="controls">
<input class="span3" type="file" name="img1" id="img1" />
</div>
This is the jQuery
$(document).on('change', 'input[type=file]', function() {
var input = $(this),
numFiles = input.get(0).files ? input.get(0).files.length : 1,
label = input.val().replace(/\\/g, '/').replace(/.*\//, '');
input.trigger('fileselect', [numFiles, label]);
});
$(document).ready(function() {
var fileinput = $('input[type=file]', this);
var file_parent = fileinput.parent(); // get the parent
var fileinputhtml = file_parent.html(); // the HTML of the parent (which is input)
file_parent.replaceWith('<span class="btn btn-file"><span class="btn-class btn-primary">Browse</span>'+fileinputhtml+'<span class="form-control"></span></span>');
// The upload function has been triggerd
fileinput.on('fileselect', function(event, numFiles, label) {
console.log(label); // When the .replaceWith() is active, it doesn't show this log.
var input = $(this).parent().find('.fileupload-filename');
console.log(input.val(label));
if( input.length ) {
input.val( label );
}
});
});
Maybe it has an easy solution but I really can't seem to get this to work.
You help would be highly appericiated

datetimepicker not showing up in bootstrap dialog

I am using the datetimepicker from http://eonasdan.github.io/bootstrap-datetimepicker/
I have a bootstrap dialogbox which contains a textfield and an ID. I have exactly copied it, but my datetimepicker does not show up... Does anyone have an idea?
Javascript/HTML:
BootstrapDialog.show({
//Set properties
draggable:true,
title: cObj.title,
message: function (dialogItself) {
var form = $('<form id="createEventForm"> </form>');
var klantNaam = $('<input id="titleDrop" type="text" />');
var description = $('<textarea id="descriptionDrop"></textarea>');
var employee = $('<select class="form-control" id="employee">');
var starttime = $('<input id="starttime" type="text" class="form-control" /><span class="input-group-addon"><span class="glyphicon glyphicon-time"></span></span>');
var startTimeDiv =
$('<div/>', {
id: 'datetimepicker4',
class: 'input-group date',
html: starttime
});
var endtime = $('<input type="text" class="endtime" id="endtime"/>');
dialogItself.setData('field-klant-naam', klantNaam);
dialogItself.setData('field-description', description); // Put it in dialog data's container then you can get it easier by using dialog.getData() later.
dialogItself.setData('select-user', employee); // Put it in dialog data's container then you can get it easier by using dialog.getData() later.
dialogItself.setData('starttime', startTimeDiv); // Put it in dialog data's container then you can get it easier by using dialog.getData() later.
dialogItself.setData('endtime', endtime);
form.append('<label>Klant naam</label>').append(klantNaam);
form.append('<label>Beschrijving</label>').append(description);
form.append('<label>Medewerker</label>').append(employee);
form.append('<label>Start tijd</label>').append(startTimeDiv);
form.append('<label>Eind tijd</label>').append(endtime);
$.each(<?php echo $list?>, function(key, value) {
employee.append($("<option/>", {
value: value.key,
text: value.value
}));
});
return form;
},
})
$('#datetimepicker4').datetimepicker();
CSS:
#datepicker4{
z-index: 99999;
}
You need to call datetimepicker() on element existing in the document, in your case you are just defining the message: function() {} that is returned to the BootstrapDialog object, which means it's still in memory and hasn't been added to the DOM yet.
after taking a look on the documentation of BootstrapDialog it turns out that onShow() is invoked after the message has been added to the DOM
BootstrapDialog.show({
//Set properties
draggable:true,
title: cObj.title,
onShow: function() {
if (!this.datetime_invoked) {
this.datetime_invoked = true;
$('#datetimepicker4').datetimepicker();
}
},
message: function (dialogItself) {
var form = $('<form id="createEventForm"> </form>');
var klantNaam = $('<input id="titleDrop" type="text" />');
var description = $('<textarea id="descriptionDrop"></textarea>');
var employee = $('<select class="form-control" id="employee">');
var starttime = $('<input id="starttime" type="text" class="form-control" /><span class="input-group-addon"><span class="glyphicon glyphicon-time"></span></span>');
var startTimeDiv =
$('<div/>', {
id: 'datetimepicker4',
class: 'input-group date',
html: starttime
});
var endtime = $('<input type="text" class="endtime" id="endtime"/>');
dialogItself.setData('field-klant-naam', klantNaam);
dialogItself.setData('field-description', description); // Put it in dialog data's container then you can get it easier by using dialog.getData() later.
dialogItself.setData('select-user', employee); // Put it in dialog data's container then you can get it easier by using dialog.getData() later.
dialogItself.setData('starttime', startTimeDiv); // Put it in dialog data's container then you can get it easier by using dialog.getData() later.
dialogItself.setData('endtime', endtime);
form.append('<label>Klant naam</label>').append(klantNaam);
form.append('<label>Beschrijving</label>').append(description);
form.append('<label>Medewerker</label>').append(employee);
form.append('<label>Start tijd</label>').append(startTimeDiv);
form.append('<label>Eind tijd</label>').append(endtime);
$.each(<?php echo $list?>, function(key, value) {
employee.append($("<option/>", {
value: value.key,
text: value.value
}));
});
return form;
},
})
Your ID is different in your CSS file. In your markup you have #datetimepicker4, but in your css #datepicker4
Try to change in the CSS and see if it appears.
Also, check if the datetime markup is appearing when you view the source in Firebug. If so, the above may fix it as its likely a z-index issue.
i fixed with this code:
onshown: function(dialogRef){
$('#submit_date').datepicker({
language: 'ja',
isRTL: false,
//autoclose: true,
});
},

select images as per choice and display their name as an alert in javascript

I am new here, I have generated 5 images from an array. Now I want to select those images as we select using checkbox (means i can select 1 image or 2 image or more as per choice). After selecting I want to display their name as an alert that you have selected these images. Please guide me because i am new in javascript. Thanks in advance.
It's not entirely clear what an acceptable output is but here is something which accumulates selected photos and displays the image src for the selected photos.
var PhotoSrcArray = [
"http://placekitten.com/g/60/60",
"http://placekitten.com/70/60",
"http://placekitten.com/g/60/70",
"http://placekitten.com/70/70",
"http://placekitten.com/g/80/80"
];
for(var i = 0; i < PhotoSrcArray.length; i++){
$("#imgs").append('<li><label><input type="checkbox"></input><img src="'+PhotoSrcArray[i] + '" data-index="'+(i+1).toString() + '"/></label></li>');
}
var myArray = [];
$("li input").change(function(event){
if (this.checked){
myArray.push($(event.currentTarget).next('img').attr('data-index'));
}
else {
var indexOfPhoto = myArray.indexOf($(event.currentTarget).next('img').attr('data-index'));
if (indexOfPhoto > -1){
myArray.splice(indexOfPhoto, 1);
}
}
myArray.sort();
$("#output").html( myArray.join(' '));
//or alert it if you'ld like
});
Here is a working fiddle here.
This is the working JsFiddle.
You can try this function, it will bind a checkbox to an image:
function bind_checkbox_image(checkboxId, imageId)
{
document.getElementById(checkboxId).onchange = function () {
alert(document.getElementById(imageId).getAttribute("title"));
};
}
The image should have a title and a change on the checkbox will show that title:
<img id="myimage" title="the image text" src="..." />
<input type="checkbox" id="mycheckbox" />
You can now bind those:
bind_checkbox_image("mycheckbox", "myimage");
EDIT: bugfix inverted ids of checkbox and image

Categories

Resources