Right click not displayed on an image - javascript

I have a basic issue with an image.
Indeed, I can't make display a right click menu on the image (in order to see it in full display) :
I have just put a :
<img class="center" width="700" height ="381" src="./Image_Init_Scene.png"/>
Maybe the issue comes from other things in my HTML page (like jQuery etc).

It looks like the normal behavior of the contextmenu event is prevented somewhere in your code...
So you can find where it is prevented to remove this "protection"...
Or you can create you own custom context menu.
The event is still triggered, so you can use it.
$(".body_content img.center").on("contextmenu",function(){
console.log("Context menu!");
// Do what ever you want!
});

Context Menu is being interrupted by an event handler somewhere in your code. While searching for event.preventDefault() works, this may be the long way out. Also this may not work if programmer is using return false
The easy way is to set a break point in the Debugger. Chrome offers a context menu breakpoint among others under Event Listener Breakpoints. Pausing the execution on modification will tell you, where the context menu is being manipulated.
For example, in your code, context menu is being used in two places postload.js and orbitcontrols.js. Orbit controls is preventing the context menu action with
function onContextMenu( event ) {
event.preventDefault();
}
scope.domElement.addEventListener( 'contextmenu', onContextMenu, false );
Removing this will restore context menu to original state.

Related

Javascript manually 'declick' then click child element whilst clicked

Hi please feel free to suggest a better title I couldn't think of a way to word it.
Issue
I have a Google Maps with pointer events set to none; this stops the map being scrolled into when you scroll over it and it works great.
I have a div that is wrapped around this element and when you click into it, it allows all pointer events on the map inside it therefore allowing you too scroll on the map.
Once you then leave the map with your mouse it re-enables pointer events none so that you can scroll over it.
The main issue is that when you click the map you then have to click it again to scroll.
I want to know if it possible to click on the overlay then to get it to un-click and click again for the user to save them being confused about having to click again. The reason this may be difficult is because when the user has clicked down it needs to un-click and click whilst they are still pressed down.
Code
The issue I am having is that I have a Google Maps inside a div like so in the HTML:
<div id="gmap-holder" class="dealer-details__map gmap-scroll-block--on">
<div id="map" class="dealer-details-gmap"></div>
</div>
JS working as explained in the header
$('.dealer-details__map').on('click', function(){
$(this).removeClass('gmap-scroll-block--on');
$(this).addClass('gmap-scroll-block--off');
});
$('.dealer-details__map').on('mouseleave', function(){
$(this).addClass('gmap-scroll-block--on');
$(this).removeClass('gmap-scroll-block--off');
});
Pseudo of what I am trying to achieve
$('.dealer-details__map').on('click', function(){
$(this).removeClass('gmap-scroll-block--on');
$(this).addClass('gmap-scroll-block--off');
//pseudo start
//$(this).unclick()
//$(this).child().click();
//pseudo end
});
You might want to use Custom Controls, so that you can create your own controls to handle interaction with the user. This involves Drawing Custom Control, Handling Events from Custom Controls and Positioning Custom Controls, it will also be easier to track as your function is in a button. You can take a look on the sample code, for reference on how the implementation would be. Hope this helps!
$('.dealer-details__map').on('click', function(event){
event.stopPropagation();
$(this).child().click();
});

How to capture all scrolling events on a page without attaching an onscroll handler to every single container

Consider the following Web page:
<html>
<body onscroll="alert('body scroll event')">
<div style='width:200px;height:200px;overflow:auto' onscroll="alert('div scroll event')">
<div style='height:400px'>
</div>
</div>
</body>
</html>
This html creates a div with a scrollbar. If you move the scrollbar, the onscroll event on the div element is triggered. However, the onscroll event on the body is NOT fired. This is expected, since the W3C states that element onscroll events do not "bubble".
However, I'm developing a client-side web framework that needs to know any time a scroll bar on ANY element of the page is scrolled. This would be easy to do if onscroll bubbled, but unfortunately it does not. Is there any other way to detect onscroll events across an entire page? (Right now I'm focusing mainly on Webkit, so a Webkit-specific solution would be fine...)
Here are some things I've tried:
Capturing DOMAttrModified (doesn't seem to fire for moving scrollbars.)
Using DOM Observers (also don't seem to fire for scrollbars)
Changing the onscroll event type to bubble (seems to not be possible)
It seems the ONLY way to capture onscroll events globally is to attach an onscroll event to EVERY element that may scroll, which is very ugly and is going to hurt the performance of my framework.
Anyone know a better way?
The simplest way to detect all scroll events in modern browser would be using 'capturing' rather than 'bubbling' when attaching the event:
window.addEventListener('scroll', function(){ code goes here }, true)
Unfortunately as I am aware there is no equivalent in older browser such as <= IE8
I had this same issue.
The easiest way of course is to use jQuery. Be aware that this method could potentially slow down your page significantly. Also it will not account for any new elements that are added after the event is bound.
$("*").scroll(function(e) {
// Handle scroll event
});
In vanilla JavaScript, you can set the useCapture boolean to true on your addEventListener call, and it will fire on all elements, including those added dynamically.
document.addEventListener('scroll', function(e) {
// Handle scroll event
}, true);
Note though that this will fire before the scroll event actually happens. As I understand it, there's two phases events go through. The capture phase happens first, and starts from the page root (ownerDocument?) and traverses down to the element where the event happened. After this comes the bubbling phase, which traverses from the element back up to the root.
Some quick testing too showed that this may be how jQuery handles it (for tracking scrolls on all page elements at least), but I'm not 100% sure.
Here's a JSFiddle showing the vanilla JavaScript method http://jsfiddle.net/0qpq8pcf/
*...crickets chirping... *
OK, I guess this question isn't going to get any stackoverflow love, so I might as well answer my own question as to the best solution I've found so far, in case another user stumbles across this question:
The best solution I've come up with is to capture "onmousedown" and "onkeydown" for the BODY element: These events bubble, and so if a user tries to move a scrollbar on the page these global functions will fire as a by-product. Then, in these functions, simply look up event.target and attach a temporary "onscroll" event to those objects until the mouse/key is "up" again. Using that method, you can avoid "handler bloat" and still globally capture all "onscroll" events. (I think this will work for "mouse wheel" scrolling as well, but my research on that final wrinkle is still pending.)
The following works fine when you want to i.e. close a dialog after anything in the background is scrolled:
var scrollListener = function(e) {
// TODO: hide dialog
document.removeEventListener('scroll', scrollListener, true);
};
document.addEventListener('scroll', scrollListener, true);
I needed to handle scrolling in any context in a complex of custom elements with scroll events in shadowRoots. This covers at least part of the problem in my scenario and generally borrows from the answers and comments here in the context of these newer web component APIs. Attaching and detaching the listener in the appropriate lifecycle callbacks works well so-far (once might not fit your use-case).
self.addEventListener('mousewheel', handler, {capture: true, once: true});
self.addEventListener('keydown', handler, {capture: true, once: true});
Note too the event.composedPath() provides the entire event path through all the shadowRoots with all the nodes if specifics about the scrolling context are needed. If this is the case it might make sense to use this approach and attach a new handler for that specific scenario--to the node of interest.
Like drcode said, capture on body tag is the trick. I just add touchmove to work on mobile.
document
.querySelector("body")
.addEventListener("mousewheel", e => {
console.log("scroll");
});
document
.querySelector("body")
.addEventListener("touchmove", e => {
console.log("scroll");
});
Regards,

Disabling Javascript event fall-throughs when dealing with z-ordered HTML elements

I have a silly (and hopefully easily fixed) problem, which I will now attempt to describe.
The scenario-> I am trying to create a context menu using HTML / CSS / JS. Just a DIV with a high z-order that appears where a user right-clicks. Simple, and that portion works. The portion which does not is my attempt to make the menu disappear if the user clicks somewhere where a context menu is not supported; I am attempting to achieve this end with a general function in the BODY tag that fires onclick. Since the BODY tag is given a z-order of -1, and any other tags which might trigger the context menu to appear are given a higher z-order value, my hope was that if I right-clicked an element with a z-order of, say, 3, then it would fire the showMenu() function; instead, it appears that it does this, as well as passes the event to the underlying BODY tag, which causes the menu to become hidden again.
As you might imagine, it is incredibly frustrating. Does anyone know how to make prevent events from being passed down? (The INPUT button is what you may want to look at, the A anchor is something similar, but not coded to work just yet).
Here's the HTML code:
http://pastebin.com/YeTxdHYq
And here's my CSS file:
http://pastebin.com/5hNjF99p
This appears to be a problem with IE, Firefox, and Chrome.
A lot of DOM events "bubble" from the bottom object up through container objects, which means they'll eventually reach the body. But you can stop this - try adding the following code to the click handler on your element:
e.cancelBubble = true;
if (e.stopPropagation) e.stopPropagation();
...where e is the variable you already have in your function representing the event object.
event.stopPropagation(); should work in modern browsers, but the old IE way was event.cancelBubble = true; - to be safe you can just do both (but as shown above check that .stopPropagation is defined before trying to call it).
With the above code added, if you click on the element your function will stop container objects (include the body) from seeing the click. If you click somewhere else your function isn't called so then the body will process the click.
There's more info about this at MDN and QuirksMode.org.
Note: I've ignored the z-order issue because in this case I think it is a non-issue - all elements are descendents of the body so (unless you stop it) I would expect events to bubble to the body regardless of z-order.

Controlling dijit.MenuBar with MouseOver events

In Dojo, is it possible to configure dijit.MenuBar so that the menus are triggered by MouseOver and MouseOut events? Actually this behavior is available already, but it is switched on or off by initial or successive mouse click events - so initially, MouseOver would not cause menu popup, but if the user clicks on a menu item, the menubar then becomes responsive to MouseOver events. A successive mouse click would again switch off this behavior.
What I would like to have is menus and sub-menus popping up based on MouseOver events without interference from click events. Please check the examples at http://dojotoolkit.org/reference-guide/dijit/MenuBar.html to see what I mean.
Your question piqued my interest enough to make a working solution.
I checked the dijit._MenuBase source code at dijit/Menu.js and apparently there is a this.isActive flag that is checked before proceeding. So I created a subclass that just sets this flag as true beforehand:
_ActivateOnMouseoverMixin = dojo.declare(null, {
onItemHover: function(item){
if(!this.isActive){
this._markActive();
}
this.inherited(arguments);
}
});
ActiveMenuBar = dojo.declare([dijit.MenuBar, _ActivateOnMouseoverMixin], {});
As a bonus, you can also modify the delay with the popupDelay variable (I changed it to be faster in the example)
I have no idea if there is another, more sane, way to do the same thing.
Here is an example that extends the solution of 'Hugomg' to case of unhovering the menu and the sub-menu:
[enter link description here][1]
[1]: http://jsfiddle.net/vg10c9md/2/

How can I create an exception for a jquery mouseout event only if another mouseover event hasn't been triggered?

Basically my client wants hidden navigation to appear when mouseover an image. I've solved the problem of the navigation not hiding when you mouseover the navigation and then hiding when you leave the navigation. There are two problems I'm running into and I've tried a variety of different combinations that I thought would work, but of course didn't. The two problems are:
When you mouseout the image without mouseover the navigation then the navigation needs to hide, as of right now it stays open until you either mouseover the image again or mouseleave the navigation.
Second problem is when you mouseleave the navigation directly to mouseover the image it loops the function and hides the nav then opens the nav again, I've tried changing slideToggle to show, but that causes a whole bunch of other issues.
Right now the code is behaving as close to how I want it and could be considered acceptable, but I'd love to know how to solve the problems above. I thought about using the hoverIntent plugin to sense the mouse movements and only trigger the functions once the mouse has slowed, but couldn't get it working properly. Clearly, I am a novice when it comes to javascript and jquery so please forgive me, but I'd really appreciate any help.
Here is my code
$(document).ready(function(){
$(".nav-body").hide();
$(".nav-head").mouseover(function(){
$(this).next(".nav-body").slideToggle(600);
$(".nav-body").mouseleave(function(){
$(this).hide(700);
});
});
});
Here is my html:
<p class="nav-head"><img src="/images/face-btn.jpg" /></p>
<div class="nav-body">
<ul><?php wp_list_pages('title_li=&child_of=12&depth=1'); ?></ul>
</div>
Markup change
<div class="nav-container">
<p class="nav-head"></p>
<div class="nav-body"></div>
</div>
Javascript
var eventHandler;
eventHandler = function(){$(".nav-head").one("mouseover",function(){
$(this).next(".nav-body").slideToggle(600);
$(".nav-container").one("mouseleave", function(){
$(this).find(".nav-body").hide(700, eventHandler);
});
});};
eventHandler();
The first change is from mouseleave to mouseout. Inside the navigation, there are likely to be descendent elements that cover the actual nav-body. With mouse leave, the handler only triggers when the mouse leaves the bound element. If it goes over descend it elements, it is considered leaving. Mouseout only triggers if it is outside the bounds of the bound object.
The second thing I did was assign a delegate to the handler binding operation so that I could use it as a callback function for hide(). This way, the event handler won't be restored to the nav-head until the hide is completely done.
The last was to assign the mouseout handler to the containing div. This way, the so long as it leaves the nav-head (or the nav-body) since its contained, the body will hide.

Categories