Fixes and improvements
This commit is contained in:
+40
-4
@@ -34,6 +34,10 @@ type CheckType =
|
||||
| "attribute-equals"
|
||||
| "css-property"
|
||||
| "element-count"
|
||||
| "interaction-text-contains"
|
||||
| "interaction-attribute-equals"
|
||||
| "interaction-css-property"
|
||||
| "interaction-element-count"
|
||||
| "visual-match";
|
||||
|
||||
type CheckDefinition = {
|
||||
@@ -42,6 +46,9 @@ type CheckDefinition = {
|
||||
value?: string;
|
||||
attribute?: string;
|
||||
property?: string;
|
||||
actionSelector?: string;
|
||||
inputSelector?: string;
|
||||
inputValue?: string;
|
||||
count?: number;
|
||||
threshold?: number;
|
||||
weight?: number;
|
||||
@@ -1149,6 +1156,24 @@ function CheckBuilder(props: {
|
||||
onChange: (index: number, patch: Partial<CheckDefinition>) => void;
|
||||
onDelete: (index: number) => void;
|
||||
}) {
|
||||
const valueCheckTypes: CheckType[] = [
|
||||
"text-contains",
|
||||
"attribute-equals",
|
||||
"css-property",
|
||||
"interaction-text-contains",
|
||||
"interaction-attribute-equals",
|
||||
"interaction-css-property"
|
||||
];
|
||||
const attributeCheckTypes: CheckType[] = ["attribute-equals", "interaction-attribute-equals"];
|
||||
const cssCheckTypes: CheckType[] = ["css-property", "interaction-css-property"];
|
||||
const countCheckTypes: CheckType[] = ["element-count", "interaction-element-count"];
|
||||
const interactionCheckTypes: CheckType[] = [
|
||||
"interaction-text-contains",
|
||||
"interaction-attribute-equals",
|
||||
"interaction-css-property",
|
||||
"interaction-element-count"
|
||||
];
|
||||
|
||||
return (
|
||||
<section className="checks">
|
||||
<div className="section-heading">
|
||||
@@ -1165,21 +1190,32 @@ function CheckBuilder(props: {
|
||||
<option value="attribute-equals">Attribute equals</option>
|
||||
<option value="css-property">CSS property</option>
|
||||
<option value="element-count">Element count</option>
|
||||
<option value="interaction-text-contains">After click: text contains</option>
|
||||
<option value="interaction-attribute-equals">After click: attribute equals</option>
|
||||
<option value="interaction-css-property">After click: CSS property</option>
|
||||
<option value="interaction-element-count">After click: element count</option>
|
||||
<option value="visual-match">Visual match</option>
|
||||
</select>
|
||||
{check.type !== "visual-match" && (
|
||||
<input value={check.selector ?? ""} onChange={(event) => props.onChange(index, { selector: event.target.value })} placeholder="selector" />
|
||||
)}
|
||||
{check.type === "attribute-equals" && (
|
||||
{interactionCheckTypes.includes(check.type) && (
|
||||
<>
|
||||
<input value={check.actionSelector ?? ""} onChange={(event) => props.onChange(index, { actionSelector: event.target.value })} placeholder="click selector" />
|
||||
<input value={check.inputSelector ?? ""} onChange={(event) => props.onChange(index, { inputSelector: event.target.value })} placeholder="input selector" />
|
||||
<input value={check.inputValue ?? ""} onChange={(event) => props.onChange(index, { inputValue: event.target.value })} placeholder="input value" />
|
||||
</>
|
||||
)}
|
||||
{attributeCheckTypes.includes(check.type) && (
|
||||
<input value={check.attribute ?? ""} onChange={(event) => props.onChange(index, { attribute: event.target.value })} placeholder="attribute" />
|
||||
)}
|
||||
{check.type === "css-property" && (
|
||||
{cssCheckTypes.includes(check.type) && (
|
||||
<input value={check.property ?? ""} onChange={(event) => props.onChange(index, { property: event.target.value })} placeholder="property" />
|
||||
)}
|
||||
{["text-contains", "attribute-equals", "css-property"].includes(check.type) && (
|
||||
{valueCheckTypes.includes(check.type) && (
|
||||
<input value={check.value ?? ""} onChange={(event) => props.onChange(index, { value: event.target.value })} placeholder="expected value" />
|
||||
)}
|
||||
{check.type === "element-count" && (
|
||||
{countCheckTypes.includes(check.type) && (
|
||||
<input type="number" value={check.count ?? 1} onChange={(event) => props.onChange(index, { count: Number(event.target.value) })} />
|
||||
)}
|
||||
{check.type === "visual-match" && (
|
||||
|
||||
@@ -314,6 +314,7 @@ p {
|
||||
grid-template-columns: minmax(360px, 1fr) minmax(320px, 42%);
|
||||
gap: 1rem;
|
||||
margin-top: 1rem;
|
||||
min-width: 0;
|
||||
}
|
||||
|
||||
.editors,
|
||||
@@ -327,6 +328,7 @@ p {
|
||||
.submission-detail {
|
||||
display: grid;
|
||||
gap: 0.7rem;
|
||||
min-width: 0;
|
||||
}
|
||||
|
||||
.editor-section,
|
||||
@@ -340,6 +342,7 @@ p {
|
||||
background: #fff;
|
||||
border: 1px solid #d8e0e8;
|
||||
border-radius: 8px;
|
||||
min-width: 0;
|
||||
}
|
||||
|
||||
.section-title,
|
||||
@@ -569,6 +572,7 @@ p {
|
||||
.submitted-code {
|
||||
display: grid;
|
||||
gap: 0.7rem;
|
||||
min-width: 0;
|
||||
}
|
||||
|
||||
.submitted-code h3 {
|
||||
@@ -657,11 +661,28 @@ p {
|
||||
}
|
||||
|
||||
.cm-editor {
|
||||
width: 100%;
|
||||
max-width: 100%;
|
||||
min-width: 0;
|
||||
border: 1px solid #d8e0e8;
|
||||
border-radius: 6px;
|
||||
overflow: hidden;
|
||||
}
|
||||
|
||||
.cm-scroller {
|
||||
max-width: 100%;
|
||||
overflow-x: auto;
|
||||
}
|
||||
|
||||
.cm-content {
|
||||
overflow-wrap: anywhere;
|
||||
}
|
||||
|
||||
.cm-line {
|
||||
white-space: pre-wrap;
|
||||
overflow-wrap: anywhere;
|
||||
}
|
||||
|
||||
@media (max-width: 1050px) {
|
||||
.student-layout,
|
||||
.admin-layout,
|
||||
|
||||
Reference in New Issue
Block a user