Files
Skrift-Auto-Article/wordpress/skrift-ratgeber-felder.php

594 lines
22 KiB
PHP

<?php
/**
* Plugin Name: Skrift Ratgeber Felder
* Description: Meta-Felder fuer Ratgeberartikel (kurzantwort, faq, cta_ziel, stand_datum) mit Eingabebox im Editor, Shortcodes und Elementor-Widgets, die das FAQ-Feld automatisch als Umschalter ausgeben.
* Version: 1.1.0
* Author: Lucas Orth
*
* Ablage: wp-content/mu-plugins/skrift-ratgeber-felder.php
*/
if ( ! defined( 'ABSPATH' ) ) {
exit;
}
/* ------------------------------------------------------------------------
* 1. Meta-Felder registrieren (REST-schreibbar fuer n8n)
* --------------------------------------------------------------------- */
function skrift_ratgeber_meta_auth( $allowed, $meta_key, $post_id ) {
return current_user_can( 'edit_post', $post_id );
}
add_action( 'init', function () {
register_post_meta( 'post', 'kurzantwort', array(
'type' => 'string',
'single' => true,
'show_in_rest' => true,
'sanitize_callback' => 'wp_kses_post',
'auth_callback' => 'skrift_ratgeber_meta_auth',
) );
register_post_meta( 'post', 'cta_ziel', array(
'type' => 'string',
'single' => true,
'show_in_rest' => true,
'sanitize_callback' => 'esc_url_raw',
'auth_callback' => 'skrift_ratgeber_meta_auth',
) );
register_post_meta( 'post', 'stand_datum', array(
'type' => 'string',
'single' => true,
'show_in_rest' => true,
'sanitize_callback' => 'skrift_ratgeber_datum',
'auth_callback' => 'skrift_ratgeber_meta_auth',
) );
register_post_meta( 'post', 'faq', array(
'type' => 'array',
'single' => true,
'default' => array(),
'show_in_rest' => array(
'schema' => array(
'type' => 'array',
'items' => array(
'type' => 'object',
'properties' => array(
'frage' => array( 'type' => 'string' ),
'antwort' => array( 'type' => 'string' ),
),
'additionalProperties' => false,
),
),
),
'auth_callback' => 'skrift_ratgeber_meta_auth',
) );
} );
function skrift_ratgeber_datum( $wert ) {
return preg_match( '/^\d{4}-\d{2}-\d{2}$/', (string) $wert ) ? $wert : '';
}
/* ------------------------------------------------------------------------
* 2. Eingabebox im Beitragseditor (Gutenberg und klassisch)
* --------------------------------------------------------------------- */
add_action( 'add_meta_boxes_post', function () {
add_meta_box(
'skrift_ratgeber',
'Ratgeber: Kurzantwort, CTA und FAQ',
'skrift_ratgeber_metabox',
'post',
'normal',
'high'
);
} );
function skrift_ratgeber_metabox( $post ) {
wp_nonce_field( 'skrift_ratgeber_speichern', 'skrift_ratgeber_nonce' );
$kurz = (string) get_post_meta( $post->ID, 'kurzantwort', true );
$cta = (string) get_post_meta( $post->ID, 'cta_ziel', true );
$stand = (string) get_post_meta( $post->ID, 'stand_datum', true );
$faq = get_post_meta( $post->ID, 'faq', true );
if ( ! is_array( $faq ) ) {
$faq = array();
}
?>
<style>
.skrift-mb p { margin: 0 0 14px; }
.skrift-mb label { display: block; font-weight: 600; margin-bottom: 4px; }
.skrift-mb .skrift-mb__zeile { display: flex; gap: 16px; }
.skrift-mb .skrift-mb__zeile > p { flex: 1; }
.skrift-faq-zeile { border: 1px solid #dcdcde; border-radius: 4px; padding: 10px 12px; margin-bottom: 10px; background: #fafafa; }
.skrift-faq-zeile input, .skrift-faq-zeile textarea { width: 100%; }
.skrift-faq-zeile textarea { margin-top: 6px; }
.skrift-faq-zeile .skrift-faq-weg { margin-top: 6px; color: #b32d2e; }
.skrift-mb .description { color: #646970; font-size: 12px; }
</style>
<div class="skrift-mb">
<p>
<label for="skrift_kurzantwort">Kurzantwort</label>
<textarea id="skrift_kurzantwort" name="skrift_kurzantwort" rows="3" class="widefat"><?php echo esc_textarea( $kurz ); ?></textarea>
<span class="description">Zwei bis drei Saetze, Preise nur per [skrift_preis key="..."].</span>
</p>
<div class="skrift-mb__zeile">
<p>
<label for="skrift_cta_ziel">CTA-Ziel</label>
<input type="url" id="skrift_cta_ziel" name="skrift_cta_ziel" class="widefat" value="<?php echo esc_attr( $cta ); ?>">
</p>
<p>
<label for="skrift_stand_datum">Stand</label>
<input type="date" id="skrift_stand_datum" name="skrift_stand_datum" value="<?php echo esc_attr( $stand ); ?>">
</p>
</div>
<label>FAQ</label>
<div id="skrift-faq-liste">
<?php foreach ( $faq as $i => $e ) : ?>
<?php skrift_ratgeber_faq_zeile( (string) $i, $e['frage'] ?? '', $e['antwort'] ?? '' ); ?>
<?php endforeach; ?>
</div>
<template id="skrift-faq-vorlage">
<?php skrift_ratgeber_faq_zeile( '__i__', '', '' ); ?>
</template>
<button type="button" class="button" id="skrift-faq-neu">Frage hinzufuegen</button>
<span class="description">Leere Fragen werden beim Speichern entfernt.</span>
</div>
<script>
( function () {
var liste = document.getElementById( 'skrift-faq-liste' );
var vorlage = document.getElementById( 'skrift-faq-vorlage' );
document.getElementById( 'skrift-faq-neu' ).addEventListener( 'click', function () {
var html = vorlage.innerHTML.replace( /__i__/g, 'n' + Date.now() );
liste.insertAdjacentHTML( 'beforeend', html );
} );
liste.addEventListener( 'click', function ( ev ) {
if ( ev.target.classList.contains( 'skrift-faq-weg' ) ) {
ev.preventDefault();
ev.target.closest( '.skrift-faq-zeile' ).remove();
}
} );
} )();
</script>
<?php
}
function skrift_ratgeber_faq_zeile( $i, $frage, $antwort ) {
?>
<div class="skrift-faq-zeile">
<input type="text" name="skrift_faq[<?php echo esc_attr( $i ); ?>][frage]" placeholder="Frage" value="<?php echo esc_attr( $frage ); ?>">
<textarea name="skrift_faq[<?php echo esc_attr( $i ); ?>][antwort]" rows="3" placeholder="Antwort"><?php echo esc_textarea( $antwort ); ?></textarea>
<a href="#" class="skrift-faq-weg">Frage entfernen</a>
</div>
<?php
}
add_action( 'save_post_post', function ( $post_id ) {
// Nur wenn das Formular der Eingabebox mitgeschickt wurde. REST-Aufrufe aus n8n
// enthalten keine Nonce und bleiben damit unberuehrt.
if ( ! isset( $_POST['skrift_ratgeber_nonce'] ) ) {
return;
}
if ( ! wp_verify_nonce( sanitize_text_field( wp_unslash( $_POST['skrift_ratgeber_nonce'] ) ), 'skrift_ratgeber_speichern' ) ) {
return;
}
if ( defined( 'DOING_AUTOSAVE' ) && DOING_AUTOSAVE ) {
return;
}
if ( wp_is_post_revision( $post_id ) || ! current_user_can( 'edit_post', $post_id ) ) {
return;
}
update_post_meta( $post_id, 'kurzantwort', wp_kses_post( wp_unslash( $_POST['skrift_kurzantwort'] ?? '' ) ) );
update_post_meta( $post_id, 'cta_ziel', esc_url_raw( wp_unslash( $_POST['skrift_cta_ziel'] ?? '' ) ) );
update_post_meta( $post_id, 'stand_datum', skrift_ratgeber_datum( sanitize_text_field( wp_unslash( $_POST['skrift_stand_datum'] ?? '' ) ) ) );
$faq = array();
$roh = isset( $_POST['skrift_faq'] ) && is_array( $_POST['skrift_faq'] ) ? wp_unslash( $_POST['skrift_faq'] ) : array();
foreach ( $roh as $e ) {
$frage = sanitize_text_field( $e['frage'] ?? '' );
if ( '' === $frage ) {
continue;
}
$faq[] = array(
'frage' => $frage,
'antwort' => wp_kses_post( $e['antwort'] ?? '' ),
);
}
update_post_meta( $post_id, 'faq', $faq );
} );
/* ------------------------------------------------------------------------
* 3. Ausgabe: gemeinsamer Renderer fuer Shortcode und Elementor-Widget
* --------------------------------------------------------------------- */
function skrift_faq_eintraege( $post_id = 0 ) {
$post_id = $post_id ? (int) $post_id : get_the_ID();
$faq = get_post_meta( $post_id, 'faq', true );
if ( ! is_array( $faq ) ) {
return array();
}
$raus = array();
foreach ( $faq as $e ) {
if ( ! empty( $e['frage'] ) ) {
$raus[] = $e;
}
}
return $raus;
}
function skrift_faq_basis_css() {
static $fertig = false;
if ( $fertig ) {
return '';
}
$fertig = true;
return '<style>'
. '.skrift-faq__eintrag{border-bottom:1px solid rgba(0,0,0,.12)}'
. '.skrift-faq__frage{cursor:pointer;list-style:none;display:flex;justify-content:space-between;align-items:center;gap:16px;padding:16px 0;font-weight:600}'
. '.skrift-faq__frage::-webkit-details-marker{display:none}'
. '.skrift-faq__frage::after{content:"";flex:0 0 auto;width:9px;height:9px;border-right:2px solid currentColor;border-bottom:2px solid currentColor;transform:rotate(45deg);transition:transform .2s}'
. '.skrift-faq__eintrag[open] .skrift-faq__frage::after{transform:rotate(-135deg)}'
. '.skrift-faq__antwort{padding:0 0 16px}'
. '.skrift-faq__antwort>*:last-child{margin-bottom:0}'
. '</style>';
}
function skrift_faq_schema( $faq ) {
$fragen = array();
foreach ( $faq as $e ) {
$fragen[] = array(
'@type' => 'Question',
'name' => wp_strip_all_tags( $e['frage'] ),
'acceptedAnswer' => array(
'@type' => 'Answer',
'text' => wp_strip_all_tags( do_shortcode( $e['antwort'] ?? '' ) ),
),
);
}
return '<script type="application/ld+json">'
. wp_json_encode( array(
'@context' => 'https://schema.org',
'@type' => 'FAQPage',
'mainEntity' => $fragen,
), JSON_UNESCAPED_UNICODE | JSON_UNESCAPED_SLASHES )
. '</script>';
}
function skrift_faq_html( $faq, $args = array() ) {
$args = wp_parse_args( $args, array(
'titel' => '',
'titel_tag' => 'h2',
'erste_offen' => false,
'schema' => true,
) );
if ( empty( $faq ) ) {
return '';
}
$tag = in_array( $args['titel_tag'], array( 'h2', 'h3', 'h4', 'div' ), true ) ? $args['titel_tag'] : 'h2';
$html = skrift_faq_basis_css() . '<div class="skrift-faq">';
if ( '' !== $args['titel'] ) {
$html .= sprintf( '<%1$s class="skrift-faq__titel">%2$s</%1$s>', $tag, esc_html( $args['titel'] ) );
}
foreach ( array_values( $faq ) as $i => $e ) {
$offen = ( $args['erste_offen'] && 0 === $i ) ? ' open' : '';
$html .= '<details class="skrift-faq__eintrag"' . $offen . '>';
$html .= '<summary class="skrift-faq__frage">' . esc_html( $e['frage'] ) . '</summary>';
$html .= '<div class="skrift-faq__antwort">' . wp_kses_post( wpautop( do_shortcode( $e['antwort'] ?? '' ) ) ) . '</div>';
$html .= '</details>';
}
$html .= '</div>';
if ( $args['schema'] ) {
$html .= skrift_faq_schema( $faq );
}
return $html;
}
function skrift_kurzantwort_html( $post_id = 0 ) {
$post_id = $post_id ? (int) $post_id : get_the_ID();
$text = (string) get_post_meta( $post_id, 'kurzantwort', true );
if ( '' === trim( $text ) ) {
return '';
}
return '<div class="skrift-kurzantwort">' . wp_kses_post( wpautop( do_shortcode( $text ) ) ) . '</div>';
}
/* Shortcodes, z. B. fuer das Elementor-Shortcode-Widget oder klassische Themes */
add_shortcode( 'skrift_faq', function ( $atts ) {
$atts = shortcode_atts( array(
'titel' => '',
'erste_offen' => '0',
'schema' => '1',
'post_id' => 0,
), $atts, 'skrift_faq' );
return skrift_faq_html( skrift_faq_eintraege( $atts['post_id'] ), array(
'titel' => $atts['titel'],
'erste_offen' => '1' === (string) $atts['erste_offen'],
'schema' => '1' === (string) $atts['schema'],
) );
} );
add_shortcode( 'skrift_kurzantwort', function ( $atts ) {
$atts = shortcode_atts( array( 'post_id' => 0 ), $atts, 'skrift_kurzantwort' );
return skrift_kurzantwort_html( $atts['post_id'] );
} );
/* ------------------------------------------------------------------------
* 4. Elementor-Widgets: Skrift FAQ und Skrift Kurzantwort
* Einmal ins Single-Post-Template (Theme Builder) setzen, dann zeigt
* jeder Beitrag automatisch seine eigenen Fragen.
* --------------------------------------------------------------------- */
function skrift_elementor_bearbeitungsmodus() {
if ( ! class_exists( '\Elementor\Plugin' ) ) {
return false;
}
$e = \Elementor\Plugin::$instance;
if ( isset( $e->editor ) && $e->editor->is_edit_mode() ) {
return true;
}
return isset( $e->preview ) && $e->preview->is_preview_mode();
}
add_action( 'elementor/widgets/register', function ( $widgets_manager ) {
if ( ! class_exists( '\Elementor\Widget_Base' ) ) {
return;
}
if ( ! class_exists( 'Skrift_FAQ_Widget' ) ) {
class Skrift_FAQ_Widget extends \Elementor\Widget_Base {
public function get_name() {
return 'skrift_faq';
}
public function get_title() {
return 'Skrift FAQ';
}
public function get_icon() {
return 'eicon-accordion';
}
public function get_categories() {
return array( 'general' );
}
public function get_keywords() {
return array( 'faq', 'fragen', 'skrift', 'akkordeon', 'umschalter', 'toggle' );
}
protected function register_controls() {
$C = '\Elementor\Controls_Manager';
$this->start_controls_section( 'inhalt', array( 'label' => 'Inhalt' ) );
$this->add_control( 'hinweis', array(
'type' => $C::RAW_HTML,
'raw' => 'Fragen und Antworten kommen aus dem Meta-Feld <code>faq</code> des jeweiligen Beitrags.',
) );
$this->add_control( 'titel', array(
'label' => 'Ueberschrift',
'type' => $C::TEXT,
'default' => 'Häufige Fragen',
) );
$this->add_control( 'titel_tag', array(
'label' => 'HTML-Tag der Ueberschrift',
'type' => $C::SELECT,
'default' => 'h2',
'options' => array( 'h2' => 'H2', 'h3' => 'H3', 'h4' => 'H4', 'div' => 'div' ),
) );
$this->add_control( 'erste_offen', array(
'label' => 'Erste Frage geoeffnet',
'type' => $C::SWITCHER,
'default' => '',
) );
$this->add_control( 'schema', array(
'label' => 'FAQ-Schema ausgeben',
'type' => $C::SWITCHER,
'default' => 'yes',
) );
$this->end_controls_section();
$this->start_controls_section( 'stil_titel', array( 'label' => 'Ueberschrift', 'tab' => $C::TAB_STYLE ) );
$this->add_group_control( \Elementor\Group_Control_Typography::get_type(), array(
'name' => 'titel_typo',
'selector' => '{{WRAPPER}} .skrift-faq__titel',
) );
$this->add_control( 'titel_farbe', array(
'label' => 'Farbe',
'type' => $C::COLOR,
'selectors' => array( '{{WRAPPER}} .skrift-faq__titel' => 'color: {{VALUE}};' ),
) );
$this->add_responsive_control( 'titel_abstand', array(
'label' => 'Abstand darunter',
'type' => $C::SLIDER,
'size_units' => array( 'px', 'em' ),
'selectors' => array( '{{WRAPPER}} .skrift-faq__titel' => 'margin-bottom: {{SIZE}}{{UNIT}};' ),
) );
$this->end_controls_section();
$this->start_controls_section( 'stil_frage', array( 'label' => 'Frage', 'tab' => $C::TAB_STYLE ) );
$this->add_group_control( \Elementor\Group_Control_Typography::get_type(), array(
'name' => 'frage_typo',
'selector' => '{{WRAPPER}} .skrift-faq__frage',
) );
$this->add_control( 'frage_farbe', array(
'label' => 'Farbe',
'type' => $C::COLOR,
'selectors' => array( '{{WRAPPER}} .skrift-faq__frage' => 'color: {{VALUE}};' ),
) );
$this->add_control( 'frage_farbe_offen', array(
'label' => 'Farbe geoeffnet',
'type' => $C::COLOR,
'selectors' => array( '{{WRAPPER}} .skrift-faq__eintrag[open] .skrift-faq__frage' => 'color: {{VALUE}};' ),
) );
$this->add_control( 'frage_hintergrund', array(
'label' => 'Hintergrund',
'type' => $C::COLOR,
'selectors' => array( '{{WRAPPER}} .skrift-faq__frage' => 'background-color: {{VALUE}};' ),
) );
$this->add_responsive_control( 'frage_innenabstand', array(
'label' => 'Innenabstand',
'type' => $C::DIMENSIONS,
'size_units' => array( 'px', 'em' ),
'selectors' => array( '{{WRAPPER}} .skrift-faq__frage' => 'padding: {{TOP}}{{UNIT}} {{RIGHT}}{{UNIT}} {{BOTTOM}}{{UNIT}} {{LEFT}}{{UNIT}};' ),
) );
$this->end_controls_section();
$this->start_controls_section( 'stil_antwort', array( 'label' => 'Antwort', 'tab' => $C::TAB_STYLE ) );
$this->add_group_control( \Elementor\Group_Control_Typography::get_type(), array(
'name' => 'antwort_typo',
'selector' => '{{WRAPPER}} .skrift-faq__antwort',
) );
$this->add_control( 'antwort_farbe', array(
'label' => 'Farbe',
'type' => $C::COLOR,
'selectors' => array( '{{WRAPPER}} .skrift-faq__antwort' => 'color: {{VALUE}};' ),
) );
$this->add_responsive_control( 'antwort_innenabstand', array(
'label' => 'Innenabstand',
'type' => $C::DIMENSIONS,
'size_units' => array( 'px', 'em' ),
'selectors' => array( '{{WRAPPER}} .skrift-faq__antwort' => 'padding: {{TOP}}{{UNIT}} {{RIGHT}}{{UNIT}} {{BOTTOM}}{{UNIT}} {{LEFT}}{{UNIT}};' ),
) );
$this->end_controls_section();
$this->start_controls_section( 'stil_eintrag', array( 'label' => 'Eintrag', 'tab' => $C::TAB_STYLE ) );
$this->add_group_control( \Elementor\Group_Control_Border::get_type(), array(
'name' => 'eintrag_rahmen',
'selector' => '{{WRAPPER}} .skrift-faq__eintrag',
) );
$this->add_control( 'eintrag_radius', array(
'label' => 'Eckenradius',
'type' => $C::DIMENSIONS,
'size_units' => array( 'px' ),
'selectors' => array( '{{WRAPPER}} .skrift-faq__eintrag' => 'border-radius: {{TOP}}{{UNIT}} {{RIGHT}}{{UNIT}} {{BOTTOM}}{{UNIT}} {{LEFT}}{{UNIT}}; overflow: hidden;' ),
) );
$this->add_control( 'eintrag_hintergrund', array(
'label' => 'Hintergrund',
'type' => $C::COLOR,
'selectors' => array( '{{WRAPPER}} .skrift-faq__eintrag' => 'background-color: {{VALUE}};' ),
) );
$this->add_responsive_control( 'eintrag_abstand', array(
'label' => 'Abstand zwischen Eintraegen',
'type' => $C::SLIDER,
'size_units' => array( 'px', 'em' ),
'selectors' => array( '{{WRAPPER}} .skrift-faq__eintrag + .skrift-faq__eintrag' => 'margin-top: {{SIZE}}{{UNIT}};' ),
) );
$this->end_controls_section();
}
protected function render() {
$s = $this->get_settings_for_display();
$faq = skrift_faq_eintraege();
$bearbeiten = skrift_elementor_bearbeitungsmodus();
// Im Theme-Builder-Template gibt es keinen Beitrag mit FAQ,
// deshalb dort Platzhalter zum Gestalten.
if ( empty( $faq ) && $bearbeiten ) {
$faq = array(
array( 'frage' => 'Beispielfrage aus dem Feld faq', 'antwort' => 'Im Beitrag erscheinen hier die Antworten aus dem Meta-Feld faq.' ),
array( 'frage' => 'Zweite Beispielfrage', 'antwort' => 'Die Gestaltung legen Sie hier im Widget fest, sie gilt fuer alle Beitraege.' ),
array( 'frage' => 'Dritte Beispielfrage', 'antwort' => 'Beitraege ohne FAQ zeigen an dieser Stelle nichts an.' ),
);
}
echo skrift_faq_html( $faq, array( // phpcs:ignore WordPress.Security.EscapeOutput
'titel' => (string) ( $s['titel'] ?? '' ),
'titel_tag' => (string) ( $s['titel_tag'] ?? 'h2' ),
'erste_offen' => 'yes' === ( $s['erste_offen'] ?? '' ),
'schema' => 'yes' === ( $s['schema'] ?? '' ) && ! $bearbeiten,
) );
}
}
}
if ( ! class_exists( 'Skrift_Kurzantwort_Widget' ) ) {
class Skrift_Kurzantwort_Widget extends \Elementor\Widget_Base {
public function get_name() {
return 'skrift_kurzantwort';
}
public function get_title() {
return 'Skrift Kurzantwort';
}
public function get_icon() {
return 'eicon-text';
}
public function get_categories() {
return array( 'general' );
}
public function get_keywords() {
return array( 'kurzantwort', 'skrift', 'zusammenfassung', 'box' );
}
protected function register_controls() {
$C = '\Elementor\Controls_Manager';
$this->start_controls_section( 'inhalt', array( 'label' => 'Inhalt' ) );
$this->add_control( 'hinweis', array(
'type' => $C::RAW_HTML,
'raw' => 'Der Text kommt aus dem Meta-Feld <code>kurzantwort</code>. Preis-Shortcodes darin werden aufgeloest.',
) );
$this->end_controls_section();
$this->start_controls_section( 'stil_box', array( 'label' => 'Box', 'tab' => $C::TAB_STYLE ) );
$this->add_group_control( \Elementor\Group_Control_Typography::get_type(), array(
'name' => 'box_typo',
'selector' => '{{WRAPPER}} .skrift-kurzantwort',
) );
$this->add_control( 'box_farbe', array(
'label' => 'Textfarbe',
'type' => $C::COLOR,
'selectors' => array( '{{WRAPPER}} .skrift-kurzantwort' => 'color: {{VALUE}};' ),
) );
$this->add_control( 'box_hintergrund', array(
'label' => 'Hintergrund',
'type' => $C::COLOR,
'selectors' => array( '{{WRAPPER}} .skrift-kurzantwort' => 'background-color: {{VALUE}};' ),
) );
$this->add_group_control( \Elementor\Group_Control_Border::get_type(), array(
'name' => 'box_rahmen',
'selector' => '{{WRAPPER}} .skrift-kurzantwort',
) );
$this->add_control( 'box_radius', array(
'label' => 'Eckenradius',
'type' => $C::DIMENSIONS,
'size_units' => array( 'px' ),
'selectors' => array( '{{WRAPPER}} .skrift-kurzantwort' => 'border-radius: {{TOP}}{{UNIT}} {{RIGHT}}{{UNIT}} {{BOTTOM}}{{UNIT}} {{LEFT}}{{UNIT}};' ),
) );
$this->add_responsive_control( 'box_innenabstand', array(
'label' => 'Innenabstand',
'type' => $C::DIMENSIONS,
'size_units' => array( 'px', 'em' ),
'selectors' => array( '{{WRAPPER}} .skrift-kurzantwort' => 'padding: {{TOP}}{{UNIT}} {{RIGHT}}{{UNIT}} {{BOTTOM}}{{UNIT}} {{LEFT}}{{UNIT}};' ),
) );
$this->end_controls_section();
}
protected function render() {
$html = skrift_kurzantwort_html();
if ( '' === $html && skrift_elementor_bearbeitungsmodus() ) {
$html = '<div class="skrift-kurzantwort"><p>Platzhalter: Hier erscheint die Kurzantwort des jeweiligen Beitrags.</p></div>';
}
echo $html; // phpcs:ignore WordPress.Security.EscapeOutput
}
}
}
$widgets_manager->register( new Skrift_FAQ_Widget() );
$widgets_manager->register( new Skrift_Kurzantwort_Widget() );
} );