@botonic/react 0.20.8 → 0.21.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/webview.jsx"],"names":["App","props","url","URL","window","location","href","params","Array","from","searchParams","entries","filter","key","value","reduce","o","session","JSON","parse","get","state","options","payload","path","s","baseUrl","_hubtype_api","method","bot","id","data","chat_id","user","resp","console","log","provider","PROVIDER","WHATSAPP","imp_id","MessengerExtensions","requestCloseBrowser","undefined","err","e","parent","postMessage","requestContext","getString","stringId","locales","__locale","closeWebview","close","bind","webviews","map","Webview","i","name","React","Component","WebviewApp","dest"],"mappings":"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","sourcesContent":["import { getString, params2queryString, PROVIDER } from '@botonic/core'\nimport axios from 'axios'\nimport React from 'react'\nimport { render } from 'react-dom'\nimport { BrowserRouter, Route } from 'react-router-dom'\n\nimport { RequestContext } from './contexts'\n\nclass App extends React.Component {\n constructor(props) {\n super(props)\n const url = new URL(window.location.href)\n const params = Array.from(url.searchParams.entries())\n .filter(([key, value]) => key != 'context')\n .reduce((o, [key, value]) => {\n o[key] = value\n return o\n }, {})\n const session = JSON.parse(url.searchParams.get('context') || {})\n this.state = { session, params }\n }\n\n async close(options) {\n let payload = options ? options.payload : null\n if (options.path) payload = `__PATH_PAYLOAD__${options.path}`\n if (payload) {\n if (options.params) {\n payload = `${payload}?${params2queryString(options.params)}`\n }\n const s = this.state.session\n try {\n const baseUrl = s._hubtype_api || 'https://api.hubtype.com'\n const resp = await axios({\n method: 'post',\n url: `${baseUrl}/v1/bots/${s.bot.id}/send_postback/`,\n // eslint-disable-next-line @typescript-eslint/naming-convention\n data: { payload: payload, chat_id: s.user.id },\n })\n } catch (e) {\n console.log(e)\n }\n }\n if (this.state.session.user.provider === PROVIDER.WHATSAPP) {\n location.href = 'https://wa.me/' + this.state.session.user.imp_id\n } else {\n try {\n window.MessengerExtensions.requestCloseBrowser(\n () => undefined,\n err => console.log(err)\n )\n } catch (e) {}\n try {\n await parent.postMessage('botonicCloseWebview', '*')\n } catch (e) {}\n }\n }\n\n render() {\n const requestContext = {\n getString: stringId =>\n getString(this.props.locales, this.state.session.__locale, stringId),\n session: this.state.session || {},\n params: this.state.params || {},\n closeWebview: this.close.bind(this),\n }\n\n return (\n <RequestContext.Provider value={requestContext}>\n {this.props.webviews.map((Webview, i) => (\n <Route key={i} path={`/${Webview.name}`} component={Webview} />\n ))}\n </RequestContext.Provider>\n )\n }\n}\n\nexport class WebviewApp {\n constructor({ webviews, locales }) {\n this.webviews = webviews\n this.locales = locales\n }\n\n render(dest) {\n render(\n <BrowserRouter>\n <App webviews={this.webviews} locales={this.locales} />\n </BrowserRouter>,\n dest\n )\n }\n}\n"],"file":"webview.js"}
1
+ {"version":3,"sources":["../src/webview.jsx"],"names":["App","props","url","URL","window","location","href","params","Array","from","searchParams","entries","filter","key","value","reduce","o","session","JSON","parse","get","state","options","payload","path","s","baseUrl","_hubtype_api","method","bot","id","data","chat_id","user","resp","console","log","provider","impId","imp_id","PROVIDER","WHATSAPP","TELEGRAM","APPLE","TWITTER","FACEBOOK","MessengerExtensions","requestCloseBrowser","undefined","err","e","WEBCHAT","parent","postMessage","requestContext","getString","stringId","locales","__locale","closeWebview","close","bind","webviews","map","Webview","i","name","React","Component","WebviewApp","dest"],"mappings":"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","sourcesContent":["import { getString, params2queryString, PROVIDER } from '@botonic/core'\nimport axios from 'axios'\nimport React from 'react'\nimport { render } from 'react-dom'\nimport { BrowserRouter, Route } from 'react-router-dom'\n\nimport { RequestContext } from './contexts'\n\nclass App extends React.Component {\n constructor(props) {\n super(props)\n const url = new URL(window.location.href)\n const params = Array.from(url.searchParams.entries())\n .filter(([key, value]) => key != 'context')\n .reduce((o, [key, value]) => {\n o[key] = value\n return o\n }, {})\n const session = JSON.parse(url.searchParams.get('context') || {})\n this.state = { session, params }\n }\n\n async close(options) {\n let payload = options ? options.payload : null\n if (options.path) payload = `__PATH_PAYLOAD__${options.path}`\n if (payload) {\n if (options.params) {\n payload = `${payload}?${params2queryString(options.params)}`\n }\n const s = this.state.session\n try {\n const baseUrl = s._hubtype_api || 'https://api.hubtype.com'\n const resp = await axios({\n method: 'post',\n url: `${baseUrl}/v1/bots/${s.bot.id}/send_postback/`,\n // eslint-disable-next-line @typescript-eslint/naming-convention\n data: { payload: payload, chat_id: s.user.id },\n })\n } catch (e) {\n console.log(e)\n }\n }\n const provider = this.state.session.user.provider\n const impId = this.state.session.user.imp_id\n if (provider === PROVIDER.WHATSAPP) {\n location.href = 'https://wa.me/' + impId\n }\n if (provider === PROVIDER.TELEGRAM) {\n location.href = 'https://t.me/' + impId\n }\n if (provider === PROVIDER.APPLE) {\n location.href = 'https://bcrw.apple.com/urn:biz:' + impId\n }\n if (provider === PROVIDER.TWITTER) {\n location.href =\n 'https://twitter.com/messages/compose?recipient_id=' + impId\n }\n if (provider === PROVIDER.FACEBOOK) {\n try {\n window.MessengerExtensions.requestCloseBrowser(\n () => undefined,\n err => console.log(err)\n )\n } catch (e) {}\n }\n if (provider === PROVIDER.WEBCHAT) {\n try {\n await parent.postMessage('botonicCloseWebview', '*')\n } catch (e) {}\n }\n }\n\n render() {\n const requestContext = {\n getString: stringId =>\n getString(this.props.locales, this.state.session.__locale, stringId),\n session: this.state.session || {},\n params: this.state.params || {},\n closeWebview: this.close.bind(this),\n }\n\n return (\n <RequestContext.Provider value={requestContext}>\n {this.props.webviews.map((Webview, i) => (\n <Route key={i} path={`/${Webview.name}`} component={Webview} />\n ))}\n </RequestContext.Provider>\n )\n }\n}\n\nexport class WebviewApp {\n constructor({ webviews, locales }) {\n this.webviews = webviews\n this.locales = locales\n }\n\n render(dest) {\n render(\n <BrowserRouter>\n <App webviews={this.webviews} locales={this.locales} />\n </BrowserRouter>,\n dest\n )\n }\n}\n"],"file":"webview.js"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@botonic/react",
3
- "version": "0.20.8",
3
+ "version": "0.21.0",
4
4
  "license": "MIT",
5
5
  "description": "Build Chatbots using React",
6
6
  "main": "src/index.js",
@@ -28,7 +28,7 @@
28
28
  "README.md"
29
29
  ],
30
30
  "dependencies": {
31
- "@botonic/core": "^0.20.5",
31
+ "@botonic/core": "0.21.0",
32
32
  "axios": "^0.24.0",
33
33
  "emoji-picker-react": "^3.2.3",
34
34
  "framer-motion": "^3.1.1",
@@ -313,7 +313,9 @@ export const Message = props => {
313
313
  ) : (
314
314
  <BlobText blob={blob}>{textChildren}</BlobText>
315
315
  )}
316
- {buttons}
316
+ {!!buttons.length && (
317
+ <div className='message-buttons-container'>{buttons}</div>
318
+ )}
317
319
  {Boolean(blob) && hasBlobTick() && getBlobTick(6)}
318
320
  {Boolean(blob) && hasBlobTick() && getBlobTick(5)}
319
321
  </Blob>
@@ -7,13 +7,20 @@ import { ROLES } from '../../constants'
7
7
  import { useComponentVisible } from '../hooks'
8
8
  import { Icon, IconContainer } from './common'
9
9
 
10
- export const EmojiPicker = props => (
11
- <IconContainer role={ROLES.EMOJI_PICKER_ICON}>
12
- <div onClick={props.onClick}>
13
- <Icon src={LogoEmoji} />
14
- </div>
15
- </IconContainer>
16
- )
10
+ export const EmojiPicker = props =>{
11
+ const onClick = event =>{
12
+ props.onClick()
13
+ event.stopPropagation()
14
+ }
15
+
16
+ return (
17
+ <IconContainer role={ROLES.EMOJI_PICKER_ICON}>
18
+ <div onClick={onClick}>
19
+ <Icon src={LogoEmoji} />
20
+ </div>
21
+ </IconContainer>
22
+ )
23
+ }
17
24
 
18
25
  const Container = styled.div`
19
26
  display: flex;
@@ -83,7 +83,10 @@ export class ScrollbarController {
83
83
  this.webchat.ontouchstart = {}
84
84
  return
85
85
  }
86
- this.webchat.ontouchmove = e => e.preventDefault()
86
+ this.webchat.ontouchmove = e => {
87
+ if(e.target === e.currentTarget)
88
+ e.preventDefault()
89
+ }
87
90
  }
88
91
 
89
92
  limitScrollBoundaries() {
@@ -247,7 +247,7 @@ export function useComponentVisible(initialIsVisible, onClickOutside) {
247
247
  const [isComponentVisible, setIsComponentVisible] = useState(initialIsVisible)
248
248
  const ref = useRef(null)
249
249
  const handleClickOutside = event => {
250
- if (ref.current && !ref.current.contains(event.target)) {
250
+ if (ref.current && !ref.current.contains(event.path[0])) {
251
251
  setIsComponentVisible(false)
252
252
  onClickOutside()
253
253
  }
@@ -258,6 +258,21 @@ export const Webchat = forwardRef((props, ref) => {
258
258
  })
259
259
  }
260
260
 
261
+ const sendChatEvent = async chatEvent => {
262
+ const chatEventInput = {
263
+ id: uuidv4(),
264
+ type: INPUT.CHAT_EVENT,
265
+ data: chatEvent,
266
+ }
267
+ props.onUserInput &&
268
+ props.onUserInput({
269
+ user: webchatState.session.user,
270
+ input: chatEventInput,
271
+ session: webchatState.session,
272
+ lastRoutePath: webchatState.lastRoutePath,
273
+ })
274
+ }
275
+
261
276
  // Load styles stored in window._botonicInsertStyles by Webpack
262
277
  useComponentWillMount(() => {
263
278
  if (window._botonicInsertStyles && window._botonicInsertStyles.length) {
@@ -642,11 +657,43 @@ export const Webchat = forwardRef((props, ref) => {
642
657
  textArea.current.value = ''
643
658
  }
644
659
 
660
+ let isTyping = false
661
+ let typingTimeout = null
662
+
663
+ function clearTimeoutWithReset(reset) {
664
+ const waitTime = 20 * 1000
665
+ if (typingTimeout) clearTimeout(typingTimeout)
666
+ if (reset) typingTimeout = setTimeout(stopTyping, waitTime)
667
+ }
668
+
669
+ function startTyping() {
670
+ isTyping = true
671
+ sendChatEvent('typing_on')
672
+ }
673
+
674
+ function stopTyping() {
675
+ clearTimeoutWithReset(false)
676
+ isTyping = false
677
+ sendChatEvent('typing_off')
678
+ }
679
+
645
680
  const onKeyDown = event => {
646
- if (event.keyCode == 13 && event.shiftKey == false) {
681
+ if (event.keyCode === 13 && event.shiftKey === false) {
647
682
  event.preventDefault()
648
683
  sendTextAreaText()
684
+ stopTyping()
685
+ }
686
+ }
687
+
688
+ const onKeyUp = () => {
689
+ if (textArea.current.value === '') {
690
+ stopTyping()
691
+ return
692
+ }
693
+ if (!isTyping) {
694
+ startTyping()
649
695
  }
696
+ clearTimeoutWithReset(true)
650
697
  }
651
698
 
652
699
  const webviewRequestContext = {
@@ -798,6 +845,7 @@ export const Webchat = forwardRef((props, ref) => {
798
845
  autoFocus={true}
799
846
  inputRef={textArea}
800
847
  onKeyDown={e => onKeyDown(e)}
848
+ onKeyUp={onKeyUp}
801
849
  style={{
802
850
  display: 'flex',
803
851
  fontSize: deviceAdapter.fontSize(14),