Link to home
Start Free TrialLog in
Avatar of dm404
dm404

asked on

Calling JS Calendar from image rather than text box in form

Hi there,

I've got a form on page. It has two inputs:

1) hidden input that is set through an area variable
2) text box that when clicked calls a javascript calendar. When a date is selected it also submits the form.

What I want is to not use a text box but use an image that when clicked makes the JS calendar appear. Is this possible?

I've included two parts of my script. The form and the JS for the calendar.

Thanks in advance,

Daniel
<form action="clubnights.php" method="post" id="myForm">
 
Change date to: <input onclick="ds_sh(this);" name="clubnightdate" readonly="readonly" style="cursor: text" size="20">
 
<input type="hidden" name="areaid" value="<?php echo $aid; ?>"  />
<input type="hidden" name="submitted" value="TRUE" />
 
 
</form>
 
JS calendar
 
<script type="text/javascript">
// <!-- <![CDATA[
 
// Project: Dynamic Date Selector (DtTvB) - 2006-03-16
// Script featured on JavaScript Kit- http://www.javascriptkit.com
// Code begin...
// Set the initial date.
var ds_i_date = new Date();
ds_c_month = ds_i_date.getMonth() + 1;
ds_c_year = ds_i_date.getFullYear();
 
// Get Element By Id
function ds_getel(id) {
	return document.getElementById(id);
}
 
// Get the left and the top of the element.
function ds_getleft(el) {
	var tmp = el.offsetLeft;
	el = el.offsetParent
	while(el) {
		tmp += el.offsetLeft;
		el = el.offsetParent;
	}
	return tmp;
}
function ds_gettop(el) {
	var tmp = el.offsetTop;
	el = el.offsetParent
	while(el) {
		tmp += el.offsetTop;
		el = el.offsetParent;
	}
	return tmp;
}
 
// Output Element
var ds_oe = ds_getel('ds_calclass');
// Container
var ds_ce = ds_getel('ds_conclass');
 
// Output Buffering
var ds_ob = ''; 
function ds_ob_clean() {
	ds_ob = '';
}
function ds_ob_flush() {
	ds_oe.innerHTML = ds_ob;
	ds_ob_clean();
}
function ds_echo(t) {
	ds_ob += t;
}
 
var ds_element; // Text Element...
 
var ds_monthnames = [
'January', 'February', 'March', 'April', 'May', 'June',
'July', 'August', 'September', 'October', 'November', 'December'
]; // You can translate it for your language.
 
var ds_daynames = [
'Sun', 'Mon', 'Tue', 'Wed', 'Thu', 'Fri', 'Sat'
]; // You can translate it for your language.
 
// Calendar template
function ds_template_main_above(t) {
	return '<table cellpadding="3" cellspacing="1" class="ds_tbl">'
	     + '<tr>'
		 + '<td class="ds_head" style="cursor: pointer" onclick="ds_py();">&lt;&lt;</td>'
		 + '<td class="ds_head" style="cursor: pointer" onclick="ds_pm();">&lt;</td>'
		 + '<td class="ds_head" style="cursor: pointer" onclick="ds_hi();" colspan="3">[Close]</td>'
		 + '<td class="ds_head" style="cursor: pointer" onclick="ds_nm();">&gt;</td>'
		 + '<td class="ds_head" style="cursor: pointer" onclick="ds_ny();">&gt;&gt;</td>'
		 + '</tr>'
	     + '<tr>'
		 + '<td colspan="7" class="ds_head">' + t + '</td>'
		 + '</tr>'
		 + '<tr>';
}
 
function ds_template_day_row(t) {
	return '<td class="ds_subhead">' + t + '</td>';
	// Define width in CSS, XHTML 1.0 Strict doesn't have width property for it.
}
 
function ds_template_new_week() {
	return '</tr><tr>';
}
 
function ds_template_blank_cell(colspan) {
	return '<td colspan="' + colspan + '"></td>'
}
 
function ds_template_day(d, m, y) {
	return '<td class="ds_cell" onclick="ds_onclick(' + d + ',' + m + ',' + y + ')">' + d + '</td>';
	// Define width the day row.
}
 
function ds_template_main_below() {
	return '</tr>'
	     + '</table>';
}
 
// This one draws calendar...
function ds_draw_calendar(m, y) {
	// First clean the output buffer.
	ds_ob_clean();
	// Here we go, do the header
	ds_echo (ds_template_main_above(ds_monthnames[m - 1] + ' ' + y));
	for (i = 0; i < 7; i ++) {
		ds_echo (ds_template_day_row(ds_daynames[i]));
	}
	// Make a date object.
	var ds_dc_date = new Date();
	ds_dc_date.setMonth(m - 1);
	ds_dc_date.setFullYear(y);
	ds_dc_date.setDate(1);
	if (m == 1 || m == 3 || m == 5 || m == 7 || m == 8 || m == 10 || m == 12) {
		days = 31;
	} else if (m == 4 || m == 6 || m == 9 || m == 11) {
		days = 30;
	} else {
		days = (y % 4 == 0) ? 29 : 28;
	}
	var first_day = ds_dc_date.getDay();
	var first_loop = 1;
	// Start the first week
	ds_echo (ds_template_new_week());
	// If sunday is not the first day of the month, make a blank cell...
	if (first_day != 0) {
		ds_echo (ds_template_blank_cell(first_day));
	}
	var j = first_day;
	for (i = 0; i < days; i ++) {
		// Today is sunday, make a new week.
		// If this sunday is the first day of the month,
		// we've made a new row for you already.
		if (j == 0 && !first_loop) {
			// New week!!
			ds_echo (ds_template_new_week());
		}
		// Make a row of that day!
		ds_echo (ds_template_day(i + 1, m, y));
		// This is not first loop anymore...
		first_loop = 0;
		// What is the next day?
		j ++;
		j %= 7;
	}
	// Do the footer
	ds_echo (ds_template_main_below());
	// And let's display..
	ds_ob_flush();
	// Scroll it into view.
	ds_ce.scrollIntoView();
}
 
// A function to show the calendar.
// When user click on the date, it will set the content of t.
function ds_sh(t) {
	// Set the element to set...
	ds_element = t;
	// Make a new date, and set the current month and year.
	var ds_sh_date = new Date();
	ds_c_month = ds_sh_date.getMonth() + 1;
	ds_c_year = ds_sh_date.getFullYear();
	// Draw the calendar
	ds_draw_calendar(ds_c_month, ds_c_year);
	// To change the position properly, we must show it first.
	ds_ce.style.display = '';
		// Move the calendar container!
	the_left = ds_getleft(t);
	the_top = ds_gettop(t) + t.offsetHeight;
	ds_ce.style.left = the_left + 'px';
	ds_ce.style.top = the_top + 'px';
 
}
 
// Hide the calendar.
function ds_hi() {
	ds_ce.style.display = 'none';
}
 
// Moves to the next month...
function ds_nm() {
	// Increase the current month.
	ds_c_month ++;
	// We have passed December, let's go to the next year.
	// Increase the current year, and set the current month to January.
	if (ds_c_month > 12) {
		ds_c_month = 1; 
		ds_c_year++;
	}
	// Redraw the calendar.
	ds_draw_calendar(ds_c_month, ds_c_year);
}
 
// Moves to the previous month...
function ds_pm() {
	ds_c_month = ds_c_month - 1; // Can't use dash-dash here, it will make the page invalid.
	// We have passed January, let's go back to the previous year.
	// Decrease the current year, and set the current month to December.
	if (ds_c_month < 1) {
		ds_c_month = 12; 
		ds_c_year = ds_c_year - 1; // Can't use dash-dash here, it will make the page invalid.
	}
	// Redraw the calendar.
	ds_draw_calendar(ds_c_month, ds_c_year);
}
 
// Moves to the next year...
function ds_ny() {
	// Increase the current year.
	ds_c_year++;
	// Redraw the calendar.
	ds_draw_calendar(ds_c_month, ds_c_year);
}
 
// Moves to the previous year...
function ds_py() {
	// Decrease the current year.
	ds_c_year = ds_c_year - 1; // Can't use dash-dash here, it will make the page invalid.
	// Redraw the calendar.
	ds_draw_calendar(ds_c_month, ds_c_year);
}
 
// Format the date to output.
function ds_format_date(d, m, y) {
	// 2 digits month.
	m2 = '00' + m;
	m2 = m2.substr(m2.length - 2);
	// 2 digits day.
	d2 = '00' + d;
	d2 = d2.substr(d2.length - 2);
	// YYYY-MM-DD
	return y + '-' + m2 + '-' + d2;
}
 
// When the user clicks the day.
function ds_onclick(d, m, y) {
	// Hide the calendar.
	ds_hi();
	
	// ***** add the line below
	
	// Set the value of it, if we can.
      if (typeof(ds_element.value) != 'undefined') {
            ds_element.value = ds_format_date(d, m, y);
      // Maybe we want to set the HTML in it.
      } else if (typeof(ds_element.innerHTML) != 'undefined') {
            ds_element.innerHTML = ds_format_date(d, m, y);
      // I don't know how should we display it, just alert it to user.
      } else {
            alert (ds_format_date(d, m, y));
      }
 
 
   // we ADD THe FOLLOWING:
   document.getElementById("myForm").submit();
   }

Open in new window

Avatar of msfletch
msfletch
Flag of United States of America image

You can try something like this:

<!--- include field --->
Change date to: <input onclick="ds_sh(this);" id="clubnightdate" name="clubnightdate" readonly="readonly" style="cursor: text" size="20">
<!--- include image --->
<a href="Javascript:ds_sh('clubnightdate');"><img src="images/ico_calendar_bl.gif" width="12" height="12" border="0"></a>

Avatar of dm404
dm404

ASKER

Hi msfletch,

The script produces the same textbox, which acts the same as it did before.

Also there is a small square next to it, which calls the calendar but also has a pop up after day has been selected.

Any more ideas?

Thanks in advance,

Daniel
Daniel,

The square is caused by the fact that you most likely do not have the image "images/ico_calendar_bl.gif" on your server. Replace the image ref with whatever image you are wanting to use.

So you do not want the textbox to show, and you want the calendar to submit on checkout?

Try this:

<!--- include hidden date field --->
<input type=hidden id="clubnightdate" name="clubnightdate" onChange="document.myForm.submit();">

** The above will require you to add the name element to the form tag at the top of the page and call it myForm like:

<form action="clubnights.php" method="post" id="myForm" name="myForm">

<!--- include image --->
Change date to: <a href="Javascript:ds_sh('clubnightdate');"><img src="calendar_icon_here" width="12" height="12" border="0"></a>

** Above requires you to replace the "calendar_icon_here" with the image reference for whatever you want people to click on to open the calendar.

Hope this helps.
Avatar of dm404

ASKER

Hi msflecth.

The good news is that I can now see the image and it calls the calendar when clicked.

The bad news..

The page functionality has stopped working i.e. its not returning any records.

The way I have it set up at the moment is that when a day is selected on the calendar the form is submitted. This was working fine, this is included in the JS of the calendar (see below).

I'm not sure how to get around this problem?

// When the user clicks the day.
function ds_onclick(d, m, y) {
	// Hide the calendar.
	ds_hi();
	
	// Set the value of it, if we can.
      if (typeof(ds_element.value) != 'undefined') {
            ds_element.value = ds_format_date(d, m, y);
      // Maybe we want to set the HTML in it.
      } else if (typeof(ds_element.innerHTML) != 'undefined') {
            ds_element.innerHTML = ds_format_date(d, m, y);
      // I don't know how should we display it, just alert it to user.
      } else {
            alert (ds_format_date(d, m, y));
      }
 
 
   // we ADD THe FOLLOWING:
   document.getElementById("myForm").submit();
   }

Open in new window

OK,

So you already have the calendar submitting from the existing JS. Try removing the onChange="document.myForm.submit();" from the "clubnightdate" form field. This is likely keeping things from processing correctly.
Avatar of dm404

ASKER

HI MSflecth,

Thanks for your time again.

OK so I removed the onChange="document.myForm.submit();" .

From what I can see the form is being submitted however its still not working properly. This is what happens..

I click a date, a pop up appears with the date I selected, the form submits, page reloads without date value present?

Any idea why this is happening?

Thanks again,

Daniel
Daniel,

Are there any javascript errors that appear, like "value expected" or anything like that? I will have to look at the code more closely to see what the JS is actually doing, but until then, a thought I had was that the problem may be due to the JS submitting the form before the value is added.

You can try adding the onChange="document.myForm.submit();" back to the hidden text field and removing the document.getElementById("myForm").submit(); from the JS to see what happens.

Let me know how that goes.
Avatar of dm404

ASKER

Hmm when I do the above it says error on page on the bottom left of the browser... : (.

Thanks for your efforts so far.

The way I have the form at the top definitely works.
Just to verify, did you add the name="myForm" to the form code like so:

<form action="clubnights.php" method="post" id="myForm" name="myForm">

Referencing a form with the onChange="document.myForm.submit();" would not read the ID value of the form element, only the name element.

You could also change the inline peice from:

<input type=hidden id="clubnightdate" name="clubnightdate" onChange="document.myForm.submit();">

... to what you had in the JS:

<input type=hidden id="clubnightdate" name="clubnightdate" onChange="document.getElementById("myForm").submit(); ">

Also,

Double-clicking the "error on page" message should bring up an alert box mith more information and a line number reference. Having the actual error and the code from that line number (along eith the 10 lines before and after) would be helpful in troubleshooting the issue.
Avatar of dm404

ASKER

Just to verify, did you add the name="myForm" to the form code like so:

<form action="clubnights.php" method="post" id="myForm" name="myForm">
-- Yes i have done this.

The error that comes on the bottom left declares line 397 which is the } else { line....

      // Set the value of it, if we can.
      if (typeof(ds_element.value) != 'undefined') {
            ds_element.value = ds_format_date(d, m, y);
      // Maybe we want to set the HTML in it.
      } else if (typeof(ds_element.innerHTML) != 'undefined') {
            ds_element.innerHTML = ds_format_date(d, m, y);
      // I don't know how should we display it, just alert it to user.
      } else {
            alert (ds_format_date(d, m, y));
      }


   // we ADD THe FOLLOWING:
   document.getElementById("myForm").submit();
   }

Hope this helps,
#

Thanks again!
OK dm404,

Sometimes these things come down to relationships and context which are hard to identify without the code to test. Can you post your entire code set (as it now sits) so I can view it all in context.

Thanks.

Sorry I couldn't help more. Good luck.
dm404,

I just wanted to post my final thoughts here in case anyone happened upon before the question was deleted. If you have not already solved the issue, this may help:

Since the text field was working correctly before being hidden and before the the image reference was added, it would seemt o indicate that one of two things would cause the problem:

1) The javascript is having an issue with the "hidden" type of the text field. You could try replacing it with [style="display:none"] to achieve the same visible effect without actually defining it as hidden. This might workbetter with the JS Calendar Javascript.

2) The JS Calendar code is having a problem with the pointing if the reference. You could try using a fully qualified reference like:

<a href="Javascript:ds_sh('document.myForm.clubnightdate');"><img src="calendar_icon_here" width="12" height="12" border="0"></a>

... instead of:

<a href="Javascript:ds_sh('clubnightdate');"><img src="calendar_icon_here" width="12" height="12" border="0"></a>

Anyway .. happy coding!
Avatar of dm404

ASKER

Hi MSfletch,

Thanks for your persistance!! I'll have a go tonight.

PS I didn't realise the question would be deleted!

Don't care about the refund..I just want to call this JS from an image :)
No worries. I don't like to see questions go unanswered, especially with so much good back and forth. Good luck! =)
Avatar of dm404

ASKER

Hi PenguinMod,

I'd very much like to leave the question open. If you could call additional experts that would be awesome, it is a tricky question so the more the merrier!

Thanks again,

Dan
ASKER CERTIFIED SOLUTION
Avatar of Michel Plungjan
Michel Plungjan
Flag of Denmark image

Link to home
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
Start Free Trial
And the "B" grade was because?
Grades should be given based on answers from an individual, not the group as a whole. They affect the point total given to the one whose answer is accepted.
Avatar of dm404

ASKER

My bad.
Avatar of dm404

ASKER

Good Job, sorry about the previous grading.