我希望使用VueJS中的按钮实现水平滚动。我有一个容器,该容器具有水平堆叠的几个div,我想使用按钮滚动浏览它们。
Here是SO上用于JQuery的相同线程。 This demo是JQuery中的解决方案。它应该说明我所追求的效果。
如何使用VueJS达到这种效果?
我已经看过的一些库包括vue-scroll-to和jump。
Vue-scroll-to要求用户指定要滚动到的元素,而我想在特定元素内水平滚动一定数量的像素。
跳转允许用户滚动显示一定数量的像素,但只能垂直显示,并且只能在窗口上滚动。
编辑:我在VanillaJS中找到了一个完成此任务的小库:https://github.com/tarun-dugar/easy-scroll
答案 0 :(得分:3)
我为此做了一个沙盒:see it here
逻辑是这样的:
var heading = google.maps.geometry.spherical.computeHeading(pos1, pos2);
var directionIcon = {
path: google.maps.SymbolPath.FORWARD_OPEN_ARROW,
scale: 5,
rotation: heading
};
if (!endArrowMarker) {
endArrowMarker = new Marker({
position: pos2,
clickable: false,
icon: directionIcon,
map: map
});
} else {
endArrowMarker.setIcon(directionIcon);
}
您有一个包装,并且您增加/减少了scroll_left() {
let content = document.querySelector(".wrapper-box");
content.scrollLeft -= 50;
},
scroll_right() {
let content = document.querySelector(".wrapper-box");
content.scrollLeft += 40;
}
属性
完整代码可在here
中找到答案 1 :(得分:2)
您只能使用JavaScript,在您给我的示例中,我仅将其转换为JavaScript,这是它的代码笔。
https://codepen.io/immad-hamid/pen/yEmayr
这是可以代替您发送的示例的JavaScript。
const rightBtn = document.querySelector('#right-button');
const leftBtn = document.querySelector('#left-button');
rightBtn.addEventListener("click", function(event) {
const conent = document.querySelector('#content');
conent.scrollLeft += 300;
event.preventDefault();
});
leftBtn.addEventListener("click", function(event) {
const conent = document.querySelector('#content');
conent.scrollLeft -= 300;
event.preventDefault();
});
对于动画,您必须使用某些东西...可以做到吗?
答案 2 :(得分:1)
codepen 还有这个例子
$ Here's the link
https://codepen.io/wa23/pen/pObyrq
这里是重要的事情: HTML(哈巴狗)
link(href="https://fonts.googleapis.com/css?family=Source+Sans+Pro:200,300,400" rel="stylesheet")
h1 Vue Carousel
script#v-carousel(type="x/template")
.card-carousel-wrapper
.card-carousel--nav__left(
@click="moveCarousel(-1)"
:disabled="atHeadOfList"
)
.card-carousel
.card-carousel--overflow-container
.card-carousel-cards(:style="{ transform: 'translateX' + '(' + currentOffset + 'px' + ')'}")
.card-carousel--card(v-for="item in items")
img(src="https://placehold.it/200x200")
.card-carousel--card--footer
p {{ item.name }}
p.tag(v-for="(tag,index) in item.tag" :class="index > 0 ? 'secondary' : ''") {{ tag }}
.card-carousel--nav__right(
@click="moveCarousel(1)"
:disabled="atEndOfList"
)
#app
carousel
CSS (Scss)
$vue-navy: #2c3e50;
$vue-navy-light: #3a5169;
$vue-teal: #42b883;
$vue-teal-light: #42b983;
$gray: #666a73;
$light-gray: #f8f8f8;
body {
background: $light-gray;
color: $vue-navy;
font-family: 'Source Sans Pro', sans-serif;
}
.card-carousel-wrapper {
display: flex;
align-items: center;
justify-content: center;
margin: 20px 0 40px;
color: $gray;
}
.card-carousel {
display: flex;
justify-content: center;
width: 640px;
&--overflow-container {
overflow: hidden;
}
&--nav__left,
&--nav__right {
display: inline-block;
width: 15px;
height: 15px;
padding: 10px;
box-sizing: border-box;
border-top: 2px solid $vue-teal;
border-right: 2px solid $vue-teal;
cursor: pointer;
margin: 0 20px;
transition: transform 150ms linear;
&[disabled] {
opacity: 0.2;
border-color: black;
}
}
&--nav__left {
transform: rotate(-135deg);
&:active {
transform: rotate(-135deg) scale(0.9);
}
}
&--nav__right {
transform: rotate(45deg);
&:active {
transform: rotate(45deg) scale(0.9);
}
}
}
.card-carousel-cards {
display: flex;
transition: transform 150ms ease-out;
transform: translatex(0px);
.card-carousel--card {
margin: 0 10px;
cursor: pointer;
box-shadow: 0 4px 15px 0 rgba(40,44,53,.06), 0 2px 2px 0 rgba(40,44,53,.08);
background-color: #fff;
border-radius: 4px;
z-index: 3;
margin-bottom: 2px;
&:first-child {
margin-left: 0;
}
&:last-child {
margin-right: 0;
}
img {
vertical-align: bottom;
border-top-left-radius: 4px;
border-top-right-radius: 4px;
transition: opacity 150ms linear;
user-select: none;
&:hover {
opacity: 0.5;
}
}
&--footer {
border-top: 0;
padding: 7px 15px;
p {
padding: 3px 0;
margin: 0;
margin-bottom: 2px;
font-size: 19px;
font-weight: 500;
color: $vue-navy;
user-select: none;
&.tag {
font-size: 11px;
font-weight: 300;
padding: 4px;
background: rgba(40,44,53,.06);
display: inline-block;
position: relative;
margin-left: 4px;
color: $gray;
&:before {
content:"";
float:left;
position:absolute;
top:0;
left: -12px;
width:0;
height:0;
border-color:transparent rgba(40,44,53,.06) transparent transparent;
border-style:solid;
border-width:8px 12px 12px 0;
}
&.secondary {
margin-left: 0;
border-left: 1.45px dashed white;
&:before {
display: none !important;
}
}
&:after {
content:"";
position:absolute;
top:8px;
left:-3px;
float:left;
width:4px;
height:4px;
border-radius: 2px;
background: white;
box-shadow:-0px -0px 0px #004977;
}
}
}
}
}
}
h1 {
font-size: 3.6em;
font-weight: 100;
text-align: center;
margin-bottom: 0;
color: $vue-teal;
}
JS
Vue.component("carousel", {
template: "#v-carousel",
data() {
return {
currentOffset: 0,
windowSize: 3,
paginationFactor: 220,
items: [
{name: 'Kin Khao', tag: ["Thai"]},
{name: 'Jū-Ni', tag: ["Sushi", "Japanese", "$$$$"]},
{name: 'Delfina', tag: ["Pizza", "Casual"]},
{name: 'San Tung', tag: ["Chinese", "$$"]},
{name: 'Anchor Oyster Bar', tag: ["Seafood", "Cioppino"]},
{name: 'Locanda', tag: ["Italian"]},
{name: 'Garden Creamery', tag: ["Ice cream"]},
]
}
},
computed: {
atEndOfList() {
return this.currentOffset <= (this.paginationFactor * -1) * (this.items.length - this.windowSize);
},
atHeadOfList() {
return this.currentOffset === 0;
},
},
methods: {
moveCarousel(direction) {
// Find a more elegant way to express the :style. consider using props to make it truly generic
if (direction === 1 && !this.atEndOfList) {
this.currentOffset -= this.paginationFactor;
} else if (direction === -1 && !this.atHeadOfList) {
this.currentOffset += this.paginationFactor;
}
},
}
});
new Vue({
el:"#app"
});
编辑:抱歉没有尽快回复,因为我这几天很忙