Hinzufügen eines Divs zum Umschließen des Widget-Inhalts nach dem Widget-Titel


10

Ich versuche, dem Inhalt eines Widgets in meiner dynamischen Seitenleiste ein Div hinzuzufügen.

Hier ist der Registercode;

register_sidebar(array(
        'name' => "Sidebar1",
        'id' => 'home-sidebar-1',
        'before_widget' => '<div class="sidebar-box">',
        'after_widget' => '</div>',
        'before_title' => '<div class="title">',
        'after_title' => '</div>',
    ));

Aber dieser Code verursacht so;

<div class="sidebar-box">
    <div class="title">{WIDGET TITLE}</div>
     {WIDGET CONTENT}
</div>

Folgendes versuche ich zu tun;

<div class="sidebar-box">
    <div class="title">{WIDGET TITLE}</div>
    <div class="content">
           {WIDGET CONTENT}
    </div> 
</div>

Wie geht das?

Antworten:


18

Zusätzlich zu Toschos Antwort benötigen Sie Folgendes für eine robuste Lösung:

// if no title then add widget content wrapper to before widget
add_filter( 'dynamic_sidebar_params', 'check_sidebar_params' );
function check_sidebar_params( $params ) {
    global $wp_registered_widgets;

    $settings_getter = $wp_registered_widgets[ $params[0]['widget_id'] ]['callback'][0];
    $settings = $settings_getter->get_settings();
    $settings = $settings[ $params[1]['number'] ];

    if ( $params[0][ 'after_widget' ] == '</div></div>' && isset( $settings[ 'title' ] ) && empty( $settings[ 'title' ] ) )
        $params[0][ 'before_widget' ] .= '<div class="content">';

    return $params;
}

Aus Toschos Antwort:

register_sidebar(array(
    'name' => "Sidebar1",
    'id' => 'home-sidebar-1',
    'before_widget' => '<div class="sidebar-box">',
    'after_widget' => '</div></div>',
    'before_title' => '<div class="title">',
    'after_title' => '</div><div class="content">',
));

Was dies tut ist:

  • Überprüft die Einstellungen für die registrierte Seitenleiste auf Widgets, die mit 2 schließenden <div>s enden
  • prüft, ob kein Titel vorhanden ist
  • Wenn nicht, wird die before_widgetAusgabe so geändert , dass der Inhalt des öffnenden Widgets angezeigt wird

Mit diesem Ansatz können Sie die Seitenleistenargumente auf andere Weise so ändern, dass sie auf den Einstellungen der Widget-Instanz basieren.


Ich habe ein Problem damit: Einige Widgets (wie z. B. WP-Standard-Widgets) legen einen Standardtitel fest, wenn Sie diesen leer lassen. Ihre Funktion fügt also das div hinzu, da zu diesem Zeitpunkt kein Titel in den Parametern vorhanden ist, das Widget ihn jedoch später hinzufügt und der Code durcheinander gebracht wird. Wissen Sie, wie Sie den Titel "innerhalb" des Widgets suchen können? Vielen Dank
Cmorales

Nicht ohne ein Widget durch Widget-Check oder einen schrecklich komplexen Code hinzuzufügen, um das Widget still zu rendern und es dann nach einem Titel zu analysieren ... Wird eine
Überlegung

Vielleicht würde es helfen , sich an diesen codex.wordpress.org/Function_Reference/the_widget zu binden ? Sie verwenden es (aus anderen Gründen) in diesem Artikel wp.smashingmagazine.com/2012/12/11/…
Cmorales

1
the_widget()wird in der dynamic_sidebar()Funktion nicht verwendet , sondern dient zum Aufrufen eines Widgets mit den von Ihnen angegebenen Optionen. Es ist jedoch ein weiterer Ort zum Filtern, sodass meine Lösung diese Eventualität nicht abdeckt. Prost
Sanchothefat

2

Fügen Sie die zweite divzum Titelparameter hinzu:

register_sidebar(array(
        'name' => "Sidebar1",
        'id' => 'home-sidebar-1',
        'before_widget' => '<div class="sidebar-box">',
        'after_widget' => '</div></div>',
        'before_title' => '<div class="title">',
        'after_title' => '</div><div class="content">',
    ));

Das schlägt fehl, wenn es keinen Widget-Titel gibt - es kann aber gemacht werden
sanchothefat

Ja, es schlägt fehl, wenn es keinen Titel gibt.
MBraiN

Ich habe eine Antwort mit Code hinzugefügt, um das Titelproblem zu beheben. Sollte wahrscheinlich wirklich mit
Toschos

2

Ich mochte die Idee, sowohl @tosco- als auch @sanchothefat-Antworten zu finden - ich habe jedoch mit dieser Kombination zu kämpfen, da empty( $settings[ 'title' ]das Widget selbst möglicherweise einen Standardtitel ausgibt, wenn keiner festgelegt ist. Dieser Titel wird dann in der eingewickelt before_titleund after_titleMarkup und wieder die Seitenumbrüche. Dies ist ohnehin bei einigen Standard-Widgets der Fall.

Es ist einfacher, sich nur an die Standardregistrierungsparameter für Widgets zu halten.

register_sidebar(array(
    'id' => 'sidebar1',
    'name' => __( 'Sidebar 1', 'bonestheme' ),
    'description' => __( 'The first (primary) sidebar.', 'bonestheme' ),
    'before_widget' => '<div class="block">',
    'after_widget' => '</div>',
    'before_title' => '<div class="block-title">',
    'after_title' => '</div>',
));

und fügen Sie dann eine Filteraktion gemäß der Antwort von Marventus hier hinzu.

http://wordpress.org/support/topic/add-html-wrapper-around-widget-content

function widget_content_wrap($content) {
    $content = '<div class="block-content">'.$content.'</div>';
    return $content;
}
add_filter('widget_text', 'widget_content_wrap');

3
und das funktioniert nur für "Text Widgets"
Silver Moon

1

Folgendes tun Sie, um dies zu erreichen:

register_sidebar(array(
        'name' => "Sidebar1",
        'id' => 'home-sidebar-1',
        'before_widget' => '<div class="sidebar-box"><div class="content">',
        'after_widget' => '</div></div>',
        'before_title' => '</div><div class="title">',
        'after_title' => '</div><div class="content">',
    ))

Wenn es keinen Titel gibt, erhalten Sie:

<div class="sidebar-box"><div class="content">
{CONTENT}
</div></div>

Wenn es einen Titel gibt, erhalten Sie:

<div class="sidebar-box"><div class="content">
</div><div class="title">
{TITLE}
<div class="content">
{CONTENT}
</div></div>

Um sicherzustellen, dass das erste leere Inhalts-Div im letzteren Fall nicht angezeigt wird, fügen Sie dies Ihrem CSS hinzu:

.sidebar-box .content:empty {display:none !important;}

0

Nachdem ich mir die vorherigen Antworten angesehen habe, glaube ich, dass ich das Problem behoben habe, das Cmorales mit der Antwort von sanchothefat identifiziert hat. Definieren Sie Ihr Widget wie folgt:

register_sidebar( array(
    'name' => 'Sidebar',
    'id' => 'sidebar',
    'before_widget' => '<div class="panel panel-default %2$s" id="%1$s">',
    'after_widget' => '</div>',
    'before_title' => '',
    'after_title' => ''
) );

Es ist wichtig, dass die Standardeinstellungen before_titleund after_titleentfernt werden. Nach einigem Ausprobieren stellte ich fest, dass der erste Filter, der einen Standardtitel zeigte, war widget_title. Verwenden Sie dann den widget_titleFilter wie folgt:

function widget_title( $title ) {
    if ( $title )
        $title = '<div class="panel-heading"><h3 class="panel-title">' . $title . '</h3></div>';
    $title .= '<div class="panel-body">';
    return $title;
}

Grundsätzlich <div class="panel-heading"><h3 class="panel-title">ist mein before_titleund </h3></div>ist mein after_title. Verwenden Sie dynamic_sidebar_paramszum Schluss ein abschließendes Div für unseren Inhaltsumbruch:

function dynamic_sidebar_params( $params ) {
    $params[0]['after_widget'] = '</div>' . $params[0]['after_widget'];
    return $params;
}

Es ist nicht schön, aber es funktioniert.


War anfangs sehr aufgeregt von diesem Ansatz, aber ich stieß auf ein Problem mit Widgets, die esc_html ($ title) (dh BuddyPress) verwenden. In diesem Fall wird der hinzugefügte HTML-Code maskiert angezeigt und nicht im Frontend gerendert.
Ryan

0

Ich ändere den Code nur leicht, damit ich register_sidebar nicht berühren muss . Registrieren Sie regelmäßig eine Seitenleiste:

register_sidebar(array(
    'name' => "Sidebar1",
    'id' => 'home-sidebar-1',
    'before_widget' => '<div class="sidebar-box">',
    'after_widget' => '</div>',
    'before_title' => '<div class="title">',
    'after_title' => '</div>',
));

Und unten ist modifizierter Code aus Sanchothefats Lösung:

/**
 * If no title given then add widget-content wrapper to before_widget
 * If title given then add content wrapper to before_widget
*/
add_filter('dynamic_sidebar_params', 'check_widget_template');
function check_widget_template($params){
    global $wp_registered_widgets;

    $settings_obj = $wp_registered_widgets[$params[0]['widget_id']]['callback'][0];
    $the_settings = $settings_obj->get_settings();
    $the_settings = $the_settings[$params[1]['number']];

    if (isset($params[0]['id']) && $params[0]['id'] == 'home-sidebar-1') {
        if (!isset($the_settings['title']) && empty($the_settings['title'])) {
            $params[0]['before_widget'] .= '<div class="widget-inner">';
            $params[0]['after_widget']  .= '</div>';
        } else {
            $params[0]['after_widget']  .= '</div>';
            $params[0]['after_title']   .= '<div class="widget-inner">';
        }
    }

    return $params;
}

0

Wie in den Kommentaren erwähnt, fügen einige Kern-Widgets ihren eigenen Titel hinzu, der dann zweimal mit dem Inhalts-Div umbrochen wird. Um sie zu entfernen, können Sie einfach eine leere Zeichenfolge zurückgeben. Der einzige Nachteil ist, dass Sie alle Titel manuell eingeben müssen.

function remove_default_widget_title( $title, $instance = [], $id = '' ) {
    if ( isset($instance['title']) && trim($instance['title']) == '' ) {
        return '';
    }
    return $title;
};
add_filter( 'widget_title', 'remove_default_widget_title', 10, 3 );

Korrigieren Sie mich, wenn ich hier etwas vermisse, aber ich denke, das ist ziemlich solide.

Durch die Nutzung unserer Website bestätigen Sie, dass Sie unsere Cookie-Richtlinie und Datenschutzrichtlinie gelesen und verstanden haben.
Licensed under cc by-sa 3.0 with attribution required.