Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
60 changes: 38 additions & 22 deletions AppointmentsManager/ClientApp/src/components/Appointment.js
Original file line number Diff line number Diff line change
@@ -1,42 +1,58 @@
import { activeId, entry, openModal } from "./Lib";


export default function Appointment(props) {

const handlingDelete = (id) =>{
activeId.id = id
const handlingDelete = (id) => {
activeId.id = id;
// update state
props.stateListener(Math.random() * 848 * Math.random())
//open edit modal
openModal("delete-modal")
}
props.stateListener(Math.random() * 848 * Math.random());
// open delete modal
openModal("delete-modal");
};

const handlingEdit = (row)=>{
Object.assign(entry, row)
const handlingEdit = (row) => {
Object.assign(entry, row);
// update state
props.stateListener(Math.random() * 548 * Math.random())
//open edit modal
openModal("edit-modal")
}
props.stateListener(Math.random() * 548 * Math.random());
// open edit modal
openModal("edit-modal");
};

const levelOfImportance = ["Very Low", "Low", "Normal", "Medium", "High", "Very High"];

// Helper to get color class based on importance for the badge UI
const getImportanceClass = (level) => {
if (level >= 4) return 'bc-red'; // High / Very High
if (level >= 2) return 'bc-gold'; // Normal / Medium
return 'bc-green'; // Low
};

return (
<div className={`row py-5 underline ${props.item.deleted ? ' bc-red' : props.item.done ? ' bc-green' : ''}`} key={props.item.id}>
<div className={`row py-5 underline ${props.item.deleted ? ' bc-red' : props.item.done ? ' bc-green' : ''}`} key={props.item.id}>
<div className="column id">{props.item.id}</div>
<div className="column title">{props.item.title}</div>

{/* Added <b> tag for a more prominent Title */}
<div className="column title"><b>{props.item.title}</b></div>

<div className="column description">{props.item.description}</div>
<div className={`column importance ${props.item.levelOfImportance === 0 ? ' bc-green' :
props.item.levelOfImportance === 4 ? ' bc-gold' : props.item.levelOfImportance === 5 ? ' bc-red' : ''}`}>
{levelOfImportance[props.item.levelOfImportance]}</div>

<div className="column importance">
{/* Wrapped in a span with 'badge' class for a professional UI look */}
<span className={`badge ${getImportanceClass(props.item.levelOfImportance)}`}>
{levelOfImportance[props.item.levelOfImportance]}
</span>
</div>

<div className="column date">{props.item.date.split("T")[0]}</div>
<div className="column time">{props.item.time}</div>
<div className="column addr">{props.item.address}</div>
<div className="column edit">
<div className="btn edit" onClick={()=> handlingEdit(props.item)}>Edit</div>
<div className="btn edit" onClick={() => handlingEdit(props.item)}>Edit</div>
</div>
<div className={`column delete ${props.item.deleted ? ' not-allowed' : ''}`}>
<div className={`btn delete ${props.item.deleted ? ' no-event' : ''}`} onClick={()=> handlingDelete(props.item.id)}>Delete</div>

<div className={`column delete ${props.item.deleted ? ' not-allowed' : ''}`}>
<div className={`btn delete ${props.item.deleted ? ' no-event' : ''}`} onClick={() => handlingDelete(props.item.id)}>Delete</div>
</div>
</div>
)
);
}
43 changes: 42 additions & 1 deletion AppointmentsManager/ClientApp/src/components/Home.js
Original file line number Diff line number Diff line change
Expand Up @@ -9,10 +9,13 @@ import { getDefault, openModal, filter, getAppointments, notifyUser } from "./Li
export default function Home(props) {

const [dataList, setDataList] = useState([])

const [refreshData, setRefreshData] = useState(0)
const [stateListener, setStateListener] = useState(0)

// NEW STATE FOR SEARCH AND SORT
const [searchTerm, setSearchTerm] = useState("");
const [sortKey, setSortKey] = useState("default");

const filterApp = (e) => {
let name_ = e.target.name;
let v_ = e.target.value;
Expand Down Expand Up @@ -75,6 +78,18 @@ export default function Home(props) {
}).catch(e => console.log("Error getting data on filter: ", e))
}

// LOGIC TO PROCESS THE LIST
const processedList = dataList
.filter(item =>
item.title.toLowerCase().includes(searchTerm.toLowerCase()) ||
item.description.toLowerCase().includes(searchTerm.toLowerCase())
)
.sort((a, b) => {
if (sortKey === "importance") return b.levelOfImportance - a.levelOfImportance;
if (sortKey === "date") return new Date(a.date) - new Date(b.date);
return 0;
});


useEffect(() => {
getDefault().then(data => {
Expand All @@ -94,6 +109,26 @@ export default function Home(props) {
<section className="row justify-btw items-center filter">
<div className="modal-title">Filter</div>
<div className="row items-center filter-items">
{/* Contribution */}
<div className="me-15">
<label>Search</label> <br/>
<input
type="text"
placeholder="Search title..."
onChange={(e) => setSearchTerm(e.target.value)}
/>
</div>

{/* NEW SORT DROPDOWN */}
<div className="me-15">
<label>Sort By</label> <br/>
<select onChange={(e) => setSortKey(e.target.value)}>
<option value="default">None</option>
<option value="importance">Highest Importance</option>
<option value="date">Earliest Date</option>
</select>
</div>

<button className="me-15" onClick={()=> window.location.reload()}>Clear Filters</button>
<div>
<label htmlFor="All_f">All</label> <br />
Expand Down Expand Up @@ -178,6 +213,12 @@ export default function Home(props) {
<Delete stateListener={stateListener} refreshApp={setRefreshData} />
</section>
</section>
{/* UPDATE THE MAPPING TO USE processedList */}
{
processedList.length === 0 ?
<div className="row mt-15 waiting">No matches found <div className="loading">...</div></div> :
processedList.map(item => <Appointment item={item} key={item.id} stateListener={setStateListener} />)
}
</main>
)
}
21 changes: 21 additions & 0 deletions AppointmentsManager/ClientApp/src/custom.css
Original file line number Diff line number Diff line change
Expand Up @@ -277,6 +277,27 @@ input[type="checkbox"] {
overflow: hidden;
}

/* Badge styling for importance */
.badge {
padding: 4px 10px;
border-radius: 12px;
font-size: 12px;
font-weight: bold;
color: white;
}

/* Specific Importance Colors */
.bc-red { background-color: #ff4d4d !important; }
.bc-gold { background-color: #ffcc00 !important; color: #333; }
.bc-green { background-color: #2ecc71 !important; }

/* Styling for the search input in the filter bar */
.filter-items input[type="text"] {
padding: 5px;
border: 1px solid #ccc;
border-radius: 4px;
}

.hidden {
display: none;
}
Expand Down
2 changes: 1 addition & 1 deletion AppointmentsManager/appsettings.json
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,6 @@
},
"AllowedHosts": "*",
"ConnectionStrings": {
"DefaultConnection": "Data Source=YourMachineName\\SQL_InstanceName;Database=WebApiReact;Integrated Security=True;Connect Timeout=30;Encrypt=False;Trust Server Certificate=False;Application Intent=ReadWrite;Multi Subnet Failover=False"
"DefaultConnection": "DataSource=app.db;Cache=Shared"
}
}