I am creating an editable calendar, very similar to the one in Gmail. It is a grid of div
boxes, and each div
box can be clicked and a Modal will pop up where the user can edit/add data to that specific entry.
I am having one slight issue with my Modal within my For Loop. I understand the IDs used for the Divs must be unique, but my variable $i
will echo
accurately within div
id="myBtn' . $i . '"
but not accurate within div
id="myModal' . $i . '"
and the same applies to retrieving data from my database. Accurate within the "myBtn" div
but not the "myModal" div
.
Additionally, I can't close out of the Modal once I open it when I have the code set to div
id="myModal' . $i . '"
but when it is just div
id="myModal"
it functions fine, but the data is wrong.
I read the other posts similar to my issue, but couldn't seem to find a working solution. What am I doing wrong?
<?php
for($i = 0; $i <= 365; $i++){
$d=strtotime($i . " Day");
$day = date("l (m/d)", $d);
$end_month = date("l (m/01)", $d);
$str = strcmp($day, $end_month);
$query_date = date("m/d/Y l", $d);
$sql = "SELECT * FROM XXXXXXXX WHERE date = '$query_date' AND user_id = 1 ORDER BY start_time ASC";
$result = mysqli_query($connection, $sql);
while($row = mysqli_fetch_array($result)){
$entry_id = $row['entry_id'];
$schedule_date = date("l (m/d)", strtotime($row['date']));
$location_name .= "<strong>" . $row['location_name'] . "</strong><br/>(" . $row['start_time'] . " - " . $row['end_time'] . ")<br/><br/>";
}
$test = strcmp($day, $schedule_date);
if($str == 0){
echo '<div id="myBtn' . $i . '" class="menu2" style="width: 100%;">' . date("F", $d) . '</div>';
}
echo '
<!-- The Modal -->
<form action="" name="add-location" method="POST">
<div id="myModal' . $i . '" class="modal">
<!-- Modal content -->
<div class="modal-content">
<span class="close">×</span>
<p style="color: black;">' . $i . '</p>
<input type="text" name="" class="booking_input" style="width: 100%;" placeholder="' . $i . '"/>
<input type="submit" name="submit" class="button" style="vertical-align: middle; line-height: 15px;" />
</div>
</div>
</form>';
echo '<div id="myBtn' . $i . '" class="menu2" style="text-align: center;"><span style="font-size: 16px; color: #c11414;"><strong><u>' . $day . $i . '</u></strong></span></br/><br/>';
if($test == 0){
echo $location_name . "<br/>";
}
echo "</div>";
?>
<script>
// Get the modal
var modal = document.getElementById('myModal<?php echo $i; ?>');
// Get the button that opens the modal
var btn = document.getElementById("myBtn<?php echo $i; ?>");
// Get the <span> element that closes the modal
var span = document.getElementsByClassName("close")[0];
// When the user clicks the button, open the modal
btn.onclick = function() {
modal.style.display = "block";
}
// When the user clicks on <span> (x), close the modal
span.onclick = function() {
modal.style.display = "none";
}
// When the user clicks anywhere outside of the modal, close it
window.onclick = function(event) {
if (event.target == modal) {
modal.style.display = "none";
}
}
</script>
<?php
unset($location_name);
unset($address);
unset($start_time);
unset($end_time);
}
?>
Not very relevant, but here is the style
tag to go with the above code:
<style>
* {
box-sizing: border-box;
}
.header {
border: .5px solid #2f363e;
padding: 15px;
}
.menu2 {
width: 14.28%;
float: left;
padding: 15px;
border: .5px solid #2f363e;
height: 150px;
color: #2f363e;
}
.main {
width: 75%;
float: left;
padding: 15px;
border: .5px solid #2f363e;
}
</style>
<style>
/* The Modal (background) */
.modal {
display: none; /* Hidden by default */
position: fixed; /* Stay in place */
z-index: 1; /* Sit on top */
padding-top: 100px; /* Location of the box */
left: 0;
top: 0;
width: 100%; /* Full width */
height: 100%; /* Full height */
overflow: auto; /* Enable scroll if needed */
background-color: rgb(0,0,0); /* Fallback color */
background-color: rgba(0,0,0,0.4); /* Black w/ opacity */
}
/* Modal Content */
.modal-content {
background-color: #fefefe;
margin: auto;
padding: 20px;
border: 1px solid #888;
width: 80%;
}
/* The Close Button */
.close {
color: #aaaaaa;
float: right;
font-size: 28px;
font-weight: bold;
z-index: 1;
}
.close:hover,
.close:focus {
color: #000;
text-decoration: none;
cursor: pointer;
z-index: 1;
}
</style>
Why don't simply add the function calls direct to the buttons and use a general function to show/hide modal dialog? like this:
<?php
for($i = 0; $i <= 365; $i++){
$d=strtotime($i . " Day");
$day = date("l (m/d)", $d);
$end_month = date("l (m/01)", $d);
$str = strcmp($day, $end_month);
$query_date = date("m/d/Y l", $d);
$sql = "SELECT * FROM XXXXXXXX WHERE date = '$query_date' AND user_id = 1 ORDER BY start_time ASC";
$result = mysqli_query($connection, $sql);
while($row = mysqli_fetch_array($result)){
$entry_id = $row['entry_id'];
$schedule_date = date("l (m/d)", strtotime($row['date']));
$location_name .= "<strong>" . $row['location_name'] . "</strong><br/>(" . $row['start_time'] . " - " . $row['end_time'] . ")<br/><br/>";
}
$test = strcmp($day, $schedule_date);
if($str == 0){
echo '<div id="myBtn' . $i . '" class="menu2" style="width: 100%;">' . date("F", $d) . '</div>';
}
echo '
<!-- The Modal -->
<form action="" name="add-location" method="POST">
<div id="myModal' . $i . '" class="modal">
<!-- Modal content -->
<div class="modal-content">
<span class="close" onclick="closeModal('.$i.')">×</span>
<p style="color: black;">' . $i . '</p>
<input type="text" name="" class="booking_input" style="width: 100%;" placeholder="' . $i . '"/>
<input type="submit" name="submit" class="button" style="vertical-align: middle; line-height: 15px;" />
</div>
</div>
</form>';
echo '<div id="myBtn' . $i . '" class="menu2" onclick="showModal('.$i.')" style="text-align: center;"><span style="font-size: 16px; color: #c11414;"><strong><u>' . $day . $i . '</u></strong></span></br/><br/>';
if($test == 0){
echo $location_name . "<br/>";
}
echo "</div>";
?>
<?php
unset($location_name);
unset($address);
unset($start_time);
unset($end_time);
}
?>
<script>
function closeModal(id){
// Get the modal
var modal = document.getElementById('myModal'+id);
modal.style.display = "none";
}
function showModal(id){
// Get the modal
var modal = document.getElementById('myModal'+id);
modal.style.display = "block";
}
</script>
This is breaking because each iteration of the loop overwrites the javascript variables from the previous iteration.
To show you what I mean, look at this version of your loops distilled down to the simplest for that shows the bug
for ($i = 0; $i <= 2; $i++) {
?>
<script>
var modal = document.getElementById('myModal<?php echo $i; ?>');
</script>
<?php
}
The output of this will look like
<script>
var modal = document.getElementById('myModal0');
</script>
<script>
var modal = document.getElementById('myModal1');
</script>
<script>
var modal = document.getElementById('myModal2');
</script>
Or perhaps re-written to be even more illustrative
<script>
var modal = document.getElementById('myModal0');
var modal = document.getElementById('myModal1');
var modal = document.getElementById('myModal2');
</script>
Nothing in your implementation attempts to prevent this clobbering of the javascript variables. Glufu posted a solution that works, but it's based on HTML-DOM event handlers which is a pretty outdated way of doing things. You really should be using a library like jQuery to do this in a much better way
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.