first commit 2
This commit is contained in:
@@ -0,0 +1,15 @@
|
||||
<?php
|
||||
if (!defined('_GNUBOARD_')) exit;
|
||||
|
||||
/**
|
||||
* rb.custom :: rolling_banner_footer/config.php
|
||||
* 하단 롤링 배너 모듈 설정 파일
|
||||
*/
|
||||
|
||||
$rolling_banner_config = [
|
||||
'position' => 'rolling_footer', // 배너 위치 (관리자 페이지에서 등록한 위치)
|
||||
'timeout' => 3000, // 롤링 간격 (밀리초)
|
||||
'speed' => 1000, // 슬라이드 속도
|
||||
'visible' => 6, // 한 번에 보여줄 배너 개수 (PC 기준)
|
||||
];
|
||||
?>
|
||||
@@ -0,0 +1,99 @@
|
||||
/* Rolling Banner Footer Style - Final Button Fix */
|
||||
|
||||
.rolling-banner-footer {
|
||||
background-color: #ffffff;
|
||||
padding: 20px 0;
|
||||
border-top: 1px solid #eee;
|
||||
}
|
||||
|
||||
.rolling-banner-wrap {
|
||||
position: relative;
|
||||
padding: 0 50px;
|
||||
height: 60px;
|
||||
overflow: hidden;
|
||||
}
|
||||
|
||||
/*.swiper-container {*/
|
||||
/* width: 100%;*/
|
||||
/* height: 100%;*/
|
||||
/*}*/
|
||||
|
||||
/* 💡 [핵심 수정] 고정 너비 삭제 */
|
||||
.swiper-slide.banner-item {
|
||||
/* width: 160px; */ /* Swiper가 자동으로 계산하도록 삭제 */
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.banner-item a {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
height: 100%;
|
||||
}
|
||||
|
||||
.banner-item img {
|
||||
max-width: 100%;
|
||||
max-height: 100%;
|
||||
object-fit: contain;
|
||||
transition: opacity 0.3s;
|
||||
}
|
||||
|
||||
.banner-item a:hover img {
|
||||
opacity: 0.8;
|
||||
}
|
||||
|
||||
.slider-controls .swiper-button-prev,
|
||||
.slider-controls .swiper-button-next {
|
||||
color: #fff;
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
background-color: #fff;
|
||||
border: 1px solid #ddd;
|
||||
border-radius: 50%;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
margin-top: 0;
|
||||
}
|
||||
|
||||
.slider-controls .swiper-button-prev:after,
|
||||
.slider-controls .swiper-button-next:after {
|
||||
font-size: 16px;
|
||||
font-weight: bold;
|
||||
}
|
||||
|
||||
.slider-controls .swiper-button-prev {
|
||||
left: 0;
|
||||
}
|
||||
|
||||
.slider-controls .swiper-button-next {
|
||||
right: 0;
|
||||
}
|
||||
|
||||
.empty-banner {
|
||||
text-align: center;
|
||||
padding: 20px;
|
||||
color: #fff;
|
||||
line-height: 60px;
|
||||
}
|
||||
|
||||
|
||||
/* 💡 [수정] 제목 영역 스타일 (밑줄 강화 및 위치 수정) */
|
||||
.rolling-banner-footer .bbs_main_wrap_tit {
|
||||
margin-bottom: 20px;
|
||||
border-bottom: 2px solid #333; /* 💡 밑줄 두께 2px, 색상 진하게(#333) */
|
||||
padding-bottom: 7px; /* 💡 [수정] 밑줄과 텍스트 사이 간격 줄임 (15px -> 7px) */
|
||||
overflow: hidden; /* 💡 float 해제 (높이 잡기) */
|
||||
}
|
||||
|
||||
.rolling-banner-footer .bbs_main_wrap_tit_l {
|
||||
float: left;
|
||||
}
|
||||
|
||||
.rolling-banner-footer .bbs_main_wrap_tit_r {
|
||||
float: right;
|
||||
padding-top: 5px; /* 버튼 위치 미세 조정 */
|
||||
}
|
||||
|
||||
.rolling-banner-footer .cb {
|
||||
clear: both;
|
||||
}
|
||||
@@ -0,0 +1,61 @@
|
||||
(function($) {
|
||||
"use strict";
|
||||
|
||||
if (typeof window.initRollingBannerFooter === 'function') {
|
||||
// return;
|
||||
}
|
||||
|
||||
window.initRollingBannerFooter = function(moduleId) {
|
||||
const $module = $('#' + moduleId);
|
||||
if (!$module.length) return;
|
||||
|
||||
const $swiperContainer = $module.find('.swiper-container');
|
||||
|
||||
const autoplayDelay = parseInt($swiperContainer.data('autoplay-delay'), 10) || 3000;
|
||||
const slidesPerViewPC = parseInt($swiperContainer.data('slides-per-view'), 10) || 6;
|
||||
const bannerCount = parseInt($swiperContainer.data('banner-count'), 10) || 0;
|
||||
|
||||
// 💡 [핵심 수정] 배너 개수가 화면에 보여줄 개수보다 많을 때만 loop를 활성화
|
||||
const isLoop = bannerCount > slidesPerViewPC;
|
||||
|
||||
new Swiper($swiperContainer[0], {
|
||||
spaceBetween: 20,
|
||||
loop: isLoop, // 💡 [수정] 동적으로 loop 설정
|
||||
autoplay: {
|
||||
delay: autoplayDelay,
|
||||
disableOnInteraction: false,
|
||||
},
|
||||
navigation: {
|
||||
nextEl: $module.find('.swiper-button-next')[0],
|
||||
prevEl: $module.find('.swiper-button-prev')[0],
|
||||
},
|
||||
observer: true,
|
||||
observeParents: true,
|
||||
// 💡 [핵심 수정] 반응형 Breakpoints 설정
|
||||
breakpoints: {
|
||||
// 320px 이상일 때
|
||||
320: {
|
||||
slidesPerView: 3,
|
||||
spaceBetween: 10
|
||||
},
|
||||
// 768px 이상일 때 (태블릿)
|
||||
768: {
|
||||
slidesPerView: 4,
|
||||
spaceBetween: 20
|
||||
},
|
||||
// 1024px 이상일 때 (PC)
|
||||
1024: {
|
||||
slidesPerView: slidesPerViewPC,
|
||||
spaceBetween: 20
|
||||
},
|
||||
}
|
||||
});
|
||||
};
|
||||
|
||||
$(function() {
|
||||
$('.rolling-banner-footer').each(function() {
|
||||
window.initRollingBannerFooter($(this).attr('id'));
|
||||
});
|
||||
});
|
||||
|
||||
})(jQuery);
|
||||
@@ -0,0 +1,58 @@
|
||||
(function($) {
|
||||
"use strict";
|
||||
|
||||
if (typeof window.initRollingBannerFooter === 'function') {
|
||||
// return;
|
||||
}
|
||||
|
||||
window.initRollingBannerFooter = function(moduleId) {
|
||||
const $module = $('#' + moduleId);
|
||||
if (!$module.length) return;
|
||||
|
||||
const $swiperContainer = $module.find('.swiper-container');
|
||||
|
||||
const autoplayDelay = parseInt($swiperContainer.data('autoplay-delay'), 10) || 3000;
|
||||
const slidesPerViewPC = parseInt($swiperContainer.data('slides-per-view'), 10) || 6;
|
||||
|
||||
new Swiper($swiperContainer[0], {
|
||||
// slidesPerView: 'auto', // 💡 [삭제] 자동 너비 대신 개수 지정
|
||||
spaceBetween: 20,
|
||||
loop: true,
|
||||
autoplay: {
|
||||
delay: autoplayDelay,
|
||||
disableOnInteraction: false,
|
||||
},
|
||||
navigation: {
|
||||
nextEl: $module.find('.swiper-button-next')[0],
|
||||
prevEl: $module.find('.swiper-button-prev')[0],
|
||||
},
|
||||
observer: true,
|
||||
observeParents: true,
|
||||
// 💡 [핵심 수정] 반응형 Breakpoints 설정
|
||||
breakpoints: {
|
||||
// 320px 이상일 때
|
||||
320: {
|
||||
slidesPerView: 3,
|
||||
spaceBetween: 10
|
||||
},
|
||||
// 768px 이상일 때 (태블릿)
|
||||
768: {
|
||||
slidesPerView: 4,
|
||||
spaceBetween: 20
|
||||
},
|
||||
// 1024px 이상일 때 (PC)
|
||||
1024: {
|
||||
slidesPerView: slidesPerViewPC,
|
||||
spaceBetween: 20
|
||||
},
|
||||
}
|
||||
});
|
||||
};
|
||||
|
||||
$(function() {
|
||||
$('.rolling-banner-footer').each(function() {
|
||||
window.initRollingBannerFooter($(this).attr('id'));
|
||||
});
|
||||
});
|
||||
|
||||
})(jQuery);
|
||||
@@ -0,0 +1,121 @@
|
||||
<?php
|
||||
if (!defined('_GNUBOARD_')) exit;
|
||||
|
||||
// 1. 설정 파일 로드
|
||||
$config_path = __DIR__ . '/config.php';
|
||||
if (!file_exists($config_path)) return;
|
||||
include_once($config_path);
|
||||
include_once(G5_LIB_PATH.'/thumbnail.lib.php');
|
||||
|
||||
// 💡 [핵심] $md_id 변수를 사용하여 모듈 설정 로드
|
||||
if (isset($md_id) && $md_id) {
|
||||
$rb_skin = get_rb_module_config($md_id);
|
||||
} else {
|
||||
$rb_skin = array(); // md_id가 없을 경우 빈 배열
|
||||
}
|
||||
|
||||
// 2. 데이터 가져오기
|
||||
$position = $rolling_banner_config['position'];
|
||||
$sql = " SELECT * FROM `rb_banner` WHERE bn_position = '{$position}' AND bn_begin_time <= NOW() AND bn_end_time >= NOW() ORDER BY bn_order ASC, bn_id DESC ";
|
||||
$result = sql_query($sql);
|
||||
|
||||
$banners = [];
|
||||
while ($row = sql_fetch_array($result)) {
|
||||
$banners[] = $row;
|
||||
}
|
||||
$banner_count = count($banners); // 💡 [추가] 배너 개수 저장
|
||||
$visual_id = 'rbf_' . uniqid();
|
||||
?>
|
||||
|
||||
<div class="rolling-banner-footer" id="<?php echo $visual_id; ?>">
|
||||
<ul class="bbs_main_wrap_tit" style="display:<?php echo (isset($rb_skin['md_title_hide']) && $rb_skin['md_title_hide'] == '1') ? 'none' : 'block'; ?>">
|
||||
<li class="bbs_main_wrap_tit_l">
|
||||
<a href="<?php echo $links_url; ?>">
|
||||
<h2 class="<?php echo isset($rb_skin['md_title_font']) ? $rb_skin['md_title_font'] : 'font-B'; ?>" style="color:<?php echo isset($rb_skin['md_title_color']) ? $rb_skin['md_title_color'] : '#25282b'; ?>; font-size:<?php echo isset($rb_skin['md_title_size']) ? $rb_skin['md_title_size'] : '20'; ?>px; "><?php echo isset($rb_skin['md_title']) ? $rb_skin['md_title'] : '하단 롤링 배너'; ?></h2>
|
||||
</a>
|
||||
</li>
|
||||
<div class="cb"></div>
|
||||
</ul>
|
||||
|
||||
<div class="rolling-banner-wrap">
|
||||
<!-- 💡 [핵심 수정] Swiper 구조로 변경 -->
|
||||
<div class="swiper-container rolling-swiper"
|
||||
data-autoplay-delay="<?php echo $rolling_banner_config['timeout']; ?>"
|
||||
data-slides-per-view="<?php echo $rolling_banner_config['visible']; ?>"
|
||||
data-banner-count="<?php echo $banner_count; ?>">
|
||||
<div class="swiper-wrapper">
|
||||
<?php foreach ($banners as $banner):
|
||||
$bimg = G5_DATA_PATH.'/banners/'.$banner['bn_id'];
|
||||
if (!file_exists($bimg)) continue;
|
||||
$img_src = G5_DATA_URL.'/banners/'.$banner['bn_id'];
|
||||
?>
|
||||
<div class="swiper-slide banner-item">
|
||||
<a href="<?php echo $banner['bn_url']; ?>" target="<?php echo $banner['bn_new_win'] ? '_blank' : '_self'; ?>">
|
||||
<img src="<?php echo $img_src; ?>" alt="<?php echo get_text($banner['bn_alt']); ?>">
|
||||
</a>
|
||||
</div>
|
||||
<?php endforeach; ?>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="slider-controls">
|
||||
<div class="swiper-button-prev btn-prev"><i class="fa fa-chevron-left"></i></div>
|
||||
<div class="swiper-button-next btn-next"><i class="fa fa-chevron-right"></i></div>
|
||||
</div>
|
||||
|
||||
<?php if (empty($banners)): ?>
|
||||
<div class="empty-banner">등록된 배너가 없습니다.</div>
|
||||
<?php endif; ?>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<link rel="stylesheet" href="<?php echo G5_THEME_URL; ?>/rb.custom/rolling_banner_footer/module.css?ver=<?php echo G5_CSS_VER; ?>">
|
||||
|
||||
<!-- 통합 동적 로더 -->
|
||||
<script>
|
||||
(function() {
|
||||
var currentModuleId = '<?php echo $visual_id; ?>';
|
||||
var initFunctionName = 'initRollingBannerFooter';
|
||||
var themeUrl = '<?php echo G5_THEME_URL; ?>';
|
||||
var jsVer = '<?php echo G5_JS_VER; ?>';
|
||||
|
||||
function loadScript(src, id, callback) {
|
||||
if (document.getElementById(id)) {
|
||||
if (callback) callback();
|
||||
return;
|
||||
}
|
||||
var script = document.createElement('script');
|
||||
script.id = id;
|
||||
script.src = src;
|
||||
script.async = false;
|
||||
if (callback) {
|
||||
script.onload = callback;
|
||||
}
|
||||
document.head.appendChild(script);
|
||||
}
|
||||
|
||||
function finalAction() {
|
||||
if (typeof window[initFunctionName] === 'function') {
|
||||
window[initFunctionName](currentModuleId);
|
||||
}
|
||||
}
|
||||
|
||||
function loadModuleScript() {
|
||||
loadScript(themeUrl + '/rb.custom/rolling_banner_footer/module.js?ver=' + jsVer, 'rolling-banner-footer-js', finalAction);
|
||||
}
|
||||
|
||||
// 💡 [핵심] Swiper 라이브러리 로드 확인
|
||||
if (typeof Swiper === 'undefined') {
|
||||
// Swiper CSS 로드
|
||||
var link = document.createElement('link');
|
||||
link.rel = 'stylesheet';
|
||||
link.href = 'https://unpkg.com/swiper/swiper-bundle.min.css';
|
||||
document.head.appendChild(link);
|
||||
|
||||
// Swiper JS 로드
|
||||
loadScript('https://unpkg.com/swiper/swiper-bundle.min.js', 'swiper-bundle-js', loadModuleScript);
|
||||
} else {
|
||||
loadModuleScript();
|
||||
}
|
||||
})();
|
||||
</script>
|
||||
@@ -0,0 +1,135 @@
|
||||
<?php
|
||||
if (!defined('_GNUBOARD_')) exit;
|
||||
|
||||
// 1. 설정 파일 로드
|
||||
$config_path = __DIR__ . '/config.php';
|
||||
if (!file_exists($config_path)) return;
|
||||
include_once($config_path);
|
||||
include_once(G5_LIB_PATH.'/thumbnail.lib.php');
|
||||
|
||||
// 💡 [핵심] $md_id 변수를 사용하여 모듈 설정 로드
|
||||
// 이 파일이 include 될 때 상위 스코프에서 $md_id가 정의되어 있어야 합니다.
|
||||
// 보통 index.php 등에서 모듈을 호출할 때 $md_id를 설정하고 include 합니다.
|
||||
if (isset($md_id) && $md_id) {
|
||||
$rb_skin = get_rb_module_config($md_id);
|
||||
} else {
|
||||
$rb_skin = array(); // md_id가 없을 경우 빈 배열
|
||||
}
|
||||
|
||||
// 2. 데이터 가져오기
|
||||
$position = $rolling_banner_config['position'];
|
||||
$sql = " SELECT * FROM `rb_banner` WHERE bn_position = '{$position}' AND bn_begin_time <= NOW() AND bn_end_time >= NOW() ORDER BY bn_order ASC, bn_id DESC ";
|
||||
$result = sql_query($sql);
|
||||
|
||||
$banners = [];
|
||||
while ($row = sql_fetch_array($result)) {
|
||||
$banners[] = $row;
|
||||
}
|
||||
|
||||
$visual_id = 'rbf_' . uniqid();
|
||||
?>
|
||||
|
||||
<!-- Rebuilder 표준 구조 -->
|
||||
<!--<div class="rb_layout_box" data-id="rolling_banner_footer">-->
|
||||
<!-- --><?php //if ($is_admin) { ?>
|
||||
<!-- <div class="rb_module_set">-->
|
||||
<!-- <a href="javascript:;" onclick="set_module_send(this);" class="btn_module_setup"><i class="fa fa-cog"></i></a>-->
|
||||
<!-- </div>-->
|
||||
<!-- --><?php //} ?>
|
||||
|
||||
<div class="rolling-banner-footer" id="<?php echo $visual_id; ?>">
|
||||
<!-- <div class="container">-->
|
||||
<!-- { -->
|
||||
<ul class="bbs_main_wrap_tit" style="display:<?php echo (isset($rb_skin['md_title_hide']) && $rb_skin['md_title_hide'] == '1') ? 'none' : 'block'; ?>">
|
||||
|
||||
<li class="bbs_main_wrap_tit_l">
|
||||
<!-- 타이틀 { -->
|
||||
<a href="<?php echo $links_url; ?>">
|
||||
<h2 class="<?php echo isset($rb_skin['md_title_font']) ? $rb_skin['md_title_font'] : 'font-B'; ?>" style="color:<?php echo isset($rb_skin['md_title_color']) ? $rb_skin['md_title_color'] : '#25282b'; ?>; font-size:<?php echo isset($rb_skin['md_title_size']) ? $rb_skin['md_title_size'] : '20'; ?>px; "><?php echo isset($rb_skin['md_title']) ? $rb_skin['md_title'] : '하단 롤링 배너'; ?></h2>
|
||||
</a>
|
||||
<!-- } -->
|
||||
</li>
|
||||
<div class="cb"></div>
|
||||
</ul>
|
||||
|
||||
<div class="rolling-banner-wrap">
|
||||
<!-- 💡 [핵심 수정] Swiper 구조로 변경 -->
|
||||
<div class="swiper-container rolling-swiper"
|
||||
data-autoplay-delay="<?php echo $rolling_banner_config['timeout']; ?>"
|
||||
data-slides-per-view="<?php echo $rolling_banner_config['visible']; ?>">
|
||||
<div class="swiper-wrapper">
|
||||
<?php foreach ($banners as $banner):
|
||||
$bimg = G5_DATA_PATH.'/banners/'.$banner['bn_id'];
|
||||
if (!file_exists($bimg)) continue;
|
||||
$img_src = G5_DATA_URL.'/banners/'.$banner['bn_id'];
|
||||
?>
|
||||
<div class="swiper-slide banner-item">
|
||||
<a href="<?php echo $banner['bn_url']; ?>" target="<?php echo $banner['bn_new_win'] ? '_blank' : '_self'; ?>">
|
||||
<img src="<?php echo $img_src; ?>" alt="<?php echo get_text($banner['bn_alt']); ?>">
|
||||
</a>
|
||||
</div>
|
||||
<?php endforeach; ?>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="slider-controls">
|
||||
<div class="swiper-button-prev btn-prev"><i class="fa fa-chevron-left"></i></div>
|
||||
<div class="swiper-button-next btn-next"><i class="fa fa-chevron-right"></i></div>
|
||||
</div>
|
||||
|
||||
<?php if (empty($banners)): ?>
|
||||
<div class="empty-banner">등록된 배너가 없습니다.</div>
|
||||
<?php endif; ?>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<link rel="stylesheet" href="<?php echo G5_THEME_URL; ?>/rb.custom/rolling_banner_footer/module.css?ver=<?php echo G5_CSS_VER; ?>">
|
||||
|
||||
<!-- 통합 동적 로더 -->
|
||||
<script>
|
||||
(function() {
|
||||
var currentModuleId = '<?php echo $visual_id; ?>';
|
||||
var initFunctionName = 'initRollingBannerFooter';
|
||||
var themeUrl = '<?php echo G5_THEME_URL; ?>';
|
||||
var jsVer = '<?php echo G5_JS_VER; ?>';
|
||||
|
||||
function loadScript(src, id, callback) {
|
||||
if (document.getElementById(id)) {
|
||||
if (callback) callback();
|
||||
return;
|
||||
}
|
||||
var script = document.createElement('script');
|
||||
script.id = id;
|
||||
script.src = src;
|
||||
script.async = false;
|
||||
if (callback) {
|
||||
script.onload = callback;
|
||||
}
|
||||
document.head.appendChild(script);
|
||||
}
|
||||
|
||||
function finalAction() {
|
||||
if (typeof window[initFunctionName] === 'function') {
|
||||
window[initFunctionName](currentModuleId);
|
||||
}
|
||||
}
|
||||
|
||||
function loadModuleScript() {
|
||||
loadScript(themeUrl + '/rb.custom/rolling_banner_footer/module.js?ver=' + jsVer, 'rolling-banner-footer-js', finalAction);
|
||||
}
|
||||
|
||||
// 💡 [핵심] Swiper 라이브러리 로드 확인
|
||||
if (typeof Swiper === 'undefined') {
|
||||
// Swiper CSS 로드
|
||||
var link = document.createElement('link');
|
||||
link.rel = 'stylesheet';
|
||||
link.href = 'https://unpkg.com/swiper/swiper-bundle.min.css';
|
||||
document.head.appendChild(link);
|
||||
|
||||
// Swiper JS 로드
|
||||
loadScript('https://unpkg.com/swiper/swiper-bundle.min.js', 'swiper-bundle-js', loadModuleScript);
|
||||
} else {
|
||||
loadModuleScript();
|
||||
}
|
||||
})();
|
||||
</script>
|
||||
Reference in New Issue
Block a user