Kapan menggunakan add_action ('init') vs add_action ('wp_enqueue_scripts')

10

Dalam functions.php tema saya, saya memanggil add_action untuk mendapatkan kontrol di mana jquery dimuat (di footer bersama dengan skrip tema saya yang lain).

Masalah yang saya alami adalah ketika saya menggunakan add_action ('wp_enqueue_scripts'), itu hanya akan muncul jika tidak ada plugin yang dimuat. Namun, metode add_action ('init') berfungsi di semua kasus.

Saya tidak dapat mengingat alasannya, tetapi saya percaya bahwa add_action ('wp_enqueue_scripts') lebih disukai dalam kasus ini. Jika itu benar, bagaimana saya bisa membuatnya berfungsi dalam semua kasus?

Dalam functions.php

//if(!is_admin()){add_action('init', 'my_theme_init');} //THIS WORKS ALL THE TIME
//add_action('wp_enqueue_scripts', 'my_theme_init'); //THIS ONLY WORKS WHEN NO PLUGINS PRESENT

if(!is_admin())
{
    require_once(TEMPLATEPATH . '/functions_public.php');   
}

Di functions_public.php

function my_theme_init()
{

/* PREVENT DUPLICATE COPIES OF JQUERY FROM PLUGINS
**************************************************/
wp_deregister_script('jquery');

/* LOAD THE LOCAL WORDPRESS COPY OF JQUERY AND THEME CUSTOM SCRIPTS IN THE FOOTER
***********************************************/
wp_register_script('jquery', get_bloginfo('template_directory').'/scripts.mythemescripts.js',false,false,true);

wp_enqueue_script('jquery');

}

Metode ke-2, menggunakan add_action ('wp_enqueue_scripts') tampaknya tidak dieksekusi dalam kondisi di mana plugin hadir yang menuliskan dependensi skrip pada tema.

N2Mystic
sumber
5
Tolong jangan mendaftarkan salinan jquery Anda sendiri - gunakan versi yang dikirim dengan WordPress, kalau tidak Anda akan berakhir melanggar plug-in :)
Stephen Harris
Saya setuju, sebenarnya saya menggunakan yang dikirim dengan jQuery. Saya hanya memuatnya ke dalam satu .js (mythemescripts.js) bersama dengan file js lain yang dibutuhkan tema saya, untuk mengurangi permintaan http.
N2Mystic
Di semua browser, setelah skrip diminta dari situs Anda sekali, itu di-cache secara lokal. Anda hanya akan memiliki permintaan HTTP tambahan pada pemuatan halaman pertama. Jika Anda menggabungkan semua skrip menjadi satu, Anda akan dipaksa untuk mengubahnya setiap kali WP merilis pembaruan dengan versi baru jQuery. Ini == mimpi buruk pemeliharaan.
EAMann
2
@ EAMann, ketika tema pertama kali diinstal, dan setiap kali halaman opsi tema saya disimpan setelahnya, saya menulis ulang mythemescripts.js, memuat salinan terbaru dari perpustakaan jquery ke dalamnya. Jika pengguna memperbarui versi WP mereka, rutinitas opsi tema saya memuat jquery yang menyertainya. Selalu up to date.
N2Mystic
Masalah masih terjadi ketika panggilan jquery terkandung dalam tubuh dokumen sebelum catatan kaki. Rupanya jQuery (dokumen). Sudah diaktifkan sebelum skrip .js dimuat ke footer.
N2Mystic

Jawaban:

26

Banyak pengembang plugin tidak melakukan hal-hal dengan cara yang benar. Cara yang benar adalah terhubung agar wp_enqueue_scriptsmenyukai yang Anda coba lakukan.

Namun, inilah urutan kait yang dijalankan dalam permintaan tipikal:

  • muplugins_loaded
  • terdaftar_taxonomy
  • terdaftar_post_type
  • plugins_loaded
  • sanitize_comment_cookies
  • setup_theme
  • load_textdomain
  • after_setup_theme
  • auth_cookie_malformed
  • auth_cookie_valid
  • set_current_user
  • init
  • widgets_init
  • register_sidebar
  • wp_register_sidebar_widget
  • wp_default_scripts
  • wp_default_stypes
  • admin_bar_init
  • add_admin_bar_menus
  • wp_loaded
  • parse_request
  • send_headers
  • parse_query
  • pre_get_posts
  • posts_selection
  • wp
  • template_redirect
  • get_header
  • wp_head
  • skrip wp_enqueue_
  • wp_print_styles
  • wp_print_scripts
  • ... Lebih banyak lagi

Masalahnya adalah, beberapa pengembang pada awalnya diminta untuk menggunakan initenqueue skrip mereka. Kembali sebelum kita memiliki sebuah wp_enqueue_scriptkait, itu adalah cara yang "benar" untuk melakukan sesuatu, dan tutorial yang melanggengkan praktik tersebut masih beredar di Internet merusak pengembang yang baik.

Rekomendasi saya adalah membagi fungsi Anda menjadi dua bagian. Lakukan wp_deregister_script/ wp_register_scriptpada inithook Anda dan gunakan wp_enqueue_scriptshook saat Anda benar-benar meminta jQuery.

Ini akan membuat Anda tetap berada di dunia "melakukannya dengan benar" untuk enqueue skrip Anda, dan akan membantu melindungi Anda dari ratusan pengembang yang masih "salah melakukannya" dengan menukar jQuery untuk versi gabungan Anda sebelum mereka menambahkannya ke antrian .

Anda juga ingin menambahkan initkait Anda dengan prioritas tinggi:

add_action( 'init', 'swap_out_jquery', 1 );
function swap_out_jquery() {
    // ...
}
EAMann
sumber
2
Saya akan merekomendasikan ini, tetapi kemudian saya menyadari bahwa OP sebenarnya membatalkan jQuery, dan kemudian mendaftarkan skrip yang berbeda seluruhnya dan menyebutnya "jquery". Saya tidak berpikir itu adalah praktik yang baik untuk didorong, dan berpikir bahwa rute yang lebih baik adalah dengan dequeue jQuery sepenuhnya , dan kemudian enqueue skrip kustom menggunakan pegangan kustom .
Chip Bennett
Poin yang perlu diperhatikan tentang prioritymenambahkan tindakan. Itu semua tergantung pada bagaimana Anda melihat prioritas. Jika Anda ingin milik Anda menjalankan "pertama", maka angka yang lebih rendah lebih baik - prioritas yang lebih tinggi dalam urutan antrian eksekusi. Tetapi jika Anda ingin efek fungsi Anda diutamakan daripada yang lain, Anda akan ingin menjalankannya nanti - jadi prioritas yang lebih tinggi dengan "efek". Dan dalam hal ini, itu mungkin angka yang lebih tinggi yang Anda inginkan. Meskipun ada sedikit manfaat dalam menukar versi RTM jquery, seperti yang disarankan komentator sebelumnya.
Paul G.
3

Ada beberapa masalah di sini, yang saling terkait.

  1. Kait tindakan yang benar untuk digunakan untuk enqueue skrip adalah wp_enqueue_scripts
  2. Untuk mencetak skrip di dalam footer via wp_enqueue_script(), atur $footerparameter ketrue
  3. add_action( $hook, $callback )Panggilan Anda tidak boleh dibungkus dengan apa pun; biarkan mereka mengeksekusi langsung darifunctions.php
  4. Anda harus memasukkan is_admin()cek bersyarat Anda ke dalam panggilan balik Anda
  5. Anda tidak boleh membatalkan pendaftaran skrip bundel inti dari suatu Tema, karena alasan apa pun. Meskipun tujuan Anda adalah penggabungan skrip, itu adalah wilayah Plugin .
  6. Jika Anda harus membatalkan pendaftaran jquery, maka wp_enqueue_scriptssudah terlambat . Bagi deregister / kode register Anda menjadi callback yang dikaitkan init.
  7. Memanggil beberapa skrip lain "jquery" juga mungkin bukan praktik yang baik. Taruhan Anda yang lebih baik adalah dengan memberikan jQuery , dan kemudian memuat skrip khusus Anda.
  8. Pastikan untuk menempatkan prioritas rendah pada panggilan balik Anda, sehingga Anda mengabaikan Plugin
  9. Gunakan get_template_directory()daripadaTEMPLATEPATH

Menyatukan semuanya:

<?php
function wpse55924_enqueue_scripts() {
    if ( ! is_admin() ) {

        // Dequeue jQuery
        wp_dequeue_script( 'jquery' );

        // Register/enqueue a custom script, that includes jQuery
        wp_register_script( 'mythemescripts', get_template_directory_uri() . '/scripts.mythemescripts.js', false, false,true );
        wp_enqueue_script( 'mythemescripts' ); 
    }
}
add_action( 'wp_enqueue_scripts', 'wpse55924_enqueue_scripts', 99 );

Tetapi sekali lagi: ini benar-benar bukan pendekatan terbaik. Taruhan Anda yang lebih baik adalah dengan hanya menghapus add_action () callback plugin yang membatalkan inti jQuery - atau menggunakan Plugins yang tidak melakukan sesuatu yang begitu ceroboh seperti mengganti jQuery yang dibundel dengan inti.

Chip Bennett
sumber
OP sedang menggabungkan versi jQuery yang didistribusikan WP dengan beberapa skrip lain secara terprogram sehingga hanya satu permintaan HTTP yang dibuat oleh temanya untuk memuat semua file JS. Jadi skrip khusus memang mengandung jQuery dan tidak akan merusak apa pun jika dimuat dengan cara ini. Menimpa pegangan 'jquery' yang terdaftar diperlukan untuk mencegah pemuatan jQuery dua kali - sekali dalam file JS gabungan dan sekali lagi oleh plugin apa pun yang mencoba untuk melakukan enqueue jQuery sendiri.
EAMann
Secara semantik dan praktis _doing_it_wrong()untuk memanggil sesuatu yang bukan hanya jQuery "jQuery". Juga: jQuery sendiri dapat dengan mudah dikosongkan untuk memastikan tidak dimuat dua kali. The wp_dequeue_script()panggilan hanya perlu terjadi dengan prioritas yang cukup untuk memastikan bahwa tidak ada enqueues sesudahnya.
Chip Bennett