This commit is contained in:
병준 박 2019-10-11 18:25:06 +09:00
commit 57957cc164
16 changed files with 237 additions and 57 deletions

View File

@ -8,19 +8,24 @@ import {
} from '@ucap-webmessenger/api'; } from '@ucap-webmessenger/api';
export interface MassTalkDownloadRequest extends APIRequest { export interface MassTalkDownloadRequest extends APIRequest {
userSeq: string; userSeq: number;
deviceType: DeviceType; deviceType: DeviceType;
token: string; token: string;
eventMassSeq?: string; eventMassSeq?: number;
} }
export interface MassTalkDownloadResponse extends APIResponse { export interface MassTalkDownloadResponse extends APIResponse {
Content?: string; content?: string;
UserName?: string; userName?: string;
RegDate?: string; regDate?: string;
} }
const massTalkDownloadEncodeMap = {}; const massTalkDownloadEncodeMap = {
userSeq: 'p_user_seq',
deviceType: 'p_device_type',
token: 'p_token',
eventMassSeq: 'p_event_mass_seq'
};
export const encodeMassTalkDownload: APIEncoder<MassTalkDownloadRequest> = ( export const encodeMassTalkDownload: APIEncoder<MassTalkDownloadRequest> = (
req: MassTalkDownloadRequest req: MassTalkDownloadRequest
@ -31,5 +36,11 @@ export const encodeMassTalkDownload: APIEncoder<MassTalkDownloadRequest> = (
export const decodeMassTalkDownload: APIDecoder<MassTalkDownloadResponse> = ( export const decodeMassTalkDownload: APIDecoder<MassTalkDownloadResponse> = (
res: any res: any
) => { ) => {
return {} as MassTalkDownloadResponse; return {
statusCode: res.StatusCode,
errorMessage: res.ErrorMessage,
content: res.Content,
userName: res.UserName,
regDate: res.RegDate
} as MassTalkDownloadResponse;
}; };

View File

@ -5,37 +5,20 @@
<div fxFlex fxLayout="row" fxLayoutAlign="space-between center"> <div fxFlex fxLayout="row" fxLayoutAlign="space-between center">
<div fxLayout="row" fxLayoutAlign="start center"> <div fxLayout="row" fxLayoutAlign="start center">
<!-- RESPONSIVE CHATS BUTTON--> <!-- RESPONSIVE CHATS BUTTON-->
<button <button mat-icon-button aria-label="chats button" fxHide.gt-md class="responsive-chats-button">
mat-icon-button
aria-label="chats button"
fxHide.gt-md
class="responsive-chats-button"
>
<mat-icon>chat</mat-icon> <mat-icon>chat</mat-icon>
</button> </button>
<!-- / RESPONSIVE CHATS BUTTON--> <!-- / RESPONSIVE CHATS BUTTON-->
</div> </div>
<div> <div>
<button <button *ngIf="!!roomInfo" mat-icon-button (click)="onClickReceiveAlarm($event)"
*ngIf="!!roomInfo" aria-label="Toggle Receive Alarm">
mat-icon-button <mat-icon class="amber-fg" *ngIf="roomInfo.receiveAlarm">notifications_active</mat-icon>
(click)="onClickReceiveAlarm($event)" <mat-icon class="secondary-text" *ngIf="!roomInfo.receiveAlarm">notifications_off</mat-icon>
aria-label="Toggle Receive Alarm"
>
<mat-icon class="amber-fg" *ngIf="roomInfo.receiveAlarm"
>notifications_active</mat-icon
>
<mat-icon class="secondary-text" *ngIf="!roomInfo.receiveAlarm"
>notifications_off</mat-icon
>
</button> </button>
<button <button mat-icon-button [matMenuTriggerFor]="contactMenu" aria-label="more">
mat-icon-button
[matMenuTriggerFor]="contactMenu"
aria-label="more"
>
<mat-icon>more_vert</mat-icon> <mat-icon>more_vert</mat-icon>
</button> </button>
@ -48,18 +31,12 @@
</div> </div>
</mat-toolbar> </mat-toolbar>
<!-- / CHAT TOOLBAR --> <!-- / CHAT TOOLBAR -->
<mat-progress-bar <mat-progress-bar *ngIf="eventListProcessing$ | async" mode="indeterminate"></mat-progress-bar>
*ngIf="eventListProcessing$ | async"
mode="indeterminate"
></mat-progress-bar>
<!-- CHAT CONTENT --> <!-- CHAT CONTENT -->
<div fxFlex="1 1 auto" class="chat-content" #messageBoxContainer> <div fxFlex="1 1 auto" class="chat-content" #messageBoxContainer>
<!-- CHAT MESSAGES --> <!-- CHAT MESSAGES -->
<ucap-chat-messages <ucap-chat-messages [messages]="eventList$ | async" [userInfos]="userInfoList$ | async" [loginRes]="loginRes"
[messages]="eventList$ | async" (massDetail)="onMassDetail($event)">
[userInfos]="userInfoList$ | async"
[loginRes]="loginRes"
>
</ucap-chat-messages> </ucap-chat-messages>
<!-- CHAT MESSAGES --> <!-- CHAT MESSAGES -->
</div> </div>

View File

@ -14,6 +14,7 @@ import { Info, EventType } from '@ucap-webmessenger/protocol-event';
import * as AppStore from '@app/store'; import * as AppStore from '@app/store';
import * as EventStore from '@app/store/messenger/event'; import * as EventStore from '@app/store/messenger/event';
import * as ChatStore from '@app/store/messenger/chat';
import * as RoomStore from '@app/store/messenger/room'; import * as RoomStore from '@app/store/messenger/room';
import { LoginResponse } from '@ucap-webmessenger/protocol-authentication'; import { LoginResponse } from '@ucap-webmessenger/protocol-authentication';
import { SessionStorageService } from '@ucap-webmessenger/web-storage'; import { SessionStorageService } from '@ucap-webmessenger/web-storage';
@ -118,4 +119,13 @@ export class MessagesComponent implements OnInit, OnDestroy, AfterViewChecked {
this.messageBoxContainer.nativeElement.scrollTop = this.messageBoxContainer.nativeElement.scrollHeight; this.messageBoxContainer.nativeElement.scrollTop = this.messageBoxContainer.nativeElement.scrollHeight;
} catch (err) {} } catch (err) {}
} }
/** MassText Detail View */
onMassDetail(value: number) {
this.store.dispatch(
ChatStore.selectedMassDetail({
massEventSeq: value
})
);
}
} }

View File

@ -45,6 +45,7 @@ import * as OptionStore from '@app/store/messenger/option';
import * as QueryStore from '@app/store/messenger/query'; import * as QueryStore from '@app/store/messenger/query';
import * as SyncStore from '@app/store/messenger/sync'; import * as SyncStore from '@app/store/messenger/sync';
import { VerInfo2, KEY_VER_INFO } from '@app/types/ver-info.type'; import { VerInfo2, KEY_VER_INFO } from '@app/types/ver-info.type';
import { KEY_LOGIN_RES_INFO } from '@app/types/login-res-info.type';
@Injectable() @Injectable()
export class AppMessengerResolver implements Resolve<void> { export class AppMessengerResolver implements Resolve<void> {
@ -114,6 +115,11 @@ export class AppMessengerResolver implements Resolve<void> {
}), }),
switchMap(res => { switchMap(res => {
loginRes = res; loginRes = res;
this.sessionStorageService.set<LoginResponse>(KEY_LOGIN_RES_INFO, {
...loginRes
});
return forkJoin([ return forkJoin([
this.queryProtocolService.auth({ this.queryProtocolService.auth({
deviceType: environmentsInfo.deviceType deviceType: environmentsInfo.deviceType

View File

@ -1,5 +1,9 @@
import { createAction, props } from '@ngrx/store'; import { createAction, props } from '@ngrx/store';
import { Info } from '@ucap-webmessenger/protocol-event'; import { Info } from '@ucap-webmessenger/protocol-event';
import {
MassTalkDownloadRequest,
MassTalkDownloadResponse
} from '@ucap-webmessenger/api-common';
export const selectedRoom = createAction( export const selectedRoom = createAction(
'[Messenger::Chat] selectedRoom', '[Messenger::Chat] selectedRoom',
@ -13,3 +17,20 @@ export const newEventMessage = createAction(
info: Info; info: Info;
}>() }>()
); );
export const selectedMassDetail = createAction(
'[Messenger::Chat] selectedMassDetail',
props<{ massEventSeq: number }>()
);
export const massTalkDownload = createAction(
'[Messenger::Chat] massTalkDownload',
props<MassTalkDownloadRequest>()
);
export const massTalkDownloadSuccess = createAction(
'[Messenger::Chat] massTalkDownload Success',
props<MassTalkDownloadResponse>()
);
export const massTalkDownloadFailure = createAction(
'[Messenger::Chat] massTalkDownload Failure',
props<{ error: any }>()
);

View File

@ -1,15 +1,76 @@
import { Injectable } from '@angular/core'; import { Injectable, Inject } from '@angular/core';
import { Actions } from '@ngrx/effects'; import { Actions, ofType, createEffect } from '@ngrx/effects';
import { Store } from '@ngrx/store'; import { Store } from '@ngrx/store';
import { NGXLogger } from 'ngx-logger'; import { NGXLogger } from 'ngx-logger';
import { catchError, exhaustMap, map, tap, switchMap } from 'rxjs/operators';
import {
selectedMassDetail,
massTalkDownload,
massTalkDownloadFailure,
massTalkDownloadSuccess
} from './actions';
import { of } from 'rxjs';
import { SessionStorageService } from '@ucap-webmessenger/web-storage';
import { StatusCode } from '@ucap-webmessenger/api';
import { CommonApiService } from '@ucap-webmessenger/api-common';
import { KEY_LOGIN_RES_INFO } from '@app/types/login-res-info.type';
import { EnvironmentsInfo, KEY_ENVIRONMENTS_INFO } from '@app/types';
import { LoginResponse } from '@ucap-webmessenger/protocol-authentication';
@Injectable() @Injectable()
export class Effects { export class Effects {
selectedMassDetail$ = createEffect(() =>
this.actions$.pipe(
ofType(selectedMassDetail),
map(action => {
const loginResInfo: LoginResponse = this.sessionStorageService.get<
LoginResponse
>(KEY_LOGIN_RES_INFO);
const environmentsInfo = this.sessionStorageService.get<
EnvironmentsInfo
>(KEY_ENVIRONMENTS_INFO);
return massTalkDownload({
userSeq: loginResInfo.userSeq,
deviceType: environmentsInfo.deviceType,
eventMassSeq: Number(action.massEventSeq),
token: loginResInfo.tokenString
});
})
)
);
massTalkDownload$ = createEffect(
() => {
return this.actions$.pipe(
ofType(massTalkDownload),
map(action => action),
exhaustMap(req => {
return this.commonApiService.massTalkDownload(req).pipe(
map(res => {
this.logger.debug(res);
if (res.statusCode === StatusCode.Success) {
this.store.dispatch(massTalkDownloadSuccess(res));
} else {
this.store.dispatch(massTalkDownloadFailure({ error: res }));
}
}),
catchError(error => of(massTalkDownloadFailure({ error })))
);
})
);
},
{ dispatch: false }
);
constructor( constructor(
private actions$: Actions, private actions$: Actions,
private commonApiService: CommonApiService,
private sessionStorageService: SessionStorageService,
private store: Store<any>, private store: Store<any>,
private logger: NGXLogger private logger: NGXLogger
) {} ) {}

View File

@ -1,6 +1,12 @@
import { createReducer, on } from '@ngrx/store'; import { createReducer, on } from '@ngrx/store';
import { initialState } from './state'; import { initialState } from './state';
import { selectedRoom } from './actions'; import {
selectedRoom,
selectedMassDetail,
massTalkDownloadFailure,
massTalkDownload,
massTalkDownloadSuccess
} from './actions';
export const reducer = createReducer( export const reducer = createReducer(
initialState, initialState,
@ -9,5 +15,31 @@ export const reducer = createReducer(
...state, ...state,
selectedRoom: action.roomSeq selectedRoom: action.roomSeq
}; };
}),
on(selectedMassDetail, (state, action) => {
return {
...state,
selectedMassDetail: action.massEventSeq
};
}),
on(massTalkDownload, (state, action) => {
return {
...state,
massDetailProcessing: true
};
}),
on(massTalkDownloadSuccess, (state, action) => {
return {
...state,
massDetailProcessing: false
};
}),
on(massTalkDownloadFailure, (state, action) => {
return {
...state,
massDetailProcessing: false
};
}) })
); );

View File

@ -2,10 +2,15 @@ import { Selector, createSelector } from '@ngrx/store';
export interface State { export interface State {
selectedRoom: string | null; selectedRoom: string | null;
selectedMassDetail: number | null;
massDetailProcessing: boolean;
} }
export const initialState: State = { export const initialState: State = {
selectedRoom: null selectedRoom: null,
selectedMassDetail: null,
massDetailProcessing: false
}; };
export function selectors<S>(selector: Selector<any, State>) { export function selectors<S>(selector: Selector<any, State>) {
@ -13,6 +18,10 @@ export function selectors<S>(selector: Selector<any, State>) {
selectedRoom: createSelector( selectedRoom: createSelector(
selector, selector,
(state: State) => state.selectedRoom (state: State) => state.selectedRoom
),
selectedMassDetail: createSelector(
selector,
(state: State) => state.selectedMassDetail
) )
}; };
} }

View File

@ -0,0 +1 @@
export const KEY_LOGIN_RES_INFO = 'ucap::LOGIN_RES_INFO';

View File

@ -1,8 +1,12 @@
<p> <p>
<span> <span>
{{ message.sentMessage }} {{ content }}
</span> </span>
<span> <span>
{{ message.sendDate | date: 'short' }} {{ message.sendDate | date: 'short' }}
</span> </span>
{{detailButteonShow}}
<span *ngIf="detailButteonShow">
<button mat-button (click)="onClickDetailView()">Detail View</button>
</span>
</p> </p>

View File

@ -1,5 +1,7 @@
import { Component, OnInit, Input } from '@angular/core'; import { Component, OnInit, Input, Output, EventEmitter } from '@angular/core';
import { Info } from '@ucap-webmessenger/protocol-event'; import { Info } from '@ucap-webmessenger/protocol-event';
import { NGXLogger } from 'ngx-logger';
import { StatusCode } from '@ucap-webmessenger/api';
@Component({ @Component({
selector: 'ucap-chat-message-box-mass', selector: 'ucap-chat-message-box-mass',
@ -10,7 +12,46 @@ export class MassComponent implements OnInit {
@Input() @Input()
message: Info; message: Info;
constructor() {} @Output()
massDetail = new EventEmitter<number>();
ngOnInit() {} content: string;
eventMassSeq: number;
detailButteonShow = true;
constructor(private logger: NGXLogger) {}
ngOnInit() {
try {
const contentJson: MassTextInfo = JSON.parse(this.message.sentMessage);
if (contentJson.StatusCode === StatusCode.Success) {
this.content = contentJson.Content;
} else {
this.content = contentJson.ErrorMessage || '[Error] System Error!!';
this.detailButteonShow = false;
}
if (!!contentJson.EventMassSeq) {
this.eventMassSeq = contentJson.EventMassSeq;
} else {
this.detailButteonShow = false;
}
} catch (e) {
this.logger.error(e);
this.detailButteonShow = false;
}
}
onClickDetailView() {
this.massDetail.emit(this.eventMassSeq);
}
}
export interface MassTextInfo {
StatusCode?: StatusCode;
ErrorMessage?: string;
EventMassSeq?: number;
RoomID?: string;
RegDate?: Date;
Content?: string;
} }

View File

@ -17,7 +17,9 @@
</div> </div>
<ng-container [ngSwitch]="message.type"> <ng-container [ngSwitch]="message.type">
<ucap-chat-message-box-text *ngSwitchCase="EventType.Character" [message]="message"></ucap-chat-message-box-text> <ucap-chat-message-box-text *ngSwitchCase="EventType.Character" [message]="message"></ucap-chat-message-box-text>
<ucap-chat-message-box-mass *ngSwitchCase="EventType.MassText" [message]="message"></ucap-chat-message-box-mass> <ucap-chat-message-box-mass *ngSwitchCase="EventType.MassText" [message]="message"
(massDetail)="onMassDetail($event)">
</ucap-chat-message-box-mass>
<div *ngSwitchCase="EventType.Join">Join</div> <div *ngSwitchCase="EventType.Join">Join</div>
<div *ngSwitchDefault> <div *ngSwitchDefault>
date splitter date splitter

View File

@ -1,4 +1,4 @@
import { Component, OnInit, Input } from '@angular/core'; import { Component, OnInit, Input, EventEmitter, Output } from '@angular/core';
import { Info, EventType } from '@ucap-webmessenger/protocol-event'; import { Info, EventType } from '@ucap-webmessenger/protocol-event';
import { import {
@ -22,6 +22,9 @@ export class MessagesComponent implements OnInit {
@Input() @Input()
userInfos?: UserInfo[]; userInfos?: UserInfo[];
@Output()
massDetail = new EventEmitter<number>();
EventType = EventType; EventType = EventType;
profileImageRoot: string; profileImageRoot: string;
@ -61,4 +64,8 @@ export class MessagesComponent implements OnInit {
} }
return ''; return '';
} }
onMassDetail(value: number) {
this.massDetail.emit(value);
}
} }

View File

@ -7,6 +7,7 @@ import { FlexLayoutModule } from '@angular/flex-layout';
import { MatFormFieldModule } from '@angular/material/form-field'; import { MatFormFieldModule } from '@angular/material/form-field';
import { MatIconModule } from '@angular/material/icon'; import { MatIconModule } from '@angular/material/icon';
import { MatInputModule } from '@angular/material/input'; import { MatInputModule } from '@angular/material/input';
import { MatButtonModule } from '@angular/material/button';
import { FormComponent } from './components/form.component'; import { FormComponent } from './components/form.component';
import { MessagesComponent } from './components/messages.component'; import { MessagesComponent } from './components/messages.component';
@ -55,7 +56,8 @@ const SERVICES = [];
FlexLayoutModule, FlexLayoutModule,
MatFormFieldModule, MatFormFieldModule,
MatIconModule, MatIconModule,
MatInputModule MatInputModule,
MatButtonModule
], ],
exports: [...COMPONENTS], exports: [...COMPONENTS],
declarations: [...COMPONENTS] declarations: [...COMPONENTS]

View File

@ -28,9 +28,6 @@ export class ExpansionPanelComponent implements OnInit {
@Input() @Input()
favoritBuddyList: UserInfo[]; favoritBuddyList: UserInfo[];
@Output()
selectBuddy = new EventEmitter<UserInfo>();
@ContentChild(ExpansionPanelItemDirective, { @ContentChild(ExpansionPanelItemDirective, {
read: TemplateRef, read: TemplateRef,
static: true static: true
@ -43,10 +40,6 @@ export class ExpansionPanelComponent implements OnInit {
ngOnInit() {} ngOnInit() {}
onClickBuddy(buddy: UserInfo) {
this.selectBuddy.emit(buddy);
}
expandMore() { expandMore() {
this.groupAccordion.openAll(); this.groupAccordion.openAll();
} }