src/app/modules/search/components/user-profile/user-profile.component.ts
The delete component deletes the announcement which is requested by the logged in user have announcement creator access
OnInit
AfterViewInit
selector | app-user-profile |
styleUrls | ./user-profile.component.scss |
templateUrl | ./user-profile.component.html |
Properties |
|
Methods |
constructor(userSearchService: UserSearchService, route: Router, badgesService: BadgesService, activatedRoute: ActivatedRoute, resourceService: ResourceService, toasterService: ToasterService, routerNavigationService: RouterNavigationService, learnerService: LearnerService, configService: ConfigService, userService: UserService, router: Router, navigationhelperService: NavigationHelperService)
|
||||||||||||||||||||||||||||||||||||||||||||||||||||
Constructor to create injected service(s) object Default method of DeleteComponent class
Parameters :
|
badgeToggle | ||||
badgeToggle(viewMore)
|
||||
This method is used to show/hide ViewMore based on the limit
Parameters :
Returns :
void
|
formatEndorsementList |
formatEndorsementList()
|
This method helps to show the endorsement button
Returns :
void
|
ngAfterViewInit |
ngAfterViewInit()
|
Returns :
void
|
ngOnInit |
ngOnInit()
|
Returns :
void
|
populateBadgeDescription |
populateBadgeDescription()
|
This method fetches the badge details with the badge id and populates with the user details object
Returns :
void
|
populateUserProfile |
populateUserProfile()
|
This method fetches the user data
Returns :
void
|
submitEndorsement | ||||
submitEndorsement(skillName)
|
||||
This method submits the clicked endorsement
Parameters :
Returns :
void
|
toggle | ||||
toggle(lim)
|
||||
This method helps to toggle the skills div
Parameters :
Returns :
void
|
Public activatedRoute |
Type : ActivatedRoute
|
To send activatedRoute.snapshot to routerNavigationService |
badgeDefaultLimit |
Type : number
|
Contains default limit to show awards |
badgeLimit |
Type : number
|
Used to store limit to show/hide awards |
Private badgesService |
Type : BadgesService
|
Reference of BadgesService |
badgeViewMore |
Default value : true
|
Booloean value to hide/show awards |
Public configService |
Type : ConfigService
|
To get url, app configs |
defaultLimit |
Type : number
|
Default value : 4
|
descriptionReadMore |
Default value : true
|
disableEndorsementButton |
Default value : false
|
Public learnerService |
Type : LearnerService
|
To call API |
loggedInUserId |
Type : string
|
Public navigationhelperService |
Type : NavigationHelperService
|
pageNumber |
Type : number
|
Default value : 1
|
Contains page number of outbox list |
queryParams |
Type : any
|
Public resourceService |
Type : ResourceService
|
To call resource service which helps to use language constant |
Public route |
Type : Router
|
router |
Type : Router
|
Public routerNavigationService |
Type : RouterNavigationService
|
To navigate back to parent component |
showError |
Default value : false
|
showLoader |
Default value : true
|
skillLimit |
Type : number
|
Default value : 4
|
skillViewMore |
Default value : true
|
telemetryImpression |
Type : IImpressionEventInput
|
telemetryImpression |
Private toasterService |
Type : ToasterService
|
To show toaster(error, success etc) after any API calls |
userDetails |
Type : any
|
Contains announcement details returned from API or object called from announcement service |
userId |
Type : string
|
Contains unique announcement id |
Private userSearchService |
Type : UserSearchService
|
To make get announcement by id |
Public userService |
Type : UserService
|
To get user profile of logged-in user |
import { Component, OnInit, AfterViewInit } from '@angular/core';
import { ActivatedRoute, Router } from '@angular/router';
import { ResourceService, ToasterService, RouterNavigationService, ServerResponse, ConfigService,
NavigationHelperService } from '@sunbird/shared';
import { UserSearchService } from './../../services';
import { BadgesService, LearnerService, UserService } from '@sunbird/core';
import * as _ from 'lodash-es';
import { IImpressionEventInput } from '@sunbird/telemetry';
/**
* The delete component deletes the announcement
* which is requested by the logged in user have announcement
* creator access
*/
@Component({
selector: 'app-user-profile',
templateUrl: './user-profile.component.html',
styleUrls: ['./user-profile.component.scss']
})
export class UserProfileComponent implements OnInit, AfterViewInit {
/**
* Contains unique announcement id
*/
userId: string;
queryParams: any;
/**
* Contains page number of outbox list
*/
pageNumber = 1;
descriptionReadMore = true;
skillViewMore = true;
skillLimit = 4;
defaultLimit = 4;
loggedInUserId: string;
disableEndorsementButton = false;
/**
* Booloean value to hide/show awards
*/
badgeViewMore = true;
/**
* Contains announcement details returned from API or object called from
* announcement service
*/
userDetails: any;
showLoader = true;
showError = false;
/**
* To make get announcement by id
*/
private userSearchService: UserSearchService;
/**
* Reference of BadgesService
*/
private badgesService: BadgesService;
/**
* To send activatedRoute.snapshot to routerNavigationService
*/
public activatedRoute: ActivatedRoute;
/**
* To call resource service which helps to use language constant
*/
public resourceService: ResourceService;
/**
* To show toaster(error, success etc) after any API calls
*/
private toasterService: ToasterService;
/**
* To navigate back to parent component
*/
public routerNavigationService: RouterNavigationService;
router: Router;
/**
* To call API
*/
public learnerService: LearnerService;
/**
* To get url, app configs
*/
public configService: ConfigService;
/**
* To get user profile of logged-in user
*/
public userService: UserService;
/**
* Contains default limit to show awards
*/
badgeDefaultLimit: number;
/**
* Used to store limit to show/hide awards
*/
badgeLimit: number;
/**
* telemetryImpression
*/
telemetryImpression: IImpressionEventInput;
/**
* Constructor to create injected service(s) object
*
* Default method of DeleteComponent class
*
* @param {UserSearchService} userSearchService Reference of UserSearchService
* @param {ActivatedRoute} activatedRoute Reference of ActivatedRoute
* @param {ResourceService} resourceService Reference of ResourceService
* @param {ToasterService} toasterService Reference of ToasterService
* @param {RouterNavigationService} routerNavigationService Reference of routerNavigationService
* @param {LearnerService} learnerService Reference of LearnerService
* @param {ConfigService} config Reference of ConfigService
* @param {UserService} userService Reference of contentService
*/
constructor(userSearchService: UserSearchService,
public route: Router,
badgesService: BadgesService,
activatedRoute: ActivatedRoute,
resourceService: ResourceService,
toasterService: ToasterService,
routerNavigationService: RouterNavigationService,
learnerService: LearnerService,
configService: ConfigService,
userService: UserService,
router: Router,
public navigationhelperService: NavigationHelperService) {
this.userSearchService = userSearchService;
this.badgesService = badgesService;
this.activatedRoute = activatedRoute;
this.resourceService = resourceService;
this.toasterService = toasterService;
this.routerNavigationService = routerNavigationService;
this.learnerService = learnerService;
this.configService = configService;
this.userService = userService;
this.badgeDefaultLimit = this.configService.appConfig.PROFILE.defaultViewMoreLimit;
this.badgeLimit = this.badgeDefaultLimit;
}
/**
* This method fetches the user data
*/
populateUserProfile() {
this.showLoader = true;
const option = { userId: this.userId };
this.userSearchService.getUserById(option).subscribe(
(apiResponse: ServerResponse) => {
this.userDetails = apiResponse.result.response;
this.formatEndorsementList();
// this.breadcrumbsService.setBreadcrumbs([{ label: this.userDetails.firstName, url: '' }]);
this.populateBadgeDescription();
this.showLoader = false;
},
err => {
this.toasterService.error(this.resourceService.messages.emsg.m0005);
this.showLoader = false;
this.showError = true;
}
);
}
/**
* This method helps to show the endorsement button
*/
formatEndorsementList() {
if (this.userDetails && this.userDetails.skills && this.userDetails.skills.length) {
_.each(this.userDetails.skills, (skill) => {
if (skill.endorsersList) {
const userIds = _.map(skill.endorsersList, 'userId');
skill.isEndorsable = _.includes(userIds, this.loggedInUserId);
}
});
}
}
/**
* This method submits the clicked endorsement
*/
submitEndorsement(skillName) {
this.disableEndorsementButton = true;
const requestBody = {
request: {
skillName: skillName,
endorsedUserId: this.userId,
userId: this.loggedInUserId
}
};
const option = {
url: this.configService.urlConFig.URLS.USER.ENDORSE_SKILLS,
data: requestBody
};
this.learnerService.post(option).subscribe(response => {
_.each(this.userDetails.skills, (skill) => {
if (skill.skillName === skillName) {
skill.isEndorsable = true;
skill.endorsementCount = skill.endorsementCount ? skill.endorsementCount + 1 : 1;
}
});
this.disableEndorsementButton = false;
this.toasterService.success(this.resourceService.messages.smsg.m0043);
}, (err) => {
this.disableEndorsementButton = false;
this.toasterService.error(this.resourceService.messages.emsg.m0005);
});
}
/**
* This method fetches the badge details with the badge id and
* populates with the user details object
*/
populateBadgeDescription() {
const badgeList = [];
if (this.userDetails.badgeAssertions && this.userDetails.badgeAssertions.length > 0) {
_.each(this.userDetails.badgeAssertions, (badge) => {
badgeList.push(badge['badgeId']);
});
const req = {
request: {
filters: {
'badgeList': badgeList,
'type': 'user',
'rootOrgId': this.userDetails.rootOrgId
}
}
};
this.userDetails.badgeArray = [];
this.badgesService.getDetailedBadgeAssertions(req, this.userDetails.badgeAssertions).subscribe((detailedAssertion) => {
if (detailedAssertion) {
this.userDetails.badgeArray.push(detailedAssertion);
}
});
}
}
/**
* This method helps to toggle the skills div
*/
toggle(lim) {
if (lim === true) {
this.skillViewMore = false;
} else {
this.skillLimit = 4;
this.skillViewMore = true;
}
}
ngOnInit() {
this.userService.userData$.subscribe(userdata => {
if (userdata && !userdata.err) {
this.loggedInUserId = userdata.userProfile.userId;
this.activatedRoute.params.subscribe(params => {
this.userId = params.userId;
this.populateUserProfile();
});
this.queryParams = this.activatedRoute.snapshot.queryParams;
}
});
}
ngAfterViewInit () {
setTimeout(() => {
this.telemetryImpression = {
context: {
env: this.activatedRoute.snapshot.data.telemetry.env
},
object: {
id: this.activatedRoute.snapshot.params.userId,
type: 'user',
ver: '1.0'
},
edata: {
type: this.activatedRoute.snapshot.data.telemetry.type,
pageid: this.activatedRoute.snapshot.data.telemetry.pageid,
uri: this.route.url,
subtype: this.activatedRoute.snapshot.data.telemetry.subtype,
duration: this.navigationhelperService.getPageLoadTime()
}
};
});
}
/**
* This method is used to show/hide ViewMore based on the limit
*/
badgeToggle(viewMore) {
if (viewMore === true) {
this.badgeLimit = this.userDetails.badgeArray.length;
this.badgeViewMore = false;
} else {
this.badgeViewMore = true;
this.badgeLimit = this.defaultLimit;
}
}
}
<div [appTelemetryImpression]="telemetryImpression" *ngIf="showLoader">
<div class="ui grid">
<div class="one wide column"></div>
<div class="ten wide column">
<app-loader></app-loader>
</div>
<div class="one wide column"></div>
</div>
</div>
<!-- header -->
<div class="ui grid py-10 courseStructureHeader" *ngIf="!showLoader && !showError">
<div class="one wide column"></div>
<div class=" ten wide column">
<div class="ui grid">
<div class="eight wide column">
<div class="profileheader ui link items">
<div class="ui grid">
<div class="two wide column pt-0">
<div class="userAvtarWrap field link ui small circular image header-image-profile">
<img class="ui small circular image header-image-profile" [src]="userDetails.avatar || 'assets/images/user_logo.png' | cdnprefixurl" alt="avatar image">
</div>
</div>
<div class="ten wide column profile-header-text pt-0">
<div class="content pt-10">
<div class="sectionHeading header">{{userDetails.firstName}} {{userDetails.lastName}}</div>
<div class="meta profileViewSubHeader pb-10">
<span *ngIf="userDetails.location">{{userDetails.location}}</span>
</div>
</div>
</div>
</div>
</div>
</div>
<div class="profilesettings four wide column">
<h5 class="ui right floated basic icon circular button" [queryParams]="queryParams" [routerLink]="['../../']">
<i class="ui remove icon"></i>
</h5>
</div>
</div>
</div>
<div class="one wide column"></div>
</div>
<!-- description of profile -->
<div class="ui grid" *ngIf="!showLoader && !showError">
<div class="one wide column"></div>
<div class="ten wide column">
<div class="ui grid">
<!--Profile summary-->
<div class="twelve wide column" *ngIf="userDetails.profileSummary">
<div class="mt-20 ui raised segment">
<div class="header">
<span class="segment-heading"> {{resourceService.frmelmnts?.lbl?.summary | translate}} </span>
</div>
<div class="description pt-10">
<div *ngIf="descriptionReadMore && userDetails.profileSummary.length > 120">
<span class="overflow-word-wrap">{{userDetails.profileSummary | slice:0:120 }} </span>
<span class="ui expand-or-minimize" tabindex="0" (click)="descriptionReadMore = false;">{{resourceService.frmelmnts?.lbl?.readmore | translate}}</span>
</div>
<div class="overflow-word-wrap" *ngIf="!descriptionReadMore && userDetails.profileSummary.length > 120"> {{userDetails.profileSummary}}
<span class="ui expand-or-minimize" tabindex="0" (click)="descriptionReadMore = true;">{{resourceService.frmelmnts?.lbl?.readless | translate}}</span>
</div>
</div>
</div>
</div>
<!--Address-->
<div class="twelve wide column">
<div class="ui raised segment">
<div class="header announcementCard-header">
<span class="header cardsHeading">{{resourceService.frmelmnts?.lbl?.address | translate}}</span>
</div>
<div class="profileitems ui relaxed divided items">
<div class="item" *ngFor="let address of userDetails.address">
<img class="ui avatar image" src="{{'assets/images/location.png' | cdnprefixurl}}">
<div class="content">
<p class=" header">{{address.addType}}</p>
<div class="description"> {{address.addressLine1}}
<span *ngIf="address.addressLine2"> , </span>{{address.addressLine2}}
<p>{{address.city}}
<span *ngIf="address.state"> , </span>{{address.state}}
<span *ngIf="address.country">, </span>{{address.country}}
<span *ngIf="address.zipcode">, </span>{{address.zipcode}}</p>
</div>
</div>
</div>
</div>
</div>
</div>
<!-- experience -->
<div class="twelve wide column">
<div class="ui raised segment">
<div class="header announcementCard-header">
<span class="header cardsHeading">{{resourceService.frmelmnts?.lbl?.experience | translate}}</span>
</div>
<div class="profileitems ui relaxed divided items ">
<div class="item" *ngFor="let experience of userDetails.jobProfile">
<img class="ui avatar image" src="{{'assets/images/businessman.png' | cdnprefixurl}}">
<div class="content ">
<a class=" header ">{{experience.jobName}}</a>
<div class="description ">{{experience.role}}
<span *ngIf="experience.role"> , </span>{{experience.orgName}}
<p class="mb-0 " *ngIf="experience.subject.length ">{{resourceService.frmelmnts?.lbl?.subjectstaught | transposeTerms: 'frmelmnts.lbl.subjectstaught': resourceService?.selectedLang | translate}} :
<span>
<span *ngFor="let sub of experience.subject; let last = last;">{{sub}}
<span *ngIf="!last ">, </span>
</span>
</span>
</p>
<p *ngIf="experience.joiningDate ">{{resourceService.frmelmnts?.lbl?.tcfrom | translate}} : {{experience.joiningDate}}
<span *ngIf="experience.endDate ">, {{resourceService.frmelmnts?.lbl?.tcto | translate}} : {{experience.endDate}}</span>
</p>
</div>
</div>
</div>
</div>
</div>
</div>
<!-- education -->
<div class="twelve wide column">
<div class="ui raised segment">
<div class="header announcementCard-header">
<span class="header cardsHeading">{{resourceService.frmelmnts?.lbl?.education | translate}}</span>
</div>
<div class="profileitems ui relaxed divided items ">
<div class="item" *ngFor="let education of userDetails.education">
<img class="ui avatar image" src="{{'assets/images/businessman.png' | cdnprefixurl}}">
<div class="content">
<a class=" header">{{education.degree}}</a>
<div class="description"> {{education.yearOfPassing}}
<span *ngIf="education.percentage">, </span>{{education.percentage}}
<br/>
<p>{{education.grade}}
<span *ngIf="education.name && education.grade">, </span>{{education.name}}
<span *ngIf="education.boardOrUniversity">, </span>{{education.boardOrUniversity}}
</div>
</div>
</div>
</div>
</div>
</div>
<!-- skills -->
<div class="twelve wide column">
<div class="ui raised segment mb-0">
<div class="header announcementCard-header ">
<span class="header cardsHeading">{{resourceService?.frmelmnts?.lbl?.skillTags | translate}}</span>
</div>
<div class="profileitems profile-des ui relaxed aligned list">
<div class="item " *ngFor="let skill of userDetails.skills | slice:0:skillLimit">
<div class="ui label">
{{skill.skillName}} {{skill.endorsementCount}}
<div class="detail">
<span *ngIf="skill.endorsementCount !== 0">| </span>
<span *ngIf="skill.endorsementCount !== 0">{{skill.endorsementCount}}</span>
</div>
</div>
<div *ngIf="!skill.isEndorsable" class="ui circular labels float-ContentRight ">
<a class="ui basic label" tabindex="0" (click)="submitEndorsement(skill.skillName)" [ngClass]="{'not-active': disableEndorsementButton }">
+1 </a>
</div>
</div>
</div>
</div>
<div class="ui bottom attached tabular menu expand-or-minimize-btn ng-scope " *ngIf="userDetails.skills.length > defaultLimit">
<div class="active item expand-or-minimize-btn-pad">
<a tabindex="0" (click)="toggle(true); skillLimit = userDetails.skills.length" *ngIf="skillViewMore">
<span class="cursor-pointer">
{{resourceService?.frmelmnts?.btn?.viewmore | translate}}
<i class="chevron down icon"></i>
</span>
</a>
<a tabindex="0" (click)="toggle(false)" *ngIf="!skillViewMore">
<span class="cursor-pointer">
{{resourceService?.frmelmnts?.btn?.viewless | translate}}
<i class="chevron up icon"></i>
</span>
</a>
</div>
</div>
</div>
<!--Badge-->
<div class="twelve wide column" *ngIf="userDetails.badgeArray && userDetails.badgeArray.length > 0">
<div class="ui raised segment mb-0">
<div class="header announcementCard-header">
<span class="header cardsHeading">{{resourceService?.frmelmnts?.lbl?.certificationAward | translate}}</span>
</div>
<div class="ui items mt-10">
<div class="item" *ngFor="let badge of userDetails.badgeArray | slice:0:badgeLimit">
<img class="ui avatar image" [src]="badge.image || badge.badgeClassImage">
<div class="middle aligned content pl-10">
<div class="ui huge sub header secondary-text-color-sunbird">{{badge.badgeClassName}}</div>
<div class="description">
<div class="secondary-text-color-sunbird">{{badge.description | slice:0:70 }}
<i *ngIf="badge.description && badge.description.length > 70" class="ellipsis horizontal icon" title="{{badge.description}}">
</i>
</div>
</div>
</div>
<div *ngIf="badge.createdTS || badge.createdTs" class="meta">{{badge.createdTS || badge.createdTs | dateFormat: 'MMM YYYY'}}</div>
</div>
</div>
</div>
<div class="ui bottom attached tabular menu expand-or-minimize-btn" *ngIf="userDetails.badgeArray.length > badgeDefaultLimit">
<div class="active item expand-or-minimize-btn-pad">
<a tabindex="0" (click)="badgeToggle(true)" *ngIf="badgeViewMore">
<span class="cursor-pointer">
{{resourceService?.frmelmnts?.btn?.viewmore | translate}}
<i class="chevron down icon"></i>
</span>
</a>
<a tabindex="0" (click)="badgeToggle(false)" *ngIf="!badgeViewMore">
<span class="cursor-pointer">
{{resourceService?.frmelmnts?.btn?.viewless | translate}}
<i class="chevron up icon"></i>
</span>
</a>
</div>
</div>
</div>
<!-- aditional information -->
<div class="twelve wide column">
<div class="ui raised segment ">
<div class="header announcementCard-header ">
<span class="header cardsHeading ">{{resourceService?.frmelmnts?.lbl?.addlInfo | translate}}</span>
</div>
<div class="profileitems profile-des ui relaxed aligned list ">
<div class="item ">
<div class="right floated content ">
<span>{{userDetails.location}}</span>
</div>
<div class="iniformationcontent content ">
{{resourceService.frmelmnts?.lbl?.currentlocation | translate}}
</div>
</div>
<div class="item ">
<div class="right floated content ">
<span *ngFor="let grade of userDetails.grade; let last = last">
<span>{{grade}}
<span *ngIf=!last>,</span>
</span>
</span>
</div>
<div class="iniformationcontent content ">
{{resourceService.frmelmnts?.lbl?.grades | transposeTerms: 'frmelmnts.lbl.grades': resourceService?.selectedLang | translate}}
</div>
</div>
<div class="item ">
<div class="right floated content ">
<span>{{userDetails.gender}}</span>
</div>
<div class="iniformationcontent content ">
{{resourceService.frmelmnts?.lbl?.gender | translate}}
</div>
</div>
<div class="item ">
<div class="right floated content ">
<span>{{userDetails.dob | date : "dd/MM/y"}}</span>
</div>
<div class="iniformationcontent content ">
{{resourceService.frmelmnts?.lbl?.birthdate | translate}}
</div>
</div>
<div class="item ">
<div class="right floated content" *ngIf="userDetails.subject">
{{userDetails.subject.join(', ')}}
</div>
<div class="iniformationcontent content ">
{{resourceService.frmelmnts?.lbl?.subjects | transposeTerms: 'frmelmnts.lbl.subjects': resourceService?.selectedLang | translate}}
</div>
</div>
<div class="item ">
<div class="right floated content" *ngIf="userDetails.language">
{{userDetails.language.join(', ')}}
</div>
<div class="iniformationcontent content ">
{{resourceService.frmelmnts?.lbl?.language | translate}}
</div>
</div>
</div>
</div>
</div>
</div>
</div>
<div class="one wide column"></div>
</div>
./user-profile.component.scss
.not-active {
pointer-events: none;
cursor: default;
text-decoration: none;
color: var(--black);
}
.ui.segment .segment-heading {
font-weight: bold;
font-size: 1.25em;
}