From searching the internet and StackOF, I see that my question has been asked before or at least some variation of it; but I cannot identify any real solutions.
I have acquired some code that utilizes div tags to produce a modal popup window. While this seems to work adequately aesthetically, there is a small problem of acquiring and retaining focus on the popup that would allow the user to use the tab key to navigate to screen.
function PopUp() {
$('#<%= divPopUp.ClientID%>').modal(
{
overlayCss: {
backgroundColor: '#000'
},
onShow: function (d) { d.container.css({ position: 'absolute', top: '10px' }); }
});
window.location.hash = 'SubmitButton';
}
The div tag refers to a table element that contains some labels and a couple of asp LinkButtons. The function is called from the Server-side using the ScriptManager component to Register and display the popup.
So far I've tried to set the focus from the Server side code and also made a few attempts based on others suggestions from the Client side but nothing gives.
Is there anyone here who has struggled with this or a very similar issue that wouldn't mind sharing a solution? Or is this expected behavior under the circumstances that can only be circumvented via alternative methods?
I've included VB.Net as a tag on this post because that's the Server code language.
Thanks
JS
Inside the modal open or complete function , add this line
function PopUp() {
$('#<%= divPopUp.ClientID%>').modal(
{
focus:true,
overlayCss: {
backgroundColor: '#000'
},
.....//All other stuff
});
}
OR
Use this in onshow function
$('#<%= divPopUp.ClientID%>').focus();
Related
[!Newbie alert!] I'm using a ecommerce platform that doesn't allow me to edit the source code. I can only add new codes (html, js or css) to try to do the modifications I want. And what I want to do is to find a way to disable the script of a newsletter popup on only one specific page. The only way I thought of doing it is adding an extra JS script limiting the action of the previous script that I am not allowed to edit. Is it possible to do?
The original script for de Newsletter Popup is this:
<script type="text/javascript">
$(function() {
iniciarModalNews();
});
function iniciarModalNews() {
if (!$.cookie('showModalNews')) {
showModalNews();
};
}
function showModalNews() {
$.fancybox.open({
type: 'html',
minWidth: 270,
maxWidth: 350,
content: $('#modalNewsletter'),
beforeClose: function() {
$.cookie('showModalNews', 'hide', {
expires: 1,
path: '/'
});
}
});
}
</script>
It runs on all pages of the website and I want to exclude just one page. Is there a way to do this?
Thanks
Full Disclosure: This suggestion would not be considered a best practice but if its a one-off scenario where you don't have access to the source code it'll work.
If you only need to disable this on one page and have access to insert a block of script below the declaration of showModalNews() { ... } you can override the showModalNews() function by writing a new function with the same name. The method that calls the showModalNews method is inside an closure via IIFE (https://developer.mozilla.org/en-US/docs/Glossary/IIFE) but the method showModalNews() is NOT wrapped in a closure which would give you access to override it.
Example of the overridden method
function showModalNews() { ; }
(I don't quite know what to call this kind of control, so if someone can tell me what the name is, I'll edit the question for clarity.)
I'm looking for a jQuery control that will let me make a little pop-up editor that looks like a balloon coming out from a point in the form. In my use case, I'm tight on space and I want to let the user pick a couple of date ranges.
Something like this in the iCloud Calendar new event pop-up:
I ended up using qTip2 for jQuery:
http://qtip2.com/
But to get it to put a who div in there, I had to customize the JS a bit:
events: {
show: function(event, api) {
$("#tooltipContainer").html("");
$("#btnSelectDatesPopup").detach().appendTo("#tooltipContainer");
$("#btnSelectDatesPopup").show();
},
hide: function(event, api) {
$("#btnSelectDatesPopup").hide();
$("#btnSelectDatesPopup").detach().appendTo("#originalSelectDatesPopupContainer");
$("#tooltipContainer").html("<p>...</p>");
}
}
And on the form submit, close the tooltip if it's not closed already, and put it back into the DOM where it belongs:
// On form submit, trigger the tooltip hide to preserve user-chosen values
$("#aspnetForm").submit("submit", function(event) {
qtipApi.hide();
setTimeout(function(){}, 300);
});
With the impending removal of the showModalDialog API from various browsers, our company like many others who provide large scale enterprise web applications are now faced with a significant dilemma.
Whilst we have centralised the calls to showModalDialog down to 3 lines of code, we extensively rely on this code to provide feedback from modal user prompts (a quick search of the solution reveals around 2400 instances).
We could rip out showModalDialog fairly easily and replace it with a Javascript/css based alternative, that's not a problem. The issue we face is that all of the calling code will no longer be blocking e.g.
if(doConfirm(...)) {
...
} else {
...
}
The above will simply fall through due to the introduction of a non-blocking alternative. We also cannot use the in-built blocking methods (alert, confirm) as the dialog buttons are customised in many cases and are also styled to fit in with our application.
Based on the above, are there any pragmatic workarounds/solutions that could be employed to avoid having to re-factor so much legacy previously blocking code?
You can avoid using callback functions by using my showModalDialog polyfill, which pauses execution of subsequent statements until the modal is closed. It does so by using generators, promises and the yield keyword. It works in the newest Opera and Google Chrome.
You won't get around using asynchronous, event-based code.
pragmatic workarounds to avoid having to re-factor the code manually?
You can try a javascript-to-javascript compiler that brings the await keyword to js. It should automatically transpile your code to an asynchronous version.
Disclaimer: I haven't used any of these
In jQuery's 1.11.4 version, there is a built-in <dialog> you can use, which also allows for capturing a callback parameter on close.
$("#dialog").dialog({
autoOpen: false,
width: 500,
height: 500,
modal: true
buttons: [
{
text: "Ok",
click: function () {
$(this).dialog("close");
}
},
{
text: "Cancel",
click: function () {
$(this).dialog("close");
}
}
]
});
Your value could be captured in the callback functions from the button click events.
You could even add HTML to append your own 'x' button to the existing "Close" button and hide the original, so you could do whatever you wanted:
$(document).ready(function () {
var closeHtml = '×';
$("button[title='Close']").css('display', 'none').parent().append(closeHtml);
});
then attach a click event to the dialog-close ID from the 'x' button:
var url = 'https://www.cnn.com';
// Link to open the dialog
$("#dialog-link").click(function (event) {
var dialog = $("#dialog");
dialog.dialog("open");
dialog.html('<iframe id="dialog-body" scrolling="yes" src="' + url + '" style="border: 0; width: 100%; height: 100%;"></iframe>');
$("#dialog-close").on('click', function (e) {
// ...do whatever you want here, then...
$("button[title='Close']").click();
//e.preventDefault();
//dialog.close();
});
event.preventDefault();
});
Only caveat, since this uses IFrame, it might not work if the security on the site prevents bringing in external sites to your own site, if you are using it in this way. Google, for example, prevents this use with their site.
This should be a cross-platform example - I've tested it in IE 11. "Polyfill", that I've seen others say is another way to do this, is NOT, and does NOT work in IE because it relies on Promise, which is not supported in IE, as it shows at the bottom of this page: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Promise
I want to show a popup many on click. I want that many to be in a bubble. So I created a demo: here. But that Bubble generator plugin i use tends to keep tons of trash in the DOM each time it shows a popup. Well so I tried to destroy trash via
$('.grumble-text').remove();
$('.grumble').remove();
$('.grumble-button').remove();
But it somehow brakes it at all=( So how to change grumble-bubble popup plugin code to make it either keep DOM clean or at least make plugin independent of trash it creates?
I've recently updated the plugin to provide better control of positioning and angle. The update also persists the grumble, invoking the plugin more than once on an element will not create extra left over DOM.
Try updating to the latest code. The code below should now work as you expect.
var html = ''
+'Download me'
+'<br/>'
+'Edit me'
+'<br/>'
+'Delete me';
var $grumble = $('#grumble3');
$grumble.mouseup(function(eventObj) {
$grumble.grumble({
text: html ,
angle: (Math.random() * 360 + 150),
distance: 30,
hideOnClick: true,
onShow: function() {
$grumble.addClass("hilight");
},
onBeginHide: function() {
$grumble.removeClass("hilight");
}
});
}).mousedown(function() {
$grumble.addClass("hilight");
});
Thanks for your interest. If there are any further problems please raise them as bugs on the github page. https://github.com/jamescryer/grumble.js
Use the grumble and button parameters on the onHide callback like this:
$('#grumble').grumble({
text: 'Whoaaa, this is a lot of text that i couldn\'t predict',
angle: 85,
distance: 50,
showAfter: 4000,
hideAfter: 2000,
onHide: function(grumble, button) {
grumble.bubble.remove();
grumble.text.remove();
button && button.remove();
}
});
This allows you to remove only the "trash" (I prefer "leftovers") associated with that specific tooltip/popup/bubble. Note that button only exists if hasHideButton is true, hence the button && existence check.
Why do you want to remove it? Is the 'trash' causing problems with browser performance?
In general, the only way to do this is to dig into the plugin source and add a function to remove the plugin, if one is not already present. If you just remove the related DOM elements you will leave behind references to them and events handlers that access them.
I'm using ExtJS 3.2.1 and I need a component almost identical to the bundled HtmlEditor, with one exception: it must start editing the HTML source code directly. The reason I don't use a normal TextArea is that the user should be able to preview the result of his actions before submitting.
I've tried calling toggleSourceEdit(), as per ExtJS documentation, with no success. Debugging, I see that the editor object has the sourceEditMode property set to true, and the Source Edit button seems as if it was "pressed", but clicking on it does not render the typed HTML, and clicking it again goes to the Source Mode.
I've tried calling toggleSourceEdit() after the container show() method, on the container afterLayout listener and on the editor afterRender listener. I've tried also calling it on another button that I added to the container. The result is the same on every try.
The only other option I see is updating ExtJS to 3.3.0, but I haven't seem anything related on the changelogs. Either way, it's going to be my next step. EDIT: The app had another problems when updating, we'll make a bigger effort to update later. As of right now, we are using the HtmlEditor in its original setting.
Thanks!
ran into the same problem (using 3.3.0 by the way)
stumbled upon a fix by dumb luck. i have no idea why this works, but second time is the charm. call it twice in a row to achieve the desired effect..
HTMLEditor.toggleSourceEdit(true);
HTMLEditor.toggleSourceEdit(true);
hope that helps!
Rather calling toggleSourceEdit(), try to setup the configuration while you create HtmlEditor Object
Using toggleSourceEdit() caused some problems for me. One was that this seemed to put the editor somewhere in limbo between source edit and WYSIWYG mode unless I used a timeout of 250ms or so. It also puts the focus in that editor, and I don't want to start the form's focus in the editor, especially since it's below the fold and the browser scrolls to the focused html editor when it opens.
The only thing that worked for me was to extend Ext.form.HtmlEditor and then overwrite toggleSourceEdit, removing the focus command. Then adding a listener for toggling to the source editor when the component is initialized. This is for Ext 4.1 and up. For older versions, replace me.updateLayout() with me.doComponentLayout().
var Namespace = {
SourceEditor: Ext.define('Namespace.SourceEditor', {
extend: 'Ext.form.HtmlEditor',
alias: 'widget.sourceeditor',
initComponent: function() {
this.callParent(arguments);
},
toggleSourceEdit: function (sourceEditMode) {
var me = this,
iframe = me.iframeEl,
textarea = me.textareaEl,
hiddenCls = Ext.baseCSSPrefix + 'hidden',
btn = me.getToolbar().getComponent('sourceedit');
if (!Ext.isBoolean(sourceEditMode)) {
sourceEditMode = !me.sourceEditMode;
}
me.sourceEditMode = sourceEditMode;
if (btn.pressed !== sourceEditMode) {
btn.toggle(sourceEditMode);
}
if (sourceEditMode) {
me.disableItems(true);
me.syncValue();
iframe.addCls(hiddenCls);
textarea.removeCls(hiddenCls);
textarea.dom.removeAttribute('tabindex');
//textarea.focus();
me.inputEl = textarea;
} else {
if (me.initialized) {
me.disableItems(me.readOnly);
}
me.pushValue();
iframe.removeCls(hiddenCls);
textarea.addCls(hiddenCls);
textarea.dom.setAttribute('tabindex', -1);
me.deferFocus();
me.inputEl = iframe;
}
me.fireEvent('editmodechange', me, sourceEditMode);
me.updateLayout();
}
})
}
Then to use it:
Ext.create('Namespace.SourceEditor', {
/*regular options*/
listeners: {
initialize: function(thisEditor) {
thisEditor.toggleSourceEdit();
}
}
});
htmlEditor.toggleSourceEdit(true);
one time should be enough if you do this listening to the afterrender event of the editor.