You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 

283 lines
19 KiB

{% load i18n %}
{% load unfold %}
{% component "unfold/components/container.html" with component_class="CourseAnalyticsComponent" %}
<!-- Analytics Dashboard Header -->
<div class="flex justify-between items-center mb-8">
<div>
{% component "unfold/components/title.html" with class="text-2xl font-bold text-gray-800" %}
{% trans "Course Analytics Dashboard" %}
{% endcomponent %}
{% component "unfold/components/text.html" with class="text-sm text-gray-600" %}
{% trans "Comprehensive analytics and insights for your course" %}
{% endcomponent %}
</div>
<div class="flex space-x-2">
<button class="bg-white border border-gray-300 hover:bg-gray-50 text-gray-700 px-4 py-2 rounded-lg text-sm font-medium flex items-center shadow-sm transition-all duration-200">
<svg xmlns="http://www.w3.org/2000/svg" class="h-4 w-4 mr-2" fill="none" viewBox="0 0 24 24" stroke="currentColor">
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M4 16v1a3 3 0 003 3h10a3 3 0 003-3v-1m-4-4l-4 4m0 0l-4-4m4 4V4" />
</svg>
{% trans "Export" %}
</button>
<button class="bg-blue-600 hover:bg-blue-700 text-white px-4 py-2 rounded-lg text-sm font-medium flex items-center shadow-sm transition-all duration-200">
<svg xmlns="http://www.w3.org/2000/svg" class="h-4 w-4 mr-2" fill="none" viewBox="0 0 24 24" stroke="currentColor">
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M4 4v5h.582m15.356 2A8.001 8.001 0 004.582 9m0 0H9m11 11v-5h-.581m0 0a8.003 8.003 0 01-15.357-2m15.357 2H15" />
</svg>
{% trans "Refresh Data" %}
</button>
</div>
</div>
<!-- Basic Stats Cards -->
<div class="grid grid-cols-1 md:grid-cols-3 gap-6 mb-8">
<!-- Course Lessons Count -->
{% component "unfold/components/card.html" with class="bg-gradient-to-br from-blue-50 to-blue-100 border-none shadow-md hover:shadow-lg transition-all duration-300" %}
<div class="flex items-center p-2">
<div class="bg-gradient-to-br from-blue-500 to-blue-600 text-white rounded-xl p-4 mr-5 shadow-md">
<svg xmlns="http://www.w3.org/2000/svg" class="h-8 w-8" fill="none" viewBox="0 0 24 24" stroke="currentColor">
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M12 6.253v13m0-13C10.832 5.477 9.246 5 7.5 5S4.168 5.477 3 6.253v13C4.168 18.477 5.754 18 7.5 18s3.332.477 4.5 1.253m0-13C13.168 5.477 14.754 5 16.5 5c1.747 0 3.332.477 4.5 1.253v13C19.832 18.477 18.247 18 16.5 18c-1.746 0-3.332.477-4.5 1.253" />
</svg>
</div>
<div class="flex flex-col">
{% component "unfold/components/title.html" with class="text-4xl font-bold text-blue-700 m-0" %}
{{ total_lessons }}
{% endcomponent %}
{% component "unfold/components/text.html" with class="text-sm font-medium text-blue-800 mt-1 opacity-80" %}
{% trans "Total Lessons" %}
{% endcomponent %}
</div>
</div>
{% endcomponent %}
<!-- Course Quizzes Count -->
{% component "unfold/components/card.html" with class="bg-gradient-to-br from-purple-50 to-purple-100 border-none shadow-md hover:shadow-lg transition-all duration-300" %}
<div class="flex items-center p-2">
<div class="bg-gradient-to-br from-purple-500 to-purple-600 text-white rounded-xl p-4 mr-5 shadow-md">
<svg xmlns="http://www.w3.org/2000/svg" class="h-8 w-8" fill="none" viewBox="0 0 24 24" stroke="currentColor">
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-3 7h3m-3 4h3m-6-4h.01M9 16h.01" />
</svg>
</div>
<div class="flex flex-col">
{% component "unfold/components/title.html" with class="text-4xl font-bold text-purple-700 m-0" %}
{{ quiz_scores_data.data.datasets.0.data|length }}
{% endcomponent %}
{% component "unfold/components/text.html" with class="text-sm font-medium text-purple-800 mt-1 opacity-80" %}
{% trans "Total Quizzes" %}
{% endcomponent %}
</div>
</div>
{% endcomponent %}
<!-- Course Participants Count -->
{% component "unfold/components/card.html" with class="bg-gradient-to-br from-green-50 to-green-100 border-none shadow-md hover:shadow-lg transition-all duration-300" %}
<div class="flex items-center p-2">
<div class="bg-gradient-to-br from-green-500 to-green-600 text-white rounded-xl p-4 mr-5 shadow-md">
<svg xmlns="http://www.w3.org/2000/svg" class="h-8 w-8" fill="none" viewBox="0 0 24 24" stroke="currentColor">
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M12 4.354a4 4 0 110 5.292M15 21H3v-1a6 6 0 0112 0v1zm0 0h6v-1a6 6 0 00-9-5.197M13 7a4 4 0 11-8 0 4 4 0 018 0z" />
</svg>
</div>
<div class="flex flex-col">
{% component "unfold/components/title.html" with class="text-4xl font-bold text-green-700 m-0" %}
{{ total_participants }}
{% endcomponent %}
{% component "unfold/components/text.html" with class="text-sm font-medium text-green-800 mt-1 opacity-80" %}
{% trans "Active Participants" %}
{% endcomponent %}
</div>
</div>
{% endcomponent %}
</div>
<!-- Charts Section -->
<div class="grid grid-cols-1 md:grid-cols-2 gap-8 mb-8">
<!-- Lesson Completion Chart -->
{% component "unfold/components/card.html" with class="border border-gray-200 shadow-md hover:shadow-lg transition-all duration-300" %}
<div class="p-2">
{% component "unfold/components/title.html" with class="text-xl font-bold mb-2 text-gray-800" %}
{% trans "Lesson Completion Distribution" %}
{% endcomponent %}
{% component "unfold/components/text.html" with class="text-sm text-gray-600 mb-6" %}
{% trans "Percentage of course completion by participants" %}
{% endcomponent %}
<div class="bg-gray-50 p-4 rounded-lg">
{% component "unfold/components/chart/bar.html" with data=completion_data.data height=300 %}
{% endcomponent %}
</div>
</div>
{% endcomponent %}
<!-- Quiz Scores Chart -->
{% component "unfold/components/card.html" with class="border border-gray-200 shadow-md hover:shadow-lg transition-all duration-300" %}
<div class="p-2">
{% component "unfold/components/title.html" with class="text-xl font-bold mb-2 text-gray-800" %}
{% trans "Quiz Scores Distribution" %}
{% endcomponent %}
{% component "unfold/components/text.html" with class="text-sm text-gray-600 mb-6" %}
{% trans "Distribution of scores across all quizzes" %}
{% endcomponent %}
<div class="bg-gray-50 p-4 rounded-lg">
{% component "unfold/components/chart/bar.html" with data=quiz_scores_data.data height=300 %}
{% endcomponent %}
</div>
</div>
{% endcomponent %}
</div>
<!-- Progress Bars Section -->
<div class="grid grid-cols-1 gap-6 mb-8">
{% component "unfold/components/card.html" with class="border border-gray-200 shadow-md hover:shadow-lg transition-all duration-300" %}
<div class="p-4">
{% component "unfold/components/title.html" with class="text-xl font-bold mb-6 text-gray-800" %}
{% trans "Course Engagement Metrics" %}
{% endcomponent %}
<div class="grid grid-cols-1 md:grid-cols-3 gap-8">
<!-- Lesson Completion Rate -->
<div class="bg-blue-50 p-4 rounded-lg border border-blue-100">
<div class="flex justify-between items-center mb-2">
<span class="text-sm font-medium text-blue-800">{% trans "Lesson Completion Rate" %}</span>
<span class="text-xl font-bold text-blue-700">{{ engagement_metrics.lesson_completion_rate }}%</span>
</div>
{% component "unfold/components/progress.html" with value=engagement_metrics.lesson_completion_rate class="h-2 bg-blue-200" bar_class="bg-blue-600" %}
{% endcomponent %}
<p class="text-xs text-blue-700 mt-2">{% trans "Average percentage of lessons completed by participants" %}</p>
</div>
<!-- Quiz Participation Rate -->
<div class="bg-purple-50 p-4 rounded-lg border border-purple-100">
<div class="flex justify-between items-center mb-2">
<span class="text-sm font-medium text-purple-800">{% trans "Quiz Participation Rate" %}</span>
<span class="text-xl font-bold text-purple-700">{{ engagement_metrics.quiz_participation_rate }}%</span>
</div>
{% component "unfold/components/progress.html" with value=engagement_metrics.quiz_participation_rate class="h-2 bg-purple-200" bar_class="bg-purple-600" %}
{% endcomponent %}
<p class="text-xs text-purple-700 mt-2">{% trans "Percentage of participants who attempted at least one quiz" %}</p>
</div>
<!-- Average Quiz Score -->
<div class="bg-green-50 p-4 rounded-lg border border-green-100">
<div class="flex justify-between items-center mb-2">
<span class="text-sm font-medium text-green-800">{% trans "Average Quiz Score" %}</span>
<span class="text-xl font-bold text-green-700">{{ engagement_metrics.average_quiz_score }}%</span>
</div>
{% component "unfold/components/progress.html" with value=engagement_metrics.average_quiz_score class="h-2 bg-green-200" bar_class="bg-green-600" %}
{% endcomponent %}
<p class="text-xs text-green-700 mt-2">{% trans "Average score across all quizzes" %}</p>
</div>
</div>
</div>
{% endcomponent %}
</div>
<!-- Additional Insights Section -->
<div class="grid grid-cols-1 md:grid-cols-2 gap-8 mb-8">
<!-- Top Performing Students -->
{% component "unfold/components/card.html" with class="border border-gray-200 shadow-md hover:shadow-lg transition-all duration-300" %}
<div class="p-4">
{% component "unfold/components/title.html" with class="text-xl font-bold mb-4 text-gray-800" %}
{% trans "Top Performing Students" %}
{% endcomponent %}
<div class="overflow-hidden">
<table class="min-w-full divide-y divide-gray-200">
<thead class="bg-gray-50">
<tr>
<th scope="col" class="px-6 py-3 text-left text-xs font-medium text-gray-500 uppercase tracking-wider">
{% trans "Student" %}
</th>
<th scope="col" class="px-6 py-3 text-left text-xs font-medium text-gray-500 uppercase tracking-wider">
{% trans "Completion" %}
</th>
<th scope="col" class="px-6 py-3 text-left text-xs font-medium text-gray-500 uppercase tracking-wider">
{% trans "Avg. Score" %}
</th>
</tr>
</thead>
<tbody class="bg-white divide-y divide-gray-200">
{% for student in top_students %}
<tr>
<td class="px-6 py-4 whitespace-nowrap">
<div class="flex items-center">
<div class="flex-shrink-0 h-8 w-8 bg-{{ student.color }}-100 rounded-full flex items-center justify-center">
<span class="text-{{ student.color }}-600 font-medium">{{ student.initials }}</span>
</div>
<div class="ml-4">
<div class="text-sm font-medium text-gray-900">{{ student.name }}</div>
</div>
</div>
</td>
<td class="px-6 py-4 whitespace-nowrap">
<div class="text-sm text-gray-900">{{ student.completion_percentage }}%</div>
</td>
<td class="px-6 py-4 whitespace-nowrap">
<span class="px-2 inline-flex text-xs leading-5 font-semibold rounded-full bg-green-100 text-green-800">
{{ student.average_score }}%
</span>
</td>
</tr>
{% endfor %}
</tbody>
</table>
</div>
</div>
{% endcomponent %}
<!-- Recent Activity -->
{% component "unfold/components/card.html" with class="border border-gray-200 shadow-md hover:shadow-lg transition-all duration-300" %}
<div class="p-4">
{% component "unfold/components/title.html" with class="text-xl font-bold mb-4 text-gray-800" %}
{% trans "Recent Activity" %}
{% endcomponent %}
<div class="flow-root">
<ul role="list" class="-mb-8">
{% for activity in recent_activity %}
<li>
<div class="relative pb-8">
{% if not forloop.last %}
<span class="absolute top-5 left-5 -ml-px h-full w-0.5 bg-gray-200" aria-hidden="true"></span>
{% endif %}
<div class="relative flex items-start space-x-3">
<div class="relative">
<div class="h-10 w-10 rounded-full bg-{{ activity.color }}-500 flex items-center justify-center ring-8 ring-white">
{% if activity.type == 'lesson_completion' %}
<svg xmlns="http://www.w3.org/2000/svg" class="h-5 w-5 text-white" fill="none" viewBox="0 0 24 24" stroke="currentColor">
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M9 12l2 2 4-4m6 2a9 9 0 11-18 0 9 9 0 0118 0z" />
</svg>
{% elif activity.type == 'quiz_completion' %}
<svg xmlns="http://www.w3.org/2000/svg" class="h-5 w-5 text-white" fill="none" viewBox="0 0 24 24" stroke="currentColor">
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M11 5H6a2 2 0 00-2 2v11a2 2 0 002 2h11a2 2 0 002-2v-5m-1.414-9.414a2 2 0 112.828 2.828L11.828 15H9v-2.828l8.586-8.586z" />
</svg>
{% elif activity.type == 'course_join' %}
<svg xmlns="http://www.w3.org/2000/svg" class="h-5 w-5 text-white" fill="none" viewBox="0 0 24 24" stroke="currentColor">
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M12 8v4l3 3m6-3a9 9 0 11-18 0 9 9 0 0118 0z" />
</svg>
{% endif %}
</div>
</div>
<div class="min-w-0 flex-1 py-1.5">
<div class="text-sm text-gray-500">
{% if activity.type == 'lesson_completion' %}
<span class="font-medium text-gray-900">{{ activity.student_name }}</span> درس
<span class="font-medium text-gray-900">{{ activity.lesson_title }}</span> را تکمیل کرد
<span class="whitespace-nowrap text-xs">{{ activity.time_ago }}</span>
{% elif activity.type == 'quiz_completion' %}
<span class="font-medium text-gray-900">{{ activity.student_name }}</span> در کوئیز
<span class="font-medium text-gray-900">{{ activity.quiz_title }}</span> نمره {{ activity.score }}% کسب کرد
<span class="whitespace-nowrap text-xs">{{ activity.time_ago }}</span>
{% elif activity.type == 'course_join' %}
<span class="font-medium text-gray-900">{{ activity.student_name }}</span> به دوره پیوست
<span class="whitespace-nowrap text-xs">{{ activity.time_ago }}</span>
{% endif %}
</div>
</div>
</div>
</div>
</li>
{% endfor %}
</ul>
</div>
</div>
{% endcomponent %}
</div>
{% endcomponent %}