iScroll - property undefined error - iscroll4

I'm trying to add 2 instances of iScroll on one page yet I don't think that is the cause of this:
function loaded() {
$('.iScrolls').each(function(){
var $this = $(this);
var $id = $this.attr('id');
if( $id ) {
$scrollers[$id] = new iScroll( $id, {
snap: true,
momentum: false,
hScrollbar: false,
onScrollEnd: function () {
$('#indicator > li.active').removeAttr('class');
$('#indicator > li:nth-child(' + ( this.currPageX + 1) + ')').removeAttr('class').addClass('active');
}
});
$('.prev', $this).click(function(){
$scrollers[$id].scrollToPage('prev', 0);
return false;
});
$('.next', $this).click(function(){
$scrollers[$id].scrollToPage('next', 0);
return false;
});
}
});
}
document.addEventListener('DOMContentLoaded', loaded, false);
when the "scrollToPage is triggered I get the error:
Uncaught TypeError: Cannot read property 'length' of undefined
iScroll.scrollTo iScroll.js:984
iScroll._end iScroll.js:614
iScroll.handleEvent
My question being has anyone come across this before and know what causes it?
regards

Was trying to initialise within a hidden container... thats a no no... cheers!

Just ran into this. Ended up being a silly error as I was passing jQuery style "#wrapperID" instead of just the element id "wrapperID"
Hope that helps someone.

.iScrolls is your div class name. Can you create an id on that div?
Example:
<div class="iScrolls" id="iScrolls">
<div id="main">
<div id="thelist">
// Body part
</div>
</div>
</div>

Related

I want access the component snippet in nette framework

I have using the template code like:
{snippetArea wrapper}
{control addFormControl}
{/snippetArea}
and in addFormControl component code is like:
{snippet clientSnippet}
......
{/snippet}
I am using ajax with method presenter method:
public function handleClientChange(){
$this['addFormControl']['addForm']['consignment_client']->setValue("test");
$this->redrawControl('wrapper');
$this->redrawControl('clientSnippet');
}
But it is not redraw the snippet snippet id is snippet-addFormControl-clientSnippet. Please help me to fix it.
I dont think you can call $this->redrawControl('clientSnippet'); in presenter and expect to redraw component. You should call this in the component.
Something like $this['addFormControl']->redrawControl('clientSnippet');
this is how you can do it.
In my latest project i was doing something quite similiar, it's pretty simple tho.
For Nette I use this Ajax: https://github.com/vojtech-dobes/nette.ajax.js
.latte file:
<input type="text" id="search-car" data-url="{plink refreshCars!}">
{snippet carlist}
{foreach $cars as $car}
{var $photo = $car->related('image')->fetch()}
{if $photo}
<img src="{plink Image:image $photo->filename}"/>
{/if}
</a>
{/foreach}
{/snippet}
Notice the '!' at the end of the text input. It's tells Nette to look after the handle function.
The presenter:
public function handleRefreshCars()
{
$this->redrawControl('carlist');
}
public function renderDefault($foo = null)
{
if ($foo === null || $foo === '') {
$this->template->cars = array();
} else {
$this->template->cars = $this->carDao->getFiltered($foo);
}
}
And JS:
function callFilterAjax(url, data) {
$.nette.ajax({
url: url,
data: data
});
}
$("#search-contract-car").on('load focus focusout change paste keyup', function () {
callFilterAjax($(this).data('url'), {"foo": $(this).val()});
});
This should be it. I hope you find this useful

Inline javascript is getting stripped off from the AJAX response by Prototype JS Ajax.Request method

I am working on a Magento store trying to code a widget's javascript layer with the help of Prototype js framework.
In my grid.js file AJAX call is setup like that:
loadTabContent: function(tab, tabType){
if(tab === undefined || tabType === undefined){
return this;
}
entityId = tab.id.split('-')[3];
request = new Ajax.Request(
this.tabContentLoadUrl,
{
method:'get',
onSuccess: this.onTabContentLoad.bind(tab),
onFailure: this.ajaxFailure.bind(this),
evalJS: true,
parameters: {
id: entityId,
type: tabType
}
}
);
}
Below is the success handler:
onTabContentLoad: function(transport){
if(transport && typeof transport.responseText !== undefined){
try{
response = transport.responseText;
}catch (e) {
console.log('PARSE ERROR', e);
response = {};
}
entityId = this.id.split('-')[3];
tabType = this.id.split('-')[1];
if(response && $('tab-' + tabType + '-' + entityId + '-contents')){
$('tab-' + tabType + '-' + entityId + '-contents').update(response);
}
}
},
The content for the div is getting updated correctly by the AJAX call but there is some inline JS in response which is not working.
I can't even see that javascript snippet in Elements tab(chrome developer tool)
Below is the code that handles the AJAX request on server side:
public function renderTabContentAction()
{
$entityId = Mage::app()->getRequest()->getParam('id');
if( ! $entityId){
$this->getResponse()->setHeader('HTTP/1.0', '400', true);
$this->getResponse()->setBody('Invalid parameters provided.');
}
$tabType = Mage::app()->getRequest()->getParam('type');
if( ! $tabType){
$this->getResponse()->setHeader('HTTP/1.0', '400', true);
$this->getResponse()->setBody('Invalid parameters provided.');
}
Mage::register('current_entity_id', $entityId);
Mage::register('current_tab_type', $tabType);
$tabHtml = $this->_getTabsHtml($entityId, $tabType);
$this->getResponse()->setHeader('HTTP/1.0', '200', true);
$this->getResponse()->setBody($tabHtml);
}
Below is the response that gets passed to onTabContentLoad AJAX handler:
<div class="vertical-tabs">
<div class="tabs">
<div class="tab" id="tab-vertical-137-2441">
<input type="radio" id="label-vertical-product-tab-137-2441" name="product-tab-group-137">
<label class="tabs-label" for="label-vertical-product-tab-137-2441">PG-10ml</label>
<div class="content" id="tab-vertical-137-2441-contents">
</div>
</div>
<div class="tab" id="tab-vertical-137-2442">
<input type="radio" id="label-vertical-product-tab-137-2442" name="product-tab-group-137">
<label class="tabs-label" for="label-vertical-product-tab-137-2442">PG-15ml</label>
<div class="content" id="tab-vertical-137-2442-contents">
</div>
</div>
</div>
</div>
<script type="text/javascript">
bulkOrderGrid.initVerticalTabs();
bulkOrderGrid.activateTab('2441', 'VERTICAL');
</script>
You can see that the SCRIPT tags are there in the response. Its just when the content gets updated using Element.update function it strips off the SCRIPT tags. That's what I can understand so far.
NOTE:
I have also used Ajax.Updater along with evalScripts:true and Ajax.Request along with evalJS:true.
Got stuck here. Any help would be much appreciated.
UPDATES:
Since I am using Element.update function to refresh the section. The source of the problem is this part of the code in prototype.js around line no. 2048. I can see its getting executed in js debugger. It does evaluates the js code but also removes the SCRIPT tags from the source. Commenting out stripScripts works fine.
else {
element.innerHTML = content.stripScripts();
}
content.evalScripts.bind(content).defer();
I think your problem is that
the Ajax response is passed through String#evalScripts() but the context is not the global context so instead of your script block do this
<script type="text/javascript">
window.bulkOrderGrid.initVerticalTabs();
window.bulkOrderGrid.activateTab('2441', 'VERTICAL');
</script>
if that doesnt fix it - than you can directly run transport.responseText.evalScripts() but you still need the window. in your script block to resolve the scope of the variables.
You are correct Element.update() remove script tag. you should use
Element.innerHTML

Does anyone know why this Ajax wont work?

I have some code, some to change the class of a div, the rest to load content into the ajax div.
The ajax div however, does not load content. Why might this be?
<script>
window.onload = function () {
var everyone = document.getElementById('everyone'),
favorites = document.getElementById('favorites');
everyone.onclick = function() {
loadXMLDoc('indexEveryone');
var otherClasses = favorites.className;
if (otherClasses.contains("Active")) {
everyone.className = 'statusOptionActive';
favorites.className = 'statusOption';
}
}
favorites.onclick = function() {
loadXMLDoc('indexFav');
var otherClasses = everyone.className;
if (otherClasses.contains("Active")) {
favorites.className = 'statusOptionActive';
everyone.className = 'statusOption';
}
}
function loadXMLDoc(event) {
$.ajax({
url: "../home/" + event.data + ".php",
type: "GET",
success: function (result) {
$("#centreCont").html(result);
}
});
}
}
</script>
These divs start the ajax code (or should do at least)
<div id="everyone" class="statusOptionActive" onclick="loadXMLDoc('indexEveryone')">Everyone, everywhere</div>
<div id="favorites" class="statusOption" onclick="loadXMLDoc('indexFav')">Favourites Only</div>
Why won't it work :(
DEMO
Delete your div onclick event,since already you are manipulating your click event in the script.
Edited div
<div id="everyone" class="statusOptionActive">Everyone, everywhere</div>
<div id="favorites" class="statusOption">Favourites Only</div>
And I don know what argument you are passing in to loadXMLDoc('indexFav'); and loadXMLDoc('indexEveryone'); apart from that your javascript code is correct.
Hope this helps
Thank you
One obvious problem I can see is that you pass a string to loadXMLDoc, then you try to access .data on that string.

jQuery: Get next page via ajax and append it with animation

I am getting next page on my wordpress blog using jquery, finding the desired div and appending it to the existing one. This part works without a problem. But, what I need to do is, to add slideDown animation to it.
This is how my working code so far looks like:
$.get(next_page, function(data) {
var response = $(data);
var more_div = $(response).find('.FeaturedRow1').html();
$('.FeaturedRow1').append(more_div).slideDown('slow');
$('.navigation').not(':last').hide();
I tried adding hide() to response, more_div as well as append lines. In the first case, I get error stating that it cannot set property display of undefined.
In the second case, in the console it display HTML and says "has no method hide". I also tried adding a line $(more_div).hide() but again, I get the error "Uncaught TypeError: Cannot set property 'display' of undefined".
If I use hide in the 3rd line
$('.FeaturedRow1').hide().append(more_div).slideDown('slow');
it hides the whole FeaturedRow1 div and animates it, that takes me to the top of the div, which is what I don't want.
EDIT: Here's the important HTML structure and jQuery code for the desired section
<div class="FeaturedRow1">
<div class="postspage">
//list of posts here
</div>
<div class="navigation">
<span class="loadless">
//hyperlink to previous page
</span>
<span class="loadmore">
//hyperlink to next page
</span>
</div>
</div>
When you click on the hyperlink inside the loadmore, the following jQuery code gets called
$('.loadmore a').live('click', function(e) {
e.preventDefault();
var next_page = $(this).attr('href');
$.get(next_page, function(data) {
var $response = $(data);
var $more_div = $response.find('.FeaturedRow1').hide();
$more_div.appendTo('.FeaturedRow1').delay(100).slideDown('slow')
$('.navigation').not(':last').hide();
});
});
$('.loadless').live('click', function(e) {
e.preventDefault();
if ($('.postpage').length != 1) {
$('.postpage').last().remove();
}
$('.navigation').last().remove();
$('.navigation').last().show();
});
You get error as you are using html method which returns a string not a jQuery object, try the following.
var $response = $(data);
var $more_div = $response.find('.FeaturedRow1').hide();
$more_div.appendTo('.FeaturedRow1').delay(100).slideDown('slow');
//$('.navigation').not(':last').hide();
Update:
$.get(next_page, function(data) {
var $response = $(data);
var more_div = $response.find('.FeaturedRow1').html();
$('<div/>').hide()
.append(more_div)
.appendTo('.FeaturedRow1')
.delay(100)
.slideDown('slow')
$('.navigation').not(':last').hide();
});

Passing mutiple arguments with AJAX. Values come from DIV

I am trying to pass two arguments thought ajax. The variables I am pulling from are in a div and are done on the fly. I can easily pass the date_time but I need to be able to pass a variable "id" also. The date is in an array that is being loaded and changes. The ID does not change for this page.
This is the javascript. Below that will be my div. All attempts to append this have failed. Any ideas?
<div class='letter' width=600 date_time=\"$date_time\" id=\"$id\">
....doing stuff here.....
</div>
function OnScrollLetters () { var div = document.getElementById ("userLetter");
var info = document.getElementById ("info");
if(div.scrollTop == (div.scrollHeight - div.clientHeight))
{
$('div#loadMoreComments').show();
$.ajax({
url: "get_letters_for_profile_scroll.php?lastComment="+ $(".letter:last").attr('date_time'),
success: function(html) {
if(html){
$("#userLetter").append(html);
$('div#loadMoreComments').hide();
}else{
$('div#loadMoreComments').replaceWith("<center><h1 style='color:red'>End of Letters</h1></center>");
}
}
});
}
}
This is my div.
<div class='letter' width=600 date_time=\"$date_time\" id=\"$id\">
....doing stuff here.....
</div>
Try place a "=" between parameter name and value
..."&id="+$(".letter:last").attr('id')

Resources