Custom components are existing components encapsulated based on service requirements. A custom component can be invoked multiple times in a project to improve the code readability. You can import a custom component to the host page through **element** as shown in the following code snippet:
Custom components are existing components encapsulated based on service requirements. A custom component can be invoked multiple times in a project to improve the code readability. You can introduce a custom component to the host page through **element** as shown in the following code snippet:
@@ -8,8 +9,8 @@ Custom components are existing components encapsulated based on service requirem
</div>
```
The following is an example of using a custom component with **if-else**, which displays **comp1** when **showComp1** is set to **true** and displays **comp2** otherwise.
The following is an example of using a custom component with **if-else**:
@@ -19,18 +20,142 @@ The following is an example of using a custom component with **if-else**:
</div>
```
The **name** attribute indicates the custom component name (optional), which is case-insensitive and is in lowercase by default. The **src** attribute indicates the **.hml** file path (mandatory) of the custom component. If **name** is not set, the **.hml** file name is used as the component name by default.
## Custom Events
To bind an event to a custom child component, use the **(on|@)event-name="bindParentVmMethod"** syntax. **this.$emit('eventName', { params: 'passedParameters' })** is used in the child component to trigger the event and pass parameters to the parent component. The parent component then calls the **bindParentVmMethod** API and receives parameters passed by the child component.
> **NOTE**
>
> For child component events that are named in camel case, convert the names to kebab case when binding the events to the parent component. For example, use **\@children-event** in the parent component instead of **childrenEvent** used in the child component.
**Example 1 with parameters passed**
The following example describes how to define a child component **comp**:
```html
<!-- comp.hml -->
<divclass="item">
<textclass="text-style"onclick="childClicked">Click here to view the hidden text.</text>
this.$emit('eventType1',{text:'Receive the parameters from the child component.'});
this.showObj=!this.showObj;
},
}
```
In the following example, the child component passes the **text** parameter to the parent component, and the parent component obtains the parameter through **e.detail**:
- The **name** attribute indicates the custom component name (optional), which is case-insensitive and is in lowercase by default. The **src** attribute indicates the **.hml** file path (mandatory) of the custom component. If **name** is not set, the **.hml** file name is used as the component name by default.
- Event binding: Use **(on|@)***child1* syntax to bind a child component event to a custom component. In the child component, use **this.$emit('***child1***', {params:'***parameter to pass***'})** for event triggering and value transferring. In the parent component, call **bindParentVmMethod** method and receive the parameters passed from the child component.
> **NOTE**
>
> For child component events that are named in camel case, convert the names to kebab case when binding the events to the parent component. For example, use **\@children-event** instead of **childrenEvent**: **\@children-event="bindParentVmMethod"**.
In the JS file of a custom component, you can define, pass, and process data by declaring fields such as **data**, **props**, and **computed**. For details about how to use **props** and **computed**, see [Data Transfer and Processing](js-components-custom-props.md).
| data | Object/Function | Data model of the page. If the attribute is of the function type, the return value must be of the object type. The attribute name cannot start with a dollar sign ($) or underscore (_). Do not use reserved words (**for**, **if**, **show**, and **tid**).<br>Do not use this attribute and **private** or **public** at the same time.(Rich) |
| props | Array/Object | Used for communication between components. This attribute can be transferred to components via **\<tag xxxx='value'>**. A **props** name must be in lowercase and cannot start with a dollar sign ($) or underscore (\_). Do not use reserved words (**for**, **if**, **show**, and **tid**). Currently, **props** does not support functions.|
| computed | Object | Used for pre-processing an object for reading and setting. The result is cached. The name cannot start with a dollar sign ($) or underscore (\_). Do not use reserved words.|
| data | Object\| Function | Data model of the page. If the attribute is of the function type, the return value must be of the object type. The name cannot start with a dollar sign ($) or underscore (\_). Do not use reserved words (**for**, **if**, **show**, and **tid**).<br>Do not use this attribute and **private** or **public** at the same time.|
| props | Array\| Object | Used for communication between components. This attribute can be passed to components through **\<tag xxxx='value'>**. A **props** name must be in lowercase and cannot start with a dollar sign ($) or underscore (_). Do not use reserved words (**for**, **if**, **show**, and **tid**) in the name. Currently, **props** does not support functions.|
| computed | Object | Used for pre-processing for reading and setting parameters. The result is cached. The name cannot start with a dollar sign ($) or underscore (\_). Do not use reserved words.|
You can use **props** to declare attributes of a custom component and pass the attributes to the child component. The supported types of **props** include String, Number, Boolean, Array, Object, and Function. Note that a camel case attribute name \(**compProp**\) should be converted to the kebab case format \(**comp-prop**\) when you reference the attribute in an external parent component. You can add **props** to a custom component, and pass the attribute to the child component.
```
## props
You can use **props** to declare attributes of a custom component and pass the attributes to the child component. The supported types of **props** include String, Number, Boolean, Array, Object, and Function. Note that a camel case attribute name (**compProp**) should be converted to the kebab case format (**comp-prop**) when you reference the attribute in an external parent component. The following is sample for adding **props** to a custom component and passing the attribute to the child component.
You can set the default value for a child component attribute via **default**. The default value is used if the parent component does not have **default** set. In this case, the **props** attribute must be in object format instead of an array.
```
```html
<!-- comp.hml -->
<divclass="item">
<textclass="title-style">{{title}}</text>
</div>
```
```
```js
// comp.js
exportdefault{
props:{
...
...
@@ -49,21 +53,21 @@ export default {
}
```
In this example, a **<text\>** component is added to display the title. The title content is a custom attribute, which displays the text specified by a user. If the user has not set a title, the default text will be displayed. Add the attribute when referencing the custom component.
In this example, a **\<text>** component is added to display the title. The title content is a custom attribute, which displays the text specified by a user. If the user has not set a title, the default text will be displayed. Add the attribute when referencing the custom component.
## Unidirectional Value Transfer<a name="section9681151218247"></a>
### Unidirectional Value Transfer
Data can be transferred only from the parent component to child components. You are not allowed to change the value passed to the child component. However, you can receive the value passed by **props** as a default value in **data**, and then change the **data** value.
```
```js
// comp.js
exportdefault{
props:['defaultCount'],
...
...
@@ -78,11 +82,11 @@ export default {
}
```
## Monitoring Data Changes by **$watch**<a name="section205821113182114"></a>
### Monitoring Data Changes by **$watch**
To listen for attribute changes in a component, you can use the **$watch** method to add a callback. The following code snippet shows how to use **$watch**:
To improve the development efficiency, you can use a computed property to pre-process an attribute in a custom component before reading or setting the attribute. In the **computed** field, you can set a getter or setter to be triggered when the attribute is read or written, respectively. The following is an example:
```
```js
// comp.js
exportdefault{
props:['title'],
...
...
@@ -129,5 +134,4 @@ export default {
}
```
The first computed property **message** has only a getter. The value of **message** changes depending on the **objTitle** value. The getter can only read but cannot set the value. You need a setter \(such as **notice** in the sample code\) to set the value of the computed property.
The first computed property **message** has only a getter. The value of **message** changes depending on the **objTitle** value. The getter can only read but cannot set the value (such as **time** defined during initialization in **data**). You need a setter (such as **notice** in the sample code) to set the value of the computed property.
>The APIs of this module are supported since API version 7. Updates will be marked with a superscript to indicate their earliest API version.
> **NOTE**
>
> The APIs of this module are supported since API version 7. Updates will be marked with a superscript to indicate their earliest API version.
## Default Slot<a name="section68133181214"></a>
You can use the **<slot\>** tag to create a slot inside a custom component to fill the content defined in the parent component. The sample code is as follows:
## Default Slot
```
You can use the **\<slot>** tag to create a slot inside a custom component to fill the content defined in the parent component. The sample code is as follows:
```html
<!-- comp.hml -->
<divclass="item">
<textclass="text-style">The following uses the content defined in the parent component.</text>
...
...
@@ -16,8 +18,7 @@ You can use the **<slot\>** tag to create a slot inside a custom component to
@@ -27,11 +28,12 @@ The following references the custom component:
</div>
```
## Named Slot<a name="section18337143291211"></a>
When multiple slots are need inside a custom component, you can name them, so that you can specify the slot in which you want to fill content by setting the **<name\>** attribute.
## Named Slot
```
When multiple slots are need inside a custom component, you can name them, so that you can specify the slot in which you want to fill content by setting the **<name>** attribute.
```html
<!-- comp.hml -->
<divclass="item">
<textclass="text-style">The following uses the content defined in the parent component.</text>
...
...
@@ -41,8 +43,7 @@ When multiple slots are need inside a custom component, you can name them, so th
| inherit-class | string | - | No | Class styles inherited from the parent component, separated by spaces.|
To enable a custom component to inherit the styles of its parent component, set the **inherit-calss** attribute for the custom component.
The example below is a code snippet in the HML file of the parent page that references a custom component named **comp**. This component uses the **inherit-class** attribute to inherit the styles of its parent component: **parent-class1** and **parent-class2**.
The example below is a code snippet in the HML file of the parent component that references a custom component named **comp**. This component uses the **inherit-class** attribute to inherit the styles of its parent component: **parent-class1** and **parent-class2**.