467 lines
20 KiB
HTML
467 lines
20 KiB
HTML
{% extends "base.html" %}
|
|
{% load static %}
|
|
|
|
{% block title %}{{ employee.get_full_name }} - Employee Details - {{ block.super }}{% endblock %}
|
|
|
|
{% block content %}
|
|
<div class="container-fluid">
|
|
<!-- Page Header -->
|
|
<div class="d-flex justify-content-between align-items-center mb-4">
|
|
<div>
|
|
<h1 class="h3 mb-1">
|
|
<i class="fas fa-user me-2"></i>{{ employee.get_full_name }}
|
|
</h1>
|
|
<nav aria-label="breadcrumb">
|
|
<ol class="breadcrumb mb-0">
|
|
<li class="breadcrumb-item"><a href="{% url 'hr:dashboard' %}">HR</a></li>
|
|
<li class="breadcrumb-item"><a href="{% url 'hr:employee_list' %}">Employees</a></li>
|
|
<li class="breadcrumb-item active">{{ employee.get_full_name }}</li>
|
|
</ol>
|
|
</nav>
|
|
</div>
|
|
<div class="btn-group">
|
|
<a href="{% url 'hr:employee_list' %}" class="btn btn-outline-secondary">
|
|
<i class="fas fa-arrow-left me-2"></i>Back to List
|
|
</a>
|
|
<div class="btn-group">
|
|
<button type="button" class="btn btn-outline-secondary dropdown-toggle" data-bs-toggle="dropdown">
|
|
<i class="fas fa-cog me-2"></i>Actions
|
|
</button>
|
|
<ul class="dropdown-menu">
|
|
<li><a class="dropdown-item" href="{% url 'hr:employee_update' employee.pk %}">
|
|
<i class="fas fa-edit me-2"></i>Edit Employee
|
|
</a></li>
|
|
<li><a class="dropdown-item" href="#">
|
|
<i class="fas fa-clock me-2"></i>View Schedule
|
|
</a></li>
|
|
<li><a class="dropdown-item" href="#">
|
|
<i class="fas fa-chart-line me-2"></i>Performance Review
|
|
</a></li>
|
|
<li><a class="dropdown-item" href="#">
|
|
<i class="fas fa-graduation-cap me-2"></i>Training Records
|
|
</a></li>
|
|
<li><hr class="dropdown-divider"></li>
|
|
<li><a class="dropdown-item" href="#">
|
|
<i class="fas fa-print me-2"></i>Print Profile
|
|
</a></li>
|
|
<li><a class="dropdown-item text-danger" href="{% url 'hr:employee_delete' employee.pk %}">
|
|
<i class="fas fa-trash me-2"></i>Delete Employee
|
|
</a></li>
|
|
</ul>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
|
|
<div class="row">
|
|
<!-- Main Content -->
|
|
<div class="col-lg-8">
|
|
<!-- Employee Information -->
|
|
<div class="panel panel-inverse">
|
|
<div class="panel-heading">
|
|
<h4 class="panel-title"><i class="fa fa-user-alt me-2 "></i>Employee Details</h4>
|
|
<div class="panel-heading-btn">
|
|
<a href="javascript:;" class="btn btn-xs btn-icon btn-default" data-toggle="panel-expand"><i class="fa fa-expand"></i></a>
|
|
<a href="javascript:;" class="btn btn-xs btn-icon btn-success" data-toggle="panel-reload"><i class="fa fa-redo"></i></a>
|
|
<a href="javascript:;" class="btn btn-xs btn-icon btn-warning" data-toggle="panel-collapse"><i class="fa fa-minus"></i></a>
|
|
</div>
|
|
</div>
|
|
|
|
<div class="panel-body">
|
|
<div class="card mb-4">
|
|
<div class="card-header">
|
|
<h5 class="mb-0">
|
|
<i class="fas fa-id-card me-2"></i>Employee Information
|
|
</h5>
|
|
</div>
|
|
<div class="card-body">
|
|
<div class="row">
|
|
<div class="col-md-6">
|
|
<dl class="row">
|
|
<dt class="col-sm-4">Employee ID:</dt>
|
|
<dd class="col-sm-8">
|
|
<span class="font-monospace">{{ employee.employee_number }}</span>
|
|
</dd>
|
|
|
|
<dt class="col-sm-4">Full Name:</dt>
|
|
<dd class="col-sm-8">
|
|
<strong>{{ employee.get_full_name }}</strong>
|
|
{% if employee.preferred_name %}
|
|
<br><small class="text-muted">Preferred: {{ employee.preferred_name }}</small>
|
|
{% endif %}
|
|
</dd>
|
|
|
|
<dt class="col-sm-4">Department:</dt>
|
|
<dd class="col-sm-8">
|
|
{% if employee.department %}
|
|
<span class="badge bg-info">{{ employee.department.name }}</span>
|
|
{% else %}
|
|
<span class="text-muted">Not assigned</span>
|
|
{% endif %}
|
|
</dd>
|
|
|
|
<dt class="col-sm-4">Job Title:</dt>
|
|
<dd class="col-sm-8">{{ employee.job_title|default:"Not specified" }}</dd>
|
|
</dl>
|
|
</div>
|
|
<div class="col-md-6">
|
|
<dl class="row">
|
|
<dt class="col-sm-4">Hire Date:</dt>
|
|
<dd class="col-sm-8">
|
|
{{ employee.hire_date|date:"M d, Y" }}
|
|
<br><small class="text-muted">{{ employee.hire_date|timesince }} ago</small>
|
|
</dd>
|
|
|
|
<dt class="col-sm-4">Employment Status:</dt>
|
|
<dd class="col-sm-8">
|
|
<span class="badge bg-{% if employee.employment_status == 'ACTIVE' %}success{% elif employee.employment_status == 'INACTIVE' %}secondary{% elif employee.employment_status == 'TERMINATED' %}danger{% elif employee.employment_status == 'ON_LEAVE' %}warning{% else %}secondary{% endif %}">
|
|
{{ employee.get_employment_status_display }}
|
|
</span>
|
|
</dd>
|
|
|
|
<dt class="col-sm-4">Employment Type:</dt>
|
|
<dd class="col-sm-8">{{ employee.get_employment_type_display|default:"Not specified" }}</dd>
|
|
|
|
<dt class="col-sm-4">Supervisor:</dt>
|
|
<dd class="col-sm-8">
|
|
{% if employee.supervisor %}
|
|
<a href="{% url 'hr:employee_detail' employee.supervisor.pk %}">
|
|
{{ employee.supervisor.get_full_name }}
|
|
</a>
|
|
{% else %}
|
|
<span class="text-muted">No supervisor assigned</span>
|
|
{% endif %}
|
|
</dd>
|
|
</dl>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
|
|
<!-- Contact Information -->
|
|
<div class="card mb-4">
|
|
<div class="card-header">
|
|
<h5 class="mb-0">
|
|
<i class="fas fa-address-book me-2"></i>Contact Information
|
|
</h5>
|
|
</div>
|
|
<div class="card-body">
|
|
<div class="row">
|
|
<div class="col-md-6">
|
|
<dl class="row">
|
|
<dt class="col-sm-4">Email:</dt>
|
|
<dd class="col-sm-8">
|
|
{% if employee.email %}
|
|
<a href="mailto:{{ employee.email }}">{{ employee.email }}</a>
|
|
{% else %}
|
|
<span class="text-muted">Not provided</span>
|
|
{% endif %}
|
|
</dd>
|
|
|
|
<dt class="col-sm-4">Phone:</dt>
|
|
<dd class="col-sm-8">
|
|
{% if employee.phone %}
|
|
<a href="tel:{{ employee.phone }}">{{ employee.phone }}</a>
|
|
{% else %}
|
|
<span class="text-muted">Not provided</span>
|
|
{% endif %}
|
|
</dd>
|
|
|
|
<dt class="col-sm-4">Mobile:</dt>
|
|
<dd class="col-sm-8">
|
|
{% if employee.mobile_phone %}
|
|
<a href="tel:{{ employee.mobile_phone }}">{{ employee.mobile_phone }}</a>
|
|
{% else %}
|
|
<span class="text-muted">Not provided</span>
|
|
{% endif %}
|
|
</dd>
|
|
</dl>
|
|
</div>
|
|
<div class="col-md-6">
|
|
<dl class="row">
|
|
<dt class="col-sm-4">Address:</dt>
|
|
<dd class="col-sm-8">
|
|
{% if employee.address_line_1 %}
|
|
{{ employee.address_line_1 }}<br>
|
|
{% if employee.address_line_2 %}{{ employee.address_line_2 }}<br>{% endif %}
|
|
{% if employee.city %}{{ employee.city }}, {% endif %}
|
|
{% if employee.state %}{{ employee.state }} {% endif %}
|
|
{% if employee.postal_code %}{{ employee.postal_code }}{% endif %}
|
|
{% if employee.country %}<br>{{ employee.country }}{% endif %}
|
|
{% else %}
|
|
<span class="text-muted">Not provided</span>
|
|
{% endif %}
|
|
</dd>
|
|
</dl>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
|
|
<!-- Emergency Contact -->
|
|
{% if employee.emergency_contact_name %}
|
|
<div class="card mb-4">
|
|
<div class="card-header">
|
|
<h5 class="mb-0">
|
|
<i class="fas fa-exclamation-triangle me-2"></i>Emergency Contact
|
|
</h5>
|
|
</div>
|
|
<div class="card-body">
|
|
<div class="row">
|
|
<div class="col-md-6">
|
|
<dl class="row">
|
|
<dt class="col-sm-4">Name:</dt>
|
|
<dd class="col-sm-8">{{ employee.emergency_contact_name }}</dd>
|
|
|
|
<dt class="col-sm-4">Relationship:</dt>
|
|
<dd class="col-sm-8">{{ employee.emergency_contact_relationship|default:"Not specified" }}</dd>
|
|
</dl>
|
|
</div>
|
|
<div class="col-md-6">
|
|
<dl class="row">
|
|
<dt class="col-sm-4">Phone:</dt>
|
|
<dd class="col-sm-8">
|
|
{% if employee.emergency_contact_phone %}
|
|
<a href="tel:{{ employee.emergency_contact_phone }}">{{ employee.emergency_contact_phone }}</a>
|
|
{% else %}
|
|
<span class="text-muted">Not provided</span>
|
|
{% endif %}
|
|
</dd>
|
|
</dl>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
{% endif %}
|
|
|
|
<!-- Recent Activity -->
|
|
<div class="card">
|
|
<div class="card-header">
|
|
<h5 class="mb-0">
|
|
<i class="fas fa-history me-2"></i>Recent Activity
|
|
</h5>
|
|
</div>
|
|
<div class="card-body">
|
|
<div class="timeline">
|
|
<div class="timeline-item">
|
|
<div class="timeline-marker bg-primary"></div>
|
|
<div class="timeline-content">
|
|
<h6 class="timeline-title">Employee profile updated</h6>
|
|
<p class="timeline-text">Contact information updated</p>
|
|
<small class="text-muted">{{ employee.updated_at|timesince }} ago</small>
|
|
</div>
|
|
</div>
|
|
<div class="timeline-item">
|
|
<div class="timeline-marker bg-success"></div>
|
|
<div class="timeline-content">
|
|
<h6 class="timeline-title">Employee hired</h6>
|
|
<p class="timeline-text">Joined {{ employee.department.name|default:"the organization" }}</p>
|
|
<small class="text-muted">{{ employee.hire_date|timesince }} ago</small>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
<!-- Sidebar -->
|
|
<div class="col-lg-4">
|
|
<!-- Employee Photo -->
|
|
<div class="card mb-4">
|
|
<div class="card-body text-center">
|
|
<div class="avatar-lg bg-primary bg-gradient rounded-circle d-inline-flex align-items-center justify-content-center mb-3" style="width: 120px; height: 120px;">
|
|
<span class="text-white h2 mb-0">
|
|
{{ employee.first_name.0 }}{{ employee.last_name.0 }}
|
|
</span>
|
|
</div>
|
|
<h5 class="mb-1">{{ employee.get_full_name }}</h5>
|
|
<p class="text-muted mb-3">{{ employee.job_title|default:"Employee" }}</p>
|
|
<div class="d-grid gap-2">
|
|
<a href="{% url 'hr:employee_update' employee.pk %}" class="btn btn-primary">
|
|
<i class="fas fa-edit me-2"></i>Edit Profile
|
|
</a>
|
|
<button type="button" class="btn btn-outline-secondary" onclick="sendMessage()">
|
|
<i class="fas fa-envelope me-2"></i>Send Message
|
|
</button>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
|
|
<!-- Quick Stats -->
|
|
<div class="card mb-4">
|
|
<div class="card-header">
|
|
<h5 class="mb-0">
|
|
<i class="fas fa-chart-bar me-2"></i>Quick Stats
|
|
</h5>
|
|
</div>
|
|
<div class="card-body">
|
|
<div class="d-flex justify-content-between align-items-center mb-3">
|
|
<span class="text-muted">Years of Service</span>
|
|
<span class="badge bg-primary">{{ employee.years_of_service|floatformat:1 }}</span>
|
|
</div>
|
|
<div class="d-flex justify-content-between align-items-center mb-3">
|
|
<span class="text-muted">Performance Reviews</span>
|
|
<span class="badge bg-success">{{ employee.performance_reviews.count }}</span>
|
|
</div>
|
|
<div class="d-flex justify-content-between align-items-center mb-3">
|
|
<span class="text-muted">Training Completed</span>
|
|
<span class="badge bg-info">{{ employee.training_records.count }}</span>
|
|
</div>
|
|
<div class="d-flex justify-content-between align-items-center">
|
|
<span class="text-muted">Direct Reports</span>
|
|
<span class="badge bg-warning">{{ employee.direct_reports.count }}</span>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
|
|
<!-- Quick Actions -->
|
|
<div class="card">
|
|
<div class="card-header">
|
|
<h5 class="mb-0">
|
|
<i class="fas fa-bolt me-2"></i>Quick Actions
|
|
</h5>
|
|
</div>
|
|
<div class="card-body">
|
|
<div class="d-grid gap-2">
|
|
<a href="#" class="btn btn-outline-primary">
|
|
<i class="fas fa-clock me-2"></i>View Schedule
|
|
</a>
|
|
<a href="#" class="btn btn-outline-success">
|
|
<i class="fas fa-chart-line me-2"></i>Performance Review
|
|
</a>
|
|
<a href="#" class="btn btn-outline-info">
|
|
<i class="fas fa-graduation-cap me-2"></i>Training Records
|
|
</a>
|
|
<a href="#" class="btn btn-outline-warning">
|
|
<i class="fas fa-calendar-alt me-2"></i>Time Off Requests
|
|
</a>
|
|
<button type="button" class="btn btn-outline-secondary" onclick="printProfile()">
|
|
<i class="fas fa-print me-2"></i>Print Profile
|
|
</button>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
|
|
<script>
|
|
function sendMessage() {
|
|
// Implementation would depend on your messaging system
|
|
alert('Message functionality would be implemented here');
|
|
}
|
|
|
|
function printProfile() {
|
|
window.print();
|
|
}
|
|
|
|
// Auto-refresh stats every 5 minutes
|
|
setInterval(function() {
|
|
// Refresh quick stats if needed
|
|
}, 300000);
|
|
</script>
|
|
|
|
<style>
|
|
.avatar-lg {
|
|
width: 120px;
|
|
height: 120px;
|
|
font-size: 2rem;
|
|
}
|
|
|
|
.bg-gradient {
|
|
background-image: linear-gradient(180deg, rgba(255, 255, 255, 0.15), rgba(255, 255, 255, 0));
|
|
}
|
|
|
|
.font-monospace {
|
|
font-family: 'Courier New', monospace;
|
|
font-size: 0.9rem;
|
|
}
|
|
|
|
dl.row dt {
|
|
font-weight: 600;
|
|
color: #495057;
|
|
}
|
|
|
|
dl.row dd {
|
|
color: #6c757d;
|
|
}
|
|
|
|
.timeline {
|
|
position: relative;
|
|
padding-left: 1.5rem;
|
|
}
|
|
|
|
.timeline-item {
|
|
position: relative;
|
|
padding-bottom: 1.5rem;
|
|
}
|
|
|
|
.timeline-item:not(:last-child)::before {
|
|
content: '';
|
|
position: absolute;
|
|
left: -1.5rem;
|
|
top: 1rem;
|
|
width: 2px;
|
|
height: calc(100% - 0.5rem);
|
|
background-color: #dee2e6;
|
|
}
|
|
|
|
.timeline-marker {
|
|
position: absolute;
|
|
left: -1.75rem;
|
|
top: 0.25rem;
|
|
width: 0.5rem;
|
|
height: 0.5rem;
|
|
border-radius: 50%;
|
|
}
|
|
|
|
.timeline-content {
|
|
margin-left: 0.5rem;
|
|
}
|
|
|
|
.timeline-title {
|
|
font-size: 0.875rem;
|
|
font-weight: 600;
|
|
margin-bottom: 0.25rem;
|
|
}
|
|
|
|
.timeline-text {
|
|
font-size: 0.8rem;
|
|
color: #6c757d;
|
|
margin-bottom: 0.25rem;
|
|
}
|
|
|
|
@media print {
|
|
.btn-group,
|
|
.card:last-child {
|
|
display: none !important;
|
|
}
|
|
|
|
.container-fluid {
|
|
padding: 0 !important;
|
|
}
|
|
|
|
.card {
|
|
border: 1px solid #000 !important;
|
|
break-inside: avoid;
|
|
}
|
|
}
|
|
|
|
@media (max-width: 768px) {
|
|
.timeline {
|
|
padding-left: 1rem;
|
|
}
|
|
|
|
.timeline-marker {
|
|
left: -1.25rem;
|
|
}
|
|
|
|
.d-flex.justify-content-between {
|
|
flex-direction: column;
|
|
gap: 1rem;
|
|
}
|
|
}
|
|
</style>
|
|
{% endblock %}
|
|
|