mirror of
https://github.com/billsonnn/nitro-react.git
synced 2025-01-19 05:46:27 +01:00
Add AvatarEditorView
This commit is contained in:
parent
5c73d8d459
commit
2736f262ac
8
src/events/avatar-editor/AvatarEditorEvent.ts
Normal file
8
src/events/avatar-editor/AvatarEditorEvent.ts
Normal file
@ -0,0 +1,8 @@
|
|||||||
|
import { NitroEvent } from 'nitro-renderer';
|
||||||
|
|
||||||
|
export class AvatarEditorEvent extends NitroEvent
|
||||||
|
{
|
||||||
|
public static SHOW_EDITOR: string = 'AEE_SHOW_EDITOR';
|
||||||
|
public static HIDE_EDITOR: string = 'AEE_HIDE_EDITOR';
|
||||||
|
public static TOGGLE_EDITOR: string = 'AEE_TOGGLE_EDITOR';
|
||||||
|
}
|
1
src/events/avatar-editor/index.ts
Normal file
1
src/events/avatar-editor/index.ts
Normal file
@ -0,0 +1 @@
|
|||||||
|
export * from './AvatarEditorEvent';
|
@ -1,3 +1,4 @@
|
|||||||
|
export * from './avatar-editor';
|
||||||
export * from './catalog';
|
export * from './catalog';
|
||||||
export * from './friend-list';
|
export * from './friend-list';
|
||||||
export * from './inventory';
|
export * from './inventory';
|
||||||
|
@ -1,3 +1,4 @@
|
|||||||
|
@import './avatar-editor/AvatarEditorView';
|
||||||
@import './avatar-image/AvatarImage';
|
@import './avatar-image/AvatarImage';
|
||||||
@import './badge-image/BadgeImage';
|
@import './badge-image/BadgeImage';
|
||||||
@import './catalog/CatalogView';
|
@import './catalog/CatalogView';
|
||||||
|
8
src/views/avatar-editor/AvatarEditorView.scss
Normal file
8
src/views/avatar-editor/AvatarEditorView.scss
Normal file
@ -0,0 +1,8 @@
|
|||||||
|
.nitro-avatar-editor {
|
||||||
|
width: 550px;
|
||||||
|
|
||||||
|
.content-area {
|
||||||
|
height: 300px;
|
||||||
|
max-height: 300px;
|
||||||
|
}
|
||||||
|
}
|
59
src/views/avatar-editor/AvatarEditorView.tsx
Normal file
59
src/views/avatar-editor/AvatarEditorView.tsx
Normal file
@ -0,0 +1,59 @@
|
|||||||
|
import { FC, useCallback, useEffect, useReducer, useState } from 'react';
|
||||||
|
import { AvatarEditorEvent } from '../../events/avatar-editor';
|
||||||
|
import { useUiEvent } from '../../hooks/events/ui/ui-event';
|
||||||
|
import { NitroCardContentView, NitroCardHeaderView, NitroCardTabsView, NitroCardView } from '../../layout';
|
||||||
|
import { LocalizeText } from '../../utils/LocalizeText';
|
||||||
|
import { AvatarEditorViewProps } from './AvatarEditorView.types';
|
||||||
|
import { AvatarEditorContextProvider } from './context/AvatarEditorContext';
|
||||||
|
import { AvatarEditorReducer, initialAvatarEditor } from './reducers/AvatarEditorReducer';
|
||||||
|
|
||||||
|
export const AvatarEditorView: FC<AvatarEditorViewProps> = props =>
|
||||||
|
{
|
||||||
|
const [ isVisible, setIsVisible ] = useState(false);
|
||||||
|
const [ avatarEditorState, dispatchAvatarEditorState ] = useReducer(AvatarEditorReducer, initialAvatarEditor);
|
||||||
|
const { } = avatarEditorState;
|
||||||
|
|
||||||
|
const onAvatarEditorEvent = useCallback((event: AvatarEditorEvent) =>
|
||||||
|
{
|
||||||
|
switch(event.type)
|
||||||
|
{
|
||||||
|
case AvatarEditorEvent.SHOW_EDITOR:
|
||||||
|
setIsVisible(true);
|
||||||
|
return;
|
||||||
|
case AvatarEditorEvent.HIDE_EDITOR:
|
||||||
|
setIsVisible(false);
|
||||||
|
return;
|
||||||
|
case AvatarEditorEvent.TOGGLE_EDITOR:
|
||||||
|
setIsVisible(value => !value);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}, []);
|
||||||
|
|
||||||
|
useUiEvent(AvatarEditorEvent.SHOW_EDITOR, onAvatarEditorEvent);
|
||||||
|
useUiEvent(AvatarEditorEvent.HIDE_EDITOR, onAvatarEditorEvent);
|
||||||
|
useUiEvent(AvatarEditorEvent.TOGGLE_EDITOR, onAvatarEditorEvent);
|
||||||
|
|
||||||
|
useEffect(() =>
|
||||||
|
{
|
||||||
|
if(!isVisible) return;
|
||||||
|
}, [ isVisible ]);
|
||||||
|
|
||||||
|
return (
|
||||||
|
<AvatarEditorContextProvider value={ { avatarEditorState, dispatchAvatarEditorState } }>
|
||||||
|
{ isVisible &&
|
||||||
|
<NitroCardView className="nitro-avatar-editor">
|
||||||
|
<NitroCardHeaderView headerText={ LocalizeText('avatareditor.title') } onCloseClick={ event => setIsVisible(false) } />
|
||||||
|
<NitroCardTabsView>
|
||||||
|
</NitroCardTabsView>
|
||||||
|
<NitroCardContentView>
|
||||||
|
<div className="row h-100">
|
||||||
|
<div className="col-3">
|
||||||
|
</div>
|
||||||
|
<div className="col">
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</NitroCardContentView>
|
||||||
|
</NitroCardView> }
|
||||||
|
</AvatarEditorContextProvider>
|
||||||
|
);
|
||||||
|
}
|
4
src/views/avatar-editor/AvatarEditorView.types.ts
Normal file
4
src/views/avatar-editor/AvatarEditorView.types.ts
Normal file
@ -0,0 +1,4 @@
|
|||||||
|
export interface AvatarEditorViewProps
|
||||||
|
{
|
||||||
|
|
||||||
|
}
|
14
src/views/avatar-editor/context/AvatarEditorContext.tsx
Normal file
14
src/views/avatar-editor/context/AvatarEditorContext.tsx
Normal file
@ -0,0 +1,14 @@
|
|||||||
|
import { createContext, FC, useContext } from 'react';
|
||||||
|
import { AvatarEditorContextProps, IAvatarEditorContext } from './AvatarEditorContext.types';
|
||||||
|
|
||||||
|
const AvatarEditorContext = createContext<IAvatarEditorContext>({
|
||||||
|
avatarEditorState: null,
|
||||||
|
dispatchAvatarEditorState: null
|
||||||
|
});
|
||||||
|
|
||||||
|
export const AvatarEditorContextProvider: FC<AvatarEditorContextProps> = props =>
|
||||||
|
{
|
||||||
|
return <AvatarEditorContext.Provider value={ props.value }>{ props.children }</AvatarEditorContext.Provider>
|
||||||
|
}
|
||||||
|
|
||||||
|
export const useAvatarEditorContext = () => useContext(AvatarEditorContext);
|
13
src/views/avatar-editor/context/AvatarEditorContext.types.ts
Normal file
13
src/views/avatar-editor/context/AvatarEditorContext.types.ts
Normal file
@ -0,0 +1,13 @@
|
|||||||
|
import { Dispatch, ProviderProps } from 'react';
|
||||||
|
import { IAvatarEditorAction, IAvatarEditorState } from '../reducers/AvatarEditorReducer';
|
||||||
|
|
||||||
|
export interface IAvatarEditorContext
|
||||||
|
{
|
||||||
|
avatarEditorState: IAvatarEditorState;
|
||||||
|
dispatchAvatarEditorState: Dispatch<IAvatarEditorAction>;
|
||||||
|
}
|
||||||
|
|
||||||
|
export interface AvatarEditorContextProps extends ProviderProps<IAvatarEditorContext>
|
||||||
|
{
|
||||||
|
|
||||||
|
}
|
30
src/views/avatar-editor/reducers/AvatarEditorReducer.tsx
Normal file
30
src/views/avatar-editor/reducers/AvatarEditorReducer.tsx
Normal file
@ -0,0 +1,30 @@
|
|||||||
|
import { Reducer } from 'react';
|
||||||
|
|
||||||
|
export interface IAvatarEditorState
|
||||||
|
{
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
export interface IAvatarEditorAction
|
||||||
|
{
|
||||||
|
type: string;
|
||||||
|
payload: {
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
export class AvatarEditorActions
|
||||||
|
{
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
export const initialAvatarEditor: IAvatarEditorState = {
|
||||||
|
}
|
||||||
|
|
||||||
|
export const AvatarEditorReducer: Reducer<IAvatarEditorState, IAvatarEditorAction> = (state, action) =>
|
||||||
|
{
|
||||||
|
switch(action.type)
|
||||||
|
{
|
||||||
|
default:
|
||||||
|
return state;
|
||||||
|
}
|
||||||
|
}
|
@ -3,6 +3,7 @@ import { useCallback, useEffect, useState } from 'react';
|
|||||||
import { useRoomSessionManagerEvent } from '../../hooks/events/nitro/session/room-session-manager-event';
|
import { useRoomSessionManagerEvent } from '../../hooks/events/nitro/session/room-session-manager-event';
|
||||||
import { TransitionAnimation } from '../../transitions/TransitionAnimation';
|
import { TransitionAnimation } from '../../transitions/TransitionAnimation';
|
||||||
import { TransitionAnimationTypes } from '../../transitions/TransitionAnimation.types';
|
import { TransitionAnimationTypes } from '../../transitions/TransitionAnimation.types';
|
||||||
|
import { AvatarEditorView } from '../avatar-editor/AvatarEditorView';
|
||||||
import { CatalogView } from '../catalog/CatalogView';
|
import { CatalogView } from '../catalog/CatalogView';
|
||||||
import { FriendListView } from '../friend-list/FriendListView';
|
import { FriendListView } from '../friend-list/FriendListView';
|
||||||
import { HotelView } from '../hotel-view/HotelView';
|
import { HotelView } from '../hotel-view/HotelView';
|
||||||
@ -48,6 +49,7 @@ export function MainView(props: MainViewProps): JSX.Element
|
|||||||
<TransitionAnimation className="nitro-toolbar-container" type={ TransitionAnimationTypes.FADE_UP } inProp={ isReady } timeout={ 300 }>
|
<TransitionAnimation className="nitro-toolbar-container" type={ TransitionAnimationTypes.FADE_UP } inProp={ isReady } timeout={ 300 }>
|
||||||
<ToolbarView isInRoom={ !landingViewVisible } />
|
<ToolbarView isInRoom={ !landingViewVisible } />
|
||||||
</TransitionAnimation>
|
</TransitionAnimation>
|
||||||
|
<AvatarEditorView />
|
||||||
<NavigatorView />
|
<NavigatorView />
|
||||||
<InventoryView />
|
<InventoryView />
|
||||||
<CatalogView />
|
<CatalogView />
|
||||||
|
@ -1,7 +1,7 @@
|
|||||||
import { UserInfoEvent } from 'nitro-renderer/src/nitro/communication/messages/incoming/user/data/UserInfoEvent';
|
import { UserInfoEvent } from 'nitro-renderer/src/nitro/communication/messages/incoming/user/data/UserInfoEvent';
|
||||||
import { UserInfoDataParser } from 'nitro-renderer/src/nitro/communication/messages/parser/user/data/UserInfoDataParser';
|
import { UserInfoDataParser } from 'nitro-renderer/src/nitro/communication/messages/parser/user/data/UserInfoDataParser';
|
||||||
import { MouseEvent, useCallback, useState } from 'react';
|
import { useCallback, useState } from 'react';
|
||||||
import { CatalogEvent, FriendListEvent, InventoryEvent, NavigatorEvent } from '../../events';
|
import { AvatarEditorEvent, CatalogEvent, FriendListEvent, InventoryEvent, NavigatorEvent } from '../../events';
|
||||||
import { dispatchUiEvent } from '../../hooks/events/ui/ui-event';
|
import { dispatchUiEvent } from '../../hooks/events/ui/ui-event';
|
||||||
import { CreateMessageHook } from '../../hooks/messages/message-event';
|
import { CreateMessageHook } from '../../hooks/messages/message-event';
|
||||||
import { TransitionAnimation } from '../../transitions/TransitionAnimation';
|
import { TransitionAnimation } from '../../transitions/TransitionAnimation';
|
||||||
@ -28,7 +28,7 @@ export function ToolbarView(props: ToolbarViewProps): JSX.Element
|
|||||||
setUserInfo(parser.userInfo);
|
setUserInfo(parser.userInfo);
|
||||||
}, []);
|
}, []);
|
||||||
|
|
||||||
function handleToolbarItemClick(event: MouseEvent, item: string): void
|
const handleToolbarItemClick = useCallback((item: string) =>
|
||||||
{
|
{
|
||||||
switch(item)
|
switch(item)
|
||||||
{
|
{
|
||||||
@ -44,8 +44,11 @@ export function ToolbarView(props: ToolbarViewProps): JSX.Element
|
|||||||
case ToolbarViewItems.FRIEND_LIST_ITEM:
|
case ToolbarViewItems.FRIEND_LIST_ITEM:
|
||||||
dispatchUiEvent(new CatalogEvent(FriendListEvent.TOGGLE_FRIEND_LIST));
|
dispatchUiEvent(new CatalogEvent(FriendListEvent.TOGGLE_FRIEND_LIST));
|
||||||
return;
|
return;
|
||||||
|
case ToolbarViewItems.CLOTHING_ITEM:
|
||||||
|
dispatchUiEvent(new AvatarEditorEvent(AvatarEditorEvent.TOGGLE_EDITOR));
|
||||||
|
return;
|
||||||
}
|
}
|
||||||
}
|
}, []);
|
||||||
|
|
||||||
function toggleMeToolbar(): void
|
function toggleMeToolbar(): void
|
||||||
{
|
{
|
||||||
@ -60,7 +63,7 @@ export function ToolbarView(props: ToolbarViewProps): JSX.Element
|
|||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
<TransitionAnimation type={ TransitionAnimationTypes.FADE_IN } inProp={ isMeExpanded } timeout={ 300 }>
|
<TransitionAnimation type={ TransitionAnimationTypes.FADE_IN } inProp={ isMeExpanded } timeout={ 300 }>
|
||||||
<ToolbarMeView setMeExpanded={ setMeExpanded } />
|
<ToolbarMeView setMeExpanded={ setMeExpanded } handleToolbarItemClick={ handleToolbarItemClick } />
|
||||||
</TransitionAnimation>
|
</TransitionAnimation>
|
||||||
<div className="d-flex nitro-toolbar py-1 px-3">
|
<div className="d-flex nitro-toolbar py-1 px-3">
|
||||||
<div className="navigation-items navigation-avatar pe-1 me-2">
|
<div className="navigation-items navigation-avatar pe-1 me-2">
|
||||||
@ -81,18 +84,18 @@ export function ToolbarView(props: ToolbarViewProps): JSX.Element
|
|||||||
<div className="navigation-item">
|
<div className="navigation-item">
|
||||||
<i className="icon icon-house"></i>
|
<i className="icon icon-house"></i>
|
||||||
</div>) }
|
</div>) }
|
||||||
<div className="navigation-item" onClick={ event => handleToolbarItemClick(event, ToolbarViewItems.NAVIGATOR_ITEM) }>
|
<div className="navigation-item" onClick={ event => handleToolbarItemClick(ToolbarViewItems.NAVIGATOR_ITEM) }>
|
||||||
<i className="icon icon-rooms"></i>
|
<i className="icon icon-rooms"></i>
|
||||||
</div>
|
</div>
|
||||||
<div className="navigation-item" onClick={ event => handleToolbarItemClick(event, ToolbarViewItems.CATALOG_ITEM) }>
|
<div className="navigation-item" onClick={ event => handleToolbarItemClick(ToolbarViewItems.CATALOG_ITEM) }>
|
||||||
<i className="icon icon-catalog"></i>
|
<i className="icon icon-catalog"></i>
|
||||||
</div>
|
</div>
|
||||||
<div className="navigation-item" onClick={ event => handleToolbarItemClick(event, ToolbarViewItems.INVENTORY_ITEM) }>
|
<div className="navigation-item" onClick={ event => handleToolbarItemClick(ToolbarViewItems.INVENTORY_ITEM) }>
|
||||||
<i className="icon icon-inventory"></i>
|
<i className="icon icon-inventory"></i>
|
||||||
{ (unseenInventoryCount > 0) && (
|
{ (unseenInventoryCount > 0) && (
|
||||||
<div className="position-absolute bg-danger px-1 py-0 rounded shadow count">{ unseenInventoryCount }</div>) }
|
<div className="position-absolute bg-danger px-1 py-0 rounded shadow count">{ unseenInventoryCount }</div>) }
|
||||||
</div>
|
</div>
|
||||||
<div className="navigation-item" onClick={ event => handleToolbarItemClick(event, ToolbarViewItems.FRIEND_LIST_ITEM) }>
|
<div className="navigation-item" onClick={ event => handleToolbarItemClick(ToolbarViewItems.FRIEND_LIST_ITEM) }>
|
||||||
<i className="icon icon-friendall"></i>
|
<i className="icon icon-friendall"></i>
|
||||||
{ (unseenFriendListCount > 0) && (
|
{ (unseenFriendListCount > 0) && (
|
||||||
<div className="position-absolute bg-danger px-1 py-0 rounded shadow count">{ unseenFriendListCount }</div>) }
|
<div className="position-absolute bg-danger px-1 py-0 rounded shadow count">{ unseenFriendListCount }</div>) }
|
||||||
|
@ -9,4 +9,5 @@ export class ToolbarViewItems
|
|||||||
public static INVENTORY_ITEM: string = 'TVI_INVENTORY_ITEM';
|
public static INVENTORY_ITEM: string = 'TVI_INVENTORY_ITEM';
|
||||||
public static CATALOG_ITEM: string = 'TVI_CATALOG_ITEM';
|
public static CATALOG_ITEM: string = 'TVI_CATALOG_ITEM';
|
||||||
public static FRIEND_LIST_ITEM: string = 'TVI_FRIEND_LIST_ITEM';
|
public static FRIEND_LIST_ITEM: string = 'TVI_FRIEND_LIST_ITEM';
|
||||||
|
public static CLOTHING_ITEM: string = 'TVI_CLOTHING_ITEM';
|
||||||
}
|
}
|
||||||
|
@ -1,10 +1,11 @@
|
|||||||
import { MouseEventType } from 'nitro-renderer';
|
import { MouseEventType } from 'nitro-renderer';
|
||||||
import { useEffect, useRef } from 'react';
|
import { useEffect, useRef } from 'react';
|
||||||
|
import { ToolbarViewItems } from '../ToolbarView.types';
|
||||||
import { ToolbarMeViewProps } from './ToolbarMeView.types';
|
import { ToolbarMeViewProps } from './ToolbarMeView.types';
|
||||||
|
|
||||||
export function ToolbarMeView(props: ToolbarMeViewProps): JSX.Element
|
export function ToolbarMeView(props: ToolbarMeViewProps): JSX.Element
|
||||||
{
|
{
|
||||||
const { setMeExpanded = null } = props;
|
const { setMeExpanded = null, handleToolbarItemClick = null } = props;
|
||||||
|
|
||||||
const elementRef = useRef<HTMLDivElement>();
|
const elementRef = useRef<HTMLDivElement>();
|
||||||
|
|
||||||
@ -46,7 +47,7 @@ export function ToolbarMeView(props: ToolbarMeViewProps): JSX.Element
|
|||||||
<div className="navigation-item">
|
<div className="navigation-item">
|
||||||
<i className="icon icon-me-rooms"></i>
|
<i className="icon icon-me-rooms"></i>
|
||||||
</div>
|
</div>
|
||||||
<div className="navigation-item">
|
<div className="navigation-item" onClick={ event => handleToolbarItemClick(ToolbarViewItems.CLOTHING_ITEM) }>
|
||||||
<i className="icon icon-me-clothing"></i>
|
<i className="icon icon-me-clothing"></i>
|
||||||
</div>
|
</div>
|
||||||
<div className="navigation-item">
|
<div className="navigation-item">
|
||||||
|
@ -3,4 +3,5 @@ import { Dispatch, SetStateAction } from 'react';
|
|||||||
export interface ToolbarMeViewProps
|
export interface ToolbarMeViewProps
|
||||||
{
|
{
|
||||||
setMeExpanded: Dispatch<SetStateAction<boolean>>;
|
setMeExpanded: Dispatch<SetStateAction<boolean>>;
|
||||||
|
handleToolbarItemClick: (item: string) => void;
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user