169 lines
5.1 KiB
Vue
169 lines
5.1 KiB
Vue
![]() |
<template>
|
||
|
<div class="row form-group mt-3" :key="$attrs.key">
|
||
|
<label
|
||
|
:for="localFormElement.key"
|
||
|
:class="$attrs.labelClass ?? 'col-md-3'"
|
||
|
>{{ localFormElement.label }}</label
|
||
|
>
|
||
|
|
||
|
<vue-tribute
|
||
|
:options="tributeOptions"
|
||
|
:class="[$attrs.inputClass ?? ' col-md-9', { error: hasError }]"
|
||
|
class="mt-2"
|
||
|
>
|
||
|
<input
|
||
|
@focus="clearErrors"
|
||
|
@blur="validate"
|
||
|
@input="$emit('oninput', $event)"
|
||
|
@tribute-no-match="noMatchFound"
|
||
|
@tribute-replaced="textReplaced"
|
||
|
class="form-control tribute in-advanced-search"
|
||
|
:placeholder="localFormElement.placeholder"
|
||
|
:type="localFormElement.type"
|
||
|
:id="localFormElement.key"
|
||
|
:name="localFormElement.key"
|
||
|
v-model="textValue"
|
||
|
/>
|
||
|
</vue-tribute>
|
||
|
</div>
|
||
|
</template>
|
||
|
|
||
|
<script>
|
||
|
import VueTribute from "vue-tribute";
|
||
|
import formBuilderMixin from "@mixins/formBuilderMixin";
|
||
|
export default {
|
||
|
mixins: [formBuilderMixin],
|
||
|
data() {
|
||
|
return {
|
||
|
tributeOptions: {
|
||
|
// symbol or string that starts the lookup
|
||
|
trigger: "",
|
||
|
|
||
|
// element to target for @mentions
|
||
|
iframe: null,
|
||
|
|
||
|
// class added in the flyout menu for active item
|
||
|
selectClass: "highlight",
|
||
|
|
||
|
// class added to the menu container
|
||
|
containerClass: "tribute-container mini tribute-component",
|
||
|
|
||
|
// class added to each list item
|
||
|
itemClass: "my-tribute-class",
|
||
|
|
||
|
// function called on select that returns the content to insert
|
||
|
selectTemplate: function (item) {
|
||
|
return item.original.value;
|
||
|
// return "@" + item.original.value;
|
||
|
},
|
||
|
|
||
|
// template for displaying item in menu
|
||
|
menuItemTemplate: function (item) {
|
||
|
return item.string;
|
||
|
},
|
||
|
|
||
|
// template for when no match is found (optional),
|
||
|
// If no template is provided, menu is hidden.
|
||
|
noMatchTemplate:
|
||
|
'<span class="no-result">مورد مشابهی ثبت نشده است.</span>',
|
||
|
|
||
|
// specify an alternative parent container for the menu
|
||
|
// container must be a positioned element for the menu to appear correctly ie. `position: relative;`
|
||
|
// default container is the body
|
||
|
menuContainer: document.body,
|
||
|
|
||
|
// column to search against in the object (accepts function or string)
|
||
|
lookup: "key",
|
||
|
|
||
|
// column that contains the content to insert by default
|
||
|
fillAttr: "value",
|
||
|
|
||
|
// REQUIRED: array of objects to match or a function that returns data (see 'Loading remote data' for an example)
|
||
|
// values: [
|
||
|
// {
|
||
|
// key: "سلام",
|
||
|
// value: "سلام",
|
||
|
// },
|
||
|
// {
|
||
|
// key: "باسلام",
|
||
|
// value: "باسلام",
|
||
|
// },
|
||
|
// {
|
||
|
// key: "علیک سلام",
|
||
|
// value: "علیک سلام",
|
||
|
// },
|
||
|
// {
|
||
|
// key: "بی سلام",
|
||
|
// value: "بی سلام",
|
||
|
// },
|
||
|
// {
|
||
|
// key: "صدتا سلام",
|
||
|
// value: "صدتا سلام",
|
||
|
// },
|
||
|
// ],
|
||
|
// values: ["سلام", "باسلام", "علیک سلام", "بی سلام", "صدتا سلام"],
|
||
|
values: (text, cb) => {
|
||
|
this.remoteSearch(text, (items) => cb(items));
|
||
|
},
|
||
|
// When your values function is async, an optional loading template to show
|
||
|
loadingItemTemplate: null,
|
||
|
|
||
|
// specify whether a space is required before the trigger string
|
||
|
requireLeadingSpace: true,
|
||
|
|
||
|
// specify whether a space is allowed in the middle of mentions
|
||
|
allowSpaces: true,
|
||
|
|
||
|
// optionally specify a custom suffix for the replace text
|
||
|
// (defaults to empty space if undefined)
|
||
|
// replaceTextSuffix: "",
|
||
|
|
||
|
// specify whether the menu should be positioned. Set to false and use in conjuction with menuContainer to create an inline menu
|
||
|
// (defaults to true)
|
||
|
positionMenu: true,
|
||
|
|
||
|
// when the spacebar is hit, select the current match
|
||
|
spaceSelectsMatch: false,
|
||
|
|
||
|
// turn tribute into an autocomplete
|
||
|
autocompleteMode: true,
|
||
|
|
||
|
// Customize the elements used to wrap matched strings within the results list
|
||
|
// defaults to <span></span> if undefined
|
||
|
searchOpts: {
|
||
|
pre: "<span>",
|
||
|
post: "</span>",
|
||
|
skip: false, // true will skip local search, useful if doing server-side search
|
||
|
},
|
||
|
|
||
|
// Limits the number of items in the menu
|
||
|
menuItemLimit: 25,
|
||
|
|
||
|
// specify the minimum number of characters that must be typed before menu appears
|
||
|
menuShowMinLength: 0,
|
||
|
},
|
||
|
};
|
||
|
},
|
||
|
methods: {
|
||
|
remoteSearch(text, cb) {
|
||
|
this.$emit("tribute-on-search", {
|
||
|
text,
|
||
|
cb,
|
||
|
item: this.localFormElement,
|
||
|
});
|
||
|
},
|
||
|
noMatchFound(args) {
|
||
|
// console.info(args);
|
||
|
},
|
||
|
textReplaced(args) {
|
||
|
// console.info(args);
|
||
|
},
|
||
|
},
|
||
|
components: {
|
||
|
VueTribute: () =>
|
||
|
import( "vue-tribute"),
|
||
|
},
|
||
|
};
|
||
|
</script>
|
||
|
<style scoped lang="scss"></style>
|