forked from github/plane
Fix/mentions spaces fix (#2667)
* feat: add mentions store to the space project * fix: added mentions highlights in read only comment cards * feat: added mention highlights in richtexteditor in space app
This commit is contained in:
parent
13389d1b2b
commit
6eb0bf4785
@ -8,6 +8,7 @@ interface IRichTextReadOnlyEditor {
|
|||||||
noBorder?: boolean;
|
noBorder?: boolean;
|
||||||
borderOnFocus?: boolean;
|
borderOnFocus?: boolean;
|
||||||
customClassName?: string;
|
customClassName?: string;
|
||||||
|
mentionHighlights?: string[];
|
||||||
}
|
}
|
||||||
|
|
||||||
interface RichTextReadOnlyEditorProps extends IRichTextReadOnlyEditor {
|
interface RichTextReadOnlyEditorProps extends IRichTextReadOnlyEditor {
|
||||||
@ -26,10 +27,12 @@ const RichReadOnlyEditor = ({
|
|||||||
customClassName,
|
customClassName,
|
||||||
value,
|
value,
|
||||||
forwardedRef,
|
forwardedRef,
|
||||||
|
mentionHighlights,
|
||||||
}: RichTextReadOnlyEditorProps) => {
|
}: RichTextReadOnlyEditorProps) => {
|
||||||
const editor = useReadOnlyEditor({
|
const editor = useReadOnlyEditor({
|
||||||
value,
|
value,
|
||||||
forwardedRef,
|
forwardedRef,
|
||||||
|
mentionHighlights,
|
||||||
});
|
});
|
||||||
|
|
||||||
const editorClassNames = getEditorClassNames({ noBorder, borderOnFocus, customClassName });
|
const editorClassNames = getEditorClassNames({ noBorder, borderOnFocus, customClassName });
|
||||||
|
@ -15,6 +15,7 @@ import { timeAgo } from "helpers/date-time.helper";
|
|||||||
import { Comment } from "types/issue";
|
import { Comment } from "types/issue";
|
||||||
// services
|
// services
|
||||||
import fileService from "services/file.service";
|
import fileService from "services/file.service";
|
||||||
|
import useEditorSuggestions from "hooks/use-editor-suggestions";
|
||||||
|
|
||||||
type Props = {
|
type Props = {
|
||||||
workspaceSlug: string;
|
workspaceSlug: string;
|
||||||
@ -28,6 +29,8 @@ export const CommentCard: React.FC<Props> = observer((props) => {
|
|||||||
// states
|
// states
|
||||||
const [isEditing, setIsEditing] = useState(false);
|
const [isEditing, setIsEditing] = useState(false);
|
||||||
|
|
||||||
|
const mentionsConfig = useEditorSuggestions();
|
||||||
|
|
||||||
const editorRef = React.useRef<any>(null);
|
const editorRef = React.useRef<any>(null);
|
||||||
|
|
||||||
const showEditorRef = React.useRef<any>(null);
|
const showEditorRef = React.useRef<any>(null);
|
||||||
@ -135,7 +138,7 @@ export const CommentCard: React.FC<Props> = observer((props) => {
|
|||||||
ref={showEditorRef}
|
ref={showEditorRef}
|
||||||
value={comment.comment_html}
|
value={comment.comment_html}
|
||||||
customClassName="text-xs border border-custom-border-200 bg-custom-background-100"
|
customClassName="text-xs border border-custom-border-200 bg-custom-background-100"
|
||||||
mentionHighlights={userStore.currentUser?.id ? [userStore.currentUser?.id] : []}
|
mentionHighlights={mentionsConfig.mentionHighlights}
|
||||||
/>
|
/>
|
||||||
<CommentReactions commentId={comment.id} projectId={comment.project} />
|
<CommentReactions commentId={comment.id} projectId={comment.project} />
|
||||||
</div>
|
</div>
|
||||||
|
@ -2,12 +2,17 @@ import { IssueReactions } from "components/issues/peek-overview";
|
|||||||
import { RichReadOnlyEditor } from "@plane/rich-text-editor";
|
import { RichReadOnlyEditor } from "@plane/rich-text-editor";
|
||||||
// types
|
// types
|
||||||
import { IIssue } from "types/issue";
|
import { IIssue } from "types/issue";
|
||||||
|
import useEditorSuggestions from "hooks/use-editor-suggestions";
|
||||||
|
|
||||||
type Props = {
|
type Props = {
|
||||||
issueDetails: IIssue;
|
issueDetails: IIssue;
|
||||||
};
|
};
|
||||||
|
|
||||||
export const PeekOverviewIssueDetails: React.FC<Props> = ({ issueDetails }) => (
|
export const PeekOverviewIssueDetails: React.FC<Props> = ({ issueDetails }) => {
|
||||||
|
|
||||||
|
const mentionConfig = useEditorSuggestions();
|
||||||
|
|
||||||
|
return (
|
||||||
<div className="space-y-2">
|
<div className="space-y-2">
|
||||||
<h6 className="font-medium text-custom-text-200">
|
<h6 className="font-medium text-custom-text-200">
|
||||||
{issueDetails.project_detail.identifier}-{issueDetails.sequence_id}
|
{issueDetails.project_detail.identifier}-{issueDetails.sequence_id}
|
||||||
@ -21,8 +26,9 @@ export const PeekOverviewIssueDetails: React.FC<Props> = ({ issueDetails }) => (
|
|||||||
Object.keys(issueDetails.description_html).length === 0)
|
Object.keys(issueDetails.description_html).length === 0)
|
||||||
? "<p></p>"
|
? "<p></p>"
|
||||||
: issueDetails.description_html}
|
: issueDetails.description_html}
|
||||||
customClassName="p-3 min-h-[50px] shadow-sm" />
|
customClassName="p-3 min-h-[50px] shadow-sm" mentionHighlights={mentionConfig.mentionHighlights} />
|
||||||
)}
|
)}
|
||||||
<IssueReactions />
|
<IssueReactions />
|
||||||
</div>
|
</div>
|
||||||
);
|
)
|
||||||
|
};
|
||||||
|
13
space/hooks/use-editor-suggestions.tsx
Normal file
13
space/hooks/use-editor-suggestions.tsx
Normal file
@ -0,0 +1,13 @@
|
|||||||
|
import { useMobxStore } from "lib/mobx/store-provider";
|
||||||
|
import { RootStore } from "store/root";
|
||||||
|
|
||||||
|
const useEditorSuggestions = () => {
|
||||||
|
const { mentionsStore }: RootStore = useMobxStore();
|
||||||
|
|
||||||
|
return {
|
||||||
|
// mentionSuggestions: mentionsStore.mentionSuggestions,
|
||||||
|
mentionHighlights: mentionsStore.mentionHighlights,
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
|
export default useEditorSuggestions;
|
45
space/store/mentions.store.ts
Normal file
45
space/store/mentions.store.ts
Normal file
@ -0,0 +1,45 @@
|
|||||||
|
import { IMentionHighlight } from "@plane/lite-text-editor";
|
||||||
|
import { RootStore } from "./root";
|
||||||
|
import { computed, makeObservable } from "mobx";
|
||||||
|
|
||||||
|
export interface IMentionsStore {
|
||||||
|
// mentionSuggestions: IMentionSuggestion[];
|
||||||
|
mentionHighlights: IMentionHighlight[];
|
||||||
|
}
|
||||||
|
|
||||||
|
export class MentionsStore implements IMentionsStore{
|
||||||
|
|
||||||
|
// root store
|
||||||
|
rootStore;
|
||||||
|
|
||||||
|
constructor(_rootStore: RootStore ){
|
||||||
|
|
||||||
|
// rootStore
|
||||||
|
this.rootStore = _rootStore;
|
||||||
|
|
||||||
|
makeObservable(this, {
|
||||||
|
mentionHighlights: computed,
|
||||||
|
// mentionSuggestions: computed
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
// get mentionSuggestions() {
|
||||||
|
// const projectMembers = this.rootStore.project.project.
|
||||||
|
|
||||||
|
// const suggestions = projectMembers === null ? [] : projectMembers.map((member) => ({
|
||||||
|
// id: member.member.id,
|
||||||
|
// type: "User",
|
||||||
|
// title: member.member.display_name,
|
||||||
|
// subtitle: member.member.email ?? "",
|
||||||
|
// avatar: member.member.avatar,
|
||||||
|
// redirect_uri: `/${member.workspace.slug}/profile/${member.member.id}`,
|
||||||
|
// }))
|
||||||
|
|
||||||
|
// return suggestions
|
||||||
|
// }
|
||||||
|
|
||||||
|
get mentionHighlights() {
|
||||||
|
const user = this.rootStore.user.currentUser;
|
||||||
|
return user ? [user.id] : []
|
||||||
|
}
|
||||||
|
}
|
@ -5,6 +5,7 @@ import UserStore from "./user";
|
|||||||
import IssueStore, { IIssueStore } from "./issue";
|
import IssueStore, { IIssueStore } from "./issue";
|
||||||
import ProjectStore, { IProjectStore } from "./project";
|
import ProjectStore, { IProjectStore } from "./project";
|
||||||
import IssueDetailStore, { IIssueDetailStore } from "./issue_details";
|
import IssueDetailStore, { IIssueDetailStore } from "./issue_details";
|
||||||
|
import { IMentionsStore, MentionsStore } from "./mentions.store";
|
||||||
|
|
||||||
enableStaticRendering(typeof window === "undefined");
|
enableStaticRendering(typeof window === "undefined");
|
||||||
|
|
||||||
@ -13,11 +14,13 @@ export class RootStore {
|
|||||||
issue: IIssueStore;
|
issue: IIssueStore;
|
||||||
issueDetails: IIssueDetailStore;
|
issueDetails: IIssueDetailStore;
|
||||||
project: IProjectStore;
|
project: IProjectStore;
|
||||||
|
mentionsStore: IMentionsStore;
|
||||||
|
|
||||||
constructor() {
|
constructor() {
|
||||||
this.user = new UserStore(this);
|
this.user = new UserStore(this);
|
||||||
this.issue = new IssueStore(this);
|
this.issue = new IssueStore(this);
|
||||||
this.project = new ProjectStore(this);
|
this.project = new ProjectStore(this);
|
||||||
this.issueDetails = new IssueDetailStore(this);
|
this.issueDetails = new IssueDetailStore(this);
|
||||||
|
this.mentionsStore = new MentionsStore(this);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user