├── .npmignore ├── .eslintignore ├── .gitignore ├── .eslintrc ├── CHANGELOG.md ├── stories └── react-jotform-embed.story.js ├── .github └── FUNDING.yml ├── .editorconfig ├── .babelrc ├── LICENSE ├── README.md ├── package.json └── src └── react-jotform-embed.js /.npmignore: -------------------------------------------------------------------------------- 1 | * 2 | !lib/* 3 | !LICENSE 4 | -------------------------------------------------------------------------------- /.eslintignore: -------------------------------------------------------------------------------- 1 | /tests/* 2 | /coverage 3 | /src/store/mocks 4 | /lib 5 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | node_modules 2 | .wercker 3 | *.iml 4 | .idea 5 | /lab 6 | /coverage 7 | .storybook 8 | /lib 9 | -------------------------------------------------------------------------------- /.eslintrc: -------------------------------------------------------------------------------- 1 | { 2 | "extends": "xurei/react", 3 | "parser": "babel-eslint", 4 | 5 | "plugins": [ 6 | "promise", 7 | "jsx", 8 | "react", 9 | "react-native", 10 | "security" 11 | ], 12 | 13 | "parserOptions": { 14 | "ecmaVersion": 6, 15 | "sourceType": "module", 16 | "ecmaFeatures": { 17 | "jsx": true 18 | } 19 | }, 20 | "rules": { 21 | "complexity": 0 22 | } 23 | } 24 | -------------------------------------------------------------------------------- /CHANGELOG.md: -------------------------------------------------------------------------------- 1 | # v1.1.3 - 2023-05-13 2 | - Support for React 17 and ulterior 3 | 4 | # v1.1.2 - 2021-09-20 5 | - Add module imports. Thanks to @cncolder 6 | 7 | # v1.1.1 - 2020-11-23 8 | - Add support for pre-population; Thanks to @chug2k 9 | 10 | # v1.1.0 - 2020-10-05 11 | - Added prop `scrolling`; Thanks to @chriscortez for his [PR](https://github.com/xurei/react-jotform-embed/pull/2) 12 | - Transpiled to CommonJS and ES6 for modern stacks 13 | -------------------------------------------------------------------------------- /stories/react-jotform-embed.story.js: -------------------------------------------------------------------------------- 1 | import React from 'react'; //eslint-disable-line no-unused-vars 2 | 3 | import { storiesOf } from '@storybook/react'; 4 | 5 | //import JotformEmbed from '../lib/cjs/react-jotform-embed'; 6 | import JotformEmbed from '../lib/module/react-jotform-embed'; 7 | 8 | storiesOf('JobformEmbed', module) 9 | .add('Simple', () => ) 10 | .add('Scrollable', () => ); 11 | -------------------------------------------------------------------------------- /.github/FUNDING.yml: -------------------------------------------------------------------------------- 1 | # These are supported funding model platforms 2 | 3 | github: xurei 4 | #patreon: # Replace with a single Patreon username 5 | #open_collective: # Replace with a single Open Collective username 6 | #ko_fi: # Replace with a single Ko-fi username 7 | #tidelift: # Replace with a single Tidelift platform-name/package-name e.g., npm/babel 8 | #community_bridge: # Replace with a single Community Bridge project-name e.g., cloud-foundry 9 | #liberapay: # Replace with a single Liberapay username 10 | #issuehunt: # Replace with a single IssueHunt username 11 | #otechie: # Replace with a single Otechie username 12 | #custom: # Replace with up to 4 custom sponsorship URLs e.g., ['link1', 'link2'] 13 | -------------------------------------------------------------------------------- /.editorconfig: -------------------------------------------------------------------------------- 1 | # EditorConfig helps developers define and maintain consistent 2 | # coding styles between different editors and IDEs 3 | # editorconfig.org 4 | 5 | root = true 6 | 7 | [*] 8 | # Change these settings to your own preference 9 | indent_style = tab 10 | indent_size = 4 11 | 12 | # We recommend you to keep these unchanged 13 | end_of_line = lf 14 | charset = utf-8 15 | trim_trailing_whitespace = true 16 | insert_final_newline = true 17 | 18 | [package.json] 19 | # Change these settings to your own preference 20 | indent_style = space 21 | indent_size = 2 22 | 23 | [.eslintrc] 24 | # Change these settings to your own preference 25 | indent_style = space 26 | indent_size = 2 27 | 28 | [*.md] 29 | trim_trailing_whitespace = false 30 | indent_style = space 31 | indent_size = 2 32 | -------------------------------------------------------------------------------- /.babelrc: -------------------------------------------------------------------------------- 1 | { 2 | "presets": [ 3 | ["@babel/preset-env", { 4 | "modules": "commonjs", 5 | "corejs": 3, 6 | "useBuiltIns": "usage", 7 | "targets": { 8 | "node": "6", 9 | "chrome": "40", 10 | "firefox": "40", 11 | "ie": "10", 12 | "edge": "12" 13 | } 14 | }], 15 | "@babel/preset-react" 16 | ], 17 | "plugins": [ 18 | "@babel/plugin-proposal-class-properties" 19 | ], 20 | 21 | "env": { 22 | "module": { 23 | "presets": [ 24 | [ 25 | "@babel/preset-env", 26 | { 27 | "modules": false, 28 | "corejs": 3, 29 | "useBuiltIns": "usage", 30 | "targets": { 31 | "node": "6", 32 | "chrome": "40", 33 | "firefox": "40", 34 | "ie": "10", 35 | "edge": "12" 36 | } 37 | } 38 | ], 39 | "@babel/preset-react" 40 | ], 41 | "plugins": [ 42 | "@babel/plugin-proposal-class-properties" 43 | ] 44 | } 45 | } 46 | } 47 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2017 Olivier Bourdoux 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # react-jotform-embed 2 | 3 | #### ⚠ This project is no more maintained. Check (https://github.com/sbayd/jotform-react) for a more up-to-date alternative. ⚠ 4 | 5 | A rewrite for React of the embedded iframe provided by JotForm [https://www.jotform.com/](https://www.jotform.com/) 6 | 7 | This handles the resize mechanism provided by JotForm. 8 | 9 | [![npm](https://img.shields.io/npm/v/react-jotform-embed.svg)](https://www.npmjs.com/package/react-jotform-embed) 10 | [![GitHub issues](https://img.shields.io/github/issues/xurei/react-jotform-embed.svg)](https://github.com/xurei/react-jotform-embed/issues) 11 | [![Sponsor](https://img.shields.io/static/v1?label=Sponsor&message=%E2%9D%A4&logo=GitHub&link=)](https://github.com/sponsors/xurei) 12 | 13 | ## Install 14 | ``` 15 | npm install react-jotform-embed 16 | ``` 17 | 18 | ## Usage 19 | ```jsx 20 | import JotformEmbed from 'react-jotform-embed'; 21 | 22 | 23 | ``` 24 | 25 | ## Props 26 | - src : The url of your jotform, as given in their publish section. 27 | - scrolling : A boolean to allow or disallow scrolling. Scrolling is turned off by default 28 | 29 | ## Notes 30 | 31 | To pre-populate forms in the field, add them as url params to your form. For example: 32 | 33 | ```jdx 34 | let name = "John"; 35 | 36 | ``` 37 | 38 | ## Support Open-Source 39 | Support my work on https://github.com/sponsors/xurei 40 | -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "react-jotform-embed", 3 | "version": "1.1.3", 4 | "description": "A rewrite for React of the embedded iframe provided by JotForm", 5 | "main": "lib/cjs/react-jotform-embed.js", 6 | "module": "lib/module/react-jotform-embed.js", 7 | "sideEffects": false, 8 | "files": [ 9 | "lib" 10 | ], 11 | "scripts": { 12 | "test": "echo 'no test specified'", 13 | "pretest": "node_modules/.bin/eslint .", 14 | "preversion": "npm test", 15 | "build": "rimraf lib/* && npm run build:module && npm run build:cjs", 16 | "build:module": "BABEL_ENV=module node_modules/.bin/babel src -d lib/module", 17 | "build:cjs": "node_modules/.bin/babel src -d lib/cjs", 18 | "prepublishOnly": "npm run build", 19 | "storybook": "start-storybook -p 6006", 20 | "build-storybook": "build-storybook" 21 | }, 22 | "keywords": [ 23 | "react", 24 | "jotform", 25 | "resize" 26 | ], 27 | "author": "Olivier Bourdoux", 28 | "license": "MIT", 29 | "repository": { 30 | "type": "git", 31 | "url": "git+https://github.com/xurei/react-jotform-embed.git" 32 | }, 33 | "peerDependencies": { 34 | "react": ">= 15.0.0", 35 | "react-dom": ">= 15.0.0", 36 | "prop-types": ">= 15.0.0" 37 | }, 38 | "devDependencies": { 39 | "@babel/cli": "^7.11.6", 40 | "@babel/core": "^7.11.6", 41 | "@babel/plugin-proposal-class-properties": "^7.2.3", 42 | "@babel/preset-env": "^7.11.5", 43 | "@babel/preset-react": "^7.10.4", 44 | "@storybook/react": "^6.0.26", 45 | "babel-eslint": "^10.1.0", 46 | "babel-loader": "^8.1.0", 47 | "eslint": "^7.0.0", 48 | "eslint-config-xurei": "^1.1.1", 49 | "eslint-plugin-jsx": "0.1.0", 50 | "eslint-plugin-promise": "^4.2.0", 51 | "eslint-plugin-react": "^7.21.3", 52 | "eslint-plugin-react-native": "^3.5.0", 53 | "eslint-plugin-security": "^1.4.0", 54 | "react": "^16.0.0", 55 | "react-dom": "^16.0.0", 56 | "rimraf": "^3.0.2" 57 | }, 58 | "dependencies": { 59 | "core-js": "^3.0.0" 60 | } 61 | } 62 | -------------------------------------------------------------------------------- /src/react-jotform-embed.js: -------------------------------------------------------------------------------- 1 | import 'core-js/stable'; 2 | 3 | const React = require('react'); //eslint-disable-line no-unused-vars 4 | const ReactDOM = require('react-dom'); 5 | const PropTypes = require('prop-types'); 6 | 7 | const iframeStyle = { 8 | width: '100%', 9 | height: '300px', 10 | }; 11 | 12 | export default class JotformEmbed extends React.Component { 13 | static propTypes = { 14 | src: PropTypes.string.isRequired, 15 | className: PropTypes.string, 16 | scrolling: PropTypes.bool, 17 | }; 18 | 19 | constructor(props) { 20 | super(props); 21 | this.handleIframeMessage = this.handleIframeMessage.bind(this); 22 | } 23 | 24 | handleIframeMessage(e) { 25 | const props = this.props; 26 | if (!e.data.split) { 27 | return; 28 | } 29 | const args = e.data.split(':'); 30 | const formId = args[2]; 31 | const iframe = ReactDOM.findDOMNode(this.refs.iframe); 32 | if (!!iframe && (!formId || props.src.split('?')[0].endsWith(formId))) { 33 | switch (args[0]) { 34 | case 'scrollIntoView': 35 | iframe.scrollIntoView(); 36 | break; 37 | case 'setHeight': 38 | iframe.style.height = `${args[1]}px`; 39 | break; 40 | case 'collapseErrorPage': 41 | if (iframe.clientHeight > global.innerHeight) { 42 | iframe.style.height = `${global.innerHeight}px`; 43 | } 44 | break; 45 | case 'reloadPage': 46 | global.location.reload(); 47 | break; 48 | } 49 | const isJotForm = (e.origin.indexOf('jotform') > -1); 50 | if (isJotForm && 'contentWindow' in iframe && 'postMessage' in iframe.contentWindow) { 51 | const urls = { 52 | 'docurl': encodeURIComponent(global.document.URL), 53 | 'referrer': encodeURIComponent(global.document.referrer), 54 | }; 55 | iframe.contentWindow.postMessage(JSON.stringify({'type': 'urls', 'value': urls}), '*'); 56 | } 57 | } 58 | } 59 | 60 | componentWillMount() { 61 | if (global.addEventListener) { 62 | global.addEventListener('message', this.handleIframeMessage, false); 63 | } 64 | else if (global.attachEvent) { 65 | global.attachEvent('onmessage', this.handleIframeMessage); 66 | } 67 | } 68 | 69 | componentWillUnmount() { 70 | if (global.removeEventListener) { 71 | global.removeEventListener('message', this.handleIframeMessage, false); 72 | } 73 | else if (global.detachEvent) { 74 | global.detachEvent('onmessage', this.handleIframeMessage); 75 | } 76 | } 77 | 78 | render() { 79 | const props = this.props; 80 | return ( 81 |