Adding jqGrid Custom Navigation to Top Toolbar - javascript

Is it possible to add navigation items to the "top pager" in a jqGrid? And if so, what's the syntax for doing so?
I have an HTML snippet on my page that looks like this
<table id="mygrid">
</table>
<div id="mygrid_pager"></div>
And then an jqGrid initialization that looks something like this
$('#mygrid').jqGrid({
..., //full config string removed for brevity,
pager:jQuery('#mygrid'),
toppager:true
});
$('#mygrid').jqGrid('navGrid', '#mygrid_pager'),{
'add':false,
'del':false,
'edit':false,
'search':false,
'refresh':false,
'cloneToTop':true,
}).navButtonAdd('',{...}); //config navbutton string for button removed for brevity
A "top pager" with the id of #mygrid_toppager is automatically inserted into the page, but its custom buttons (which appear on the bottom pager) don't come along for the ride.
I see that there's a "cloneToTop" option included for the navGrid, but its description seems confusing, and I can only assume I'm using it wrong.
Clones all the actions from the bottom pager to the top pager
if defined. Note that the navGrid can be applied to the top
pager only. The id of the top pager is a combination of grid id and
"_toppager"
My understanding of the option is it will take buttons added to the bottom pager, and clone them to the top. However, the description then goes on to say "the navGrid can be applied to the top pager only, which doesn't make any sense since you're cloning it. The pont being, I clearly have a deep misunderstanding of how the API is supposed to be used.
If anyone can point me in the right direction (even just to a working example somewhere) I'd appreciate it. I'd prefer to do this through official APIs, as opposed to clever DOM manipulation, as seen elsewhere on StackOverflow.

OK, it seems that I found a way which looks like better. The idea is to use navButtonAdd with the "#list_toppager_left" instead of "#pager".
I modified the old answer so, that one custom button are added on the top of the navigation toolbar together with one standard button. Other elements from the top navigation toolbar will be removed. The results will looks like
You can see the corresponding demo live here.

Related

GridStack how to disable moving or dragging grid widgets

As the title suggests, I have issues disabling moving or dragging grid widgets. I have tried using data-gs-no-move, data-gs-lockedand data-gs-no-resize as listed in GridStack documents, but it still draggable and moveable in my browser. Is there any workarounds to it?
Currently using GridStack 0.2.6.
Add the data attribute data-gs-no-move="yes" to the grid-stack-item, as demonstrated below.
<div class="grid-stack-item" data-gs-no-move="yes">
<div class="grid-stack-item-content">
<!-- content goes here -->
</div>
</div>
If you need to prevent it from being moved when another item is dragged, then you will also need to the data-gs-locked="yes" attribute.
If you want to stop it being resized, then add the data-gs-no-resize="yes" attribute.
You can mix and match as you require.
Hope that helps someone.
You can use data-gs-no-move="yes" and data-gs-no-resize="yes". locked refers only to other widgets affecting the widget in question.
PS - The docs are h*ckin old. I'll update them soon and hopefully they won't leave anyone baffled.
I was not able to get this to work using the previous answers, but this did using the latest version of GridStack (v7.2.3):
grid.update($gridItem, {
locked: true,
noResize: true,
noMove: true
});
Where $gridItem is the HTML element of the grid item you want to update, or you can use a class string.

Need to expand multiple lines with javascript, text overflow

http://jsfiddle.net/10h8t3ah/
function changeHeight(rowNum) {
document.getElementById("demo").style.height= "70px";
var fooBar = document.getElementById(rowNum);
fooBar.style.height = "100px";
}
What I am trying to accomplish here is to pass through a variable defined as row1, row2, row3, and row4 as rowNum and it will change the height of both the link and the paragraph with the corresponding row#.
I am trying to pass the ID of both the paragraph and the link so that if you hover over the link and vice versa, the height will change.
Essentially, if you hover over either the link or the paragraph, the corresponding containers side by side of each other will expand in height and the text in the paragraph will be visible. The paragraph text I have set with wrap-text property of break word but it seems to just overflow out anyway.
OK - there are couple of concepts that need to be corrected to understand why this is not working:
the id of a DOM object must be unique (your jsfiddle uses the same ID on both of your "rows" - I've updated your code to use a class instead of an id so that)
the parameter you are passing to your changeHeight function must be a string (if you pass row1, then row1 must be a defined variable, instead you should pass 'row1' -- again, see my updated fiddle code)
Here is a jsfiddle that does most of what you want, I think : http://jsfiddle.net/zwyr4hn1/10/
There were also a couple of little things that I've fixed up:
1. you need to return the other rows back to the smaller size when a new one is hovered (I've used the class row on all the row objects to do this ) 2. this css is needed to get your a objects to resize in the way you want : a { display: inline-block; }
I haven't addressed the wrap-text issue you mentioned because I didn't see that on the jsfiddle.
Instead of designing the complex JavaScript functions on your own, ust use accordion to expand the contents. Here's the Bootstrap framework accordions, especially designed for these purposes.
Link to page where you can learn more about it.
http://www.w3schools.com/bootstrap/bootstrap_collapse.asp

jQuery UI Dialog: Dialog Element Disappearing from the DOM

I'm working on a project and I am attempting to create a modal dialog "pop-up" to capture data in a form. I haven't worked with jQuery UI's Dialog widget previously, but I've worked with others and it seemed straight forward.
I created the following very simple code snippet to test as I went along:
<div class="app-email">
<div>
<a href="#"
class="app-email-opener">
Click to add or edit your e-mail settings.
</a>
</div>
<div class="app-email-modal">
Oh, Hai.
</div>
</div>
$('.content').on({
click: function () {
console.log('I was totes clicked.');
var parent = $(this).parents('.app-email');
console.log(parent);
var target = parent.find('.app-email-modal');
console.log(target);
$(target).dialog('open');
}
}, '.app-email-opener');
$('.app-email-modal').dialog({
autoOpen: false,
modal: true,
show: false
});
For reference: the class 'content' is a higher level block to catch delegated events without having to go all the way up the DOM.
The issue I'm running into is that the div with class="app-email-modal" seems to flash onto the page and then disappear from the DOM completely. jQuery, therefore, isn't able to find it and do anything because at that point it simply doesn't exist.
The overall project is in ASP.NET MVC 4, using Visual Studio 2013.
Any information would be greatly appreciated.
So, finally discovered what's happening via this previously answered question:
Jquery Dialog - div disappears after initialization
//EDIT
For any possible future usefuless -
What was happening was that jQuery UI will move any DOM elements specified as Dialogs to the bottom of the page, rather than keep them in the location specified in the HTML markup. So, in my case, I was looking for things by class, but only within the scope of the app-email-openers parent app-email div.
To remedy this, I used templating (in my case, Razor) to add unique ids to each app-email-modal div, and added a data- attribute to associate the link with the specific unique id. This way they jQuery UI can move the elements as it sees fit, but there still easily accessible.
//END EDIT
I feel like that functionality should be better spelled out in the documentation. Even their own example doesn't operate like this.
Corollary: I attempted to use the appendTo option to have the DOM elements not be shifted to the bottom of the page, but they're still moved to the bottom. So, there's that.

Expand/Collapse Text

The code below works fine with ONE Reveal/Hide Text process
<div class="reveal">Click Here to READ MORE...</div>
<div style="display:none;">
<div class="collapse" style="display:none;">Collapse Text</div>
However if this code is duplicated multiple times, the Collapse Text shows up and doesn't disappear and in fact conflicts with the Expand to reveal even more text instead of collapsing as it should.
In this http://jsfiddle.net/syEM3/4/ click on any of the Click Here to READ MORE...
Notice how the Collapse Text shows up at the bottom of the paragraphs and doesn't disappear. Click on the Collapse and it reveal more text.
How do I prevent this and getting to work as it should?
The two slideDown function calls are not specific to the .reveal and/or .collapse that you are currently doing. i.e.
$(".collapse").slideDown(100);
will find all the elements with the class .collapse on the page, and slide them down. irrespective of what element you just clicked.
I would change the slideDown call to be relavant to the element you just clicked i.e. something like this
$('.reveal').click(function() {
$(this).slideUp(100);
$(this).next().slideToggle();
$(this).next().next(".collapse").slideToggle(100);
});
in your code
$('.reveal').click(function() {
$(this).slideUp(100);
$(this).next().slideToggle();
$(".collapse").slideDown(100);
});
$('.collapse').click(function() {
$(this).slideUp(100);
$(this).prev().slideToggle();
$(".reveal").slideDown(100);
});
this two rows doesn’t do what you want as they act on all elements of the specified class
$(".reveal").slideDown(100);
$(".collapse").slideDown(100);
When you do $(".collapse").slideDown(100);, jQuery runs slideDown on everything with the .collapse class, not just the one that's related to your current this. To fix this, refer to the collapse based on its location to $(this).
Do do this, use something like $(this).siblings(".collapse").slideDown(100);
Note that this particular selector will only work if you enclose each text block in its own div. With each text element in its own div, like you have it now, .siblings(".collapse"), which selects all the siblings of $(this) with the collapse class, will still select both of the collapse elements.
Okay, I think you should take a different approach to your problem.
See, jQuery basically has two purposes:
Selecting one or more DOM elements from your HTML page
manipulate the selected elements in some way
This can be repeated multiple times, since jQuery functions are chainable (this means you can call function after function after function...).
If I understood your problem correctly, you are trying to build a list of blog posts and only display teasers of them.
After the user clicks the "read more" button, the complete article gets expanded.
Keep in mind: jQuery selects your elements very much like CSS would do. This makes it extremely easy to
come up with a query for certain elements, but you need to structure your HTML in a good way, like
you would do for formatting reasons.
So I suggest you should use this basic markup for each of your articles (heads up, HTML5 at work!):
<article class="article">
<section class="teaser">
Hey, I am a incredible teaser text! I just introduce you to the article.
</section>
<section class="full">
I am the articles body text. You should not see me initially.
</section>
</article>
You can replace the article and section elements with div elements if you like to.
And here is the CSS for this markup:
/* In case you want to display multiple articles underneath, separate them a bit */
.article{
margin-bottom: 50px;
}
/* we want the teaser to stand out a bit, so we format it bold */
.teaser{
font-weight: bold;
}
/* The article body should be a bit separated from the teaser */
.full{
padding-top: 10px;
}
/* This class is used to hide elements */
.hidden{
display: none;
}
The way we created the markup and CSS allows us to put multiple articles underneath.
Okay, you may have noticed: I completely omitted any "read more" or "collapse" buttons. This is done by intention.
If somebody visits the blog site with javascript disabled (maybe a search engine, or a old mobile which doesn't support JS or whatever),
the logic would be broken. Also, many text-snippets like "read more" and "collapse" are not relevant if they don't actually do anything and are not part of the article.
Initially, no article body is hidden, since we didn't apply the hidden css class anywhere. If we would
have embedded it in the HTML and someone really has no JavaScript, he would be unable to read anything.
Adding some jQuery magic
At the bottom of the page, we are embedding the jQuery library from the google CDN.
<script src="//ajax.googleapis.com/ajax/libs/jquery/1.9.1/jquery.min.js"></script>
This is a best practice and will normally speed up your page loading time. Since MANY websites are embedding
jQuery through this URL, chances are high that its already in the visitors browser cache and doesn't have
to be downloaded another time.
Notice that the http: at the beginning of the URL is omitted. This causes browsers to use the pages current protocol,
may it be http or https. If you would try and embed the jQuery lib via http protocol on a https website, some browsers will refuse to download the file from a unsecure connection.
After you included jQuery into the page, we are going to add our logic into a script tag. Normally we would
save the logic into a separate file (again caching and what not all), but this time a script block will do fine.
Finally some JavaScript
At first, we want to hide all elements with the css-class full, since only teasers should remain displayed. This is very easy with jQuery:
$('.full').hide();
The beginning of the script $('.full') tells jQuery: I need all elements with the CSS-class full. Then we call a function on that result, namingly hide() which purpose should be clear.
Okay, in the next step, we want to add some "read more" buttons, next to every teaser. Thats an easy task, too:
$('.teaser').after('<button class="more">Read more</button>');
We now select every element with the css-class teaser and append some HTML code after() each element - a button with the css-class more.
In the next step, we tell jQuery to observe clicks on every one of this freshly created buttons. When a user has clicked, we want to expand the next element with the css-class full after the clicked button.
$('.more').on('click', function(){
//"this" is a reference to the button element!
$(this).slideUp().next('.full').slideDown();
});
Phew, what did we do here?
First, we told jQuery that we wanted to manipulate this, which is a reference to the clicked button. Then we told
jQuery to hide that button (since its not needed anymore) slowly with slideUp().
We immediately continued telling jQuery what to do: Now take the next() element (with the css-class full) and make it visible by sliding it down with slideDown().
Thats the power of jQuerys chaining!
Hiding again
But wait, you wanted to be able to collapse the articles again! So we need a "collapse" button, too and
some more JavaScript:
$('.full').append('<button class="collapse">Collapse text</button>');
Note: we didn't use the after() function to add this button, but the append() function to place the button
INSIDE every element with the css-class full, rather than next to it. This is because we want the
collapse buttons to be hidden with the full texts, too.
Now we need to have some action when the user clicks one of those buttons, too:
$('.collapse').on('click', function(){
$(this).parent().slideUp().prev('.more').slideDown();
});
Now, this was easy: We start with the button element, move the focus to its parent() (which is the element that contains the full text) and tell jQuery to hide that element by sliding it up with slideUp().
Then we move the focus from the full-text container to its previous element with the css-class more, which is its expanding button that has been hidden when expanding the text. We slowly show that button again by calling slideDown().
Thats it :)
I've uploaded my example on jsBin.

jQuery sortable with overflow: hidden; between two lists

I have two lists in which using jQuery sortable i can move the items between them.
$( '#productsList, #orderList' )
.sortable({connectWith: '.containerDiv'})
.disableSelection();
However I run into a problem when i want to use custom scroll bar and set overflow:hidden; on the two lists. I want them to be with max-height:400px.
If i set overflow hidden i cant see the items after i drag them outside of one div, If i dont set hidden the list will have default scroll bar.
Can anyone suggest a solution.
thanks
If you remove the style position:relative from your lists is seems to work as you want it to.
http://jsfiddle.net/cCDcQ/2/
Edit:
I would have thought that using the appendTo option would fix this issue and I was right. After a bit more fiddling, I got it to work. This way, you can keep the position:relative if you need it.
http://jsfiddle.net/cCDcQ/4/
I know this ticket is somewhat dated, but I had ran into the same issue while using my custom scrollbar solution and attempting to drag between Sortable's with overflow hidden. After adding code to fix-up Sortable to work with my Scrollpane, I noticed what appeared to be an omission for the appendTo functionality.
The code for appendTo only appends the helper to the target if it doesn't exist in the DOM. That's why the clone options works for some (but not for all and I won't go into that here). The key to fixing it was to add this code toward the end of the _mouseStart function of the widget:
if (!this.helper.parent().is(this.appendTo)) {
this.helper.detach().appendTo(this.appendTo);
// update position
this.offset.parent = this._getParentOffset();
}
Note that this.appendTo is set-up earlier in the function:
this.appendTo = $( o.appendTo !== "parent" ?
o.appendTo :
this.currentItem.parent() );
With this fix in place, I specified an appendTo that targeted the div that contained both Sortable's and ceased to have the overflow issue.
The complete fix-up, including other flow fixes, is available in the scrollsortable JS file for the jQuery-UI-ScrollPane available here: https://github.com/borgboyone/jQuery-UI-ScrollPane.
Cheers!

Categories