1+ <template >
2+ <div class =" vue-tiny-pagination" >
3+ <ul class =" tiny-pagination" :class =" customClass" >
4+ <li class =" page-item" :class =" classFirstPage" >
5+ <a class =" btn-prev-page" href =" #" @click.prevent =" lastPage" >{{translation.prev}}</a >
6+ </li >
7+ <li class =" page-item" >
8+ <span >{{titlePage}}</span >
9+ </li >
10+ <li class =" page-item" :class =" classLastPage" >
11+ <a class =" btn-next-page" href =" #" @click.prevent =" nextPage" >{{translation.next}}</a >
12+ </li >
13+ <li v-if =" showLimit" class =" page-item" >
14+ <select class =" tiny-form-select" v-model =" currentLimit" @change =" onLimitChange" >
15+ <option
16+ v-for =" (limit, index) in limits"
17+ :value =" limit"
18+ :key =" index" >{{limit}}/{{translation.title}}</option >
19+ </select >
20+ </li >
21+ </ul >
22+ </div >
23+ </template >
24+
25+ <script >
26+ export default {
27+ name: ' TinyPagination' ,
28+ props: {
29+ total: {
30+ type: Number ,
31+ required: true ,
32+ },
33+ page: {
34+ type: Number ,
35+ default: 1 ,
36+ },
37+ lang: {
38+ type: String ,
39+ default: ' en' ,
40+ },
41+ customClass: {
42+ type: String ,
43+ },
44+ limits: {
45+ type: Array ,
46+ default () {
47+ return [10 , 15 , 20 , 50 , 100 ];
48+ },
49+ },
50+ showLimit: {
51+ type: Boolean ,
52+ default: true ,
53+ }
54+ },
55+ data () {
56+ return {
57+ version: ' 0.2.1' ,
58+ currentPage: 1 ,
59+ currentLimit: 10 ,
60+ translations: {
61+ en: {
62+ prev: ' Previous' ,
63+ title: ' Page' ,
64+ next: ' Next' ,
65+ },
66+ es: {
67+ prev: ' Anterior' ,
68+ title: ' Página' ,
69+ next: ' Siguiente' ,
70+ }
71+ },
72+ availableLanguages: [' en' , ' es' ],
73+ };
74+ },
75+ created () {
76+ this .currentPage = this .page
77+ },
78+ computed: {
79+ translation () {
80+ return (this .availableLanguages .includes (this .lang )) ?
81+ this .translations [this .lang ]
82+ : this .translations [' en' ]
83+ },
84+ totalPages () {
85+ return Math .ceil (this .total / this .currentLimit )
86+ },
87+ titlePage () {
88+ return ` ${ this .translation .title } ${ this .currentPage } `
89+ },
90+ classFirstPage () {
91+ return {
92+ disabled: (this .currentPage === 1 ),
93+ ' c-not-allowed' : true
94+ }
95+ },
96+ classLastPage () {
97+ return {
98+ disabled: (this .currentPage === this .totalPages ),
99+ ' c-not-allowed' : true
100+ }
101+ }
102+ },
103+ methods: {
104+ nextPage () {
105+ if (this .currentPage !== this .totalPages ) {
106+ this .currentPage += 1
107+ }
108+ },
109+ lastPage () {
110+ if (this .currentPage > 1 ) {
111+ this .currentPage -= 1
112+ }
113+ },
114+ onLimitChange () {
115+ this .currentPage = 1
116+ }
117+ },
118+ watch: {
119+ currentPage (value ) {
120+ this .$emit (' tiny:change-page' , {
121+ page: value
122+ })
123+ },
124+ currentLimit (value ) {
125+ this .$emit (' tiny:change-limit' , {
126+ limit: value
127+ })
128+ }
129+ }
130+ }
131+ </script >
132+
133+ <style lang="scss">
134+ // Pagination
135+ .tiny-pagination {
136+ font-family : -apple-system , system-ui , BlinkMacSystemFont, " Segoe UI" , Roboto, " Helvetica Neue" , sans-serif ;
137+ display : flex ;
138+ list-style : none ;
139+ margin : .2rem 0 ;
140+ padding : .2rem 0 ;
141+
142+ .page-item {
143+ margin : .2rem .05rem ;
144+
145+ span {
146+ display : inline-block ;
147+ padding : .2rem .2rem ;
148+ }
149+
150+ a {
151+ border-radius : .1rem ;
152+ color : #667189 ;
153+ display : inline-block ;
154+ padding : .2rem .4rem ;
155+ text-decoration : none ;
156+ & :focus ,
157+ & :hover {
158+ color : #5755d9 ;
159+ }
160+ }
161+
162+ & .disabled {
163+ a {
164+ cursor : default ;
165+ opacity : .5 ;
166+ pointer-events : none ;
167+ }
168+ }
169+
170+ & .active {
171+ a {
172+ background : #5755d9 ;
173+ color : #fff ;
174+ }
175+ }
176+
177+ & .page-prev ,
178+ & .page-next {
179+ flex : 1 0 50% ;
180+ }
181+
182+ & .page-next {
183+ text-align : right ;
184+ }
185+
186+ .page-item-title {
187+ margin : 0 ;
188+ }
189+
190+ .page-item-subtitle {
191+ margin : 0 ;
192+ opacity : .5 ;
193+ }
194+ }
195+
196+ .tiny-form-select {
197+ -webkit-appearance : none ;
198+ -moz-appearance : none ;
199+ appearance : none ;
200+ text-transform : lowercase ;
201+ border : .05rem solid #caced7 ;
202+ border-radius : .1rem ;
203+ font-size : .8rem ;
204+ height : 1.8rem ;
205+ line-height : 1rem ;
206+ outline : none ;
207+ padding : .35rem .4rem ;
208+ vertical-align : middle ;
209+ width : 100% ;
210+ & :focus {
211+ border-color : #5755d9 ;
212+ box-shadow : 0 0 0 0.1rem rgba (87 , 85 , 217 , .2 )
213+ }
214+ }
215+
216+ .tiny-form-select :not ([multiple ]):not ([size ]) {
217+ background : #fff url (' data:image/svg+xml;charset=utf8,%3Csvg%20xmlns="http://www.w3.org/2000/svg"…path%20fill="%23667189"%20d="M2%200L0%202h4zm0%205L0%203h4z"/%3E%3C/svg%3E' ) no-repeat right .35rem center / .4rem .5rem ;
218+ padding-right : 1.2rem ;
219+ }
220+ }
221+ </style >
0 commit comments