'array', 'sanitize_callback' => array( __CLASS__, 'sanitize' ), ) ); } /** * Sanitize the submitted options. * * @param mixed $input Raw input. * @return array */ public static function sanitize( $input ): array { $current = Fontdelbosc_Transit_Plugin::get_options(); $input = is_array( $input ) ? $input : array(); $clean = array( 'incident_cache_ttl' => self::clamp( Fontdelbosc_Transit_Payload::int( $input['incident_cache_ttl'] ?? null ) ?? 300, 60, 86400 ), 'zbe_cache_ttl' => self::clamp( Fontdelbosc_Transit_Payload::int( $input['zbe_cache_ttl'] ?? null ) ?? 86400, 3600, 604800 ), 'default_view' => 'all' === Fontdelbosc_Transit_Payload::str( $input['default_view'] ?? null ) ? 'all' : 'c15', 'max_incidents' => self::clamp( Fontdelbosc_Transit_Payload::int( $input['max_incidents'] ?? null ) ?? 20, 1, 50 ), 'show_zbe_2026_notice' => empty( $input['show_zbe_2026_notice'] ) ? false : true, 'delete_data_on_uninstall' => empty( $input['delete_data_on_uninstall'] ) ? false : true, ); $zones = array(); if ( isset( $input['zbe_municipalities'] ) && is_array( $input['zbe_municipalities'] ) ) { foreach ( $input['zbe_municipalities'] as $slug ) { $zones[] = Fontdelbosc_Transit_Api_Zbe::sanitize_slug( Fontdelbosc_Transit_Payload::str( $slug ) ?? '' ); } } $clean['zbe_municipalities'] = array_values( array_unique( array_filter( $zones ) ) ); if ( array() === $clean['zbe_municipalities'] && isset( $input['zbe_municipalities'] ) ) { $clean['zbe_municipalities'] = (array) $current['zbe_municipalities']; } return $clean; } /** * Clamp an integer between bounds. * * @param int $value Raw value. * @param int $min Minimum. * @param int $max Maximum. * @return int */ private static function clamp( int $value, int $min, int $max ): int { return max( $min, min( $max, $value ) ); } /** * Handle the cache flush action. */ public static function handle_flush(): void { if ( ! current_user_can( 'manage_options' ) ) { wp_die( esc_html__( 'Insufficient permissions.', 'fontdelbosc-transit' ) ); } check_admin_referer( 'fontdelbosc_transit_flush' ); Fontdelbosc_Transit_Data_Manager::flush(); wp_safe_redirect( add_query_arg( 'fontdelbosc_transit_flushed', '1', admin_url( 'options-general.php?page=fontdelbosc-transit' ) ) ); exit; } /** * Admin notices: activation 2026 info and flush confirmation. */ public static function notices(): void { if ( get_transient( 'fontdelbosc_transit_2026_notice' ) ) { delete_transient( 'fontdelbosc_transit_2026_notice' ); echo '

'; echo '' . esc_html__( 'Font del Bosc — Trànsit', 'fontdelbosc-transit' ) . ': '; echo esc_html__( 'From 1 January 2026, label B vehicles are banned in Catalan ZBEs when high-pollution protocols are activated.', 'fontdelbosc-transit' ); echo '

'; } if ( isset( $_GET['fontdelbosc_transit_flushed'] ) && '1' === $_GET['fontdelbosc_transit_flushed'] ) { echo '

' . esc_html__( 'Cache flushed.', 'fontdelbosc-transit' ) . '

'; } } /** * Render the settings page. */ public static function render_page(): void { if ( ! current_user_can( 'manage_options' ) ) { wp_die( esc_html__( 'Insufficient permissions.', 'fontdelbosc-transit' ) ); } $view = FONTDELBOSC_TRANSIT_DIR . 'admin/views/settings-page.php'; if ( file_exists( $view ) ) { include $view; } } }