add notification search view

This commit is contained in:
Layne 2022-03-26 05:54:44 +00:00 committed by Bill
parent 60ed7087a1
commit bb7351a560
6 changed files with 75 additions and 7 deletions

View File

@ -5,4 +5,5 @@ export class NotificationAlertType
public static MODERATION: string = 'moderation';
public static EVENT: string = 'event';
public static NITRO: string = 'nitro';
public static SEARCH: string = 'search';
}

View File

@ -76,14 +76,14 @@ export class NotificationUtilities
const linkTitle = this.getNotificationPart(options, type, 'linkTitle', false);
const linkUrl = this.getNotificationPart(options, type, 'linkUrl', false);
const image = this.getNotificationImageUrl(options, type);
if(options.get('display') === 'BUBBLE')
{
this.showSingleBubble(LocalizeText(message), NotificationBubbleType.INFO, image, linkUrl);
}
else
{
this.simpleAlert(message, NotificationAlertType.EVENT, linkUrl, linkTitle, title, image);
this.simpleAlert(message, type, linkUrl, linkTitle, title, image);
}
if(options.get('sound')) PlaySound(options.get('sound'));

View File

@ -193,7 +193,7 @@
.nitro-alert {
width: 350px;
min-height: 150px;
max-height: 550px;
max-height: 350px;
}
.nitro-notification-bubble {

View File

@ -1,6 +1,7 @@
import { NotificationAlertItem, NotificationAlertType } from '../../../../api';
import { NitroSystemAlertView } from './NitroSystemAlertView';
import { NotificationDefaultAlertView } from './NotificationDefaultAlertView';
import { NotificationSeachAlertView } from './NotificationSearchAlertView';
export const GetAlertLayout = (item: NotificationAlertItem, close: () => void) =>
{
@ -11,7 +12,9 @@ export const GetAlertLayout = (item: NotificationAlertItem, close: () => void) =
switch(item.alertType)
{
case NotificationAlertType.NITRO:
return <NitroSystemAlertView { ...props } />
return <NitroSystemAlertView {...props} />
case NotificationAlertType.SEARCH:
return <NotificationSeachAlertView { ...props } />
default:
return <NotificationDefaultAlertView { ...props } />
}

View File

@ -1,4 +1,4 @@
import { FC, useCallback } from 'react';
import { FC, useCallback, useState } from 'react';
import { LocalizeText, NotificationAlertItem, NotificationAlertType, NotificationUtilities } from '../../../../api';
import { Base, Button, Column, Flex, LayoutNotificationAlertView, LayoutNotificationAlertViewProps } from '../../../../common';
@ -11,12 +11,15 @@ export const NotificationDefaultAlertView: FC<NotificationDefaultAlertViewProps>
{
const { item = null, title = ((props.item && props.item.title) || ''), close = null, ...rest } = props;
const [imageFailed, setImageFailed] = useState<boolean>(false)
const visitUrl = useCallback(() =>
{
NotificationUtilities.openUrl(item.clickUrl);
close();
}, [ item, close ]);
const isAction = (item.clickUrl && item.clickUrl.startsWith('event:'));
@ -24,8 +27,9 @@ export const NotificationDefaultAlertView: FC<NotificationDefaultAlertViewProps>
return (
<LayoutNotificationAlertView title={title} close={close} {...rest}>
<Flex fullHeight overflow="auto" gap={ 2 }>
{ hasFrank && <Base className="notification-frank flex-shrink-0" /> }
<Flex fullHeight overflow="auto" gap={2}>
{hasFrank && !item.imageUrl && <Base className="notification-frank flex-shrink-0" /> }
{item.imageUrl && !imageFailed && <img src={item.imageUrl} alt={ item.title } onError={() => { setImageFailed(true) } } /> }
{ (item.messages.length > 0) && item.messages.map((message, index) =>
{
const htmlText = message.replace(/\r\n|\r|\n/g, '<br />');

View File

@ -0,0 +1,60 @@
import { FC, useCallback, useEffect, useState } from 'react';
import { LocalizeText, NotificationAlertItem, NotificationUtilities } from '../../../../api';
import { AutoGrid, Button, Column, Flex, LayoutNotificationAlertView, LayoutNotificationAlertViewProps } from '../../../../common';
interface NotificationDefaultAlertViewProps extends LayoutNotificationAlertViewProps
{
item: NotificationAlertItem;
}
export const NotificationSeachAlertView: FC<NotificationDefaultAlertViewProps> = props =>
{
const { item = null, title = ((props.item && props.item.title) || ''), close = null, ...rest } = props;
const [ searchValue, setSearchValue ] = useState('');
const [ results, setResults] = useState<string[]>([]);
const visitUrl = useCallback(() =>
{
NotificationUtilities.openUrl(item.clickUrl);
close();
}, [item, close]);
useEffect(() =>
{
setResults(JSON.parse(item.messages[0]));
}, [item])
const updateSearchValue = useCallback((value: string) =>
{
let res = JSON.parse(item.messages[0]);
setResults(res.filter((val: string) => val.includes(value)));
setSearchValue(value);
},[item])
const isAction = (item.clickUrl && item.clickUrl.startsWith('event:'));
return (
<LayoutNotificationAlertView title={title} close={close} {...rest}>
<Flex fullWidth alignItems="center" position="relative">
<input type="text" className="form-control form-control-sm" placeholder={ LocalizeText('generic.search') } value={ searchValue } onChange={ event => updateSearchValue(event.target.value) } />
</Flex>
<Column fullHeight className="py-1" overflow="hidden">
<AutoGrid gap={1} columnCount={1}>
{results && results.map((n, index) =>
{
return <span key={ index }>{ n }</span>
})}
</AutoGrid>
</Column>
<hr className="my-2"/>
<Column alignItems="center" center gap={ 1 }>
{ !isAction && !item.clickUrl &&
<Button onClick={ close }>{ LocalizeText('generic.close') }</Button> }
{ item.clickUrl && (item.clickUrl.length > 0) &&
<Button onClick={ visitUrl }>{ LocalizeText(item.clickUrlText) }</Button> }
</Column>
</LayoutNotificationAlertView>
);
}