การกำหนดเวอร์ชัน @import ของ style.css ของ parent parent


28

บริบท

ฉันสร้างชุดรูปแบบเด็กตาม Twenty Thirteen ซึ่งทำงานได้ค่อนข้างดี หลังจากการปรับปรุงรูปแบบแม่เพื่อรุ่น 1.3 style.cssผมสังเกตเห็นพฤติกรรมแปลกกับสไตล์ที่มีสาเหตุมาจากรูปแบบการปกครองที่เก็บไว้ชั่วคราวของ

นี่คือเนื้อหาของชุดรูปแบบลูกของฉันstyle.css(ละเว้นส่วนหัว)

/* =Imports styles from the parent theme
-------------------------------------------------------------- */
@import url('../twentythirteen/style.css');

ดังนั้นรูปแบบเด็กเป็นไม่ได้ทำอะไรมากไปกว่าการนำเข้าธีมของผู้ปกครองstyle.cssstyle.css

ฉันยังมีไฟล์ css อีกไฟล์ที่มีการปรับแต่งธีมลูกของฉันซึ่งฉันเข้าคิวด้วยเช่นนี้ในfunctions.php:

// Enqueue parent theme's style.css (faster than using @import in our style.css)
$themeVersion = wp_get_theme()->get('Version');

// Enqueue child theme customizations
wp_enqueue_style('child_main', get_stylesheet_directory_uri() . '/css/main.css',
    null, $themeVersion);

นี่ทำให้ฉันมี CSS ที่ดีมาก ๆ เช่นนี้: domain.com/wp-content/themes/toutprettoutbon/css/main.css?ver=1.0.1ทำให้แน่ใจว่าสไตล์ชีทจะถูกบรรจุใหม่เมื่ออัปเดตธีมลูก

ตอนนี้ปัญหา

คำสั่ง@import url('../twentythirteen/style.css');ไม่ขึ้นอยู่กับเวอร์ชันของธีมหลักที่เกี่ยวข้อง ในความเป็นจริงรูปแบบที่ผู้ปกครองสามารถปรับปรุงได้โดยไม่มีการปรับปรุงรูปแบบเด็ก ../twentythirteen/style.cssแต่เบราว์เซอร์จะยังคงใช้รุ่นเก่าที่เก็บไว้ชั่วคราว

รหัสที่เกี่ยวข้องในยี่สิบสามที่ enqueues style.css:

function twentythirteen_scripts_styles() {
    // ...

    // Add Genericons font, used in the main stylesheet.
    wp_enqueue_style( 'genericons', get_template_directory_uri() . '/genericons/genericons.css', array(), '3.03' );

    // Loads our main stylesheet.
    wp_enqueue_style( 'twentythirteen-style', get_stylesheet_uri(), array(), '2013-07-18' );
    // Note usage of get_stylesheet_uri() which actually enqueues child-theme/style.css

    // Loads the Internet Explorer specific stylesheet.
    wp_enqueue_style( 'twentythirteen-ie', get_template_directory_uri() . '/css/ie.css', array( 'twentythirteen-style' ), '2013-07-18' );
}
add_action( 'wp_enqueue_scripts', 'twentythirteen_scripts_styles' );

ฉันสามารถคิดถึงวิธีแก้ปัญหานี้สองสามวิธี แต่ไม่มีใครพอใจ:

  1. อัปเดตชุดรูปแบบลูกของฉันทุกครั้งที่มีการปรับปรุงชุดรูปแบบหลักเพื่อเปลี่ยนสายรุ่นในstyle.css(เช่น@import url('../twentythirteen/style.css?ver=NEW_VERSION');) สิ่งนี้สร้างลิงก์ที่ไม่จำเป็นและน่ารำคาญระหว่างเวอร์ชันของธีมหลักกับลูก

  2. ในเด็กของฉันfunctions.php, 1) wp_dequeue_styleธีมเด็กรวมของstyle.cssและ 2) ปกครองธีมเป็นโดยตรงกับสตริงรุ่น สิ่งนี้จะทำให้ลำดับของ CSS ที่อยู่ในคิวในธีมหลักเสียหายwp_enqueue_stylestyle.css

  3. ใช้style_loader_tagตัวกรองเพื่อแก้ไข<link>แท็กcss ที่สร้างขึ้นสำหรับstyle.cssและปรับเปลี่ยนพา ธ เพื่อชี้ไปยังสตริงหลักของชุดรูปแบบParentโดยตรง style.cssดูเหมือนจะค่อนข้างคลุมเครือสำหรับความต้องการทั่วไป (การป้องกันแคช)

  4. การถ่ายโอนข้อมูลของธีมปกครองในรูปของบุตรหลานstyle.css style.cssเหมือนกับ (1) จริง ๆ แต่เร็วกว่าเล็กน้อย

  5. ทำให้รูปแบบของเด็กstyle.cssเป็น symlink style.cssไปของธีมพ่อแม่ ดูเหมือนว่าจะค่อนข้างแฮ็ก ...

ฉันพลาดอะไรไปหรือเปล่า ข้อเสนอแนะใด ๆ

แก้ไข

เพิ่มgenericicons.cssและie.cssสไตล์ชีทในชุดรูปแบบหลักเพื่อชี้แจงว่าทำไมฉันไม่สามารถเปลี่ยน@importคำสั่ง css เป็นwp_enqueue_styleในธีมลูกของฉัน ขณะนี้มี@importคำสั่งในชุดรูปแบบลูกของstyle.cssฉันฉันมีคำสั่งนี้ในหน้าสร้าง:

  1. ยี่สิบสาม / genericons / genericons.css -> จัดทำโดยธีมผู้ปกครอง
  2. child-theme / style.css -> จัดทำโดยชุดรูปแบบผู้ปกครอง @imports ยี่สิบสาม / style.css
  3. ยี่สิบสาม / css / ie.css -> จัดทำโดยชุดรูปแบบผู้ปกครอง
  4. child-theme / css / main.css -> จัดทำโดยธีมลูก

ถ้าฉันเข้าสุหนัตของผู้ปกครองstyle.cssเป็นการพึ่งพาของmain.cssสิ่งนี้จะกลายเป็น:

  1. ยี่สิบสาม / genericons / genericons.css -> จัดทำโดยธีมผู้ปกครอง
  2. child-theme / style.css -> ว่างจัดทำโดยธีมผู้ปกครอง
  3. ยี่สิบสาม / css / ie.css -> จัดทำโดยชุดรูปแบบผู้ปกครอง
  4. ยี่สิบสาม / style.css -> จัดทำโดยชุดรูปแบบของเด็กที่ขึ้นอยู่กับ main.css
  5. child-theme / css / main.css -> จัดทำโดยธีมลูก

โปรดทราบว่า ie.css style.cssจะรวมอยู่ในขณะนี้ก่อนของธีมปกครอง ฉันไม่ต้องการเปลี่ยนลำดับการจัดคิวของไฟล์ css ของธีมพาเรนต์เพราะฉันไม่สามารถสันนิษฐานได้ว่าสิ่งนี้จะไม่ทำให้เกิดปัญหากับลำดับความสำคัญของกฎ css


5
ห้ามใช้@importให้ตั้งค่าสไตล์ชีทของธีมหลักเป็นการอ้างอิงสไตล์ชีทของคุณเองแทน
fuxia

ฉันรู้ว่ามันไม่ใช่วิธีที่ดีที่สุด แต่แนะนำที่นี่: codex.wordpress.org/Child_Themes
bernie

นอกจากนี้การทำสิ่งที่คุณแนะนำไม่ได้ช่วยแก้ไขปัญหาของฉัน ชุดรูปแบบของผู้ปกครองstyle.cssจะไม่รวมอยู่ในสถานที่เดียวกันกับที่เป็นอยู่ในขณะนี้ พาเรนต์มีไฟล์ css อื่น ๆ ซึ่งต้องอยู่ระหว่างstyle.cssCSS และธีมลูกของฉัน
bernie

3
โปรดละเว้น codex โดยสมบูรณ์ มันเต็มไปด้วยข้อมูลที่ผิด การใช้พารามิเตอร์การพึ่งพาจะรวมถึงสไตล์ชีทในลำดับที่ถูกต้อง
fuxia

โปรดดูการแก้ไขของฉัน
bernie

คำตอบ:


19

คุณไม่จำเป็นต้องใช้ @import เป็นการดีที่สุดที่จะไม่จริง การใช้วิธีการจัดคิวน่าจะดีกว่าทั่ว

นี่คือส่วนที่เกี่ยวข้องของรหัสที่สิบสาม:

function twentythirteen_scripts_styles() {
...
    // Loads our main stylesheet.
    wp_enqueue_style( 'twentythirteen-style', get_stylesheet_uri(), array(), '2013-07-18' );
...
}
add_action( 'wp_enqueue_scripts', 'twentythirteen_scripts_styles' );

นี่คือสิ่งที่คุณทำในรหัสของคุณ:

function child_scripts_styles() {
    wp_enqueue_style( 'child-style', get_stylesheet_directory_uri().'/css/main.css', array('twentythirteen-style'), 'YOUR_THEME_VERSION' );
}
add_action( 'wp_enqueue_scripts', 'child_scripts_styles' );

หาก main.css ของคุณต้องมาตาม style.css ของผู้ปกครองคุณเพียง แต่ทำให้มันขึ้นอยู่กับสิ่งนั้น

ตอนนี้ถ้าคุณมี B.css อยู่ในเด็กด้วยคุณต้องตั้งค่าการอ้างอิงตาม:

function child_scripts_styles() {
    wp_enqueue_style( 'child-B-style', get_stylesheet_directory_uri().'/B.css', array('twentythirteen-style'), 'YOUR_THEME_VERSION' );
    wp_enqueue_style( 'child-style', get_stylesheet_directory_uri().'/css/main.css', array('child-B-style'), 'YOUR_THEME_VERSION' );
}
add_action( 'wp_enqueue_scripts', 'child_scripts_styles' );

ทำให้การอ้างอิงที่คุณกำหนดสำหรับแต่ละรายการสะท้อนความเป็นจริงของการอ้างอิงเหล่านั้นจริงๆ ถ้า main.css ต้องมาหลังจาก B.css แล้วมันขึ้นอยู่กับมัน ถ้า B.css ต้องมาหลัง style.css ของผู้ปกครอง B จะขึ้นอยู่กับสิ่งนั้น ระบบจัดคิวจะจัดเรียงให้คุณ

และถ้าคุณไม่ได้ใช้สไตล์ของเด็กจริง ๆคุณจะได้ไม่ต้องเข้าคิวอีกเลย เป็นเพียงตัวยึดตำแหน่งที่จะเก็บข้อมูลส่วนหัวของธีมของคุณ ไม่ได้ใช้มัน? อย่าโหลดมัน

นอกจากนี้คุณกำลังทำอะไรที่ขึ้นอยู่กับการสั่งซื้อที่นี่? CSS ไม่สนใจสั่งโหลดในสถานการณ์ส่วนใหญ่ CSS นั้นขึ้นอยู่กับความจำเพาะของตัวเลือก หากคุณต้องการแทนที่บางสิ่งคุณต้องเลือกให้เฉพาะเจาะจงมากขึ้น สามารถมาก่อนหรือสุดท้ายหรืออะไรก็ได้ในระหว่างนั้นตัวเลือกที่เฉพาะเจาะจงมากขึ้นจะเป็นผู้ชนะเสมอ

แก้ไข

อ่านความคิดเห็นของคุณและดูรหัสให้ละเอียดยิ่งขึ้นฉันเห็นว่าความผิดพลาดอยู่ตรงไหน รหัสที่สิบสามคือ enqueueing "get_stylesheet_uri ()" ซึ่งในกรณีที่ชุดรูปแบบเด็กจะเป็นไฟล์ style.css ของชุดรูปแบบลูกของคุณไม่ใช่ไฟล์ของผู้ปกครอง นั่นเป็นสาเหตุที่ @import ทำงานและรักษาลำดับเดิมไว้ (ซึ่งอีกครั้งไม่สำคัญเท่าที่คุณคิด)

ในกรณีนี้หากคุณไม่ต้องการใช้การนำเข้าฉันขอแนะนำให้จัดคิวของ style.css ของผู้ปกครองโดยตรง ชอบมาก

function child_scripts_styles() {
    wp_enqueue_style( 'parent-style', get_template_directory_uri().'/style.css', array() );
}
add_action( 'wp_enqueue_scripts', 'child_scripts_styles' );

โค้ดในฟังก์ชั่นชุดรูปแบบของเด็ก PHP ทำงานก่อนดังนั้น wp_enqueue_scripts ของคุณเองจะทำงานก่อนและสิ่งนี้จะทำให้ผู้เข้าชม style.css ของชุดรูปแบบผู้ปกครองซึ่งชุดรูปแบบผู้ปกครองไม่ได้ทำเอง โดยไม่ทำให้มันขึ้นอยู่กับอะไรเช่นเดียวกับผู้ปกครองแล้วมันก็จะได้รับการใส่อย่างถูกต้อง โปรดทราบว่าลำดับของไฟล์นี้และ genericons.css นั้นไม่สำคัญเพราะต้นฉบับ "ยี่สิบสามสไตล์" ไม่มี genericons.css เป็นการอ้างอิงที่ขึ้นทะเบียน

สไตล์ลูกของคุณเองจะโหลดขึ้นมาและตรงไปตรงมานี่คือที่ที่คุณควรใส่การเปลี่ยนแปลงของธีมลูกไม่เข้ากับ main.css แยกต่างหาก ไม่มีสิ่งใดที่จะป้องกันไม่ให้คุณทำการเปลี่ยนแปลง แต่ไม่มีเหตุผลที่แท้จริงที่จะมีไฟล์ css เพิ่มเติม


ฉันเห็นด้วยอย่างยิ่งว่า@importไม่ใช่วิธีที่ดีที่สุดที่จะไป โปรดดูส่วน "แก้ไข" ของฉันสำหรับข้อมูลที่แม่นยำยิ่งขึ้น ฉันไม่มีความต้องการพิเศษเกี่ยวกับการสั่งซื้อ css ฉันไม่ต้องการแก้ไขการเรียงลำดับภายในของไฟล์ css ของธีมพาเรนต์ซึ่งอาจทำให้เกิดปัญหากับลำดับความสำคัญของกฎ css
bernie

ในการชี้แจง B.css (ตอนนี้เปลี่ยนเป็น ie.css ที่เป็นปัญหา) ไม่ใช่ส่วนหนึ่งของชุดรูปแบบลูกของฉัน แต่จริง ๆ แล้วเป็นส่วนหนึ่งของชุดรูปแบบหลัก
bernie

2
หากคุณต้องการให้สไตล์ของคุณตามหลังสไตล์ ie.css แล้วทำให้สไตล์ของคุณขึ้นอยู่กับสไตล์นั้น ชื่อของมันคือ "ยี่สิบสาม-ie" การจัดการคำสั่งซื้อทั้งหมดขึ้นอยู่กับสิ่งที่คุณประกาศ แต่อีกครั้งกับ CSS ลำดับที่แท้จริงของพวกเขาในเอกสารมักจะไม่สำคัญดังนั้นฉันไม่แน่ใจว่าทำไมคุณถึงสนใจมากเกินไป
อ็อตโต

2
แก้ไขคำตอบของฉันเพื่อรวมวิธีการอื่น
อ็อตโต

ใช่ฉันเดาฉันได้ดำเนินการไปด้วย "ต้องการ" เพื่อให้การสั่งซื้อ CSS หากคำสั่งนั้นสำคัญสำหรับธีมหลักควรระบุไว้ในการอ้างอิง
bernie

9

คำตอบก่อนหน้าของฉันซับซ้อนเกินไปและอาจไม่เคารพห่วงโซ่การพึ่งพาของธีมหลัก (ดูหมายเหตุในคำตอบอื่น ๆ )

นี่เป็นอีกวิธีที่ง่ายกว่าที่ควรจะทำได้ดีกว่า:

function use_parent_theme_stylesheet() {
    // Use the parent theme's stylesheet
    return get_template_directory_uri() . '/style.css';
}

function my_theme_styles() {
    $themeVersion = wp_get_theme()->get('Version');

    // Enqueue our style.css with our own version
    wp_enqueue_style('child-theme-style', get_stylesheet_directory_uri() . '/style.css',
        array(), $themeVersion);
}

// Filter get_stylesheet_uri() to return the parent theme's stylesheet 
add_filter('stylesheet_uri', 'use_parent_theme_stylesheet');

// Enqueue this theme's scripts and styles (after parent theme)
add_action('wp_enqueue_scripts', 'my_theme_styles', 20);

แนวคิดคือเพียงกรองการเรียกไปยังget_stylesheet_uri()ธีมหลักเพื่อส่งคืนสไตล์ชีทของตัวเองแทนที่จะเป็นธีมย่อย สไตล์ธีมของเด็กเป็น enqueued my_theme_stylesแล้วต่อไปในการดำเนินการเบ็ด


เพียงเพื่อบันทึก: 1) รหัสของคุณจะสร้าง html เหมือนกับการใช้@importเวอร์ชันเก่าโดยไม่มีผลกระทบต่อประสิทธิภาพเลยจะมี style.css แยกกันสองคำขอการร้องขอไปยังเซิร์ฟเวอร์ 2) คำตอบนี้จะลดการพึ่งพาทั้งหมดทั้งหมด ด้วยกัน ... 3) คุณสามารถตรวจสอบget_template_directory_uriและget_template_stylesheet_uriกำลังทำอยู่ที่นี่: core.trac.wordpress.org/browser/tags/4.8/src/wp-includes/...อีกครั้งจำเป็นสำหรับส่วนมากของรหัสที่ไม่มี
bg17aw

1
@ bg17aw การใช้wp_enqueue_styleเพิ่มสตริงข้อความค้นหาที่ป้องกันการแคชไปยัง URL ที่สร้าง (เช่น?ver=2013-07-18) ตามเวอร์ชันของธีมโดยอัตโนมัติ สิ่งนี้ไม่ได้ทำโดย@importคำสั่ง
bernie

2

การเตือน

วิธีนี้ไม่เคารพการอ้างอิงของธีมหลัก ! การเปลี่ยนชื่อหมายเลขอ้างอิงของชุดรูปแบบหลักมีผลกระทบต่อสายโซ่ของการพึ่งพาที่ตั้งค่าไว้ในชุดรูปแบบหลัก ดูของฉันง่ายมากคำตอบอื่น

คำตอบดั้งเดิม

แม้ว่าคำตอบของอ็อตโตนั้นค่อนข้างดี แต่ฉันก็ลงเอยด้วยฟังก์ชั่นชุดรูปแบบลูกของฉันด้วย

function my_theme_styles() {
    global $wp_styles;
    $parentOriginalHandle = 'twentythirteen-style';
    $parentNewHandle = 'parent-style';

    // Deregister our style.css which was enqueued by the parent theme; we want
    // to control the versioning ourself.
    $parentStyleVersion = $wp_styles->registered[$parentOriginalHandle]->ver;
    $parentDeps = $wp_styles->registered[$parentOriginalHandle]->deps;
    wp_deregister_style($parentOriginalHandle);

    // Enqueue the parent theme's style.css with whatever version it used instead
    // of @import-ing it in the child theme's style.css
    wp_register_style($parentNewHandle, get_template_directory_uri() . '/style.css',
        $parentDeps, $parentStyleVersion);

    // Enqueue our style.css with our own version
    $themeVersion = wp_get_theme()->get('Version');
    wp_enqueue_style($parentOriginalHandle, get_stylesheet_directory_uri() . '/style.css',
        [$parentNewHandle], $themeVersion);
}

// Run this action action the parent theme has enqueued its styles.
add_action('wp_enqueue_scripts', 'my_theme_styles', 20);

มันจะเก็บธีมแม่สั่งซื้อและหมายเลขรุ่นขณะที่การควบคุมรุ่นของชุดรูปแบบเด็กstyle.cssstyle.css


5
มันรบกวนความคิดของฉันว่าซอฟต์แวร์บล็อกยอดนิยมต้องใช้โค้ดมากกว่า 20 บรรทัดเพื่อปรับแต่ง CSS ของธีมที่มีอยู่ ฉันเดาว่านั่นเป็นงานความปลอดภัย
Carl G

ฉันต้องเปลี่ยน[$parentNewHandle]เป็นarray($parentNewHandle)
Carl G

@CarlG: แนะนำให้ใช้ไวยากรณ์อาร์เรย์ (วงเล็บเหลี่ยม) ใน PHP 5.4
bernie

สำหรับผู้ที่สนใจมากขึ้น: โปรดดูคำตอบอื่น ๆ ของฉันที่ช่วยแก้ปัญหาด้วยอันนี้
bernie

มันเป็นความเข้าใจผิดอย่างใหญ่หลวงไม่จำเป็นต้องมีสิ่งใดเลย ที่จริงแล้ว@importวิธีการเดิมนั้นใช้งานได้ดีด้วยโปรดเปรียบเทียบทั้งสองวิธี สำหรับการขึ้นต่อกันของธีมลูกบนธีมพาเรนต์ไม่จำเป็นต้องมีธีมนั้น เด็กstyle.cssจะโหลดหลังจากผู้ปกครองเสมออย่างน้อยจากการทดสอบของฉัน รักที่จะพิสูจน์ว่าผิด
bg17aw
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.