Skip to content

Commit bd95eb0

Browse files
authored
Merge pull request #85 from CS3219-AY2425S1/ben/n4-attempt
Attempt at N4 to add JavaScript into Code Editor
2 parents 91be737 + c8f437c commit bd95eb0

File tree

5 files changed

+75
-68
lines changed

5 files changed

+75
-68
lines changed

apps/frontend/pnpm-lock.yaml

Lines changed: 3 additions & 3 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

apps/frontend/src/app/collaboration/[id]/page.tsx

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -396,6 +396,7 @@ export default function CollaborationPage(props: CollaborationProps) {
396396
localStorage.removeItem("collabId");
397397
localStorage.removeItem("questionDocRefId");
398398
localStorage.removeItem("matchedTopics");
399+
localStorage.removeItem("editor-language"); // Remove editor language type when session closed
399400
};
400401

401402
return (

apps/frontend/src/components/CollaborativeEditor/CollaborativeEditor.tsx

Lines changed: 62 additions & 57 deletions
Original file line numberDiff line numberDiff line change
@@ -77,6 +77,10 @@ interface Awareness {
7777
submitting: boolean;
7878
id: number;
7979
};
80+
editorState: {
81+
language: string;
82+
id: number;
83+
};
8084
}
8185

8286
export const usercolors = [
@@ -101,8 +105,10 @@ const CollaborativeEditor = forwardRef(
101105
) => {
102106
const editorRef = useRef(null);
103107
// const providerRef = useRef<WebrtcProvider | null>(null);
104-
const [selectedLanguage, setSelectedLanguage] = useState("Python");
108+
const [selectedLanguage, setSelectedLanguage] = useState("python");
109+
const [mounted, setMounted] = useState(false);
105110
let sessionEndNotified = false;
111+
let sessionEndTimeout: any;
106112

107113
const languageConf = new Compartment();
108114

@@ -113,57 +119,25 @@ const CollaborativeEditor = forwardRef(
113119
});
114120

115121
// Referenced: https://codemirror.net/examples/config/#dynamic-configuration
116-
// const autoLanguage = EditorState.transactionExtender.of((tr) => {
117-
// if (!tr.docChanged) return null;
118-
119-
// const snippet = tr.newDoc.sliceString(0, 100);
120-
121-
// // Handle code change
122-
// props.onCodeChange(tr.newDoc.toString());
123-
124-
// // Test for various language
125-
// const docIsPython = /^\s*(def|class)\s/.test(snippet);
126-
// const docIsJava = /^\s*(class|public\s+static\s+void\s+main)\s/.test(
127-
// snippet
128-
// ); // Java has some problems
129-
// const docIsCpp = /^\s*(#include|namespace|int\s+main)\s/.test(snippet); // Yet to test c++
130-
// const docIsGo = /^(package|import|func|type|var|const)\s/.test(snippet);
131-
132-
// let newLanguage;
133-
// let languageType;
134-
// let languageLabel;
135-
136-
// if (docIsPython) {
137-
// newLanguage = python();
138-
// languageLabel = "Python";
139-
// languageType = pythonLanguage;
140-
// } else if (docIsJava) {
141-
// newLanguage = java();
142-
// languageLabel = "Java";
143-
// languageType = javaLanguage;
144-
// } else if (docIsGo) {
145-
// newLanguage = go();
146-
// languageLabel = "Go";
147-
// languageType = goLanguage;
148-
// } else if (docIsCpp) {
149-
// newLanguage = cpp();
150-
// languageLabel = "C++";
151-
// languageType = cppLanguage;
152-
// } else {
153-
// newLanguage = javascript(); // Default to JavaScript
154-
// languageLabel = "JavaScript";
155-
// languageType = javascriptLanguage;
156-
// }
157-
158-
// const stateLanguage = tr.startState.facet(language);
159-
// if (languageType == stateLanguage) return null;
160-
161-
// setSelectedLanguage(languageLabel);
162-
163-
// return {
164-
// effects: languageConf.reconfigure(newLanguage),
165-
// };
166-
// });
122+
const autoLanguage = EditorState.transactionExtender.of((tr) => {
123+
if (!tr.docChanged) return null;
124+
const editorLanguage = localStorage.getItem("editor-language") ?? "";
125+
let stateIsJs = tr.startState.facet(language) == javascriptLanguage;
126+
let stateIsPython = tr.startState.facet(language) == pythonLanguage;
127+
if (
128+
(stateIsJs && editorLanguage.toLowerCase() === "javascript") ||
129+
(stateIsPython && editorLanguage.toLowerCase() === "python")
130+
)
131+
return null;
132+
133+
return {
134+
effects: languageConf.reconfigure(
135+
editorLanguage.toLowerCase() === "javascript"
136+
? javascript()
137+
: python()
138+
),
139+
};
140+
});
167141

168142
const [messageApi, contextHolder] = message.useMessage();
169143

@@ -199,6 +173,7 @@ const CollaborativeEditor = forwardRef(
199173
let latestSubmissionId: number = new Date(0).getTime();
200174
let latestExecutingId: number = new Date(0).getTime();
201175
let latestSubmittingId: number = new Date(0).getTime();
176+
let latestLanguageChangeId: number = new Date(0).getTime();
202177

203178
useImperativeHandle(ref, () => ({
204179
endSession: () => {
@@ -219,7 +194,20 @@ const CollaborativeEditor = forwardRef(
219194
},
220195
}));
221196

222-
let sessionEndTimeout: any;
197+
useEffect(() => {
198+
localStorage.setItem("editor-language", selectedLanguage);
199+
200+
if (props.providerRef.current && mounted) {
201+
latestLanguageChangeId = Date.now();
202+
props.providerRef.current.awareness.setLocalStateField("editorState", {
203+
language: selectedLanguage,
204+
id: latestLanguageChangeId,
205+
});
206+
success(`Changed Code Editor's language to ${selectedLanguage}`);
207+
} else {
208+
setMounted(true);
209+
}
210+
}, [selectedLanguage]);
223211

224212
useEffect(() => {
225213
if (process.env.NEXT_PUBLIC_SIGNALLING_SERVICE_URL === undefined) {
@@ -309,6 +297,21 @@ const CollaborativeEditor = forwardRef(
309297
.getStates()
310298
.get(clientID) as Awareness;
311299

300+
// New section to check for changes in language
301+
if (
302+
state &&
303+
state.editorState &&
304+
state.editorState.id !== latestLanguageChangeId
305+
) {
306+
latestSubmissionId = state.editorState.id;
307+
setSelectedLanguage(state.editorState.language);
308+
// if (props.user === state.user.name) {
309+
// console.log("ownself update ownself");
310+
// } else {
311+
// console.log("others update ownself");
312+
// }
313+
}
314+
312315
if (
313316
state &&
314317
state.submissionResultsState &&
@@ -383,7 +386,7 @@ const CollaborativeEditor = forwardRef(
383386
basicSetup,
384387
languageConf.of(python()),
385388
// languageConf.of(javascript()),
386-
// autoLanguage,
389+
autoLanguage,
387390
yCollab(ytext, provider.awareness, { undoManager }),
388391
keymap.of([indentWithTab]),
389392
codeChangeListener,
@@ -410,10 +413,12 @@ const CollaborativeEditor = forwardRef(
410413
<div className="code-language">Select Language:</div>
411414
<Select
412415
className="language-select"
413-
defaultValue={selectedLanguage}
416+
// defaultValue={localStorage.getItem("editor-language")}
417+
value={selectedLanguage}
414418
options={ProgrammingLanguageOptions}
415-
onSelect={(val) => setSelectedLanguage(val)}
416-
disabled
419+
onSelect={(val) => {
420+
setSelectedLanguage(val);
421+
}}
417422
/>
418423
</div>
419424
<div

apps/frontend/src/components/Header/header.tsx

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -70,6 +70,7 @@ const Header = (props: HeaderProps): JSX.Element => {
7070
onClick: () => {
7171
// Clear away the previously stored jwt token in localstorage
7272
deleteToken();
73+
localStorage.clear();
7374
// Redirect user to login page
7475
push("/login");
7576
},

apps/frontend/src/utils/SelectOptions.ts

Lines changed: 8 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -133,14 +133,14 @@ export const ProgrammingLanguageOptions = [
133133
value: "python",
134134
label: "Python",
135135
},
136-
{
137-
value: "java",
138-
label: "Java",
139-
},
140-
{
141-
value: "c++",
142-
label: "C++",
143-
},
136+
// {
137+
// value: "java",
138+
// label: "Java",
139+
// },
140+
// {
141+
// value: "c++",
142+
// label: "C++",
143+
// },
144144
{
145145
value: "javascript",
146146
label: "JavaScript",

0 commit comments

Comments
 (0)