I am using a checkbox and a checkbox list in one of my web pages.
The UI is like
Color - Header Checkbox
Checkboxlist items are
Red
Green
Blue
Yellow
Complete selection - clicking on the header checkbox selects/ deselects the entire checkbox list.
Partial selection of the checkbox list shows the header checkbox with a different background color to indicate partial selection.
I do a check for number of selected items in each of the checkbox list selection changes. In a client server environment, there is a time delay and if we make two continuous selections in the checkbox list, an update of the header control is done for the first selection and by the time UI is refreshed, the second selection is gone.
I also implemented the above one using JavaScript but then also the behavior is same.
What could be an alternative for this?
Your question is not particularly clear, but it sounds like you want some sort of three state check box? It also sounds like the postback is occurring and wiping out your second selection?
If so, there are some control options out there. Here's a link to one that may help. http://www.chadscharf.com/index.php/2008/10/3-state-checkbox-using-microsoft-ajax/
You really need to post some code and link to the screen shots you mention.
There are two scenarios you are trying to satisfy and the simpliest approach is utilising Javascript. Certainly one direction is using Jquery to simplify the wiring of DOM elements together.
Following is an example that kinda covers the two scenarios. One the top level control checks / unchecks all the elements. Second, the individuals change the background of the top level element. This is not drop and run code, it merely demonstrates the technique in isolation. Changes and tweaks I've leave to you + if you're unfamiliar with Jquery: simply search each function on Jquery site. Enjoy!
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
<html>
<head>
<script src="http://ajax.googleapis.com/ajax/libs/jquery/1.6.1/jquery.min.js" type="text/javascript"></script>
<script type="text/javascript">
$(document).ready(function(){
// Wire up the 'select-all' to the child elements
$('#topLevel').bind('change' , function(){
// Record this object
var base = this;
// Change the child elements
$('#checkboxContainer input').each( function(){
$(this).attr('checked' , $(base).is(':checked'))
})
});
// Make the individual checkbox selects alter the
// background of the top-level wrapper
$('#checkboxContainer input').bind('change' , function(){
// Get a handle to the top item
var topLevel = $('#topLevelWrapper');
// Have we selected the item?
if($(this).is(':checked')){
// Remove the previous class assignments
topLevel.attr('class' , '');
// Assign the current css class from the parent
topLevel.addClass( $(this).parent().attr('class') );
}
});
})
</script>
<style type="text/css">
.Red{
background-color:#F00;
}
.Green{
background-color:#0F0;
}
.Blue{
background-color:#00F;
}
</style>
</head>
<body>
<div id="topLevelWrapper">
<label for="topLevel">Top level selection</label>
<input type="checkbox" id="topLevel" />
</div>
<div id="checkboxContainer">
<ul>
<li class="Red">
<label for="topLevel">Red</label>
<input type="checkbox" />
</li>
<li class="Blue">
<label for="topLevel">Blue</label>
<input type="checkbox" />
</li>
<li class="Green">
<label for="topLevel">Green</label>
<input type="checkbox" />
</li>
</ul>
</div>
</body>
Related
I have a page containing a push button and two radio buttons placed near the bottom of the page. My goal is to create a function triggered by the push button that scrolls the page up or down, depending on whether or not the two radio buttons are active. Once users select the two radio buttons, the push button will then scroll to the top of the page. The snippet provided has the code that I have so far. Once the two radio buttons are activated, I want the 'scroll down' code to no longer work and just have the button move the user to the top of the page. It works as intended in this example and in Firefox, but chrome and edge have trouble interpreting it. In these browsers, the page will scroll to the bottom when it is at the top, which makes sense considering that the 'scroll-down' code is placed at the beginning of the function. How can the code be optimized/separated so that it works as intended without the two window.scrollTo's interacting with each other?
function Push() {
window.scrollTo(0,document.body.scrollHeight);
if(mode1.checked) {
if(mode2.checked) {
window.scrollTo({top: 0});
}}}
<style>
html {
height: 500px;
}
</style>
<body>
</br></br></br></br></br></br></br></br></br></br></br>
<div align="center">
<button id="button01" onclick="Push()">Push</button>
</div>
</br></br></br></br></br></br></br></br></br></br></br></br>
<div align="center">
<form id="mode">
<label><input type="radio" id="mode1"/></label>
<label><input type="radio" id="mode2"/></label>
</form>
</div>
</body>
The way you have it written; when both radios are checked and the Push() function is called, the page will scroll to the bottom first and then to the top. It happens so fast you don't notice it (at least I don't), but the code says that is happening.
EDIT: I did prove that this is the case by testing in codepen by setting a breakpoint here: window.scrollTo({top: 0});. When it breaks here it has scrolled to the bottom and then when I step into the next function call it scrolls to the top.
I would change the Push() function like this:
function Push() {
if(mode1.checked && mode2.checked) {
window.scrollTo({top: 0});
} else {
window.scrollTo(0,document.body.scrollHeight);
}
}
Doing so results in only one scroll action firing (up or down).
It also appears that IE does not support using scrollTo with options as you do here: window.scrollTo({top: 0});. May be best to use window.scrollTo(0,0). I used that in the snippet below.
This may be your Chrome and Edge issue as well depending on what version of each you are testing on. See this: https://caniuse.com/#feat=element-scroll-methods
One last notable observation: You currently have no way to "uncheck" the radio buttons due to the designed functionality of radio buttons. I assume you know that and is not an issue, but thought I would mention it. Using checkboxes or custom checkboxes would allow you to accomplish this if needed. There are other ways to accomplish this as well.
function Push() {
if(mode1.checked && mode2.checked) {
window.scrollTo(0,0);
} else {
window.scrollTo(0,document.body.scrollHeight);
}
}
html {
height: 500px;
}
<html>
<body>
</br></br></br></br></br></br></br></br></br></br></br>
<div align="center">
<button id="button01" onclick="Push()">Push</button>
</div>
</br></br></br></br></br></br></br></br></br></br></br></br>
<div align="center">
<form id="mode">
<label><input type="radio" id="mode1"/></label>
<label><input type="radio" id="mode2"/></label>
</form>
</div>
</body>
</html>
I find myself needing to change style of all elements that have an attribute in common (let's say a class name) when one of these elements is hovered. This is super easy to do with jQuery, like this:
$(function() {
$('.bookId4').hover( function(){
$(this).css('background-color', '#F00');
},
function(){
$(this).css('background-color', '#000');
});
});
Though I don't know how to achieve this with Angular. In this example, the elements that have the class .bookId4 are generated with Angular AJAX call, so I'd like to use Angular to create the hover effect as well. Thank you!
EDIT
To explain further, I will have many divs being generated with an AJAX call, and the div's that are in the same group will have the same class. This is the HTML code:
<div class="bookId{{ privateTour.booking.id }}"> <!-- Wrapper for hover effect -->
When one of the divs is hovered I want ALL of the divs (not only the div that is being hovered) with the same class (or some other value that they may have in common) to have a hover effect. My preferred way would be for Angular to search the whole page for all divs with a certain class name and apply a style to that class (to not have to for example generate tons of CSS for all the classes that were generated, which I'm not even sure it would work).
You can do that by using ng-mouseenter and ng-mouseleave directives, Here is the simple code, you can build on top of it to meet your requirements
<!doctype html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Example - example-example73-production</title>
<script src="//ajax.googleapis.com/ajax/libs/angularjs/1.5.6/angular.min.js"></script>
</head>
<body ng-app="">
<h1 ng-style="myStyle" ng-mouseenter="myStyle={'background-color':'blue'}"" ng-mouseleave="myStyle={'background-color':'none'}"">Hello World</h1>
</body>
</html>
You can apply simple css solution for hover, like
.bookId4:hover {
background-color: '#F00';
}
No need for angular or jQuery :-)
Yes I agree with using ng-mouseenter and ng-mouseleave.
I did a example hope can help you
https://embed.plnkr.co/Cxfv0I9IEfBhZYj8A3zS/
use ng-class, create one scope variable which is by default false.
when mouseEnter OR mouseLeave event occurs make it TRUE/False accordingly.
<style>
.bookId4{color: red;}
</style>
<span ng-mouseenter="ctrl.hovered()" ng-mouseout="ctrl.nothovered()" ng-class="{ 'bookId4' : ctrl.ishovered==true }">soemthing 1</span>
<span ng-mouseenter="ctrl.hovered()" ng-mouseout="ctrl.nothovered()" ng-class="{ 'bookId4' : ctrl.ishovered==true }">soemthing 2</span>
<span ng-mouseenter="ctrl.hovered()" ng-mouseout="ctrl.nothovered()" ng-class="{ 'bookId4' : ctrl.ishovered==true }">soemthing 3</span>
_this.ishovered =false;
_this.hovered = function(){
_this.ishovered =true;
}
_this.nothovered = function(){
_this.ishovered =false;
}
In the end I found using an ng-class condition to be the best solution, and a variable decides what group should be highlighted. This line that I initially tried using did not work correctly:
<div ng-class="hovering == privateTour.booking.id ? 'hl' : ''" ng-mouseenter="hovering = privateTour.booking.id" ng-mouseleave="hovering = 0"> <!-- Wrapper for hover effect -->
For some reason, only the hovered div was highlighted, so I had to send the signal to a variable using a function instead for it to have a global effect. I ended up using this code for the div wrappers:
<div ng-class="hovering == privateTour.booking.id ? 'hl' : ''" ng-mouseenter="setHover(privateTour.booking.id)" ng-mouseleave="setHover(0)"> <!-- Wrapper for hover effect -->
And I wrote this simple function in the scope:
$scope.setHover = function(bookId) {
$scope.hovering = bookId;
};
And here's the style for the highlight class .hl:
.hl {
background-color: red;
}
Thank you for everyone giving the lead of ng-mouseenter and ng-mouseleave!
I'm using jquerymobile. And on a list I have a filter. When a user types something in it filters great. However when I add more items to the list, then the filtering does not refresh.
Any idea how I can refresh the filtering? (re-filter the list?)
Thanks
Trigger a change event on the search input field like this after items are added to list.
$(".ui-input-search .ui-input-text").trigger("change");
A sample:
<html>
<head>
<link rel="stylesheet" href="http://code.jquery.com/mobile/1.0.1/jquery.mobile-1.0.1.min.css" />
<script src="http://code.jquery.com/jquery-1.6.4.min.js"></script>
<script>
$("#btn").live("click",function(){
$("#list").append("<li><a href='#'>100</a></li><li><a href='#'>200</a></li><li><a href='#'>400</a></li><li><a href='#'>500</a></li><li><a href='#'>1000</a></li>");
$("#list").listview("refresh");
$("#page").trigger("create");
$(".ui-input-search .ui-input-text").trigger("change");
});
</script>
<script src="http://code.jquery.com/mobile/1.0.1/jquery.mobile-1.0.1.min.js"></script>
</head>
<body>
<div id="page" data-role="page">
<div data-role="header">
<h1>Test Page</h1>
</div>
<div data-role="content">
<ul id="list" data-role="listview" data-inset="true" data-filter="true">
<li>1</li>
<li>12</li>
<li>41</li>
<li>8</li>
<li>91</li>
<li>65</li>
</ul>
<a data-role="button" id="btn">Add more</a>
</div>
</div><!-- /page -->
</body>
</html>
Demo - http://pastehtml.com/view/bnl7lpe3o.html
Let me know if that helps.
Update for jQuery Mobile 1.4
The filter behavior has been separated out into a filterable widget. You can update your listview content and rerun the filter in one swipe:
$( ".listselector" ).filterable( "refresh" );
A nice benefit of this is that the list items are filtered immediately. You do not experience the visual glitch of seeing the items for a split second before they get filtered, as you would when manually triggering the input control.
See http://api.jquerymobile.com/filterable/#method-refresh
The code above would no longer work, because jQuery Mobile keeps track of the last text entered into the filter, and does not filter if the input has not changed. If you did want to trigger the input control, you would need the following hack to first clear the last entered input:
$(".ui-input-search input").attr('data-lastval', '').trigger("change");
But, please use the filterable function going forward.
I think the problem should be resolved with refresh method, but I am not sure:
$('#mylist').listview('refresh');
After updating the list view, adding the below code will refresh the contents so that it becomes visible :
$("#list").listview("refresh");
Besides using the previously mentioned listview refresh, take note that using jQuery's .show() on a listitem will cause display:block; to be added to the element's CSS. Because it takes precedence over jQM's ui-screen-hidden class, it interferes with the searchfilter's ability to hide items when they don't match.
So if you are adding items to the list by way of .show()/.hide() combos, use .css('display','') instead of .show().
My general order for adding new hidden items:
// 1. Clear display:none and display:block, if necessary, from the listitem
$(yourLI).css('display','');
// 2. Apply jQM formatting, such as corners and other CSS, to the entire listview
$(yourListView).listview('refresh');
// 3. Make sure the searchfilter runs on the new items without user intervention
$(".ui-input-search .ui-input-text").trigger("change");
I want to show all of the items of a dropdown list as it is opened without clicking the down arrow. Do you have any suggestions?
Use a ListBox or show all options in a grid control such as a Repeater or ListView.
Don't know an API in javascript that would do it for you - so i would change the control if it were me.
There's a lot of ways to do this.
The most basic way is as follows:
<html>
<head>
<title>Example</title>
</head>
<body>
<div style="float:left; width:100%; height:30px;">
<select id="AutoDropdown" OnMouseOver="DoDropDown(this);" OnMouseOut="DoDropDown(this);">
<option>Test1</option>
<option>Test2</option>
<option>Test3</option>
<option>Test4</option>
</select>
</div>
<div>
<p>Here is some text that we hope the drop down list will appear over</p>
</div>
<script type="text/javascript">
function DoDropDown(objSel){
if(objSel.size > 1){
objSel.size = 1;
objSel.style.position='static';
}
else{
objSel.size = objSel.options.length;
objSel.style.position='absolute';
objSel.style.height='auto';
}
}
</script>
</body>
</html>
This emulates the effect I think you are trying to achieve but doesn't look great.
You can get a better effect by emulating a drop down list - there are plenty of control alternatives on the web.
There's a Silverlight version here:
http://gallery.expression.microsoft.com/OpenComboBoxDropDown
There's also a variety of controls you could adapt in the AJAX toolkit:
http://www.asp.net/ajaxLibrary/AjaxControlToolkitSampleSite
I'm pretty sure you can make both the DropDown and PopupControls appear on a MouseOver event.
With the PopupControl, tie it to a text box, and when the user selects a value, populate the text box.
Some of the third party controls (like Telerik's) also support this style.
I have a stack of <div> elements that show a name. I'd like to include a + link off to the side of each <div> that, when clicked, expands the <div> and adds more detailed information (from a RoR controller).
After poking around on the net, I found link_to_remote and related RoR stuff, but I can't seem to get the right combination to work together. Can someone point me to a tutorial or show what the controller and view interaction should look like?
Thanks!
You can do this really easily with Javascript in the example below:
<html>
<head>
<title>Text Page</title>
<script language="Javascript">
function toggleDiv(divid) {
if (document.getElementById(divid).style.visibility == 'hidden') {
document.getElementById(divid).style.visibility = 'visible';
}
else {
document.getElementById(divid).style.visibility = 'hidden';
}
}
</script>
</head>
<body>
<span onClick="toggleDiv('div1');" style="cursor:pointer;">+</span>
<div id="div1" style="visibility:hidden;">This is DIV 1</div>
<span onClick="toggleDiv('div2');" style="cursor:pointer;">+</span>
<div id="div2" style="visibility:hidden;">This is DIV 2</div>
</body>
</html>
If you set the initial visibility of the DIV's to hidden, you can use the toggleDiv function shown above to toggle the visibility of any DIV given the ID. You will probably need to tweak the style definitions for the DIVs to display next to the plus signs (put them in adjacent <TD>'s in a table for example), but I figured I'd keep it simple.
Good Luck.