...

View Full Version : jQuery - Rounding Numbers



mickormick
11-11-2010, 08:01 PM
Wizards - I have a challenge!

I am writing a timecard app. The stipulatioin is all Hours fields can only be whole hours or half hour increments. For example, 1.0 is good, 1.5 is good, 1.2 is bad, 1.9 is bad.

I would like to have the field automatically change a value of 1.9 to a value of 2.0 (perhaps onKeyUp).

I would like to have the field automatically change a value of 3.2 to a value of 3.0.

In a nutshell - only allow whole and half hour values. Otherwise round up OR round down.

Thanks for any help you can provide. I am successfully using the Pengoworks plugin for calculations - absolutely priceless. If you think modifications can be made to it, plz let me know.

Philip M
11-11-2010, 08:58 PM
Here you are:-


Enter hours <input type = "text" id = "hours" size = "5" maxlength = "5" onkeyup ="chk()">

<script type = "text/javascript">
function chk() {
var val = document.getElementById("hours").value;
val = val.replace(/[^0-9\.]/gi, ""); // strip all but digits and decimal point
var valsplit = val.split(".");
valsplit[0] = parseInt(valsplit[0]);

if (valsplit[1]) {
valsplit[1] = valsplit[1].replace(/(\d)(.)/, '$1'); // only one digit after decimal point

if (valsplit[1] >5) {
valsplit[1] = 0;
valsplit[0] = valsplit[0] +1;
}

if (valsplit[1] <5) {
valsplit[1] = 0;
}

}

var newval = valsplit.join(".");
if (isNaN(newval)) {newval = ""}
document.getElementById("hours").value = newval;
}

</script>
Quizmaster: Name something a bald man does not have to buy.
Contestant: A razor.

Old Pedant
11-11-2010, 09:03 PM
You can also do it mathematically.


<input name="hours"
onchange="this.value = 0.5 * Math.round(parseFloat(this.value)*2);"/>

This will show "NaN" if the user doesn't enter a valid number, so it doesn't have the protections of Philip's code.

Hmmm...I guess we could add to that:


<input name="hours"
onchange="this.value = 0.5 * Math.round(parseFloat(this.value)*2);
if (this.value=='NaN') this.value=0;" />

Yeah, that works.

Philip M
11-11-2010, 09:11 PM
<input name="hours"
onchange="this.value = 0.5 * Math.round(parseFloat(this.value)*2);
if (this.value=='NaN') this.value=0;" />

Yeah, that works.

Oh no it doesn't! :p:p Your script merely rounds to the nearest .5.

I enter 12.3 and get 12.5, not 12.0 which is what the OP asked for. Likewise I enter 12.7 and get 12.5, not 13.0.

In any case the OP wanted onkeyup, not onchange.

With onkeyup I enter 12.9 and get 129. :eek:

Old Pedant
11-11-2010, 09:12 PM
Hmmm...that converts "3.2" to "3". No trailing ".0".

Okay...if that's important:


<input name="hours"
onchange="var n = 0.5 * Math.round(parseFloat(this.value)*2);
this.value= isNaN(n) ? 0 : n.toFixed(1);" />

Old Pedant
11-11-2010, 09:16 PM
Ahhh...granted.

But (a) he said "(perhaps onKeyUp)"

(b) onkeyup is a bad solution in my never overly humble opinion. What about the person who uses MOUSE ONLY to copy/paste a value into a form field? You will never get an onkeyup event. I'm not fanatic about it, but I very, very seldom use onkeyup in stuff I do.

Old Pedant
11-11-2010, 09:22 PM
I have to admit I like how your code gets around several possible pitfalls. Very clean.

Philip M
11-11-2010, 09:24 PM
Hmmm...that converts "3.2" to "3". No trailing ".0".

Okay...if that's important:


<input name="hours"
onchange="var n = 0.5 * Math.round(parseFloat(this.value)*2);
this.value= isNaN(n) ? 0 : n.toFixed(1);" />


Still wrong.
Enter 2.4 and get 2.5. Enter 2.6 and get 2.5. Suggest you read carefully what the OP wants.

Philip M
11-11-2010, 09:32 PM
Ahhh...granted.

But (a) he said "(perhaps onKeyUp)"

(b) onkeyup is a bad solution in my never overly humble opinion. What about the person who uses MOUSE ONLY to copy/paste a value into a form field? You will never get an onkeyup event. I'm not fanatic about it, but I very, very seldom use onkeyup in stuff I do.

Well, simply make it read

Enter hours <input type = "text" id = "hours" size = "5" maxlength = "5" onkeyup ="chk()" onchange = "chk()" >

Old Pedant
11-11-2010, 09:51 PM
Yep. And as I said, yours is pretty nice in the way it handles idiotic entries. I'd still not worry about onkeyup on my own pages, but for anybody who wants to use it, your code is great.

glenngv
11-11-2010, 10:14 PM
I'd suggest to pass the field reference to make the function reusable with other Hour fields that the original poster has.


<input type="text" id="hours" size="5" maxlength="5" onkeyup="chk(this);" onchange="chk(this);" />

<script type = "text/javascript">
function chk(objFld) {
var val = objFld.value;

....

var newval = valsplit.join(".");
objFld.value = newval;
}
</script>

mickormick
11-11-2010, 10:49 PM
Now I have to humble myself, reveal my true lack of understanding, and ask for one more favor...

Why can't I get this function to work?

<html>
<head>
<script type="text/javascript" language="javascript">
function roundme(myhours){
var fhours = 0.5 * Math.round(parseFloat(myhours)*2);
fhours.toFixed(1);
}
</script>
</head>
<body>
<form name="form1" id="form1">
<input name="hours1" onkeyup="roundme(this.value)" value="0.0" size="2" /><br />
<input name="hours2" onkeyup="roundme(this.value)" value="0.0" size="2" /><br />
<input name="hours3" onkeyup="roundme(this.value)" value="0.0" size="2" /><br />
</form>
</body>
</html>

Old Pedant
11-11-2010, 11:13 PM
Ummm....you really should NOT be using my code if you are going to use onkeyup

As Philip correctly pointed out, it can't handle decimal points correctly.

But anyway, you are missing the *ASSIGNMENT* of the value back into the form field.


function roundme(myhours){
var fhours = 0.5 * Math.round(parseFloat(myhours)*2);
myhours.value = fhours.toFixed(1);
}

mickormick
11-12-2010, 12:22 AM
You managed to come up with a solution within an hour! I have been struggling for days.

Thanks for the examples (solution).

-Dave

Old Pedant
11-12-2010, 02:09 AM
You managed to come up with a solution within an hour!

I dunno about Philip, but my solution took about 2 minutes. <grin/>

(Of course, mine was the much easier one.)

Philip M
11-12-2010, 09:11 AM
Looks like I wasted my time as the OP seemed to want something other than simple round up/down to nearest whole number or half. I interpreted it to mean that he wanted 3.4 to change to 3.0, not 3.5.

He said "only allow whole and half hour values. Otherwise round up OR round down." I understood that to mean if the value is not .5 round up OR round down to the nearest whole number. :p



EZ Archive Ads Plugin for vBulletin Copyright 2006 Computer Help Forum