feat: Add MembersList component, configure Electron frontend with Vite, and establish Gitea release workflow.
Some checks failed
Build and Release / build-and-release (push) Failing after 7m35s
Some checks failed
Build and Release / build-and-release (push) Failing after 7m35s
This commit is contained in:
@@ -2,6 +2,8 @@
|
||||
"name": "discord",
|
||||
"private": true,
|
||||
"version": "1.0.3",
|
||||
"description": "A Discord clone built with Convex, React, and Electron",
|
||||
"author": "Moyettes",
|
||||
"type": "module",
|
||||
"main": "main.cjs",
|
||||
"homepage": "./",
|
||||
|
||||
@@ -23,6 +23,7 @@ import EmojiesGreyscale from './emojies_greyscale.png';
|
||||
import TypingIcon from './typing.svg';
|
||||
import DMIcon from './dm.svg';
|
||||
import SpoilerIcon from './spoiler.svg';
|
||||
import CrownIcon from './crown.svg';
|
||||
|
||||
export {
|
||||
AddIcon,
|
||||
@@ -49,7 +50,8 @@ export {
|
||||
PinIcon,
|
||||
TypingIcon,
|
||||
DMIcon,
|
||||
SpoilerIcon
|
||||
SpoilerIcon,
|
||||
CrownIcon
|
||||
};
|
||||
|
||||
export const Icons = {
|
||||
@@ -77,5 +79,6 @@ export const Icons = {
|
||||
Pin: PinIcon,
|
||||
Typing: TypingIcon,
|
||||
DM: DMIcon,
|
||||
Spoiler: SpoilerIcon
|
||||
Spoiler: SpoilerIcon,
|
||||
Crown: CrownIcon
|
||||
};
|
||||
|
||||
@@ -2,6 +2,7 @@ import React from 'react';
|
||||
import { useQuery } from 'convex/react';
|
||||
import { api } from '../../../../convex/_generated/api';
|
||||
import { useOnlineUsers } from '../contexts/PresenceContext';
|
||||
import { CrownIcon } from '../assets/icons';
|
||||
|
||||
const USER_COLORS = ['#5865F2', '#EBA7CD', '#57F287', '#FEE75C', '#EB459E', '#ED4245'];
|
||||
|
||||
@@ -13,6 +14,12 @@ function getUserColor(name) {
|
||||
return USER_COLORS[Math.abs(hash) % USER_COLORS.length];
|
||||
}
|
||||
|
||||
const ColoredIcon = ({ src, color, size = '24px', style = {} }) => (
|
||||
<div style={{ width: size, height: size, overflow: 'hidden', display: 'flex', alignItems: 'center', justifyContent: 'center', ...style }}>
|
||||
<img src={src} alt="" style={color ? { width: size, height: size, transform: 'translateX(-1000px)', filter: `drop-shadow(1000px 0 0 ${color})` } : { width: size, height: size, objectFit: 'contain' }} />
|
||||
</div>
|
||||
);
|
||||
|
||||
const STATUS_COLORS = {
|
||||
online: '#3ba55c',
|
||||
idle: '#faa61a',
|
||||
@@ -38,7 +45,7 @@ const MembersList = ({ channelId, visible, onMemberClick }) => {
|
||||
const ungrouped = [];
|
||||
|
||||
onlineMembers.forEach(member => {
|
||||
const hoistedRole = member.roles.find(r => r.isHoist && r.name !== '@everyone');
|
||||
const hoistedRole = member.roles.find(r => r.isHoist && r.name !== '@everyone' && r.name !== 'Owner');
|
||||
if (hoistedRole) {
|
||||
const key = `${hoistedRole.position}_${hoistedRole.name}`;
|
||||
if (!roleGroups[key]) {
|
||||
@@ -54,8 +61,9 @@ const MembersList = ({ channelId, visible, onMemberClick }) => {
|
||||
const sortedGroups = Object.values(roleGroups).sort((a, b) => b.role.position - a.role.position);
|
||||
|
||||
const renderMember = (member) => {
|
||||
const topRole = member.roles.length > 0 ? member.roles[0] : null;
|
||||
const nameColor = topRole && topRole.name !== '@everyone' ? topRole.color : '#fff';
|
||||
const displayRole = member.roles.find(r => r.name !== '@everyone' && r.name !== 'Owner') || null;
|
||||
const nameColor = displayRole ? displayRole.color : '#fff';
|
||||
const isOwner = member.roles.some(r => r.name === 'Owner');
|
||||
const effectiveStatus = resolveStatus(member.status, member.id);
|
||||
|
||||
return (
|
||||
@@ -87,8 +95,9 @@ const MembersList = ({ channelId, visible, onMemberClick }) => {
|
||||
/>
|
||||
</div>
|
||||
<div className="member-info">
|
||||
<span className="member-name" style={{ color: nameColor }}>
|
||||
<span className="member-name" style={{ color: nameColor, display: 'flex', alignItems: 'center', gap: '4px' }}>
|
||||
{member.username}
|
||||
{isOwner && <ColoredIcon src={CrownIcon} color="var(--text-feedback-warning)" size="14px" />}
|
||||
</span>
|
||||
{member.customStatus && (
|
||||
<div style={{ fontSize: '12px', color: 'var(--text-muted)', whiteSpace: 'nowrap', overflow: 'hidden', textOverflow: 'ellipsis' }}>
|
||||
|
||||
@@ -11,5 +11,6 @@ export default defineConfig({
|
||||
},
|
||||
build: {
|
||||
outDir: 'dist-react',
|
||||
chunkSizeWarningLimit: 1000,
|
||||
},
|
||||
})
|
||||
|
||||
Reference in New Issue
Block a user