settings = $settings; $this->catalog = $catalog; $this->mappings = $mappings; $this->integrations = $integrations; } /** * Render the page. * * @return void */ public function render(): void { // phpcs:ignore WordPress.Security.NonceVerification.Recommended -- Read-only screen state. $action = isset( $_GET['action'] ) ? sanitize_key( wp_unslash( (string) $_GET['action'] ) ) : ''; // phpcs:ignore WordPress.Security.NonceVerification.Recommended -- Read-only screen state. $editing_id = isset( $_GET['mapping'] ) ? absint( wp_unslash( (string) $_GET['mapping'] ) ) : 0; $is_editor = in_array( $action, array( 'new', 'edit' ), true ) || $editing_id > 0; $editing = $editing_id > 0 ? $this->mappings->find( $editing_id ) : null; $catalog = $this->catalog->all(); $active_catalog = array_values( array_filter( $catalog, static function ( array $certificate ): bool { return 'active' === $certificate['status']; } ) ); $auto_certificate = ( null === $editing && 1 === count( $active_catalog ) ) ? $active_catalog[0]['id'] : ''; $trigger_event = $editing ? $editing->getEvent() : Mapping::EVENT_COURSE_COMPLETED; $trigger_event = in_array( $trigger_event, array( Mapping::EVENT_COURSE_COMPLETED, Mapping::EVENT_QUIZ_PASSED, Mapping::EVENT_LESSON_COMPLETED ), true ) ? $trigger_event : Mapping::EVENT_COURSE_COMPLETED; $score_min = $editing ? $editing->getScoreMin() : 0.0; $trigger_id = $editing ? $editing->getTriggerId() : 0; $available_lms = $this->integrations->active(); $current_lms = $editing ? $editing->getIntegration() : ''; $known_lms = '' !== $current_lms ? $this->integrations->get( $current_lms ) : null; if ( null !== $known_lms ) { $available_lms[ $current_lms ] = $known_lms; } if ( '' === $current_lms || ! isset( $available_lms[ $current_lms ] ) ) { $current_lms = (string) array_key_first( $available_lms ); } $object_value = $editing ? (string) $editing->getCourseId() . ':' . (string) $trigger_id : '0:0'; $mappings_url = add_query_arg( 'page', 'verifycate-mappings', admin_url( 'admin.php' ) ); $new_mapping_url = add_query_arg( array( 'page' => 'verifycate-mappings', 'action' => 'new', ), admin_url( 'admin.php' ) ); $search = ''; $paged = 1; $per_page = 20; $total = 0; $total_pages = 1; $orderby = 'id'; $order = 'desc'; $mappings = array(); if ( ! $is_editor ) { // phpcs:ignore WordPress.Security.NonceVerification.Recommended -- Read-only screen state. $search = isset( $_GET['s'] ) ? sanitize_text_field( wp_unslash( (string) $_GET['s'] ) ) : ''; // phpcs:ignore WordPress.Security.NonceVerification.Recommended -- Read-only screen state. $paged = isset( $_GET['paged'] ) ? max( 1, absint( wp_unslash( (string) $_GET['paged'] ) ) ) : 1; // phpcs:ignore WordPress.Security.NonceVerification.Recommended -- Read-only screen state. $orderby = isset( $_GET['orderby'] ) ? sanitize_key( wp_unslash( (string) $_GET['orderby'] ) ) : 'id'; // phpcs:ignore WordPress.Security.NonceVerification.Recommended -- Read-only screen state. $order = isset( $_GET['order'] ) && 'asc' === strtolower( sanitize_key( wp_unslash( (string) $_GET['order'] ) ) ) ? 'asc' : 'desc'; $allowed_orderby = array( 'id', 'course', 'certificate', 'status', 'repeat', 'release' ); if ( ! in_array( $orderby, $allowed_orderby, true ) ) { $orderby = 'id'; } $total = $this->mappings->count( $search ); $total_pages = max( 1, (int) ceil( $total / $per_page ) ); $paged = min( $paged, $total_pages ); $mappings = $this->mappings->paginate( $paged, $per_page, $search, $orderby, $order ); } $attribute_values = $editing ? $editing->getAttributes() : array(); $attribute_certificate = $editing ? $editing->getCertificateId() : $auto_certificate; $attribute_defs = '' !== $attribute_certificate ? $this->catalog->attributes( $attribute_certificate ) : array(); Notices::render(); ?>

settings->isConnected() ) : ?>

' . esc_html__( 'Open Get started', 'verifycate' ) . '' ) ); ?>

0 || '' !== $search ) : ?>
0 ) : ?>

renderSortableHeader( 'course', __( 'Course', 'verifycate' ), $orderby, $order, $search ); ?> renderSortableHeader( 'certificate', __( 'Certificate Name', 'verifycate' ), $orderby, $order, $search ); ?> renderSortableHeader( 'status', __( 'Status', 'verifycate' ), $orderby, $order, $search ); ?> renderSortableHeader( 'repeat', __( 'Repeat completions', 'verifycate' ), $orderby, $order, $search ); ?> renderSortableHeader( 'release', __( 'Automatic release', 'verifycate' ), $orderby, $order, $search ); ?> getId(); $edit_url = add_query_arg( array( 'page' => 'verifycate-mappings', 'action' => 'edit', 'mapping' => $mapping_id, ), admin_url( 'admin.php' ) ); ?>
courseLabel( $mapping ) ); ?> certificateLabel( $mapping ) ); ?>
getCertificateId() ); ?>
triggerLabel( $mapping ) ); ?> isEnabled() ? esc_html__( 'Enabled', 'verifycate' ) : esc_html__( 'Disabled', 'verifycate' ); ?> getAttributes() ) ); ?> getDuplicatePolicy() ? esc_html__( 'Issue again', 'verifycate' ) : esc_html__( 'Skip duplicates', 'verifycate' ); ?> shouldAutoIssue() ? esc_html__( 'Yes', 'verifycate' ) : esc_html__( 'No', 'verifycate' ); ?>
1 ) : ?>
'verifycate-mappings', 'paged' => '%#%', ); if ( '' !== $search ) { $pagination_args['s'] = $search; } if ( 'id' !== $orderby ) { $pagination_args['orderby'] = $orderby; $pagination_args['order'] = $order; } $pagination = paginate_links( array( 'base' => add_query_arg( $pagination_args, admin_url( 'admin.php' ) ), 'format' => '', 'current' => $paged, 'total' => $total_pages, 'prev_text' => '‹', 'next_text' => '›', 'type' => 'plain', ) ); if ( is_string( $pagination ) && '' !== $pagination ) { echo wp_kses_post( $pagination ); } ?>

>

>

>

renderAttributeField( $attribute_certificate, $attribute_defs, $attribute_values ); ?>
$attribute_defs Attribute definitions. * @param array $attribute_values Current values. * @return void */ private function renderAttributeField( string $attribute_certificate, array $attribute_defs, array $attribute_values ): void { ?>

renderAttributeRows( $attribute_defs, $attribute_values ); ?>

{user_meta:key}', '{course_meta:key}', '{context:key}' ) ); ?>

    $label ) : ?>
'verifycate-mappings', 'orderby' => $key, 'order' => $next_order, ); if ( '' !== $search ) { $args['s'] = $search; } $url = add_query_arg( $args, admin_url( 'admin.php' ) ); $aria_sort = $is_sorted ? ( 'asc' === $order ? 'ascending' : 'descending' ) : 'none'; ?> integrations->get( $mapping->getIntegration() ); $name = null === $integration ? $mapping->getIntegration() : $integration->getLabel(); if ( 'custom' === $mapping->getIntegration() ) { $event = '' === $mapping->getEvent() ? 'course_completed' : $mapping->getEvent(); return sprintf( /* translators: 1: event name, 2: course id or "any". */ __( 'Custom hook: %1$s (course %2$s)', 'verifycate' ), $event, $mapping->getCourseId() > 0 ? (string) $mapping->getCourseId() : __( 'any', 'verifycate' ) ); } if ( 0 === $mapping->getCourseId() ) { return sprintf( /* translators: %s: LMS name. */ __( 'Any %s course', 'verifycate' ), $name ); } $title = get_the_title( $mapping->getCourseId() ); $title = is_string( $title ) && '' !== $title ? $title : '#' . $mapping->getCourseId(); return sprintf( /* translators: 1: LMS name, 2: course title. */ __( '%1$s: %2$s', 'verifycate' ), $name, $title ); } /** * Human-readable certificate label. * * @param Mapping $mapping Mapping. * @return string */ private function certificateLabel( Mapping $mapping ): string { return '' !== $mapping->getCertificateName() ? $mapping->getCertificateName() : $mapping->getCertificateId(); } /** * Human-readable trigger label. * * @param Mapping $mapping Mapping. * @return string */ private function triggerLabel( Mapping $mapping ): string { if ( 'custom' === $mapping->getIntegration() ) { return sprintf( /* translators: %s: custom event name. */ __( 'Custom: %s', 'verifycate' ), $mapping->getEvent() ); } switch ( $mapping->getEvent() ) { case Mapping::EVENT_QUIZ_PASSED: $label = __( 'Quiz passed', 'verifycate' ); break; case Mapping::EVENT_LESSON_COMPLETED: $label = __( 'Lesson completed', 'verifycate' ); break; case Mapping::EVENT_COURSE_COMPLETED: $label = __( 'Course completed', 'verifycate' ); break; default: $label = $mapping->getEvent(); } if ( $mapping->getTriggerId() > 0 ) { $title = get_the_title( $mapping->getTriggerId() ); $title = is_string( $title ) && '' !== $title ? $title : '#' . $mapping->getTriggerId(); return sprintf( /* translators: 1: trigger name, 2: quiz or lesson title. */ __( '%1$s — %2$s', 'verifycate' ), $label, $title ); } return $label; } /** * Render one row per declared certificate attribute. * * @param array $definitions Attribute definitions. * @param array $values Current templates. * @return void */ private function renderAttributeRows( array $definitions, array $values ): void { foreach ( $definitions as $definition ) { $key = isset( $definition['key'] ) ? (string) $definition['key'] : ''; $label = isset( $definition['label'] ) ? (string) $definition['label'] : $key; if ( '' === $key ) { continue; } $value = isset( $values[ $key ] ) ? $values[ $key ] : ''; $id = 'verifycate-attribute-' . sanitize_html_class( $key ); ?>
__( 'Learner name', 'verifycate' ), '{user_email}' => __( 'Email', 'verifycate' ), '{course_title}' => __( 'Course title', 'verifycate' ), '{completion_date}' => __( 'Date', 'verifycate' ), '{score}' => __( 'Score', 'verifycate' ), ); ?>
$token_label ) : ?>

—

$attributes Attributes. * @return string */ private function formatAttributes( array $attributes ): string { $lines = array(); foreach ( $attributes as $key => $template ) { $lines[] = $key . ' = ' . $template; } return implode( "\n", $lines ); } }