2016-07-18 16:39:37 +00:00
< ? php
function uojHandleAtSign ( $str , $uri ) {
$referrers = array ();
2022-11-06 02:26:21 +00:00
$res = preg_replace_callback ( '/@(@|[a-zA-Z0-9_]{1,20})/' , function ( $matches ) use ( & $referrers ) {
2016-07-18 16:39:37 +00:00
if ( $matches [ 1 ] === '@' ) {
return '@' ;
} else {
$user = queryUser ( $matches [ 1 ]);
if ( $user == null ) {
return $matches [ 0 ];
} else {
$referrers [ $user [ 'username' ]] = '' ;
2022-11-06 02:26:21 +00:00
return '<span class="uoj-username">@' . $user [ 'username' ] . '</span>' ;
2016-07-18 16:39:37 +00:00
}
}
}, $str );
2022-11-06 02:26:21 +00:00
2016-07-18 16:39:37 +00:00
$referrers_list = array ();
foreach ( $referrers as $referrer => $val ) {
$referrers_list [] = $referrer ;
}
2022-11-06 02:26:21 +00:00
2016-07-18 16:39:37 +00:00
return array ( $res , $referrers_list );
}
2022-11-06 02:26:21 +00:00
function uojStringPreview ( $str , $output_limit , $type = 'text' ) {
switch ( $type ) {
2018-10-11 15:01:50 +00:00
case 'text' :
2022-11-06 02:26:21 +00:00
return strOmit ( $str , $output_limit );
case 'binary' :
return strOmit ( chunk_split ( chunk_split ( bin2hex ( $str ), 8 , ' ' ), ( 8 + 1 ) * 8 , " \n " ), $output_limit * 2 );
2018-10-11 15:01:50 +00:00
default :
2022-11-06 02:26:21 +00:00
return false ;
2018-10-11 15:01:50 +00:00
}
2016-07-18 16:39:37 +00:00
}
2022-11-06 02:26:21 +00:00
function uojFilePreview ( $file_name , $output_limit , $file_type = 'text' ) {
return uojStringPreview ( file_get_contents ( $file_name , false , null , 0 , $output_limit + 4 ), $output_limit , $file_type );
}
2016-07-18 16:39:37 +00:00
function uojIncludeView ( $name , $view_params = array ()) {
extract ( $view_params );
2022-11-06 02:26:21 +00:00
include $_SERVER [ 'DOCUMENT_ROOT' ] . '/app/views/' . $name . '.php' ;
2016-07-18 16:39:37 +00:00
}
2022-11-06 02:26:21 +00:00
function redirectTo ( string $url ) {
header ( 'Location: ' . $url );
die ();
}
function permanentlyRedirectTo ( string $url ) {
header ( " HTTP/1.1 301 Moved Permanently " );
header ( 'Location: ' . $url );
die ();
}
function permanentlyRedirectToHTTPS () {
if ( UOJContext :: isUsingHttps ()) {
return false ;
}
permanentlyRedirectTo ( 'https://' . UOJContext :: httpHost () . UOJContext :: requestURI ());
2016-07-18 16:39:37 +00:00
die ();
}
2022-11-06 02:26:21 +00:00
function permanentlyRedirectToHTTP () {
if ( ! UOJContext :: isUsingHttps ()) {
return false ;
}
permanentlyRedirectTo ( 'http://' . UOJContext :: httpHost () . UOJContext :: requestURI ());
2016-07-18 16:39:37 +00:00
die ();
}
function redirectToLogin () {
if ( UOJContext :: isAjax ()) {
2022-11-06 02:26:21 +00:00
die ( 'please <a href="' . HTML :: url ( '/login' ) . '">login</a>' );
2016-07-18 16:39:37 +00:00
} else {
2022-11-06 02:26:21 +00:00
header ( 'Location: ' . HTML :: url ( '/login' ));
2016-07-18 16:39:37 +00:00
die ();
}
}
function becomeMsgPage ( $msg , $title = '消息' ) {
2022-09-23 22:25:27 +00:00
global $REQUIRE_LIB ;
2016-07-18 16:39:37 +00:00
if ( UOJContext :: isAjax ()) {
die ( $msg );
} else {
2022-10-22 13:12:13 +00:00
$REQUIRE_LIB [ 'bootstrap5' ] = '' ;
2022-09-23 22:25:27 +00:00
2016-07-18 16:39:37 +00:00
echoUOJPageHeader ( $title );
echo $msg ;
echoUOJPageFooter ();
die ();
}
}
2022-04-02 10:01:26 +00:00
function become404Page ( $message = '未找到页面。' ) {
2016-07-18 16:39:37 +00:00
header ( $_SERVER [ 'SERVER_PROTOCOL' ] . " 404 Not Found " , true , 404 );
2022-04-02 10:01:26 +00:00
becomeMsgPage ( '<div class="text-center"><div style="font-size:150px">404</div><p>' . $message . '</p></div>' , '404' );
2016-07-18 16:39:37 +00:00
}
2022-04-02 10:01:26 +00:00
function become403Page ( $message = '访问被拒绝,您可能需要适当的权限以访问此页面。' ) {
2022-11-06 02:26:21 +00:00
header ( $_SERVER [ 'SERVER_PROTOCOL' ] . " 403 Forbidden " , true , 403 );
2022-04-02 10:01:26 +00:00
becomeMsgPage ( '<div class="text-center"><div style="font-size:150px">403</div><p>' . $message . '</p></div>' , '403' );
2016-07-18 16:39:37 +00:00
}
2022-03-17 03:02:44 +00:00
function getUserLink ( $username ) {
2022-10-01 10:00:42 +00:00
if ( validateUsername ( $username ) && ( $user = queryUser ( $username )) && $user [ 'usergroup' ] != 'B' ) {
2022-03-17 10:26:29 +00:00
$realname = $user [ 'realname' ];
if ( $realname == " " ) {
2022-11-06 02:26:21 +00:00
return '<span class="uoj-username">' . $username . '</span>' ;
2022-03-17 10:26:29 +00:00
} else {
2022-11-06 02:26:21 +00:00
return '<span class="uoj-username" data-realname="' . HTML :: escape ( $realname ) . '">' . $username . '</span>' ;
2022-03-17 10:26:29 +00:00
}
2016-07-18 16:39:37 +00:00
} else {
$esc_username = HTML :: escape ( $username );
2022-11-06 02:26:21 +00:00
return '<span>' . $esc_username . '</span>' ;
2016-07-18 16:39:37 +00:00
}
}
2022-03-17 10:26:29 +00:00
function getUserName ( $username , $realname = null ) {
if ( $realname == null ) {
if ( validateUsername ( $username ) && ( $user = queryUser ( $username ))) {
$realname = $user [ 'realname' ];
}
}
if ( $realname == " " ) {
return " $username " ;
} else {
return " $username ( $realname ) " ;
}
}
2016-07-18 16:39:37 +00:00
function getProblemLink ( $problem , $problem_title = '!title_only' ) {
2022-09-24 00:13:39 +00:00
global $REQUIRE_LIB ;
2016-07-18 16:39:37 +00:00
if ( $problem_title == '!title_only' ) {
$problem_title = $problem [ 'title' ];
2020-06-25 12:41:16 +00:00
} elseif ( $problem_title == '!id_and_title' ) {
2016-07-18 16:39:37 +00:00
$problem_title = " # ${ problem['id'] } . ${ problem['title'] } " ;
}
2022-09-24 00:13:39 +00:00
$result = '<a ' ;
if ( isset ( $REQUIRE_LIB [ 'bootstrap5' ])) {
$result .= ' class="text-decoration-none" ' ;
}
2022-11-06 02:26:21 +00:00
$result .= ' href="/problem/' . $problem [ 'id' ] . '">' . $problem_title . '</a>' ;
2022-09-24 00:13:39 +00:00
return $result ;
2016-07-18 16:39:37 +00:00
}
function getContestProblemLink ( $problem , $contest_id , $problem_title = '!title_only' ) {
if ( $problem_title == '!title_only' ) {
$problem_title = $problem [ 'title' ];
2020-06-25 12:41:16 +00:00
} elseif ( $problem_title == '!id_and_title' ) {
2016-07-18 16:39:37 +00:00
$problem_title = " # { $problem [ 'id' ] } . { $problem [ 'title' ] } " ;
}
2022-11-06 02:26:21 +00:00
$result = '<a class="text-decoration-none" href="/contest/' . $contest_id . '/problem/' . $problem [ 'id' ] . '">' . $problem_title . '</a>' ;
2022-09-24 00:13:39 +00:00
return $result ;
2016-07-18 16:39:37 +00:00
}
function getBlogLink ( $id ) {
2022-09-26 12:55:56 +00:00
$result = '' ;
2016-07-18 16:39:37 +00:00
if ( validateUInt ( $id ) && $blog = queryBlog ( $id )) {
2022-11-06 02:26:21 +00:00
$result = '<a class="text-decoration-none" href="/blogs/' . $id . '">' . $blog [ 'title' ] . '</a>' ;
2016-07-18 16:39:37 +00:00
}
2022-09-26 12:55:56 +00:00
return $result ;
2016-07-18 16:39:37 +00:00
}
function getLongTablePageRawUri ( $page ) {
2020-06-25 12:41:16 +00:00
$path = strtok ( UOJContext :: requestURI (), '?' );
$query_string = strtok ( '?' );
parse_str ( $query_string , $param );
2022-11-06 02:26:21 +00:00
2020-06-25 12:41:16 +00:00
$param [ 'page' ] = $page ;
if ( $page == 1 ) {
unset ( $param [ 'page' ]);
}
2022-11-06 02:26:21 +00:00
2020-06-25 12:41:16 +00:00
if ( $param ) {
return $path . '?' . http_build_query ( $param );
} else {
return $path ;
2016-07-18 16:39:37 +00:00
}
2020-06-25 12:41:16 +00:00
}
2016-07-18 16:39:37 +00:00
function getLongTablePageUri ( $page ) {
return HTML :: escape ( getLongTablePageRawUri ( $page ));
}
function echoLongTable ( $col_names , $table_name , $cond , $tail , $header_row , $print_row , $config ) {
$pag_config = $config ;
$pag_config [ 'col_names' ] = $col_names ;
$pag_config [ 'table_name' ] = $table_name ;
$pag_config [ 'cond' ] = $cond ;
$pag_config [ 'tail' ] = $tail ;
$pag = new Paginator ( $pag_config );
2022-11-06 02:26:21 +00:00
$div_classes = isset ( $config [ 'div_classes' ]) ? $config [ 'div_classes' ] : [ 'table-responsive' ];
$table_classes = isset ( $config [ 'table_classes' ]) ? $config [ 'table_classes' ] : [ 'table' , 'text-center' , 'align-middle' ];
2022-09-20 09:19:51 +00:00
if ( isset ( $config [ 'head_pagination' ]) && $config [ 'head_pagination' ]) {
echo $pag -> pagination ();
}
2022-11-06 02:26:21 +00:00
echo '<div class="' , implode ( ' ' , $div_classes ), '">' ;
2022-10-22 11:24:48 +00:00
if ( isset ( $config [ 'print_before_table' ])) {
$fun = $config [ 'print_before_table' ];
$fun ();
}
2022-11-06 02:26:21 +00:00
echo '<table class="' , implode ( ' ' , $table_classes ), '">' ;
2016-07-18 16:39:37 +00:00
echo '<thead>' ;
echo $header_row ;
echo '</thead>' ;
echo '<tbody>' ;
foreach ( $pag -> get () as $idx => $row ) {
if ( isset ( $config [ 'get_row_index' ])) {
$print_row ( $row , $idx );
} else {
$print_row ( $row );
}
}
if ( $pag -> isEmpty ()) {
2022-11-06 02:26:21 +00:00
echo HTML :: tr_none ();
2016-07-18 16:39:37 +00:00
}
echo '</tbody>' ;
echo '</table>' ;
2022-10-22 11:24:48 +00:00
2016-07-18 16:39:37 +00:00
if ( isset ( $config [ 'print_after_table' ])) {
$fun = $config [ 'print_after_table' ];
$fun ();
}
2022-10-22 11:24:48 +00:00
echo '</div>' ;
2022-11-06 02:26:21 +00:00
2016-07-18 16:39:37 +00:00
echo $pag -> pagination ();
}
function getSubmissionStatusDetails ( $submission ) {
2022-11-06 02:26:21 +00:00
$html = '<td class="text-center" colspan="233" style="vertical-align: middle">' ;
2016-07-18 16:39:37 +00:00
$out_status = explode ( ', ' , $submission [ 'status' ])[ 0 ];
2022-11-06 02:26:21 +00:00
2019-09-10 02:20:30 +00:00
$fly = '<img src="/images/utility/qpx_n/b37.gif" alt="小熊像超人一样飞" class="img-rounded" />' ;
$think = '<img src="/images/utility/qpx_n/b29.gif" alt="小熊像在思考" class="img-rounded" />' ;
2022-11-06 02:26:21 +00:00
2016-07-18 16:39:37 +00:00
if ( $out_status == 'Judged' ) {
$status_text = '<strong>Judged!</strong>' ;
$status_img = $fly ;
} else {
if ( $submission [ 'status_details' ] !== '' ) {
$status_img = $fly ;
$status_text = HTML :: escape ( $submission [ 'status_details' ]);
2020-06-25 12:41:16 +00:00
} else {
2016-07-18 16:39:37 +00:00
$status_img = $think ;
$status_text = $out_status ;
}
}
$html .= '<div class="uoj-status-details-img-div">' . $status_img . '</div>' ;
$html .= '<div class="uoj-status-details-text-div">' . $status_text . '</div>' ;
$html .= '</td>' ;
return $html ;
}
2022-11-06 02:26:21 +00:00
function getSubmissionStatusDetailsHTML ( $status , $status_details ) {
$html = '<td class="text-center" colspan="233" style="vertical-align: middle">' ;
2022-09-24 00:13:39 +00:00
2022-11-06 02:26:21 +00:00
$fly = '<img src="/images/utility/qpx_n/b37.gif" alt="小熊像超人一样飞" class="img-rounded" />' ;
$think = '<img src="/images/utility/qpx_n/b29.gif" alt="小熊像在思考" class="img-rounded" />' ;
if ( $status == 'Judged' ) {
$status_text = '<strong>Judged!</strong>' ;
$status_img = $fly ;
2016-07-18 16:39:37 +00:00
} else {
2022-11-06 02:26:21 +00:00
if ( $status_details !== '' ) {
$status_img = $fly ;
$status_text = HTML :: escape ( $status_details );
2016-07-18 16:39:37 +00:00
} else {
2022-11-06 02:26:21 +00:00
$status_img = $think ;
$status_text = $status ;
2016-07-18 16:39:37 +00:00
}
2020-06-25 12:41:16 +00:00
}
2022-11-06 02:26:21 +00:00
$html .= '<div class="uoj-status-details-img-div">' . $status_img . '</div>' ;
$html .= '<div class="uoj-status-details-text-div">' . $status_text . '</div>' ;
2016-07-18 16:39:37 +00:00
2022-11-06 02:26:21 +00:00
$html .= '</td>' ;
return $html ;
}
2016-07-18 16:39:37 +00:00
2022-11-06 02:26:21 +00:00
function echoSubmission ( $submission , $config , $viewer ) {
$usubm = new UOJSubmission ( $submission );
$usubm -> setProblem ();
$usubm -> echoStatusTableRow ( $config , $viewer );
2016-07-18 16:39:37 +00:00
}
function echoSubmissionsListOnlyOne ( $submission , $config , $user ) {
2022-11-06 02:26:21 +00:00
echo '<div class="card mb-3 table-responsive">' ;
echo '<table class="table text-center uoj-table mb-0">' ;
2016-07-18 16:39:37 +00:00
echo '<thead>' ;
echo '<tr>' ;
2020-06-25 12:41:16 +00:00
if ( ! isset ( $config [ 'id_hidden' ])) {
2016-07-18 16:39:37 +00:00
echo '<th>ID</th>' ;
2020-06-25 12:41:16 +00:00
}
if ( ! isset ( $config [ 'problem_hidden' ])) {
2022-11-06 02:26:21 +00:00
echo '<th>' . UOJLocale :: get ( 'problems::problem' ) . '</th>' ;
2020-06-25 12:41:16 +00:00
}
if ( ! isset ( $config [ 'submitter_hidden' ])) {
2022-11-06 02:26:21 +00:00
echo '<th>' . UOJLocale :: get ( 'problems::submitter' ) . '</th>' ;
2020-06-25 12:41:16 +00:00
}
if ( ! isset ( $config [ 'result_hidden' ])) {
2022-11-06 06:22:22 +00:00
echo '<th style="min-width:3em">' . UOJLocale :: get ( 'problems::result' ) . '</th>' ;
2020-06-25 12:41:16 +00:00
}
if ( ! isset ( $config [ 'used_time_hidden' ])) {
2022-11-06 02:26:21 +00:00
echo '<th>' . UOJLocale :: get ( 'problems::used time' ) . '</th>' ;
2020-06-25 12:41:16 +00:00
}
if ( ! isset ( $config [ 'used_memory_hidden' ])) {
2022-11-06 02:26:21 +00:00
echo '<th>' . UOJLocale :: get ( 'problems::used memory' ) . '</th>' ;
2020-06-25 12:41:16 +00:00
}
2022-11-06 06:22:22 +00:00
echo '<th style="min-width:5em">' . UOJLocale :: get ( 'problems::language' ) . '</th>' ;
echo '<th style="min-width:5em">' . UOJLocale :: get ( 'problems::file size' ) . '</th>' ;
2020-06-25 12:41:16 +00:00
if ( ! isset ( $config [ 'submit_time_hidden' ])) {
2022-11-06 02:26:21 +00:00
echo '<th>' . UOJLocale :: get ( 'problems::submit time' ) . '</th>' ;
2020-06-25 12:41:16 +00:00
}
if ( ! isset ( $config [ 'judge_time_hidden' ])) {
2022-11-06 02:26:21 +00:00
echo '<th>' . UOJLocale :: get ( 'problems::judge time' ) . '</th>' ;
2020-06-25 12:41:16 +00:00
}
2016-07-18 16:39:37 +00:00
echo '</tr>' ;
echo '</thead>' ;
echo '<tbody>' ;
echoSubmission ( $submission , $config , $user );
echo '</tbody>' ;
echo '</table>' ;
echo '</div>' ;
}
function echoSubmissionsList ( $cond , $tail , $config , $user ) {
$header_row = '<tr>' ;
2022-11-06 02:26:21 +00:00
$col_names = [
'submissions.status_details' ,
'submissions.status' ,
'submissions.result_error' ,
'submissions.score' ,
];
if ( ! isset ( $config [ 'problem' ])) {
$config [ 'problem' ] = null ;
}
2016-07-18 16:39:37 +00:00
if ( ! isset ( $config [ 'id_hidden' ])) {
$header_row .= '<th>ID</th>' ;
$col_names [] = 'submissions.id' ;
}
if ( ! isset ( $config [ 'problem_hidden' ])) {
2022-11-06 02:26:21 +00:00
$header_row .= '<th>' . UOJLocale :: get ( 'problems::problem' ) . '</th>' ;
2016-07-18 16:39:37 +00:00
$col_names [] = 'submissions.problem_id' ;
$col_names [] = 'submissions.contest_id' ;
}
if ( ! isset ( $config [ 'submitter_hidden' ])) {
2022-11-06 02:26:21 +00:00
$header_row .= '<th>' . UOJLocale :: get ( 'problems::submitter' ) . '</th>' ;
2016-07-18 16:39:37 +00:00
$col_names [] = 'submissions.submitter' ;
}
if ( ! isset ( $config [ 'result_hidden' ])) {
2022-11-06 06:15:07 +00:00
$header_row .= '<th style="min-width:3em">' . UOJLocale :: get ( 'problems::result' ) . '</th>' ;
2016-07-18 16:39:37 +00:00
}
if ( ! isset ( $config [ 'used_time_hidden' ])) {
2022-11-06 02:26:21 +00:00
$header_row .= '<th>' . UOJLocale :: get ( 'problems::used time' ) . '</th>' ;
2016-07-18 16:39:37 +00:00
$col_names [] = 'submissions.used_time' ;
}
if ( ! isset ( $config [ 'used_memory_hidden' ])) {
2022-11-06 02:26:21 +00:00
$header_row .= '<th>' . UOJLocale :: get ( 'problems::used memory' ) . '</th>' ;
2016-07-18 16:39:37 +00:00
$col_names [] = 'submissions.used_memory' ;
}
2022-11-06 06:15:07 +00:00
$header_row .= '<th style="min-width:5em">' . UOJLocale :: get ( 'problems::language' ) . '</th>' ;
2016-07-18 16:39:37 +00:00
$col_names [] = 'submissions.language' ;
2022-11-06 06:15:07 +00:00
$header_row .= '<th style="min-width:5em">' . UOJLocale :: get ( 'problems::file size' ) . '</th>' ;
2016-07-18 16:39:37 +00:00
$col_names [] = 'submissions.tot_size' ;
if ( ! isset ( $config [ 'submit_time_hidden' ])) {
2022-11-06 02:26:21 +00:00
$header_row .= '<th>' . UOJLocale :: get ( 'problems::submit time' ) . '</th>' ;
2016-07-18 16:39:37 +00:00
$col_names [] = 'submissions.submit_time' ;
}
if ( ! isset ( $config [ 'judge_time_hidden' ])) {
2022-11-06 02:26:21 +00:00
$header_row .= '<th>' . UOJLocale :: get ( 'problems::judge time' ) . '</th>' ;
2016-07-18 16:39:37 +00:00
$col_names [] = 'submissions.judge_time' ;
}
$header_row .= '</tr>' ;
2022-11-06 02:26:21 +00:00
2016-07-18 16:39:37 +00:00
$table_name = isset ( $config [ 'table_name' ]) ? $config [ 'table_name' ] : 'submissions' ;
2022-11-06 02:26:21 +00:00
2022-10-10 09:03:57 +00:00
if ( ! isProblemManager ( $user )) {
2016-07-18 16:39:37 +00:00
if ( $user != null ) {
2022-11-06 02:26:21 +00:00
$permission_cond = DB :: lor ([
2022-11-06 07:00:59 +00:00
" submissions.is_hidden " => false ,
2022-11-06 02:26:21 +00:00
" submissions.submitter " => $user [ 'username' ],
DB :: land ([
" submissions.is_hidden " => true ,
DB :: lor ([
" submissions.problem_id in (select problem_id from problems_permissions where username = ' { $user [ 'username' ] } ') " ,
2022-11-06 07:00:59 +00:00
" submissions.problem_id in (select id from problems where uploader = ' { $user [ 'username' ] } ') " ,
2022-11-06 02:26:21 +00:00
]),
]),
]);
2016-07-18 16:39:37 +00:00
} else {
2022-11-06 02:26:21 +00:00
$permission_cond = [ " submissions.is_hidden " => " false " ];
2016-07-18 16:39:37 +00:00
}
if ( $cond !== '1' ) {
2022-11-06 02:26:21 +00:00
$cond = DB :: land ( $cond , $permission_cond );
2016-07-18 16:39:37 +00:00
} else {
$cond = $permission_cond ;
}
}
2022-11-06 02:26:21 +00:00
2016-07-18 16:39:37 +00:00
$table_config = isset ( $config [ 'table_config' ]) ? $config [ 'table_config' ] : null ;
2022-11-06 02:26:21 +00:00
echoLongTable (
$col_names ,
$table_name ,
$cond ,
$tail ,
$header_row ,
function ( $submission ) use ( $config , $user ) {
2016-07-18 16:39:37 +00:00
echoSubmission ( $submission , $config , $user );
2022-11-06 02:26:21 +00:00
},
$table_config
);
2016-07-18 16:39:37 +00:00
}
function echoSubmissionContent ( $submission , $requirement ) {
$zip_file = new ZipArchive ();
$submission_content = json_decode ( $submission [ 'content' ], true );
2022-11-06 02:26:21 +00:00
$zip_file -> open ( UOJContext :: storagePath () . $submission_content [ 'file_name' ]);
2016-07-18 16:39:37 +00:00
$config = array ();
foreach ( $submission_content [ 'config' ] as $config_key => $config_val ) {
$config [ $config_val [ 0 ]] = $config_val [ 1 ];
}
2022-11-06 02:26:21 +00:00
2016-07-18 16:39:37 +00:00
foreach ( $requirement as $req ) {
if ( $req [ 'type' ] == " source code " ) {
$file_content = $zip_file -> getFromName ( " { $req [ 'name' ] } .code " );
$file_content = uojTextEncode ( $file_content , array ( 'allow_CR' => true , 'html_escape' => true ));
$file_language = htmlspecialchars ( $config [ " { $req [ 'name' ] } _language " ]);
2022-11-06 02:26:21 +00:00
$footer_text = UOJLocale :: get ( 'problems::source code' ) . ', ' . UOJLocale :: get ( 'problems::language' ) . ': ' . $file_language ;
2016-07-18 16:39:37 +00:00
switch ( $file_language ) {
case 'C++' :
case 'C++11' :
2022-09-18 02:54:13 +00:00
case 'C++17' :
2022-10-04 13:31:28 +00:00
case 'C++20' :
2022-09-18 02:54:13 +00:00
case 'C++98' :
2022-10-04 13:31:28 +00:00
case 'C++03' :
2022-10-04 23:47:56 +00:00
$sh_class = 'sh_cpp language-cpp' ;
2016-07-18 16:39:37 +00:00
break ;
2019-06-28 08:40:41 +00:00
case 'Python2' :
2022-10-04 13:31:28 +00:00
case 'Python2.7' :
2016-07-18 16:39:37 +00:00
case 'Python3' :
2022-10-04 23:47:56 +00:00
$sh_class = 'sh_python language-python' ;
break ;
case 'Java8' :
case 'Java11' :
case 'Java17' :
$sh_class = 'sh_java language-java' ;
2016-07-18 16:39:37 +00:00
break ;
case 'C' :
2022-10-04 23:47:56 +00:00
$sh_class = 'sh_c language-c' ;
2016-07-18 16:39:37 +00:00
break ;
case 'Pascal' :
2022-10-04 23:47:56 +00:00
$sh_class = 'sh_pascal language-pascal' ;
2016-07-18 16:39:37 +00:00
break ;
default :
$sh_class = '' ;
break ;
}
2019-09-10 02:15:20 +00:00
echo '<div class="card border-info mb-3">' ;
echo '<div class="card-header bg-info">' ;
2022-11-06 02:26:21 +00:00
echo '<h4 class="card-title">' . $req [ 'name' ] . '</h4>' ;
2016-07-18 16:39:37 +00:00
echo '</div>' ;
2019-09-10 02:15:20 +00:00
echo '<div class="card-body">' ;
2022-11-06 02:26:21 +00:00
echo '<pre><code class="' . $sh_class . ' bg-light rounded p-3">' . $file_content . " \n " . '</code></pre>' ;
2016-07-18 16:39:37 +00:00
echo '</div>' ;
2022-11-06 02:26:21 +00:00
echo '<div class="card-footer">' . $footer_text . '</div>' ;
2016-07-18 16:39:37 +00:00
echo '</div>' ;
2020-06-25 12:41:16 +00:00
} elseif ( $req [ 'type' ] == " text " ) {
2016-07-18 16:39:37 +00:00
$file_content = $zip_file -> getFromName ( " { $req [ 'file_name' ] } " , 504 );
$file_content = strOmit ( $file_content , 500 );
$file_content = uojTextEncode ( $file_content , array ( 'allow_CR' => true , 'html_escape' => true ));
$footer_text = UOJLocale :: get ( 'problems::text file' );
2019-09-10 02:15:20 +00:00
echo '<div class="card border-info mb-3">' ;
echo '<div class="card-header bg-info">' ;
2022-11-06 02:26:21 +00:00
echo '<h4 class="card-title">' . $req [ 'file_name' ] . '</h4>' ;
2016-07-18 16:39:37 +00:00
echo '</div>' ;
2019-09-10 02:15:20 +00:00
echo '<div class="card-body">' ;
2022-11-06 02:26:21 +00:00
echo '<pre class="bg-light rounded p-3 ">' , " \n " . $file_content . " \n " . '</pre>' ;
2016-07-18 16:39:37 +00:00
echo '</div>' ;
2022-11-06 02:26:21 +00:00
echo '<div class="card-footer">' . $footer_text . '</div>' ;
2016-07-18 16:39:37 +00:00
echo '</div>' ;
}
}
$zip_file -> close ();
}
2022-11-06 02:26:21 +00:00
class JudgmentDetailsPrinter {
2016-07-18 16:39:37 +00:00
private $name ;
private $styler ;
2022-11-06 02:26:21 +00:00
private DOMDocument $dom ;
2016-07-18 16:39:37 +00:00
private $subtask_num ;
2022-11-06 02:26:21 +00:00
private function _get_attr ( DOMElement $node , string $attr , $default = '' ) {
$val = $node -> getAttribute ( $attr );
if ( $val === '' ) {
$val = $default ;
}
return $val ;
}
private function _print_c ( DOMElement $node ) {
2016-07-18 16:39:37 +00:00
foreach ( $node -> childNodes as $child ) {
if ( $child -> nodeName == '#text' ) {
echo htmlspecialchars ( $child -> nodeValue );
} else {
$this -> _print ( $child );
}
}
}
2022-11-06 02:26:21 +00:00
private function _print ( DOMElement $node ) {
2016-07-18 16:39:37 +00:00
if ( $node -> nodeName == 'error' ) {
2022-11-06 02:26:21 +00:00
echo '<pre class="bg-light rounded p-3">' , " \n " ;
2016-07-18 16:39:37 +00:00
$this -> _print_c ( $node );
echo " \n </pre> " ;
} elseif ( $node -> nodeName == 'tests' ) {
2022-11-06 02:26:21 +00:00
if ( $node -> hasAttribute ( " errcode " )) {
echo " <pre> " , " Judgment Failed. Error Code: " , $node -> getAttribute ( " errcode " ), " .</pre> " ;
2022-09-24 13:50:59 +00:00
}
2022-11-06 02:26:21 +00:00
echo '<div id="' , $this -> name , '_details_accordion">' ;
$this -> _print_c ( $node );
2016-07-18 16:39:37 +00:00
if ( $this -> styler -> show_small_tip ) {
2022-11-06 02:26:21 +00:00
echo '<div class="my-2 px-2 text-end text-muted">' , '小提示:点击横条可展开更详细的信息' , '</div>' ;
2022-09-24 13:50:59 +00:00
}
2016-07-18 16:39:37 +00:00
echo '</div>' ;
} elseif ( $node -> nodeName == 'subtask' ) {
2022-11-06 02:26:21 +00:00
$subtask_info = $node -> getAttribute ( 'info' );
2016-07-18 16:39:37 +00:00
$subtask_num = $node -> getAttribute ( 'num' );
$subtask_score = $node -> getAttribute ( 'score' );
2022-11-06 02:26:21 +00:00
$subtask_time = $this -> _get_attr ( $node , 'time' , - 1 );
$subtask_memory = $this -> _get_attr ( $node , 'memory' , - 1 );
$subtask_type = $this -> _get_attr ( $node , 'type' , 'packed' );
$subtask_used_time_type = $this -> _get_attr ( $node , 'used-time-type' , 'sum' );
echo '<div class="card border-0 rounded-0 border-bottom ' , $this -> styler -> getTestInfoClass ( $subtask_info ), '">' ;
2016-07-18 16:39:37 +00:00
$accordion_parent = " { $this -> name } _details_accordion " ;
$accordion_collapse = " { $accordion_parent } _collapse_subtask_ { $subtask_num } " ;
$accordion_collapse_accordion = " { $accordion_collapse } _accordion " ;
2022-11-06 02:26:21 +00:00
echo '<div class="card-header uoj-submission-result-item bg-transparent rounded-0 border-0" data-bs-toggle="collapse" data-bs-parent="#' , $accordion_parent , '" data-bs-target="#' , $accordion_collapse , '">' ;
2022-09-24 13:50:59 +00:00
2016-07-18 16:39:37 +00:00
echo '<div class="row">' ;
2022-09-24 13:50:59 +00:00
echo '<div class="col-sm-4">' ;
2022-11-06 02:26:21 +00:00
echo '<h3 class="fs-5">' , 'Subtask #' , $subtask_num , ': ' , '</h3>' ;
2016-07-18 16:39:37 +00:00
echo '</div>' ;
2022-11-06 02:26:21 +00:00
2016-07-18 16:39:37 +00:00
if ( $this -> styler -> show_score ) {
echo '<div class="col-sm-2">' ;
2022-11-07 14:02:56 +00:00
echo '<i class="bi bi-clipboard-check"></i> ' , $subtask_score , ' pts' ;
2016-07-18 16:39:37 +00:00
echo '</div>' ;
2022-09-24 14:01:38 +00:00
echo '<div class="col-sm-2 uoj-status-text">' ;
2022-11-06 02:26:21 +00:00
echo $this -> styler -> getTestInfoIcon ( $subtask_info );
2016-07-18 16:39:37 +00:00
echo htmlspecialchars ( $subtask_info );
echo '</div>' ;
} else {
echo '<div class="col-sm-4">' ;
2022-11-06 02:26:21 +00:00
echo $this -> styler -> getTestInfoIcon ( $subtask_info );
2016-07-18 16:39:37 +00:00
echo htmlspecialchars ( $subtask_info );
echo '</div>' ;
}
2022-11-06 02:26:21 +00:00
if ( $subtask_time >= 0 ) {
2022-11-06 23:46:13 +00:00
echo '<div class="col-sm-2">' ;
2022-11-06 02:26:21 +00:00
echo '<i class="bi bi-hourglass-split"></i> ' , $subtask_time , ' ms' ;
echo '</div>' ;
}
if ( $subtask_memory >= 0 ) {
2022-11-06 23:46:13 +00:00
echo '<div class="col-sm-2">' ;
2022-11-06 02:26:21 +00:00
echo '<i class="bi bi-memory"></i> ' , $subtask_memory , ' kB' ;
echo '</div>' ;
}
2016-07-18 16:39:37 +00:00
echo '</div>' ;
echo '</div>' ;
2022-11-06 02:26:21 +00:00
2019-09-10 02:15:20 +00:00
echo '<div id="' , $accordion_collapse , '" class="card-collapse collapse">' ;
2022-11-06 02:26:21 +00:00
echo '<div class="card-body pt-0">' ;
2016-07-18 16:39:37 +00:00
2022-11-06 02:26:21 +00:00
echo '<div id="' , $accordion_collapse_accordion , '" class="border rounded overflow-hidden">' ;
2016-07-18 16:39:37 +00:00
$this -> subtask_num = $subtask_num ;
$this -> _print_c ( $node );
$this -> subtask_num = null ;
echo '</div>' ;
echo '</div>' ;
echo '</div>' ;
echo '</div>' ;
} elseif ( $node -> nodeName == 'test' ) {
$test_info = $node -> getAttribute ( 'info' );
$test_num = $node -> getAttribute ( 'num' );
$test_score = $node -> getAttribute ( 'score' );
2022-11-06 02:26:21 +00:00
$test_time = $this -> _get_attr ( $node , 'time' , - 1 );
$test_memory = $this -> _get_attr ( $node , 'memory' , - 1 );
echo '<div class="card border-0 rounded-0 border-bottom ' , $this -> styler -> getTestInfoClass ( $test_info ), '">' ;
2016-07-18 16:39:37 +00:00
$accordion_parent = " { $this -> name } _details_accordion " ;
if ( $this -> subtask_num != null ) {
$accordion_parent .= " _collapse_subtask_ { $this -> subtask_num } _accordion " ;
}
$accordion_collapse = " { $accordion_parent } _collapse_test_ { $test_num } " ;
if ( ! $this -> styler -> shouldFadeDetails ( $test_info )) {
2022-11-06 02:26:21 +00:00
echo '<div class="card-header uoj-submission-result-item bg-transparent rounded-0 border-0" data-bs-toggle="collapse" data-bs-parent="#' , $accordion_parent , '" data-bs-target="#' , $accordion_collapse , '">' ;
} else {
echo '<div class="card-header uoj-submission-result-item bg-transparent rounded-0 border-0">' ;
2016-07-18 16:39:37 +00:00
}
echo '<div class="row">' ;
2022-09-24 13:19:48 +00:00
echo '<div class="col-sm-4">' ;
2016-07-18 16:39:37 +00:00
if ( $test_num > 0 ) {
2022-11-06 02:26:21 +00:00
echo '<h4 class="fs-5">' , 'Test #' , $test_num , ': ' , '</h4>' ;
2016-07-18 16:39:37 +00:00
} else {
2022-11-06 02:26:21 +00:00
echo '<h4 class="fs-5">' , 'Extra Test:' , '</h4>' ;
2016-07-18 16:39:37 +00:00
}
echo '</div>' ;
2022-11-06 02:26:21 +00:00
2016-07-18 16:39:37 +00:00
if ( $this -> styler -> show_score ) {
echo '<div class="col-sm-2">' ;
2022-11-06 02:26:21 +00:00
echo '<i class="bi bi-clipboard-check"></i> ' , $test_score , ' pts' ;
2016-07-18 16:39:37 +00:00
echo '</div>' ;
2022-11-06 02:26:21 +00:00
echo '<div class="col-sm-2 uoj-status-text">' ;
echo $this -> styler -> getTestInfoIcon ( $test_info );
2016-07-18 16:39:37 +00:00
echo htmlspecialchars ( $test_info );
echo '</div>' ;
} else {
2022-11-06 02:26:21 +00:00
echo '<div class="col-sm-4 uoj-status-text">' ;
echo $this -> styler -> getTestInfoIcon ( $test_info );
2016-07-18 16:39:37 +00:00
echo htmlspecialchars ( $test_info );
echo '</div>' ;
}
2022-09-24 13:19:48 +00:00
2016-07-18 16:39:37 +00:00
if ( $test_time >= 0 ) {
2022-11-06 02:26:21 +00:00
echo '<div class="col-sm-2">' ;
echo '<i class="bi bi-hourglass-split"></i> ' , $test_time , ' ms' ;
echo '</div>' ;
2016-07-18 16:39:37 +00:00
}
if ( $test_memory >= 0 ) {
2022-11-06 02:26:21 +00:00
echo '<div class="col-sm-2">' ;
echo '<i class="bi bi-memory"></i> ' , $test_memory , 'kB' ;
echo '</div>' ;
2016-07-18 16:39:37 +00:00
}
echo '</div>' ;
echo '</div>' ;
if ( ! $this -> styler -> shouldFadeDetails ( $test_info )) {
2019-09-10 02:15:20 +00:00
$accordion_collapse_class = 'card-collapse collapse' ;
2016-07-18 16:39:37 +00:00
if ( $this -> styler -> collapse_in ) {
$accordion_collapse_class .= ' in' ;
}
2022-09-20 05:10:25 +00:00
echo '<div id="' , $accordion_collapse , '" class="uoj-testcase ' , $accordion_collapse_class , '" data-test=' . $test_num . '>' ;
2019-09-10 02:15:20 +00:00
echo '<div class="card-body">' ;
2016-07-18 16:39:37 +00:00
$this -> _print_c ( $node );
echo '</div>' ;
echo '</div>' ;
}
echo '</div>' ;
} elseif ( $node -> nodeName == 'custom-test' ) {
$test_info = $node -> getAttribute ( 'info' );
2022-11-06 02:26:21 +00:00
$test_time = $this -> _get_attr ( $node , 'time' , - 1 );
$test_memory = $this -> _get_attr ( $node , 'memory' , - 1 );
2016-07-18 16:39:37 +00:00
2022-11-06 02:26:21 +00:00
echo '<div class="card ' , $this -> styler -> getTestInfoClass ( $test_info ), ' mb-3">' ;
2022-09-25 10:28:43 +00:00
2016-07-18 16:39:37 +00:00
$accordion_parent = " { $this -> name } _details_accordion " ;
$accordion_collapse = " { $accordion_parent } _collapse_custom_test " ;
if ( ! $this -> styler -> shouldFadeDetails ( $test_info )) {
2022-11-06 02:26:21 +00:00
echo '<div class="card-header uoj-submission-result-item bg-transparent rounded-0 border-0" data-bs-toggle="collapse" data-bs-parent="#' , $accordion_parent , '" data-bs-target="#' , $accordion_collapse , '">' ;
} else {
echo '<div class="card-header uoj-submission-result-item bg-transparent rounded-0 border-0">' ;
2016-07-18 16:39:37 +00:00
}
echo '<div class="row">' ;
2022-09-27 08:53:39 +00:00
echo '<div class="col-sm-4">' ;
2019-09-10 02:15:20 +00:00
echo '<h4 class="card-title">' , 'Custom Test: ' , '</h4>' ;
2016-07-18 16:39:37 +00:00
echo '</div>' ;
2022-09-27 08:53:39 +00:00
2022-11-06 02:26:21 +00:00
echo '<div class="col-sm-4 uoj-status-text">' ;
echo $this -> styler -> getTestInfoIcon ( $test_info );
2016-07-18 16:39:37 +00:00
echo htmlspecialchars ( $test_info );
echo '</div>' ;
2022-11-06 02:26:21 +00:00
2016-07-18 16:39:37 +00:00
if ( $test_time >= 0 ) {
2022-11-06 02:26:21 +00:00
echo '<div class="col-sm-2">' ;
echo '<i class="bi bi-hourglass-split"></i> ' , $test_time , ' ms' ;
echo '</div>' ;
2016-07-18 16:39:37 +00:00
}
if ( $test_memory >= 0 ) {
2022-11-06 02:26:21 +00:00
echo '<div class="col-sm-2">' ;
echo '<i class="bi bi-memory"></i> ' , $test_memory , ' kB' ;
echo '</div>' ;
2016-07-18 16:39:37 +00:00
}
echo '</div>' ;
echo '</div>' ;
if ( ! $this -> styler -> shouldFadeDetails ( $test_info )) {
2019-09-10 02:15:20 +00:00
$accordion_collapse_class = 'card-collapse collapse' ;
2016-07-18 16:39:37 +00:00
if ( $this -> styler -> collapse_in ) {
$accordion_collapse_class .= ' in' ;
}
echo '<div id="' , $accordion_collapse , '" class="' , $accordion_collapse_class , '">' ;
2019-09-10 02:15:20 +00:00
echo '<div class="card-body">' ;
2016-07-18 16:39:37 +00:00
$this -> _print_c ( $node );
echo '</div>' ;
echo '</div>' ;
echo '</div>' ;
}
} elseif ( $node -> nodeName == 'in' ) {
2022-11-06 02:26:21 +00:00
echo '<h4 class="fs-6"><span>input: </span></h4>' ;
echo '<pre class="bg-light p-3 rounded">' , " \n " ;
2016-07-18 16:39:37 +00:00
$this -> _print_c ( $node );
echo " \n </pre> " ;
} elseif ( $node -> nodeName == 'out' ) {
2022-11-06 02:26:21 +00:00
echo '<h4 class="fs-6"><span>output: </span></h4>' ;
echo '<pre class="bg-light p-3 rounded">' , " \n " ;
2016-07-18 16:39:37 +00:00
$this -> _print_c ( $node );
echo " \n </pre> " ;
} elseif ( $node -> nodeName == 'res' ) {
2022-11-06 02:26:21 +00:00
echo '<h4 class="fs-6"><span>result: </span></h4>' ;
echo '<pre class="bg-light p-3 rounded">' , " \n " ;
if ( $node -> hasChildNodes ()) {
$this -> _print_c ( $node );
2022-09-24 13:19:48 +00:00
} else {
2022-11-06 02:26:21 +00:00
echo " \n " ;
}
echo " </pre> " ;
} elseif ( $node -> nodeName == " info-block " ) {
echo '<div>' ;
if ( $node -> hasAttribute ( " title " )) {
if ( $node -> hasAttribute ( " size " )) {
echo '<div class="float-end text-muted">' ;
if ( $node -> getAttribute ( " size " ) <= 1 ) {
echo '(' , $node -> getAttribute ( " size " ), ' byte)' ;
} else {
echo '(' , $node -> getAttribute ( " size " ), ' bytes)' ;
}
echo '</div>' ;
}
echo '<h4 class="mb-2">' , $node -> getAttribute ( " title " ), " :</h4> " ;
2022-09-24 13:19:48 +00:00
}
2022-11-06 02:26:21 +00:00
echo '<pre>' , " \n " ;
2016-07-18 16:39:37 +00:00
$this -> _print_c ( $node );
echo " \n </pre> " ;
2022-11-06 02:26:21 +00:00
echo '</div>' ;
2016-07-18 16:39:37 +00:00
} else {
echo '<' , $node -> nodeName ;
foreach ( $node -> attributes as $attr ) {
echo ' ' , $attr -> name , '="' , htmlspecialchars ( $attr -> value ), '"' ;
}
echo '>' ;
$this -> _print_c ( $node );
echo '</' , $node -> nodeName , '>' ;
}
}
public function __construct ( $details , $styler , $name ) {
$this -> name = $name ;
$this -> styler = $styler ;
$this -> details = $details ;
$this -> dom = new DOMDocument ();
if ( ! $this -> dom -> loadXML ( $this -> details )) {
throw new Exception ( " XML syntax error " );
}
$this -> details = '' ;
}
public function printHTML () {
$this -> subtask_num = null ;
$this -> _print ( $this -> dom -> documentElement );
}
}
function echoJudgementDetails ( $raw_details , $styler , $name ) {
try {
2022-11-06 02:26:21 +00:00
$printer = new JudgmentDetailsPrinter ( $raw_details , $styler , $name );
2016-07-18 16:39:37 +00:00
$printer -> printHTML ();
} catch ( Exception $e ) {
echo 'Failed to show details' ;
}
}
class SubmissionDetailsStyler {
public $show_score = true ;
public $show_small_tip = true ;
public $collapse_in = false ;
public $fade_all_details = false ;
public function getTestInfoClass ( $info ) {
if ( $info == 'Accepted' || $info == 'Extra Test Passed' ) {
2019-09-10 02:15:20 +00:00
return 'card-uoj-accepted' ;
2016-07-18 16:39:37 +00:00
} elseif ( $info == 'Time Limit Exceeded' ) {
2019-09-10 02:15:20 +00:00
return 'card-uoj-tle' ;
2016-07-18 16:39:37 +00:00
} elseif ( $info == 'Acceptable Answer' ) {
2019-09-10 02:15:20 +00:00
return 'card-uoj-acceptable-answer' ;
2016-07-18 16:39:37 +00:00
} else {
2019-09-10 02:15:20 +00:00
return 'card-uoj-wrong' ;
2016-07-18 16:39:37 +00:00
}
}
2022-09-24 13:50:59 +00:00
public function getTestInfoIcon ( $test_info ) {
if ( $test_info == 'Accepted' || $test_info == 'Extra Test Passed' ) {
return '<i class="bi bi-check-lg"></i> ' ;
} elseif ( $test_info == 'Time Limit Exceeded' ) {
return '<i class="bi bi-clock"></i> ' ;
} elseif ( $test_info == 'Acceptable Answer' ) {
return '<i class="bi bi-dash-square"></i> ' ;
} elseif ( $test_info == 'Wrong Answer' ) {
return '<i class="bi bi-x-lg"></i> ' ;
} else {
return '<i class="bi bi-slash-circle"></i> ' ;
}
}
2016-07-18 16:39:37 +00:00
public function shouldFadeDetails ( $info ) {
return $this -> fade_all_details || $info == 'Extra Test Passed' ;
}
}
class CustomTestSubmissionDetailsStyler {
public $show_score = true ;
public $show_small_tip = false ;
public $collapse_in = true ;
public $fade_all_details = false ;
2019-06-11 03:03:53 +00:00
public $ioi_contest_is_running = false ;
2016-07-18 16:39:37 +00:00
public function getTestInfoClass ( $info ) {
if ( $info == 'Success' ) {
2019-09-10 02:15:20 +00:00
return 'card-uoj-accepted' ;
2016-07-18 16:39:37 +00:00
} elseif ( $info == 'Time Limit Exceeded' ) {
2019-09-10 02:15:20 +00:00
return 'card-uoj-tle' ;
2016-07-18 16:39:37 +00:00
} elseif ( $info == 'Acceptable Answer' ) {
2019-09-10 02:15:20 +00:00
return 'card-uoj-acceptable-answer' ;
2016-07-18 16:39:37 +00:00
} else {
2019-09-10 02:15:20 +00:00
return 'card-uoj-wrong' ;
2016-07-18 16:39:37 +00:00
}
}
2022-09-27 08:53:39 +00:00
public function getTestInfoIcon ( $test_info ) {
if ( $test_info == 'Success' ) {
return '<i class="bi bi-check-lg"></i> ' ;
} elseif ( $test_info == 'Time Limit Exceeded' ) {
return '<i class="bi bi-clock"></i> ' ;
} elseif ( $test_info == 'Acceptable Answer' ) {
return '<i class="bi bi-dash-square"></i> ' ;
} elseif ( $test_info == 'Wrong Answer' ) {
return '<i class="bi bi-x-lg"></i> ' ;
} else {
return '<i class="bi bi-slash-circle"></i> ' ;
}
}
2016-07-18 16:39:37 +00:00
public function shouldFadeDetails ( $info ) {
return $this -> fade_all_details ;
}
}
class HackDetailsStyler {
public $show_score = false ;
public $show_small_tip = false ;
public $collapse_in = true ;
public $fade_all_details = false ;
public function getTestInfoClass ( $info ) {
if ( $info == 'Accepted' || $info == 'Extra Test Passed' ) {
2019-09-10 02:15:20 +00:00
return 'card-uoj-accepted' ;
2016-07-18 16:39:37 +00:00
} elseif ( $info == 'Time Limit Exceeded' ) {
2019-09-10 02:15:20 +00:00
return 'card-uoj-tle' ;
2016-07-18 16:39:37 +00:00
} elseif ( $info == 'Acceptable Answer' ) {
2019-09-10 02:15:20 +00:00
return 'card-uoj-acceptable-answer' ;
2016-07-18 16:39:37 +00:00
} else {
2019-09-10 02:15:20 +00:00
return 'card-uoj-wrong' ;
2016-07-18 16:39:37 +00:00
}
}
2022-09-25 02:44:33 +00:00
public function getTestInfoIcon ( $test_info ) {
if ( $test_info == 'Accepted' || $test_info == 'Extra Test Passed' ) {
return '<i class="bi bi-check-lg"></i> ' ;
} elseif ( $test_info == 'Time Limit Exceeded' ) {
return '<i class="bi bi-clock"></i> ' ;
} elseif ( $test_info == 'Acceptable Answer' ) {
return '<i class="bi bi-dash-square"></i> ' ;
} elseif ( $test_info == 'Wrong Answer' ) {
return '<i class="bi bi-x-lg"></i> ' ;
} else {
return '<i class="bi bi-slash-circle"></i> ' ;
}
}
2016-07-18 16:39:37 +00:00
public function shouldFadeDetails ( $info ) {
return $this -> fade_all_details ;
}
}
function echoSubmissionDetails ( $submission_details , $name ) {
echoJudgementDetails ( $submission_details , new SubmissionDetailsStyler (), $name );
}
function echoCustomTestSubmissionDetails ( $submission_details , $name ) {
echoJudgementDetails ( $submission_details , new CustomTestSubmissionDetailsStyler (), $name );
}
function echoHackDetails ( $hack_details , $name ) {
echoJudgementDetails ( $hack_details , new HackDetailsStyler (), $name );
}
function echoHack ( $hack , $config , $user ) {
$problem = queryProblemBrief ( $hack [ 'problem_id' ]);
echo '<tr>' ;
2020-06-25 12:41:16 +00:00
if ( ! isset ( $config [ 'id_hidden' ])) {
2022-11-06 02:26:21 +00:00
echo '<td><a href="/hack/' , $hack [ 'id' ], '">#' , $hack [ 'id' ], '</a></td>' ;
2020-06-25 12:41:16 +00:00
}
if ( ! isset ( $config [ 'submission_hidden' ])) {
2022-11-06 02:26:21 +00:00
echo '<td><a href="/submission/' , $hack [ 'submission_id' ], '">#' , $hack [ 'submission_id' ], '</a></td>' ;
2020-06-25 12:41:16 +00:00
}
2016-07-18 16:39:37 +00:00
if ( ! isset ( $config [ 'problem_hidden' ])) {
if ( $hack [ 'contest_id' ]) {
echo '<td>' , getContestProblemLink ( $problem , $hack [ 'contest_id' ], '!id_and_title' ), '</td>' ;
} else {
echo '<td>' , getProblemLink ( $problem , '!id_and_title' ), '</td>' ;
}
}
2020-06-25 12:41:16 +00:00
if ( ! isset ( $config [ 'hacker_hidden' ])) {
2016-07-18 16:39:37 +00:00
echo '<td>' , getUserLink ( $hack [ 'hacker' ]), '</td>' ;
2020-06-25 12:41:16 +00:00
}
if ( ! isset ( $config [ 'owner_hidden' ])) {
2016-07-18 16:39:37 +00:00
echo '<td>' , getUserLink ( $hack [ 'owner' ]), '</td>' ;
2020-06-25 12:41:16 +00:00
}
if ( ! isset ( $config [ 'result_hidden' ])) {
if ( $hack [ 'judge_time' ] == null ) {
2022-11-06 02:26:21 +00:00
echo '<td><a href="/hack/' , $hack [ 'id' ], '">Waiting</a></td>' ;
2016-07-18 16:39:37 +00:00
} elseif ( $hack [ 'success' ] == null ) {
2022-11-06 02:26:21 +00:00
echo '<td><a href="/hack/' , $hack [ 'id' ], '">Judging</a></td>' ;
2016-07-18 16:39:37 +00:00
} elseif ( $hack [ 'success' ]) {
2022-11-06 02:26:21 +00:00
echo '<td><a href="/hack/' , $hack [ 'id' ], '" class="uoj-status" data-success="1"><strong>Success!</strong></a></td>' ;
2016-07-18 16:39:37 +00:00
} else {
2022-11-06 02:26:21 +00:00
echo '<td><a href="/hack/' , $hack [ 'id' ], '" class="uoj-status" data-success="0"><strong>Failed.</strong></a></td>' ;
2016-07-18 16:39:37 +00:00
}
2020-06-25 12:41:16 +00:00
} else {
2016-07-18 16:39:37 +00:00
echo '<td>Hidden</td>' ;
2020-06-25 12:41:16 +00:00
}
if ( ! isset ( $config [ 'submit_time_hidden' ])) {
2016-07-18 16:39:37 +00:00
echo '<td>' , $hack [ 'submit_time' ], '</td>' ;
2020-06-25 12:41:16 +00:00
}
if ( ! isset ( $config [ 'judge_time_hidden' ])) {
2016-07-18 16:39:37 +00:00
echo '<td>' , $hack [ 'judge_time' ], '</td>' ;
2020-06-25 12:41:16 +00:00
}
2016-07-18 16:39:37 +00:00
echo '</tr>' ;
}
function echoHackListOnlyOne ( $hack , $config , $user ) {
2022-11-06 02:26:21 +00:00
echo '<div class="card mb-3 table-responsive">' ;
echo '<table class="table text-center uoj-table mb-0">' ;
2016-07-18 16:39:37 +00:00
echo '<thead>' ;
echo '<tr>' ;
2020-06-25 12:41:16 +00:00
if ( ! isset ( $config [ 'id_hidden' ])) {
2016-07-18 16:39:37 +00:00
echo '<th>ID</th>' ;
2020-06-25 12:41:16 +00:00
}
if ( ! isset ( $config [ 'submission_id_hidden' ])) {
2022-11-06 02:26:21 +00:00
echo '<th>' . UOJLocale :: get ( 'problems::submission id' ) . '</th>' ;
2020-06-25 12:41:16 +00:00
}
if ( ! isset ( $config [ 'problem_hidden' ])) {
2022-11-06 02:26:21 +00:00
echo '<th>' . UOJLocale :: get ( 'problems::problem' ) . '</th>' ;
2020-06-25 12:41:16 +00:00
}
if ( ! isset ( $config [ 'hacker_hidden' ])) {
2022-11-06 02:26:21 +00:00
echo '<th>' . UOJLocale :: get ( 'problems::hacker' ) . '</th>' ;
2020-06-25 12:41:16 +00:00
}
if ( ! isset ( $config [ 'owner_hidden' ])) {
2022-11-06 02:26:21 +00:00
echo '<th>' . UOJLocale :: get ( 'problems::owner' ) . '</th>' ;
2020-06-25 12:41:16 +00:00
}
if ( ! isset ( $config [ 'result_hidden' ])) {
2022-11-06 02:26:21 +00:00
echo '<th>' . UOJLocale :: get ( 'problems::result' ) . '</th>' ;
2020-06-25 12:41:16 +00:00
}
if ( ! isset ( $config [ 'submit_time_hidden' ])) {
2022-11-06 02:26:21 +00:00
echo '<th>' . UOJLocale :: get ( 'problems::submit time' ) . '</th>' ;
2020-06-25 12:41:16 +00:00
}
if ( ! isset ( $config [ 'judge_time_hidden' ])) {
2022-11-06 02:26:21 +00:00
echo '<th>' . UOJLocale :: get ( 'problems::judge time' ) . '</th>' ;
2020-06-25 12:41:16 +00:00
}
2016-07-18 16:39:37 +00:00
echo '</tr>' ;
echo '</thead>' ;
echo '<tbody>' ;
echoHack ( $hack , $config , $user );
echo '</tbody>' ;
echo '</table>' ;
echo '</div>' ;
}
function echoHacksList ( $cond , $tail , $config , $user ) {
$header_row = '<tr>' ;
2022-11-06 02:26:21 +00:00
$col_names = [];
2016-07-18 16:39:37 +00:00
$col_names [] = 'id' ;
$col_names [] = 'success' ;
2022-11-06 02:26:21 +00:00
$col_names [] = 'status' ;
2016-07-18 16:39:37 +00:00
$col_names [] = 'judge_time' ;
2022-11-06 02:26:21 +00:00
2016-07-18 16:39:37 +00:00
if ( ! isset ( $config [ 'id_hidden' ])) {
$header_row .= '<th>ID</th>' ;
}
if ( ! isset ( $config [ 'submission_id_hidden' ])) {
2022-11-06 02:26:21 +00:00
$header_row .= '<th>' . UOJLocale :: get ( 'problems::submission id' ) . '</th>' ;
2016-07-18 16:39:37 +00:00
$col_names [] = 'submission_id' ;
}
if ( ! isset ( $config [ 'problem_hidden' ])) {
2022-11-06 02:26:21 +00:00
$header_row .= '<th>' . UOJLocale :: get ( 'problems::problem' ) . '</th>' ;
2016-07-18 16:39:37 +00:00
$col_names [] = 'problem_id' ;
}
if ( ! isset ( $config [ 'hacker_hidden' ])) {
2022-11-06 02:26:21 +00:00
$header_row .= '<th>' . UOJLocale :: get ( 'problems::hacker' ) . '</th>' ;
2016-07-18 16:39:37 +00:00
$col_names [] = 'hacker' ;
}
if ( ! isset ( $config [ 'owner_hidden' ])) {
2022-11-06 02:26:21 +00:00
$header_row .= '<th>' . UOJLocale :: get ( 'problems::owner' ) . '</th>' ;
2016-07-18 16:39:37 +00:00
$col_names [] = 'owner' ;
}
if ( ! isset ( $config [ 'result_hidden' ])) {
2022-11-06 02:26:21 +00:00
$header_row .= '<th>' . UOJLocale :: get ( 'problems::result' ) . '</th>' ;
2016-07-18 16:39:37 +00:00
}
if ( ! isset ( $config [ 'submit_time_hidden' ])) {
2022-11-06 02:26:21 +00:00
$header_row .= '<th>' . UOJLocale :: get ( 'problems::submit time' ) . '</th>' ;
2016-07-18 16:39:37 +00:00
$col_names [] = 'submit_time' ;
}
if ( ! isset ( $config [ 'judge_time_hidden' ])) {
2022-11-06 02:26:21 +00:00
$header_row .= '<th>' . UOJLocale :: get ( 'problems::judge time' ) . '</th>' ;
2016-07-18 16:39:37 +00:00
}
$header_row .= '</tr>' ;
if ( ! isSuperUser ( $user )) {
if ( $user != null ) {
2022-11-06 02:26:21 +00:00
$permission_cond = DB :: lor ([
'is_hidden' => false ,
DB :: land ([
'is_hidden' => true ,
DB :: lor ([
[
'problem_id' , 'in' , DB :: rawbracket ([
'select problem_id from problems_permissions' ,
'where' , [ 'username' => $user [ 'username' ]]
])
],
[
'problem_id' , 'in' , DB :: rawbracket ([
'select problem_id from problems' ,
'where' , [ 'uploader' => $user [ 'username' ]]
])
]
])
])
]);
2016-07-18 16:39:37 +00:00
} else {
2022-11-06 02:26:21 +00:00
$permission_cond = [ 'is_hidden' => false ];
2016-07-18 16:39:37 +00:00
}
if ( $cond !== '1' ) {
2022-11-06 02:26:21 +00:00
$cond = [
DB :: conds ( $cond ),
DB :: conds ( $permission_cond )
];
2016-07-18 16:39:37 +00:00
} else {
$cond = $permission_cond ;
}
}
2022-09-26 12:42:46 +00:00
$table_config = isset ( $config [ 'table_config' ]) ? $config [ 'table_config' ] : null ;
2022-11-06 02:26:21 +00:00
echoLongTable (
$col_names ,
'hacks' ,
$cond ,
$tail ,
$header_row ,
function ( $hacks ) use ( $config , $user ) {
2016-07-18 16:39:37 +00:00
echoHack ( $hacks , $config , $user );
2022-11-06 02:26:21 +00:00
},
$table_config
);
2016-07-18 16:39:37 +00:00
}
function echoBlog ( $blog , $config = array ()) {
2022-09-29 14:02:56 +00:00
global $REQUIRE_LIB ;
2016-07-18 16:39:37 +00:00
$default_config = array (
'blog' => $blog ,
'show_title_only' => false ,
'is_preview' => false
);
foreach ( $default_config as $key => $val ) {
if ( ! isset ( $config [ $key ])) {
$config [ $key ] = $val ;
}
}
2022-09-29 14:02:56 +00:00
$config [ 'REQUIRE_LIB' ] = $REQUIRE_LIB ;
2016-07-18 16:39:37 +00:00
uojIncludeView ( 'blog-preview' , $config );
}
function echoBlogTag ( $tag ) {
2022-11-06 02:26:21 +00:00
echo ' <a class="uoj-blog-tag">' , '<span class="badge bg-secondary">' , HTML :: escape ( $tag ), '</span></a> ' ;
2016-07-18 16:39:37 +00:00
}
function echoUOJPageHeader ( $page_title , $extra_config = array ()) {
global $REQUIRE_LIB ;
$config = UOJContext :: pageConfig ();
$config [ 'REQUIRE_LIB' ] = $REQUIRE_LIB ;
$config [ 'PageTitle' ] = $page_title ;
$config = array_merge ( $config , $extra_config );
uojIncludeView ( 'page-header' , $config );
}
function echoUOJPageFooter ( $config = array ()) {
2022-09-23 13:00:17 +00:00
global $REQUIRE_LIB ;
$config [ 'REQUIRE_LIB' ] = $REQUIRE_LIB ;
2016-07-18 16:39:37 +00:00
uojIncludeView ( 'page-footer' , $config );
}
2022-03-21 02:51:31 +00:00
2022-11-06 02:26:21 +00:00
function echoRanklist ( $config = []) {
2022-03-21 02:51:31 +00:00
$header_row = '' ;
$header_row .= '<tr>' ;
$header_row .= '<th style="width: 5em;">#</th>' ;
2022-11-06 02:26:21 +00:00
$header_row .= '<th style="width: 14em;">' . UOJLocale :: get ( 'username' ) . '</th>' ;
$header_row .= '<th style="width: 50em;">' . UOJLocale :: get ( 'motto' ) . '</th>' ;
$header_row .= '<th style="width: 5em;">' . UOJLocale :: get ( 'solved' ) . '</th>' ;
2022-03-21 02:51:31 +00:00
$header_row .= '</tr>' ;
2022-10-12 11:13:33 +00:00
$parsedown = HTML :: parsedown ();
2022-10-09 13:33:13 +00:00
$purifier = HTML :: purifier_inline ();
2022-11-06 02:26:21 +00:00
$users = [];
$print_row = function ( $user , $now_cnt ) use ( & $users , $config , $purifier , $parsedown ) {
2022-03-21 02:51:31 +00:00
if ( ! $users ) {
if ( $now_cnt == 1 ) {
$rank = 1 ;
} else {
$rank = DB :: selectCount ( " select count(*) from (select b.username as username, count(*) as accepted from best_ac_submissions a inner join user_info b on a.submitter = b.username group by username) as derived where accepted > { $user [ 'ac_num' ] } " ) + 1 ;
}
} else {
$rank = $now_cnt ;
}
$user [ 'rank' ] = $rank ;
echo '<tr>' ;
echo '<td>' . $user [ 'rank' ] . '</td>' ;
echo '<td>' . getUserLink ( $user [ 'username' ]) . '</td>' ;
2022-10-08 11:42:04 +00:00
echo " <td> " ;
2022-10-12 11:13:33 +00:00
echo $purifier -> purify ( $parsedown -> line ( $user [ 'motto' ]));
2022-10-08 11:42:04 +00:00
echo " </td> " ;
2022-03-21 02:51:31 +00:00
echo '<td>' . $user [ 'ac_num' ] . '</td>' ;
echo '</tr>' ;
2022-11-06 02:26:21 +00:00
2022-03-21 02:51:31 +00:00
$users [] = $user ;
};
2022-11-06 02:26:21 +00:00
$from = 'user_info' ;
$col_names = [ 'user_info.username as username' , 'ac_num' , 'motto' ];
2022-03-21 02:51:31 +00:00
$cond = '1' ;
2022-11-06 02:26:21 +00:00
$tail = 'group by user_info.username order by ac_num desc, user_info.username asc' ;
2022-03-21 02:51:31 +00:00
if ( isset ( $config [ 'group_id' ])) {
$group_id = $config [ 'group_id' ];
2022-11-06 02:26:21 +00:00
$from = " user_info inner join groups_users on (user_info.username = groups_users.username and groups_users.group_id = { $group_id } ) " ;
2022-10-22 01:29:51 +00:00
$config [ 'pagination_cond' ] = " group_id = { $group_id } " ;
2022-03-21 02:51:31 +00:00
}
if ( isset ( $config [ 'top10' ])) {
$tail .= ' limit 10' ;
}
$config [ 'get_row_index' ] = '' ;
echoLongTable ( $col_names , $from , $cond , $tail , $header_row , $print_row , $config );
}
2022-11-06 02:26:21 +00:00
// ===== uoj.ac =====
function echoJudgmentDetails ( $raw_details , $styler , $name ) {
try {
$printer = new JudgmentDetailsPrinter ( $raw_details , $styler , $name );
$printer -> printHTML ();
} catch ( Exception $e ) {
echo 'Failed to show details' ;
}
}