Show Div When Dates Match Using .Each - javascript

I have a list of job postings and would like to display a div that say 'New' when the date is equal to today's date.
To create this I have created a javascript code that will execute on a loop for each set of outer div's, but I am having trouble correctly running the .each function.
Here is the link to a JSFiddle: http://jsfiddle.net/jeremyccrane/2p9f7/
Here is the HTML Code:
<div class="outer">
<div class="job-date">07-Feb-13</div>
<div class="new" style="display:none;">NEW</div>
<div class="value"></div>
</div>
<div class="outer">
<div class="job-date">12-Feb-13</div>
<div class="new" style="display:none;">NEW</div>
<div class="value"></div>
</div>
Here is the Javascript code:
$( ".outer" ).each(function(i) {
var jd = $(".job-date").text();
j = jd.substr(0,2);
var today = new Date();
var dd = ( '0' + (today.getDate()) ).slice( -2 )
$('.value').html(dd + "/" + j);
if(dd === j) {
$('.new').show();
} else {
$('.new').show();
}
return false;
});

Not too sure what you think the problem is but I could see a couple of issues. Mainly, when you do for example:
$('.new').show();
you're calling show() on ALL matching elements of class new, not just the one 'under' the outer you're in. Try this:
$('.new', this).show();
You were setting the new to show whichever way your date comparison went too. I had a stab at updating your fiddle below:
$( ".outer" ).each(function(i) {
var jd = $(".job-date", this).text();
j = jd.substr(0,2);
var today = new Date();
var dd = ( '0' + (today.getDate()) ).slice( -2 )
$('.value', this).html(dd + "/" + j);
if(dd === j) {
$('.new', this).show();
} else {
// $('.new', this).show();
// do something different here
}
});

This code appears to do what you want:
$(".outer").each(function(i) {
var jd = $(this).find(".job-date").text();
var j = jd.substr(0,2);
var today = new Date();
var dd = ('0' + (today.getDate())).slice(-2);
$(this).find('.value').html(dd + "/" + j);
if(dd == j) {
$(this).find('.new').show();
} else {
$(this).find('.new').hide();
}
return false;
});
http://jsfiddle.net/Dk4dQ/
Your main problem was that you were missing all of the $(this).find() calls. You are iterating through containers. Using $(this).find() will get you the controls within those containers. The plain $() calls will find all matching elements in the document, which is not what you want.
The this in this case refers to the container. Wrapping it in the jQuery function lets us use the jQuery find method to get it's children.
Also, as the others mentioned, you were show()ing the div regardless of success or failure, which again is not what you want.

You have 2 problems here. First of all, you're triggering show() regardless of whether the dates match or not:
if(dd === j) {
$('.new').show();
} else {
$('.new').show(); // <-- shouldn't show in this case
}
The second problem is that you're showing everything with the class "new", when you only want to show particular divs. You'll need to give unique IDs to each "new" div, and then fix your code to only show the divs with that particular ID.

You don't need a complicated iterator function. All you need is:
$(".outer .job-date" ).filter(function() {
return (Date.parse($(this).text()) / 86400000 | 0) == (new Date() / 86400000 | 0);
}).next().show();
filter seems like a better choice for what you're doing than each. First we just want the set of elements that have a date equal to today.
To do that we can take the dates and get rid of the time part. Dates are represented in terms of number of milliseconds since the epoch. By dividing by the number of milliseconds in a day (86400000, or 60*60*24*1000) and then truncating any decimal part (javascript idiom: |0) we are comparing the number of full days since the epoch.
Now with a set of elements containing today's date, next() advances every matched element to the next sibling (the hidden div with class new), and show() shows it.

Related

Collection Boolean isn't being set to false - Meteor

So in short, the app that i'm developing is a bus timetable app using Meteor, as a practice project.
inside my body.js, I have an interval that runs every second, to fetch the current time and compare to items in a collection.
To show relevant times, I have added an isActive boolean, whenever the current time = sartTime of the collection, it sets it to true, and that is working fine.
But when I do the same thing for endTime and try to set it to false, so I can hide that timeslot, it just doesn't work. Even consoles don't show up. What am I missing? I have recently just started doing meteor, so excuse the redundancies.
Worth noting that the times that I'm comparing to are times imported from an CSV file, so they have to be in the 00:00 AM/PM format.
Thank you guys so much for your time.
Body.js code:
Template.Body.onCreated(function appBodyOnCreated() {
Meteor.setInterval(() => {
var h = (new Date()).getHours();
const m = ((new Date()).getMinutes() <10?'0':'') + ((new Date()).getMinutes());
var ampm = h >= 12 ? ' PM' : ' AM';
ampmReac.set(ampm);
if (h > 12) {
h -= 12;
} else if (h === 0) {
h = 12;
}
const timeAsAString = `${h}${m}`;
const timeAsAStringFormat = `${h}:${m}`;
whatTimeIsItString.set(timeAsAStringFormat + ampm); // convert to a string
const timeAsANumber = parseInt(timeAsAString); // convert to a number
whatTimeIsIt.set(timeAsANumber); // update our reactive variable
if (Timetables.findOne({TimeStart: whatTimeIsItString.get()}).TimeStart == whatTimeIsItString.get())
{
var nowTimetable = Timetables.findOne({TimeStart: whatTimeIsItString.get() });
Timetables.update({_id : nowTimetable._id },{$set:{isActive : true}});
console.log('I am inside the START statement');
}
else if (Timetables.findOne({TimeEnd: whatTimeIsItString.get()}).TimeEnd == whatTimeIsItString.get())
{
var nowTimetable = Timetables.findOne({TimeEnd: whatTimeIsItString.get() });
Timetables.update({_id : nowTimetable._id },{$set:{isActive : false}});
console.log('I am inside the END statement');
}
}, 1000); //reactivate this function every second
});
})
Very probably it is just that your if / else blocks does what you ask it:
It tries to find a document in Timetables, with specified TimeStart. If so, it makes this document as "active".
If no document is previously found, i.e. there is no timeslot which TimeStart is equal to current time, then it tries to find a document with specified TimeEnd.
But your else if block is executed only if the previous if block does not find anything.
Therefore if you have a next timeslot which starts when your current timeslot ends, your if block gets executed for that next timeslot, but the else if block is never executed to de-activate your current timeslot.
An easy solution would be to transform your else if block in an independent if block, so that it is tested whether the previous one (i.e. TimeStart) finds something or not.
Ok so I got it to work eventually. My problem was that it was never going to the second IF statement.
What I have done is set up a whole new Meteor.interval(() >) function, and placed that second IF in there, as is.
I think the problem was that it was it checks the first IF statement and gets stuck there, no matter what the outcome of the parameters is.

search command ignores special characters

What I'm trying to do: I'm trying to parse Google Calendar events and create a Google Document if the following string is found in the title or description of the event "#notes".
What actually happens: A document is created as soon as the string "notes" is found. It doesn't require an hashtag. The same thing happens with #.
function createMeetingNotesNextTimePeriod() {
//<-------------------------------------VARIABLES
// get today's date
var today = new Date();
// number of hours from now to check for meetings
var hours = 2
// create variable for now
var now = new Date();
// create variable for number of hours from now in milliseconds
var period_from_now = new Date(now.getTime() + (hours * 60 * 60 * 1000));
// retrieve all calendar events for time period with #notes string
var tagword = ('#notes');
var events = CalendarApp.getDefaultCalendar().getEvents(now, period_from_now, {search: tagword}) ;
Logger.log('Number of events: ' + events.length);
} // functionCreateMeetingNotesNextTimePeriod
The log commands tells me that it found one event but the event in question just has 'notes' in it's title, no hashtag. Thanks for all help.
EDIT
I think I found the problem but I'm still stumped about solving it. It seems that the search option from .getEvents ignores most special characters and returns a positive whenever you search for a special character. For example, I replaced my original search for tagword with this:
var events = CalendarApp.getDefaultCalendar().getEvents(now, period_from_now, {search: 'notes' + '#' +'#' + '±' }) ;
It gives me a positive match on my search while I don't have either a '#', a '#' nor a '±' in my event.
That does seem odd that it ignores special characters however here is a work around that should work:
var tagword = '#notes';
var events = CalendarApp.getDefaultCalendar().getEvents(now, period_from_now, {search : tagword})
if (events.length > 0) {
for (i in events) {
if ( events[i].getTitle().indexOf(tagword) >-1 || events[i].getDescription().indexOf(tagword) >-1) {
//do something
}
}
}
Basically it will find all events that have notes (ignoring the special characters) then loop through the event titles and descriptions to check if the tag word is present (including special characters).
You will need to use some Regex to do what you are trying to do in Javascript.
I am not exactly sure how to do it for your particular case but here are two references that can help you out.
JS Extract HashTags From Text
JS Regex Searching for HashTags
I hope this helps !
EDIT
try
var tagword = ('/#/g' + notes);
OR
var tagword = ('/#notes/g');
I tried it out and it seems to have worked.

How to write arguments in function?

I have been using functions but I am not able to tackle this.
What I have done is created a function, then made this to use the values provided by the document class or ids and do the work. Once work is done then just give the data back! It worked!
Now I want to make this function happen for two divs, the first function works good. The issue is with the second one. The function is correct, their is some other bug while writing the result.
Here is my code:
function time_untilCom(id) {
var Time2 = Date.parse(document.getElementById("time_" + 2).value);
var curTime2 = new Date();
var timeToWrite2 = "";
var seconds2 = Math.floor((curTime2 - Time2) / (1000));
if (seconds2 > 0 && seconds2 < 60) {// seconds..
timeToWrite2 = seconds2 + " seconds ago";
$('#update_' + 2).html(seconds2);
$('#jstime_' + 2).html(timeToWrite2 + " <b>Time that was captured!</b>");
}
}
If I use it as it is, it works! The issue comes when I try to replace these
("time_" + 2), ("#update_" + 2), ("#jstime" + 2) with ("time_" + id), ("#update_" + id), ("#jstime_" + id).
What i want to happen is that the function would be provided with a common ID that is applied throughout the div and use that ID, to get the value of time, convert it to seconds, do other stuff and then provide me with the result in the corresponding element with the id that was in the argument.
function works great, it do provide me with the result. But the issue is with the id its not being sent I guess. Or if is being sent then not being applied. What might be the issue here? And don't mind the seconds i have that covered too.
I am really very sorry for short code:
Pardon me, I was about to write the code for the function too. But electricity ran out!
Here is the code: onload="time_untilCom('2'), this is the way I am executing this.
And once in the main code, it will be executed like this: onload="time_untilCom(#row.Id) because I am using ASP.NET Web Pages I will be using the server side code to write the ID from Database. And will then user the ID throughtout the div to update the time!
From what I understand, you probably want to replace the second line
var Time2 = Date.parse(document.getElementById("time_" + 2).value);
with
var Time2 = Date.parse(document.getElementById(id).value);
And at the end you can also use
$('#'+id).html(timeToWrite2 + " <b>Time that was captured!</b>");
You are passing "id" as an argument, but you never use it inside the function. My question is: In your example you are using 2 as appendix to id attributes. Is it the 2 (or other numbers respectively) that you want to have as the id parameter of the function?
Then you could just replace each + 2 in your code by + id
function time_untilCom(id) {
var Time2 = Date.parse(document.getElementById("time_" + id).value);
var curTime2 = new Date();
var timeToWrite2 = "";
var seconds2 = Math.floor((curTime2 - Time2) / (1000));
if (seconds2 > 0 && seconds2 < 60) {// seconds..
timeToWrite2 = seconds2 + " seconds ago";
$('#update_' + id).html(seconds2);
$('#jstime_' + id).html(timeToWrite2 + " <b>Time that was captured!</b>");
}
}
EDIT: Please tell us where and how exactly do you call time_untilCom? Did you pass the id there?

How to check if all divs are hidden with variable class in jQuery

I'm very new to javascript/jQuery so apologies if this is a very basic question.
I have a variable which uses Math.random to select one of 9 potential classes from an array, the classes are the same except with a different number 1-9 at the end. I want to use javascript to check if all elements with this class are hidden. I can get it to check if all divs are hidden when I actually specify the class, but am not sure how to do this with a variable or expression. Below is what I'm using at the moment, which only works when the div is specified.
if ($('div.item9:visible').length == 0)
I assumed something like this would do what I want, but it doesn't seem to work.
if ($(variable + ':visible').length == 0)
EDIT: if ($(variable + ':visible').length == 0) this does work, I had another div on the page with this class which I didn't realise and therefore there was always an unhidden element, thanks for the help everyone.
you can use the same variable in your class name which you have used to select a number from 1-9 for example
var x = Math.floor(Math.random() * (10 - 1) + 1);
this will generate a random integer between 1-10 then you can just add the x in the class name
like this
if ($('div.item'+x+':visible').length == 0)
Cheers !
try this:
var elements = [1,2,3,4,5,6,7,8,9];
function getRandomClassNumber(){
//will give you random index
var index = Math.floor((Math.random()*elements.length));
return (elements[index]);
}
$("#btnRandom").on("click",function(){
var classNumber = getRandomClassNumber();
if($(".item"+classNumber).is(":visible")){
alert("item" + classNumber + " is visible");
}else{
alert("item" + classNumber + " not visible");
}
});
working fiddle here: http://jsfiddle.net/6neFA/

How to achieve String Manipulation in JavaScript

The problem statement is like this: I have a contract. On renewal on every month the contract name should append with renewal identifier. For example at beginning the name is myContract then on first renewal name should be myContract-R1, next renewal name should be myContract-R2 and so on.. On each renewal, the name should automatically change. So in Jquery how can I do this?
This is a JavaScript question, not a jQuery question. jQuery adds little to JavaScript's built-in string manipulation.
It sounds like you want to take a string in the form "myContract" or "myContract-Rx" and have a function that appends "-R1" (if there's no "-Rx" already) or increments the number that's there.
There's no shortcut for that, you have to do it. Here's a sketch that works, I expect it could be optimized:
function incrementContract(name) {
var match = /^(.*)-R([0-9]+)$/.exec(name);
if (match) {
// Increment previous revision number
name = match[1] + "-R" + (parseInt(match[2], 10) + 1);
}
else {
// No previous revision number
name += "-R1";
}
return name;
}
Live copy
You can use a regular expression for this:
s = s.replace(/(-R\d+)?$/, function(m) {
return '-R' + (m.length === 0 ? 1 : parseInt(m.substr(2), 10) + 1);
});
The pattern (-R\d+)?$ will match the revision number (-R\d+) if there is one (?), and the end of the string ($).
The replacement will return -R1 if there was no revision number before, otherwise it will parse the revision number and increment it.
how you get renewal number? Calculating from date, or getting from database?
var renewal = 1,
name = 'myContract',
newname = name+'R'+renewal;
or maybe like
$(function(){
function renew(contract){
var num_re = /\d+/,
num = contract.match(num_re);
if (num==null) {
return contract+'-R1';
} else {
return contract.replace(num_re,++num[0]);
}
}
var str = 'myContract';
new_contract = renew(str); // myContract-1
new_contract = renew(new_contract); // myContract-2
new_contract = renew(new_contract); // myContract-3
});
Here jQuery can't help you. It's pure JavaScript working with strings
P.S. I have here simple reg exp, that's not concrete for your example (but it works). Better use reg-exp from example of T.J. Crowder

Categories

Resources