|
<!DOCTYPE html> |
|
<html lang="en"> |
|
<head> |
|
<meta charset="UTF-8"> |
|
<meta name="viewport" content="width=device-width, initial-scale=1.0"> |
|
<title>Taskly - Smart To-Do List</title> |
|
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/6.4.0/css/all.min.css"> |
|
<style> |
|
:root { |
|
--primary-color: #5e72e4; |
|
--primary-dark: #3f51b5; |
|
--accent-color: #ff4081; |
|
--text-primary: #2d3748; |
|
--text-secondary: #4a5568; |
|
--bg-color: #f8f9fa; |
|
--card-bg: #ffffff; |
|
--border-color: #e2e8f0; |
|
--success-color: #48bb78; |
|
--warning-color: #ed8936; |
|
--danger-color: #f56565; |
|
--low-priority: #4299e1; |
|
--medium-priority: #ed8936; |
|
--high-priority: #f56565; |
|
} |
|
|
|
[data-theme="dark"] { |
|
--primary-color: #667eea; |
|
--primary-dark: #5a67d8; |
|
--text-primary: #f7fafc; |
|
--text-secondary: #cbd5e0; |
|
--bg-color: #1a202c; |
|
--card-bg: #2d3748; |
|
--border-color: #4a5568; |
|
} |
|
|
|
* { |
|
margin: 0; |
|
padding: 0; |
|
box-sizing: border-box; |
|
font-family: 'Segoe UI', Tahoma, Geneva, Verdana, sans-serif; |
|
} |
|
|
|
body { |
|
background-color: var(--bg-color); |
|
color: var(--text-primary); |
|
transition: all 0.3s ease; |
|
} |
|
|
|
.container { |
|
max-width: 100%; |
|
width: 100%; |
|
height: 100vh; |
|
max-height: 100vh; |
|
position: relative; |
|
overflow: hidden; |
|
display: flex; |
|
flex-direction: column; |
|
} |
|
|
|
|
|
header { |
|
display: flex; |
|
justify-content: space-between; |
|
align-items: center; |
|
padding: 1rem 1.5rem; |
|
background-color: var(--primary-color); |
|
color: white; |
|
box-shadow: 0 2px 10px rgba(0, 0, 0, 0.1); |
|
z-index: 100; |
|
} |
|
|
|
.logo { |
|
display: flex; |
|
align-items: center; |
|
gap: 0.5rem; |
|
font-weight: 700; |
|
font-size: 1.2rem; |
|
} |
|
|
|
.logo i { |
|
font-size: 1.4rem; |
|
} |
|
|
|
.header-actions { |
|
display: flex; |
|
gap: 1rem; |
|
align-items: center; |
|
} |
|
|
|
.theme-toggle, .user-avatar { |
|
width: 35px; |
|
height: 35px; |
|
border-radius: 50%; |
|
display: flex; |
|
align-items: center; |
|
justify-content: center; |
|
background-color: rgba(255, 255, 255, 0.2); |
|
cursor: pointer; |
|
border: none; |
|
color: white; |
|
font-size: 1rem; |
|
} |
|
|
|
.user-avatar { |
|
background-color: white; |
|
color: var(--primary-color); |
|
font-weight: bold; |
|
} |
|
|
|
|
|
.main-content { |
|
flex: 1; |
|
padding: 1rem; |
|
overflow-y: auto; |
|
padding-bottom: 80px; |
|
} |
|
|
|
|
|
.date-section { |
|
display: flex; |
|
justify-content: space-between; |
|
align-items: center; |
|
margin-bottom: 1.5rem; |
|
} |
|
|
|
.current-date h2 { |
|
font-size: 1.5rem; |
|
font-weight: 600; |
|
} |
|
|
|
.current-date p { |
|
color: var(--text-secondary); |
|
font-size: 0.9rem; |
|
} |
|
|
|
.calendar-btn { |
|
background-color: var(--card-bg); |
|
border: 1px solid var(--border-color); |
|
padding: 0.7rem; |
|
border-radius: 12px; |
|
display: flex; |
|
align-items: center; |
|
justify-content: center; |
|
cursor: pointer; |
|
} |
|
|
|
|
|
.stats-section { |
|
display: flex; |
|
gap: 1rem; |
|
margin-bottom: 1.5rem; |
|
} |
|
|
|
.stat-card { |
|
flex: 1; |
|
background-color: var(--card-bg); |
|
border-radius: 12px; |
|
padding: 1rem; |
|
display: flex; |
|
flex-direction: column; |
|
align-items: center; |
|
box-shadow: 0 2px 5px rgba(0, 0, 0, 0.05); |
|
} |
|
|
|
.stat-icon { |
|
width: 40px; |
|
height: 40px; |
|
border-radius: 12px; |
|
display: flex; |
|
align-items: center; |
|
justify-content: center; |
|
margin-bottom: 0.5rem; |
|
} |
|
|
|
.completed .stat-icon { |
|
background-color: rgba(73, 187, 120, 0.1); |
|
color: var(--success-color); |
|
} |
|
|
|
.pending .stat-icon { |
|
background-color: rgba(237, 137, 54, 0.1); |
|
color: var(--warning-color); |
|
} |
|
|
|
.overdue .stat-icon { |
|
background-color: rgba(245, 101, 101, 0.1); |
|
color: var(--danger-color); |
|
} |
|
|
|
.stat-card h3 { |
|
font-size: 1.1rem; |
|
font-weight: 600; |
|
margin-bottom: 0.3rem; |
|
text-align: center; |
|
} |
|
|
|
.stat-card p { |
|
font-size: 0.8rem; |
|
color: var(--text-secondary); |
|
text-align: center; |
|
} |
|
|
|
|
|
.add-task-container { |
|
position: fixed; |
|
bottom: 80px; |
|
left: 50%; |
|
transform: translateX(-50%); |
|
width: calc(100% - 2rem); |
|
z-index: 50; |
|
} |
|
|
|
.add-task-btn { |
|
width: 100%; |
|
display: flex; |
|
align-items: center; |
|
justify-content: center; |
|
gap: 0.5rem; |
|
padding: 1rem; |
|
background-color: var(--primary-color); |
|
border: none; |
|
border-radius: 12px; |
|
color: white; |
|
font-size: 1rem; |
|
cursor: pointer; |
|
box-shadow: 0 4px 12px rgba(94, 114, 228, 0.3); |
|
font-weight: 600; |
|
} |
|
|
|
|
|
.tasks-container { |
|
margin-bottom: 1rem; |
|
} |
|
|
|
.section-header { |
|
display: flex; |
|
justify-content: space-between; |
|
align-items: center; |
|
margin-bottom: 1rem; |
|
} |
|
|
|
.section-header h3 { |
|
font-size: 1.1rem; |
|
font-weight: 600; |
|
} |
|
|
|
.section-header span { |
|
background-color: var(--border-color); |
|
color: var(--text-secondary); |
|
padding: 0.2rem 0.5rem; |
|
border-radius: 10px; |
|
font-size: 0.8rem; |
|
} |
|
|
|
.task-list { |
|
display: flex; |
|
flex-direction: column; |
|
gap: 0.8rem; |
|
} |
|
|
|
.task-item { |
|
background-color: var(--card-bg); |
|
border: 1px solid var(--border-color); |
|
border-radius: 12px; |
|
padding: 1rem; |
|
display: flex; |
|
align-items: center; |
|
gap: 1rem; |
|
transition: all 0.2s ease; |
|
position: relative; |
|
overflow: hidden; |
|
} |
|
|
|
.task-item:hover { |
|
transform: translateY(-2px); |
|
box-shadow: 0 4px 8px rgba(0, 0, 0, 0.05); |
|
} |
|
|
|
.task-checkbox { |
|
width: 20px; |
|
height: 20px; |
|
border-radius: 6px; |
|
border: 2px solid var(--border-color); |
|
appearance: none; |
|
cursor: pointer; |
|
flex-shrink: 0; |
|
display: flex; |
|
align-items: center; |
|
justify-content: center; |
|
} |
|
|
|
.task-checkbox:checked { |
|
background-color: var(--primary-color); |
|
border-color: var(--primary-color); |
|
} |
|
|
|
.task-checkbox:checked::after { |
|
content: "\f00c"; |
|
font-family: "Font Awesome 6 Free"; |
|
font-weight: 900; |
|
color: white; |
|
font-size: 0.7rem; |
|
} |
|
|
|
.task-content { |
|
flex: 1; |
|
overflow: hidden; |
|
} |
|
|
|
.task-title { |
|
font-weight: 600; |
|
margin-bottom: 0.2rem; |
|
position: relative; |
|
} |
|
|
|
.task-title.completed { |
|
text-decoration: line-through; |
|
color: var(--text-secondary); |
|
} |
|
|
|
.task-details { |
|
display: flex; |
|
align-items: center; |
|
gap: 0.7rem; |
|
margin-top: 0.4rem; |
|
} |
|
|
|
.task-detail { |
|
display: flex; |
|
align-items: center; |
|
gap: 0.3rem; |
|
font-size: 0.8rem; |
|
color: var(--text-secondary); |
|
} |
|
|
|
.task-detail i { |
|
font-size: 0.8rem; |
|
} |
|
|
|
.task-priority { |
|
width: 10px; |
|
height: 10px; |
|
border-radius: 50%; |
|
display: inline-block; |
|
} |
|
|
|
.priority-low { |
|
background-color: var(--low-priority); |
|
} |
|
|
|
.priority-medium { |
|
background-color: var(--medium-priority); |
|
} |
|
|
|
.priority-high { |
|
background-color: var(--high-priority); |
|
} |
|
|
|
.task-actions { |
|
display: flex; |
|
gap: 0.5rem; |
|
align-items: center; |
|
} |
|
|
|
.task-action-btn { |
|
background: none; |
|
border: none; |
|
color: var(--text-secondary); |
|
cursor: pointer; |
|
font-size: 1rem; |
|
transition: all 0.2s ease; |
|
} |
|
|
|
.task-action-btn:hover { |
|
color: var(--primary-color); |
|
} |
|
|
|
|
|
.bottom-nav { |
|
position: fixed; |
|
bottom: 0; |
|
left: 0; |
|
right: 0; |
|
background-color: var(--card-bg); |
|
display: flex; |
|
justify-content: space-around; |
|
padding: 0.8rem 0; |
|
box-shadow: 0 -2px 10px rgba(0, 0, 0, 0.05); |
|
z-index: 100; |
|
} |
|
|
|
.nav-item { |
|
display: flex; |
|
flex-direction: column; |
|
align-items: center; |
|
gap: 0.2rem; |
|
color: var(--text-secondary); |
|
text-decoration: none; |
|
font-size: 0.9rem; |
|
} |
|
|
|
.nav-item.active { |
|
color: var(--primary-color); |
|
} |
|
|
|
.nav-item i { |
|
font-size: 1.2rem; |
|
} |
|
|
|
|
|
.modal { |
|
position: fixed; |
|
top: 0; |
|
left: 0; |
|
right: 0; |
|
bottom: 0; |
|
background-color: rgba(0, 0, 0, 0.5); |
|
display: flex; |
|
justify-content: center; |
|
align-items: center; |
|
z-index: 200; |
|
opacity: 0; |
|
pointer-events: none; |
|
transition: all 0.3s ease; |
|
} |
|
|
|
.modal.active { |
|
opacity: 1; |
|
pointer-events: all; |
|
} |
|
|
|
.modal-content { |
|
background-color: var(--card-bg); |
|
width: 90%; |
|
max-width: 500px; |
|
border-radius: 16px; |
|
padding: 1.5rem; |
|
box-shadow: 0 10px 25px rgba(0, 0, 0, 0.1); |
|
transform: translateY(20px); |
|
transition: all 0.3s ease; |
|
max-height: 90vh; |
|
overflow-y: auto; |
|
} |
|
|
|
.modal.active .modal-content { |
|
transform: translateY(0); |
|
} |
|
|
|
.modal-header { |
|
display: flex; |
|
justify-content: space-between; |
|
align-items: center; |
|
margin-bottom: 1.5rem; |
|
} |
|
|
|
.modal-title { |
|
font-size: 1.3rem; |
|
font-weight: 600; |
|
} |
|
|
|
.modal-close { |
|
background: none; |
|
border: none; |
|
font-size: 1.5rem; |
|
color: var(--text-secondary); |
|
cursor: pointer; |
|
} |
|
|
|
.form-group { |
|
margin-bottom: 1.2rem; |
|
} |
|
|
|
.form-group label { |
|
display: block; |
|
margin-bottom: 0.5rem; |
|
font-weight: 500; |
|
} |
|
|
|
.form-control { |
|
width: 100%; |
|
padding: 0.8rem; |
|
border: 1px solid var(--border-color); |
|
border-radius: 10px; |
|
background-color: var(--card-bg); |
|
color: var(--text-primary); |
|
font-size: 1rem; |
|
} |
|
|
|
.form-control:focus { |
|
outline: none; |
|
border-color: var(--primary-color); |
|
} |
|
|
|
.priority-buttons { |
|
display: flex; |
|
gap: 0.5rem; |
|
} |
|
|
|
.priority-btn { |
|
flex: 1; |
|
padding: 0.5rem; |
|
border-radius: 8px; |
|
border: 1px solid var(--border-color); |
|
background-color: transparent; |
|
display: flex; |
|
align-items: center; |
|
justify-content: center; |
|
gap: 0.3rem; |
|
cursor: pointer; |
|
font-size: 0.9rem; |
|
color: var(--text-secondary); |
|
} |
|
|
|
.priority-btn.active { |
|
border-color: var(--primary-color); |
|
color: var(--primary-color); |
|
background-color: rgba(94, 114, 228, 0.1); |
|
} |
|
|
|
.priority-dot { |
|
width: 10px; |
|
height: 10px; |
|
border-radius: 50%; |
|
} |
|
|
|
.category-tags { |
|
display: flex; |
|
flex-wrap: wrap; |
|
gap: 0.5rem; |
|
margin-bottom: 0.5rem; |
|
} |
|
|
|
.category-tag { |
|
padding: 0.3rem 0.8rem; |
|
border-radius: 20px; |
|
font-size: 0.8rem; |
|
background-color: var(--border-color); |
|
color: var(--text-secondary); |
|
border: none; |
|
cursor: pointer; |
|
} |
|
|
|
.category-tag.active { |
|
background-color: var(--primary-color); |
|
color: white; |
|
} |
|
|
|
.date-time-row { |
|
display: flex; |
|
gap: 0.8rem; |
|
} |
|
|
|
.date-time-row .form-group { |
|
flex: 1; |
|
} |
|
|
|
.input-with-icon { |
|
position: relative; |
|
} |
|
|
|
.input-with-icon i { |
|
position: absolute; |
|
right: 12px; |
|
top: 50%; |
|
transform: translateY(-50%); |
|
color: var(--text-secondary); |
|
} |
|
|
|
.modal-footer { |
|
display: flex; |
|
gap: 1rem; |
|
margin-top: 1.5rem; |
|
} |
|
|
|
.btn { |
|
padding: 0.8rem 1.5rem; |
|
border-radius: 10px; |
|
font-weight: 500; |
|
cursor: pointer; |
|
font-size: 1rem; |
|
border: none; |
|
} |
|
|
|
.btn-primary { |
|
background-color: var(--primary-color); |
|
color: white; |
|
flex: 1; |
|
} |
|
|
|
.btn-outline { |
|
background-color: transparent; |
|
border: 1px solid var(--border-color); |
|
color: var(--text-primary); |
|
} |
|
|
|
|
|
@keyframes fadeIn { |
|
from { opacity: 0; transform: translateY(10px); } |
|
to { opacity: 1; transform: translateY(0); } |
|
} |
|
|
|
.task-item { |
|
animation: fadeIn 0.3s ease forwards; |
|
} |
|
|
|
|
|
@media (min-width: 768px) { |
|
.container { |
|
max-width: 500px; |
|
margin: 0 auto; |
|
height: 90vh; |
|
max-height: 900px; |
|
margin-top: 5vh; |
|
border-radius: 16px; |
|
box-shadow: 0 10px 25px rgba(0, 0, 0, 0.1); |
|
overflow: hidden; |
|
} |
|
|
|
.bottom-nav { |
|
width: 500px; |
|
left: 50%; |
|
transform: translateX(-50%); |
|
border-bottom-left-radius: 16px; |
|
border-bottom-right-radius: 16px; |
|
} |
|
|
|
.add-task-container { |
|
width: 460px; |
|
} |
|
} |
|
</style> |
|
</head> |
|
<body> |
|
<div class="container"> |
|
<header> |
|
<div class="logo"> |
|
<i class="fas fa-tasks"></i> |
|
<span>Taskly</span> |
|
</div> |
|
<div class="header-actions"> |
|
<button class="theme-toggle" id="themeToggle"> |
|
<i class="fas fa-moon"></i> |
|
</button> |
|
<button class="user-avatar">JS</button> |
|
</div> |
|
</header> |
|
|
|
<main class="main-content"> |
|
<section class="date-section"> |
|
<div class="current-date"> |
|
<h2 id="currentDate">Today, June 15</h2> |
|
<p id="currentTodos">You have 5 tasks to complete</p> |
|
</div> |
|
<button class="calendar-btn"> |
|
<i class="fas fa-calendar-alt"></i> |
|
</button> |
|
</section> |
|
|
|
<section class="stats-section"> |
|
<div class="stat-card completed"> |
|
<div class="stat-icon"> |
|
<i class="fas fa-check"></i> |
|
</div> |
|
<h3>12</h3> |
|
<p>Completed</p> |
|
</div> |
|
<div class="stat-card pending"> |
|
<div class="stat-icon"> |
|
<i class="fas fa-clock"></i> |
|
</div> |
|
<h3>5</h3> |
|
<p>Pending</p> |
|
</div> |
|
<div class="stat-card overdue"> |
|
<div class="stat-icon"> |
|
<i class="fas fa-exclamation"></i> |
|
</div> |
|
<h3>2</h3> |
|
<p>Overdue</p> |
|
</div> |
|
</section> |
|
|
|
<section class="tasks-container"> |
|
<div class="section-header"> |
|
<h3>Today's Tasks</h3> |
|
<span>5 tasks</span> |
|
</div> |
|
<div class="task-list" id="todayTasks"> |
|
|
|
</div> |
|
</section> |
|
|
|
<section class="tasks-container"> |
|
<div class="section-header"> |
|
<h3>Upcoming</h3> |
|
<span>3 tasks</span> |
|
</div> |
|
<div class="task-list" id="upcomingTasks"> |
|
|
|
</div> |
|
</section> |
|
</main> |
|
|
|
<div class="add-task-container"> |
|
<button class="add-task-btn" id="addTaskBtn"> |
|
<i class="fas fa-plus"></i> |
|
<span>Add Task</span> |
|
</button> |
|
</div> |
|
|
|
<nav class="bottom-nav"> |
|
<a href="#" class="nav-item active"> |
|
<i class="fas fa-home"></i> |
|
<span>Home</span> |
|
</a> |
|
<a href="#" class="nav-item"> |
|
<i class="fas fa-calendar"></i> |
|
<span>Calendar</span> |
|
</a> |
|
<a href="#" class="nav-item"> |
|
<i class="fas fa-chart-pie"></i> |
|
<span>Stats</span> |
|
</a> |
|
<a href="#" class="nav-item"> |
|
<i class="fas fa-cog"></i> |
|
<span>Settings</span> |
|
</a> |
|
</nav> |
|
</div> |
|
|
|
|
|
<div class="modal" id="taskModal"> |
|
<div class="modal-content"> |
|
<div class="modal-header"> |
|
<h2 class="modal-title">Add New Task</h2> |
|
<button class="modal-close" id="closeModal">×</button> |
|
</div> |
|
<form id="taskForm"> |
|
<div class="form-group"> |
|
<label for="taskTitle">Task Title</label> |
|
<input type="text" id="taskTitle" class="form-control" placeholder="Enter task title" required> |
|
</div> |
|
<div class="form-group"> |
|
<label for="taskDescription">Description</label> |
|
<textarea id="taskDescription" class="form-control" rows="3" placeholder="Enter task description (optional)"></textarea> |
|
</div> |
|
<div class="form-group"> |
|
<label>Priority</label> |
|
<div class="priority-buttons"> |
|
<button type="button" class="priority-btn" data-priority="low"> |
|
<span class="priority-dot priority-low"></span> |
|
Low |
|
</button> |
|
<button type="button" class="priority-btn active" data-priority="medium"> |
|
<span class="priority-dot priority-medium"></span> |
|
Medium |
|
</button> |
|
<button type="button" class="priority-btn" data-priority="high"> |
|
<span class="priority-dot priority-high"></span> |
|
High |
|
</button> |
|
</div> |
|
</div> |
|
<div class="form-group"> |
|
<label>Category</label> |
|
<div class="category-tags"> |
|
<button type="button" class="category-tag active" data-category="personal">Personal</button> |
|
<button type="button" class="category-tag" data-category="work">Work</button> |
|
<button type="button" class="category-tag" data-category="shopping">Shopping</button> |
|
<button type="button" class="category-tag" data-category="health">Health</button> |
|
<button type="button" class="category-tag" data-category="other">Other</button> |
|
</div> |
|
</div> |
|
<div class="form-group"> |
|
<div class="date-time-row"> |
|
<div class="form-group"> |
|
<label for="taskDate">Date</label> |
|
<div class="input-with-icon"> |
|
<input type="date" id="taskDate" class="form-control" required> |
|
<i class="fas fa-calendar"></i> |
|
</div> |
|
</div> |
|
<div class="form-group"> |
|
<label for="taskTime">Time</label> |
|
<div class="input-with-icon"> |
|
<input type="time" id="taskTime" class="form-control"> |
|
<i class="fas fa-clock"></i> |
|
</div> |
|
</div> |
|
</div> |
|
</div> |
|
<div class="modal-footer"> |
|
<button type="button" class="btn btn-outline" id="cancelTask">Cancel</button> |
|
<button type="submit" class="btn btn-primary">Add Task</button> |
|
</div> |
|
</form> |
|
</div> |
|
</div> |
|
|
|
<script> |
|
|
|
const tasks = [ |
|
{ |
|
id: 1, |
|
title: "Complete project presentation", |
|
description: "Finish slides and rehearse presentation", |
|
completed: false, |
|
priority: "high", |
|
category: "work", |
|
date: new Date(), |
|
time: "15:00" |
|
}, |
|
{ |
|
id: 2, |
|
title: "Buy groceries", |
|
description: "Milk, eggs, bread, fruits", |
|
completed: false, |
|
priority: "medium", |
|
category: "shopping", |
|
date: new Date(), |
|
time: null |
|
}, |
|
{ |
|
id: 3, |
|
title: "Morning workout", |
|
description: "30 minutes of cardio", |
|
completed: true, |
|
priority: "low", |
|
category: "health", |
|
date: new Date(), |
|
time: "07:00" |
|
}, |
|
{ |
|
id: 4, |
|
title: "Call mom", |
|
description: "Wish her happy birthday", |
|
completed: false, |
|
priority: "medium", |
|
category: "personal", |
|
date: new Date(), |
|
time: "18:00" |
|
}, |
|
{ |
|
id: 5, |
|
title: "Read 20 pages", |
|
description: "Current book: Atomic Habits", |
|
completed: false, |
|
priority: "low", |
|
category: "personal", |
|
date: new Date(), |
|
time: null |
|
}, |
|
{ |
|
id: 6, |
|
title: "Team meeting", |
|
description: "Discuss Q3 goals", |
|
completed: false, |
|
priority: "high", |
|
category: "work", |
|
date: new Date(new Date().getTime() + 86400000), |
|
time: "10:30" |
|
}, |
|
{ |
|
id: 7, |
|
title: "Dentist appointment", |
|
description: "Annual checkup", |
|
completed: false, |
|
priority: "medium", |
|
category: "health", |
|
date: new Date(new Date().getTime() + 2 * 86400000), |
|
time: "14:15" |
|
} |
|
]; |
|
|
|
|
|
const themeToggle = document.getElementById('themeToggle'); |
|
const addTaskBtn = document.getElementById('addTaskBtn'); |
|
const taskModal = document.getElementById('taskModal'); |
|
const closeModal = document.getElementById('closeModal'); |
|
const cancelTask = document.getElementById('cancelTask'); |
|
const taskForm = document.getElementById('taskForm'); |
|
const todayTasksContainer = document.getElementById('todayTasks'); |
|
const upcomingTasksContainer = document.getElementById('upcomingTasks'); |
|
const currentDateElement = document.getElementById('currentDate'); |
|
const currentTodosElement = document.getElementById('currentTodos'); |
|
const priorityButtons = document.querySelectorAll('.priority-btn'); |
|
const categoryButtons = document.querySelectorAll('.category-tag'); |
|
|
|
|
|
const options = { weekday: 'long', month: 'long', day: 'numeric' }; |
|
const today = new Date(); |
|
currentDateElement.textContent = today.toLocaleDateString('en-US', { weekday: 'long', month: 'long', day: 'numeric' }); |
|
|
|
|
|
const todayTasks = tasks.filter(task => { |
|
return task.date.toDateString() === today.toDateString(); |
|
}); |
|
|
|
const upcomingTasks = tasks.filter(task => { |
|
return task.date > today && task.date.toDateString() !== today.toDateString(); |
|
}); |
|
|
|
|
|
currentTodosElement.textContent = `You have ${todayTasks.length} tasks to complete`; |
|
|
|
|
|
themeToggle.addEventListener('click', () => { |
|
document.body.setAttribute('data-theme', |
|
document.body.getAttribute('data-theme') === 'dark' ? 'light' : 'dark'); |
|
|
|
const icon = themeToggle.querySelector('i'); |
|
if (document.body.getAttribute('data-theme') === 'dark') { |
|
icon.classList.remove('fa-moon'); |
|
icon.classList.add('fa-sun'); |
|
} else { |
|
icon.classList.remove('fa-sun'); |
|
icon.classList.add('fa-moon'); |
|
} |
|
}); |
|
|
|
|
|
addTaskBtn.addEventListener('click', () => { |
|
taskModal.classList.add('active'); |
|
document.getElementById('taskTitle').focus(); |
|
}); |
|
|
|
closeModal.addEventListener('click', () => { |
|
taskModal.classList.remove('active'); |
|
}); |
|
|
|
cancelTask.addEventListener('click', () => { |
|
taskModal.classList.remove('active'); |
|
}); |
|
|
|
|
|
taskModal.addEventListener('click', (e) => { |
|
if (e.target === taskModal) { |
|
taskModal.classList.remove('active'); |
|
} |
|
}); |
|
|
|
|
|
priorityButtons.forEach(button => { |
|
button.addEventListener('click', () => { |
|
priorityButtons.forEach(btn => btn.classList.remove('active')); |
|
button.classList.add('active'); |
|
}); |
|
}); |
|
|
|
|
|
categoryButtons.forEach(button => { |
|
button.addEventListener('click', () => { |
|
categoryButtons.forEach(btn => btn.classList.remove('active')); |
|
button.classList.add('active'); |
|
}); |
|
}); |
|
|
|
|
|
function renderTasks() { |
|
|
|
todayTasksContainer.innerHTML = ''; |
|
upcomingTasksContainer.innerHTML = ''; |
|
|
|
|
|
todayTasks.forEach(task => { |
|
const taskElement = createTaskElement(task); |
|
todayTasksContainer.appendChild(taskElement); |
|
}); |
|
|
|
|
|
upcomingTasks.forEach(task => { |
|
const taskElement = createTaskElement(task); |
|
upcomingTasksContainer.appendChild(taskElement); |
|
}); |
|
|
|
|
|
document.querySelectorAll('.task-checkbox').forEach(checkbox => { |
|
checkbox.addEventListener('change', function() { |
|
const taskId = parseInt(this.getAttribute('data-task-id')); |
|
const taskItem = tasks.find(t => t.id === taskId); |
|
if (taskItem) { |
|
taskItem.completed = this.checked; |
|
renderTasks(); |
|
|
|
} |
|
}); |
|
}); |
|
|
|
|
|
document.querySelectorAll('.task-action-btn').forEach(button => { |
|
button.addEventListener('click', function() { |
|
const action = this.getAttribute('data-action'); |
|
const taskId = parseInt(this.getAttribute('data-task-id')); |
|
const taskItem = tasks.find(t => t.id === taskId); |
|
|
|
if (action === 'delete' && confirm('Are you sure you want to delete this task?')) { |
|
const taskIndex = tasks.findIndex(t => t.id === taskId); |
|
if (taskIndex !== -1) { |
|
tasks.splice(taskIndex, 1); |
|
renderTasks(); |
|
|
|
} |
|
} else if (action === 'edit') { |
|
|
|
alert('Edit functionality would be implemented here'); |
|
} |
|
}); |
|
}); |
|
} |
|
|
|
function createTaskElement(task) { |
|
const taskElement = document.createElement('div'); |
|
taskElement.className = `task-item ${task.completed ? 'completed' : ''}`; |
|
|
|
let timeDisplay = ''; |
|
if (task.time) { |
|
const [hours, minutes] = task.time.split(':'); |
|
const time = new Date(); |
|
time.setHours(parseInt(hours)); |
|
time.setMinutes(parseInt(minutes)); |
|
timeDisplay = time.toLocaleTimeString([], { hour: '2-digit', minute: '2-digit' }); |
|
} |
|
|
|
const taskDateOptions = { month: 'short', day: 'numeric' }; |
|
const taskDateDisplay = task.date.toLocaleDateString('en-US', taskDateOptions); |
|
|
|
taskElement.innerHTML = ` |
|
<input type="checkbox" class="task-checkbox" data-task-id="${task.id}" ${task.completed ? 'checked' : ''}> |
|
<div class="task-content"> |
|
<h3 class="task-title ${task.completed ? 'completed' : ''}">${task.title}</h3> |
|
${task.description ? `<p class="task-description">${task.description}</p>` : ''} |
|
<div class="task-details"> |
|
<div class="task-detail"> |
|
<span class="task-priority priority-${task.priority}"></span> |
|
${task.priority.charAt(0).toUpperCase() + task.priority.slice(1)} |
|
</div> |
|
<div class="task-detail"> |
|
<i class="fas fa-tag"></i> |
|
${task.category.charAt(0).toUpperCase() + task.category.slice(1)} |
|
</div> |
|
${task.time ? ` |
|
<div class="task-detail"> |
|
<i class="fas fa-clock"></i> |
|
${timeDisplay} |
|
</div> |
|
` : ''} |
|
</div> |
|
</div> |
|
<div class="task-actions"> |
|
<button class="task-action-btn" data-task-id="${task.id}" data-action="edit"> |
|
<i class="fas fa-edit"></i> |
|
</button> |
|
<button class="task-action-btn" data-task-id="${task.id}" data-action="delete"> |
|
<i class="fas fa-trash-alt"></i> |
|
</button> |
|
</div> |
|
`; |
|
|
|
return taskElement; |
|
} |
|
|
|
|
|
taskForm.addEventListener('submit', (e) => { |
|
e.preventDefault(); |
|
|
|
|
|
const title = document.getElementById('taskTitle').value; |
|
const description = document.getElementById('taskDescription').value; |
|
const priority = document.querySelector('.priority-btn.active').getAttribute('data-priority'); |
|
const category = document.querySelector('.category-tag.active').getAttribute('data-category'); |
|
const date = document.getElementById('taskDate').value; |
|
const time = document.getElementById('taskTime').value; |
|
|
|
|
|
const newTask = { |
|
id: tasks.length > 0 ? Math.max(...tasks.map(t => t.id)) + 1 : 1, |
|
title, |
|
description, |
|
completed: false, |
|
priority, |
|
category, |
|
date: new Date(date), |
|
time: time || null |
|
}; |
|
|
|
|
|
tasks.push(newTask); |
|
|
|
|
|
renderTasks(); |
|
|
|
|
|
taskModal.classList.remove('active'); |
|
taskForm.reset(); |
|
|
|
|
|
priorityButtons.forEach(btn => btn.classList.remove('active')); |
|
document.querySelector('.priority-btn[data-priority="medium"]').classList.add('active'); |
|
|
|
|
|
categoryButtons.forEach(btn => btn.classList.remove('active')); |
|
document.querySelector('.category-tag[data-category="personal"]').classList.add('active'); |
|
}); |
|
|
|
|
|
document.getElementById('taskDate').valueAsDate = new Date(); |
|
|
|
|
|
renderTasks(); |
|
</script> |
|
</body> |
|
</html> |