Initiated PickList component

pull/41/head
cagataycivici 2019-07-18 23:29:20 +03:00
parent ac6098ddd8
commit 094c52e6fc
9 changed files with 879 additions and 4 deletions

View File

@ -60,6 +60,7 @@
<router-link to="/fullcalendar">&#9679; FullCalendar</router-link>
<router-link to="/orderlist">&#9679; OrderList</router-link>
<router-link to="/paginator">&#9679; Paginator</router-link>
<router-link to="/picklist">&#9679; PickList</router-link>
</div>
</div>
</transition>

14
src/components/picklist/PickList.d.ts vendored Normal file
View File

@ -0,0 +1,14 @@
import Vue, {VNode} from 'vue';
export declare class PickList extends Vue {
value?: any[];
dataKey?: string;
selection?: any[];
metaKeySelection?: boolean;
listStyle?: any;
$emit(eventName: 'reorder', e: { originalEvent: Event, value: any[]; direction: string}): this;
$slots: {
header: VNode[];
item: VNode[];
}
}

View File

@ -0,0 +1,554 @@
<template>
<div class="p-picklist p-component p-picklist-responsive">
<div class="p-picklist-buttons p-picklist-source-controls">
<div class="p-picklist-buttons-cell">
<OLButton type="button" icon="pi pi-angle-up" @click="moveUp($event, 0)"></OLButton>
<OLButton type="button" icon="pi pi-angle-double-up" @click="moveTop($event, 0)"></OLButton>
<OLButton type="button" icon="pi pi-angle-down" @click="moveDown($event, 0)"></OLButton>
<OLButton type="button" icon="pi pi-angle-double-down" @click="moveBottom($event, 0)"></OLButton>
</div>
</div>
<div class="p-picklist-list-wrapper p-picklist-source-wrapper">
<div class="p-picklist-caption" v-if="$slots.header">
<slot name="sourceHeader"></slot>
</div>
<transition-group ref="sourceList" name="p-picklist-flip" tag="ul" class="p-picklist-list p-picklist-source" :style="listStyle">
<template v-for="(item, i) of sourceList">
<li tabindex="0" :key="getItemKey(item, i)" :class="['p-picklist-item', {'p-highlight': isSelected(item, 0)}]"
@click="onItemClick($event, item, i, 0)" @keydown="onItemKeyDown($event, item, i, 0)" @touchend="onItemTouchEnd">
<slot name="item" :item="item" :index="i"> </slot>
</li>
</template>
</transition-group>
</div>
<div class="p-picklist-buttons">
<div class="p-picklist-buttons-cell">
<OLButton type="button" icon="pi pi-angle-right" @click="moveToTarget"></OLButton>
<OLButton type="button" icon="pi pi-angle-double-right" @click="moveAllToTarget"></OLButton>
<OLButton type="button" icon="pi pi-angle-left" @click="moveToSource"></OLButton>
<OLButton type="button" icon="pi pi-angle-double-left" @click="moveAllToSource"></OLButton>
</div>
</div>
<div class="p-picklist-list-wrapper p-picklist-target-wrapper">
<div class="p-picklist-caption" v-if="$slots.header">
<slot name="targetHeader"></slot>
</div>
<transition-group ref="targetList" name="p-picklist-flip" tag="ul" class="p-picklist-list p-picklist-target" :style="listStyle">
<template v-for="(item, i) of targetList">
<li tabindex="0" :key="getItemKey(item, i)" :class="['p-picklist-item', {'p-highlight': isSelected(item, 1)}]"
@click="onItemClick($event, item, i, 1)" @keydown="onItemKeyDown($event, item, i, 1)" @touchend="onItemTouchEnd">
<slot name="item" :item="item" :index="i"> </slot>
</li>
</template>
</transition-group>
</div>
<div class="p-picklist-buttons p-picklist-target-controls">
<div class="p-picklist-buttons-cell">
<OLButton type="button" icon="pi pi-angle-up" @click="moveUp($event, 1)"></OLButton>
<OLButton type="button" icon="pi pi-angle-double-up" @click="moveTop($event, 1)"></OLButton>
<OLButton type="button" icon="pi pi-angle-down" @click="moveDown($event, 1)"></OLButton>
<OLButton type="button" icon="pi pi-angle-double-down" @click="moveBottom($event, 1)"></OLButton>
</div>
</div>
</div>
</template>
<script>
import Button from '../button/Button';
import ObjectUtils from '../utils/ObjectUtils';
import DomHandler from '../utils/DomHandler';
export default {
props: {
value: {
type: Array,
default: () => [[],[]]
},
selection: {
type: Array,
default: () => [[],[]]
},
dataKey: {
type: String,
default: null
},
listStyle: {
type: null,
default: null
},
metaKeySelection: {
type: Boolean,
default: true
}
},
itemTouched: false,
reorderDirection: null,
data() {
return {
d_selection: this.selection
}
},
updated() {
if (this.reorderDirection) {
this.updateListScroll(this.$refs.sourceList.$el);
this.updateListScroll(this.$refs.targetList.$el);
this.reorderDirection = null;
}
},
watch: {
selection(newValue) {
this.d_selection = this.selection;
}
},
methods: {
getItemKey(item, index) {
return this.dataKey ? ObjectUtils.resolveFieldData(item, this.dataKey): index;
},
isSelected(item, listIndex) {
return ObjectUtils.findIndexInList(item, this.d_selection[listIndex]) != -1;
},
moveUp(event, listIndex) {
if (this.d_selection && this.d_selection[listIndex]) {
let valueList = [...this.value[listIndex]];
let selectionList = this.d_selection[listIndex];
for (let i = 0; i < selectionList.length; i++) {
let selectedItem = selectionList[i];
let selectedItemIndex = ObjectUtils.findIndexInList(selectedItem, valueList);
if (selectedItemIndex !== 0) {
let movedItem = valueList[selectedItemIndex];
let temp = valueList[selectedItemIndex - 1];
valueList[selectedItemIndex - 1] = movedItem;
valueList[selectedItemIndex] = temp;
}
else {
break;
}
}
let value = [...this.value];
value[listIndex] = valueList;
this.reorderDirection = 'up';
this.$emit('input', value);
this.$emit('reorder', {
originalEvent: event,
value: value,
direction: this.reorderDirection
});
}
},
moveTop(event, listIndex) {
if(this.d_selection) {
let valueList = [...this.value[listIndex]];
let selectionList = this.d_selection[listIndex];
for (let i = 0; i < selectionList.length; i++) {
let selectedItem = selectionList[i];
let selectedItemIndex = ObjectUtils.findIndexInList(selectedItem, valueList);
if (selectedItemIndex !== 0) {
let movedItem = valueList.splice(selectedItemIndex, 1)[0];
valueList.unshift(movedItem);
}
else {
break;
}
}
let value = [...this.value];
value[listIndex] = valueList;
this.reorderDirection = 'top';
this.$emit('input', value);
this.$emit('reorder', {
originalEvent: event,
value: value,
direction: this.reorderDirection
});
}
},
moveDown(event, listIndex) {
if(this.d_selection) {
let valueList = [...this.value[listIndex]];
let selectionList = this.d_selection[listIndex];
for (let i = selectionList.length - 1; i >= 0; i--) {
let selectedItem = selectionList[i];
let selectedItemIndex = ObjectUtils.findIndexInList(selectedItem, valueList);
if (selectedItemIndex !== (valueList.length - 1)) {
let movedItem = valueList[selectedItemIndex];
let temp = valueList[selectedItemIndex + 1];
valueList[selectedItemIndex + 1] = movedItem;
valueList[selectedItemIndex] = temp;
}
else {
break;
}
}
let value = [...this.value];
value[listIndex] = valueList;
this.reorderDirection = 'down';
this.$emit('input', value);
this.$emit('reorder', {
originalEvent: event,
value: value,
direction: this.reorderDirection
});
}
},
moveBottom(event, listIndex) {
if (this.d_selection) {
let valueList = [...this.value[listIndex]];
let selectionList = this.d_selection[listIndex];
for (let i = selectionList.length - 1; i >= 0; i--) {
let selectedItem = selectionList[i];
let selectedItemIndex = ObjectUtils.findIndexInList(selectedItem, valueList);
if (selectedItemIndex !== (valueList.length - 1)) {
let movedItem = valueList.splice(selectedItemIndex, 1)[0];
valueList.push(movedItem);
}
else {
break;
}
}
let value = [...this.value];
value[listIndex] = valueList;
this.reorderDirection = 'bottom';
this.$emit('input', value);
this.$emit('reorder', {
originalEvent: event,
value: value,
direction: this.reorderDirection
});
}
},
moveToTarget(event) {
let selection = this.d_selection && this.d_selection[0] ? this.d_selection[0] : null;
let sourceList = [...this.value[0]];
let targetList = [...this.value[1]];
if (selection) {
for (let i = 0; i < selection.length; i++) {
let selectedItem = selection[i];
if (ObjectUtils.findIndexInList(selectedItem, targetList) == -1) {
targetList.push(sourceList.splice(ObjectUtils.findIndexInList(selectedItem, sourceList),1)[0]);
}
}
let value = [...this.value];
value[0] = sourceList;
value[1] = targetList;
this.$emit('input', value);
this.$emit('move-to-target', {
originalEvent: event,
items: selection
});
this.d_selection[0] = [];
this.$emit('update:selection', this.d_selection);
this.$emit('selection-change', {
originalEvent: event,
value: this.d_selection
});
}
},
moveAllToTarget(event) {
if (this.value[0]) {
let sourceList = [...this.value[0]];
let targetList = [...this.value[1]];
this.$emit('move-all-to-target', {
originalEvent: event,
items: sourceList
});
targetList = [...targetList, ...sourceList];
sourceList = [];
let value = [...this.value];
value[0] = sourceList;
value[1] = targetList;
this.$emit('input', value);
this.d_selection[0] = [];
this.$emit('update:selection', this.d_selection);
this.$emit('selection-change', {
originalEvent: event,
value: this.d_selection
});
}
},
moveToSource(event) {
let selection = this.d_selection && this.d_selection[1] ? this.d_selection[1] : null;
let sourceList = [...this.value[0]];
let targetList = [...this.value[1]];
if (selection) {
for (let i = 0; i < selection.length; i++) {
let selectedItem = selection[i];
if (ObjectUtils.findIndexInList(selectedItem, sourceList) == -1) {
sourceList.push(targetList.splice(ObjectUtils.findIndexInList(selectedItem, targetList),1)[0]);
}
}
let value = [...this.value];
value[0] = sourceList;
value[1] = targetList;
this.$emit('input', value);
this.$emit('move-to-source', {
originalEvent: event,
items: selection
});
this.d_selection[1] = [];
this.$emit('update:selection', this.d_selection);
this.$emit('selection-change', {
originalEvent: event,
value: this.d_selection
});
}
},
moveAllToSource(event) {
if (this.value[1]) {
let sourceList = [...this.value[0]];
let targetList = [...this.value[1]];
this.$emit('move-all-to-source', {
originalEvent: event,
items: sourceList
});
sourceList = [...sourceList, ...targetList];
targetList = [];
let value = [...this.value];
value[0] = sourceList;
value[1] = targetList;
this.$emit('input', value);
this.d_selection[1] = [];
this.$emit('update:selection', this.d_selection);
this.$emit('selection-change', {
originalEvent: event,
value: this.d_selection
});
}
},
onItemClick(event, item, index, listIndex) {
this.itemTouched = false;
const selectionList = this.d_selection[listIndex];
const selectedIndex = ObjectUtils.findIndexInList(item, selectionList);
const selected = (selectedIndex != -1);
const metaSelection = this.itemTouched ? false : this.metaKeySelection;
let _selection;
if (metaSelection) {
let metaKey = (event.metaKey || event.ctrlKey);
if (selected && metaKey) {
_selection = selectionList.filter((val, index) => index !== selectedIndex);
}
else {
_selection = (metaKey) ? selectionList ? [...selectionList] : [] : [];
_selection.push(item);
}
}
else {
if (selected) {
_selection = selectionList.filter((val, index) => index !== selectedIndex);
}
else {
_selection = selectionList ? [...selectionList] : [];
_selection.push(item);
}
}
let newSelection = [...this.d_selection];
newSelection[listIndex] = _selection;
this.d_selection = newSelection;
this.$emit('update:selection', this.d_selection);
this.$emit('selection-change', {
originalEvent:event,
value: this.d_selection
});
},
onItemTouchEnd() {
this.itemTouched = true;
},
onItemKeyDown(event, item, index) {
let listItem = event.currentTarget;
switch(event.which) {
//down
case 40:
var nextItem = this.findNextItem(listItem);
if (nextItem) {
nextItem.focus();
}
event.preventDefault();
break;
//up
case 38:
var prevItem = this.findPrevItem(listItem);
if (prevItem) {
prevItem.focus();
}
event.preventDefault();
break;
//enter
case 13:
this.onItemClick(event, item, index);
event.preventDefault();
break;
default:
break;
}
},
findNextItem(item) {
let nextItem = item.nextElementSibling;
if (nextItem)
return !DomHandler.hasClass(nextItem, 'p-picklist-item') ? this.findNextItem(nextItem) : nextItem;
else
return null;
},
findPrevItem(item) {
let prevItem = item.previousElementSibling;
if (prevItem)
return !DomHandler.hasClass(prevItem, 'p-picklist-item') ? this.findPrevItem(prevItem) : prevItem;
else
return null;
},
updateListScroll(listElement) {
const listItems = DomHandler.find(listElement, '.p-picklist-item.p-highlight');
if (listItems && listItems.length) {
switch(this.reorderDirection) {
case 'up':
DomHandler.scrollInView(listElement, listItems[0]);
break;
case 'top':
listElement.scrollTop = 0;
break;
case 'down':
DomHandler.scrollInView(listElement, listItems[listItems.length - 1]);
break;
case 'bottom':
listElement.scrollTop = listElement.scrollHeight;
break;
default:
break;
}
}
}
},
computed: {
sourceList() {
return this.value && this.value[0] ? this.value[0] : null;
},
targetList() {
return this.value && this.value[1] ? this.value[1] : null;
}
},
components: {
'OLButton': Button
}
}
</script>
<style>
.p-picklist {
display: flex;
flex-wrap: wrap;
}
.p-picklist-buttons,
.p-picklist-list-wrapper {
flex: 0 0 auto;
}
.p-picklist-buttons {
padding: 0 .25em;
width: 10%;
align-self: center;
}
.p-picklist-buttons .p-button.p-button-icon-only {
display: block;
margin-bottom: 0.25em;
width: 100%;
}
.p-picklist-list-wrapper {
width: 35%;
}
.p-picklist-list {
list-style-type: none;
margin: 0;
padding: 0;
overflow:auto;
height: 12.5em;
}
.p-picklist-caption {
text-align: center;
padding: .5em .75em;
border-bottom: 0 none;
}
.p-picklist-item {
margin: 1px;
padding: .125em;
cursor: pointer;
border: 0 none;
font-weight: inherit;
}
.p-picklist-item.p-picklist-flip-enter-active.p-picklist-flip-enter-to,
.p-picklist-item.p-picklist-flip-leave-active.p-picklist-flip-leave-to {
transition: none;
}
@media (max-width: 767px) {
.p-picklist-buttons {
width: 100%;
text-align: center;
}
.p-picklist-list-wrapper {
width: 100%;
}
.p-picklist-buttons .p-button.p-button-icon-only {
display: inline-block;
width: 20%;
margin-right: .25em;
}
}
</style>

View File

@ -31,6 +31,7 @@ import OverlayPanel from './components/overlaypanel/OverlayPanel';
import Paginator from './components/paginator/Paginator';
import Panel from './components/panel/Panel';
import Password from './components/password/Password';
import PickList from './components/picklist/PickList';
import ProgressBar from './components/progressbar/ProgressBar';
import Rating from './components/rating/Rating';
import RadioButton from './components/radiobutton/RadioButton';
@ -93,6 +94,7 @@ Vue.component('OverlayPanel', OverlayPanel);
Vue.component('Paginator', Paginator);
Vue.component('Panel', Panel);
Vue.component('Password', Password);
Vue.component('PickList', PickList);
Vue.component('ProgressBar', ProgressBar);
Vue.component('RadioButton', RadioButton);
Vue.component('Rating', Rating);

View File

@ -260,6 +260,11 @@ export default new Router({
path: '/panel',
name: 'panel',
component: () => import('./views/panel/PanelDemo.vue')
},
{
path: '/picklist',
name: 'picklist',
component: () => import('./views/picklist/PickListDemo.vue')
},
{
path: '/password',

View File

@ -8,7 +8,7 @@
</div>
<div class="content-section implementation">
<OrderList v-model="cars" header="List of Cars" listStyle="height:auto" dataKey="vin">
<OrderList v-model="cars" listStyle="height:auto" dataKey="vin">
<template #header>
List of Cars
</template>

View File

@ -14,7 +14,7 @@ import OrderList from 'primevue/orderlist';
</p>
<CodeHighlight>
<template v-pre>
&lt;OrderList v-model="cars" header="List of Cars" listStyle="height:auto" dataKey="vin"&gt;
&lt;OrderList v-model="cars" listStyle="height:auto" dataKey="vin"&gt;
&lt;template #header&gt;
List of Cars
&lt;/template&gt;
@ -37,7 +37,7 @@ import OrderList from 'primevue/orderlist';
<CodeHighlight>
<template v-pre>
&lt;OrderList v-model="cars" header="List of Cars" listStyle="height:auto" dataKey="vin" :dragdrop="true"&gt;
&lt;OrderList v-model="cars" listStyle="height:auto" dataKey="vin" :dragdrop="true"&gt;
&lt;template #header&gt;
List of Cars
&lt;/template&gt;
@ -164,7 +164,7 @@ import OrderList from 'primevue/orderlist';
</a>
<CodeHighlight>
<template v-pre>
&lt;OrderList v-model="cars" header="List of Cars" listStyle="height:auto" dataKey="vin"&gt;
&lt;OrderList v-model="cars" listStyle="height:auto" dataKey="vin"&gt;
&lt;template #header&gt;
List of Cars
&lt;/template&gt;

View File

@ -0,0 +1,74 @@
<template>
<div>
<div class="content-section introduction">
<div class="feature-intro">
<h1>PickList</h1>
<p>PickList is used to reorder items between different lists.</p>
</div>
</div>
<div class="content-section implementation">
<PickList v-model="cars" listStyle="height:342px" dataKey="vin">
<template #sourceHeader>
Available
</template>
<template #targetHeader>
Selected
</template>
<template #item="slotProps">
<div class="p-caritem">
<img :src="'demo/images/car/' + slotProps.item.brand + '.png'">
<div>{{slotProps.item.brand}} - {{slotProps.item.year}} - {{slotProps.item.color}}</div>
</div>
</template>
</PickList>
</div>
<PickListDoc />
</div>
</template>
<script>
import PickListDoc from './PickListDoc';
import CarService from '../../service/CarService';
export default {
data() {
return {
cars: null
}
},
carService: null,
created() {
this.carService = new CarService();
},
mounted() {
this.carService.getCarsSmall().then(data => this.cars = [data.slice(0,5),[]]);
},
components: {
'PickListDoc': PickListDoc
}
}
</script>
<style lang="scss" scoped>
.p-caritem {
&:after {
content: "";
display: table;
clear: both;
}
img {
display:inline-block;
margin:2px 0 2px 2px;
width: 48px;
height: 48px;
}
div {
font-size:14px;
float:right;
margin: 16px 6px 0 0;
}
}
</style>

View File

@ -0,0 +1,225 @@
<template>
<div class="content-section documentation">
<TabView>
<TabPanel header="Documentation">
<h3>Import</h3>
<CodeHighlight lang="javascript">
import OrderList from 'primevue/orderlist';
</CodeHighlight>
<h3>Getting Started</h3>
<p>OrderList requires an array as its value bound with the v-model directive and a template for its content.</p>
<p>Header of the component is defined with the "header" template and to define the content of an item in the list a named templated called "item" needs to be defined which gets the
<i>item</i> and the <i>index</i> via slotProps.
</p>
<CodeHighlight>
<template v-pre>
&lt;OrderList v-model="cars" header="List of Cars" listStyle="height:auto" dataKey="vin"&gt;
&lt;template #header&gt;
List of Cars
&lt;/template&gt;
&lt;template #item="slotProps"&gt;
&lt;div class="p-caritem"&gt;
&lt;img :src="'demo/images/car/' + slotProps.item.brand + '.png'"&gt;
&lt;div&gt;&#123;&#123;slotProps.item.brand&#125;&#125; - &#123;&#123;slotProps.item.year&#125;&#125; - &#123;&#123;slotProps.item.color&#125;&#125;&lt;/div&gt;
&lt;/div&gt;
&lt;/template&gt;
&lt;/OrderList&gt;
</template>
</CodeHighlight>
<h3>Selection</h3>
<p>In case you'd need to access the selected items in the list, define a binding to the <i>selection</i> property with the sync operator so that
it gets updated when the user makes a selection. Since it is two-way binding enabled, your changes to the selection will be reflected as well. Note that
this is optional and only necessary when you need to access the selection.</p>
<p>Use the sync operator to enable two-way binding.</p>
<CodeHighlight>
<template v-pre>
&lt;OrderList v-model="cars" header="List of Cars" listStyle="height:auto" dataKey="vin" :dragdrop="true"&gt;
&lt;template #header&gt;
List of Cars
&lt;/template&gt;
&lt;template #item="slotProps"&gt;
&lt;div class="p-caritem"&gt;
&lt;img :src="'demo/images/car/' + slotProps.item.brand + '.png'"&gt;
&lt;div&gt;&#123;&#123;slotProps.item.brand&#125;&#125; - &#123;&#123;slotProps.item.year&#125;&#125; - &#123;&#123;slotProps.item.color&#125;&#125;&lt;/div&gt;
&lt;/div&gt;
&lt;/template&gt;
&lt;/OrderList&gt;
</template>
</CodeHighlight>
<h3>DataKey</h3>
<p>It is recommended to provide the name of the field that uniquely identifies the a record in the data via the <i>dataKey</i> property for better performance.</p>
<h3>Properties</h3>
<p>Any attribute such as style and class are passed to the main container element. Following are the additional properties to configure the component.</p>
<div class="doc-tablewrapper">
<table class="doc-table">
<thead>
<tr>
<th>Name</th>
<th>Type</th>
<th>Default</th>
<th>Description</th>
</tr>
</thead>
<tbody>
<tr>
<td>value</td>
<td>array</td>
<td>null</td>
<td>Value of the component.</td>
</tr>
<tr>
<td>selection</td>
<td>any</td>
<td>null</td>
<td>Selected items in the list.</td>
</tr>
<tr>
<td>metaKeySelection</td>
<td>boolean</td>
<td>true</td>
<td>Defines whether metaKey is requred or not for the selection. <br/>
When true metaKey needs to be pressed to select or unselect an item and <br/>
when set to false selection of each item
can be toggled individually. On touch enabled devices, metaKeySelection is turned off automatically.</td>
</tr>
<tr>
<td>dataKey</td>
<td>string</td>
<td>null</td>
<td>Name of the field that uniquely identifies the a record in the data.</td>
</tr>
<tr>
<td>listStyle</td>
<td>object</td>
<td>null</td>
<td>Inline style of the the list element.</td>
</tr>
</tbody>
</table>
</div>
<h3>Events</h3>
<div class="doc-tablewrapper">
<table class="doc-table">
<thead>
<tr>
<th>Name</th>
<th>Parameters</th>
<th>Description</th>
</tr>
</thead>
<tbody>
<tr>
<td>reorder</td>
<td>event.originalEvent: browser event <br />
event.value: Ordered list <br />
event.direction: Direction of the change; "up", "down", "bottom", "top"
</td>
<td>Callback to invoke when the list is reordered.</td>
</tr>
</tbody>
</table>
</div>
<h3>Styling</h3>
<p>Following is the list of structural style classes, for theming classes visit <router-link to="/theming">theming</router-link> page.</p>
<div class="doc-tablewrapper">
<table class="doc-table">
<thead>
<tr>
<th>Name</th>
<th>Element</th>
</tr>
</thead>
<tbody>
<tr>
<td>p-orderlist</td>
<td>Container element.</td>
</tr>
<tr>
<td>p-orderlist-list</td>
<td>List container.</td>
</tr>
<tr>
<td>p-orderlist-item</td>
<td>An item in the list</td>
</tr>
</tbody>
</table>
</div>
<h3>Dependencies</h3>
<p>None.</p>
</TabPanel>
<TabPanel header="Source">
<a href="https://github.com/primefaces/primevue/tree/master/src/views/panel" class="btn-viewsource" target="_blank" rel="noopener noreferrer">
<span>View on GitHub</span>
</a>
<CodeHighlight>
<template v-pre>
&lt;OrderList v-model="cars" header="List of Cars" listStyle="height:auto" dataKey="vin"&gt;
&lt;template #header&gt;
List of Cars
&lt;/template&gt;
&lt;template #item="slotProps"&gt;
&lt;div class="p-caritem"&gt;
&lt;img :src="'demo/images/car/' + slotProps.item.brand + '.png'"&gt;
&lt;div&gt;&#123;&#123;slotProps.item.brand&#125;&#125; - &#123;&#123;slotProps.item.year&#125;&#125; - &#123;&#123;slotProps.item.color&#125;&#125;&lt;/div&gt;
&lt;/div&gt;
&lt;/template&gt;
&lt;/OrderList&gt;
</template>
</CodeHighlight>
<CodeHighlight lang="js">
import CarService from '../../service/CarService';
export default {
data() {
return {
cars: null
}
},
carService: null,
created() {
this.carService = new CarService();
},
mounted() {
this.carService.getCarsSmall().then(data => this.cars = data.slice(0,5));
}
}
</CodeHighlight>
<CodeHighlight lang="css">
.p-caritem {
&amp;:after {
content: "";
display: table;
clear: both;
}
img {
display:inline-block;
margin:2px 0 2px 2px;
width: 48px;
height: 48px;
}
div {
font-size:14px;
float:right;
margin: 16px 6px 0 0;
}
}
</CodeHighlight>
</TabPanel>
</TabView>
</div>
</template>