I've been trying for sometime now to access this one object "baseURI":
If you look at the image above, I'm trying to get "baseURI".
In order to get what I have in the image, I do this:
var onDrop = function(e) {
e.preventDefault();
console.log(e.originalEvent);
}
But when I try to get the objects inside of MouseEvent, I get "undefined". Here's what I tried.
var onDrop = function(e) {
e.preventDefault();
console.log(e.originalEvent.MouseEvent.srcElement.baseURI);
}
I also tried a bunch of other ways, what am I missing?
I made a fiddle if it helps:
http://jsfiddle.net/sta2M/1/
MouseEvent is its prototype, not a property. You can ommit .MouseEvent.
Related
As the title explain, i'm trying to send data to a function by event handler.
i've tried the following:
canvas.on("mouse:wheel",{name:"spin"}, constructSpin);
function constructSpin(e){
console.log(e.data.name);
}
sadly this is not working :(
is there any way to send data to a function using event handler ?
NOTE: i've found this in fabric document:
on(eventName, handler) → {Self}
so it look like there is no data in on construction !
You should construct and call the constructSpin function in the following way, if you wish to pass some custom data on mouse:wheel event :
canvas.on("mouse:wheel", function(e) {
constructSpin(e, { name: "spin" });
});
function constructSpin(event, data) {
console.log(data.name);
}
The fabric events are sort of syntetic.
You are spinning the wheel on the canvas element and you get back 2 events, one at canvas level and one at object level.
if spin is a particular object on your canvas, or is a name property of your objects you can have:
canvas.on("mouse:wheel", function(opt) {
// opt.e => real event
// opt.target => object where you spinned over
// opt.target.name maybe is what are you looking for
});
If my assumption is wrong, you can just do what is already suggested in another answer:
canvas.on("mouse:wheel", function(opt) {
// opt.e => real event
// opt.target => object where you spinned over
opt.name = 'spin'
yourFunction(opt);
});
Question
How could I, while providing the file, trigger a drop event of a field, on which I do not have access at loading.
Details
There is a page with a field on which is attached a drop listener that process an image when dropped. I would like to be able to use this process by pasting an image. I know how to get the file from a paste, but I do not know how to dispatch a drop event that would contains this very file.
The obstacles are:
The code is obfuscated, I cannot access the function linked with the listener by name.
There is no way to get the drop listener after it being attached to an element. It seems there is some way to do it in the console, but not from a script.
I do not control the page rendering; i.e. I cannot intercept the event listener addition.
Vanilla Javascript & could only work in Chrome (extension).
This page is built in vanilla; i.e. no jQuery or anything.
Does anyone have an idea on how to tackle this task?
I am looking into DragEvent but "although this interface has a constructor, it is not possible to create a useful DataTransfer object from script, since DataTransfer objects have a processing and security model that is coordinated by the browser during drag-and-drops."
I saw a possible approach https://stackoverflow.com/a/39066443/1004274 but I want to mimic a real drop event with its data, i.e. pass a file I got via clipboardData.items[0].getAsFile(); instead of just text.
You can fake the drop event, and fake pretty much everything that's in there. What you'll have problem doing is triggering a default event, such as opening a file in a tab by dropping it. The reason isn't so much because of the dataTransfer object being protected, but the event not being trusted. By having trusted event and protected dataTransfer, you can be sure you won't pass data to a trusted event, and that you won't trigger default event with unwanted data.
But depending on how the drop function is accessing the file that is dropped, you might be able to trick it with a fake drop event and a fake dataTransfer object. See this fiddle for a general idea of how it may work:
var a = document.getElementById('link');
var dropZone1 = document.getElementById('dropZone1');
var dropZone2 = document.getElementById('dropZone2');
var fakeDropBtn = document.getElementById('fakeDropBtn');
dropZone1.addEventListener('dragover', function(e) {
e.preventDefault();
});
dropZone2.addEventListener('dragover', function(e) {
e.preventDefault();
});
dropZone1.addEventListener('drop', function(e) {
// This first drop zone is simply to get access to a file.
// In your case the file would come from the clipboard
// but you need to work with an extension to have access
// to paste data, so here I use a drop event
e.preventDefault();
fakeDropBtn.classList.remove('disabled');
dropZone2.classList.remove('disabled');
var fileToDrop = e.dataTransfer.files[0];
// You create a drop event
var fakeDropEvent = new DragEvent('drop');
// You override dataTransfer with whichever property
// and method the drop function needs
Object.defineProperty(fakeDropEvent, 'dataTransfer', {
value: new FakeDataTransfer(fileToDrop)
});
fakeDropBtn.addEventListener('click', function(e) {
e.preventDefault();
// the fake event will be called on the button click
dropZone2.dispatchEvent(fakeDropEvent);
});
});
dropZone2.addEventListener('drop', function(e) {
e.preventDefault();
// this is the fake event being called. In this case for
// example, the function gets access to dataTransfer files.
// You'll see the result will be the same with a real
// drop event or with a fake drop event. The only thing
// that matters is to override the specific property this function
// is using.
var url = window.URL.createObjectURL(e.dataTransfer.files[0]);
a.href = url;
a.click();
window.URL.revokeObjectURL(url);
});
function FakeDataTransfer(file) {
this.dropEffect = 'all';
this.effectAllowed = 'all';
this.items = [];
this.types = ['Files'];
this.getData = function() {
return file;
};
this.files = [file];
};
https://jsfiddle.net/5m2u0tux/6/
I am trying to get access and modify this function (second one) in jqueryUI. I have tried everything. What I want to do is to add something in the function. I know it is possible and I need to do something like this :
var snapIt = $.ui.draggable.prototype.drag;
$.ui.draggable.prototype.drag = function() {
console.log("hello"); // exemple of a thing I want to add
// Now go back to jQuery's original function()
return snapIt.apply(this, arguments);
};
On top it will get the function add in console "hello" and then continue normally with the rest of the jQuery function. But I just can't find this function. I know this doesn't work: $.ui.draggable.prototype.start and dozens of others I tried.
$.ui.plugin.add("draggable", "snap", {
start: function( event, ui, i ) {
click.x2 = event.clientX;
click.y2 = event.clientY;
var o = i.options;
i.snapElements = [];
$(o.snap.constructor !== String ? ( o.snap.items || ":data(ui-draggable)" ) : o.snap).each(function() {
var $t = $(this),
$o = $t.offset();
if (this !== i.element[0]) {
//...........
I don't want the drag: function(event, ui) {..... I need to modify the function because I use ui.position = {left..... and it make the snap method not work. The only way was to change the drag method. I know it work because I tried manualy. But changing the library might be problematic for futur dev.
Don't know if I am clear but basically I want the path to $.ui.plugin.add("draggable", "snap", {//stuff}); in jqueryUI library
Thx in advance
There are 3 different sources of behaviors that are called on the different events in jquery-ui, each with its own structure.
First you have the "private" functions, that are defined on the prototype and that are called directly on native events. These are on $.ui.draggable.prototype and begin with a _ character. For example you have $.ui.draggable.prototype._mouseDrag function.
These are called directly and are the ones triggering the events. They are not directly accessible from the options.
Then you have the plugins functions. These are the ones that are added using add. Basically what add does is that it sets functions to be called on the events that are accessible via the options. And these plugins callbacks are called if their corresponding option is true. The structure goes like this:
Each plugin is an object that defines a callback for different
events. The events available are the same that are accessible in the options. For draggable, you have start, drag and stop.
These callbacks are pushed in arrays contained by
$.ui.draggable.plugins object, in which each property is one of the available event.
A function goes through the event array and validates if the plugin
should be ran based on the option set.
Once the plugins are done, the options callbacks are called. These are the ones that you set in the options.
So depending what ou want to modify, you can either change the prototype:
$.ui.draggable.prototype._mouseDrag
Or you can add a plugin. Like this:
$.ui.plugin.add( "draggable", "customPlugin", {
drag: function(event, ui, draggable){
console.log("I'm the custom plugin");
});
Or you can modify snap plugin. This one is a bit more complicated, and much less reliable since the functions are stored in arrays and not in an object, and they are added. The structure goes like this:
Each property key is an event, and every property is an array of
arrays.
Each of the array first element is the name of the option associated
with the callback, that is the second element of the array.
So the drag callback associated to snap is $.ui.draggable.prototype.plugins.drag[2], because it's the third callback that's been added to drag event. $.ui.draggable.prototype.plugins.drag[2][0] is the string "snap", which is used to check if the option was set to true. And the callback is $.ui.draggable.prototype.plugins.drag[2][1]. So you can modify it like this:
$.ui.draggable.prototype.plugins.drag[2][1] = function(){
console.log("I'm the modified plugin");
}
If you want a better control, you can iterate through $.ui.draggable.prototype.plugins.drag array and check the first element to make sure you modify the proper plugin.
Obviously, as you tried, you need to store the original callback if you want the behavior to work.
See here how this goes:
$.ui.plugin.add("draggable", "customPlugin", {
drag: function() {
console.log("%c I'm a custom plugin", 'color: blue');
}
});
var _temp = $.ui.draggable.prototype.plugins.drag[2][1];
$.ui.draggable.prototype.plugins.drag[2][1] = function() {
console.log("%c I'm the modified snap plugin drag callback", 'color: red');
_temp.apply(this, arguments);
}
$('div').draggable({
snap: true,
customPlugin: true,
drag: function() {
console.log("%c I'm the options callback", 'color: green');
}
})
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<script type="text/javascript" src="//code.jquery.com/ui/1.11.4/jquery-ui.js"></script>
<div>Drag me</div>
<div>Or me</div>
This works:
var picdrag = document.getElementById('picdrag');
picdrag.addEventListener('drop', picSelect, false);
function picSelect(e) {
var pics = e.dataTransfer.files;
}
This doesn't:
$('#picdrag').on('drop', function(e) {picSelect(e);});
function picSelect(e) {
var pics = e.dataTransfer.files;
}
because it reports an error 'e.dataTransfer is undefined'. I hate it when I don't know why something works or doesn't work. This is specific to the drop event, like jQuery handles it differently.
You can try:
var pics = e.originalEvent.dataTransfer.files;
From the docs:
Certain events may have properties specific to them. Those can be
accessed as properties of the event.originalEvent object. To make
special properties available in all event objects, they can be added
to the jQuery.event.props array. This is not recommended, since it
adds overhead to every event delivered by jQuery.
There is also an example that should be of interest:
// add the dataTransfer property for use with the native `drop` event
// to capture information about files dropped into the browser window
jQuery.event.props.push("dataTransfer");
$('#picdrag').on('drop', picSelect);
var picSelect = function(e) {
var pics = e.dataTransfer.files;
};
How can I use the this function in meteor? for example, I want to be able to click on any given element and find out what its class is. Also, how can I get information on the item that I click on with Meteor?
Let's say somewhere in the code you have a template handling events:
Template.tmpl_name.events = {
'click #logo': function (e) {
// Instead of using $(this), you can do:
var $this = $(e.target);
// Your usual code here, e.g.:
console.log($this.attr('href'));
}
};