rendering channel icon and subject

This commit is contained in:
Roland Osborne 2022-08-09 22:41:40 -07:00
parent 8a1531bcee
commit 6365145df7
7 changed files with 115 additions and 72 deletions

View File

@ -79,6 +79,7 @@ export const SessionWrapper = styled.div`
.bottom { .bottom {
height: 48px; height: 48px;
position: relative; position: relative;
box-shadow: 0px -8px 16px 0px rgba(0,0,0,0.3);
} }
} }
`; `;

View File

@ -8,13 +8,12 @@ export function Channels() {
const { state, actions } = useChannels(); const { state, actions } = useChannels();
console.log(state);
return ( return (
<ChannelsWrapper> <ChannelsWrapper>
<div class="search"> <div class="search">
<div class="filter"> <div class="filter">
<Input bordered={false} allowClear={true} placeholder="Channels" prefix={<SearchOutlined />} /> <Input bordered={false} allowClear={true} placeholder="Channels" prefix={<SearchOutlined />}
size="large" spellCheck="false" onChange={(e) => actions.onFilter(e.target.value)} />
</div> </div>
</div> </div>
<div class="results"> <div class="results">

View File

@ -8,9 +8,11 @@ export const ChannelsWrapper = styled.div`
flex-direction: column; flex-direction: column;
background-color: ${Colors.formBackground}; background-color: ${Colors.formBackground};
min-height: 0; min-height: 0;
overflow: scroll;
.search { .search {
padding: 8px; padding: 16px;
border-bottom: 1px solid ${Colors.divider};
.filter { .filter {
border: 1px solid ${Colors.divider}; border: 1px solid ${Colors.divider};
@ -20,6 +22,5 @@ export const ChannelsWrapper = styled.div`
} }
.results { .results {
min-height: 0; }
overflow: scroll;
`; `;

View File

@ -1,29 +1,36 @@
import { ChannelItemWrapper } from './ChannelItem.styled'; import { ChannelItemWrapper } from './ChannelItem.styled';
import { useChannelItem } from './useChannelItem.hook'; import { Logo } from 'logo/Logo';
import { SolutionOutlined } from '@ant-design/icons'; import { AppstoreFilled, SolutionOutlined } from '@ant-design/icons';
export function ChannelItem({ item }) { export function ChannelItem({ item }) {
const { state, actions } = useChannelItem(item); console.log(item.contacts);
return ( return (
<ChannelItemWrapper> <ChannelItemWrapper>
{ state.contacts.length === 0 && ( { item.contacts.length === 0 && (
<div class="notes"> <div class="item">
<div class="logo"> <div class="logo">
<SolutionOutlined /> <SolutionOutlined />
</div> </div>
<div class="subject"> <div class="subject">{ item.subject }</div>
</div>
<div class="markup">
</div>
</div> </div>
)} )}
{ state.contacts.length === 1 && ( { item.contacts.length === 1 && (
<div>PERSONAL</div> <div class="item">
<Logo url={item.logo} width={32} height={32} radius={8} />
<div class="subject">{ item.subject }</div>
<div class="markup"></div>
</div>
)} )}
{ state.contacts.length > 1 && ( { item.contacts.length > 1 && (
<div>GROUP</div> <div class="item">
<div class="logo">
<AppstoreFilled />
</div>
<div class="subject">{ item.subject }</div>
<div class="markup"></div>
</div>
)} )}
</ChannelItemWrapper> </ChannelItemWrapper>
) )

View File

@ -5,25 +5,38 @@ export const ChannelItemWrapper = styled.div`
height: 48px; height: 48px;
width: 100%; width: 100%;
display: flex; display: flex;
flex-direction: row; align-items: center;
flex-align: center;
border-bottom: 1px solid ${Colors.divider}; border-bottom: 1px solid ${Colors.divider};
padding-left: 16px;
padding-right: 16px;
.logo { &:hover {
background-color: ${Colors.formHover};
cursor: pointer;
}
.item {
display: flex; display: flex;
flex-direction: row;
align-items: center; align-items: center;
justify-content: center;
border: 1px solid ${Colors.grey};
width: 32px;
height: 32px;
border-radius: 8px;
font-size: 18px;
}
.subject { .logo {
flex-grow: 1; display: flex;
} align-items: center;
justify-content: center;
border: 1px solid ${Colors.grey};
width: 32px;
height: 32px;
border-radius: 8px;
font-size: 18px;
}
.markup { .subject {
padding-left: 16px;
flex-grow: 1;
}
.markup {
}
} }
`; `;

View File

@ -1,36 +0,0 @@
import { useContext, useState, useEffect } from 'react';
import { ProfileContext } from 'context/ProfileContext';
import { CardContext } from 'context/CardContext';
export function useChannelItem(item) {
const [state, setState] = useState({
contacts: [],
});
const profile = useContext(ProfileContext);
const card = useContext(CardContext);
const updateState = (value) => {
setState((s) => ({ ...s, ...value }));
}
const actions = {
};
useEffect(() => {
let contacts = [];
if (item.guid != null && profile.state.profile.guid != item.guid) {
contacts.push(card.actions.getCardByGuid(item.guid));
}
for (let guid of item.data.channelDetail?.members) {
if (guid != profile.state.profile.guid) {
contacts.push(card.actions.getCardByGuid(guid));
}
}
updateState({ contacts });
}, [profile, item]);
return { state, actions };
}

View File

@ -2,9 +2,12 @@ import { useContext, useState, useEffect } from 'react';
import { StoreContext } from 'context/StoreContext'; import { StoreContext } from 'context/StoreContext';
import { ChannelContext } from 'context/ChannelContext'; import { ChannelContext } from 'context/ChannelContext';
import { CardContext } from 'context/CardContext'; import { CardContext } from 'context/CardContext';
import { ProfileContext } from 'context/ProfileContext';
export function useChannels() { export function useChannels() {
const [filter, setFilter] = useState(null);
const [state, setState] = useState({ const [state, setState] = useState({
channels: [], channels: [],
busy: false } busy: false }
@ -13,12 +16,16 @@ export function useChannels() {
const card = useContext(CardContext); const card = useContext(CardContext);
const channel = useContext(ChannelContext); const channel = useContext(ChannelContext);
const store = useContext(StoreContext); const store = useContext(StoreContext);
const profile = useContext(ProfileContext);
const updateState = (value) => { const updateState = (value) => {
setState((s) => ({ ...s, ...value })); setState((s) => ({ ...s, ...value }));
} }
const actions = { const actions = {
onFilter: (value) => {
setFilter(value.toUpperCase());
},
}; };
const setUpdated = (chan) => { const setUpdated = (chan) => {
@ -39,6 +46,46 @@ export function useChannels() {
} }
} }
const setContacts = (chan) => {
let contacts = [];
if (chan.guid != null && profile.state.profile.guid != chan.guid) {
contacts.push(card.actions.getCardByGuid(chan.guid));
}
for (let guid of chan.data.channelDetail?.members) {
if (guid != profile.state.profile.guid) {
contacts.push(card.actions.getCardByGuid(guid));
}
}
chan.contacts = contacts;
if (contacts.length === 1 && contacts[0]) {
chan.logo = card.actions.getImageUrl(contacts[0].id);
}
}
const setSubject = (chan) => {
let subject = "";
if (chan.data.channelDetail?.data) {
try {
subject = JSON.parse(chan.data.channelDetail?.data).subject;
}
catch (err) {
console.log(err);
}
}
if (!subject) {
let names = [];
for (let contact of chan.contacts) {
names.push(contact?.data?.cardProfile?.name);
}
subject = names.join(", ");
}
if (!subject && !chan.contacts?.length) {
subject = "notes";
}
chan.subject = subject;
}
useEffect(() => { useEffect(() => {
let merged = []; let merged = [];
card.state.cards.forEach((value, key, map) => { card.state.cards.forEach((value, key, map) => {
@ -53,9 +100,20 @@ export function useChannels() {
return 1; return 1;
}); });
merged.forEach(chan => { setUpdated(chan) }); merged.forEach(chan => {
updateState({ channels: merged }); setUpdated(chan);
}, [channel, card, store]); setContacts(chan);
setSubject(chan);
});
const filtered = merged.filter((chan) => {
let subject = chan?.subject?.toUpperCase();
return !filter || subject?.includes(filter);
});
updateState({ channels: filtered });
}, [channel, card, store, filter]);
return { state, actions }; return { state, actions };
} }