avatar base
This commit is contained in:
parent
a3775ed3ac
commit
500a56e429
1
projects/ui/src/lib/avatar/avatar.component.html
Normal file
1
projects/ui/src/lib/avatar/avatar.component.html
Normal file
@ -0,0 +1 @@
|
||||
{{shortUsername}}
|
24
projects/ui/src/lib/avatar/avatar.component.scss
Normal file
24
projects/ui/src/lib/avatar/avatar.component.scss
Normal file
@ -0,0 +1,24 @@
|
||||
:host {
|
||||
display: block;
|
||||
aspect-ratio: 1/1;
|
||||
text-transform: uppercase;
|
||||
color: #000;
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
align-items: center;
|
||||
width: var(--local-size, 50px);
|
||||
font-size: var(--local-size);
|
||||
|
||||
&[data-size="default"] {
|
||||
--local-size: 50px;
|
||||
}
|
||||
&[data-size="small"] {
|
||||
--local-size: 50px;
|
||||
}
|
||||
&[data-size="medium"] {
|
||||
--local-size: 50px;
|
||||
}
|
||||
&[data-size="large"] {
|
||||
--local-size: 50px;
|
||||
}
|
||||
}
|
23
projects/ui/src/lib/avatar/avatar.component.spec.ts
Normal file
23
projects/ui/src/lib/avatar/avatar.component.spec.ts
Normal file
@ -0,0 +1,23 @@
|
||||
import { ComponentFixture, TestBed } from '@angular/core/testing';
|
||||
|
||||
import { AvatarComponent } from './avatar.component';
|
||||
|
||||
describe('AvatarComponent', () => {
|
||||
let component: AvatarComponent;
|
||||
let fixture: ComponentFixture<AvatarComponent>;
|
||||
|
||||
beforeEach(async () => {
|
||||
await TestBed.configureTestingModule({
|
||||
declarations: [ AvatarComponent ]
|
||||
})
|
||||
.compileComponents();
|
||||
|
||||
fixture = TestBed.createComponent(AvatarComponent);
|
||||
component = fixture.componentInstance;
|
||||
fixture.detectChanges();
|
||||
});
|
||||
|
||||
it('should create', () => {
|
||||
expect(component).toBeTruthy();
|
||||
});
|
||||
});
|
33
projects/ui/src/lib/avatar/avatar.component.ts
Normal file
33
projects/ui/src/lib/avatar/avatar.component.ts
Normal file
@ -0,0 +1,33 @@
|
||||
import { Component, HostBinding, Input, OnInit } from '@angular/core';
|
||||
import { stringHashToHsl } from '../utils/string-hash-to-hsl';
|
||||
import { AvatarSize } from './avatar.interface';
|
||||
|
||||
@Component({
|
||||
selector: 'skirda-avatar',
|
||||
templateUrl: './avatar.component.html',
|
||||
styleUrls: ['./avatar.component.scss'],
|
||||
})
|
||||
export class AvatarComponent implements OnInit {
|
||||
@Input() username: string = 'username';
|
||||
@Input() size: AvatarSize = 'default';
|
||||
|
||||
constructor() {}
|
||||
|
||||
ngOnInit(): void {}
|
||||
|
||||
@HostBinding('style.background-color')
|
||||
get color() {
|
||||
return stringHashToHsl(this.username);
|
||||
}
|
||||
|
||||
@HostBinding('data-size')
|
||||
get avatarSize() {
|
||||
return `${this.size}px`;
|
||||
}
|
||||
|
||||
get shortUsername() {
|
||||
let array = this.username.split(' ');
|
||||
if (array.length >= 2) return array[0].charAt(0) + array[1].charAt(0);
|
||||
else return this.username.charAt(0);
|
||||
}
|
||||
}
|
1
projects/ui/src/lib/avatar/avatar.interface.ts
Normal file
1
projects/ui/src/lib/avatar/avatar.interface.ts
Normal file
@ -0,0 +1 @@
|
||||
export type AvatarSize = 'default' | 'small' | 'medium' | 'large';
|
18
projects/ui/src/lib/avatar/avatar.module.ts
Normal file
18
projects/ui/src/lib/avatar/avatar.module.ts
Normal file
@ -0,0 +1,18 @@
|
||||
import { NgModule } from '@angular/core';
|
||||
import { CommonModule } from '@angular/common';
|
||||
import { AvatarComponent } from './avatar.component';
|
||||
|
||||
|
||||
|
||||
@NgModule({
|
||||
declarations: [
|
||||
AvatarComponent
|
||||
],
|
||||
imports: [
|
||||
CommonModule
|
||||
],
|
||||
exports: [
|
||||
AvatarComponent
|
||||
]
|
||||
})
|
||||
export class AvatarModule { }
|
@ -1,4 +1,4 @@
|
||||
<div class="popup-overlay" (click)="closeViaClick($event)" [attr.style]="'--local-overlay:' + config.overlay.background" [ngClass]="{'shown': loaded, 'hiding': hiding}" skirdaKeyboard (escape)="closeViaEscape($event)">
|
||||
<div class="popup-overlay" [style.left]="offsetLeft + 'px'" (click)="closeViaClick($event)" [attr.style]="'--local-overlay:' + config.overlay.background" [ngClass]="{'shown': loaded, 'hiding': hiding}" skirdaKeyboard (escape)="closeViaEscape($event)">
|
||||
<div class="popup-window-wrapper" [attr.data-appearance]="config.appearance" [attr.data-theme]="config.theme">
|
||||
<div class="popup-window">
|
||||
<div class="popup-head">
|
||||
|
@ -1,5 +1,10 @@
|
||||
:host::ng-deep {
|
||||
position: absolute;
|
||||
width: 100vw;
|
||||
height: 100vh;
|
||||
// background-color: red;
|
||||
top: 0;
|
||||
left: 0px;
|
||||
|
||||
@keyframes show {
|
||||
from {
|
||||
@ -43,10 +48,10 @@
|
||||
|
||||
.popup-overlay {
|
||||
display: block;
|
||||
position: fixed;
|
||||
position: absolute;
|
||||
top: 0;
|
||||
left: 0;
|
||||
width: 100%;
|
||||
width: 100vw;
|
||||
height: 100vh;
|
||||
background-color: var(--local-overlay, var(--sk-overlay));
|
||||
display: flex;
|
||||
|
@ -1,6 +1,7 @@
|
||||
import {
|
||||
AfterViewInit,
|
||||
Component,
|
||||
ElementRef,
|
||||
EventEmitter,
|
||||
Input,
|
||||
OnInit,
|
||||
@ -21,16 +22,21 @@ export class PopupComponent implements OnInit, AfterViewInit {
|
||||
loaded: boolean = false;
|
||||
hiding: boolean = false;
|
||||
contentQueue?: TemplateRef<any>;
|
||||
offsetLeft: number = 0;
|
||||
|
||||
@Output() event: EventEmitter<string> = new EventEmitter();
|
||||
|
||||
@ViewChild(PopupDirective) private popupContent!: PopupDirective;
|
||||
|
||||
constructor() {}
|
||||
constructor(private element: ElementRef<HTMLElement>) {}
|
||||
|
||||
ngOnInit(): void {}
|
||||
|
||||
ngAfterViewInit(): void {
|
||||
setTimeout(() => {
|
||||
this.offsetLeft =
|
||||
-this.element.nativeElement.getBoundingClientRect().left;
|
||||
}, 0);
|
||||
if (this.contentQueue) {
|
||||
this.load(this.contentQueue);
|
||||
this.contentQueue = undefined;
|
||||
|
@ -10,8 +10,9 @@ import { ButtonModule } from './button/button.module';
|
||||
import { TagModule } from './tag/tag.module';
|
||||
import { PipesModule } from './pipes/pipes.module';
|
||||
import { GameModule } from './game/game.module';
|
||||
import { PopupModule } from '../public-api';
|
||||
import { DirectivesModule } from './directives/directives.module';
|
||||
import { PopupModule } from './popup/popup.module';
|
||||
import { AvatarModule } from './avatar/avatar.module';
|
||||
|
||||
@NgModule({
|
||||
declarations: [],
|
||||
@ -29,6 +30,7 @@ import { DirectivesModule } from './directives/directives.module';
|
||||
GameModule,
|
||||
PopupModule,
|
||||
DirectivesModule,
|
||||
AvatarModule,
|
||||
],
|
||||
exports: [
|
||||
IconModule,
|
||||
@ -44,6 +46,7 @@ import { DirectivesModule } from './directives/directives.module';
|
||||
GameModule,
|
||||
PopupModule,
|
||||
DirectivesModule,
|
||||
AvatarModule,
|
||||
],
|
||||
})
|
||||
export class UiModule {}
|
||||
|
21
projects/ui/src/lib/utils/string-hash-to-hsl.ts
Normal file
21
projects/ui/src/lib/utils/string-hash-to-hsl.ts
Normal file
@ -0,0 +1,21 @@
|
||||
/**
|
||||
* Converts a string to an HSL color
|
||||
* @param value string to convert
|
||||
* @return HSL color string
|
||||
*/
|
||||
export function stringHashToHsl(value: string): string {
|
||||
if (value === ``) return ``;
|
||||
|
||||
let hash = 0;
|
||||
|
||||
for (let i = 0; i < value.length; i++) {
|
||||
hash = value.charCodeAt(i) + ((hash << 5) - hash);
|
||||
hash = hash & hash;
|
||||
}
|
||||
|
||||
const hue = hash % 360;
|
||||
const saturation = 60 + (hash % 5);
|
||||
const lightness = 80 + (hash % 5);
|
||||
|
||||
return `hsl(${hue},${saturation}%,${lightness}%)`;
|
||||
}
|
@ -14,3 +14,4 @@ export * from './lib/tag/tag.module';
|
||||
export * from './lib/pipes/pipes.module';
|
||||
export * from './lib/game/game.module';
|
||||
export * from './lib/popup/popup.module';
|
||||
export * from './lib/avatar/avatar.module';
|
||||
|
@ -36,6 +36,7 @@
|
||||
transition: 0.1s ease;
|
||||
border-radius: var(--sk-br-m);
|
||||
cursor: pointer;
|
||||
flex-shrink: 0;
|
||||
|
||||
&:hover {
|
||||
background-color: rgba(255, 255, 255, 0.05);
|
||||
|
@ -26,6 +26,6 @@
|
||||
background-color: rgba(0,0,0,0.15);
|
||||
display: flex;
|
||||
backdrop-filter: blur(2rem);
|
||||
overflow-y: auto;
|
||||
// overflow-y: auto;
|
||||
}
|
||||
}
|
||||
|
@ -56,7 +56,7 @@ export class GamePageComponent implements OnInit, OnDestroy {
|
||||
// background: 'rgba(255, 255, 255, 1)',
|
||||
},
|
||||
body: 'Humblebrag chillwave sriracha, ramps polaroid distillery edison bulb palo santo etsy sus pabst knausgaard typewriter dreamcatcher.',
|
||||
theme: 'light',
|
||||
theme: 'dark',
|
||||
})
|
||||
.subscribe((event) => {
|
||||
console.log(`event: ${event}`);
|
||||
|
@ -29,3 +29,8 @@
|
||||
<p>Church-key listicle whatever hoodie hexagon pour-over ascot paleo tacos, organic aesthetic tbh meggings raclette.</p>
|
||||
</ng-template>
|
||||
<skirda-button (click)="openPopup(popupContent)">Call popup</skirda-button>
|
||||
|
||||
<hr>
|
||||
|
||||
<h3>Avatar</h3>
|
||||
<skirda-avatar></skirda-avatar>
|
||||
|
Loading…
Reference in New Issue
Block a user