core: contest(OI): 订正模式

This commit is contained in:
undefined committed 2021-05-19 13:26:37 +08:00
1 parent e70beab967
commit 15827eeabb
7 files changed
+60 -26

No files matched your search

+1 -1
View File
@@ -1,6 +1,6 @@
{ {
"name": "hydrooj", "name": "hydrooj",
"version": "2.26.14", "version": "2.26.15",
"bin": "bin/hydrooj.js", "bin": "bin/hydrooj.js",
"main": "dist/loader.js", "main": "dist/loader.js",
"typings": "dist/loader.d.ts", "typings": "dist/loader.d.ts",
+4 -3
View File
@@ -269,9 +269,10 @@ export interface RecordDoc {
} }
export interface ScoreboardNode { export interface ScoreboardNode {
type: string, type: string;
value: string, value: string;
raw?: any, raw?: any;
score?: number;
} }
export type ScoreboardRow = ScoreboardNode[] & { raw?: any }; export type ScoreboardRow = ScoreboardNode[] & { raw?: any };
+39 -18
View File
@@ -110,21 +110,10 @@ const acm: ContestRule = {
} }
for (const pid of tdoc.pids) { for (const pid of tdoc.pids) {
const doc = tsddict[pid] || {}; const doc = tsddict[pid] || {};
let rid; const rid = doc.accept ? doc.rid : null;
let colAccepted; const colAccepted = `${doc.accept ? `${_('Accepted')} ` : ''}${doc.naccept ? ` (-${doc.naccept})` : ''}`;
let colTime; const colTime = doc.accept ? doc.time : '-';
let colTimeStr; const colTimeStr = doc.accept ? misc.formatSeconds(colTime) : '-';
if (doc.accept) {
rid = doc.rid;
colAccepted = `${_('Accepted')} ${doc.naccept ? ` (-${doc.naccept})` : ''}`;
colTime = doc.time;
colTimeStr = misc.formatSeconds(colTime);
} else {
rid = null;
colAccepted = doc.naccept ? `(-${doc.naccept})` : '-';
colTime = '-';
colTimeStr = '';
}
if (isExport) { if (isExport) {
row.push({ type: 'string', value: colAccepted }); row.push({ type: 'string', value: colAccepted });
row.push({ type: 'string', value: colTime }); row.push({ type: 'string', value: colTime });
@@ -132,7 +121,8 @@ const acm: ContestRule = {
} else { } else {
row.push({ row.push({
type: 'record', type: 'record',
value: '{0}<br>{1}'.format(colAccepted, colTimeStr), score: doc.accept ? 100 : 0,
value: '{0}\n{1}'.format(colAccepted, colTimeStr),
raw: rid, raw: rid,
}); });
} }
@@ -185,6 +175,19 @@ const oi: ContestRule = {
}); });
} }
} }
const psdict = {};
// eslint-disable-next-line @typescript-eslint/no-use-before-define
if (isDone(tdoc)) {
const psdocs = await problem.getMultiStatus(tdoc.domainId, {
$or: rankedTsdocs.map(([, i]) => ({
uid: i.uid,
docId: { $in: tdoc.pids },
})),
}).toArray();
for (const psdoc of psdocs) {
psdict[`${psdoc.uid}/${psdoc.docId}`] = psdoc;
}
}
const rows = [columns]; const rows = [columns];
for (const [rank, tsdoc] of rankedTsdocs) { for (const [rank, tsdoc] of rankedTsdocs) {
const tsddict = {}; const tsddict = {};
@@ -198,12 +201,30 @@ const oi: ContestRule = {
{ type: 'string', value: tsdoc.score || 0 }, { type: 'string', value: tsdoc.score || 0 },
); );
for (const pid of tdoc.pids) { for (const pid of tdoc.pids) {
// eslint-disable-next-line @typescript-eslint/no-use-before-define
if (isDone(tdoc)) {
row.push({
type: 'records',
value: '',
raw: [
{
value: tsddict[pid]?.score ?? '-',
raw: tsddict[pid]?.rid || null,
},
{
value: psdict[`${tsdoc.uid}/${pid}`]?.score ?? '-',
raw: psdict[`${tsdoc.uid}/${pid}`]?.rid ?? null,
},
],
});
} else {
row.push({ row.push({
type: 'record', type: 'record',
value: tsddict[pid]?.score ?? '-', value: tsddict[pid]?.score ?? '-',
raw: tsddict[pid]?.rid || null, raw: tsddict[pid]?.rid || null,
}); });
} }
}
rows.push(row); rows.push(row);
} }
return [rows, udict, nPages]; return [rows, udict, nPages];
@@ -313,13 +334,13 @@ const homework: ContestRule = {
}); });
} }
} }
const rows = [columns]; const rows: ScoreboardRow[] = [columns];
for (const [rank, tsdoc] of rankedTsdocs) { for (const [rank, tsdoc] of rankedTsdocs) {
const tsddict = {}; const tsddict = {};
for (const item of tsdoc.detail || []) { for (const item of tsdoc.detail || []) {
tsddict[item.pid] = item; tsddict[item.pid] = item;
} }
const row = [ const row: ScoreboardRow = [
{ type: 'string', value: rank }, { type: 'string', value: rank },
{ {
type: 'user', type: 'user',
@@ -66,6 +66,7 @@ class Nunjucks extends nunjucks.Environment {
this.addFilter('base64_encode', (s) => Buffer.from(s).toString('base64')); this.addFilter('base64_encode', (s) => Buffer.from(s).toString('base64'));
this.addFilter('base64_decode', (s) => Buffer.from(s, 'base64').toString()); this.addFilter('base64_decode', (s) => Buffer.from(s, 'base64').toString());
this.addFilter('bitand', (self, val) => self & val); this.addFilter('bitand', (self, val) => self & val);
this.addFilter('replaceBr', (self) => self.toString().replace(/\n/g, '<br>'));
this.addFilter('toString', (self) => (typeof self === 'string' ? self : JSON.stringify(self, replacer))); this.addFilter('toString', (self) => (typeof self === 'string' ? self : JSON.stringify(self, replacer)));
this.addFilter('content', (content, language, html) => { this.addFilter('content', (content, language, html) => {
let s = ''; let s = '';
+1 -1
View File
@@ -1,6 +1,6 @@
{ {
"name": "@hydrooj/ui-default", "name": "@hydrooj/ui-default",
"version": "4.8.29", "version": "4.8.30",
"author": "undefined <i@undefined.moe>", "author": "undefined <i@undefined.moe>",
"license": "AGPL-3.0", "license": "AGPL-3.0",
"main": "hydro.js", "main": "hydro.js",
@@ -41,10 +41,21 @@
{{ user.render_inline(udict[column.raw], badge=false) }} {{ user.render_inline(udict[column.raw], badge=false) }}
{% elif column.type == 'record' and column.raw %} {% elif column.type == 'record' and column.raw %}
<a href="{{ url('record_detail', rid=column.raw) }}"> <a href="{{ url('record_detail', rid=column.raw) }}">
<span style="font-weight:bold;color:{{ utils.status.getScoreColor(column.value) }}">{{ column.value|safe }}</span> <span style="font-weight:bold;color:{{ utils.status.getScoreColor(column.score|default(column.value)) }}">{{ column.value|replaceBr|safe }}</span>
</a>
{% elif column.type == 'records' %}
{%- for record in column.raw -%}
{% if loop.index0 %}/{% endif %}
{% if record.raw %}
<a href="{{ url('record_detail', rid=record.raw) }}">
<span style="font-weight:bold;color:{{ utils.status.getScoreColor(record.score|default(record.value)) }}">{{ record.value|replaceBr|safe }}</span>
</a> </a>
{% else %} {% else %}
{{ column.value|safe }} {{ record.value|replaceBr|safe }}
{% endif %}
{%- endfor -%}
{% else %}
{{ column.value|replaceBr|safe }}
{% endif %} {% endif %}
</td> </td>
{%- endfor -%} {%- endfor -%}
+1 -1
View File
@@ -292,7 +292,7 @@ function _digit2(number: number) {
} }
export function formatSeconds(_seconds = '0') { export function formatSeconds(_seconds = '0') {
const seconds = parseInt(_seconds, 10); const seconds = +_seconds;
return '{0}:{1}:{2}'.format( return '{0}:{1}:{2}'.format(
_digit2(Math.floor(seconds / 3600)), _digit2(Math.floor(seconds / 3600)),
_digit2(Math.floor((seconds % 3600) / 60)), _digit2(Math.floor((seconds % 3600) / 60)),