Skip to content

Commit

Permalink
Profile link component (#4459)
Browse files Browse the repository at this point in the history
Co-authored-by: Matt Grogan <[email protected]>
  • Loading branch information
julianjelfs and megrogan authored Sep 28, 2023
1 parent 78542b1 commit c654dfd
Show file tree
Hide file tree
Showing 16 changed files with 183 additions and 145 deletions.
13 changes: 12 additions & 1 deletion frontend/app/rollup.config.mjs
Original file line number Diff line number Diff line change
Expand Up @@ -78,7 +78,7 @@ const development = build_env === "development";
const testnet = !development && !production;
const watch = process.env.ROLLUP_WATCH;

const env = process.env.NODE_ENV ?? (development ? "development": "production");
const env = process.env.NODE_ENV ?? (development ? "development" : "production");
const version = process.env.OPENCHAT_WEBSITE_VERSION;
if (!development && !version) {
throw Error("OPENCHAT_WEBSITE_VERSION environment variable not set");
Expand Down Expand Up @@ -335,6 +335,17 @@ export default {
.join("")}
${inlineScripts.map((s) => `<script>${s}</script>`).join("")}
</head>
<template id="profile-link-template">
<style>
.profile-link {
cursor: pointer;
font-weight: 700;
text-decoration: underline;
}
</style>
<strong class="profile-link"></strong>
</template>
<body></body>
</html>
`;
Expand Down
1 change: 1 addition & 0 deletions frontend/app/src/components/App.svelte
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@
redirectLandingPageLinksIfNecessary,
removeQueryStringParam,
} from "../utils/urls";
import "../components/web-components/profileLink";
import page from "page";
import { menuStore } from "../stores/menu";
import { framed } from "../stores/xframe";
Expand Down
32 changes: 7 additions & 25 deletions frontend/app/src/components/home/ChatMessage.svelte
Original file line number Diff line number Diff line change
Expand Up @@ -45,7 +45,6 @@
import TimeAndTicks from "./TimeAndTicks.svelte";
import { iconSize } from "../../stores/iconSize";
import MessageReaction from "./MessageReaction.svelte";
import ViewUserProfile from "./profile/ViewUserProfile.svelte";
import ThreadSummary from "./ThreadSummary.svelte";
import { pathParams } from "../../routes";
import { canShareMessage } from "../../utils/share";
Expand All @@ -56,6 +55,7 @@
import { longpress } from "../../actions/longpress";
import TipBuilder from "./TipBuilder.svelte";
import TipThumbnail from "./TipThumbnail.svelte";
import type { ProfileLinkClickedEvent } from "../web-components/profileLink";
const client = getContext<OpenChat>("client");
const dispatch = createEventDispatcher();
Expand Down Expand Up @@ -100,8 +100,6 @@
let multiUserChat = chatType === "group_chat" || chatType === "channel";
let showEmojiPicker = false;
let debug = false;
let viewProfile = false;
let alignProfileTo: DOMRect | undefined = undefined;
let crypto = msg.content.kind === "crypto_content";
let poll = msg.content.kind === "poll_content";
let canRevealDeleted = false;
Expand Down Expand Up @@ -176,11 +174,6 @@
}
});
function chatWithUser() {
closeUserProfile();
dispatch("chatWith", { kind: "direct_chat", userId: msg.sender });
}
function createReplyContext(): EnhancedReplyContext {
return {
kind: "rehydrated_reply_context",
Expand Down Expand Up @@ -327,14 +320,12 @@
}
function openUserProfile(ev: Event) {
if (ev.target) {
alignProfileTo = (ev.target as HTMLElement).getBoundingClientRect();
}
viewProfile = true;
}
function closeUserProfile() {
viewProfile = false;
ev.target?.dispatchEvent(
new CustomEvent<ProfileLinkClickedEvent>("profile-clicked", {
detail: { userId: msg.sender, chatButton: multiUserChat, inGlobalContext: false },
bubbles: true,
})
);
}
function registerVote(ev: CustomEvent<{ answerIndex: number; type: "register" | "delete" }>) {
Expand Down Expand Up @@ -420,15 +411,6 @@
on:close={() => (showReport = false)} />
{/if}

{#if viewProfile}
<ViewUserProfile
alignTo={alignProfileTo}
userId={msg.sender}
chatButton={multiUserChat}
on:openDirectChat={chatWithUser}
on:close={closeUserProfile} />
{/if}

<div class="message-wrapper" class:last>
<div
bind:this={msgElement}
Expand Down
19 changes: 8 additions & 11 deletions frontend/app/src/components/home/CurrentChatHeader.svelte
Original file line number Diff line number Diff line change
Expand Up @@ -15,9 +15,9 @@
import Typing from "../Typing.svelte";
import { iconSize } from "../../stores/iconSize";
import { now } from "../../stores/time";
import ViewUserProfile from "./profile/ViewUserProfile.svelte";
import SuspendModal from "./SuspendModal.svelte";
import { rightPanelHistory } from "../../stores/rightPanel";
import type { ProfileLinkClickedEvent } from "../web-components/profileLink";
const client = getContext<OpenChat>("client");
const dispatch = createEventDispatcher();
Expand All @@ -28,7 +28,6 @@
export let unreadMessages: number;
export let hasPinned: boolean;
let viewProfile = false;
let showSuspendUserModal = false;
$: typersByContext = client.typersByContext;
Expand Down Expand Up @@ -90,16 +89,17 @@
}
}
function openUserProfile() {
function openUserProfile(ev: Event) {
if (hasUserProfile) {
viewProfile = true;
ev.target?.dispatchEvent(
new CustomEvent<ProfileLinkClickedEvent>("profile-clicked", {
detail: { userId, chatButton: false, inGlobalContext: false },
bubbles: true,
})
);
}
}
function closeUserProfile() {
viewProfile = false;
}
$: chat = normaliseChatSummary($now, selectedChatSummary, $typersByContext);
</script>

Expand All @@ -119,9 +119,6 @@
</HoverIcon>
</div>
{/if}
{#if viewProfile}
<ViewUserProfile {userId} chatButton={false} on:close={closeUserProfile} />
{/if}

<div class="avatar" class:has-user-profile={hasUserProfile} on:click={openUserProfile}>
<Avatar
Expand Down
41 changes: 41 additions & 0 deletions frontend/app/src/components/home/Home.svelte
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@
import SelectChatModal from "../SelectChatModal.svelte";
import MiddlePanel from "./MiddlePanel.svelte";
import RightPanel from "./RightPanel.svelte";
import ViewUserProfile from "./profile/ViewUserProfile.svelte";
import EditCommunity from "./communities/edit/Edit.svelte";
import type {
EnhancedReplyContext,
Expand Down Expand Up @@ -80,13 +81,22 @@
import { createCandidateCommunity } from "../../stores/community";
import { interpolateLevel } from "../../utils/i18n";
import Convert from "./communities/Convert.svelte";
import type { ProfileLinkClickedEvent } from "../web-components/profileLink";
type ViewProfileConfig = {
userId: string;
chatButton: boolean;
alignTo?: DOMRect;
inGlobalContext: boolean;
};
const client = getContext<OpenChat>("client");
const user = client.user;
let candidateGroup: CandidateGroupChat | undefined;
let candidateCommunity: CommunitySummary | undefined;
let candidateCommunityRules: Rules = defaultChatRules("community");
let convertGroup: GroupChatSummary | undefined = undefined;
let showProfileCard: ViewProfileConfig | undefined = undefined;
type ConfirmActionEvent =
| ConfirmLeaveEvent
Expand Down Expand Up @@ -899,10 +909,39 @@
page(`/community/${ev.detail.communityId}`);
}
function profileLinkClicked(ev: CustomEvent<ProfileLinkClickedEvent>) {
showProfileCard = {
userId: ev.detail.userId,
chatButton: ev.detail.chatButton,
inGlobalContext: ev.detail.inGlobalContext,
alignTo: ev.target ? (ev.target as HTMLElement).getBoundingClientRect() : undefined,
};
}
function chatWithFromProfileCard() {
if (showProfileCard === undefined) return;
chatWith(
new CustomEvent("chatWith", {
detail: { kind: "direct_chat", userId: showProfileCard.userId },
})
);
showProfileCard = undefined;
}
$: bgHeight = $dimensions.height * 0.9;
$: bgClip = (($dimensions.height - 32) / bgHeight) * 361;
</script>

{#if showProfileCard !== undefined}
<ViewUserProfile
userId={showProfileCard.userId}
inGlobalContext={showProfileCard.inGlobalContext}
chatButton={showProfileCard.chatButton}
alignTo={showProfileCard.alignTo}
on:openDirectChat={chatWithFromProfileCard}
on:close={() => (showProfileCard = undefined)} />
{/if}

<main>
{#if $layoutStore.showNav}
<LeftNav
Expand Down Expand Up @@ -1049,6 +1088,8 @@

<Convert bind:group={convertGroup} />

<svelte:body on:profile-clicked={profileLinkClicked} />

<style lang="scss">
:global(.edited-msg) {
@include font(light, normal, fs-70);
Expand Down
2 changes: 1 addition & 1 deletion frontend/app/src/components/home/Markdown.svelte
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,7 @@
return text.replace(/@UserId\(([\d\w-]+)\)/g, (match, p1) => {
const u = $userStore[p1];
if (u !== undefined) {
return `**[@${u.username}](/user/${u.userId})**`;
return `<profile-link text="${u.username}" user-id="${u.userId}" suppress-links="${suppressLinks}"></profile-link>`;
}
return match;
});
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -22,13 +22,9 @@
function unblockUser() {
dispatch("unblockUser", user);
}
function openUserProfile() {
dispatch("openUserProfile", user.userId);
}
</script>

<User {user} {searchTerm} on:open={openUserProfile}>
<User {user} {searchTerm}>
{#if canUnblockUser}
<span class="menu">
<MenuIcon position={"bottom"} align={"end"}>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -22,13 +22,9 @@
function uninviteUser() {
dispatch("uninviteUser", user);
}
function openUserProfile() {
dispatch("openUserProfile", user.userId);
}
</script>

<User {user} {searchTerm} on:open={openUserProfile}>
<User {user} {searchTerm}>
{#if canUninviteUser}
<span class="menu">
<MenuIcon position={"bottom"} align={"end"}>
Expand Down
7 changes: 1 addition & 6 deletions frontend/app/src/components/home/groupdetails/Member.svelte
Original file line number Diff line number Diff line change
Expand Up @@ -63,10 +63,6 @@
function blockUser() {
dispatch("blockUser", { userId: member.userId });
}
function openUserProfile() {
dispatch("openUserProfile", member.userId);
}
</script>

<User
Expand All @@ -75,8 +71,7 @@
{searchTerm}
role={member.role === "moderator" || member.role === "admin" || member.role === "owner"
? member.role
: undefined}
on:open={openUserProfile}>
: undefined}>
{#if showMenu}
<span class="menu">
<MenuIcon position={"bottom"} align={"end"}>
Expand Down
35 changes: 2 additions & 33 deletions frontend/app/src/components/home/groupdetails/Members.svelte
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,6 @@
import { createEventDispatcher, getContext } from "svelte";
import SelectionButton from "../SelectionButton.svelte";
import InvitedUser from "./InvitedUser.svelte";
import ViewUserProfile from "../profile/ViewUserProfile.svelte";
import { menuCloser } from "../../../actions/closeMenu";
import UserGroups from "../communities/details/UserGroups.svelte";
Expand Down Expand Up @@ -54,7 +53,6 @@
let membersList: VirtualList;
let memberView: "members" | "blocked" | "invited" = "members";
let selectedTab: "users" | "groups" = "users";
let profileUserId: string | undefined = undefined;
$: searchTermLower = searchTerm.toLowerCase();
Expand Down Expand Up @@ -123,20 +121,6 @@
memberView = v;
}
function openUserProfile(ev: CustomEvent<string>) {
profileUserId = ev.detail;
}
function closeUserProfile() {
profileUserId = undefined;
}
function userSelected() {
if (profileUserId === undefined) return;
dispatch("chatWith", { kind: "direct_chat", userId: profileUserId });
closeUserProfile();
}
function selectTab(tab: "users" | "groups") {
selectedTab = tab;
userGroups?.reset();
Expand Down Expand Up @@ -200,13 +184,6 @@
</div>
{/if}

{#if profileUserId !== undefined}
<ViewUserProfile
userId={profileUserId}
on:openDirectChat={userSelected}
on:close={closeUserProfile} />
{/if}

{#if memberView === "members"}
{#if me !== undefined}
<Member
Expand All @@ -216,7 +193,6 @@
canDemoteToAdmin={client.canDemote(collection.id, me.role, "admin")}
canDemoteToModerator={client.canDemote(collection.id, me.role, "moderator")}
canDemoteToMember={client.canDemote(collection.id, me.role, "member")}
on:openUserProfile={openUserProfile}
on:changeRole />
{/if}
<VirtualList
Expand All @@ -239,8 +215,7 @@
on:blockUser
on:chatWith
on:changeRole
on:removeMember
on:openUserProfile={openUserProfile} />
on:removeMember />
</VirtualList>
{:else if memberView === "blocked"}
<div use:menuCloser class="user-list">
Expand All @@ -249,19 +224,13 @@
{user}
{searchTerm}
canUnblockUser={client.canUnblockUsers(collection.id)}
on:openUserProfile={openUserProfile}
on:unblockUser />
{/each}
</div>
{:else if memberView === "invited"}
<div use:menuCloser class="user-list">
{#each invitedUsers as user}
<InvitedUser
{user}
{searchTerm}
canUninviteUser={false}
on:openUserProfile={openUserProfile}
on:uninviteUser />
<InvitedUser {user} {searchTerm} canUninviteUser={false} on:uninviteUser />
{/each}
</div>
{/if}
Expand Down
Loading

0 comments on commit c654dfd

Please sign in to comment.