Upgraded site-badges to display properly
This commit is contained in:
parent
b9243d9ddb
commit
c12396f9c2
|
@ -30,7 +30,18 @@ export default {
|
|||
unsubmitted: "unsubmitted",
|
||||
nogrades: "nogrades",
|
||||
unknown: "unknown",
|
||||
},
|
||||
completion: {
|
||||
completion_completed: "completion_completed",
|
||||
completion_incomplete: "completion_incomplete",
|
||||
},
|
||||
badge: {
|
||||
share_badge: "share_badge",
|
||||
dateissued: "dateissued",
|
||||
dateexpire: "dateexpire",
|
||||
badgeinfo: "badgeinfo",
|
||||
}
|
||||
|
||||
});
|
||||
|
||||
/************************************
|
||||
|
@ -1640,22 +1651,88 @@ export default {
|
|||
},
|
||||
data() {
|
||||
return {
|
||||
txt: strings
|
||||
};
|
||||
},
|
||||
computed: {
|
||||
completion() {
|
||||
return this.value.badge.issued?"completed":"incomplete";
|
||||
},
|
||||
issued_icon(){
|
||||
switch(this.value.badge.issued){
|
||||
default: // "nogrades":
|
||||
return "circle-o";
|
||||
case true:
|
||||
return "check";
|
||||
}
|
||||
},
|
||||
},
|
||||
methods: {
|
||||
},
|
||||
template: `
|
||||
<div :class="'r-item-badge r-item-filter completion-'+completion" v-b-tooltip.hover :title="value.badge.name">
|
||||
<svg class="r-badge-backdrop" width='50px' height='50px'>
|
||||
<circle cx="25px" cy="25px" r="24px" />
|
||||
</svg>
|
||||
<img class="badge-image" :src="value.badge.imageurl">
|
||||
<div :class="'r-item-badge r-item-filter r-completion-'+completion" v-b-tooltip.hover :title="value.badge.name">
|
||||
<a v-b-modal="'r-item-badge-details-'+value.id"
|
||||
><svg class="r-badge-backdrop " width='50px' height='50px' viewBox="0 0 100 100">
|
||||
<title>{{value.badge.name}}</title>
|
||||
<circle v-if="teachermode" cx="50" cy="50" r="46"
|
||||
style="stroke: #999; stroke-width: 6; fill: #ddd; fill-opacity: 0.8;"/>
|
||||
<circle v-else-if="value.badge.issued" cx="50" cy="50" r="46"
|
||||
style="stroke: currentcolor; stroke-width: 4; fill: currentcolor; fill-opacity: 0.5;"/>
|
||||
<circle v-else cx="50" cy="50" r="46"
|
||||
stroke-dasharray="6 9"
|
||||
style="stroke: #999; stroke-width: 6; fill: #ddd; fill-opacity: 0.8;"/>
|
||||
<image class="badge-image" clip-path="circle() fill-box"
|
||||
:href="value.badge.imageurl" x="12" y="12" width="76" height="76"
|
||||
:style="(value.badge.issued||teachermode)?'':'opacity: 0.4;'" />
|
||||
</svg></a>
|
||||
|
||||
<b-modal
|
||||
:id="'r-item-badge-details-'+value.id"
|
||||
:title="value.badge.name"
|
||||
size="lg"
|
||||
ok-only
|
||||
centered
|
||||
scrollable
|
||||
>
|
||||
<template #modal-header>
|
||||
<div>
|
||||
<h1><i class="fa fa-certificate"></i>
|
||||
<a :href="(!guestmode)?(value.badge.infolink):undefined" target="_blank"
|
||||
>{{ value.badge.name }}</a
|
||||
></h1>
|
||||
</div>
|
||||
<div class="r-course-detail-header-right">
|
||||
<div class="r-completion-detail-header">
|
||||
{{ txt.completion['completion_'+completion] }}
|
||||
<i v-b-popover.hover :class="'fa fa-'+issued_icon+' r-completion-'+completion"
|
||||
:title="txt.completion['completion_'+completion]"></i>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
<b-container fluid>
|
||||
<b-row><b-col cols="3">
|
||||
<img :src="value.badge.imageurl"/>
|
||||
</b-col><b-col cols="9">
|
||||
<p>{{value.badge.description}}</p>
|
||||
<ul v-if="value.badge.issued" class="list-unstyled pt-1 mb-1 border-grey border-top">
|
||||
<li><strong><i class="fa fa-calendar-check-o r-completion-complete-pass"></i>
|
||||
{{txt.badge.dateissued}}:</strong> {{ value.badge.dateissued }}</li>
|
||||
<li v-if='value.badge.dateexpired'
|
||||
><strong><i class="fa fa-calendar-times-o r-completion-complete"></i>
|
||||
{{txt.badge.dateexpired}}:</strong> {{ value.badge.dateexpired }}</li>
|
||||
<li><strong><i class="fa fa-share-alt r-completion-complete-pass"></i>
|
||||
<a href="value.badge.issuedlink">{{txt.badge.share_badge}}</a></strong> </li>
|
||||
</ul>
|
||||
<ul class="list-unstyled w-100 border-grey border-top border-bottom pt-1 pb-1 mb-1"
|
||||
v-if="value.badge.criteria"><li v-for="crit in value.badge.criteria"
|
||||
><span v-html='crit'></span></li></ul>
|
||||
<p v-if="(!guestmode)"><strong><i class="fa fa-link"></i>
|
||||
<a :href="value.badge.infolink">{{ txt.badge.badgeinfo }}</a></strong></p>
|
||||
</b-col></b-row>
|
||||
</b-container>
|
||||
</b-modal>
|
||||
</div>
|
||||
|
||||
`,
|
||||
});
|
||||
},
|
||||
|
|
|
@ -169,6 +169,16 @@ export default {
|
|||
invalid: {
|
||||
error: 'error',
|
||||
},
|
||||
completion: {
|
||||
completion_completed: "completion_completed",
|
||||
completion_incomplete: "completion_incomplete",
|
||||
},
|
||||
badge: {
|
||||
share_badge: "share_badge",
|
||||
dateissued: "dateissued",
|
||||
dateexpire: "dateexpire",
|
||||
badgeinfo: "badgeinfo",
|
||||
}
|
||||
});
|
||||
|
||||
|
||||
|
@ -1934,7 +1944,7 @@ export default {
|
|||
return !(["start",].includes(this.value.type));
|
||||
},
|
||||
hasContext() {
|
||||
return ['start','junction','finish',].includes(this.value.type);
|
||||
return ['junction','finish'].includes(this.value.type);
|
||||
}
|
||||
},
|
||||
created(){
|
||||
|
@ -2456,21 +2466,57 @@ export default {
|
|||
props: {
|
||||
value : {
|
||||
type: Object,
|
||||
default: function(){ return {};},
|
||||
default: function(){ return { badge: {}};},
|
||||
},
|
||||
},
|
||||
data() {
|
||||
return {
|
||||
txt: strings,
|
||||
};
|
||||
},
|
||||
methods: {
|
||||
},
|
||||
template: `
|
||||
<div class='t-item-badge t-item-filter' v-b-tooltip.hover :title="value.badge.name">
|
||||
<svg class="t-badge-backdrop" width='50px' height='50px'>
|
||||
<circle cx="25px" cy="25px" r="24px" />
|
||||
<svg class="t-badge-backdrop " width='50px' height='50px' viewBox="0 0 100 100">
|
||||
<title>{{value.badge.name}}</title>
|
||||
<circle cx="50" cy="50" r="46"
|
||||
style="stroke: currentcolor; stroke-width: 4; fill: currentcolor; fill-opacity: 0.5;"/>
|
||||
<image class="badge-image" clip-path="circle() fill-box"
|
||||
:href="value.badge.imageurl" x="12" y="12" width="76" height="76"/>
|
||||
</svg>
|
||||
<img class="badge-image" :src="value.badge.imageurl">
|
||||
<a class="t-item-config badge"
|
||||
v-b-modal="'t-item-badge-details-'+value.id" href="#" @click.prevent=""><i class="fa fa-gear"></i></a>
|
||||
<b-modal
|
||||
:id="'t-item-badge-details-'+value.id"
|
||||
:title="value.badge.name"
|
||||
size="lg"
|
||||
ok-only
|
||||
centered
|
||||
scrollable
|
||||
>
|
||||
<template #modal-header>
|
||||
<div>
|
||||
<h1><i class="fa fa-certificate"></i>
|
||||
<a :href="value.badge.infolink" target="_blank"
|
||||
>{{ value.badge.name }}</a
|
||||
></h1>
|
||||
</div>
|
||||
</template>
|
||||
<b-container fluid>
|
||||
<b-row><b-col cols="3">
|
||||
<img :src="value.badge.imageurl"/>
|
||||
</b-col><b-col cols="9">
|
||||
<p>{{value.badge.description}}</p>
|
||||
<ul class="list-unstyled w-100 border-grey border-top border-bottom pt-1 pb-1 mb-1"
|
||||
v-if="value.badge.criteria"><li v-for="crit in value.badge.criteria"
|
||||
><span v-html='crit'></span></li></ul>
|
||||
<p><strong><i class="fa fa-link"></i>
|
||||
<a :href="value.badge.infolink">{{ txt.badge.badgeinfo }}</a></strong></p>
|
||||
</b-col></b-row>
|
||||
</b-container>
|
||||
</b-modal>
|
||||
|
||||
</div>
|
||||
`,
|
||||
});
|
||||
|
|
|
@ -43,9 +43,11 @@ class badgeinfo {
|
|||
public static function editor_structure($value=VALUE_REQUIRED){
|
||||
return new \external_single_structure([
|
||||
"id" => new \external_value(PARAM_INT, 'id of badge'),
|
||||
"infolink" => new \external_value(PARAM_TEXT, 'badge issue information link', VALUE_OPTIONAL),
|
||||
"name" => new \external_value(PARAM_TEXT, 'badge name'),
|
||||
"status" => new \external_value(PARAM_TEXT, 'badge status'),
|
||||
"locked" => new \external_value(PARAM_TEXT, 'badge lock status'),
|
||||
"criteria" => new \external_multiple_structure(new \external_value(PARAM_RAW, 'criteria text'),'badge criteria',VALUE_OPTIONAL),
|
||||
"description"=> new \external_value(PARAM_TEXT, 'badge description'),
|
||||
"imageurl" => new \external_value(PARAM_TEXT, 'url of badge image'),
|
||||
],"Badge info",$value);
|
||||
|
@ -55,11 +57,18 @@ class badgeinfo {
|
|||
{
|
||||
$context = ($this->badge->type == BADGE_TYPE_SITE) ? \context_system::instance() : \context_course::instance($this->badge->courseid);
|
||||
// If the user is viewing another user's badge and doesn't have the right capability return only part of the data.
|
||||
|
||||
$criteria = [];
|
||||
foreach($this->badge->get_criteria() as $bc){
|
||||
$criteria[] = $bc->get_title()." ".$bc->get_details();
|
||||
}
|
||||
$model = [
|
||||
'id' => $this->badge->id,
|
||||
'infolink' => (new \moodle_url('/badges/overview.php', ['id' => $this->badge->id]))->out(false),
|
||||
'name' => $this->badge->name,
|
||||
'status' => self::STATUSINFO[$this->badge->status],
|
||||
'locked' => self::LOCKEDINFO[$this->badge->status],
|
||||
'criteria' => $criteria,
|
||||
'description' => $this->badge->description,
|
||||
'imageurl' => \moodle_url::make_pluginfile_url($context->id, 'badges', 'badgeimage', $this->badge->id, '/','f1')->out(false),
|
||||
];
|
||||
|
@ -70,10 +79,14 @@ class badgeinfo {
|
|||
{
|
||||
return new \external_single_structure([
|
||||
"id" => new \external_value(PARAM_INT, 'id of badge'),
|
||||
"infolink" => new \external_value(PARAM_TEXT, 'badge issue information link', VALUE_OPTIONAL),
|
||||
"name" => new \external_value(PARAM_TEXT, 'badge name'),
|
||||
"criteria" => new \external_multiple_structure(new \external_value(PARAM_RAW, 'criteria text'),'badge criteria',VALUE_OPTIONAL),
|
||||
"description"=> new \external_value(PARAM_TEXT, 'badge description'),
|
||||
"imageurl" => new \external_value(PARAM_TEXT, 'url of badge image'),
|
||||
"issued" => new \external_value(PARAM_BOOL, 'badge is issued'),
|
||||
"dateissued" => new \external_value(PARAM_TEXT, 'date the badge was issued',VALUE_OPTIONAL),
|
||||
"dateexpire" => new \external_value(PARAM_TEXT, 'date the badge will expire',VALUE_OPTIONAL),
|
||||
"uniquehash" => new \external_value(PARAM_TEXT, 'badge issue hash', VALUE_OPTIONAL),
|
||||
"issuedlink" => new \external_value(PARAM_TEXT, 'badge issue information link', VALUE_OPTIONAL),
|
||||
],"Badge info",$value);
|
||||
|
@ -87,18 +100,28 @@ class badgeinfo {
|
|||
$issued = $this->badge->is_issued($userid);
|
||||
|
||||
// If the user is viewing another user's badge and doesn't have the right capability return only part of the data.
|
||||
$criteria = [];
|
||||
foreach($this->badge->get_criteria() as $bc){
|
||||
$criteria[] = $bc->get_title()."".$bc->get_details();
|
||||
}
|
||||
$badge = [
|
||||
'id' => $this->badge->id,
|
||||
'name' => $this->badge->name,
|
||||
'description' => $this->badge->description,
|
||||
'imageurl' => \moodle_url::make_pluginfile_url($context->id, 'badges', 'badgeimage', $this->badge->id, '/','f1')->out(false),
|
||||
'criteria' => $criteria,
|
||||
'issued' => $issued,
|
||||
'infolink' => (new \moodle_url('/badges/overview.php', ['id' => $this->badge->id]))->out(false),
|
||||
];
|
||||
|
||||
if($issued) {
|
||||
$issueinfo = $DB->get_record('badge_issued', array('badgeid' => $this->badge->id, 'userid' => $userid));
|
||||
$badge['dateissued'] = userdate($issueinfo->dateissued,"%e %b %G");
|
||||
if($issueinfo->expiredate){
|
||||
$badge['dateexpire'] = userdate($issueinfo->dateexpire,"%e %b %G");
|
||||
}
|
||||
$badge['uniquehash'] = $issueinfo->uniquehash;
|
||||
$badge['issuedlink'] = new \moodle_url('/badges/badge.php', array('hash' => $issueinfo->uniquehash));
|
||||
$badge['issuedlink'] = (new \moodle_url('/badges/badge.php', ['hash' => $issueinfo->uniquehash]))->out(false);
|
||||
}
|
||||
|
||||
return $badge;
|
||||
|
|
|
@ -616,13 +616,18 @@ class studyplanservice extends \external_api
|
|||
|
||||
public static function list_badges()
|
||||
{
|
||||
//TODO: Include course badges somehow... Just site badges is not enough
|
||||
$systemcontext = webservicehelper::system_context();
|
||||
|
||||
$result = [];
|
||||
$badges = badges_get_badges(BADGE_TYPE_SITE,"timemodified");
|
||||
foreach ($badges as $badge) {
|
||||
$result[] = (new badgeinfo($badge))->editor_model();
|
||||
// TODO: Add config option to list only active badges
|
||||
// if($badge->is_active()){
|
||||
$result[] = (new badgeinfo($badge))->editor_model();
|
||||
// }
|
||||
|
||||
//TODO: Include course badges somehow... Just site badges is not enough
|
||||
|
||||
}
|
||||
return $result;
|
||||
|
||||
|
|
|
@ -382,7 +382,7 @@ ul.t-toolbox li {
|
|||
color: #009900;
|
||||
}
|
||||
|
||||
.t-item-badge i {
|
||||
.t-item-badge svg {
|
||||
color: #ddaa00;
|
||||
}
|
||||
|
||||
|
@ -412,6 +412,14 @@ a.t-item-config {
|
|||
right: -5px;
|
||||
}
|
||||
|
||||
a.t-item-config.badge {
|
||||
top: -5px;
|
||||
right: -5px;
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
|
||||
|
||||
a.t-item-course-config {
|
||||
font-size: 16pt;
|
||||
vertical-align: middle;
|
||||
|
@ -463,12 +471,6 @@ a.t-item-course-config {
|
|||
transform: translate(-50%, -50%);
|
||||
}
|
||||
|
||||
.t-item-badge svg.t-badge-backdrop circle {
|
||||
stroke: black;
|
||||
stroke-width: 2px;
|
||||
fill: #ccc;
|
||||
|
||||
}
|
||||
|
||||
.l-leaderline-linewrapper {
|
||||
width: 0;
|
||||
|
@ -660,13 +662,12 @@ a.t-item-course-config {
|
|||
stroke: black;
|
||||
stroke-width: 2px;
|
||||
fill: #ccc;
|
||||
|
||||
}
|
||||
|
||||
.r-studyplan-line-wrapper {
|
||||
width: 0;
|
||||
height: 0;
|
||||
position: relative; /* Origin of coordinates for lines, and scrolled content (i.e. not `absolute`) */
|
||||
position: relative; /* Origin of coordinates for lines, and scrolled content (i.e. not `abcomsolute`) */
|
||||
}
|
||||
|
||||
.r-item-module-children {
|
||||
|
@ -773,7 +774,7 @@ table.r-item-course-grade-details td {
|
|||
|
||||
.t-timing-past,
|
||||
.r-timing-past {
|
||||
color: darkgreen;
|
||||
color: var(--purple);
|
||||
}
|
||||
.t-timing-present,
|
||||
.r-timing-present {
|
||||
|
@ -802,7 +803,7 @@ table.r-item-course-grade-details td {
|
|||
|
||||
.t-timing-indicator.timing-past,
|
||||
.r-timing-indicator.timing-past {
|
||||
background-color: #3a3;
|
||||
background-color: var(--purple);
|
||||
}
|
||||
|
||||
.t-timing-indicator.timing-present,
|
||||
|
@ -952,3 +953,7 @@ table.r-item-course-grade-details td {
|
|||
|
||||
.s-edit-mod-form [data-fieldtype=submit] { display: none ! important; }
|
||||
.s-edit-mod-form.genericonly form > fieldset:not(#id_general) { display: none ! important; }
|
||||
|
||||
.border-grey {
|
||||
border-color: #aaa;
|
||||
}
|
|
@ -244,3 +244,8 @@ $string["aggregation_overall_all"] = "Complete all of the categories";
|
|||
$string["aggregation_overall_any"] = "Complete one or more of the categories";
|
||||
$string["aggregation_all"] = "Complete all";
|
||||
$string["aggregation_any"] = "Complete one or more";
|
||||
|
||||
$string["share_badge"] = "Share badge";
|
||||
$string["dateissued"] = "Issued on";
|
||||
$string["dateexpire"] = "Expires on";
|
||||
$string["badgeinfo"] = "Badge details";
|
|
@ -247,3 +247,8 @@ $string["aggregation_overall_all"] = "Behaal alle categorieë";
|
|||
$string["aggregation_overall_any"] = "Behaal één of meer categorieën";
|
||||
$string["aggregation_all"] = "Alles behalen";
|
||||
$string["aggregation_any"] = "Eén of meer behalen";
|
||||
|
||||
$string["share_badge"] = "Bewijs delen";
|
||||
$string["dateissued"] = "Afgegeven op";
|
||||
$string["dateexpire"] = "Veloopt op";
|
||||
$string["badgeinfo"] = "Meer details";
|
Loading…
Reference in New Issue
Block a user