Social: Improve skill wheel and reporting

pull/5179/head
christianbeeznst 2 years ago
parent 40a262c830
commit 01e61e528e
  1. 205
      assets/css/app.scss
  2. 1
      assets/css/scss/index.scss
  3. 4
      assets/vue/components/social/MySkillsCard.vue
  4. 4
      public/main/inc/lib/SkillModel.php
  5. 41
      public/main/inc/lib/api.lib.php
  6. 6
      public/main/inc/lib/usermanager.lib.php
  7. 18
      public/main/social/skills_ranking.php
  8. 2
      public/main/social/skills_wheel.php
  9. 95
      public/main/template/default/skill/skill_wheel_student.html.twig

@ -255,211 +255,6 @@
text-decoration: underline; text-decoration: underline;
} }
#skillList .header-title{
padding: 8px;
border-bottom: 2px solid #ddd;
font-weight: bold;
margin-bottom: 15px;
}
.skills-badges{
display: grid;
grid-gap: 1rem;
grid-row-gap: 16px;
grid-template-columns: repeat(6, 1fr);
}
.skills-badges .item{
display: inline-block;
width: 100%;
text-align: center;
justify-content: center;
align-items: center;
}
.skills-badges a .caption{
text-align: center;
}
.list-horizontal .list-skills{
display: grid;
grid-gap: 1rem;
grid-row-gap: 16px;
grid-template-columns: repeat(4, 1fr);
}
.list-vertical .list-skills{
display: grid;
grid-gap: 1rem;
grid-row-gap: 16px;
grid-template-columns: repeat(2, 1fr);
}
.list-skills .item{
display: inline-block;
width: 100%;
text-align: center;
justify-content: center;
align-items: center;
}
.skill-options .legend {
border: 1px dashed #cccccc;
padding: 1em;
-webkit-border-radius: 10px;
-moz-border-radius: 10px;
border-radius: 10px;
margin-bottom: 1em;
margin-top: 1em;
background-color: #FFFFFF;
}
.skill-options .skill-home {
margin-top: 1em;
margin-bottom: 1em;
}
.skill-options .btn-block {
box-sizing: border-box;
display: block;
padding-left: 0;
padding-right: 0;
width: 100%;
}
.skill-options .accordion-inner {
padding: 9px 15px;
/*border: 1px solid #dadada;*/
background-color: #FFFFFF;
}
.skill-options .load_wheel {
}
.skill-options .skill-winner {
list-style: none;
margin: 0;
padding: 0;
}
.skill-options .skill-winner li {
float: left;
margin-right: 1em;
padding-bottom: 1em;
}
.skill-options .skill-winner li a {
/*background: url("/main/img/icons/16/winner.png") no-repeat;*/
padding-left: 1.5em;
padding-bottom: 1em;
}
.search-skill ul.holder li.bit-input input {
width: 100%;
}
.skill-legend-basic {
color: #3A87AD;
}
.skill-legend-add {
color: #F89406;
}
.skill-legend-search {
color: #B94A48;
}
.skill-legend-badges {
color: #31A354;
}
.page-skill .panel-default {
border-color: #DDDDDD;
}
.page-skill .btn-default {
background-color: #F6F6F6;
}
.page-skill .btn-default:hover {
background-color: #E6E6E6;
}
.page-skill #skill_info {
font-size: 12px;
}
.page-skill #skill_wheel tspan {
font-size: 12px;
}
.page-skill .holder_simple li.bit-box a {
color: #8A6D3B;
}
.skill_partition {
cursor: pointer;
stroke: #000000;
stroke-width: 0.5px;
}
.items-user .avatar-user {
text-align: center;
margin-bottom: 10px;
}
.items-user p {
font-size: 12px;
margin-bottom: 5px;
}
.items-user .list-group {
font-size: 12px;
}
table#skill_holder {
margin-top: 15px;
}
.badges-sidebar {
height: 250px;
}
.panel figure figcaption {
background: none;
text-align: center;
}
.skill_root {
box-shadow: 2px 2px 19px #aaa;
border-radius: 6px;
background-color: #ccc;
border: 0.1em dotted #D4E06B;
color: black;
font-size: 0.9em;
height: 4em;
opacity: 0.8;
padding-top: 0.9em;
text-align: center;
width: 120px;
z-index: 40;
position: relative;
}
.skill_child {
box-shadow: 2px 2px 19px #aaa;
border-radius: 6px;
background-color: white;
border: 0.1em dotted #D4E06B;
color: black;
font-size: 0.9em;
height: 4em;
opacity: 0.8;
padding-top: 0.9em;
text-align: center;
width: 120px;
z-index: 40;
float: left;
margin-left: 20px;
margin-bottom: 20px;
margin-top: 10px;
position: relative;
}
.category-forum .custom-panel-group { .category-forum .custom-panel-group {
width: 100%; width: 100%;
} }

@ -72,3 +72,4 @@
@import 'lp'; @import 'lp';
@import "userreluser"; @import "userreluser";
@import 'social'; @import 'social';
@import 'skill';

@ -13,10 +13,10 @@
<div class="skill-name">{{ skill.name }}</div> <div class="skill-name">{{ skill.name }}</div>
</div> </div>
</div> </div>
<!--div class="skills-links mt-2"> <div class="skills-links mt-2">
<a href="/main/social/skills_wheel.php">{{ t('Skills Wheel') }}</a> | <a href="/main/social/skills_wheel.php">{{ t('Skills Wheel') }}</a> |
<a href="/main/social/skills_ranking.php">{{ t('Your skill ranking') }}</a> <a href="/main/social/skills_ranking.php">{{ t('Your skill ranking') }}</a>
</div--> </div>
</div> </div>
<div v-else> <div v-else>
<p>{{ t('Without achieved skills') }}</p> <p>{{ t('Without achieved skills') }}</p>

@ -1286,12 +1286,12 @@ class SkillModel extends Model
*/ */
public function getCountSkillsByCourse($courseCode) public function getCountSkillsByCourse($courseCode)
{ {
$courseCode = Database::escape_string($courseCode); $cid = api_get_course_int_id($courseCode);
$sql = "SELECT count(skill_id) as count $sql = "SELECT count(skill_id) as count
FROM {$this->table_gradebook} g FROM {$this->table_gradebook} g
INNER JOIN {$this->table_skill_rel_gradebook} sg INNER JOIN {$this->table_skill_rel_gradebook} sg
ON g.id = sg.gradebook_id ON g.id = sg.gradebook_id
WHERE course_code = '$courseCode'"; WHERE c_id = '$cid'";
$result = Database::query($sql); $result = Database::query($sql);
if (Database::num_rows($result)) { if (Database::num_rows($result)) {

@ -1334,6 +1334,47 @@ function _api_format_user($user, $add_password = false, $loadAvatars = true)
$result['avatar_no_query'] = ''; $result['avatar_no_query'] = '';
$result['avatar_small'] = ''; $result['avatar_small'] = '';
$result['avatar_medium'] = ''; $result['avatar_medium'] = '';
if (empty($user['avatar'])) {
$originalFile = UserManager::getUserPicture(
$user_id,
USER_IMAGE_SIZE_ORIGINAL,
null,
$result
);
$result['avatar'] = $originalFile;
$avatarString = explode('?', $result['avatar']);
$result['avatar_no_query'] = reset($avatarString);
} else {
$result['avatar'] = $user['avatar'];
$avatarString = explode('?', $user['avatar']);
$result['avatar_no_query'] = reset($avatarString);
}
if (!isset($user['avatar_small'])) {
$smallFile = UserManager::getUserPicture(
$user_id,
USER_IMAGE_SIZE_SMALL,
null,
$result
);
$result['avatar_small'] = $smallFile;
} else {
$result['avatar_small'] = $user['avatar_small'];
}
if (!isset($user['avatar_medium'])) {
$mediumFile = UserManager::getUserPicture(
$user_id,
USER_IMAGE_SIZE_MEDIUM,
null,
$result
);
$result['avatar_medium'] = $mediumFile;
} else {
$result['avatar_medium'] = $user['avatar_medium'];
}
$urlImg = api_get_path(WEB_IMG_PATH); $urlImg = api_get_path(WEB_IMG_PATH);
$iconStatus = ''; $iconStatus = '';
$iconStatusMedium = ''; $iconStatusMedium = '';

@ -2933,7 +2933,7 @@ class UserManager
$sessionLimitRestriction = "LIMIT $sessionLimit"; $sessionLimitRestriction = "LIMIT $sessionLimit";
} }
$sql = "SELECT DISTINCT s.id, name, access_start_date, access_end_date $sql = "SELECT DISTINCT s.id, s.title, access_start_date, access_end_date
FROM $tbl_session_user su INNER JOIN $tbl_session s FROM $tbl_session_user su INNER JOIN $tbl_session s
ON (s.id = su.session_id) ON (s.id = su.session_id)
WHERE ( WHERE (
@ -2941,7 +2941,7 @@ class UserManager
su.relation_type = ".SessionEntity::STUDENT." su.relation_type = ".SessionEntity::STUDENT."
) )
$coachCourseConditions $coachCourseConditions
ORDER BY access_start_date, access_end_date, name ORDER BY access_start_date, access_end_date, s.title
$sessionLimitRestriction $sessionLimitRestriction
"; ";
@ -3042,7 +3042,7 @@ class UserManager
access_start_date, access_start_date,
access_end_date, access_end_date,
session.id as session_id, session.id as session_id,
session.name as session_name, session.title as session_name,
IF((session_course_user.user_id = 3 AND session_course_user.status = ".SessionEntity::COURSE_COACH."),'2', '5') IF((session_course_user.user_id = 3 AND session_course_user.status = ".SessionEntity::COURSE_COACH."),'2', '5')
FROM $tbl_session_course_user as session_course_user FROM $tbl_session_course_user as session_course_user
INNER JOIN $tbl_course AS course INNER JOIN $tbl_course AS course

@ -33,52 +33,52 @@ $column_model = [
[ [
'name' => 'photo', 'name' => 'photo',
'index' => 'photo', 'index' => 'photo',
'width' => '10', 'width' => '150px',
'align' => 'center', 'align' => 'center',
'sortable' => 'false', 'sortable' => 'false',
], ],
[ [
'name' => 'firstname', 'name' => 'firstname',
'index' => 'firstname', 'index' => 'firstname',
'width' => '70', 'width' => '250px',
'align' => 'center', 'align' => 'center',
'sortable' => 'false', 'sortable' => 'false',
], ],
[ [
'name' => 'lastname', 'name' => 'lastname',
'index' => 'lastname', 'index' => 'lastname',
'width' => '70', 'width' => '250px',
'align' => 'center', 'align' => 'center',
'sortable' => 'false', 'sortable' => 'false',
], ],
[ [
'name' => 'skills_acquired', 'name' => 'skills_acquired',
'index' => 'skills_acquired', 'index' => 'skills_acquired',
'width' => '30 ', 'width' => '100px',
'align' => 'center', 'align' => 'center',
'sortable' => 'false', 'sortable' => 'false',
], ],
[ [
'name' => 'currently_learning', 'name' => 'currently_learning',
'index' => 'currently_learning', 'index' => 'currently_learning',
'width' => '30', 'width' => '150px',
'align' => 'center', 'align' => 'center',
'sortable' => 'false', 'sortable' => 'false',
], ],
[ [
'name' => 'rank', 'name' => 'rank',
'index' => 'rank', 'index' => 'rank',
'width' => '30', 'width' => '100px',
'align' => 'center', 'align' => 'center',
'sortable' => 'false', 'sortable' => 'false',
], ],
]; ];
//Autowidth //Autowidth
$extra_params['autowidth'] = 'true'; //$extra_params['autowidth'] = 'true';
//height auto //height auto
$extra_params['height'] = 'auto'; //$extra_params['height'] = 'auto';
//$extra_params['excel'] = 'excel'; //$extra_params['excel'] = 'excel';
//$extra_params['rowList'] = array(10, 20 ,30); //$extra_params['rowList'] = array(10, 20 ,30);
@ -87,7 +87,7 @@ $jqgrid = Display::grid_js(
$url, $url,
$columns, $columns,
$column_model, $column_model,
$extra_params, [],
[], [],
null, null,
true true

@ -21,7 +21,7 @@ $htmlHeadXtra[] = api_get_js('skills.js');
$tpl = new Template(null, false, false); $tpl = new Template(null, false, false);
$userId = api_get_user_id(); $userId = api_get_user_id();
$userInfo = api_get_user_info(); $userInfo = api_get_user_info($userId);
$skill = new SkillModel(); $skill = new SkillModel();
$ranking = $skill->getUserSkillRanking($userId); $ranking = $skill->getUserSkillRanking($userId);

@ -1,7 +1,59 @@
{% include '@ChamiloCore/Skill/skill_wheel.js.html.twig' %} {% include '@ChamiloCore/Skill/skill_wheel.js.html.twig' %}
{% autoescape false %} {% autoescape false %}
<script> <script>
/* Skill search input in the left menu */ document.addEventListener('DOMContentLoaded', function () {
var accordionLinks = document.querySelectorAll('[data-toggle="collapse"]');
accordionLinks.forEach(function(link) {
link.addEventListener('click', function(event) {
event.preventDefault();
var collapseTargetId = this.getAttribute('href');
var collapseTarget = document.querySelector(collapseTargetId);
if (collapseTarget.classList.contains('in')) {
collapseTarget.classList.remove('in');
} else {
var parentAccordionId = this.getAttribute('data-parent');
var parentAccordion = document.querySelector(parentAccordionId);
var allPanels = parentAccordion.querySelectorAll('.panel-collapse');
allPanels.forEach(function(panel) {
panel.classList.remove('in');
});
collapseTarget.classList.add('in');
}
});
});
var modalToggles = document.querySelectorAll('[data-toggle="modal"]');
modalToggles.forEach(function(toggle) {
toggle.addEventListener('click', function(e) {
e.preventDefault();
var target = document.querySelector(this.getAttribute('data-target'));
target.style.display = 'block';
setTimeout(function() {
target.classList.add('in');
}, 10);
});
});
var closeButtons = document.querySelectorAll('[data-dismiss="modal"], .modal .close');
closeButtons.forEach(function(button) {
button.addEventListener('click', function() {
var modal = this.closest('.modal');
modal.classList.remove('in');
setTimeout(function() {
modal.style.display = 'none';
}, 150);
});
});
});
/* Skill search input in the left menu */
function check_skills_sidebar() { function check_skills_sidebar() {
//Selecting only selected skills //Selecting only selected skills
$("#skill_id option:selected").each(function () { $("#skill_id option:selected").each(function () {
@ -10,12 +62,9 @@
$.ajax({ $.ajax({
url: "{{ url }}&a=skill_exists", url: "{{ url }}&a=skill_exists",
data: "skill_id=" + skill_id, data: "skill_id=" + skill_id,
// async: false,
success: function (return_value) { success: function (return_value) {
if (return_value == 0) { if (return_value == 0) {
alert("{{ 'SkillDoesNotExist'|trans }}"); alert("{{ 'SkillDoesNotExist'|trans }}");
//Deleting select option tag
//$("#skill_id option[value="+skill_id+"]").remove();
$("#skill_id").empty(); $("#skill_id").empty();
//Deleting holder //Deleting holder
@ -56,7 +105,7 @@
<td>' + skill_name + '</td>\n\ <td>' + skill_name + '</td>\n\
<td class="text-right">\n\ <td class="text-right">\n\
<button type="button" id="skill_to_select_id_' + skill_id + '" class="btn btn--warning btn-sm load_wheel" data-id="' + skill_id + '" title="{{ 'PlaceOnTheWheel'|trans }}" aria-label="{{ 'PlaceOnTheWheel'|trans }}">\n\ <button type="button" id="skill_to_select_id_' + skill_id + '" class="btn btn--warning btn-sm load_wheel" data-id="' + skill_id + '" title="{{ 'PlaceOnTheWheel'|trans }}" aria-label="{{ 'PlaceOnTheWheel'|trans }}">\n\
<span class="fa fa-crosshairs fa-fw" aria-hidden="true"></span>\n\ <span class="mdi mdi-crosshairs mdi-fw" aria-hidden="true"></span>\n\
</button>\n\ </button>\n\
</td>\n\ </td>\n\
</tr>'; </tr>';
@ -139,7 +188,7 @@
} }
}, },
cache: false, cache: false,
placeholder: '{{ 'EnterTheSkillNameToSearch'|trans }}' placeholder: '{{ 'Enter the skill name to search'|trans }}'
}).on('change', function () { }).on('change', function () {
check_skills_sidebar(); check_skills_sidebar();
}); });
@ -162,10 +211,10 @@
<div class="col-md-3 skill-options"> <div class="col-md-3 skill-options">
<p class="skill-home"> <p class="skill-home">
<a class="btn btn-large btn-block btn--primary" href="{{ _p.web }}social"> <a class="btn btn-large btn-block btn--primary" href="{{ _p.web }}social">
<em class="fa fa-home"></em> {{ "Return "|trans }} <em class="mdi mdi-home"></em> {{ "Return "|trans }}
</a> </a>
</p> </p>
<div class="panel panel-default"> <div class="panel panel-default skill-profile-block">
<div class="panel-body"> <div class="panel-body">
<figure class="text-center"> <figure class="text-center">
<img width="100px" src="{{ user_info.avatar }}" class="img-circle center-block"> <img width="100px" src="{{ user_info.avatar }}" class="img-circle center-block">
@ -173,7 +222,7 @@
</figure> </figure>
<p class="text-center"> <p class="text-center">
<a href="{{ _p.web_main }}social/skills_ranking.php" class="btn btn--plain" target="_blank"> <a href="{{ _p.web_main }}social/skills_ranking.php" class="btn btn--plain" target="_blank">
{{ 'YourSkillRankingX'|trans|format(ranking) }} {{ 'Your skill ranking X'|trans|format(ranking) }}
</a> </a>
</p> </p>
<div class="text-center"> <div class="text-center">
@ -195,14 +244,14 @@
<div class="panel panel-default"> <div class="panel panel-default">
<div class="panel-heading"> <div class="panel-heading">
<a data-toggle="collapse" data-parent="#accordion2" href="#collapseTwo"> <a data-toggle="collapse" data-parent="#accordion2" href="#collapseTwo">
{{ 'GetNewSkills'|trans }} {{ 'Get new skills'|trans }}
</a> </a>
</div> </div>
<div id="collapseTwo" class="panel-collapse collapse"> <div id="collapseTwo" class="panel-collapse collapse">
<div class="panel-body"> <div class="panel-body">
<!-- SEARCH --> <!-- SEARCH -->
<div class="search-skill"> <div class="search-skill">
<h5 class="page-header">{{ 'SkillsSearch'|trans }}</h5> <h5 class="page-header">{{ 'Skills search'|trans }}</h5>
<form id="skill_search" class="form-search"> <form id="skill_search" class="form-search">
<select id="skill_id" name="skill_id" multiple style="width: 100%;"></select> <select id="skill_id" name="skill_id" multiple style="width: 100%;"></select>
<table id="skill_holder" class="table table-condensed"></table> <table id="skill_holder" class="table table-condensed"></table>
@ -210,12 +259,12 @@
</div> </div>
<!-- END SEARCH --> <!-- END SEARCH -->
<!-- INFO SKILL --> <!-- INFO SKILL -->
<h5 class="page-header">{{ 'SkillInfo'|trans }}</h5> <h5 class="page-header">{{ 'Skill information'|trans }}</h5>
<div id="skill_info"></div> <div id="skill_info"></div>
<!-- END INFO SKILL --> <!-- END INFO SKILL -->
<p> <p>
<a class="btn btn--plain btn-block load_root" rel="0" href="#"> <a class="btn btn--plain btn-block load_root" rel="0" href="#">
<em class="fa fa-eye"></em> {{ "ViewSkillsWheel"|trans }} <em class="mdi mdi-eye"></em> {{ "View skills wheel"|trans }}
</a> </a>
</p> </p>
</div> </div>
@ -233,18 +282,18 @@
</div> </div>
<div id="wheel-legend-collapse" class="panel-collapse collapse in" role="tabpanel" aria-labelledby="wheel-legend-heading"> <div id="wheel-legend-collapse" class="panel-collapse collapse in" role="tabpanel" aria-labelledby="wheel-legend-heading">
<div class="panel-body"> <div class="panel-body">
<ul class="fa-ul"> <ul class="mdi-ul">
<li> <li>
<em class="fa fa-li fa-square skill-legend-basic"></em> {{ "BasicSkills"|trans }} <em class="mdi mdi-li mdi-square skill-legend-basic"></em> {{ "Basic skills"|trans }}
</li> </li>
<li> <li>
<em class="fa fa-li fa-square skill-legend-badges"></em> {{ "SkillsYouAcquired"|trans }} <em class="mdi mdi-li mdi-square skill-legend-badges"></em> {{ "Skills you acquired"|trans }}
</li> </li>
<li> <li>
<em class="fa fa-li fa-square skill-legend-add"></em> {{ "SkillsYouCanLearn"|trans }} <em class="mdi mdi-li mdi-square skill-legend-add"></em> {{ "Skills sou can learn"|trans }}
</li> </li>
<li> <li>
<em class="fa fa-li fa-square skill-legend-search"></em> {{ "SkillsSearchedFor"|trans }} <em class="mdi mdi-li mdi-square skill-legend-search"></em> {{ "Skills searched for"|trans }}
</li> </li>
</ul> </ul>
</div> </div>
@ -254,17 +303,17 @@
<div class="panel-heading" role="tab" id="wheel-display-heading"> <div class="panel-heading" role="tab" id="wheel-display-heading">
<h4 class="panel-title"> <h4 class="panel-title">
<a class="collapsed" role="button" data-toggle="collapse" data-parent="#wheel-second-accordion" href="#wheel-display-collapse" aria-expanded="false" aria-controls="wheel-display-collapse"> <a class="collapsed" role="button" data-toggle="collapse" data-parent="#wheel-second-accordion" href="#wheel-display-collapse" aria-expanded="false" aria-controls="wheel-display-collapse">
{{ 'DisplayOptions'|trans }} {{ 'Display options'|trans }}
</a> </a>
</h4> </h4>
</div> </div>
<div id="wheel-display-collapse" class="panel-collapse collapse" role="tabpanel" aria-labelledby="wheel-display-heading"> <div id="wheel-display-collapse" class="panel-collapse collapse" role="tabpanel" aria-labelledby="wheel-display-heading">
<div class="panel-body"> <div class="panel-body">
<p>{{ 'ChooseABackgroundColor'|trans }}</p> <p>{{ 'Choose a background color'|trans }}</p>
<ul class="list-unstyled" id="skill-change-background-options"> <ul class="list-unstyled" id="skill-change-background-options">
<li><a href="#" data-color="#FFFFFF">{{ 'White'|trans }}</a></li> <li><a href="#" data-color="#FFFFFF">{{ 'White'|trans }}</a></li>
<li><a href="#" data-color="#000000">{{ 'Black'|trans }}</a></li> <li><a href="#" data-color="#000000">{{ 'Black'|trans }}</a></li>
<li><a href="#" data-color="#A9E2F3">{{ 'LightBlue' }}</a></li> <li><a href="#" data-color="#A9E2F3">{{ 'Light blue' }}</a></li>
<li><a href="#" data-color="#848484">{{ 'Gray'|trans }}</a></li> <li><a href="#" data-color="#848484">{{ 'Gray'|trans }}</a></li>
<li><a href="#" data-color="#F7F8E0">{{ 'Corn'|trans }}</a></li> <li><a href="#" data-color="#F7F8E0">{{ 'Corn'|trans }}</a></li>
</ul> </ul>
@ -311,7 +360,7 @@
<button type="button" class="close" data-dismiss="modal" aria-label="{{ "Close" | trans }}"> <button type="button" class="close" data-dismiss="modal" aria-label="{{ "Close" | trans }}">
<span aria-hidden="true">&times;</span> <span aria-hidden="true">&times;</span>
</button> </button>
<h4 class="modal-title" id="form-course-info-title">{{ "ChooseCourse" | trans }}</h4> <h4 class="modal-title" id="form-course-info-title">{{ "Choose course" | trans }}</h4>
</div> </div>
<div class="modal-body"></div> <div class="modal-body"></div>
<div class="modal-footer"> <div class="modal-footer">

Loading…
Cancel
Save