ENCOA-277, ENCOA-276, ENCOA-282, ENCOA-283

This commit is contained in:
Carlos-Mesquita
2024-12-21 19:23:53 +00:00
parent f6d387ce2d
commit 98a1636d0c
31 changed files with 2513 additions and 194 deletions

View File

@@ -16,11 +16,10 @@ interface Props {
onDiscard: () => void;
onEdit?: () => void;
module: Module;
listeningSection?: number;
context: Generating;
}
const SectionContext: React.FC<Props> = ({ sectionId, title, description, renderContent, editing, onSave, onDiscard, onEdit, mode = "edit", module, context, listeningSection }) => {
const SectionContext: React.FC<Props> = ({ sectionId, title, description, renderContent, editing, onSave, onDiscard, onEdit, mode = "edit", module, context }) => {
const { currentModule } = useExamEditorStore();
const { generating, levelGenerating } = useExamEditorStore(
(state) => state.modules[currentModule].sections.find((section) => section.sectionId === sectionId)!
@@ -54,7 +53,7 @@ const SectionContext: React.FC<Props> = ({ sectionId, title, description, render
{loading ? (
<GenLoader module={module} />
) : (
renderContent(editing, listeningSection)
renderContent(editing)
)}
</div>
</div>

View File

@@ -1,5 +1,5 @@
import { useEffect, useState } from "react";
import { LevelPart, ListeningPart } from "@/interfaces/exam";
import { useCallback, useEffect, useState } from "react";
import { LevelPart, ListeningPart, Script } from "@/interfaces/exam";
import SectionContext from ".";
import useExamEditorStore from "@/stores/examEditor";
import useSectionEdit from "../../Hooks/useSectionEdit";
@@ -22,9 +22,10 @@ interface Props {
const ListeningContext: React.FC<Props> = ({ sectionId, module, listeningSection, level = false }) => {
const { dispatch } = useExamEditorStore();
const { genResult, state, generating, levelGenResults, levelGenerating } = useExamEditorStore(
const { genResult, state, generating, levelGenResults, levelGenerating, scriptLoading } = useExamEditorStore(
(state) => state.modules[module].sections.find((section) => section.sectionId === sectionId)!
);
const listeningPart = state as ListeningPart | LevelPart;
const [isDialogDropdownOpen, setIsDialogDropdownOpen] = useState(false);
@@ -51,9 +52,11 @@ const ListeningContext: React.FC<Props> = ({ sectionId, module, listeningSection
},
});
useEffect(()=> {
useEffect(() => {
if (listeningPart.script == undefined) {
setScriptLocal(undefined);
setScriptLocal(undefined);
} else {
setScriptLocal(listeningPart.script);
}
}, [listeningPart])
@@ -93,8 +96,8 @@ const ListeningContext: React.FC<Props> = ({ sectionId, module, listeningSection
// eslint-disable-next-line react-hooks/exhaustive-deps
}, [levelGenResults]);
const renderContent = (editing: boolean, listeningSection?: number) => {
if (scriptLocal === undefined && !editing) {
const memoizedRenderContent = useCallback(() => {
if (scriptLocal === undefined && !editing && !scriptLoading) {
return (
<Card>
<CardContent className="py-10">
@@ -105,18 +108,23 @@ const ListeningContext: React.FC<Props> = ({ sectionId, module, listeningSection
}
return (
<>
{generating === "audio" ? (<GenLoader module="listening" custom="Generating audio ..." />) : (
{(generating === "audio" || scriptLoading) ? (
<GenLoader
module="listening"
custom={scriptLoading ? 'Transcribing Audio ...' : 'Generating audio ...'}
/>
) : (
<>
{listeningPart.audio?.source && (
{listeningPart.audio?.source !== undefined && (
<AudioPlayer
key={sectionId}
key={`${sectionId}-${scriptLocal?.length}`}
src={listeningPart.audio?.source ?? ''}
color="listening"
/>
)}
</>
)}
<Dropdown
{!scriptLoading && <Dropdown
className="mt-8 w-full flex items-center justify-between p-4 bg-white hover:bg-gray-50 transition-colors border rounded-xl border-gray-200"
contentWrapperClassName="rounded-xl mt-2"
customTitle={
@@ -125,10 +133,10 @@ const ListeningContext: React.FC<Props> = ({ sectionId, module, listeningSection
"h-5 w-5",
`text-ielts-${module}`
)} />
<span className="font-medium text-gray-900">{
listeningSection === undefined ?
([1, 3].includes(sectionId) ? "Conversation" : "Monologue") :
([1, 3].includes(listeningSection) ? "Conversation" : "Monologue")}
<span className="font-medium text-gray-900">
{listeningSection === undefined
? ([1, 3].includes(sectionId) ? "Conversation" : "Monologue")
: ([1, 3].includes(listeningSection) ? "Conversation" : "Monologue")}
</span>
</div>
}
@@ -136,15 +144,32 @@ const ListeningContext: React.FC<Props> = ({ sectionId, module, listeningSection
setIsOpen={setIsDialogDropdownOpen}
>
<ScriptRender
key={scriptLocal?.length}
local={scriptLocal}
setLocal={setScriptLocal}
section={level ? listeningSection! : sectionId}
editing={editing}
/>
</Dropdown>
}
</>
);
};
// eslint-disable-next-line react-hooks/exhaustive-deps
}, [
scriptLoading,
generating,
listeningPart.audio?.source,
listeningPart.script,
sectionId,
module,
isDialogDropdownOpen,
setIsDialogDropdownOpen,
setScriptLocal,
level,
scriptLocal,
editing,
listeningSection
]);
return (
<SectionContext
@@ -155,14 +180,13 @@ const ListeningContext: React.FC<Props> = ({ sectionId, module, listeningSection
([1, 3].includes(listeningSection) ? "Conversation" : "Monologue")
}
description={`Enter the section's ${(sectionId === 1 || sectionId === 3) ? "conversation" : "monologue"} or import your own`}
renderContent={renderContent}
renderContent={memoizedRenderContent}
editing={editing}
onSave={handleSave}
onEdit={handleEdit}
onDiscard={handleDiscard}
module={module}
context="listeningScript"
listeningSection={listeningSection}
/>
);
};