CreateTextRange is not working in Chrome - javascript

In this code, createRange is not working in Chrome. In IE it is working. Please help how to rectify in this. Is there any other property to work like create range. So that it will helpful for my project.
<script language=javascript>
var isSelected;
function markSelection ( txtObj ) {
if ( txtObj.createTextRange ) {
txtObj.caretPos = document.selection.createRange().duplicate();
isSelected = true;
}
}
function insertTag ( txtName, enclose ) {
if(document.f_activity_email == null) {
var tag = document.getElementById('EmailTokenID').value;
}
else {
var formC = document.f_activity_email;
var tag = formC.EmailTokenID.value;
}
var closeTag = tag;
if ( enclose ) {
var attribSplit = tag.indexOf ( ' ' );
if ( tag.indexOf ( ' ' ) > -1 )
closeTag = tag.substring ( 0, attribSplit );
}
if ( isSelected ) {
var txtObj = eval ( "document.forms[0]." + txtName );
if (txtObj.createTextRange && txtObj.caretPos) {
var caretPos = txtObj.caretPos;
caretPos.text = ( ( enclose ) ? "<"+tag+">"+caretPos.text+"</"+closeTag+">" : tag+caretPos.text );
markSelection ( txtObj );
if ( txtObj.caretPos.text=='' ) {
isSelected=false;
txtObj.focus();
}
}
} else {
// placeholder for loss of focus handler
}
}

CreateTextRange is a Microsoft specific function, but there is an easy work around.
Use createRange instead as in this post for example:
if (document.selection) { //IE
var range = document.body.createTextRange();
range.moveToElementText(document.getElementById(containerid));
range.select();
} else if (window.getSelection) { //others
var range = document.createRange();
range.selectNode(document.getElementById(containerid));
window.getSelection().addRange(range);
}

I had this issue with node's JSDOM and codemirror (which attempts to use document.createRange)
It happens because document.createRange (chrome) does not exist ATM on JSDOM and so it tries to use document.body.createTextRange (IE) instead and falls over.
To fix this I had to stub the document.createRange function in my unit test setup as follows:
global.document.createRange = () => {
return {
setEnd: () => {},
setStart: () => {},
getBoundingClientRect: () => {}
}
}
There is talk about JSDOM polyfilling document.createRange:
See https://github.com/tmpvar/jsdom/issues/399
At the time of writing this has not yet happened.

createTextRange is only in IE.
Have a look at this one
http://help.dottoro.com/ljrvjsfe.php

As of March 31, 2020. This works for mocking JSDOM for jest unit tests
(window as any).global.document.createRange = () => {
return {
setEnd: () => {},
setStart: () => {},
getBoundingClientRect: () => {},
getClientRects: () => []
};
};

Related

Jquery string replacement €

I use this Jquery code to hide the € symbol on my page.
(function($){
jQuery(document).ready(function() {
jQuery(".amount:contains('€')").html(function(_, html) {
return html.replace(/(€ )/g, '');
});
});
})(jQuery);
but for some reason I'm unable to get it to work inside WordPress.
I know it has to be in the Document ready function because of the no-conflict mode.
So that is what I have done.
This code is in the same js file i use for other scripts loaded on the same page;
(function($){
jQuery(document).ready(function() {
jQuery(".amount:contains('€')").html(function(_, html) {
return html.replace(/(€ )/g, '');
});
});
})(jQuery);
(function($){
jQuery(document).ready(function(){
console.log("ready to use!");
if(jQuery('.single-product').length > 0) {
var _sfm_brand = '';
var _sfm_model = '';
var _sfm_generation = '';
var _sfm_engine = '';
var _sfm_engine_ecu = '';
function getUrlVars() {
var vars = [], hash;
var hashes = window.location.href.slice(window.location.href.indexOf('?') + 1).split('&');
for(var i = 0; i < hashes.length; i++){
hash = hashes[i].split('=');
vars.push(hash[0]);
vars[hash[0]] = hash[1];
}
return vars;
}
_sfm_brand = getUrlVars()["_sfm_brand"];
_sfm_model = getUrlVars()["_sfm_model"];
_sfm_generation = getUrlVars()["_sfm_generation"];
_sfm_engine = getUrlVars()["_sfm_engine"];
_sfm_engine_ecu = getUrlVars()["_sfm_engine_ecu"];
if(typeof _sfm_brand !== "undefined" && _sfm_brand != "") {
jQuery('input[name="tmcp_textfield_0"]').val(decodeURIComponent(_sfm_brand));
jQuery('input[name="tmcp_textfield_0"]').prop('readonly',true);
} else {
jQuery('input[name="tmcp_textfield_0"]').val('');
}
if(typeof _sfm_model !== "undefined" && _sfm_model != "") {
jQuery('input[name="tmcp_textfield_1"]').val(decodeURIComponent(_sfm_model));
jQuery('input[name="tmcp_textfield_1"]').prop('readonly',true);
} else {
jQuery('input[name="tmcp_textfield_1"]').val(decodeURIComponent(""));
}
if(typeof _sfm_generation !== "undefined" && _sfm_generation != "") {
jQuery('input[name="tmcp_textfield_2"]').val(decodeURIComponent(_sfm_generation));
jQuery('input[name="tmcp_textfield_2"]').prop('readonly',true);
} else {
jQuery('input[name="tmcp_textfield_2"]').val(decodeURIComponent(""));
}
if(typeof _sfm_engine !== "undefined" && _sfm_engine != "") {
jQuery('input[name="tmcp_textfield_3"]').val(decodeURIComponent(_sfm_engine));
jQuery('input[name="tmcp_textfield_3"]').prop('readonly',true);
} else {
jQuery('input[name="tmcp_textfield_3"]').val(decodeURIComponent(""));
}
if(typeof _sfm_engine_ecu !== "undefined" && _sfm_engine_ecu != "") {
jQuery('input[name="tmcp_textfield_4"]').val(decodeURIComponent(_sfm_engine_ecu));
jQuery('input[name="tmcp_textfield_4"]').prop('readonly',true);
} else {
jQuery('input[name="tmcp_textfield_4"]').val(decodeURIComponent(""));
}
}
});
})(jQuery);
And that code is working great. So I'm sure the file is loaded.
Also, what is strange is when loading the js file by the url I get it like this:
(function($){
jQuery(document).ready(function() {
jQuery(".amount:contains('€')").html(function(_, html) {
return html.replace(/(€ )/g, '');
});
});
})(jQuery);
I also tried to change the € symbol with € and u20ac but they are also not working.
Any one who can help me out?
Thank you :)
EDIT: in Jsfiddle it is working. And I allready did some other articles, but with no luck. So that is why I'm posting my own.
Wordpress had alot of javascript and php functions loaded, so may one of theme overide or conflict with your codes.
If what you want is hide € character, better add this into your theme's functions.php:
function replace_text($text) {
$text = str_replace('€', '', $text);
return $text;
}
add_filter('the_content', 'replace_text');
in case above method not working. Use this instead:
jQuery(document).ready(function(){
jQuery('body').hover(function() {
let search = '€';
if(jQuery('.amount:contains('+search+')').html()!=undefined){
var text =
jQuery('.amount:contains('+search+')').html().replace(search, '');
jQuery('.amount:contains('+search+')').html(text);
}else{
return false;
}
});
});
I also did try to change the currency symbol with an function. But It is not getting the page-template;
add_filter( 'woocommerce_currency_symbol', 'change_currency_symbol', 10, 2 );
function change_currency_symbol( $symbols, $currency ) {
if ( is_page_template( 'archive-chiptuning.php' ) && ( 'EUR' === $currency )) {
return '';
}
return $symbols;
}
Without is_page_template it is working, but since I use different products, with different currencys (€ and credit(s)) I'm not able to use it like that. Because it changes all the symbols.
EDIT: check for page template outside loop:
add_filter( 'woocommerce_currency_symbol', 'change_currency_symbol', 10, 2 );
function change_currency_symbol( $symbols, $currency ) {
global $template;
if ( basename( $template ) === 'archive-chiptuning.php' && ( 'EUR' === $currency )) {
return '';
}
return $symbols;
}
Use:
global $template;
if ( basename( $template ) === 'archive-chiptuning.php'
Thanks to this post: https://wordpress.stackexchange.com/questions/328384/is-page-template-not-working/375028#375028

executeScript not work

I have some JS-scripts in my tests. I don't understand why, but it stoped working now.
Maybe it happened after protractor updating (to version 3.3.0).
Maybe somebody know what may happend?
My scripts:
PsComponent.prototype.getHighlightedText = function () {
return browser.executeScript_(function getSelectionText() {
var text = "";
if (window.getSelection) {
text = window.getSelection().toString();
} else if (document.selection && document.selection.type != "Control") {
text = document.selection.createRange().text;
}
return text;
});
};
Result:
nothing
And:
PsComponent.prototype.getCaretPosition = function () {
return browser.executeScript(function (input) {
if (document.selection && document.selection.createRange) {
var range = document.selection.createRange();
var bookmark = range.getBookmark();
var caret_pos = bookmark.charCodeAt(2) - 2;
} else {
if (input.setSelectionRange){
caret_pos = input.selectionStart;
}
}
return caret_pos;
});
};
Result:
- Failed: JavaScript error (WARNING: The server did not provide any stacktrace information)
Not directly answering the question, but here are the similar functions we are using (I guess things like that would naturally come up in any browser test automation project):
this.getCaretPosition = function (elm) {
return browser.executeScript(function () {
var webElement = arguments[0];
return webElement.value.slice(0, webElement.selectionStart).length;
}, elm.getWebElement())
};
this.getInputSelection = function (elm) {
return browser.executeScript(function () {
var webElement = arguments[0];
return webElement.value.substring(webElement.selectionStart, webElement.selectionEnd);
}, elm.getWebElement())
};
Usage samples:
expect(helpers.getCaretPosition(amountInput)).toEqual(1);
expect(helpers.getInputSelection(amountInput)).toEqual("-100.00");

rrdFlotAsync and realtime

I'm trying to call rrdFlotAsnc in a timeout for realtime updates, I always get an Exception:
0x80004005 ...FetchBinaryURLAsync::....data:no
without calling from a timer, all works fine, so I'm a little confused.
I used the debugger and I'm more confused:
my code:
if ( typeof (f) == 'undefined' ) {
var f=new rrdFlotAsync("mygraph2",fname,null,{yaxis:{min:1000,max:1030}},gtype_format,ops);
} else {
f= rrdFlotAsync("mygraph2",fname,null,{yaxis:{min:1000,max:1030}},gtype_format,ops);
}
Every time, the program jumps into both cases???? But why?? Is it a problem of missing parameter ?
and whats the reason for the exception.
All remarks are welcome.
the complete code:
function drawBaro() {
document.write('<div id="mygraph2"></div>');
//document.getElementById("infotable").deleteRow(0);
fname="/Aurora/db/baro.rrd";
var gtype_format={'druck':{ title: 'druck', label:'Druck', color: "#ff8080"}}
var ops={use_checked_DSs: true, checked_DSs: ['druck'], use_rra:true, rra:0, graph_width:"800px", use_windows: false, graph_only:true}
// the rrdFlotAsync object creates and handles the graph
var vorh = 0;
if ( typeof (f) == 'undefined' ) {
vorh = 1;
} else {
vorh = 2;
}
// var f=new rrdFlotAsync("mygraph2",fname,null,{yaxis:{min:1000,max:1030}},gtype_format,ops);
if ( vorh == 1) {
var f=new rrdFlotAsync("mygraph2",fname,null,{yaxis:{min:1000,max:1030}},gtype_format,ops,null, null, ucallb);
} else {
f= rrdFlotAsync("mygraph2",fname,null,{yaxis:{min:1000,max:1030}},gtype_format,ops);
}
}
function ucallb () {
alert ();
}
function drawBaroDia () {
var updateInterval = 20 * 1000;
$(this).val("" + updateInterval);
update ();
}
function update () {
var updateInterval = 20 * 1000;
drawBaro ();
setTimeout ( update, updateInterval );
}
}

jQuery Name Spacing and setTimeout

I'm trying to build a jQuery Plugin using there Name spacing as per there direction here:
http://docs.jquery.com/Plugins/Authoring#Namespacing
Now i have run into a problem my plugin need to use a setTimeout to fire one of its methods,
var jScrollerMethods = {
ready:function(){
return this.each(function(){
var self = this,
$this = $(this),
data = $this.data('jScroller');
settings.timeoutHandle = setTimeout(function(){
if(settings.direction = "left"){
this.moveLeft();
}else if(settings.direction = "right"){
this.moveRight();
}
}, settings.time);
$this.data('jScroller', {
settings: settings,
element: this
});
});
}
$.fn.jScroller = function(call){
if ( jScrollerMethods[call] ) {
return jScrollerMethods[call].apply( this, Array.prototype.slice.call( arguments, 1 ));
} else if ( typeof call === 'object' || ! call ) {
if (call) { $.extend(settings, call); }
return jScrollerMethods.init.apply( this, call );
} else {
$.error( 'Method ' + call + ' does not exist on jQuery.jScroller' );
}
}
but as I though would happen setTimeout is fired from the Window not the plugin object and being that I want the plugin to be usable on more than once per page so I can't just save the current object to the window how can I achieve this?
I found out that when using this outside of the return this.each will give you the exact selector results
So with some work i have managed to do it,
var jScrollerMethods = {
ready:function(){
selector = this;
return this.each(function(){
var self = this,
$this = $(this),
data = $this.data('jScroller');
settings.timeoutHandle = setTimeout(function(){
if(settings.direction = "left"){
selector.jScroller("moveLeft");
}else if(settings.direction = "right"){
selector.jScroller("moveRight");
}
}, settings.time);
$this.data('jScroller', {
settings: settings,
element: this
});
});
}
$.fn.jScroller = function(call){
if ( jScrollerMethods[call] ) {
return jScrollerMethods[call].apply( this, Array.prototype.slice.call( arguments, 1 ));
} else if ( typeof call === 'object' || ! call ) {
if (call) { $.extend(settings, call); }
return jScrollerMethods.init.apply( this, call );
} else {
$.error( 'Method ' + call + ' does not exist on jQuery.jScroller' );
}
}

jquery conflict with js script

welcome all ,
i have a problem with my images slider , it runs successfuly until poll script excuted then it stops , tried to combine both scripts didn't work also tried to use noConflict but in stops both of them .
this is the slider
(function ($) {
$.fn.s3Slider = function (vars) {
var element = this;
var timeOut = (vars.timeOut != undefined) ? vars.timeOut : 4000;
var current = null;
var timeOutFn = null;
var faderStat = true;
var mOver = false;
var items = $("#sliderContent .sliderImage");
var itemsSpan = $("#sliderContent .sliderImage span");
items.each(function (i) {
$(items[i]).mouseover(function () {
mOver = true
});
$(items[i]).mouseout(function () {
mOver = false;
fadeElement(true)
})
});
var fadeElement = function (isMouseOut) {
var thisTimeOut = (isMouseOut) ? (timeOut / 2) : timeOut;
thisTimeOut = (faderStat) ? 10 : thisTimeOut;
if (items.length > 0) {
timeOutFn = setTimeout(makeSlider, thisTimeOut)
} else {
console.log("Poof..")
}
};
var makeSlider = function () {
current = (current != null) ? current : items[(items.length - 1)];
var currNo = jQuery.inArray(current, items) + 1;
currNo = (currNo == items.length) ? 0 : (currNo - 1);
var newMargin = $(element).width() * currNo;
if (faderStat == true) {
if (!mOver) {
$(items[currNo]).fadeIn((timeOut / 6), function () {
if ($(itemsSpan[currNo]).css("bottom") == 0) {
$(itemsSpan[currNo]).slideUp((timeOut / 6), function () {
faderStat = false;
current = items[currNo];
if (!mOver) {
fadeElement(false)
}
})
} else {
$(itemsSpan[currNo]).slideDown((timeOut / 6), function () {
faderStat = false;
current = items[currNo];
if (!mOver) {
fadeElement(false)
}
})
}
})
}
} else {
if (!mOver) {
if ($(itemsSpan[currNo]).css("bottom") == 0) {
$(itemsSpan[currNo]).slideDown((timeOut / 6), function () {
$(items[currNo]).fadeOut((timeOut / 6), function () {
faderStat = true;
current = items[(currNo + 1)];
if (!mOver) {
fadeElement(false)
}
})
})
} else {
$(itemsSpan[currNo]).slideUp((timeOut / 6), function () {
$(items[currNo]).fadeOut((timeOut / 6), function () {
faderStat = true;
current = items[(currNo + 1)];
if (!mOver) {
fadeElement(false)
}
})
})
}
}
}
};
makeSlider()
}
})(jQuery);
and this is the poll script
window.onload = function() {
$(".sidePollCon").load("ar_poll.html", function(r, s, xhr) {
if (s == "error") {
$(".sidePollCon").load("poll.html");
} else {
$(".vote_booroo").html("صوت الان");
$(".viewresults").html("شاهد النتيجة");
$("fieldset p").html("");
$(".results_booroo p").html("");
$(".result_booroo").attr("src", "../images/poll_color.jpg");
}
});
};
One potential problem could be the window.onload assignment. It is very prone to conflict.
Every time you do window.onload = the previous assignemnt will be overridden. See demo here:
The output shows that the first window.onload assignment never gets called, while the jQuery alternative does get called.
jQuery.noConflict does little in this regard. All it does is to prevent override the $ symbol so that another lib can use it.
So if you are also using the window.onload event to invoke the slider, then you have conflict. You can easily solve this problem by using the jquery format:
$(window).load(function() {
...
});
However usually you would tie the event to $(document).load(function(){...}); or in short form: $(function(){...}).
So for your poll that would be:
$(function(){
$(".sidePollCon").load("ar_poll.html", function(r, s, xhr) {
if (s == "error") {
$(".sidePollCon").load("poll.html");
} else {
$(".vote_booroo").html("صوت الان");
$(".viewresults").html("شاهد النتيجة");
$("fieldset p").html("");
$(".results_booroo p").html("");
$(".result_booroo").attr("src", "../images/poll_color.jpg");
}
});
});
Hope that helps.
resolving conflicts in jquery (possibly with another JS library .. like script.aculo.us) can be resolved using noconflict()
http://api.jquery.com/jQuery.noConflict/
$.noConflict();
but make sure that u have no error in your javascript code itself. use firebug and
console.log('') to test your script.

Categories