@Dobromir Good point! Ok here goes, and maybe this can serve as a time for some QA on what I’ve done to. Happy for improvement suggestions
Problem
I want to create a custom, re-usable component that follows Vue.js conventions as well as Quasar conventions, where they apply.
To add context, many online forums, articles & posts at the time of this post’s writing focus on use if the template
property within a component definition, which has caused a runtime error unless set up correctly.
Solution
Parent component
<template><!-- use of tag-based templating within this parent component -->
<div><!-- single root node, required -->
<h1>A Route View</h1>
<h2>Here is a custom component:</h2>
<!--
this component differs from the basic input component provided by
Vue.js and Quasar in that it will contain a button which can be used to
auto-populate the input value with the return value of supplied function.
for this example, i have not implemented the supplied function part.
-->
<child-component
label="My Label"
componentclasses="floating-label"
inputclasses="full-width"
></child-component>
</div>
</template>
<script>
// import our custom component to use within this component
import ChildComponent from '../ChildComponent'
export default {
name: 'ParentComponent',
// be sure to list our custom component here, i've used kebab-case here as
// the name to be used in the above <template> definition. ComponentCamelCase
// is used for the actual component definition
components: {
'child-component': ChildComponent
}
}
</script>
Child component
<template><!-- use of tag-based templating within this child component -->
<div :class="componentclasses">
<input :required="required" :class="inputclasses" v-model="model" :disabled="disable">
<label v-show="label">{{label}}</label>
<a @click="generateValue()" class="icon icon-generate"></a>
</div>
</template>
<script>
export default {
methods: {
/**
* Given a generator function, this component's inputValue is set
* to the return value of the generator.
*
* @param Function
**/
generateValue: function (generator) {
// set this component's value prop as result of supplied generator function
return
}
},
props: {
'value': String,
'required': Boolean,
'disable': Boolean,
'label': String,
'inputclasses': String,
'componentclasses': String
},
computed: {
model: {
get () {
return this.value
},
set (value) {
this.$emit('input', value)
}
}
}
}
</script>
<style>
.icon-generate {
float:right;
width:16px;
height:16px;
border:1px dashed red;
}
</style>
Recap
Counter to tutorials & posts I’ve read through, no template
property on ChildComponent
is used, instead tag-based templating combined with component names & importing are used.
My original post asked about installing components in some official way, as with Quasar components via quasar/src/install.js
, but nothing was needed.
Screenshot
Final note
If anyone can offer suggestions around that ChildComponent
being able to accept a per-instance generator
function into it’s generateValue
method - your help would be much appreciated.
To illustrate my needs by example, the parent component, when including the child, might want to auto-populate the input field with a name picked randomly from a default set of names. I can’t directly add that logic into the child component because then it only has a single use. I might also want to use that child component again and be able to pass a different function into generateValue
which returns a fruit picked randomly from a default set of fruits.