Cum să adaugi atributul defer="defer" în scripturile JavaScript ale plugin-urilor?

9 ian. 2012, 09:59:34
Vizualizări: 40.9K
Voturi: 31

Nu am putut adăuga atributul defer în scripturile JavaScript ale plugin-ului. Testul Google PageSpeed îmi sugerează să adaug atributul defer în scripturile Contact Form 7.

Iată cum include Contact Form 7 JavaScript-ul în header.

add_action( 'wp_enqueue_scripts', 'wpcf7_enqueue_scripts' );

function wpcf7_enqueue_scripts() {
    // jquery.form.js inițial inclus cu WordPress este învechit și depreciat
    // așa că trebuie să-l deînregistrăm și să re-înregistrăm ultima versiune
    wp_deregister_script( 'jquery-form' );
    wp_register_script( 'jquery-form', wpcf7_plugin_url( 'jquery.form.js' ),
        array( 'jquery' ), '2.52', true );

    $in_footer = true;
    if ( 'header' === WPCF7_LOAD_JS )
        $in_footer = false;

    wp_enqueue_script( 'contact-form-7', wpcf7_plugin_url( 'scripts.js' ),
        array( 'jquery', 'jquery-form' ), WPCF7_VERSION, $in_footer );

    do_action( 'wpcf7_enqueue_scripts' );
}

Acum, cum pot adăuga atributul defer="defer" în codul de mai sus?

2
Comentarii

Bilet relevant: http://core.trac.wordpress.org/ticket/12009

scribu scribu
9 ian. 2012 19:15:15

Întrebare bună @Viruthagiri.

Ramkumar M Ramkumar M
2 feb. 2012 15:30:47
Toate răspunsurile la întrebare 2
6
63

Începând cu WordPress 4.1 există un filtru: script_loader_tag. Îl puteți utiliza pentru a găsi scriptul corect:

add_filter( 'script_loader_tag', function ( $tag, $handle ) {

    if ( 'contact-form-7' !== $handle )
        return $tag;

    return str_replace( ' src', ' defer="defer" src', $tag );
}, 10, 2 );

Răspuns vechi

Nu există un filtru dedicat disponibil... cel puțin nu văd unul. Dar...

  • wp_print_scripts() apelează WP_Scripts->do_items()
  • care apelează WP_Scripts->do_item()
  • care folosește esc_url()
  • care are un filtru: 'clean_url'.

Și iată cum:

function add_defer_to_cf7( $url )
{
    if ( FALSE === strpos( $url, 'contact-form-7' )
      or FALSE === strpos( $url, '.js' )
    )
    { // nu este fișierul nostru
        return $url;
    }
    // Trebuie să fie ', nu "!
    return "$url' defer='defer";
}
add_filter( 'clean_url', 'add_defer_to_cf7', 11, 1 );

Atenție: netestat, doar o idee. :)

Actualizare

Am scris și testat un plugin cu acest cod.

9 ian. 2012 13:56:46
Comentarii

Este perfect și pentru utilizarea cu data-main în requirejs

Nicola Peluchetti Nicola Peluchetti
6 iun. 2012 18:07:47

Este un hack frumos și atât de simplu. Cred că ar fi bun și pentru adăugarea charset='utf-8' când este necesar!

webaware webaware
16 ian. 2013 10:16:09

Excelent, dar de ce: Trebuie să fie ', nu "! ?

henrywright henrywright
1 feb. 2014 04:09:52

@henrywright WordPress adaugă ' pe ambele părți ale șirului returnat, un " ar rezulta în HTML invalid.

fuxia fuxia
1 feb. 2014 12:54:48

Probabil o idee bună, în cazul în care cineva dorește să adapteze acest lucru pentru a funcționa cu alte scripturi, ar fi să vă asigurați că validați utilizarea doar pe partea de front-end, eventual folosind if( ! is_admin() ){}. Pluginuri populare cum ar fi ACF v-ar putea crea probleme.

crissoca crissoca
28 apr. 2015 05:09:37

@crissoca, mulțumesc, amice. Uitasem de asta până când TinyMCE nu a făcut ce trebuia (lipsesc qtags și altele :-D ). Deci da, folosiți asta DOAR pe front-end!

Charles Charles
12 iun. 2015 15:46:31
Arată celelalte 1 comentarii
0

Răspunsul acceptat este corect, dar am vrut să fac unele îmbunătățiri/actualizări pentru un caz mai general, pentru oricine, inclusiv pentru mine în viitor, care ar putea da peste acest lucru în timp ce caută un răspuns. Pentru cazurile generale care nu se referă la acest plugin contact-form-7, unde adăugați atributul defer la toate scripturile, probabil doriți să-l excludeți de pe paginile de administrare, deoarece acestea se bazează pe faptul că scripturile sunt executate într-o anumită ordine. De asemenea, pentru paginile non-administrative, doriți să excludeți jQuery, deoarece jQuery ar trebui încărcat în head înainte de orice altceva. În plus, în loc să manipulați șirul de tag-uri, o abordare mai bună ar fi să-l încărcați într-un obiect DOMDocument, să-l manipulați și apoi să-l convertiți înapoi într-un șir. De asemenea, versiunile mai noi de PHP au verificare de tip, așa că ar trebui să adăugați tipurile de parametri și return în apelul funcției.

<?php

    add_filter('script_loader_tag', function (string $tag, string $handle, string $src):string {
        if (is_admin()) {
            return $tag;
        }
        if (in_array($handle, array('jquery-core', 'jquery-migrate'))) {
            return $tag;
        }
        $dom = new \DomDocument();
        $dom->loadHTML($tag, LIBXML_HTML_NOIMPLIED | LIBXML_HTML_NODEFDTD);
        $dom->getElementsByTagName('script')[0]->setAttribute("defer", "defer");
        $tag = $dom->saveHTML();
        return $tag;
    }, 10, 3);

?>
6 iun. 2023 01:05:52