mirror of
https://github.com/billsonnn/nitro-react.git
synced 2024-11-26 23:50:52 +01:00
Groups updates
This commit is contained in:
parent
dcf18449b8
commit
820a147120
7
src/api/groups/TryJoinGroup.ts
Normal file
7
src/api/groups/TryJoinGroup.ts
Normal file
@ -0,0 +1,7 @@
|
||||
import { GroupJoinComposer } from '@nitrots/nitro-renderer';
|
||||
import { SendMessageHook } from '../../hooks';
|
||||
|
||||
export function TryJoinGroup(groupId: number): void
|
||||
{
|
||||
SendMessageHook(new GroupJoinComposer(groupId));
|
||||
}
|
@ -4,6 +4,7 @@ import { CatalogLayoutDefaultView } from './default/CatalogLayoutDefaultView';
|
||||
import { CatalogLayoutFrontpage4View } from './frontpage4/CatalogLayoutFrontpage4View';
|
||||
import { CatalogLayouGuildCustomFurniView } from './guild-custom-furni/CatalogLayoutGuildCustomFurniView';
|
||||
import { CatalogLayouGuildForumView } from './guild-forum/CatalogLayoutGuildForumView';
|
||||
import { CatalogLayouGuildFrontpageView } from './guild-frontpage/CatalogLayoutGuildFrontpageView';
|
||||
import { CatalogLayoutInfoLoyaltyView } from './info-loyalty/CatalogLayoutInfoLoyaltyView';
|
||||
import { CatalogLayoutPetView } from './pets/CatalogLayoutPetView';
|
||||
import { CatalogLayoutPets2View } from './pets2/CatalogLayoutPets2View';
|
||||
@ -30,7 +31,7 @@ export const GetCatalogLayout = (pageParser: CatalogPageMessageParser, roomPrevi
|
||||
case 'vip_buy':
|
||||
return <CatalogLayoutVipBuyView roomPreviewer={ roomPreviewer } pageParser={ pageParser } />;
|
||||
case 'guild_frontpage':
|
||||
return null;
|
||||
return <CatalogLayouGuildFrontpageView roomPreviewer={ roomPreviewer } pageParser={ pageParser } />;
|
||||
case 'guild_forum':
|
||||
return <CatalogLayouGuildForumView roomPreviewer={ roomPreviewer } pageParser={ pageParser } />;
|
||||
case 'guild_custom_furni':
|
||||
|
@ -1,7 +1,8 @@
|
||||
import { CatalogGroupsComposer } from '@nitrots/nitro-renderer';
|
||||
import { FC, useEffect } from 'react';
|
||||
import { CatalogGroupsComposer, StringDataType } from '@nitrots/nitro-renderer';
|
||||
import { FC, useEffect, useState } from 'react';
|
||||
import { LocalizeText } from '../../../../../../api';
|
||||
import { SendMessageHook } from '../../../../../../hooks/messages';
|
||||
import { BadgeImageView } from '../../../../../shared/badge-image/BadgeImageView';
|
||||
import { GetOfferName } from '../../../../common/CatalogUtilities';
|
||||
import { useCatalogContext } from '../../../../context/CatalogContext';
|
||||
import { CatalogRoomPreviewerView } from '../../../catalog-room-previewer/CatalogRoomPreviewerView';
|
||||
@ -18,11 +19,32 @@ export const CatalogLayouGuildCustomFurniView: FC<CatalogLayoutGuildCustomFurniV
|
||||
|
||||
const product = ((activeOffer && activeOffer.products[0]) || null);
|
||||
|
||||
const [ selectedGroupIndex, setSelectedGroupIndex ] = useState<number>(0);
|
||||
|
||||
useEffect(() =>
|
||||
{
|
||||
SendMessageHook(new CatalogGroupsComposer());
|
||||
}, [ pageParser ]);
|
||||
|
||||
useEffect(() =>
|
||||
{
|
||||
if(!groups[selectedGroupIndex]) return;
|
||||
|
||||
const productData = [];
|
||||
productData.push('0');
|
||||
productData.push(groups[selectedGroupIndex].groupId);
|
||||
productData.push(groups[selectedGroupIndex].badgeCode);
|
||||
productData.push(groups[selectedGroupIndex].colorA);
|
||||
productData.push(groups[selectedGroupIndex].colorB);
|
||||
|
||||
const stringDataType = new StringDataType();
|
||||
stringDataType.setValue(productData);
|
||||
|
||||
roomPreviewer.updateObjectStuffData(stringDataType);
|
||||
}, [ selectedGroupIndex, activeOffer ]);
|
||||
|
||||
if(!groups) return null;
|
||||
|
||||
return (
|
||||
<div className="row h-100 nitro-catalog-layout-guild-custom-furni">
|
||||
<div className="d-flex flex-column col-7 h-100">
|
||||
@ -30,13 +52,30 @@ export const CatalogLayouGuildCustomFurniView: FC<CatalogLayoutGuildCustomFurniV
|
||||
</div>
|
||||
{ product &&
|
||||
<div className="col position-relative d-flex flex-column">
|
||||
{ groups[selectedGroupIndex] && <div className="position-absolute" style={{ width: '50px', height: '50px', zIndex: 1 }}>
|
||||
<BadgeImageView badgeCode={ groups[selectedGroupIndex].badgeCode } isGroup={ true } />
|
||||
</div> }
|
||||
<CatalogRoomPreviewerView roomPreviewer={ roomPreviewer } height={ 140 } />
|
||||
<div className="fs-6 text-black mt-1 overflow-hidden">{ GetOfferName(activeOffer) }</div>
|
||||
{ groups.length === 0 && <div className="bg-muted text-center rounded p-1 text-black mt-auto">
|
||||
{ LocalizeText('catalog.guild_selector.members_only') }
|
||||
<button className="btn btn-sm btn-primary mt-1">{ LocalizeText('catalog.guild_selector.find_groups') }</button>
|
||||
</div> }
|
||||
{ groups.length > 0 && <CatalogPurchaseView offer={ activeOffer } pageId={ pageParser.pageId } /> }
|
||||
{ groups.length > 0 && <>
|
||||
<div className="d-flex mb-2">
|
||||
<div className="rounded d-flex overflow-hidden me-1 border">
|
||||
<div className="h-100" style={{ width: '20px', backgroundColor: '#' + groups[selectedGroupIndex].colorA }}></div>
|
||||
<div className="h-100" style={{ width: '20px', backgroundColor: '#' + groups[selectedGroupIndex].colorB }}></div>
|
||||
</div>
|
||||
<select className="form-select form-select-sm" value={ selectedGroupIndex } onChange={ (e) => setSelectedGroupIndex(parseInt(e.target.value)) }>
|
||||
{ groups.map((group, index) =>
|
||||
{
|
||||
return <option key={ index } value={ index }>{ group.groupName }</option>;
|
||||
}) }
|
||||
</select>
|
||||
</div>
|
||||
<CatalogPurchaseView offer={ activeOffer } pageId={ pageParser.pageId } extra={ groups[selectedGroupIndex] ? groups[selectedGroupIndex].groupId.toString() : '' } />
|
||||
</> }
|
||||
</div> }
|
||||
</div>
|
||||
);
|
||||
|
@ -0,0 +1,28 @@
|
||||
import { FC } from 'react';
|
||||
import { CreateLinkEvent, LocalizeText } from '../../../../../../api';
|
||||
import { GetCatalogPageImage, GetCatalogPageText } from '../../../../common/CatalogUtilities';
|
||||
import { useCatalogContext } from '../../../../context/CatalogContext';
|
||||
import { CatalogLayoutGuildFrontpageViewProps } from './CatalogLayoutGuildFrontpageView.types';
|
||||
|
||||
export const CatalogLayouGuildFrontpageView: FC<CatalogLayoutGuildFrontpageViewProps> = props =>
|
||||
{
|
||||
const { pageParser = null } = props;
|
||||
|
||||
const { catalogState = null, dispatchCatalogState = null } = useCatalogContext();
|
||||
|
||||
return (
|
||||
<div className="row h-100 nitro-catalog-layout-guild-custom-furni">
|
||||
<div className="col-7 overflow-auto h-100 d-flex flex-column bg-muted rounded py-1 px-2 text-black">
|
||||
<div dangerouslySetInnerHTML={ { __html: GetCatalogPageText(pageParser, 2) } } />
|
||||
<div dangerouslySetInnerHTML={ { __html: GetCatalogPageText(pageParser, 0) } } />
|
||||
<div dangerouslySetInnerHTML={ { __html: GetCatalogPageText(pageParser, 1) } } />
|
||||
<div className="d-block mb-2">
|
||||
<img alt="" src={ GetCatalogPageImage(pageParser, 1) } />
|
||||
</div>
|
||||
</div>
|
||||
<div className="col position-relative d-flex flex-column justify-content-center" onClick={ () => CreateLinkEvent('groups/create') }>
|
||||
<button className="btn btn-sm btn-primary mt-1">{ LocalizeText('catalog.start.guild.purchase.button') }</button>
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
}
|
@ -0,0 +1,4 @@
|
||||
import { CatalogLayoutProps } from '../CatalogLayout.types';
|
||||
|
||||
export interface CatalogLayoutGuildFrontpageViewProps extends CatalogLayoutProps
|
||||
{}
|
27
src/views/groups/GroupsMessageHandler.tsx
Normal file
27
src/views/groups/GroupsMessageHandler.tsx
Normal file
@ -0,0 +1,27 @@
|
||||
import { GroupBadgePartsEvent } from '@nitrots/nitro-renderer';
|
||||
import { FC, useCallback } from 'react';
|
||||
import { CreateMessageHook } from '../../hooks';
|
||||
import { useGroupsContext } from './context/GroupsContext';
|
||||
import { GroupsActions } from './context/GroupsContext.types';
|
||||
|
||||
export const GroupsMessageHandler: FC<{}> = props =>
|
||||
{
|
||||
const { groupsState = null, dispatchGroupsState = null } = useGroupsContext();
|
||||
|
||||
const onGroupBadgePartsEvent = useCallback((event: GroupBadgePartsEvent) =>
|
||||
{
|
||||
const parser = event.getParser();
|
||||
|
||||
dispatchGroupsState({
|
||||
type: GroupsActions.SET_BADGE_PARTS,
|
||||
payload: {
|
||||
arrayMaps: [ parser.bases, parser.symbols ],
|
||||
stringMaps: [ parser.partColors, parser.colorsA, parser.colorsB ]
|
||||
}
|
||||
})
|
||||
}, [ dispatchGroupsState ]);
|
||||
|
||||
CreateMessageHook(GroupBadgePartsEvent, onGroupBadgePartsEvent);
|
||||
|
||||
return null;
|
||||
};
|
@ -1,11 +1,50 @@
|
||||
import { FC } from 'react';
|
||||
import { GroupInformationBoxView } from './views/information-standalone/GroupInformationStandaloneView';
|
||||
import { GroupBadgePartsComposer, ILinkEventTracker } from '@nitrots/nitro-renderer';
|
||||
import { FC, useCallback, useEffect, useReducer } from 'react';
|
||||
import { AddEventLinkTracker, RemoveLinkEventTracker } from '../../api';
|
||||
import { SendMessageHook } from '../../hooks';
|
||||
import { GroupsContextProvider } from './context/GroupsContext';
|
||||
import { GroupsReducer, initialGroups } from './context/GroupsContext.types';
|
||||
import { GroupsMessageHandler } from './GroupsMessageHandler';
|
||||
import { GroupInformationStandaloneView } from './views/information-standalone/GroupInformationStandaloneView';
|
||||
|
||||
export const GroupsView: FC<{}> = props =>
|
||||
{
|
||||
const [ groupsState, dispatchGroupsState ] = useReducer(GroupsReducer, initialGroups);
|
||||
|
||||
useEffect(() =>
|
||||
{
|
||||
SendMessageHook(new GroupBadgePartsComposer());
|
||||
}, []);
|
||||
|
||||
const linkReceived = useCallback((url: string) =>
|
||||
{
|
||||
const parts = url.split('/');
|
||||
|
||||
if(parts.length < 2) return;
|
||||
|
||||
switch(parts[1])
|
||||
{
|
||||
case 'create':
|
||||
return;
|
||||
}
|
||||
}, []);
|
||||
|
||||
useEffect(() =>
|
||||
{
|
||||
const linkTracker: ILinkEventTracker = {
|
||||
linkReceived,
|
||||
eventUrlPrefix: 'groups/'
|
||||
};
|
||||
|
||||
AddEventLinkTracker(linkTracker);
|
||||
|
||||
return () => RemoveLinkEventTracker(linkTracker);
|
||||
}, [ linkReceived ]);
|
||||
|
||||
return (
|
||||
<>
|
||||
<GroupInformationBoxView />
|
||||
</>
|
||||
<GroupsContextProvider value={ { groupsState, dispatchGroupsState } }>
|
||||
<GroupsMessageHandler />
|
||||
<GroupInformationStandaloneView />
|
||||
</GroupsContextProvider>
|
||||
);
|
||||
};
|
||||
|
14
src/views/groups/context/GroupsContext.tsx
Normal file
14
src/views/groups/context/GroupsContext.tsx
Normal file
@ -0,0 +1,14 @@
|
||||
import { createContext, FC, useContext } from 'react';
|
||||
import { GroupsContextProps, IGroupsContext } from './GroupsContext.types';
|
||||
|
||||
const GroupsContext = createContext<IGroupsContext>({
|
||||
groupsState: null,
|
||||
dispatchGroupsState: null
|
||||
});
|
||||
|
||||
export const GroupsContextProvider: FC<GroupsContextProps> = props =>
|
||||
{
|
||||
return <GroupsContext.Provider value={ props.value }>{ props.children }</GroupsContext.Provider>
|
||||
}
|
||||
|
||||
export const useGroupsContext = () => useContext(GroupsContext);
|
61
src/views/groups/context/GroupsContext.types.ts
Normal file
61
src/views/groups/context/GroupsContext.types.ts
Normal file
@ -0,0 +1,61 @@
|
||||
import { Dispatch, ProviderProps, Reducer } from 'react';
|
||||
|
||||
export interface IGroupsContext
|
||||
{
|
||||
groupsState: IGroupsState;
|
||||
dispatchGroupsState: Dispatch<IGroupsAction>;
|
||||
}
|
||||
|
||||
export interface GroupsContextProps extends ProviderProps<IGroupsContext>
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
export interface IGroupsState
|
||||
{
|
||||
badgeBases: Map<number, string[]>;
|
||||
badgeSymbols: Map<number, string[]>;
|
||||
badgePartColors: Map<number, string>;
|
||||
groupColorsA: Map<number, string>;
|
||||
groupColorsB: Map<number, string>;
|
||||
}
|
||||
|
||||
export interface IGroupsAction
|
||||
{
|
||||
type: string;
|
||||
payload: {
|
||||
arrayMaps?: Map<number, string[]>[];
|
||||
stringMaps?: Map<number, string>[];
|
||||
}
|
||||
}
|
||||
|
||||
export class GroupsActions
|
||||
{
|
||||
public static SET_BADGE_PARTS: string = 'GA_SET_BADGE_PARTS';
|
||||
}
|
||||
|
||||
export const initialGroups: IGroupsState = {
|
||||
badgeBases: null,
|
||||
badgeSymbols: null,
|
||||
badgePartColors: null,
|
||||
groupColorsA: null,
|
||||
groupColorsB: null
|
||||
};
|
||||
|
||||
export const GroupsReducer: Reducer<IGroupsState, IGroupsAction> = (state, action) =>
|
||||
{
|
||||
switch(action.type)
|
||||
{
|
||||
case GroupsActions.SET_BADGE_PARTS: {
|
||||
const badgeBases = (action.payload.arrayMaps[0] || state.badgeBases || null);
|
||||
const badgeSymbols = (action.payload.arrayMaps[1] || state.badgeSymbols || null);
|
||||
const badgePartColors = (action.payload.stringMaps[0] || state.badgePartColors || null);
|
||||
const groupColorsA = (action.payload.stringMaps[1] || state.groupColorsA || null);
|
||||
const groupColorsB = (action.payload.stringMaps[2] || state.groupColorsB || null);
|
||||
|
||||
return { ...state, badgeBases, badgeSymbols, badgePartColors, groupColorsA, groupColorsB };
|
||||
}
|
||||
default:
|
||||
return state;
|
||||
}
|
||||
}
|
@ -5,7 +5,7 @@ import { CreateMessageHook } from '../../../../hooks';
|
||||
import { NitroCardContentView, NitroCardHeaderView, NitroCardView } from '../../../../layout';
|
||||
import { GroupInformationView } from '../information/GroupInformationView';
|
||||
|
||||
export const GroupInformationBoxView: FC<{}> = props =>
|
||||
export const GroupInformationStandaloneView: FC<{}> = props =>
|
||||
{
|
||||
const [ groupInformation, setGroupInformation ] = useState<GroupInformationParser>(null);
|
||||
|
||||
@ -15,10 +15,9 @@ export const GroupInformationBoxView: FC<{}> = props =>
|
||||
|
||||
if(!parser.flag) return;
|
||||
|
||||
if(groupInformation) setGroupInformation(null);
|
||||
|
||||
setGroupInformation(null);
|
||||
setGroupInformation(parser);
|
||||
}, [ groupInformation ]);
|
||||
}, []);
|
||||
|
||||
CreateMessageHook(GroupInformationEvent, onGroupInformationEvent);
|
||||
|
||||
|
@ -1,6 +1,7 @@
|
||||
import { GroupDeleteComposer, GroupInformationComposer, GroupJoinComposer, GroupRemoveMemberComposer } from '@nitrots/nitro-renderer';
|
||||
import { GroupDeleteComposer, GroupRemoveMemberComposer } from '@nitrots/nitro-renderer';
|
||||
import { FC, useCallback } from 'react';
|
||||
import { CreateLinkEvent, GetSessionDataManager, LocalizeText, TryVisitRoom } from '../../../../api';
|
||||
import { TryJoinGroup } from '../../../../api/groups/TryJoinGroup';
|
||||
import { SendMessageHook } from '../../../../hooks';
|
||||
import { CatalogPageName } from '../../../catalog/common/CatalogPageName';
|
||||
import { BadgeImageView } from '../../../shared/badge-image/BadgeImageView';
|
||||
@ -12,18 +13,16 @@ export const GroupInformationView: FC<GroupInformationViewProps> = props =>
|
||||
{
|
||||
const { groupInformation = null, onClose = null } = props;
|
||||
|
||||
const tryJoinGroup = useCallback(() =>
|
||||
const joinGroup = useCallback(() =>
|
||||
{
|
||||
if(!groupInformation) return;
|
||||
|
||||
SendMessageHook(new GroupJoinComposer(groupInformation.id));
|
||||
SendMessageHook(new GroupInformationComposer(groupInformation.id, false));
|
||||
TryJoinGroup(groupInformation.id);
|
||||
}, [ groupInformation ]);
|
||||
|
||||
const tryLeaveGroup = useCallback(() =>
|
||||
const leaveGroup = useCallback(() =>
|
||||
{
|
||||
SendMessageHook(new GroupRemoveMemberComposer(groupInformation.id, GetSessionDataManager().userId));
|
||||
SendMessageHook(new GroupInformationComposer(groupInformation.id, false));
|
||||
if(onClose) onClose();
|
||||
}, [ groupInformation, onClose ]);
|
||||
|
||||
@ -67,10 +66,10 @@ export const GroupInformationView: FC<GroupInformationViewProps> = props =>
|
||||
{
|
||||
if(groupInformation.type === GroupType.PRIVATE && groupInformation.membershipType === GroupMembershipType.NOT_MEMBER) return;
|
||||
|
||||
if(groupInformation.membershipType === GroupMembershipType.MEMBER) return tryLeaveGroup();
|
||||
if(groupInformation.membershipType === GroupMembershipType.MEMBER) return leaveGroup();
|
||||
|
||||
return tryJoinGroup();
|
||||
}, [ groupInformation, tryLeaveGroup, tryJoinGroup ]);
|
||||
return joinGroup();
|
||||
}, [ groupInformation, leaveGroup, joinGroup ]);
|
||||
|
||||
const handleAction = useCallback((action: string) =>
|
||||
{
|
||||
|
@ -3,5 +3,6 @@ import { GroupInformationParser } from '@nitrots/nitro-renderer';
|
||||
export interface GroupInformationViewProps
|
||||
{
|
||||
groupInformation: GroupInformationParser;
|
||||
onJoin?: () => void;
|
||||
onClose?: () => void;
|
||||
}
|
||||
|
@ -70,9 +70,9 @@ export const GroupRoomInformationView: FC<{}> = props =>
|
||||
|
||||
const getButtonText = useCallback(() =>
|
||||
{
|
||||
if(groupInformation.type === GroupType.PRIVATE) return '';
|
||||
if(isRealOwner()) return 'group.manage';
|
||||
|
||||
if(isRealOwner()) return 'group.youareowner';
|
||||
if(groupInformation.type === GroupType.PRIVATE) return '';
|
||||
|
||||
if(groupInformation.membershipType === GroupMembershipType.MEMBER) return 'group.leave';
|
||||
|
||||
@ -112,8 +112,8 @@ export const GroupRoomInformationView: FC<{}> = props =>
|
||||
{ groupInformation.title }
|
||||
</div>
|
||||
</div>
|
||||
{ groupInformation.type !== GroupType.PRIVATE && !isRealOwner() &&
|
||||
<button className="btn btn-sm btn-primary w-100 mt-1" disabled={ groupInformation.membershipType === GroupMembershipType.REQUEST_PENDING || isRealOwner() } onClick={ handleButtonClick }>
|
||||
{ (groupInformation.type !== GroupType.PRIVATE || isRealOwner()) &&
|
||||
<button className="btn btn-sm btn-primary w-100 mt-1" disabled={ groupInformation.membershipType === GroupMembershipType.REQUEST_PENDING } onClick={ handleButtonClick }>
|
||||
{ LocalizeText(getButtonText()) }
|
||||
</button>
|
||||
}
|
||||
|
@ -1,7 +1,7 @@
|
||||
import { RoomMuteComposer, RoomSettingsComposer, RoomStaffPickComposer, SecurityLevel, UserHomeRoomComposer } from '@nitrots/nitro-renderer';
|
||||
import classNames from 'classnames';
|
||||
import { FC, useCallback, useEffect, useState } from 'react';
|
||||
import { GetConfiguration, GetSessionDataManager, LocalizeText } from '../../../../api';
|
||||
import { GetConfiguration, GetGroupInformation, GetSessionDataManager, LocalizeText } from '../../../../api';
|
||||
import { NavigatorEvent } from '../../../../events';
|
||||
import { RoomWidgetThumbnailEvent } from '../../../../events/room-widgets/thumbnail';
|
||||
import { dispatchUiEvent } from '../../../../hooks/events';
|
||||
@ -82,6 +82,7 @@ export const NavigatorRoomInfoView: FC<NavigatorRoomInfoViewProps> = props =>
|
||||
dispatchUiEvent(new RoomWidgetThumbnailEvent(RoomWidgetThumbnailEvent.TOGGLE_THUMBNAIL));
|
||||
return;
|
||||
case 'open_group_info':
|
||||
GetGroupInformation(roomInfoData.enteredGuestRoom.habboGroupId);
|
||||
return;
|
||||
case 'toggle_room_link':
|
||||
dispatchUiEvent(new NavigatorEvent(NavigatorEvent.TOGGLE_ROOM_LINK));
|
||||
@ -137,7 +138,7 @@ export const NavigatorRoomInfoView: FC<NavigatorRoomInfoViewProps> = props =>
|
||||
</div>
|
||||
<div>{ roomInfoData.enteredGuestRoom.description }</div>
|
||||
<div className="room-thumbnail border mt-1 mb-2">
|
||||
<i className="icon icon-camera-small position-absolute b-0 r-0 m-1 cursor-pointer" onClick={ () => processAction('open_room_thumbnail_camera') } />
|
||||
{ hasPermission('settings') && <i className="icon icon-camera-small position-absolute b-0 r-0 m-1 cursor-pointer" onClick={ () => processAction('open_room_thumbnail_camera') } /> }
|
||||
{ roomThumbnail && <img alt="" src={ roomThumbnail } /> }
|
||||
</div>
|
||||
{ roomInfoData.enteredGuestRoom.habboGroupId > 0 && <div className="d-flex align-items-center mb-2 cursor-pointer" onClick={ () => processAction('open_group_info') }>
|
||||
|
@ -1,6 +1,9 @@
|
||||
import { ContextMenuEnum, RoomEngineTriggerWidgetEvent, RoomObjectCategory } from '@nitrots/nitro-renderer';
|
||||
import { ContextMenuEnum, FurnitureGroupInfoComposer, GroupFurniContextMenuInfoMessageParser, RoomEngineTriggerWidgetEvent, RoomObjectCategory, RoomObjectVariable } from '@nitrots/nitro-renderer';
|
||||
import { GroupFurniContextMenuInfoMessageEvent } from '@nitrots/nitro-renderer/src/nitro/communication/messages/incoming/room/furniture/GroupFurniContextMenuInfoMessageEvent';
|
||||
import { FC, useCallback, useState } from 'react';
|
||||
import { GetRoomEngine, IsOwnerOfFurniture, LocalizeText, RoomWidgetFurniActionMessage } from '../../../../../api';
|
||||
import { GetRoomEngine, IsOwnerOfFurniture, LocalizeText, RoomWidgetFurniActionMessage, TryVisitRoom } from '../../../../../api';
|
||||
import { TryJoinGroup } from '../../../../../api/groups/TryJoinGroup';
|
||||
import { CreateMessageHook, SendMessageHook } from '../../../../../hooks';
|
||||
import { useRoomEngineEvent } from '../../../../../hooks/events';
|
||||
import { useRoomContext } from '../../../context/RoomContext';
|
||||
import { ContextMenuView } from '../../context-menu/ContextMenuView';
|
||||
@ -18,6 +21,9 @@ export const FurnitureContextMenuView: FC<{}> = props =>
|
||||
const [ mode, setMode ] = useState<string>(null);
|
||||
const [ confirmMode, setConfirmMode ] = useState<string>(null);
|
||||
const [ confirmingObjectId, setConfirmingObjectId ] = useState(-1);
|
||||
const [ groupData, setGroupData ] = useState<GroupFurniContextMenuInfoMessageParser>(null);
|
||||
const [ isGroupMember, setIsGroupMember ] = useState<boolean>(false);
|
||||
|
||||
const { roomSession = null, widgetHandler = null } = useRoomContext();
|
||||
|
||||
const close = useCallback(() =>
|
||||
@ -71,6 +77,9 @@ export const FurnitureContextMenuView: FC<{}> = props =>
|
||||
case ContextMenuEnum.PURCHASABLE_CLOTHING:
|
||||
if(IsOwnerOfFurniture(object)) setMode(ContextMenuEnum.PURCHASABLE_CLOTHING);
|
||||
return;
|
||||
case ContextMenuEnum.GROUP_FURNITURE:
|
||||
SendMessageHook(new FurnitureGroupInfoComposer(object.id, object.model.getValue<number>(RoomObjectVariable.FURNITURE_GUILD_CUSTOMIZED_GUILD_ID)));
|
||||
return;
|
||||
}
|
||||
|
||||
return;
|
||||
@ -85,6 +94,18 @@ export const FurnitureContextMenuView: FC<{}> = props =>
|
||||
useRoomEngineEvent(RoomEngineTriggerWidgetEvent.REQUEST_MONSTERPLANT_SEED_PLANT_CONFIRMATION_DIALOG, onRoomEngineTriggerWidgetEvent);
|
||||
useRoomEngineEvent(RoomEngineTriggerWidgetEvent.REQUEST_PURCHASABLE_CLOTHING_CONFIRMATION_DIALOG, onRoomEngineTriggerWidgetEvent);
|
||||
|
||||
const onGroupFurniContextMenuInfoMessageEvent = useCallback((event: GroupFurniContextMenuInfoMessageEvent) =>
|
||||
{
|
||||
const parser = event.getParser();
|
||||
|
||||
setGroupData(null);
|
||||
setGroupData(parser);
|
||||
setIsGroupMember(parser.userIsMember);
|
||||
setMode(ContextMenuEnum.GROUP_FURNITURE);
|
||||
}, []);
|
||||
|
||||
CreateMessageHook(GroupFurniContextMenuInfoMessageEvent, onGroupFurniContextMenuInfoMessageEvent);
|
||||
|
||||
const processAction = useCallback((name: string) =>
|
||||
{
|
||||
if(name)
|
||||
@ -105,11 +126,18 @@ export const FurnitureContextMenuView: FC<{}> = props =>
|
||||
setConfirmMode(PURCHASABLE_CLOTHING_CONFIRMATION);
|
||||
setConfirmingObjectId(objectId);
|
||||
break;
|
||||
case 'join_group':
|
||||
TryJoinGroup(groupData.guildId);
|
||||
setIsGroupMember(true);
|
||||
return;
|
||||
case 'go_to_group_homeroom':
|
||||
if(groupData) TryVisitRoom(groupData.guildHomeRoomId);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
close();
|
||||
}, [ roomSession, widgetHandler, objectId, close ]);
|
||||
}, [ roomSession, widgetHandler, objectId, groupData, close ]);
|
||||
|
||||
return (
|
||||
<>
|
||||
@ -153,6 +181,18 @@ export const FurnitureContextMenuView: FC<{}> = props =>
|
||||
{ LocalizeText('widget.generic_usable.button.use') }
|
||||
</ContextMenuListItemView>
|
||||
</> }
|
||||
{ (mode === ContextMenuEnum.GROUP_FURNITURE) && groupData &&
|
||||
<>
|
||||
<ContextMenuHeaderView>
|
||||
{ groupData.guildName }
|
||||
</ContextMenuHeaderView>
|
||||
{ !isGroupMember && <ContextMenuListItemView onClick={ event => processAction('join_group') }>
|
||||
{ LocalizeText('widget.furniture.button.join.group') }
|
||||
</ContextMenuListItemView> }
|
||||
<ContextMenuListItemView onClick={ event => processAction('go_to_group_homeroom') }>
|
||||
{ LocalizeText('widget.furniture.button.go.to.group.home.room') }
|
||||
</ContextMenuListItemView>
|
||||
</> }
|
||||
</ContextMenuView> }
|
||||
</>
|
||||
)
|
||||
|
@ -1,7 +1,7 @@
|
||||
import { CrackableDataType, RoomControllerLevel, RoomObjectCategory, RoomObjectVariable, RoomWidgetEnumItemExtradataParameter, RoomWidgetFurniInfoUsagePolicyEnum, SetObjectDataMessageComposer, StringDataType, UserProfileComposer } from '@nitrots/nitro-renderer';
|
||||
import { CrackableDataType, GroupInformationComposer, GroupInformationEvent, RoomControllerLevel, RoomObjectCategory, RoomObjectVariable, RoomWidgetEnumItemExtradataParameter, RoomWidgetFurniInfoUsagePolicyEnum, SetObjectDataMessageComposer, StringDataType } from '@nitrots/nitro-renderer';
|
||||
import { FC, useCallback, useEffect, useState } from 'react';
|
||||
import { CreateLinkEvent, GetRoomEngine, LocalizeText, RoomWidgetFurniActionMessage } from '../../../../../../api';
|
||||
import { SendMessageHook } from '../../../../../../hooks';
|
||||
import { CreateLinkEvent, GetGroupInformation, GetRoomEngine, LocalizeText, RoomWidgetFurniActionMessage } from '../../../../../../api';
|
||||
import { CreateMessageHook, SendMessageHook } from '../../../../../../hooks';
|
||||
import { BadgeImageView } from '../../../../../shared/badge-image/BadgeImageView';
|
||||
import { LimitedEditionCompactPlateView } from '../../../../../shared/limited-edition/compact-plate/LimitedEditionCompactPlateView';
|
||||
import { RarityLevelView } from '../../../../../shared/rarity-level/RarityLevelView';
|
||||
@ -31,6 +31,7 @@ export const InfoStandWidgetFurniView: FC<InfoStandWidgetFurniViewProps> = props
|
||||
const [ crackableHits, setCrackableHits ] = useState(0);
|
||||
const [ crackableTarget, setCrackableTarget ] = useState(0);
|
||||
const [ godMode, setGodMode ] = useState(false);
|
||||
const [ groupName, setGroupName ] = useState<string>(null);
|
||||
|
||||
useEffect(() =>
|
||||
{
|
||||
@ -128,12 +129,23 @@ export const InfoStandWidgetFurniView: FC<InfoStandWidgetFurniViewProps> = props
|
||||
setCrackableHits(crackableHits);
|
||||
setCrackableTarget(crackableTarget);
|
||||
setGodMode(godMode);
|
||||
setGroupName(null);
|
||||
|
||||
if(furniData.groupId) SendMessageHook(new GroupInformationComposer(furniData.groupId, false));
|
||||
}, [ roomSession, furniData ]);
|
||||
|
||||
const openFurniGroupInfo = useCallback(() =>
|
||||
const onGroupInformationEvent = useCallback((event: GroupInformationEvent) =>
|
||||
{
|
||||
const parser = event.getParser();
|
||||
|
||||
}, []);
|
||||
if(!furniData || furniData.groupId !== parser.id || parser.flag) return;
|
||||
|
||||
if(groupName) setGroupName(null);
|
||||
|
||||
setGroupName(parser.title);
|
||||
}, [ furniData, groupName ]);
|
||||
|
||||
CreateMessageHook(GroupInformationEvent, onGroupInformationEvent);
|
||||
|
||||
const onFurniSettingChange = useCallback((index: number, value: string) =>
|
||||
{
|
||||
@ -223,9 +235,13 @@ export const InfoStandWidgetFurniView: FC<InfoStandWidgetFurniViewProps> = props
|
||||
widgetHandler.processWidgetMessage(new RoomWidgetFurniActionMessage(messageType, furniData.id, furniData.category, furniData.purchaseOfferId, objectData));
|
||||
}, [ widgetHandler, furniData, pickupMode, customKeys, customValues, getFurniSettingsAsString ]);
|
||||
|
||||
const openProfile = useCallback(() =>
|
||||
const getGroupBadgeCode = useCallback(() =>
|
||||
{
|
||||
SendMessageHook(new UserProfileComposer(furniData.ownerId));
|
||||
const stringDataType = (furniData.stuffData as StringDataType);
|
||||
|
||||
if(!stringDataType || !(stringDataType instanceof StringDataType)) return null;
|
||||
|
||||
return stringDataType.getValue(2);
|
||||
}, [ furniData ]);
|
||||
|
||||
if(!furniData) return null;
|
||||
@ -258,11 +274,12 @@ export const InfoStandWidgetFurniView: FC<InfoStandWidgetFurniViewProps> = props
|
||||
<hr className="m-0 my-1" />
|
||||
<div className="small text-wrap">{ LocalizeText('infostand.crackable_furni.hits_remaining', [ 'hits', 'target' ], [ crackableHits.toString(), crackableTarget.toString() ]) }</div>
|
||||
</> }
|
||||
{ (furniData.groupId > 0) &&
|
||||
{ furniData.groupId > 0 &&
|
||||
<>
|
||||
<hr className="m-0 my-1" />
|
||||
<div className="badge badge-secondary mb-0" onClick={ openFurniGroupInfo }>
|
||||
<BadgeImageView badgeCode={ (furniData.stuffData as StringDataType).getValue(2) } />
|
||||
<div className="d-flex align-items-center cursor-pointer text-decoration-underline gap-2" onClick={ () => GetGroupInformation(furniData.groupId) }>
|
||||
<BadgeImageView badgeCode={ getGroupBadgeCode() } isGroup={ true } />
|
||||
<div>{ groupName }</div>
|
||||
</div>
|
||||
</> }
|
||||
{ godMode &&
|
||||
|
Loading…
Reference in New Issue
Block a user