Chiamare un metodo da functions.php al click di un pulsante
Sto lavorando a un progetto dove devo chiamare un metodo (che accetta l'ID utente come input) al click di un pulsante di submit (pulsante Accetta).
Ho provato vari modi, ma la sfida principale è capire come ottenere l'ID utente nel frontend e passarlo al metodo.
Il mio metodo aggiorna i meta dati dell'utente specifico.
Codice HTML:
<div id="modal">
<div class="modalconent">
<h3 align=center>GDPR</h3>
<p>Questo è un popup GDPR</p><br><br><br>
<form>
<input name="accept" type="checkbox" value="Gdpr" required/>Accetto il GDPR
<input type="submit" id="accept-button" value="Accetta">
</form>
</div>
</div>
<script>
window.onload = function () {
document.getElementById('accept-button').onclick = function () {
document.getElementById('modal').style.display = "none"
};
};
</script>
Attualmente, il mio pulsante Accetta quando cliccato imposta solo display:none. Vorrei chiamare il metodo insieme a display:none;
Il mio codice PHP:
function updateHasReadFlag($user) {
// Ho aggiunto il supporto per usare questa funzione sia con ID utente che con oggetto utente
if ( $user && is_int( $user ) ) {
$user_id = $user;
} else if ( ! empty( $user->ID ) ) {
$user_id = $user->ID;
} else {
return;
}
return update_user_meta( $user_id, 'META_KEY', true );
}
Il codice del form generato:
<form method="post" action="<?php echo esc_url( home_url() ); ?>">
<input name="accept" type="checkbox" value="Gdpr" required=""> Accetto il GDPR
<input type="submit" id="accept-button" value="Accetta">
<!--?php wp_nonce_field( 'accept-gdpr', 'accept_gdpr_nonce' ); ?-->
</form>
Non capisco perché il campo nonce sia commentato. Questo è esattamente il codice generato, non ho modificato nulla.

Potresti utilizzare AJAX se non vuoi ricaricare la pagina corrente — ad esempio, al click del pulsante "Accetta", effettua una richiesta AJAX per aggiornare i metadati dell'utente, tutto senza lasciare la pagina corrente.
Tuttavia, la soluzione che propongo non utilizza AJAX; invece, inviamo semplicemente il form (impostando l'attributo action
) alla homepage e poi utilizziamo l'hook template_redirect
per aggiornare i metadati (e reindirizzare alla pagina precedente o di provenienza).
I Passaggi
Modifica il tag
form
in:<form method="post" action="<?php echo esc_url( home_url() ); ?>">
e aggiungi questo campo nonce:
<?php wp_nonce_field( 'accept-gdpr', 'accept_gdpr_nonce' ); ?>
quindi il tuo
form
ora apparirà così:<form method="post" action="<?php echo esc_url( home_url() ); ?>"> <input name="accept" type="checkbox" value="Gdpr" required /> Accetto il GDPR <input type="submit" id="accept-button" value="Accetta" /> <?php wp_nonce_field( 'accept-gdpr', 'accept_gdpr_nonce' ); ?> </form>
Aggiungi questo al file
functions.php
del tema:function accept_gdpr() { // Verifica se l'utente è autenticato. if ( ! is_user_logged_in() ) { return; } // Verifica se abbiamo tutti i dati necessari. if ( empty( $_POST['accept_gdpr_nonce'] ) || empty( $_POST['accept'] ) || 'Gdpr' !== $_POST['accept'] ) { return; } // Verifica il nonce. if ( ! wp_verify_nonce( $_POST['accept_gdpr_nonce'], 'accept-gdpr' ) ) { return; } // Aggiorna il meta. update_user_meta( get_current_user_id(), 'META_KEY', '1' ); // Reindirizza alla pagina precedente. wp_safe_redirect( wp_get_referer() ); exit; } add_action( 'template_redirect', 'accept_gdpr' );
Note:
Il valore
Gdpr
in'Gdpr' !== $_POST['accept']
deve corrispondere a quello nell'<input name="accept" type="checkbox" value="Gdpr" required />
sopra.Assicurati di sostituire
META_KEY
con la chiave meta effettiva.Presumo che l'accettazione del GDPR sia rivolta solo agli utenti autenticati, ecco perché ho utilizzato
is_user_logged_in()
eget_current_user_id()
nel codice/funzione sopra.
AGGIORNAMENTO
wp_safe_redirect()
non ha funzionato per l'OP, quindi ha utilizzato wp_redirect()
.

Dovrai utilizzare wp_localize_script() disponibile anche qui.
In breve: è il modo di WordPress per chiamare PHP
in JS
Quindi potresti fare qualcosa come segue.
PRIMO crea una cartella js
alla radice del tuo tema, allo stesso livello di style.css, se non ne hai già una, poi in questa cartella js
crea un file call-php.js
. Puoi chiamarlo come vuoi, l'importante è che sia un file .js
Nel tuo functions.php dopo la tua funzione function updateHasReadFlag($user)
aggiungi:
/**
* Aggancio del codice JS.
*/
function call_php_in_js() {
wp_enqueue_script( 'call-php-in-js', get_template_directory_uri() . '/js/call-php.js', array( 'jquery' ), filemtime( get_theme_file_path( '/js/call-php.js' ) ), true );
$php_to_js = array(
'my_php_function' => updateHasReadFlag( $user ),
);
wp_localize_script( 'call-php-in-js', 'object_name', $php_to_js );
}
add_action( 'wp_enqueue_scripts', 'call_php_in_js' );
SECONDO, nel file call-php.js
aggiungi:
( function( $ ) {
$( "#accept-button" ).click( function( e ) {
e.preventDefault();
$( "#modal" ).hide();
object_name.my_php_function;
});
} )( jQuery );
Spero che questo risolva il tuo problema.
Non l'ho testato ma dovrebbe funzionare.
Fammi sapere dopo averlo provato.

grazie per la risposta. Lo apprezzo. Ma in qualche modo non funziona. La mia function updateHasReadFlag($user)
non viene chiamata. O forse viene chiamata ma update_user_meta( $user_id, 'META_KEY', true );
in qualche modo non funziona. Puoi darci un'occhiata. Ho anche rimosso <script>
</script>
dal mio codice html.

Te lo chiedo solo per confermare, la mia function updateHasReadFlag($user)
accetta come parametro l'userID o l'oggetto utente, così può aggiornare i metadati di quell'utente specifico. Stiamo passando questo come parametro quando chiamiamo la function updateHasReadFlag($user)
?

potresti per favore sostituire object_name.my_php_function;
con console.log(object_name.my_php_function);
e dirmi cosa vedi nella console. Solo per sapere, il #modal
si nasconde quando clicchi su #accept-button
usando la mia risposta?

il #modal
viene nascosto quando clicchi su #accept-button
usando la mia risposta?

potresti per favore usare BugFu Console Debugger sulla tua funzione function updateHasReadFlag($user)
per vedere l'output esatto, se funziona... Fammi sapere quando lo fai, penso che capirai qual è il problema.

Ho usato il debugger BugFu. my_php_function
è null. Questo è quello che ho trovato.

Penso di aver trovato un problema. Il mio codice php updateHasReadFlag($user)
è nel mio child theme, mentre call-php.js
è nel parent theme. get_template_directory_uri()
sta puntando al parent theme. Quindi ho pensato che forse è per questo che my_php_function
è null. Ma ora sto indirizzando tutto al child theme e my_php_function
è ancora null.

Dovresti fare tutto quanto menzionato sopra SOLAMENTE nel tuo child theme !!! Quindi la tua funzione dovrebbe andare nel functions.php del tuo child theme e tutti i passaggi nella mia risposta dovrebbero essere applicati nel child theme.

Sì, l'ho fatto. Ho sostituito get_template_directory_uri()
con get_stylesheet_directory_uri()
e filemtime( get_theme_file_path( '/js/call-php.js' )
con filemtime( get_stylesheet_directory( '/js/call-php.js' )
. Ma il log risulta ancora null.

Usa il codice come fornito ! filemtime( get_stylesheet_directory( '/js/call-php.js' )
è sbagliato ! Se vuoi modificarlo dovrebbe essere filemtime( get_stylesheet_directory() . '/js/call-php.js' )
. ! Controlla il Code Reference prima di apportare modifiche. Penso che tu stia facendo una chiamata d'azione errata nella tua funzione PHP.
