|
|
<?php
|
|
|
/**
|
|
|
* FAQ 区块模板
|
|
|
* 显示常见问题和答案,支持手风琴折叠效果
|
|
|
*/
|
|
|
|
|
|
// 防止直接访问
|
|
|
if (!defined('ABSPATH')) {
|
|
|
exit;
|
|
|
}
|
|
|
|
|
|
// 获取短代码参数
|
|
|
global $faq_shortcode_atts;
|
|
|
$id = isset($faq_shortcode_atts['id']) ? $faq_shortcode_atts['id'] : 'nenghui-faq';
|
|
|
$class = isset($faq_shortcode_atts['class']) ? $faq_shortcode_atts['class'] : '';
|
|
|
$title = isset($faq_shortcode_atts['title']) ? $faq_shortcode_atts['title'] : 'Frequently Asked Questions';
|
|
|
$posts_per_page = isset($faq_shortcode_atts['posts_per_page']) ? $faq_shortcode_atts['posts_per_page'] : '-1';
|
|
|
$order_by = isset($faq_shortcode_atts['order_by']) ? $faq_shortcode_atts['order_by'] : 'menu_order';
|
|
|
$order = isset($faq_shortcode_atts['order']) ? $faq_shortcode_atts['order'] : 'ASC';
|
|
|
$show_animation = isset($faq_shortcode_atts['show_animation']) ? $faq_shortcode_atts['show_animation'] : 'true';
|
|
|
|
|
|
// 构建查询参数
|
|
|
$query_args = array(
|
|
|
'post_type' => 'faq',
|
|
|
'post_status' => 'publish',
|
|
|
'posts_per_page' => intval($posts_per_page),
|
|
|
'orderby' => $order_by,
|
|
|
'order' => $order
|
|
|
);
|
|
|
|
|
|
// 执行查询
|
|
|
$faq_query = new WP_Query($query_args);
|
|
|
|
|
|
// 生成唯一ID
|
|
|
$unique_id = $id . '-' . uniqid();
|
|
|
?>
|
|
|
|
|
|
<section id="<?php echo esc_attr($unique_id); ?>" class="faq-section <?php echo esc_attr($class); ?>">
|
|
|
<div class="faq-container">
|
|
|
<?php if (!empty($title)): ?>
|
|
|
<div class="faq-header">
|
|
|
<h2 class="faq-title"><?php echo esc_html($title); ?></h2>
|
|
|
</div>
|
|
|
<?php endif; ?>
|
|
|
|
|
|
<?php if ($faq_query->have_posts()): ?>
|
|
|
<div class="faq-accordion">
|
|
|
<?php
|
|
|
$item_index = 0;
|
|
|
while ($faq_query->have_posts()):
|
|
|
$faq_query->the_post();
|
|
|
$item_index++;
|
|
|
$item_id = $unique_id . '-item-' . $item_index;
|
|
|
?>
|
|
|
<div class="faq-item" data-aos="<?php echo $show_animation === 'true' ? 'fade-up' : ''; ?>" data-aos-delay="<?php echo $item_index * 100; ?>">
|
|
|
<div class="faq-question" data-target="<?php echo esc_attr($item_id); ?>">
|
|
|
<h3 class="faq-question-title"><?php the_title(); ?></h3>
|
|
|
<span class="faq-toggle-icon">
|
|
|
<svg width="24" height="24" viewBox="0 0 24 24" fill="none" xmlns="http://www.w3.org/2000/svg">
|
|
|
<path class="faq-icon-horizontal" d="M12 5V19" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"/>
|
|
|
<path class="faq-icon-vertical" d="M5 12H19" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"/>
|
|
|
</svg>
|
|
|
</span>
|
|
|
</div>
|
|
|
<div class="faq-answer" id="<?php echo esc_attr($item_id); ?>">
|
|
|
<div class="faq-answer-content">
|
|
|
<?php
|
|
|
// 显示内容,如果没有内容则显示摘要
|
|
|
$content = get_the_content();
|
|
|
if (!empty($content)) {
|
|
|
echo apply_filters('the_content', $content);
|
|
|
} else {
|
|
|
echo '<p>' . get_the_excerpt() . '</p>';
|
|
|
}
|
|
|
?>
|
|
|
</div>
|
|
|
</div>
|
|
|
</div>
|
|
|
<?php endwhile; ?>
|
|
|
</div>
|
|
|
<?php else: ?>
|
|
|
<div class="faq-no-content">
|
|
|
<p>暂无FAQ内容。</p>
|
|
|
</div>
|
|
|
<?php endif; ?>
|
|
|
</div>
|
|
|
</section>
|
|
|
|
|
|
<?php wp_reset_postdata(); ?>
|
|
|
|
|
|
<style>
|
|
|
.faq-section {
|
|
|
padding: 80px 0;
|
|
|
background-color: #f8f9fa;
|
|
|
}
|
|
|
|
|
|
.faq-container {
|
|
|
max-width: 1200px;
|
|
|
margin: 0 auto;
|
|
|
padding: 0 20px;
|
|
|
}
|
|
|
|
|
|
.faq-header {
|
|
|
text-align: center;
|
|
|
margin-bottom: 60px;
|
|
|
}
|
|
|
|
|
|
.faq-title {
|
|
|
font-size: 2.5rem;
|
|
|
font-weight: 700;
|
|
|
color: #333333;
|
|
|
margin: 0;
|
|
|
position: relative;
|
|
|
}
|
|
|
|
|
|
.faq-title::after {
|
|
|
content: '';
|
|
|
position: absolute;
|
|
|
bottom: -15px;
|
|
|
left: 50%;
|
|
|
transform: translateX(-50%);
|
|
|
width: 80px;
|
|
|
height: 4px;
|
|
|
background: linear-gradient(135deg, #2cb5a9, #00699f);
|
|
|
border-radius: 2px;
|
|
|
}
|
|
|
|
|
|
.faq-accordion {
|
|
|
max-width: 900px;
|
|
|
margin: 0 auto;
|
|
|
}
|
|
|
|
|
|
.faq-item {
|
|
|
margin-bottom: 20px;
|
|
|
border-radius: 12px;
|
|
|
overflow: hidden;
|
|
|
box-shadow: 0 4px 20px rgba(0, 0, 0, 0.08);
|
|
|
background: #ffffff;
|
|
|
transition: all 0.3s ease;
|
|
|
}
|
|
|
|
|
|
.faq-item:hover {
|
|
|
box-shadow: 0 8px 30px rgba(0, 0, 0, 0.12);
|
|
|
transform: translateY(-2px);
|
|
|
transition: all 0.3s ease;
|
|
|
}
|
|
|
|
|
|
.faq-question {
|
|
|
background-size: cover;
|
|
|
background-position: center;
|
|
|
background-repeat: no-repeat;
|
|
|
padding: 25px 30px;
|
|
|
cursor: pointer;
|
|
|
display: flex;
|
|
|
justify-content: space-between;
|
|
|
align-items: center;
|
|
|
transition: all 0.3s ease;
|
|
|
position: relative;
|
|
|
}
|
|
|
|
|
|
.faq-question:hover {
|
|
|
background-image: url('<?php echo get_template_directory_uri(); ?>/assets/images/faq-title-bg.webp');
|
|
|
}
|
|
|
|
|
|
.faq-item.active .faq-question {
|
|
|
background-image: url('<?php echo get_template_directory_uri(); ?>/assets/images/faq-title-bg.webp');
|
|
|
}
|
|
|
|
|
|
.faq-question::before {
|
|
|
content: '';
|
|
|
position: absolute;
|
|
|
top: 0;
|
|
|
left: 0;
|
|
|
right: 0;
|
|
|
bottom: 0;
|
|
|
transition: all 0.3s ease;
|
|
|
}
|
|
|
|
|
|
.faq-question:hover::before {
|
|
|
background: rgba(0, 86, 179, 0.9);
|
|
|
transition: all 0.3s ease;
|
|
|
}
|
|
|
|
|
|
.faq-question-title {
|
|
|
font-size: 1.2rem;
|
|
|
font-weight: 600;
|
|
|
color: #000000;
|
|
|
margin: 0;
|
|
|
flex: 1;
|
|
|
position: relative;
|
|
|
z-index: 1;
|
|
|
line-height: 1.4;
|
|
|
transition: all 0.3s ease;
|
|
|
}
|
|
|
|
|
|
.faq-question:hover .faq-question-title,
|
|
|
.faq-item.active .faq-question .faq-question-title {
|
|
|
color: #ffffff;
|
|
|
}
|
|
|
|
|
|
.faq-toggle-icon {
|
|
|
width: 24px;
|
|
|
height: 24px;
|
|
|
color: #000000;
|
|
|
transition: transform 0.3s ease, color 0.3s ease;
|
|
|
position: relative;
|
|
|
z-index: 1;
|
|
|
flex-shrink: 0;
|
|
|
margin-left: 20px;
|
|
|
}
|
|
|
|
|
|
.faq-question:hover .faq-toggle-icon,
|
|
|
.faq-item.active .faq-question .faq-toggle-icon {
|
|
|
color: #ffffff;
|
|
|
}
|
|
|
|
|
|
.faq-item.active .faq-toggle-icon {
|
|
|
transform: rotate(45deg);
|
|
|
}
|
|
|
|
|
|
.faq-answer {
|
|
|
max-height: 0;
|
|
|
overflow: hidden;
|
|
|
transition: max-height 0.4s ease, padding 0.4s ease;
|
|
|
background: #ffffff;
|
|
|
}
|
|
|
|
|
|
.faq-item.active .faq-answer {
|
|
|
max-height: 1000px;
|
|
|
padding: 30px;
|
|
|
}
|
|
|
|
|
|
.faq-answer-content {
|
|
|
color: #555555;
|
|
|
line-height: 1.7;
|
|
|
font-size: 1rem;
|
|
|
}
|
|
|
|
|
|
.faq-answer-content p {
|
|
|
margin: 0 0 15px 0;
|
|
|
}
|
|
|
|
|
|
.faq-answer-content p:last-child {
|
|
|
margin-bottom: 0;
|
|
|
}
|
|
|
|
|
|
.faq-answer-content ul,
|
|
|
.faq-answer-content ol {
|
|
|
margin: 15px 0;
|
|
|
padding-left: 25px;
|
|
|
}
|
|
|
|
|
|
.faq-answer-content li {
|
|
|
margin-bottom: 8px;
|
|
|
}
|
|
|
|
|
|
.faq-answer-content strong {
|
|
|
color: #333333;
|
|
|
font-weight: 600;
|
|
|
}
|
|
|
|
|
|
.faq-answer-content a {
|
|
|
color: #007bff;
|
|
|
text-decoration: none;
|
|
|
transition: color 0.3s ease;
|
|
|
}
|
|
|
|
|
|
.faq-answer-content a:hover {
|
|
|
color: #0056b3;
|
|
|
text-decoration: underline;
|
|
|
transition: all 0.3s ease;
|
|
|
}
|
|
|
|
|
|
.faq-no-content {
|
|
|
text-align: center;
|
|
|
padding: 60px 20px;
|
|
|
color: #666666;
|
|
|
font-size: 1.1rem;
|
|
|
}
|
|
|
|
|
|
/* 响应式设计 */
|
|
|
@media (max-width: 768px) {
|
|
|
.faq-section {
|
|
|
padding: 60px 0;
|
|
|
}
|
|
|
|
|
|
.faq-container {
|
|
|
padding: 0 15px;
|
|
|
}
|
|
|
|
|
|
.faq-title {
|
|
|
font-size: 2rem;
|
|
|
}
|
|
|
|
|
|
.faq-header {
|
|
|
margin-bottom: 40px;
|
|
|
}
|
|
|
|
|
|
.faq-question {
|
|
|
padding: 20px;
|
|
|
}
|
|
|
|
|
|
.faq-question-title {
|
|
|
font-size: 1.1rem;
|
|
|
}
|
|
|
|
|
|
.faq-toggle-icon {
|
|
|
margin-left: 15px;
|
|
|
}
|
|
|
|
|
|
.faq-item.active .faq-answer {
|
|
|
padding: 20px;
|
|
|
}
|
|
|
|
|
|
.faq-answer-content {
|
|
|
font-size: 0.95rem;
|
|
|
}
|
|
|
}
|
|
|
|
|
|
@media (max-width: 480px) {
|
|
|
.faq-title {
|
|
|
font-size: 1.8rem;
|
|
|
}
|
|
|
|
|
|
.faq-question {
|
|
|
padding: 18px 15px;
|
|
|
}
|
|
|
|
|
|
.faq-question-title {
|
|
|
font-size: 1rem;
|
|
|
}
|
|
|
|
|
|
.faq-item.active .faq-answer {
|
|
|
padding: 15px;
|
|
|
}
|
|
|
}
|
|
|
</style>
|
|
|
|
|
|
<script>
|
|
|
document.addEventListener('DOMContentLoaded', function() {
|
|
|
const faqSection = document.getElementById('<?php echo esc_js($unique_id); ?>');
|
|
|
if (!faqSection) return;
|
|
|
|
|
|
const faqQuestions = faqSection.querySelectorAll('.faq-question');
|
|
|
|
|
|
faqQuestions.forEach(function(question) {
|
|
|
question.addEventListener('click', function() {
|
|
|
const targetId = this.getAttribute('data-target');
|
|
|
const faqItem = this.closest('.faq-item');
|
|
|
const answer = document.getElementById(targetId);
|
|
|
|
|
|
if (!answer || !faqItem) return;
|
|
|
|
|
|
// 切换当前项目的状态
|
|
|
const isActive = faqItem.classList.contains('active');
|
|
|
|
|
|
// 关闭所有其他项目
|
|
|
faqSection.querySelectorAll('.faq-item.active').forEach(function(activeItem) {
|
|
|
if (activeItem !== faqItem) {
|
|
|
activeItem.classList.remove('active');
|
|
|
}
|
|
|
});
|
|
|
|
|
|
// 切换当前项目
|
|
|
if (isActive) {
|
|
|
faqItem.classList.remove('active');
|
|
|
} else {
|
|
|
faqItem.classList.add('active');
|
|
|
}
|
|
|
});
|
|
|
});
|
|
|
|
|
|
// 键盘导航支持
|
|
|
faqQuestions.forEach(function(question, index) {
|
|
|
question.setAttribute('tabindex', '0');
|
|
|
question.setAttribute('role', 'button');
|
|
|
question.setAttribute('aria-expanded', 'false');
|
|
|
|
|
|
question.addEventListener('keydown', function(e) {
|
|
|
if (e.key === 'Enter' || e.key === ' ') {
|
|
|
e.preventDefault();
|
|
|
this.click();
|
|
|
}
|
|
|
});
|
|
|
});
|
|
|
|
|
|
// 更新aria-expanded属性
|
|
|
const observer = new MutationObserver(function(mutations) {
|
|
|
mutations.forEach(function(mutation) {
|
|
|
if (mutation.type === 'attributes' && mutation.attributeName === 'class') {
|
|
|
const faqItem = mutation.target;
|
|
|
const question = faqItem.querySelector('.faq-question');
|
|
|
if (question) {
|
|
|
const isActive = faqItem.classList.contains('active');
|
|
|
question.setAttribute('aria-expanded', isActive.toString());
|
|
|
}
|
|
|
}
|
|
|
});
|
|
|
});
|
|
|
|
|
|
faqSection.querySelectorAll('.faq-item').forEach(function(item) {
|
|
|
observer.observe(item, { attributes: true, attributeFilter: ['class'] });
|
|
|
});
|
|
|
});
|
|
|
</script>
|
|
|
|
|
|
<?php if ($show_animation === 'true'): ?>
|
|
|
<script>
|
|
|
// 如果AOS库可用,初始化动画
|
|
|
if (typeof AOS !== 'undefined') {
|
|
|
AOS.init({
|
|
|
duration: 800,
|
|
|
easing: 'ease-out-cubic',
|
|
|
once: true,
|
|
|
offset: 100
|
|
|
});
|
|
|
}
|
|
|
</script>
|
|
|
<?php endif; ?>
|