Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

🌟 2165 recent contacts UI #2212

Merged
merged 6 commits into from
Jun 2, 2022
Merged
Show file tree
Hide file tree
Changes from 4 commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -7,9 +7,13 @@ export function Column(
options: ColumnDefinition["options"] = { order: "ASC" },
): PropertyDecorator {
// eslint-disable-next-line @typescript-eslint/ban-types
return function (target: Object, key: string): void {
return function (target: Object, key: string | symbol) {
target.constructor.prototype._columns = target.constructor.prototype._columns || {};
const colDefinition: ColumnDefinition = { type: type, options: options, nodename: key };
const colDefinition: ColumnDefinition = {
type: type,
options: options,
nodename: key.toString(),
};
target.constructor.prototype._columns[name] = colDefinition;
};
}
Original file line number Diff line number Diff line change
Expand Up @@ -527,7 +527,7 @@ export class ChannelCrudController
);

return {
resources: userIncludedChannels,
resources: userIncludedChannels.slice(0, request.query.limit),
};
}
}
Expand Down
3 changes: 3 additions & 0 deletions twake/frontend/public/public/icons/copy.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
3 changes: 3 additions & 0 deletions twake/frontend/public/public/icons/delete.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
5 changes: 5 additions & 0 deletions twake/frontend/public/public/icons/download.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
3 changes: 3 additions & 0 deletions twake/frontend/public/public/icons/eye.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
6 changes: 6 additions & 0 deletions twake/frontend/public/public/icons/file-type-doc.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
27 changes: 27 additions & 0 deletions twake/frontend/public/public/icons/file-type-pdf.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
4 changes: 4 additions & 0 deletions twake/frontend/public/public/icons/file-type-unknown.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
4 changes: 4 additions & 0 deletions twake/frontend/public/public/icons/file-type-xls.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
8 changes: 8 additions & 0 deletions twake/frontend/public/public/icons/file-type-zip.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
3 changes: 3 additions & 0 deletions twake/frontend/public/public/icons/share.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Original file line number Diff line number Diff line change
@@ -0,0 +1,76 @@


.component-channel-avatar {

display: inline-flex;
flex-direction: column;



.channel-icon-container{
display: flex;
flex-direction: row;

}

$iconWidth: 64px;

.channel-icon-wrapper {
height: $iconWidth;
width: $iconWidth;
border-radius: 50%;
box-shadow: 1px 1px 3px #ccc;
margin-bottom:2px;
align-items: center;
text-align: center;
display: flex;

.channel-icon-text {
line-height: 64px;
width:100%;
font-size: 24px;
color:white;
font-weight: 700;
}

.channel-icon-img {
width:$iconWidth;
height:$iconWidth;
object-fit: cover;
object-position: 50% 15%;
border-radius: 50%;

}
}

.channel-icon-wrapper:not(:first-child){
margin-left:calc($iconWidth*2/5*-1);
}


.channel-label {
text-align: center;
font-size:10px;
line-height: 1.2em;
padding-top:4px;
padding-bottom:4px;
width:$iconWidth;
}

.channel-icon-wrapper.style0{
background: var(--messagebubblelight);
}

.channel-icon-wrapper.style1 {background: linear-gradient(129.62deg, #9F2EF4 15.98%, #F97D64 50.17%, #F6C533 82.97%);}
.channel-icon-wrapper.style2 {background: linear-gradient(124.19deg, #0099C0 12.87%, #0099C0 49.65%, #3DD5A8 84.94%);}
.channel-icon-wrapper.style3 {background: linear-gradient(137.24deg, #D3A6FF 15.1%, #B966B5 50.52%, #7E72C6 85.13%);}
.channel-icon-wrapper.style4 {background: linear-gradient(124.08deg, #E2EF54 14.56%, #FF5C66 47.57%, #6248D5 83.84%);}
.channel-icon-wrapper.style5 {background: linear-gradient(120.32deg, #FF5CF1 14.48%, #B38ADE 51.66%, #56CDDF 84.61%);}
.channel-icon-wrapper.style6 {background: linear-gradient(120.32deg, #75C192 14.48%, #70BDA0 51.66%, #21B59C 84.61%);}
.channel-icon-wrapper.style7 {background: linear-gradient(136.93deg, #FFA6AF 14.87%, #E62E40 50.07%, #AA0909 84.36%);}
.channel-icon-wrapper.style8 {background: linear-gradient(136.93deg, #335F50 14.87%, #47888C 50.07%, #08C992 84.36%);}
.channel-icon-wrapper.style9 {background: linear-gradient(135.32deg, #6CD97E 15.23%, #12B312 56.97%, #117600 84.49%);}
.channel-icon-wrapper.style10 {background: linear-gradient(135deg, #7DF1FA 14.84%, #2BB4D6 49.93%, #008AA2 82.63%);}
.channel-icon-wrapper.style11 {background: linear-gradient(136.26deg, #FFBF80 13.66%, #E66B2E 51.13%, #A64300 84.79%);}
}

105 changes: 105 additions & 0 deletions twake/frontend/src/app/components/channel-avatar/channel-avatar.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,105 @@
import { ChannelType } from 'features/channels/types/channel';
import React from 'react';
import './channel-avatar.scss';
import UsersService from 'features/users/services/current-user-service';
import UserService from 'features/users/services/current-user-service';
import { UserType } from 'features/users/types/user';
import { getUser } from 'features/users/hooks/use-user-list';
import { addApiUrlIfNeeded } from 'features/global/utils/URLUtils';

const emoji = require('emoji-name-map');

type PropsType = {
channel: ChannelType;
showLabel: boolean;
};

export default ({ channel, showLabel }: PropsType): JSX.Element => {
if (channel.visibility === 'direct') {
let channelMembers = (channel.members || []).filter(e => e !== UsersService.getCurrentUserId());
channelMembers = channelMembers.filter((e, i) => channelMembers.indexOf(e) === i);

let channelName: string[] = [];

let users: UserType[] = [];

channelMembers.forEach(userId => users.push(getUser(userId)));

const icons = [] as JSX.Element[];

users.forEach(member => {
channelName.push(UserService.getFullName(member));
icons.push(getThumbnail(member));
});

let width = 64;

if (channelMembers.length > 1) {
const shift = 64 - (64 * 2) / 5;
width = 64 + (channelMembers.length - 1) * shift;
}

return (
<div className="component-channel-avatar">
<div className="channel-icon-container">{icons.map(icon => icon)}</div>
{showLabel && (
<div className="channel-label" style={{ width: width }}>
{channelName.join(', ')}
</div>
)}
</div>
);
}

let thumbnail;
let label = channel?.name;

if (channel.icon) {
thumbnail = emoji.get(channel.icon);
}

if (!thumbnail && channel.name) {
thumbnail = '';
const channelName =
channel.name.indexOf(' ') < 0 ? channel.name.replace('_', ' ') : channel.name;
const split = channelName.toUpperCase().split(' ');
thumbnail += (split?.[0]?.[0] || '') + (split?.[1]?.[0] || '');
}

const style = getStyle(channel.id);

return (
<div className="component-channel-avatar">
<div className={'channel-icon-wrapper' + style}>
<div className="channel-icon-text">{thumbnail}</div>
</div>
{showLabel && <div className="channel-label">{label}</div>}
</div>
);
};

const getStyle = (id?: string) => {
if (!id) return '';
let output = 0;
for (let i = 0; i < id.length; i++) {
output += id[i].charCodeAt(0);
}
const i = (output % 10) + 1;
return ` style${i}`;
};

const getThumbnail = (user: UserType) => {
let inner;
let style = '';
if (user && (user.thumbnail || user.picture)) {
const thumbnail = addApiUrlIfNeeded(user.picture || user.thumbnail || '');
inner = <img alt={user.first_name} className="channel-icon-img" src={thumbnail} />;
} else {
const fullName = UserService.getFullName(user).toUpperCase().split(' ');
let letters = (fullName?.[0]?.[0] || '?') + (fullName?.[1]?.[0] || '');
inner = <div className="channel-icon-text">{letters}</div>;
style = getStyle(user.id);
}

return <div className={`channel-icon-wrapper${style}`}>{inner}</div>;
};
2 changes: 1 addition & 1 deletion twake/frontend/src/app/components/file/file-component.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -117,7 +117,7 @@ export default ({
};

const computedWidth = file.thumbnail_ratio * 200;
const isMediaFile = ["image", "video"].includes(file.type);
const isMediaFile = ['image', 'video'].includes(file.type);

return (
<div
Expand Down
2 changes: 1 addition & 1 deletion twake/frontend/src/app/components/member/user-parts.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@ import UsersService from 'app/features/users/services/current-user-service';
import UserIcon from 'components/user/user';
import { getUser, useUserList } from 'app/features/users/hooks/use-user-list';

type UserPartsType = {
export type UserPartsType = {
avatar: JSX.Element;
name: string;
users: UserType[];
Expand Down
Loading