1# XComponent 2 3The **\<XComponent>** can accept and display the EGL/OpenGL ES and media data input. 4 5> **NOTE** 6> 7> This component is supported since API version 8. Updates will be marked with a superscript to indicate their earliest API version. 8 9 10## Child Components 11Child components are not supported when **type** is set to **"surface"**. 12 13Since API version 9, child components are supported when **type** is set to **"component"**. 14 15## APIs 16 17### XComponent 18 19XComponent(value: {id: string, type: string, libraryname?: string, controller?: XComponentController}) 20 21**Parameters** 22 23| Name | Type | Mandatory| Description | 24| ----------- | --------------------------------------------- | ---- | ------------------------------------------------------------ | 25| id | string | Yes | Unique ID of the component. The value can contain a maximum of 128 characters. | 26| type | string | Yes | Type of the component. The options are as follows:<br>- **"surface"**: The custom content is displayed individually on the screen. This option is used for displaying EGL/OpenGL ES and media data.<br>- **"component"**<sup>9+</sup>: The component becomes a container where non-UI logic can be executed to dynamically load the display content.<br>Any other value evaluates to **"surface"**.| 27| libraryname | string | No | Name of the dynamic library generated after compilation at the application native layer. This parameter is valid only when **type** is **"surface"**.| 28| controller | [XComponentcontroller](#xcomponentcontroller) | No | Controller bound to the component, which can be used to invoke methods of the component. This parameter is valid only when the component type is **"surface"**.| 29 30### XComponent<sup>10+</sup> 31 32XComponent(value: {id: string, type: XComponentType, libraryname?: string, controller?: XComponentController}) 33 34**Parameters** 35 36| Name | Type | Mandatory| Description | 37| ----------- | --------------------------------------------- | ---- | ------------------------------------------------------------ | 38| id | string | Yes | Unique ID of the component. The value can contain a maximum of 128 characters. | 39| type | [XComponentType](#xcomponenttype10) | Yes | Type of the component. | 40| libraryname | string | No | Name of the dynamic library generated after compilation at the application native layer. This parameter is valid only when **type** is **SURFACE** or **TEXTURE**.| 41| controller | [XComponentcontroller](#xcomponentcontroller) | No | Controller bound to the component, which can be used to invoke methods of the component. This parameter is valid only when **type** is **SURFACE** or **TEXTURE**.| 42 43## XComponentType<sup>10+</sup> 44 45| Name | Description | 46| --------- | ------------------------------------------------------------ | 47| SURFACE | The custom content is displayed individually on the screen. This option is used for displaying EGL/OpenGL ES and media data.| 48| COMPONENT | The component becomes a container where non-UI logic can be executed to dynamically load the display content.| 49| TEXTURE | The custom content of the component is grouped and displayed together with content of the component.| 50 51> **NOTE** 52> 53> When **type** is set to **COMPONENT("component")**, the **\<XComponent>** functions as a container, where child components are laid out vertically. 54> 55> - Vertical alignment: [FlexAlign](ts-appendix-enums.md#flexalign).Start 56> - Horizontal alignment: [FlexAlign](ts-appendix-enums.md#flexalign).Center 57> 58> The component does not respond to any events. 59> 60> Layout changes and event responses can be set by mounting child components. 61> 62> The non-UI logic written internally needs to be encapsulated in one or more functions. 63 64## Attributes 65- You can customize the content displayed in the **\<XComponent>**. Depending on the **type** settings, the support for the universal attributes [background](ts-universal-attributes-background.md), [opacity](ts-universal-attributes-opacity.md), and [image effects](ts-universal-attributes-image-effect.md) varies. 66 67- When **type** is set to **SURFACE("surface")**, only the **shadow** attribute of [image effects](ts-universal-attributes-image-effect.md). For configuration of other attributes, you are advised to use the APIs provided by EGL/OpenGL ES instead. 68 69 > **NOTE**<br> 70 > 71 > Since API version 11, when **type** is set to **SURFACE("surface")**, the [backgroundColor](ts-universal-attributes-background.md#backgroundcolor) attribute is supported. 72 73- When **type** is set to **COMPONENT("component")**, only the **shadow** attribute of [image effects](ts-universal-attributes-image-effect.md). For configuration of other attributes, you are advised to mount child components. 74 75- When **type** is set to **TEXTURE**, the **shadow** attribute of [image effects](ts-universal-attributes-image-effect.md), [backgroundColor](ts-universal-attributes-background.md#backgroundcolor), and [opacity](ts-universal-attributes-opacity.md) are supported. For configuration of other attributes, you are advised to use the APIs provided by EGL/OpenGL ES instead. 76 77### enableAnalyzer<sup>12+</sup> 78 79enableAnalyzer(enable: boolean) 80 81Specifies whether to enable the AI image analyzer. This attribute must be used together with[StartImageAnalyzer](#startimageanalyzer12) and [StopImageAnalyzer](#stopimageanalyzer12) in **XComponentController**. 82This attribute cannot be used together with the [overlay](ts-universal-attributes-overlay.md) attribute. If they are set at the same time, the **CustomBuilder** attribute in **overlay** has no effect. This feature depends on device capabilities. 83 84**Widget capability**: This API can be used in ArkTS widgets since API version 12. 85 86**System capability**: SystemCapability.ArkUI.ArkUI.Full 87 88**Parameters** 89 90| Name| Type| Mandatory| Description| 91| -------- | -------- | -------- | -------- | 92| enable | boolean | Yes| Whether to enable the AI image analyzer.| 93 94 > **NOTE**<br> 95 > 96 > This API has effect only when **type** is set to **SURFACE** or **TEXTURE**. 97 98## Events 99 100When **type** is set to **SURFACE("surface")** or **TEXTURE**, the [universal events](ts-universal-events-click.md) are supported since API version 12, subject to the following constraints: 101 102- The following events, which are mutually exclusive with the corresponding NDK APIs, are available only when **libraryname** is not set: [click event](ts-universal-events-click.md), [touch event](ts-universal-events-touch.md), [show/hide event](ts-universal-events-show-hide.md), [key event](ts-universal-events-key.md), [focus event](ts-universal-focus-event.md), and [mouse event](ts-universal-mouse-key.md). 103 104- Other universal events do not have corresponding NDK APIs; therefore, they are available regardless of whether **libraryname** is set. 105 106When **type** is set to **SURFACE("surface")** or **TEXTURE**, the following events are supported. 107 108### onLoad 109 110onLoad(callback: (event?: object) => void ) 111 112Triggered when the plug-in is loaded. 113 114**Parameters** 115 116| Name | Type | Mandatory | Description | 117| ----- | ------ | ---- | ---------------------------------------- | 118| event | object | No | Context of the **\<XComponent>** object. The APIs contained in the context are defined at the C++ layer by developers.| 119 120### onDestroy 121 122onDestroy(event: () => void ) 123 124Triggered when the plug-in is destroyed. 125 126## XComponentController 127 128Defines the controller of the **\<XComponent>**. You can bind the controller to the **\<XComponent>** to invoke the methods of the component through the controller. 129 130### Creating an Object 131 132``` 133xcomponentController: XComponentController = new XComponentController() 134``` 135 136### getXComponentSurfaceId 137 138getXComponentSurfaceId(): string 139 140Obtains the ID of the surface held by the **\<XComponent>**, which can then be used for @ohos APIs. For details, see [Camera Management](../../apis-camera-kit/js-apis-camera.md). This API works only when **type** of the **\<XComponent>** is set to **SURFACE("surface")** or **TEXTURE**. 141 142**Return value** 143 144| Type | Description | 145| ------ | ----------------------- | 146| string | ID of the surface held by the **\<XComponent>**.| 147 148 149### setXComponentSurfaceSize<sup>(deprecated)</sup> 150 151setXComponentSurfaceSize(value: {surfaceWidth: number, surfaceHeight: number}): void 152 153Sets the width and height of the surface held by the **\<XComponent>**. This API works only when **type** of the **\<XComponent>** is set to **SURFACE("surface")** or **TEXTURE**. 154 155This API is deprecated since API version 12. You are advised to use [setXComponentSurfaceRect](#setxcomponentsurfacerect12) instead. 156 157**Parameters** 158 159| Name | Type | Mandatory | Description | 160| ------------- | ------ | ---- | ----------------------- | 161| surfaceWidth | number | Yes | Width of the surface held by the **\<XComponent>**.| 162| surfaceHeight | number | Yes | Height of the surface held by the **\<XComponent>**.| 163 164 165### getXComponentContext 166 167getXComponentContext(): Object 168 169Obtains the context of an **\<XComponent>** object. This API works only when **type** of the **\<XComponent>** is set to **SURFACE("surface")** or **TEXTURE**. 170 171**Return value** 172 173| Type | Description | 174| ------ | ------------------------------------------------------------ | 175| Object | Context of the **\<XComponent>** object. The APIs contained in the context are defined by developers. The context is passed in as the first parameter of the **onLoad** callback.| 176 177### setXComponentSurfaceRect<sup>12+</sup> 178 179setXComponentSurfaceRect(rect: SurfaceRect): void 180 181Sets the rectangle for the surface held by the **\<XComponent>**. This API works only when type of the **\<XComponent>** is set to **SURFACE("surface")** or **TEXTURE**. 182 183**Parameters** 184 185| Name| Type | Mandatory| Description | 186| ------ | ------------------------------------ | ---- | --------------------------------- | 187| rect | [SurfaceRect](#surfacerect12) | Yes | Rectangle of the surface held by the **\<XComponent>**.| 188 189> **NOTE**<br> 190> 191> If **offsetX** or **offsetY** in the **rect** parameter is not set, the surface rectangle is centered along the x-axis or y-axis relative to the upper left corner of the **\<XComponent>**. 192> 193> If **surfaceWidth** and **surfaceHeight** in the **rect** parameter are set to **0** or a negative value, this API has no effect. 194> 195> This API has a higher priority than attributes that can change the content offset and size, such as [border](ts-universal-attributes-border.md#border) and [padding](ts-universal-attributes-size.md#padding). 196 197### getXComponentSurfaceRect<sup>12+</sup> 198 199getXComponentSurfaceRect(): SurfaceRect 200 201Obtains the rectangle of the surface held by the **\<XComponent>**. This API works only when type of the **\<XComponent>** is set to **SURFACE("surface")** or **TEXTURE**. 202 203**Return value** 204 205| Type | Description | 206| ------------------------------------ | ------------------------------------- | 207| [SurfaceRect](#surfacerect12) | Rectangle of the surface held by the **\<XComponent>**.| 208 209### onSurfaceCreated<sup>12+</sup> 210 211onSurfaceCreated(surfaceId: string): void 212 213Triggered when the surface held by the **\<XComponent>** is created. This API works only when **type** of the **\<XComponent>** is set to **SURFACE("surface")** or **TEXTURE**. 214 215**Parameters** 216 217| Name | Type| Mandatory| Description | 218| --------- | -------- | ---- | ------------------------------------------------- | 219| surfaceId | string | Yes | ID of the surface held by the **\<XComponent>**.| 220 221> **NOTE**<br> 222> 223> The callback is triggered only when the **libraryname** parameter is not set for the **\<XComponent>**. 224 225### onSurfaceChanged<sup>12+</sup> 226 227onSurfaceChanged(surfaceId: string, rect: SurfaceRect): void 228 229Triggered when the surface held by the **\<XComponent>** has its size changed (including the time when the **\<XComponent>** is created with the specified size). This API works only when **type** of the **\<XComponent>** is set to **SURFACE("surface")** or **TEXTURE**. 230 231**Parameters** 232 233| Name | Type | Mandatory| Description | 234| --------- | ------------------------------------- | ---- | ------------------------------------------------------- | 235| surfaceId | string | Yes | ID of the surface held by the **\<XComponent>**. | 236| rect | [SurfaceRect](#surfacerect12) | Yes | Rectangle for displaying the surface held by the **\<XComponent>**.| 237 238> **NOTE**<br> 239> 240> The callback is triggered only when the **libraryname** parameter is not set for the **\<XComponent>**. 241 242### onSurfaceDestroyed<sup>12+</sup> 243 244onSurfaceDestroyed(surfaceId: string): void 245 246Triggered when the surface held by the **\<XComponent>** is destroyed. This API works only when **type** of the **\<XComponent>** is set to **SURFACE("surface")** or **TEXTURE**. 247 248**Parameters** 249 250| Name | Type| Mandatory| Description | 251| --------- | -------- | ---- | ------------------------------------------------- | 252| surfaceId | string | Yes | ID of the surface held by the **\<XComponent>**.| 253 254> **NOTE**<br> 255> 256> The callback is triggered only when the **libraryname** parameter is not set for the **\<XComponent>**. 257 258### SurfaceRect<sup>12+</sup> 259 260Describes the rectangle of the surface held by the **\<XComponent>**. 261 262| Name | Type | Mandatory| Description | 263| ------------- | ------ | ---- | ------------------------------------------------------------ | 264| offsetX | number | No | X coordinate of the surface rectangle relative to the upper left corner of the **\<XComponent>**.<br>Unit: px| 265| offsetY | number | No | Y coordinate of the surface rectangle relative to the upper left corner of the **\<XComponent>**.<br>Unit: px| 266| surfaceWidth | number | Yes | Width of the surface rectangle.<br>Unit: px | 267| surfaceHeight | number | Yes | Height of the surface rectangle.<br>Unit: px | 268 269### startImageAnalyzer<sup>12+</sup> 270 271startImageAnalyzer(config: ImageAnalyzerConfig): Promise\<void> 272 273Starts AI image analysis in the given settings. Before calling this API, make sure the AI image analyzer is [enabled](#enableanalyzer12).<br>Because the image frame used for analysis is the one captured when this API is called, pay attention to the invoking time of this API.<br>If this API is repeatedly called before the execution is complete, an error callback is triggered. 274 275> **NOTE**<br> 276> 277> The image analysis type cannot be dynamically modified. 278> This API depends on device capabilities. If it is called on an incompatible device, an error code is returned. 279 280**System capability**: SystemCapability.ArkUI.ArkUI.Full 281 282**Parameters** 283 284| Name| Type | Mandatory| Description | 285| ------ | --------- | ---- | ---------------------------------------------------------------------- | 286| config | [ImageAnalyzerConfig](ts-image-common.md#imageanalyzerconfig12) | Yes | Settings of the AI image analyzer.| 287 288**Return value** 289 290| Type | Description | 291| ----------------- | ------------------------------------ | 292| Promise\<void> | Promise used to return the result.| 293 294**Error codes** 295 296For details about the error codes, see [AI Image Analyzer Error Codes](../errorcode-image-analyzer.md). 297 298| ID| Error Message | 299| -------- | -------------------------------------------- | 300| 110001 | AI analysis is unsupported. | 301| 110002 | AI analysis is ongoing. | 302| 110003 | AI analysis is stopped. | 303 304### stopImageAnalyzer<sup>12+</sup> 305 306stopImageAnalyzer(): void 307 308Stops AI image analysis. The content displayed by the AI image analyzer will be destroyed. 309 310> **NOTE**<br> 311> 312> If this API is called when the **startImageAnalyzer** API has not yet returned any result, an error callback is triggered. 313> This feature depends on device capabilities. 314 315**System capability**: SystemCapability.ArkUI.ArkUI.Full 316 317## Example 318 319You can preview how this component looks on a real device, but not in the DevEco Studio Previewer. 320 321### Example 1 322 323```ts 324// xxx.ets 325@Entry 326@Component 327struct PreviewArea { 328 private surfaceId: string = '' 329 private xComponentContext: Record<string, () => void> = {} 330 xComponentController: XComponentController = new XComponentController() 331 @State rect: SurfaceRect | null = null 332 333 build() { 334 Column() { 335 Text(JSON.stringify(this.rect)) 336 .fontSize(12) 337 XComponent({ 338 id: 'xcomponent', 339 type: XComponentType.SURFACE, 340 controller: this.xComponentController 341 }) 342 .onLoad(() => { 343 this.surfaceId = this.xComponentController.getXComponentSurfaceId() 344 this.xComponentContext = this.xComponentController.getXComponentContext() as Record<string, () => void> 345 let surfaceRect: SurfaceRect = { offsetX: 20, offsetY: 20, surfaceWidth: 500, surfaceHeight: 500 } 346 this.xComponentController.setXComponentSurfaceRect(surfaceRect) 347 this.rect = this.xComponentController.getXComponentSurfaceRect() 348 }) 349 .width('640px') 350 .height('480px') 351 } 352 .position({ x: 0, y: 48 }) 353 } 354} 355``` 356 357### Example 2 358 359```ts 360// xxx.ets 361class CustomXComponentController extends XComponentController { 362 onSurfaceCreated(surfaceId: string): void { 363 console.log(`onSurfaceCreated surfaceId: ${surfaceId}`) 364 } 365 366 onSurfaceChanged(surfaceId: string, rect: SurfaceRect): void { 367 console.log(`onSurfaceChanged surfaceId: ${surfaceId}, rect: ${JSON.stringify(rect)}}`) 368 } 369 370 onSurfaceDestroyed(surfaceId: string): void { 371 console.log(`onSurfaceDestroyed surfaceId: ${surfaceId}`) 372 } 373} 374 375@Entry 376@Component 377struct SurfaceCallbackDemo { 378 xComponentController: XComponentController = new CustomXComponentController() 379 @State xcWidth: string = "320px" 380 @State xcHeight: string = "480px" 381 382 build() { 383 Column() { 384 Button("change size") 385 .onClick(() => { 386 this.xcWidth = "640px" 387 this.xcHeight = "960px" 388 }) 389 XComponent({ 390 id: 'xcomponent', 391 type: XComponentType.SURFACE, 392 controller: this.xComponentController 393 }) 394 .width(this.xcWidth) 395 .height(this.xcHeight) 396 } 397 .width("100%") 398 } 399} 400``` 401 402### Example 3 403 404This example shows how to use the AI image analyzer. 405 406```ts 407// xxx.ets 408@Entry 409@Component 410struct ImageAnalyzerExample { 411 xComponentController: XComponentController = new XComponentController() 412 private config: ImageAnalyzerConfig = { 413 types: [ImageAnalyzerType.SUBJECT, ImageAnalyzerType.TEXT] 414 } 415 416 build() { 417 Column() { 418 Button('start') 419 .width(80) 420 .height(80) 421 .onClick(() => { 422 this.xComponentController.startImageAnalyzer(this.config) 423 .then(() => { 424 console.log("analysis complete") 425 }) 426 .catch((error: BusinessError) => { 427 console.log("error code: " + error.code) 428 }) 429 }) 430 Button('stop') 431 .width(80) 432 .height(80) 433 .onClick(() => { 434 this.xComponentController.stopImageAnalyzer() 435 }) 436 XComponent({ 437 id: 'xcomponent', 438 type: XComponentType.SURFACE, 439 controller: this.xComponentController 440 }) 441 .enableAnalyzer(true) 442 .width('640px') 443 .height('480px') 444 } 445 .width("100%") 446 } 447} 448``` 449