Dynamically insert expander in jQuery Mobile - javascript

I am quite new to jQuery and are currently despairing of trying to insert a dynamically created expander into a jQuery-Mobile page which looks like the following:
<div data-role="page" id="myPage">
<div data-role="content">
<div id="myContainer"></div>
</div>
</div>
As the expander should be inserted into "myContainer", I am writing:
var expander = $("<div data-role='collapsible' data-collapsed='true'><h3 class='category' /><div class='content' /></div>");
$("#myContainer").append(expander);
expander.find(".category").text(/*Some text*/);
expander.find(".content").text(/*Some text*/);
However, only a unthemed and not collapsible div appears in my document.
I guess, I will have to manually toggle the creation of the expander similar to refreshing a listview - I did not find anything about that in the documentation, however.
Unfortunately, neither
expander.Refresh();
//nor
expander.Expander();
seems to exist.
Many thanks in advance for your responses!

This question is in fact a duplicate happening so often that I created a FAQ about it.
You need to use .page() on the topmost element that you add to DOM.
See here for details:
http://jquerymobiledictionary.dyndns.org/faq.html
[edit]
I have also reached the moment when I wanted to use .page inside a page* event and the solution was rather obvious to me - use a semaphore.
If you don't know how to implement a semaphore, see my dual column plugin code as an example (it's on the same site)

Related

If a collapsible element is clicked, collapse all other (collapsible) already opened elements - Bootstrap

I am working at the moment on my personal website and I have the following issue:
On my website I would like to use a collapsible "main menu" which should acts like the default Bootstrap Accordion. My main navigation menu is an unsorted list, which can collapse. Each <li> element has the data-toggle="collapse" attribute and the nested <div> the collapse class. This works fine.
The problem is, that the menu points does not get closed when another menu point is opened. Because of the HTML structure, which I have for design reasons and some other features I need, I am not able to use the Bootstrap default Accordion feature.
In another part on the website I am successfully using already the Accordion feature. There I can have the necessary HTML structure for the Bootstrap Accordion which looks like this (example code from this specific part on my webpage):
<div id="cases-list-elements-group" class="**panel-group**">
<li class="**panel** li-main-style ul-style">
<a class="nav-scroll list-case-style" href="#case-details-1"
data-toggle="collapse" **data-parent="#cases-list-elements-group"**>
Case 1 Details </a>
<div id="case-details-1" class="collapse case-details">
<div class="container container-cases">
The example from above works. So I know how to use the default Accordion from Bootstrap. My problem is, as explained before, I can not have this HTML structure for my main menu:
panel-group
panel
data-parent="#id-of-the-panel-group"
So I need a workaround, to close the already opened menu point, after another is expanded. I have searched for hours and found some JavaScript (jQuery) examples which should close the already opened element. Unfortunately no one of the examples I have found helped me to solve my problem. They were not detailed enough for me to understand the logic behind or didn't work at all (yes, didn't worked as well in the provided JS Fiddle examples)
I know I need to do this with some custom JavaScript. After hours of trying I thought, probably someone here can advise.
I know you searched for answers and found some jQuery examples, but have you tried it this way?
Basically what I've done is just hidden a list in each list item. If you intend to make the accordion list items links as well, just add an href tag around them. I'm sure this code could be shortened but here's the jQuery half of it:
$('#first').hide();
$('#second').hide();
$('#third').hide();
$('#fourth').hide();
$('#colours').click(function(){
$('#first').slideToggle();
$('#second:visible').toggle();
$('#third:visible').toggle();
$('#fourth:visible').toggle();
})
$('#shapes').click(function(){
$('#second').slideToggle();
$('#first:visible').toggle();
$('#third:visible').toggle();
$('#fourth:visible').toggle();
})
$('#fruit').click(function(){
$('#third').slideToggle();
$('#first:visible').toggle();
$('#second:visible').toggle();
$('#fourth:visible').toggle();
})
$('#vehicles').click(function(){
$('#fourth').slideToggle();
$('#first:visible').toggle();
$('#second:visible').toggle();
$('#third:visible').toggle();
})
And here's the full thing JSFIDDLE

How to add content to a bootstrap panel by using jQuery?

After retrieving info, I want to show it inside a bootstrap panel by using jQuery.
I use the .html() function to show the panel.
$('#id_div').html('<div class="panel panel-info"><div class="panel-heading"><h3 class="panel-title">'+my.awesome.title+'</h3></div><div class="panel-body">Content here :) There is more and this is becoming a super long line ...</div></div>');
I have found that there is a way to break this into several lines by using .append() . I have tried the following:
$('#id_div').append('<div class="panel-body">Adding more content here :) </div>');
This does not work, since the added text appears outside the panel.
How do I specify where exactly I want the code to be appended?
Solved.
According to David, by using the .find() function, you can specify where exactly you want the text to be appended.
$('#id_div').find('.panel-body').append('Adding more content here :)');

div has different width after page refresh

When someone opens the page a <div> gets full width (1200px+). If I reload the page, the width is changed to the right one (550px). The browsers have their cache cleared, so this isn't a cache issue.
First visit:
After refresh:
This is a "custom HTML code" module in a Joomla 2.5 site. This is the code of divs that have their widths swapped:
<div class="art-nostyle">
<div class="custom">
<div id="script_nn_tabs54bfa417561de" class="script_nn_tabs" style="display:none;"></div>
<div id="nn_tabs_container_1____685___" class="nn_tabs_container outline_handles outline_content align_left nn_tabs_container_1_">
<div class="nn_tabs_nav" style="display: block;"></div>
At first sight I thought that the div id="nn_tabs_container_1____685___" was the problem, so I added this jQuery script at the end of the module :
var j = jQuery.noConflict();
j(document).ready(function () {
j("div[id^='nn_tabs_content_1____']" ).css("width","550px");
});
After it failed to fix it, I noticed that the problem was at the <div class="art-nostyle">. That div has no style at all! I can't use the above script for the art-nostyle div because it is added before every single module in the site. Could someone explain how it is possible when this probably isn't a cache issue - an element getting fixed width after a page refresh? I tried it on 5 different PCs that never visited the url before.
P.S. I can't recreate the problem in JSFiddle: that's why I didn't post a fiddle link.
Edit: Link of the site if someone want to check with his own eyes. Its the in middle of the index.
Edit2: I noticed that if i disable cookies the div wont change width after refresh. It will keep the full width.
If you're using jQuery, maybe you could remove the ".art-nostyle" class that may be inheriting weird styles from Joomla. You could give the one <div class="art-nostyle"> a unique ID (e.g. id="navigationLinks"), and then use this:
$(function() {
$("#navigationLinks").removeClass("art-nostyle");
$("#navigationLinks").css("width","550px");
});
You could also check to see if there's any other Javascript that references this div, because it seems weird that the problematic div would inherit the strange behavior just from HTML/CSS.
I had the same issue. However, I have found the answer. Use $(window).load() out instead of $(document).ready().
See also: window.onload vs $(document).ready()

Creating Masonry items with jQuery

I need to be able to create Masonry items in jQuery rather than HTML. However, the below fails to output anything. By contrast, the commented out HTML equivalent works perfectly.
Is there a workaround for this?
HTML:
<div id="container" class="feed">
<!-- this would work fine:
<div class="item">hey</div>
<div class="item">hi</div>
<div class="item">hello</div>
-->
</div>
jQuery:
$("div.feed").html("<div class='item'>hey</div><div class='item'>hi</div><div class='item'>hello</div>");
EDIT
To be clear, that jQuery is appending what it's supposed to where the commented out HTML is. My issue is making Masonry respond to that - the three divs should be side-by-side.
Masonry lays out once and only once unless you bind resize to it using either one of
msnry.bindResize()
// or with jQuery
$container.masonry('bindResize')
In which case, when the window is resized, the Masonry instance will reload itself by recollecting the items and laying them out again. So there are two options to your problem.
Call window.resize() after adding items if you've binded resize.
Use masonry's appended method instead (passing the elements as a fragment): http://masonry.desandro.com/methods.html#appended
Edit:
You should really use the appended method. Here's an example using your html elements.
var $fragment = $("<div class='item'>hey</div> \
<div class='item'>hi</div><div class='item'>hello</div>");
$('div.feed').append($fragment).masonry('appended', $fragment);
JSFiddle: http://jsfiddle.net/5xfpF/

dijit.findWidgets return null array?

On the JSTL page I have following divs
<div dojoType="dijit.layout.TabContainer" style="width: 100%; height: 100%;" doLayout="false" id="dojoTabbedPane" >
<c:forEach items="${summariesMap}" var="summaryEntry">
<div dojoType="dijit.layout.ContentPane" title="${summaryEntry.key}">
I try to find all divs under (including dojoTabbedPane) in order to recersively destroy all the contentPane under it. Then I can use jQuery.load() to reload contents and use
dojo.parser.parse(dijit.byId("dojoTabbedPane"));
to re-parse the component to make sure the tabbedPane can be rendered(otherwise it doesn't and cause memory leak or error)
Here the question is:
(1) Am I on the right track to re-parse the dojo TabbedContainer?
(2) Why each time the findWidgets function just return array with size 0?
Thanks in advance.
I'll answer 2 first: because dijit.findWidgets expects a DOM node, not a widget. If you need to find all widgets inside another widget, you can use getDescendants instead:
var descWidgets = dijit.byId("dojoTabbedPane").getDescendants();
Onto question 1: First off: if you want to destroy all the tabs in a TabContainer, you can use :
dijit.byId("dojoTabbedPane").destroyDescendants();
Now, if I understand you correctly, you subsequently grab a string of HTML from the server (using jQuery), and want to add it to the TabContainer. This new content contains several ContentPane divs, and you want these to become the new tabs in the TabContainer.
I may be wrong here, but I don't think that's doable without some gnarly hack. Once you've parsed/instantiated a TabContainer, you should add tabs using addChild, passing instantiated ContentPanes.
This means that if you get new HTML content like this from the server (via your jQuery load):
<div dojoType="dijit.layout.ContentPane" title="new tab1">foo</div>
<div dojoType="dijit.layout.ContentPane" title="new tab2">bar</div>
.. then your best bet is to remove the old TabContainer and make a new one, then parse the whole thing. If you're able to change the content you get from your server, perhaps you can simply wrap that in <div dojoType="dijit.layout.TabContainer....

Categories

Resources