diff --git a/_c8oProject/mobileApplication.yaml b/_c8oProject/mobileApplication.yaml index 4031f080..faeede5c 100644 --- a/_c8oProject/mobileApplication.yaml +++ b/_c8oProject/mobileApplication.yaml @@ -2281,7 +2281,7 @@ useClickForTap: true .aichat { justify-content: end; align-items: end; - --width: 400px; + --width: 500px; } fieldset{ diff --git a/_c8oProject/mobilePages/aiChat.yaml b/_c8oProject/mobilePages/aiChat.yaml index 0b338a96..43fd2ea7 100644 --- a/_c8oProject/mobilePages/aiChat.yaml +++ b/_c8oProject/mobilePages/aiChat.yaml @@ -8,6 +8,18 @@ scriptContent: /*Begin_c8o_PageDeclaration*/ /*End_c8o_PageDeclaration*/ /*Begin_c8o_PageConstructor*/ + try { + const Speech = window["SpeechRecognition"] || window["webkitSpeechRecognition"]; + this.local.speechReco = new Speech(); + this.local.speechReco.continuous = true; + this.local.speechReco.interimResults = true; + this.local.speechReco.onresult = (evt) => { + this.local.inputModel = [...evt.results].map((r) => r[0]?.transcript.trim()).join(' '); + this.ref.detectChanges(); + }; + } catch(e){ + + } /*End_c8o_PageConstructor*/ /*Begin_c8o_PageFunction*/ /*End_c8o_PageFunction*/ @@ -121,7 +133,16 @@ title: Title for aiChat textValue: - xmlizable: - ↑classname: com.twinsoft.convertigo.beans.ngx.components.MobileSmartSourceType - - MobileSmartSourceType: source:{"filter":"Iteration","project":"C8Oforms","input":"","model":{"data":[{"priority":1730196159139}],"path":"","prefix":"","suffix":"?.content","custom":"","useCustom":false}} + - MobileSmartSourceType: source:{"filter":"Iteration","project":"C8Oforms","input":"","model":{"data":[{"priority":1730196159139}],"path":"","prefix":"","suffix":"?.content ?? ''","custom":"","useCustom":false}} + ↓Directive [ngx.components.UIControlDirective-1730731945805]: + directiveName: If + directiveSource: + - xmlizable: + - ↑classname: com.twinsoft.convertigo.beans.ngx.components.MobileSmartSourceType + - MobileSmartSourceType: source:{"filter":"Iteration","project":"C8Oforms","input":"","model":{"data":[{"priority":1730196159139}],"path":"","prefix":"","suffix":"?.waiting == true","custom":"","useCustom":false}} + ↓SkeletonText [ngx.components.UIDynamicElement-1730732038567]: + beanData: '{"ionBean":"SkeletonText","Animated":"plain:true"}' + tagName: ion-skeleton-text ↓Directive1 [ngx.components.UIControlDirective-1730196159184]: directiveName: If directiveSource: @@ -157,7 +178,7 @@ title: Title for aiChat textValue: - xmlizable: - ↑classname: com.twinsoft.convertigo.beans.ngx.components.MobileSmartSourceType - - MobileSmartSourceType: source:{"filter":"Iteration","project":"C8Oforms","input":"","model":{"data":[{"priority":1730196159139}],"path":"","prefix":"","suffix":"?.content","custom":"","useCustom":false}} + - MobileSmartSourceType: source:{"filter":"Iteration","project":"C8Oforms","input":"","model":{"data":[{"priority":1730196159139}],"path":"","prefix":"","suffix":"?.content ?? ''","custom":"","useCustom":false}} ↓Footer [ngx.components.UIDynamicElement-1730128363989]: beanData: '{"ionBean":"Footer"}' tagName: ion-footer @@ -175,6 +196,63 @@ title: Title for aiChat "Required": "plain:true" }' tagName: ion-input + ↓attr [ngx.components.UIAttribute-1730737006280]: + attrName: '[(ngModel)]' + attrValue: + - xmlizable: + - ↑classname: com.twinsoft.convertigo.beans.ngx.components.MobileSmartSourceType + - MobileSmartSourceType: script:this.local.inputModel + ↓Mic [ngx.components.UIDynamicElement-1730735186273]: + beanData: '{"ionBean":"Button","IonFill":"plain:clear"}' + tagName: ion-button + ↓attr [ngx.components.UIControlEvent-1730735186276]: + ↓activateSpeech [ngx.components.UICustomAsyncAction-1730735186279]: + actionValue: + - xmlizable: + - ↑classname: com.twinsoft.convertigo.beans.common.FormatedContent + - com.twinsoft.convertigo.beans.common.FormatedContent: + →: | + try { + if (!this.local.isRecording) { + this.local.speechReco.start(); + } else { + this.local.speechReco.stop(); + } + this.local.isRecording = !this.local.isRecording; + + } catch (e) { + + } finally { + return; + } + + page_ts_imports: + - xmlizable: + - ↑classname: com.twinsoft.convertigo.beans.common.XMLVector + - com.twinsoft.convertigo.beans.common.XMLVector: + - xmlizable: + - ↑classname: com.twinsoft.convertigo.beans.common.XMLVector + - com.twinsoft.convertigo.beans.common.XMLVector: + - java.lang.String: + - ↑value: LoadingController + - java.lang.String: + - ↑value: '@ionic/angular' + ↓Icon [ngx.components.UIDynamicElement-1730735186285]: + beanData: | + '{ + "ionBean": "Icon", + "IonColor": "script:this.local.isRecording ? ''danger'' : ''primary''", + "IconName": "source:{\"filter\":\"Icon\",\"project\":\"C8Oforms\",\"input\":\"\",\"model\":{\"data\":[{\"icon\":\"''mic-outline''\"}],\"path\":\"\",\"prefix\":\"\",\"suffix\":\"\",\"custom\":\"\",\"useCustom\":false}}", + "IconIosName": "plain:", + "IonSize": "plain:large" + }' + tagName: ion-icon + ↓attr1 [ngx.components.UIAttribute-1730736011639]: + attrName: '*ngIf' + attrValue: + - xmlizable: + - ↑classname: com.twinsoft.convertigo.beans.ngx.components.MobileSmartSourceType + - MobileSmartSourceType: plain:this.local.speechReco != undefined ↓SubmitButton [ngx.components.UIDynamicElement-1730195566682]: beanData: '{"ionBean":"SubmitButton","IonFill":"plain:clear"}' tagName: ion-button @@ -199,45 +277,17 @@ title: Title for aiChat }' ↓callChat [ngx.components.UIEventSubscriber-1730200487383]: topic: callChat - ↓CallSequence [ngx.components.UIDynamicAction-1730198395692]: - beanData: '{"ionBean":"CallSequenceAction","requestable":"plain:lib_C8Oforms_AI.Chat"}' - ↓form_id [ngx.components.UIControlVariable-1730200694043]: - comment: new variable - varValue: - - xmlizable: - - ↑classname: com.twinsoft.convertigo.beans.ngx.components.MobileSmartSourceType - - MobileSmartSourceType: script:this.navParams?.data?.form_id ?? "" - ↓message [ngx.components.UIControlVariable-1730200694045]: - comment: new variable - varValue: - - xmlizable: - - ↑classname: com.twinsoft.convertigo.beans.ngx.components.MobileSmartSourceType - - MobileSmartSourceType: source:{"filter":"Action","project":"C8Oforms","input":"","model":{"data":[{"priority":1730200487383,"rootEvent":true,"pageLocals":false}],"path":"?.out","prefix":"","suffix":"?.message ?? \"\"","custom":"","useCustom":false}} - ↓reset [ngx.components.UIControlVariable-1730219893805]: - comment: new variable - varValue: - - xmlizable: - - ↑classname: com.twinsoft.convertigo.beans.ngx.components.MobileSmartSourceType - - MobileSmartSourceType: source:{"filter":"Action","project":"C8Oforms","input":"","model":{"data":[{"priority":1730200487383,"rootEvent":true,"pageLocals":false}],"path":"?.out","prefix":"","suffix":"?.reset ?? \"false\"","custom":"","useCustom":false}} - ↓SetLocal [ngx.components.UIDynamicAction-1730280605676]: - beanData: | - '{ - "ionBean": "SetLocalAction", - "Property": "plain:chat", - "Value": "source:{\"filter\":\"Action\",\"project\":\"C8Oforms\",\"input\":\"\",\"model\":{\"data\":[{\"priority\":1730198395692,\"rootEvent\":false,\"pageLocals\":false},{\"priority\":1730200487383,\"rootEvent\":true,\"pageLocals\":false}],\"path\":\"?.out?.form\",\"prefix\":\"\",\"suffix\":\"\",\"custom\":\"\",\"useCustom\":false}}" - }' - ↓ScrollBottom [ngx.components.UICustomAction-1730201121737]: - actionValue: - - xmlizable: - - ↑classname: com.twinsoft.convertigo.beans.common.FormatedContent - - com.twinsoft.convertigo.beans.common.FormatedContent: - →: | - ' page.c8o.log.debug(''[MB] ''+ props.actionFunction +'': ''+ props.actionName); - window.setTimeout(() => { - page.content.scrollToBottom(200); - },200); - resolve(); - ' + ↓Show_Loading [ngx.components.UIDynamicAction-1730732820232]: + beanData: | + '{ + "ionBean": "ShowLoadingAction", + "message": "plain:", + "duration": "plain", + "spinner": "plain:bubbles", + "cssClass": "plain:aiLoadingMessage", + "backdropDismiss": "plain:false", + "keyboardClose": "plain:false" + }' ↓ResetForm [ngx.components.UICustomAction-1730199862999]: actionValue: - xmlizable: @@ -246,14 +296,84 @@ title: Title for aiChat →: | ' page.c8o.log.debug(''[MB] ''+ props.actionFunction +'': ''+ props.actionName); page.formAiChat.reset(); + + try { + if (this.local.isRecording) { + this.local.speechReco.stop(); + this.local.isRecording = false; + } + } catch (e) {} + + const interval = window.setInterval(() => { + const loading = window.document.querySelector(''.aiLoadingMessage .loading-content''); + if (loading) { + loading.textContent = page.translate.instant(''chatgpt_loading_ai'' + (Math.floor(Math.random() * 10) + 1)); + } else { + window.clearInterval(interval); + } + }, 5000); + const content = props.out?.message ?? false; + if (content && page.local.chat?.messages) { + page.local.chat.messages.push({ role: ''user'', content }); + page.local.chat.messages.push({ role: ''assistant'', content: '''', waiting: true }); + window.setTimeout(() => { + page.content.scrollToBottom(200); + },200); + } resolve(); ' - ↓language [ngx.components.UIControlVariable-1730385215158]: - comment: new variable - varValue: - - xmlizable: - - ↑classname: com.twinsoft.convertigo.beans.ngx.components.MobileSmartSourceType - - MobileSmartSourceType: script:this.global?.settings?.language + ↓CallSequence [ngx.components.UIDynamicAction-1730198395692]: + beanData: | + '{ + "ionBean": "CallSequenceAction", + "requestable": "plain:lib_C8Oforms_AI.Chat", + "noLoading": "plain:true" + }' + ↓form_id [ngx.components.UIControlVariable-1730200694043]: + comment: new variable + varValue: + - xmlizable: + - ↑classname: com.twinsoft.convertigo.beans.ngx.components.MobileSmartSourceType + - MobileSmartSourceType: script:this.navParams?.data?.form_id ?? "" + ↓message [ngx.components.UIControlVariable-1730200694045]: + comment: new variable + varValue: + - xmlizable: + - ↑classname: com.twinsoft.convertigo.beans.ngx.components.MobileSmartSourceType + - MobileSmartSourceType: source:{"filter":"Action","project":"C8Oforms","input":"","model":{"data":[{"priority":1730200487383,"rootEvent":true,"pageLocals":false}],"path":"?.out","prefix":"","suffix":"?.message ?? \"\"","custom":"","useCustom":false}} + ↓reset [ngx.components.UIControlVariable-1730219893805]: + comment: new variable + varValue: + - xmlizable: + - ↑classname: com.twinsoft.convertigo.beans.ngx.components.MobileSmartSourceType + - MobileSmartSourceType: source:{"filter":"Action","project":"C8Oforms","input":"","model":{"data":[{"priority":1730200487383,"rootEvent":true,"pageLocals":false}],"path":"?.out","prefix":"","suffix":"?.reset ?? \"false\"","custom":"","useCustom":false}} + ↓SetLocal [ngx.components.UIDynamicAction-1730280605676]: + beanData: | + '{ + "ionBean": "SetLocalAction", + "Property": "plain:chat", + "Value": "source:{\"filter\":\"Action\",\"project\":\"C8Oforms\",\"input\":\"\",\"model\":{\"data\":[{\"priority\":1730198395692,\"rootEvent\":false,\"pageLocals\":false},{\"priority\":1730200487383,\"rootEvent\":true,\"pageLocals\":false}],\"path\":\"?.out?.form\",\"prefix\":\"\",\"suffix\":\"\",\"custom\":\"\",\"useCustom\":false}}" + }' + ↓ScrollBottom [ngx.components.UICustomAction-1730201121737]: + actionValue: + - xmlizable: + - ↑classname: com.twinsoft.convertigo.beans.common.FormatedContent + - com.twinsoft.convertigo.beans.common.FormatedContent: + →: | + ' page.c8o.log.debug(''[MB] ''+ props.actionFunction +'': ''+ props.actionName); + window.setTimeout(() => { + page.content.scrollToBottom(200); + },200); + resolve(); + ' + ↓Close_Loading [ngx.components.UIDynamicAction-1730732860615]: + beanData: '{"ionBean":"CloseLoadingAction"}' + ↓language [ngx.components.UIControlVariable-1730385215158]: + comment: new variable + varValue: + - xmlizable: + - ↑classname: com.twinsoft.convertigo.beans.ngx.components.MobileSmartSourceType + - MobileSmartSourceType: script:this.global?.settings?.language ↓PageEvent1 [ngx.components.UIPageEvent-1730721387130]: viewEvent: onWillLeave ↓CustomAsyncAction [ngx.components.UICustomAsyncAction-1730721390390]: @@ -269,4 +389,14 @@ title: Title for aiChat } finally { return; } + try { + if (this.local.isRecording) { + this.local.speechReco.stop(); + this.local.isRecording = false; + } + } catch (e) { + + } finally { + return; + } \ No newline at end of file diff --git a/_c8oProject/mobilePages/editorPage.yaml b/_c8oProject/mobilePages/editorPage.yaml index 8ca92036..af3482c3 100644 --- a/_c8oProject/mobilePages/editorPage.yaml +++ b/_c8oProject/mobilePages/editorPage.yaml @@ -12458,46 +12458,52 @@ title: Title for editor - ↑classname: com.twinsoft.convertigo.beans.ngx.components.MobileSmartSourceType - MobileSmartSourceType: plain:some button text ↓attr [ngx.components.UIControlEvent-1696427260644]: - ↓FabContainer [ngx.components.UIDynamicElement-1730193473111]: - beanData: | - '{ - "ionBean": "FabContainer", - "IonSlot": "plain:fixed", - "Horizontal": "plain:end", - "Vertical": "plain:bottom" - }' - identifier: fabia - tagName: ion-fab - ↓FabButton [ngx.components.UIDynamicElement-1730193473102]: - beanData: '{"ionBean":"FabButton"}' - tagName: ion-fab-button - ↓Icon [ngx.components.UIDynamicElement-1730193473104]: - beanData: '{"ionBean":"Icon","IconName":"source:{\"filter\":\"Icon\",\"project\":\"C8Oforms\",\"input\":\"\",\"model\":{\"data\":[{\"icon\":\"''sparkles-outline''\"}],\"path\":\"\",\"prefix\":\"\",\"suffix\":\"\",\"custom\":\"\",\"useCustom\":false}}"}' - tagName: ion-icon - ↓Event [ngx.components.UIControlEvent-1730194087370]: - ↓ModalPage [ngx.components.UIDynamicAction-1730130298844]: - beanData: | - '{ - "ionBean": "ModalAction", - "page": "plain:C8Oforms.MobileApplication.Application.aiChat", - "data": "script:{form_id: this.form?._id}", - "showBackdrop": "plain:false", - "cssClass": "plain:aichat" - }' - ↓hideBrevo [ngx.components.UICustomAsyncAction-1730721257852]: - actionValue: - - xmlizable: - - ↑classname: com.twinsoft.convertigo.beans.common.FormatedContent - - com.twinsoft.convertigo.beans.common.FormatedContent: - →: | - try { - document.getElementById("brevo-conversations").style.visibility = "hidden"; - } catch (e) { - - } finally { - return; - } - + ↓ifHasAI [ngx.components.UIControlDirective-1730737503158]: + directiveName: If + directiveSource: + - xmlizable: + - ↑classname: com.twinsoft.convertigo.beans.ngx.components.MobileSmartSourceType + - MobileSmartSourceType: source:{"filter":"Local","project":"C8Oforms","input":"","model":{"data":[{"localObject":"local"}],"path":"","prefix":"","suffix":".hasAi == \"true\"","custom":"","useCustom":false}} + ↓FabContainer [ngx.components.UIDynamicElement-1730193473111]: + beanData: | + '{ + "ionBean": "FabContainer", + "IonSlot": "plain:fixed", + "Horizontal": "plain:end", + "Vertical": "plain:bottom" + }' + identifier: fabia + tagName: ion-fab + ↓FabButton [ngx.components.UIDynamicElement-1730193473102]: + beanData: '{"ionBean":"FabButton"}' + tagName: ion-fab-button + ↓Icon [ngx.components.UIDynamicElement-1730193473104]: + beanData: '{"ionBean":"Icon","IconName":"source:{\"filter\":\"Icon\",\"project\":\"C8Oforms\",\"input\":\"\",\"model\":{\"data\":[{\"icon\":\"''sparkles-outline''\"}],\"path\":\"\",\"prefix\":\"\",\"suffix\":\"\",\"custom\":\"\",\"useCustom\":false}}"}' + tagName: ion-icon + ↓Event [ngx.components.UIControlEvent-1730194087370]: + ↓ModalPage [ngx.components.UIDynamicAction-1730130298844]: + beanData: | + '{ + "ionBean": "ModalAction", + "page": "plain:C8Oforms.MobileApplication.Application.aiChat", + "data": "script:{form_id: this.form?._id}", + "showBackdrop": "plain:false", + "cssClass": "plain:aichat" + }' + ↓hideBrevo [ngx.components.UICustomAsyncAction-1730721257852]: + actionValue: + - xmlizable: + - ↑classname: com.twinsoft.convertigo.beans.common.FormatedContent + - com.twinsoft.convertigo.beans.common.FormatedContent: + →: | + try { + document.getElementById("brevo-conversations").style.visibility = "hidden"; + } catch (e) { + + } finally { + return; + } + ↓PageEvent [ngx.components.UIPageEvent-1537361744228]: viewEvent: onWillEnter ↓Error_Handler [ngx.components.UIActionErrorEvent-1576602087903]: @@ -12510,7 +12516,7 @@ title: Title for editor - ↑classname: com.twinsoft.convertigo.beans.common.FormatedContent - com.twinsoft.convertigo.beans.common.FormatedContent: →: | - try { + ' try { try{ let userSettings = await page.c8o.callJsonObject("C8Oforms.getCurrentUserSettings",{}).async(); //define ddoc names @@ -12530,7 +12536,7 @@ title: Title for editor } page.local.p = "editor"; - page.local.formId = page.navParams.get('formId'); + page.local.formId = page.navParams.get(''formId''); page.local.user = page.global.user; page.local.namer = namer; try{ @@ -12542,13 +12548,18 @@ title: Title for editor catch (e) { } - + try { + let hasAi = await page.c8o.callJsonObject("C8Oforms.HasProject",{projectName: "lib_C8Oforms_AI"}).async(); + page.local.hasAi = hasAi.has; + } catch (e) { + page.local.hasAi = false; + } } catch (e) { } finally { return; } - + ' module_ng_imports: - xmlizable: - ↑classname: com.twinsoft.convertigo.beans.common.XMLVector diff --git a/c8oProject.yaml b/c8oProject.yaml index 5f177a72..3c8773d8 100644 --- a/c8oProject.yaml +++ b/c8oProject.yaml @@ -4,7 +4,7 @@ contextTimeout: ${C8Oforms.context.timeout=3600} corsOrigin: =Origin httpSessionTimeout: ${C8Oforms.http_session.timeout=3600} - version: 2.0.0-beta134 + version: 2.0.0-beta135 ↓c8oforms_fs [connectors.FullSyncConnector]: 🗏 connectors/c8oforms_fs.yaml ↓c8oforms_response_fs [connectors.FullSyncConnector]: 🗏 connectors/c8oforms_response_fs.yaml ↓HTTP_connector [connectors.HttpConnector]: 🗏 connectors/HTTP_connector.yaml diff --git a/project.md b/project.md index 1d4c981a..e4340747 100644 --- a/project.md +++ b/project.md @@ -12,7 +12,7 @@ Convertigo No Code Studio ## ![](https://github.com/convertigo/convertigo/blob/develop/engine/src/com/twinsoft/convertigo/beans/references/images/ProjectSchemaReference_16x16.png?raw=true "ProjectSchemaReference") C8Oforms_PWAs -see [readme](https://github.com/convertigo/C8Oforms_PWAs/tree/master#readme) +see [readme](https://github.com/convertigo/C8Oforms_PWAs/tree/16423f0eef6427cf888bf1afe7f457bd44e0e507#readme)
@@ -30,7 +30,7 @@ see [documentation](http://localhost:18080/convertigo/xsd/couchdb/CouchDb.xsd) ## ![](https://github.com/convertigo/convertigo/blob/develop/engine/src/com/twinsoft/convertigo/beans/references/images/ProjectSchemaReference_16x16.png?raw=true "ProjectSchemaReference") lib_Actions_C8Oforms -see [readme](https://github.com/convertigo/c8oprj-lib-actions-c8oforms/tree/master#readme) +see [readme](https://github.com/convertigo/c8oprj-lib-actions-c8oforms/tree/8b85fef317f9158f4b4d16d0929bc183ffd2fc4b#readme)
@@ -57,7 +57,7 @@ see [readme](https://github.com/convertigo/c8oprj-lib-fullsync-grp/tree/e6674a8b ## ![](https://github.com/convertigo/convertigo/blob/develop/engine/src/com/twinsoft/convertigo/beans/references/images/ProjectSchemaReference_16x16.png?raw=true "ProjectSchemaReference") lib_GeneratePWAAssets -see [readme](https://github.com/convertigo/c8oprj-lib-generate-assets-pwa/tree/8.0.0#readme) +see [readme](https://github.com/convertigo/c8oprj-lib-generate-assets-pwa/tree/41f90f9e9c11a99add90bf06990f276df7e0de0a#readme)
@@ -93,7 +93,7 @@ see [readme](https://github.com/convertigo/c8oprj-product-tour/tree/master#readm ## ![](https://github.com/convertigo/convertigo/blob/develop/engine/src/com/twinsoft/convertigo/beans/references/images/ProjectSchemaReference_16x16.png?raw=true "ProjectSchemaReference") lib_UserManager Reference to secured login library -see [readme](https://github.com/convertigo/c8oprj-lib-user-manager/tree/f8941d93af0db63dc16c052daad77de2f6329747#readme) +see [readme](https://github.com/convertigo/c8oprj-lib-user-manager/tree/8.0.X#readme)