[{"data":1,"prerenderedAt":108},["ShallowReactive",2],{"blog-how-to-create-conversational-forms-for-your-website":3},{"blogData":4,"relatedArticles":29},{"id":5,"title":6,"author":7,"authorImage":8,"authorProfile":9,"coverImg":10,"coverImgAlt":11,"createdAt":12,"description":13,"featured":14,"jsonld":15,"keywords":16,"metaDescription":17,"metaImage":18,"metaTitle":19,"publishedAt":20,"slug":21,"updatedAt":22,"__hash__":23,"body":24,"coverImgWidth":25,"coverImgHeight":26,"readingStats":27},"blog\u002Fblog\u002Fhow-to-create-conversational-forms-for-your-website.md","How to create conversational forms for your websites?","Harish Kumar",null,"https:\u002F\u002Fwww.linkedin.com\u002Fin\u002Fharish-kumar2424\u002F","https:\u002F\u002Fformester-strapi.s3.ap-south-1.amazonaws.com\u002Fa_blog_post_cover_about_conversational_forms_c6e3ceb7ac.png","a blog post cover about conversational forms","2025-08-25T02:16:28.704Z","Turn long, boring forms into interactive conversations. Discover how to build conversational forms for your website that capture more responses with ease.",false,[],"form builders,\nuser experience,\nprogress bars,\ncompletion rates,\ncustomizing options,\nconversational forms,\ncard style form,","Learn how to create conversational forms that reduce form abandonment, engage users like a chat, and boost conversions on your website.",[],"How to create conversational forms for your websites","2025-08-25T02:18:10.923Z","how-to-create-conversational-forms-for-your-website","2025-12-01T12:22:43.972Z","EHKENlNCPRbA-Iw3Gr_I4DGW7jprt2zDFWJzj5ze1nA","\u003Ciframe width=\"100%\" height=\"315\" src=\"https:\u002F\u002Fwww.youtube.com\u002Fembed\u002FK0yLhsVQDLE?si=XjyFJu11UsfKp0Fp\" title=\"YouTube video player\" frameborder=\"0\" allow=\"accelerometer; autoplay; clipboard-write; encrypted-media; gyroscope; picture-in-picture; web-share\" referrerpolicy=\"strict-origin-when-cross-origin\" allowfullscreen>\u003C\u002Fiframe>\n\nAre you dealing with **high drop-off rates** in your forms and surveys? You’re not alone. Many businesses face the same problem. The reason is simple: forms are often too long, too generic, and too boring.\n\nWhen users feel overwhelmed by endless questions, they abandon the form halfway through. That means lost leads, fewer conversions, and wasted opportunities.\n\nThe solution? **Conversational forms.**\n\nUnlike static forms, conversational forms guide users through one question at a time in a **card style form layout**. They feel interactive, personal, and engaging. This creates a better user experience, which directly improves completion rates. \n\n## How to Build a Conversational Form?\nFollow the steps below to create highly engaging forms in Formester.\n\n### Step 1: Create Your Form in Formester\n![a screenshot of Formester's AI form builder](https:\u002F\u002Fformester-strapi.s3.ap-south-1.amazonaws.com\u002Fa_screenshot_of_Formester_s_AI_form_builder_eb651c7d3d.png)\n\n**You can start in two ways:**\n\n**[AI Form Builder](\u002Fai-form-generator\u002F)**: Simply describe the type of form you want — for example, job application or customer feedback. Within seconds, Formester’s AI will generate a complete form for you.\n\nImport Existing Form: Already have a form? Just bring it into Formester to transform it into a conversational experience.\n\nOnce your form is ready, review the fields. Ensure you include everything you need. If not, open the Add Elements tab and insert new questions or input fields.\n\n### Step 2: Turn It Into a Conversation\n![a screenshot of converting long form into conversational form in Formester](https:\u002F\u002Fformester-strapi.s3.ap-south-1.amazonaws.com\u002Fa_screenshot_of_converting_long_form_into_conversational_form_in_Formester_1be43f6871.png)\n\n**Here’s where the magic happens.**\n\nClick the three dots on the page title and select **One field per page**. This breaks down your form into a card style flow where users see only one question at a time. It feels less like a chore and more like a conversation.\n\nTo boost engagement further, you can add visuals. Insert images on each page, align them to the left, right, or even use them as a background. Pair this with progress bars to help users always know how far they’ve come and how much is left. This small addition helps improve completion rates because it reduces uncertainty.\n\n### Step 3: Personalize with Information Recall\n![a screenshot of Formester's information recall feature](https:\u002F\u002Fformester-strapi.s3.ap-south-1.amazonaws.com\u002Fa_screenshot_of_Formester_s_information_recall_feature_3496179e0f.png)\n\nStatic forms ask questions without context. Conversational forms, on the other hand, can remember and reuse previous answers.\n\nFormester allows you to use the **@ symbol** inside labels and descriptions to **[recall earlier inputs](\u002Ffeatures\u002Finformation-recall\u002F)**. **For example:**\n\nIf someone enters their name as **Harish**, the next question can say:\n\n >“Thanks, Harish. Can you tell us more about your goals?”\n\nThis small touch creates a natural, human-like flow. You can recall details like name, email, company, or preferences. It makes the form feel like it’s speaking directly to the user, which keeps them engaged until the end.\n\n### Step 4: Apply Conditional Logic\n![a screenshot of Formester's conditional logic feature](https:\u002F\u002Fformester-strapi.s3.ap-south-1.amazonaws.com\u002Fa_screenshot_of_Formester_s_conditional_logic_feature_30b1b6fa92.png)\n\nThe next step is to make your form smart. With **[conditional logic](\u002Fblog\u002Fwhat-is-conditional-logic-how-to-use-it\u002F)**, you can show or hide follow-up questions in real time.\n\n**Here’s an example:**\n\n>If someone selects “Yes, I own a business,” show them more questions about their company.\n\n>If they select “No,” skip those questions and move on.\n\nThis way, every user only sees what’s relevant to them. The form feels shorter, more personal, and less overwhelming, reducing drop-offs dramatically.\n\n**To set this up in Formester:**\n\n- Go to Advanced > Rules\n\n- Click Add New Rule\n\n- Choose the question for your “if” statement\n\n- Set the condition\n\n- Define what should happen next\n\nThat’s it. Your form now adapts in real time to each user.\n\n### Step 5: Customize, Publish, and Share\n\n**Now comes the fun part**. In Formester, you can tweak colors, layouts, fonts, and **background images** to align the form with your brand. These design details may seem small, but they really enhance the user experience. They also encourage users to finish their journey.\n\nOnce your chat form is ready, you can put it on your website. You can also share the link directly or add it to landing pages. Your form is now made to keep people interested until the end. It helps you capture leads, **collect feedback**, and qualify prospects.\n\n### Final Thoughts\nLong, boring forms are conversion killers. But with conversational forms, you turn that frustrating process into a dynamic, engaging interaction. By using card style forms, progress bars, and customization options, you create a smooth user experience. This helps increase completion rates and reduce abandonment.\n\nWith Formester, you can make forms in minutes using AI. You can personalize them with information recall.\n\nYou can also add smart features with conditional logic. The result? Fewer drop-offs, more completions, and happier users.\n\nReady to try it yourself? Build your first conversational form with **[Formester today](https:\u002F\u002Fapp.formester.com\u002Fusers\u002Fsign_up)**.\n",1214,630,{"text":28},"4 min read",[30,51,70,91],{"title":31,"author":32,"authorImage":8,"authorProfile":33,"coverImg":34,"coverImgAlt":35,"createdAt":36,"description":37,"featured":14,"jsonld":38,"keywords":39,"metaDescription":40,"metaImage":41,"metaTitle":42,"publishedAt":43,"slug":44,"updatedAt":45,"__hash__":46,"body":47,"id":48,"coverImgWidth":25,"coverImgHeight":26,"readingStats":49},"How to Track Form Submissions Using Hidden Fields","Harsh Shah","https:\u002F\u002Flinkedin.com\u002Fin\u002Fharshshahseo","https:\u002F\u002Fformester-strapi.s3.ap-south-1.amazonaws.com\u002F53_ee59adbe17.png","a blog post cover about how to track form conversions using hidden fields","2025-07-18T01:54:33.648Z","Discover how to track form submissions using UTM parameters and hidden fields in online forms, no need for Google Analytics or code.\n\n",[],"hidden fields,\nutm tracking,\nconversion tracking,\nform submission tracking,","Learn how to track form submissions using UTM parameters and hidden fields in online forms, no need for Google Analytics or code.\n\n",[],"How to Track Form Conversions Using Hidden Fields","2026-06-22T05:06:22.803Z","how-to-track-form-conversions-using-hidden-form-fields","2026-06-22T05:06:29.664Z","xywQJ6W_GdLucg_-NySVhFSePITQ-d-v5xighU0KyEM","\u003Cp style=\"font-size: inherit;\">You spent the budget. A lead just filled out your form. Which channel sent them, the LinkedIn ad, the newsletter, or the blog popup?\u003C\u002Fp>\n\n\u003Cp>Here is the short answer: tag your form link with UTM parameters, add a few hidden fields, and every submission carries its own source. No Google Analytics, no code, no extra tools.\u003C\u002Fp>\n\n\u003Cp>This guide shows the exact steps inside \u003Ca href=\"https:\u002F\u002Fformester.com\u002F\">Formester\u003C\u002Fa>, from building a tagged URL to filtering leads by source and exporting them. It takes a few minutes to set up once.\u003C\u002Fp>\n\n\u003Ch2>What Are UTM Parameters? (The 5 Tags Explained)\u003C\u002Fh2>\n\n\u003Cp>UTM parameters are small tags you add to the end of a link. When someone clicks a tagged link, the tags travel with them, so you can see exactly where the click came from.\u003C\u002Fp>\n\n\u003Cp>There are five, and three do most of the work:\u003C\u002Fp>\n\n\u003Cul>\n\u003Cli>\u003Cstrong>utm_source\u003C\u002Fstrong>: Where the traffic came from: linkedin, newsletter, google.\u003C\u002Fli>\n\u003Cli>\u003Cstrong>utm_medium\u003C\u002Fstrong>: The type of channel: paid, email, social, organic.\u003C\u002Fli>\n\u003Cli>\u003Cstrong>utm_campaign\u003C\u002Fstrong>: The specific campaign: crm_demo_july, spring_sale.\u003C\u002Fli>\n\u003Cli>\u003Cstrong>utm_term and utm_content\u003C\u002Fstrong>: Optional. utm_term records the paid keyword; utm_content tells two versions of the same link apart (for example, two buttons in one email).\u003C\u002Fli>\n\u003C\u002Ful>\n\n\u003Cp>A tagged form link looks like this: https:\u002F\u002Fyourform.com\u003Cwbr>?utm_source=linkedin\u003Cwbr>&amp;utm_medium=paid\u003Cwbr>&amp;utm_campaign=crm_demo. Spend money on marketing, and you should know which of those tags actually convert.\u003C\u002Fp>\n\n\u003Ch2>How to Track UTM Parameters in Your Forms: 5 Steps\u003C\u002Fh2>\n\n\u003Cp>Five steps, start to finish. Build the form, tag the link, add hidden fields, test it, then filter and export. You only set this up once per form.\u003C\u002Fp>\n\n\u003Ch3>Step 1: Build Your Lead Capture Form\u003C\u002Fh3>\n\n\u003Cp>Open your Formester dashboard and create a new \u003Ca href=\"https:\u002F\u002Fformester.com\u002Ftemplates\u002Fcategories\u002Flead-generation\u002F\">lead capture form\u003C\u002Fa>. Add the visible fields you actually need: name, email, company. Keep it short; every extra field costs you submissions.\u003C\u002Fp>\n\n\u003Ch3>Step 2: Build a UTM-Tagged Link\u003C\u002Fh3>\n\n\u003Cp>You need a version of your form link with UTM tags baked in. The easiest way is Google's free Campaign URL Builder.\u003C\u002Fp>\n\n\u003Cul>\n\u003Cli>Open Google's Campaign URL Builder (search \"campaign url builder\"; it is the first result).\u003C\u002Fli>\n\u003Cli>Paste your form URL into the Website URL field.\u003C\u002Fli>\n\u003Cli>Fill in source (linkedin), medium (paid), and campaign (crm_demo_july).\u003C\u002Fli>\n\u003C\u002Ful>\n\n\u003Cp>The builder hands you a full tagged URL. Want it tidy for an ad or bio link? Shorten it with Bitly. Make one tagged link per channel so each source stays clean.\u003C\u002Fp>\n\n\u003Ch3>Step 3: Add Hidden Fields That Auto-Fill From the URL\u003C\u002Fh3>\n\n\u003Cp>This is the part that does the work. A hidden field sits on the form, invisible to the visitor, and quietly reads its value from the URL.\u003C\u002Fp>\n\n\u003Cul>\n\u003Cli>In the Formester builder, add a single line input field.\u003C\u002Fli>\n\u003Cli>Rename the field label to match the tag exactly: utm_source.\u003C\u002Fli>\n\u003Cli>Click the eye icon to hide it from view.\u003C\u002Fli>\n\u003C\u002Ful>\n\n\u003Cp>Repeat for each tag you want to capture: utm_medium, utm_campaign, and campaign_id if you use one. The field name has to match the UTM tag character for character, or it stays blank.\u003C\u002Fp>\n\n\u003Cp>Now, when a visitor lands on the form from your tagged link, those hidden fields fill themselves in. It is the same mechanism as \u003Ca href=\"https:\u002F\u002Fformester.com\u002Fblog\u002Fhow-to-pre-fill-form-fields-by-url-parameters\u002F\">prefilling form fields from URL parameters\u003C\u002Fa>, pointed at attribution instead of convenience.\u003C\u002Fp>\n\n\u003Ch3>Step 4: Test It Before You Launch\u003C\u002Fh3>\n\n\u003Cp>Never trust attribution you have not tested. Open your tagged form link in a new browser tab, fill it out, and hit submit.\u003C\u002Fp>\n\n\u003Cp>Then open your Formester dashboard, go to the form, and open Results. Click the latest submission. You should see the hidden values captured alongside the visible ones: source linkedin, medium paid, campaign crm_demo_july.\u003C\u002Fp>\n\n\u003Cp>Run it again with a second tagged link, say source google and medium organic, and confirm the two submissions show different sources. If a field is blank, the field name and the UTM tag do not match yet.\u003C\u002Fp>\n\n\u003Ch3>Step 5: Filter, Export, and Sync Your Leads by Source\u003C\u002Fh3>\n\n\u003Cp>This is the payoff. Want every lead that came from LinkedIn?\u003C\u002Fp>\n\n\u003Cul>\n\u003Cli>Open the Results tab.\u003C\u002Fli>\n\u003Cli>In Filters, set utm_source = linkedin.\u003C\u002Fli>\n\u003Cli>Read the filtered list, or export it as a CSV in one click.\u003C\u002Fli>\n\u003C\u002Ful>\n\n\u003Cp>To keep the data flowing automatically, connect the form to \u003Ca href=\"https:\u002F\u002Fformester.com\u002Fintegrations\u002Fgoogle-sheets\u002F\">Google Sheets\u003C\u002Fa> or push leads straight into \u003Ca href=\"https:\u002F\u002Fformester.com\u002Fintegrations\u002Fhubspot\u002F\">HubSpot\u003C\u002Fa>. The UTM values ride along with each lead, so your sales and email tools know the source without anyone copying it by hand.\u003C\u002Fp>\n\n\u003Ch2>Hidden Fields vs Google Analytics vs GTM: Which to Use\u003C\u002Fh2>\n\n\u003Cp>These three approaches answer different questions, so plenty of teams run more than one.\u003C\u002Fp>\n\n\u003Cul>\n\u003Cli>\u003Cstrong>Hidden fields\u003C\u002Fstrong>: Tag the submission itself. The source lands inside your results, CSV, and CRM next to the lead. Best when you care about which channel produced an actual lead, not just a visit. No code, no setup.\u003C\u002Fli>\n\u003Cli>\u003Cstrong>Google Analytics\u003C\u002Fstrong>: Tracks the page visit and traffic shape. Great for top-of-funnel volume, weaker at tying a single lead to a single source. Formester also offers a native \u003Ca href=\"https:\u002F\u002Fformester.com\u002Fintegrations\u002Fgoogle-analytics\u002F\">Google Analytics integration\u003C\u002Fa> if you want both views.\u003C\u002Fli>\n\u003Cli>\u003Cstrong>Google Tag Manager\u003C\u002Fstrong>: Fires events when a form is submitted, useful for sending conversions to ad platforms. More moving parts, and it still does not store the source on the lead record. Connect it through Formester's \u003Ca href=\"https:\u002F\u002Fformester.com\u002Fintegrations\u002Fgoogle-tag-manager\u002F\">Google Tag Manager integration\u003C\u002Fa>.\u003C\u002Fli>\n\u003C\u002Ful>\n\n\u003Cp>Short version: use hidden fields for lead-level attribution, Analytics for traffic, GTM for ad-conversion events. The hidden-field method is the one that needs no setup and travels with the data.\u003C\u002Fp>\n\n\u003Ch2>Why Hidden Fields Beat the Alternatives\u003C\u002Fh2>\n\n\u003Cul>\n\u003Cli>No setup in Google Analytics and no scripts to maintain.\u003C\u002Fli>\n\u003Cli>Source data lives on the submission, not buried in a separate analytics report.\u003C\u002Fli>\n\u003Cli>Per-lead, not per-visit: you know which channel produced the actual form fill.\u003C\u002Fli>\n\u003Cli>Works the same across popups, landing pages, and \u003Ca href=\"https:\u002F\u002Fformester.com\u002Ffeatures\u002Fembed-forms\u002F\">embedded forms\u003C\u002Fa>.\u003C\u002Fli>\n\u003C\u002Ful>\n\n\u003Cp>Paid ads, influencer drops, content marketing: whatever the channel, every lead points back to its source.\u003C\u002Fp>\n\n\u003Ch2>Why Your Hidden Fields Might Come Back Empty\u003C\u002Fh2>\n\n\u003Cp>If a submission arrives with blank UTM fields, one of these is usually the reason:\u003C\u002Fp>\n\n\u003Cul>\n\u003Cli>The visitor came directly, from a bookmark, or from an untagged link. No tags in the URL means nothing to capture. That is expected for organic and direct traffic.\u003C\u002Fli>\n\u003Cli>The field name does not match the UTM tag exactly. utm_source captures; UTM_Source or utm-source does not.\u003C\u002Fli>\n\u003Cli>A redirect or link wrapper stripped the parameters before the form loaded. Test the final landing URL, not the link you pasted.\u003C\u002Fli>\n\u003C\u002Ful>\n\n\u003Cp>Treat blank values as a signal, not a bug. They tell you which share of leads arrived without a tracked campaign, which is useful to know on its own.\u003C\u002Fp>\n\n\u003Ch2>Start Tracking Every Lead's Source\u003C\u002Fh2>\n\n\u003Cp>Knowing where a lead came from changes how you spend. Double down on the channels that convert, cut the ones that just spend.\u003C\u002Fp>\n\n\u003Cp>Hidden fields give you that without a single line of code. Tag the link, add the fields, and the source rides along with every submission into your results, your spreadsheet, and your CRM.\u003C\u002Fp>\n\n\u003Cp>Want to see it work? \u003Ca href=\"https:\u002F\u002Fapp.formester.com\u002Fusers\u002Fsign_up\u002F\">Build a form free\u003C\u002Fa>, tag a link, and watch the first source land in your results. From there, \u003Ca href=\"https:\u002F\u002Fformester.com\u002Ffeatures\u002Fform-analytics\u002F\">form analytics\u003C\u002Fa> shows you the rest of the picture.\u003C\u002Fp>\n\n\u003Csection class=\"faq\">\n\u003Ch2>Frequently Asked Questions\u003C\u002Fh2>\n\u003Cdetails>\u003Csummary>How do I track which campaign a form submission came from?\u003C\u002Fsummary>\u003Cdiv>Tag your form link with UTM parameters, then add hidden fields named utm_source, utm_medium, and utm_campaign to the form. When someone opens the tagged link, those fields auto-fill, so every submission carries its own source.\u003C\u002Fdiv>\u003C\u002Fdetails>\n\u003Cdetails>\u003Csummary>What are the five UTM parameters?\u003C\u002Fsummary>\u003Cdiv>utm_source (where the traffic came from), utm_medium (the channel type), utm_campaign (the campaign name), utm_term (paid keyword), and utm_content (which link or ad variant). Source, medium, and campaign are the three most teams use.\u003C\u002Fdiv>\u003C\u002Fdetails>\n\u003Cdetails>\u003Csummary>Can I track form sources without Google Analytics?\u003C\u002Fsummary>\u003Cdiv>Yes. Hidden fields capture the UTM values on the form itself, so the source is stored with the submission. You can filter and export that data without setting up Google Analytics or writing any code.\u003C\u002Fdiv>\u003C\u002Fdetails>\n\u003Cdetails>\u003Csummary>Why are my hidden UTM fields coming back blank?\u003C\u002Fsummary>\u003Cdiv>Hidden fields only fill when the link carries UTM parameters. Direct visits, bookmarked links, and some redirects strip the tags, so those submissions arrive empty. Always share the full tagged URL and test it before launching.\u003C\u002Fdiv>\u003C\u002Fdetails>\n\u003Cdetails>\u003Csummary>What is the difference between UTM hidden fields and Google Analytics tracking?\u003C\u002Fsummary>\u003Cdiv>Google Analytics tracks the page visit. Hidden fields tag the actual submission, so the source travels with the lead into your results, CRM, or spreadsheet. Many teams use both: Analytics for traffic, hidden fields for lead-level attribution.\u003C\u002Fdiv>\u003C\u002Fdetails>\n\u003C\u002Fsection>\n\n","blog\u002Fblog\u002Fhow-to-track-form-conversions-using-hidden-form-fields.md",{"text":50},"7 min read",{"title":52,"author":7,"authorImage":8,"authorProfile":9,"coverImg":53,"coverImgAlt":54,"createdAt":55,"description":56,"featured":14,"jsonld":57,"keywords":58,"metaDescription":59,"metaImage":60,"metaTitle":61,"publishedAt":62,"slug":63,"updatedAt":64,"__hash__":65,"body":66,"id":67,"coverImgWidth":25,"coverImgHeight":26,"readingStats":68},"How to Make a Feedback Form in HTML (with Code, CSS, and a Backend)","https:\u002F\u002Fformester-strapi.s3.ap-south-1.amazonaws.com\u002Fan_illustration_of_how_to_make_feedback_form_in_html_c6203dc935.png","an illustration of how to make feedback form in html","2024-06-27T06:19:40.031Z","Learn how to create a feedback form in HTML with easy steps. Set up an HTML document, add form fields, style with CSS, and add JavaScript for validation. Test your form and start collecting feedback.",[],"feedback forms, fillable freedback form, how to make feedback form in html, style feedback form with css, feedback form html code","Build a working feedback form in HTML with copy-paste code, CSS styling, JavaScript validation, accessibility, and a backend that stores submissions without a server.",[],"How to Make a Feedback Form in HTML (Code, CSS, Validation, Backend)","2026-05-17T04:46:01.940Z","how-to-make-feedback-form-in-html","2026-05-17T04:46:01.948Z","wyyctYTKwdEs6QGo1-xhuZdxYoLFow0lRYEcN7glo1g","![an illustration of how to make feedback form in html](https:\u002F\u002Fformester-strapi.s3.ap-south-1.amazonaws.com\u002Fan_illustration_of_how_to_make_feedback_form_in_html_c6203dc935.png)\n\n\u003Cstyle>\n\u002F* host-link-override *\u002F\n.fmstr-cmp-ffh-body a { text-decoration: none !important; }\n.fmstr-cmp-ffh-body {\n--c-bg-card: #ffffff;\n--c-bg-soft: #f9fafb;\n--c-fg-1: #101828; --c-fg-2: #475467; --c-fg-3: #697586;\n--c-violet-500: #7f56d9; --c-violet-600: #6941c6;\n--c-tint: #f7f3ff; --c-edge: #e4d7ff; --c-border: #eaecf0;\n--c-code-bg: #0f172a; --c-code-fg: #e2e8f0;\n--c-code-keyword: #a78bfa; --c-code-attr: #67e8f9; --c-code-string: #fcd34d; --c-code-comment: #64748b;\n--c-warn-bg: #fef3c7; --c-warn-fg: #92400e; --c-warn-edge: #fde68a;\n\nbackground: transparent; padding: 24px;\nfont-family: inherit;\ncolor: var(--c-fg-1);\n}\n.fmstr-cmp-ffh-body *, .fmstr-cmp-ffh-body *::before, .fmstr-cmp-ffh-body *::after { box-sizing: border-box; }\n.fmstr-cmp-ffh-body__container { max-width: 820px; margin: 0 auto; }\n\n.fmstr-cmp-ffh-body__intro p { font-size: 17px; line-height: 1.7; color: var(--c-fg-2); margin: 0 0 16px; }\n.fmstr-cmp-ffh-body__intro a { color: var(--c-violet-600) !important; text-decoration: none !important; font-weight: 500; }\n.fmstr-cmp-ffh-body__intro a:hover { text-decoration: underline !important; }\n.fmstr-cmp-ffh-body__intro code { background: var(--c-tint); color: var(--c-violet-600); padding: 2px 6px; border-radius: 4px; font-family: ui-monospace, Menlo, Consolas, monospace; font-size: 14.5px; border: 1px solid var(--c-edge); }\n\n.fmstr-cmp-ffh-body__h2 {\nfont-size: 28px; font-weight: 700; line-height: 1.25; letter-spacing: -.02em;\nmargin: 40px 0 16px; color: var(--c-fg-1);\n}\n.fmstr-cmp-ffh-body__h3 {\nfont-size: 20px; font-weight: 700; line-height: 1.35; letter-spacing: -.01em;\nmargin: 28px 0 12px; color: var(--c-fg-1);\n}\n.fmstr-cmp-ffh-body p { font-size: 16px; line-height: 1.7; color: var(--c-fg-2); margin: 0 0 14px; }\n.fmstr-cmp-ffh-body p strong { color: var(--c-fg-1); }\n.fmstr-cmp-ffh-body a { color: var(--c-violet-600) !important; text-decoration: none !important; font-weight: 500; }\n.fmstr-cmp-ffh-body a:hover { text-decoration: underline !important; }\n.fmstr-cmp-ffh-body ul, .fmstr-cmp-ffh-body ol { margin: 0 0 16px; padding-left: 22px; }\n.fmstr-cmp-ffh-body li { font-size: 16px; line-height: 1.7; color: var(--c-fg-2); margin: 6px 0; }\n.fmstr-cmp-ffh-body li strong { color: var(--c-fg-1); }\n.fmstr-cmp-ffh-body code { background: var(--c-tint); color: var(--c-violet-600); padding: 2px 6px; border-radius: 4px; font-family: ui-monospace, Menlo, Consolas, monospace; font-size: 14.5px; border: 1px solid var(--c-edge); }\n\n.fmstr-cmp-ffh-body__code {\nbackground: var(--c-code-bg); color: var(--c-code-fg);\nborder-radius: 12px; padding: 18px 20px; margin: 8px 0 18px;\noverflow-x: auto;\nfont-family: ui-monospace, Menlo, Consolas, monospace; font-size: 13.5px; line-height: 1.6;\n}\n.fmstr-cmp-ffh-body__code pre { margin: 0; }\n.fmstr-cmp-ffh-body__code code {\nbackground: transparent !important; color: inherit !important; padding: 0; border: 0;\nfont-family: inherit !important; font-size: inherit;\n}\n.fmstr-cmp-ffh-body__code .kw { color: var(--c-code-keyword); }\n.fmstr-cmp-ffh-body__code .at { color: var(--c-code-attr); }\n.fmstr-cmp-ffh-body__code .st { color: var(--c-code-string); }\n.fmstr-cmp-ffh-body__code .cm { color: var(--c-code-comment); font-style: italic; }\n.fmstr-cmp-ffh-body__code .lang { display: inline-block; font-size: 11px; font-weight: 700; letter-spacing: .08em; text-transform: uppercase; padding: 3px 10px; border-radius: 6px; background: rgba(255,255,255,.1); color: rgba(255,255,255,.7); margin: 0 0 12px; }\n\n.fmstr-cmp-ffh-body__note {\nmargin: 14px 0 18px; padding: 14px 18px;\nbackground: var(--c-bg-soft); border-left: 3px solid var(--c-violet-500);\nborder-radius: 8px; font-size: 15.5px; color: var(--c-fg-2); line-height: 1.6;\n}\n.fmstr-cmp-ffh-body__note strong { color: var(--c-fg-1); }\n.fmstr-cmp-ffh-body__note--warn { background: var(--c-warn-bg); border-left-color: var(--c-warn-fg); }\n.fmstr-cmp-ffh-body__note--warn strong { color: var(--c-warn-fg); }\n\n.fmstr-cmp-ffh-body__variants {\ndisplay: grid; grid-template-columns: 1fr; gap: 14px; margin: 12px 0 24px;\n}\n.fmstr-cmp-ffh-body__variant {\nbackground: var(--c-bg-card); border: 1px solid var(--c-border); border-radius: 14px;\npadding: 18px 22px;\n}\n.fmstr-cmp-ffh-body__variant h4 {\nfont-size: 16px; font-weight: 700; color: var(--c-fg-1);\nmargin: 0 0 8px; line-height: 1.35;\n}\n.fmstr-cmp-ffh-body__variant p { font-size: 15px; line-height: 1.65; color: var(--c-fg-2); margin: 0; }\n\n@media (max-width: 760px) {\n.fmstr-cmp-ffh-body { padding: 16px; }\n.fmstr-cmp-ffh-body__intro p, .fmstr-cmp-ffh-body p, .fmstr-cmp-ffh-body li { font-size: 15.5px; }\n.fmstr-cmp-ffh-body__h2 { font-size: 24px; margin-top: 32px; }\n.fmstr-cmp-ffh-body__h3 { font-size: 18.5px; }\n.fmstr-cmp-ffh-body__code { padding: 14px 16px; font-size: 12.5px; border-radius: 10px; }\n.fmstr-cmp-ffh-body__variant { padding: 16px 18px; }\n}\n\u003C\u002Fstyle>\n\n\u003Csection class=\"fmstr-cmp-ffh-body\" aria-label=\"How to make a feedback form in HTML\">\n\u003Cdiv class=\"fmstr-cmp-ffh-body__container\">\n\n\u003Cdiv class=\"fmstr-cmp-ffh-body__intro\">\n\u003Cp>A feedback form in HTML is twenty lines of markup, a bit of CSS, and one decision that trips up almost everyone: what happens after the user clicks Submit?\u003C\u002Fp>\n\u003Cp>This guide ships the full pattern. You'll get a working \u003Ccode>&lt;form&gt;\u003C\u002Fcode> with name, email, and message fields, CSS that styles it without a framework, JavaScript validation that doesn't break keyboard users, and three honest options for the backend, including one that needs zero server code. Paste the snippets in order, swap the action URL, and you have a live feedback form on your site in about ten minutes.\u003C\u002Fp>\n\u003Cp>If you want to skip the code entirely, \u003Ca href=\"https:\u002F\u002Fformester.com\u002Ffeatures\u002Fdrag-and-drop-form-builder\u002F\">Formester's drag-and-drop builder\u003C\u002Fa> ships a feedback form you can \u003Ca href=\"https:\u002F\u002Fformester.com\u002Ffeatures\u002Fembed-forms\u002F\">embed in any HTML page\u003C\u002Fa> with one snippet. Keep reading for the hand-coded path.\u003C\u002Fp>\n\u003C\u002Fdiv>\n\n\u003Ch2 class=\"fmstr-cmp-ffh-body__h2\">What a feedback form in HTML actually needs\u003C\u002Fh2>\n\u003Cp>Four pieces, in order:\u003C\u002Fp>\n\u003Cul>\n\u003Cli>\u003Cstrong>A \u003Ccode>&lt;form&gt;\u003C\u002Fcode> element\u003C\u002Fstrong> with the right \u003Ccode>action\u003C\u002Fcode> and \u003Ccode>method\u003C\u002Fcode> so the browser knows where to send data.\u003C\u002Fli>\n\u003Cli>\u003Cstrong>Labeled inputs\u003C\u002Fstrong> for the fields you care about (name, email, rating, message), with \u003Ccode>name\u003C\u002Fcode> attributes so the server can read them.\u003C\u002Fli>\n\u003Cli>\u003Cstrong>Validation\u003C\u002Fstrong> on the client (for user experience) and on the server (for trust).\u003C\u002Fli>\n\u003Cli>\u003Cstrong>A backend\u003C\u002Fstrong> that receives the submission, stores it, and ideally notifies you. This is the part most tutorials skip; it's the part you need most.\u003C\u002Fli>\n\u003C\u002Ful>\n\u003Cp>Below, each piece is a separate step with a copy-paste block. The last step is a single complete file you can save as \u003Ccode>feedback.html\u003C\u002Fcode> and open in a browser.\u003C\u002Fp>\n\n\u003Ch2 class=\"fmstr-cmp-ffh-body__h2\">Step 1: Set up the HTML document\u003C\u002Fh2>\n\u003Cp>Save this as \u003Ccode>feedback.html\u003C\u002Fcode>. It's the shell every form goes inside.\u003C\u002Fp>\n\u003Cdiv class=\"fmstr-cmp-ffh-body__code\">\u003Cspan class=\"lang\">HTML\u003C\u002Fspan>\n\u003Cpre>\u003Ccode>&lt;!DOCTYPE html&gt;\n&lt;html lang=\"en\"&gt;\n&lt;head&gt;\n&#160;&#160;&lt;meta charset=\"UTF-8\"&gt;\n&#160;&#160;&lt;meta name=\"viewport\" content=\"width=device-width, initial-scale=1.0\"&gt;\n&#160;&#160;&lt;title&gt;Feedback Form&lt;\u002Ftitle&gt;\n&lt;\u002Fhead&gt;\n&lt;body&gt;\n&#160;&#160;&lt;h1&gt;Tell us what you think&lt;\u002Fh1&gt;\n&#160;&#160;&lt;!-- form goes here --&gt;\n&lt;\u002Fbody&gt;\n&lt;\u002Fhtml&gt;\u003C\u002Fcode>\u003C\u002Fpre>\n\u003C\u002Fdiv>\n\u003Cp>Two small things that matter later: \u003Ccode>lang=\"en\"\u003C\u002Fcode> helps screen readers pick the right voice, and the viewport meta tag makes the form usable on phones.\u003C\u002Fp>\n\n\u003Ch2 class=\"fmstr-cmp-ffh-body__h2\">Step 2: Add the form fields\u003C\u002Fh2>\n\u003Cp>Paste this inside \u003Ccode>&lt;body&gt;\u003C\u002Fcode>, where the comment says \"form goes here\":\u003C\u002Fp>\n\u003Cdiv class=\"fmstr-cmp-ffh-body__code\">\u003Cspan class=\"lang\">HTML\u003C\u002Fspan>\n\u003Cpre>\u003Ccode>&lt;form id=\"feedback-form\" action=\"\u002Fsubmit-feedback\" method=\"post\" novalidate&gt;\n&#160;&#160;&lt;div class=\"field\"&gt;\n&#160;&#160;&#160;&#160;&lt;label for=\"name\"&gt;Name&lt;\u002Flabel&gt;\n&#160;&#160;&#160;&#160;&lt;input type=\"text\" id=\"name\" name=\"name\" autocomplete=\"name\" required&gt;\n&#160;&#160;&lt;\u002Fdiv&gt;\n\n&#160;&#160;&lt;div class=\"field\"&gt;\n&#160;&#160;&#160;&#160;&lt;label for=\"email\"&gt;Email&lt;\u002Flabel&gt;\n&#160;&#160;&#160;&#160;&lt;input type=\"email\" id=\"email\" name=\"email\" autocomplete=\"email\" required&gt;\n&#160;&#160;&lt;\u002Fdiv&gt;\n\n&#160;&#160;&lt;div class=\"field\"&gt;\n&#160;&#160;&#160;&#160;&lt;label for=\"rating\"&gt;How was your experience?&lt;\u002Flabel&gt;\n&#160;&#160;&#160;&#160;&lt;select id=\"rating\" name=\"rating\" required&gt;\n&#160;&#160;&#160;&#160;&#160;&#160;&lt;option value=\"\"&gt;Pick one&lt;\u002Foption&gt;\n&#160;&#160;&#160;&#160;&#160;&#160;&lt;option value=\"5\"&gt;Loved it&lt;\u002Foption&gt;\n&#160;&#160;&#160;&#160;&#160;&#160;&lt;option value=\"4\"&gt;Good&lt;\u002Foption&gt;\n&#160;&#160;&#160;&#160;&#160;&#160;&lt;option value=\"3\"&gt;Okay&lt;\u002Foption&gt;\n&#160;&#160;&#160;&#160;&#160;&#160;&lt;option value=\"2\"&gt;Not great&lt;\u002Foption&gt;\n&#160;&#160;&#160;&#160;&#160;&#160;&lt;option value=\"1\"&gt;Bad&lt;\u002Foption&gt;\n&#160;&#160;&#160;&#160;&lt;\u002Fselect&gt;\n&#160;&#160;&lt;\u002Fdiv&gt;\n\n&#160;&#160;&lt;div class=\"field\"&gt;\n&#160;&#160;&#160;&#160;&lt;label for=\"message\"&gt;Your feedback&lt;\u002Flabel&gt;\n&#160;&#160;&#160;&#160;&lt;textarea id=\"message\" name=\"message\" rows=\"5\" required&gt;&lt;\u002Ftextarea&gt;\n&#160;&#160;&lt;\u002Fdiv&gt;\n\n&#160;&#160;&lt;button type=\"submit\"&gt;Send feedback&lt;\u002Fbutton&gt;\n&lt;\u002Fform&gt;\u003C\u002Fcode>\u003C\u002Fpre>\n\u003C\u002Fdiv>\n\u003Cp>Three details that beginners miss:\u003C\u002Fp>\n\u003Cul>\n\u003Cli>\u003Cstrong>Every input has a matching \u003Ccode>&lt;label for&gt;\u003C\u002Fcode>.\u003C\u002Fstrong> Click the label, the input focuses. Screen readers read the label out loud. Skip this and the form fails accessibility and loses keyboard users.\u003C\u002Fli>\n\u003Cli>\u003Cstrong>\u003Ccode>name\u003C\u002Fcode> attributes are not cosmetic.\u003C\u002Fstrong> The server reads submissions by \u003Ccode>name\u003C\u002Fcode>, so \u003Ccode>name=\"email\"\u003C\u002Fcode> is what makes the email value reach your inbox. Missing \u003Ccode>name\u003C\u002Fcode> = silent data loss.\u003C\u002Fli>\n\u003Cli>\u003Cstrong>\u003Ccode>autocomplete=\"name\"\u003C\u002Fcode> and \u003Ccode>autocomplete=\"email\"\u003C\u002Fcode>\u003C\u002Fstrong> let browsers pre-fill from saved info. One line, measurable bump in completion.\u003C\u002Fli>\n\u003C\u002Ful>\n\u003Cdiv class=\"fmstr-cmp-ffh-body__note\">\u003Cstrong>Note:\u003C\u002Fstrong> \u003Ccode>novalidate\u003C\u002Fcode> on the form tag turns off the browser's default error bubbles so you can show your own (covered in Step 4). Drop it if you want native validation only.\u003C\u002Fdiv>\n\n\u003Ch2 class=\"fmstr-cmp-ffh-body__h2\">Step 3: Style it with CSS\u003C\u002Fh2>\n\u003Cp>Paste this inside \u003Ccode>&lt;head&gt;\u003C\u002Fcode> between \u003Ccode>&lt;title&gt;\u003C\u002Fcode> and the closing \u003Ccode>&lt;\u002Fhead&gt;\u003C\u002Fcode>:\u003C\u002Fp>\n\u003Cdiv class=\"fmstr-cmp-ffh-body__code\">\u003Cspan class=\"lang\">CSS\u003C\u002Fspan>\n\u003Cpre>\u003Ccode>&lt;style&gt;\n&#160;&#160;body {\n&#160;&#160;&#160;&#160;font-family: system-ui, -apple-system, \"Segoe UI\", Roboto, sans-serif;\n&#160;&#160;&#160;&#160;background: #f7f7f9;\n&#160;&#160;&#160;&#160;margin: 0;\n&#160;&#160;&#160;&#160;padding: 40px 16px;\n&#160;&#160;&#160;&#160;color: #1a1a1a;\n&#160;&#160;}\n&#160;&#160;h1 { font-size: 1.5rem; margin: 0 0 24px; text-align: center; }\n&#160;&#160;form {\n&#160;&#160;&#160;&#160;max-width: 480px;\n&#160;&#160;&#160;&#160;margin: 0 auto;\n&#160;&#160;&#160;&#160;background: #fff;\n&#160;&#160;&#160;&#160;padding: 24px;\n&#160;&#160;&#160;&#160;border-radius: 12px;\n&#160;&#160;&#160;&#160;box-shadow: 0 2px 12px rgba(0,0,0,0.06);\n&#160;&#160;}\n&#160;&#160;.field { margin-bottom: 16px; }\n&#160;&#160;label {\n&#160;&#160;&#160;&#160;display: block;\n&#160;&#160;&#160;&#160;font-weight: 600;\n&#160;&#160;&#160;&#160;font-size: 0.9rem;\n&#160;&#160;&#160;&#160;margin-bottom: 6px;\n&#160;&#160;}\n&#160;&#160;input, select, textarea {\n&#160;&#160;&#160;&#160;width: 100%;\n&#160;&#160;&#160;&#160;box-sizing: border-box;\n&#160;&#160;&#160;&#160;padding: 10px 12px;\n&#160;&#160;&#160;&#160;font: inherit;\n&#160;&#160;&#160;&#160;border: 1px solid #d0d0d6;\n&#160;&#160;&#160;&#160;border-radius: 8px;\n&#160;&#160;&#160;&#160;background: #fff;\n&#160;&#160;}\n&#160;&#160;input:focus, select:focus, textarea:focus {\n&#160;&#160;&#160;&#160;outline: 2px solid #5b6cff;\n&#160;&#160;&#160;&#160;outline-offset: 1px;\n&#160;&#160;&#160;&#160;border-color: #5b6cff;\n&#160;&#160;}\n&#160;&#160;input[aria-invalid=\"true\"],\n&#160;&#160;select[aria-invalid=\"true\"],\n&#160;&#160;textarea[aria-invalid=\"true\"] {\n&#160;&#160;&#160;&#160;border-color: #d33;\n&#160;&#160;}\n&#160;&#160;.error {\n&#160;&#160;&#160;&#160;display: block;\n&#160;&#160;&#160;&#160;color: #d33;\n&#160;&#160;&#160;&#160;font-size: 0.8rem;\n&#160;&#160;&#160;&#160;margin-top: 4px;\n&#160;&#160;&#160;&#160;min-height: 1em;\n&#160;&#160;}\n&#160;&#160;button {\n&#160;&#160;&#160;&#160;width: 100%;\n&#160;&#160;&#160;&#160;padding: 12px;\n&#160;&#160;&#160;&#160;background: #5b6cff;\n&#160;&#160;&#160;&#160;color: #fff;\n&#160;&#160;&#160;&#160;font-weight: 600;\n&#160;&#160;&#160;&#160;border: none;\n&#160;&#160;&#160;&#160;border-radius: 8px;\n&#160;&#160;&#160;&#160;cursor: pointer;\n&#160;&#160;}\n&#160;&#160;button:hover { background: #4a59e0; }\n&lt;\u002Fstyle&gt;\u003C\u002Fcode>\u003C\u002Fpre>\n\u003C\u002Fdiv>\n\u003Cp>Two things this stylesheet does that the typical tutorial skips:\u003C\u002Fp>\n\u003Cul>\n\u003Cli>Keeps the focus outline visible. Default focus styles are ugly, so most tutorials remove them. Removing them breaks keyboard users. Replace, don't remove.\u003C\u002Fli>\n\u003Cli>Uses \u003Ccode>system-ui\u003C\u002Fcode> for fonts, so the form inherits the host site's native typography on macOS, Windows, iOS, and Android without shipping a font file.\u003C\u002Fli>\n\u003C\u002Ful>\n\n\u003Ch2 class=\"fmstr-cmp-ffh-body__h2\">Step 4: Add accessible JavaScript validation\u003C\u002Fh2>\n\u003Cp>The alert-on-submit pattern works but it's the worst possible UX. This version shows inline errors, marks invalid fields for screen readers with \u003Ccode>aria-invalid\u003C\u002Fcode>, and keeps focus where the user can fix the problem.\u003C\u002Fp>\n\u003Cp>Paste this right before \u003Ccode>&lt;\u002Fbody&gt;\u003C\u002Fcode>:\u003C\u002Fp>\n\u003Cdiv class=\"fmstr-cmp-ffh-body__code\">\u003Cspan class=\"lang\">JavaScript\u003C\u002Fspan>\n\u003Cpre>\u003Ccode>&lt;script&gt;\n&#160;&#160;const form = document.getElementById('feedback-form');\n\n&#160;&#160;function setError(input, message) {\n&#160;&#160;&#160;&#160;input.setAttribute('aria-invalid', 'true');\n&#160;&#160;&#160;&#160;let errorEl = input.parentElement.querySelector('.error');\n&#160;&#160;&#160;&#160;if (!errorEl) {\n&#160;&#160;&#160;&#160;&#160;&#160;errorEl = document.createElement('span');\n&#160;&#160;&#160;&#160;&#160;&#160;errorEl.className = 'error';\n&#160;&#160;&#160;&#160;&#160;&#160;errorEl.id = input.id + '-error';\n&#160;&#160;&#160;&#160;&#160;&#160;input.parentElement.appendChild(errorEl);\n&#160;&#160;&#160;&#160;}\n&#160;&#160;&#160;&#160;errorEl.textContent = message;\n&#160;&#160;&#160;&#160;input.setAttribute('aria-describedby', errorEl.id);\n&#160;&#160;}\n\n&#160;&#160;function clearError(input) {\n&#160;&#160;&#160;&#160;input.setAttribute('aria-invalid', 'false');\n&#160;&#160;&#160;&#160;const errorEl = input.parentElement.querySelector('.error');\n&#160;&#160;&#160;&#160;if (errorEl) errorEl.textContent = '';\n&#160;&#160;}\n\n&#160;&#160;form.addEventListener('submit', function (event) {\n&#160;&#160;&#160;&#160;let firstInvalid = null;\n\n&#160;&#160;&#160;&#160;[...form.querySelectorAll('input, select, textarea')].forEach((input) =&gt; {\n&#160;&#160;&#160;&#160;&#160;&#160;clearError(input);\n&#160;&#160;&#160;&#160;&#160;&#160;if (!input.value.trim()) {\n&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;setError(input, 'This field is required.');\n&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;firstInvalid = firstInvalid || input;\n&#160;&#160;&#160;&#160;&#160;&#160;} else if (input.type === 'email' &amp;&amp; !\u002F^\\S+@\\S+\\.\\S+$\u002F.test(input.value)) {\n&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;setError(input, 'Enter a valid email address.');\n&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;firstInvalid = firstInvalid || input;\n&#160;&#160;&#160;&#160;&#160;&#160;}\n&#160;&#160;&#160;&#160;});\n\n&#160;&#160;&#160;&#160;if (firstInvalid) {\n&#160;&#160;&#160;&#160;&#160;&#160;event.preventDefault();\n&#160;&#160;&#160;&#160;&#160;&#160;firstInvalid.focus();\n&#160;&#160;&#160;&#160;}\n&#160;&#160;});\n&lt;\u002Fscript&gt;\u003C\u002Fcode>\u003C\u002Fpre>\n\u003C\u002Fdiv>\n\u003Cp>What this does that the original snippet missed:\u003C\u002Fp>\n\u003Cul>\n\u003Cli>Sets \u003Ccode>aria-invalid=\"true\"\u003C\u002Fcode> and \u003Ccode>aria-describedby\u003C\u002Fcode> so screen readers announce the error.\u003C\u002Fli>\n\u003Cli>Inserts the error message next to the field, not in a modal.\u003C\u002Fli>\n\u003Cli>Focuses the first invalid field on failed submit, so a keyboard user lands exactly where they need to fix.\u003C\u002Fli>\n\u003Cli>Doesn't trust the email regex to be perfect (it isn't); always re-validate on the server.\u003C\u002Fli>\n\u003C\u002Ful>\n\u003Cdiv class=\"fmstr-cmp-ffh-body__note\">\u003Cstrong>Rule of thumb:\u003C\u002Fstrong> client-side validation is for UX. Server-side validation is for trust. Do both.\u003C\u002Fdiv>\n\n\u003Ch2 class=\"fmstr-cmp-ffh-body__h2\">Step 5: Test the form locally\u003C\u002Fh2>\n\u003Cp>Open \u003Ccode>feedback.html\u003C\u002Fcode> in a browser. Run this checklist:\u003C\u002Fp>\n\u003Cul>\n\u003Cli>Tab through every field with the keyboard. Focus should be visible at every stop.\u003C\u002Fli>\n\u003Cli>Try to submit empty. You should see inline error messages, focus should jump to the first empty field.\u003C\u002Fli>\n\u003Cli>Type a malformed email. You should see \"Enter a valid email address.\"\u003C\u002Fli>\n\u003Cli>Open the browser's network tab, submit a valid form. You should see a POST to \u003Ccode>\u002Fsubmit-feedback\u003C\u002Fcode>. That request will currently 404 because you don't have a backend yet. Step 6 fixes that.\u003C\u002Fli>\n\u003C\u002Ful>\n\u003Cp>If you want to skip the backend setup entirely, the next step shows the \u003Ca href=\"https:\u002F\u002Fformester.com\u002Ffeatures\u002Fhtml-form-backend\u002F\">Formester HTML form backend\u003C\u002Fa> path: change one \u003Ccode>action\u003C\u002Fcode> attribute and your form starts collecting submissions.\u003C\u002Fp>\n\n\u003Ch2 class=\"fmstr-cmp-ffh-body__h2\" id=\"step-6-backend\">Step 6: Wire up a backend that stores submissions\u003C\u002Fh2>\n\u003Cp>A feedback form without a backend is a dead form. The browser POSTs the data, the server returns 404, the user sees an error page, the feedback is gone. You have three real options, compared side-by-side below.\u003C\u002Fp>\n\n\u003C\u002Fdiv>\n\u003C\u002Fsection>\n\n\u003Cstyle>\n\u002F* host-link-override *\u002F\n.fmstr-cmp-ffh-back a { text-decoration: none !important; }\n.fmstr-cmp-ffh-back {\n--fmstr-cmp-ffh-back-bg-card: #ffffff;\n--fmstr-cmp-ffh-back-bg-code: #0f172a;\n--fmstr-cmp-ffh-back-fg-1: #101828;\n--fmstr-cmp-ffh-back-fg-2: #475467;\n--fmstr-cmp-ffh-back-fg-3: #697586;\n--fmstr-cmp-ffh-back-violet-500: #7f56d9;\n--fmstr-cmp-ffh-back-violet-600: #6941c6;\n--fmstr-cmp-ffh-back-tint: #f7f3ff;\n--fmstr-cmp-ffh-back-edge: #e4d7ff;\n--fmstr-cmp-ffh-back-border: #eaecf0;\n--fmstr-cmp-ffh-back-red: #dc2626;\n--fmstr-cmp-ffh-back-red-bg: #fef2f2;\n--fmstr-cmp-ffh-back-red-edge: #fecaca;\n--fmstr-cmp-ffh-back-amber: #d97706;\n--fmstr-cmp-ffh-back-amber-bg: #fffbeb;\n--fmstr-cmp-ffh-back-amber-edge: #fde68a;\n--fmstr-cmp-ffh-back-green: #15803d;\n--fmstr-cmp-ffh-back-green-bg: #f0fdf4;\n--fmstr-cmp-ffh-back-green-edge: #bbf7d0;\n--fmstr-cmp-ffh-back-code-fg: #e2e8f0;\n--fmstr-cmp-ffh-back-shadow: 0 4px 20px rgba(16,24,40,.06), 0 2px 6px rgba(16,24,40,.04);\n\nbackground: transparent; padding: 56px 24px;\nfont-family: inherit; color: var(--fmstr-cmp-ffh-back-fg-1);\n}\n.fmstr-cmp-ffh-back *, .fmstr-cmp-ffh-back *::before, .fmstr-cmp-ffh-back *::after { box-sizing: border-box; }\n.fmstr-cmp-ffh-back__container { max-width: 820px; margin: 0 auto; }\n.fmstr-cmp-ffh-back__head { margin: 0 0 28px; }\n.fmstr-cmp-ffh-back__eyebrow {\ndisplay: inline-block; padding: 5px 12px; border-radius: 9999px;\nbackground: var(--fmstr-cmp-ffh-back-tint); color: var(--fmstr-cmp-ffh-back-violet-600);\nfont-size: 12px; font-weight: 600; letter-spacing: .04em;\ntext-transform: uppercase; border: 1px solid var(--fmstr-cmp-ffh-back-edge); margin: 0 0 14px;\n}\n.fmstr-cmp-ffh-back__h2 { font-size: clamp(26px, 3vw, 36px); font-weight: 700; line-height: 1.15; letter-spacing: -.02em; margin: 0; }\n.fmstr-cmp-ffh-back__intro { color: var(--fmstr-cmp-ffh-back-fg-3); font-size: 17px; line-height: 1.6; margin: 14px 0 0; }\n\n.fmstr-cmp-ffh-back__grid { display: grid; grid-template-columns: 1fr; gap: 16px; }\n.fmstr-cmp-ffh-back__card {\nbackground: var(--fmstr-cmp-ffh-back-bg-card);\nborder: 1px solid var(--fmstr-cmp-ffh-back-border);\nborder-radius: 18px; padding: 24px 26px; display: flex; flex-direction: column; gap: 16px;\nbox-shadow: var(--fmstr-cmp-ffh-back-shadow); position: relative;\n}\n.fmstr-cmp-ffh-back__card--red { border-top: 4px solid var(--fmstr-cmp-ffh-back-red); }\n.fmstr-cmp-ffh-back__card--amber { border-top: 4px solid var(--fmstr-cmp-ffh-back-amber); }\n.fmstr-cmp-ffh-back__card--green { border-top: 4px solid var(--fmstr-cmp-ffh-back-violet-500); background: linear-gradient(180deg, #fdfbff 0%, #fff 60%); }\n\n.fmstr-cmp-ffh-back__verdict {\ndisplay: inline-flex; align-items: center; gap: 8px; align-self: flex-start;\npadding: 5px 12px; border-radius: 9999px; font-size: 11.5px; font-weight: 700;\nletter-spacing: .04em; text-transform: uppercase;\n}\n.fmstr-cmp-ffh-back__verdict--red { background: var(--fmstr-cmp-ffh-back-red-bg); color: var(--fmstr-cmp-ffh-back-red); border: 1px solid var(--fmstr-cmp-ffh-back-red-edge); }\n.fmstr-cmp-ffh-back__verdict--amber { background: var(--fmstr-cmp-ffh-back-amber-bg); color: var(--fmstr-cmp-ffh-back-amber); border: 1px solid var(--fmstr-cmp-ffh-back-amber-edge); }\n.fmstr-cmp-ffh-back__verdict--green { background: var(--fmstr-cmp-ffh-back-tint); color: var(--fmstr-cmp-ffh-back-violet-600); border: 1px solid var(--fmstr-cmp-ffh-back-edge); }\n\n.fmstr-cmp-ffh-back__name { font-size: 19px; font-weight: 700; margin: 0; letter-spacing: -.01em; color: var(--fmstr-cmp-ffh-back-fg-1); }\n.fmstr-cmp-ffh-back__sub { font-size: 13.5px; color: var(--fmstr-cmp-ffh-back-fg-3); margin: -8px 0 0; line-height: 1.5; }\n\n.fmstr-cmp-ffh-back__code {\nbackground: var(--fmstr-cmp-ffh-back-bg-code);\nborder-radius: 10px; padding: 14px 16px;\nfont-family: ui-monospace, Menlo, Monaco, monospace;\nfont-size: 12px; line-height: 1.55;\ncolor: var(--fmstr-cmp-ffh-back-code-fg);\noverflow-x: auto; margin: 0; white-space: pre;\n}\n.fmstr-cmp-ffh-back__code code { font-family: inherit; }\n.fmstr-cmp-ffh-back__code .t { color: #f472b6; }\n.fmstr-cmp-ffh-back__code .a { color: #a5b4fc; }\n.fmstr-cmp-ffh-back__code .s { color: #86efac; }\n.fmstr-cmp-ffh-back__code .c { color: #64748b; font-style: italic; }\n\n.fmstr-cmp-ffh-back__list { list-style: none; padding: 0; margin: 0; display: flex; flex-direction: column; gap: 8px; }\n.fmstr-cmp-ffh-back__row { display: flex; gap: 10px; font-size: 14px; line-height: 1.5; color: var(--fmstr-cmp-ffh-back-fg-2); }\n.fmstr-cmp-ffh-back__row::before {\ncontent: \"\"; width: 16px; height: 16px; border-radius: 50%; flex-shrink: 0; margin-top: 3px;\nbackground-repeat: no-repeat; background-position: center;\n}\n.fmstr-cmp-ffh-back__row--bad::before { background-color: var(--fmstr-cmp-ffh-back-red-bg); background-image: url(\"data:image\u002Fsvg+xml,%3Csvg xmlns='http:\u002F\u002Fwww.w3.org\u002F2000\u002Fsvg' width='10' height='10' viewBox='0 0 10 10' fill='none' stroke='%23dc2626' stroke-width='2' stroke-linecap='round'%3E%3Cpath d='M2 2 L8 8 M8 2 L2 8'\u002F%3E%3C\u002Fsvg%3E\"); }\n.fmstr-cmp-ffh-back__row--meh::before { background-color: var(--fmstr-cmp-ffh-back-amber-bg); background-image: url(\"data:image\u002Fsvg+xml,%3Csvg xmlns='http:\u002F\u002Fwww.w3.org\u002F2000\u002Fsvg' width='10' height='10' viewBox='0 0 10 10' fill='none' stroke='%23d97706' stroke-width='2' stroke-linecap='round'%3E%3Cpath d='M2 5 L8 5'\u002F%3E%3C\u002Fsvg%3E\"); }\n.fmstr-cmp-ffh-back__row--good::before { background-color: var(--fmstr-cmp-ffh-back-green-bg); background-image: url(\"data:image\u002Fsvg+xml,%3Csvg xmlns='http:\u002F\u002Fwww.w3.org\u002F2000\u002Fsvg' width='10' height='10' viewBox='0 0 10 10' fill='none' stroke='%2315803d' stroke-width='2' stroke-linecap='round' stroke-linejoin='round'%3E%3Cpath d='M2 5 L4 7 L8 3'\u002F%3E%3C\u002Fsvg%3E\"); }\n.fmstr-cmp-ffh-back__row strong { color: var(--fmstr-cmp-ffh-back-fg-1); font-weight: 600; }\n\n.fmstr-cmp-ffh-back__cta {\nmargin-top: auto; padding-top: 4px;\ndisplay: inline-flex; align-items: center; gap: 8px;\ncolor: var(--fmstr-cmp-ffh-back-violet-600) !important;\nfont-weight: 600; font-size: 14.5px;\ntext-decoration: none !important;\n}\n.fmstr-cmp-ffh-back__cta:hover { text-decoration: underline !important; }\n\n@media (max-width: 760px) {\n.fmstr-cmp-ffh-back { padding: 40px 16px; }\n.fmstr-cmp-ffh-back__card { padding: 22px; }\n.fmstr-cmp-ffh-back__intro { font-size: 15.5px; }\n.fmstr-cmp-ffh-back__code { font-size: 11.5px; padding: 12px 14px; }\n}\n\u003C\u002Fstyle>\n\n\u003Csection class=\"fmstr-cmp-ffh-back\" aria-labelledby=\"fmstr-cmp-ffh-back-h2\">\n\u003Cdiv class=\"fmstr-cmp-ffh-back__container\">\n\u003Cdiv class=\"fmstr-cmp-ffh-back__head\">\n\u003Cspan class=\"fmstr-cmp-ffh-back__eyebrow\">Three honest paths\u003C\u002Fspan>\n\u003Ch2 class=\"fmstr-cmp-ffh-back__h2\" id=\"fmstr-cmp-ffh-back-h2\">What happens after the user clicks Submit\u003C\u002Fh2>\n\u003Cp class=\"fmstr-cmp-ffh-back__intro\">Without a backend, a feedback form is a dead form. The browser POSTs the data, the server returns 404, the user sees an error page. Here are the three real options, ranked by how much pain each one ships with.\u003C\u002Fp>\n\u003C\u002Fdiv>\n\n\u003Cdiv class=\"fmstr-cmp-ffh-back__grid\">\n\n\u003Carticle class=\"fmstr-cmp-ffh-back__card fmstr-cmp-ffh-back__card--red\">\n\u003Cspan class=\"fmstr-cmp-ffh-back__verdict fmstr-cmp-ffh-back__verdict--red\">Don&rsquo;t ship this\u003C\u002Fspan>\n\u003Ch3 class=\"fmstr-cmp-ffh-back__name\">Path 1: \u003Ccode>mailto:\u003C\u002Fcode>\u003C\u002Fh3>\n\u003Cp class=\"fmstr-cmp-ffh-back__sub\">The \"no server\" hack that loses about half your submissions.\u003C\u002Fp>\n\u003Cpre class=\"fmstr-cmp-ffh-back__code\">\u003Ccode>\u003Cspan class=\"c\">&lt;!-- Opens the user's mail client --&gt;\u003C\u002Fspan>\n\u003Cspan class=\"t\">&lt;form\u003C\u002Fspan>\n\u003Cspan class=\"a\">action\u003C\u002Fspan>=\u003Cspan class=\"s\">\"mailto:you@example.com\"\u003C\u002Fspan>\n\u003Cspan class=\"a\">method\u003C\u002Fspan>=\u003Cspan class=\"s\">\"post\"\u003C\u002Fspan>\n\u003Cspan class=\"a\">enctype\u003C\u002Fspan>=\u003Cspan class=\"s\">\"text\u002Fplain\"\u003C\u002Fspan>\u003Cspan class=\"t\">&gt;\u003C\u002Fspan>\u003C\u002Fcode>\u003C\u002Fpre>\n\u003Cul class=\"fmstr-cmp-ffh-back__list\">\n\u003Cli class=\"fmstr-cmp-ffh-back__row fmstr-cmp-ffh-back__row--bad\">\u003Cspan>\u003Cstrong>User-action required.\u003C\u002Fstrong> Browser opens a draft email. They have to click Send manually. Half won&rsquo;t.\u003C\u002Fspan>\u003C\u002Fli>\n\u003Cli class=\"fmstr-cmp-ffh-back__row fmstr-cmp-ffh-back__row--bad\">\u003Cspan>\u003Cstrong>Breaks on mobile.\u003C\u002Fstrong> Many phones have no configured mail client.\u003C\u002Fspan>\u003C\u002Fli>\n\u003Cli class=\"fmstr-cmp-ffh-back__row fmstr-cmp-ffh-back__row--bad\">\u003Cspan>\u003Cstrong>Spam-filter bait.\u003C\u002Fstrong> Resulting messages are unsigned and easy to flag.\u003C\u002Fspan>\u003C\u002Fli>\n\u003C\u002Ful>\n\u003C\u002Farticle>\n\n\u003Carticle class=\"fmstr-cmp-ffh-back__card fmstr-cmp-ffh-back__card--amber\">\n\u003Cspan class=\"fmstr-cmp-ffh-back__verdict fmstr-cmp-ffh-back__verdict--amber\">You&rsquo;ll maintain it\u003C\u002Fspan>\n\u003Ch3 class=\"fmstr-cmp-ffh-back__name\">Path 2: Your own server\u003C\u002Fh3>\n\u003Cp class=\"fmstr-cmp-ffh-back__sub\">PHP, Node, or whatever you already run. Full control, full ownership.\u003C\u002Fp>\n\u003Cpre class=\"fmstr-cmp-ffh-back__code\">\u003Ccode>\u003Cspan class=\"c\">\u002F\u002F minimal Node\u002FExpress receiver\u003C\u002Fspan>\napp.\u003Cspan class=\"t\">post\u003C\u002Fspan>(\u003Cspan class=\"s\">'\u002Fsubmit-feedback'\u003C\u002Fspan>, (req, res) =&gt; {\n\u003Cspan class=\"t\">const\u003C\u002Fspan> { name, email, message } = req.body;\n\u003Cspan class=\"t\">if\u003C\u002Fspan> (!validate(email)) \u003Cspan class=\"t\">return\u003C\u002Fspan> res.\u003Cspan class=\"t\">status\u003C\u002Fspan>(400);\ndb.\u003Cspan class=\"t\">insert\u003C\u002Fspan>({ name, email, message });\nres.\u003Cspan class=\"t\">redirect\u003C\u002Fspan>(\u003Cspan class=\"s\">'\u002Fthank-you'\u003C\u002Fspan>);\n});\u003C\u002Fcode>\u003C\u002Fpre>\n\u003Cul class=\"fmstr-cmp-ffh-back__list\">\n\u003Cli class=\"fmstr-cmp-ffh-back__row fmstr-cmp-ffh-back__row--meh\">\u003Cspan>\u003Cstrong>You own the server.\u003C\u002Fstrong> Hosting, TLS, scaling, uptime monitoring are yours.\u003C\u002Fspan>\u003C\u002Fli>\n\u003Cli class=\"fmstr-cmp-ffh-back__row fmstr-cmp-ffh-back__row--meh\">\u003Cspan>\u003Cstrong>Spam protection is on you.\u003C\u002Fstrong> Honeypot, rate limiting, CAPTCHA, all DIY.\u003C\u002Fspan>\u003C\u002Fli>\n\u003Cli class=\"fmstr-cmp-ffh-back__row fmstr-cmp-ffh-back__row--good\">\u003Cspan>\u003Cstrong>Maximum control.\u003C\u002Fstrong> Custom logic, database, queues, webhooks however you want.\u003C\u002Fspan>\u003C\u002Fli>\n\u003C\u002Ful>\n\u003C\u002Farticle>\n\n\u003Carticle class=\"fmstr-cmp-ffh-back__card fmstr-cmp-ffh-back__card--green\">\n\u003Cspan class=\"fmstr-cmp-ffh-back__verdict fmstr-cmp-ffh-back__verdict--green\">Skip the server\u003C\u002Fspan>\n\u003Ch3 class=\"fmstr-cmp-ffh-back__name\">Path 3: Formester HTML form backend\u003C\u002Fh3>\n\u003Cp class=\"fmstr-cmp-ffh-back__sub\">One \u003Ccode>action\u003C\u002Fcode> attribute swap. No server code, no infra.\u003C\u002Fp>\n\u003Cpre class=\"fmstr-cmp-ffh-back__code\">\u003Ccode>\u003Cspan class=\"c\">&lt;!-- The only change vs. Path 2 --&gt;\u003C\u002Fspan>\n\u003Cspan class=\"t\">&lt;form\u003C\u002Fspan>\n\u003Cspan class=\"a\">action\u003C\u002Fspan>=\u003Cspan class=\"s\">\"https:\u002F\u002Fapp.formester.com\u002F\u003C\u002Fspan>\n\u003Cspan class=\"s\">    api\u002Fv1\u002Fforms\u002FYOUR_ID\u002Fsubmissions\"\u003C\u002Fspan>\n\u003Cspan class=\"a\">method\u003C\u002Fspan>=\u003Cspan class=\"s\">\"post\"\u003C\u002Fspan>\u003Cspan class=\"t\">&gt;\u003C\u002Fspan>\u003C\u002Fcode>\u003C\u002Fpre>\n\u003Cul class=\"fmstr-cmp-ffh-back__list\">\n\u003Cli class=\"fmstr-cmp-ffh-back__row fmstr-cmp-ffh-back__row--good\">\u003Cspan>\u003Cstrong>Submissions land in the dashboard.\u003C\u002Fstrong> View, filter, \u003Ca href=\"https:\u002F\u002Fformester.com\u002Ffeatures\u002Fexport-form-submission-pdf\u002F\">export to PDF\u003C\u002Fa>, push to Sheets\u002FSlack\u002FHubSpot.\u003C\u002Fspan>\u003C\u002Fli>\n\u003Cli class=\"fmstr-cmp-ffh-back__row fmstr-cmp-ffh-back__row--good\">\u003Cspan>\u003Cstrong>Spam protection built in.\u003C\u002Fstrong> Honeypot plus \u003Ca href=\"https:\u002F\u002Fformester.com\u002Ffeatures\u002Fspam-protection\u002F\">reCAPTCHA-style checks\u003C\u002Fa> on every submission.\u003C\u002Fspan>\u003C\u002Fli>\n\u003Cli class=\"fmstr-cmp-ffh-back__row fmstr-cmp-ffh-back__row--good\">\u003Cspan>\u003Cstrong>Free with unlimited submissions.\u003C\u002Fstrong> Email notifications, dashboard, integrations included. Used by 56,000+ teams.\u003C\u002Fspan>\u003C\u002Fli>\n\u003C\u002Ful>\n\u003Ca class=\"fmstr-cmp-ffh-back__cta\" href=\"https:\u002F\u002Fformester.com\u002Ffeatures\u002Fhtml-form-backend\u002F\">See the HTML form backend &rarr;\u003C\u002Fa>\n\u003C\u002Farticle>\n\n\u003C\u002Fdiv>\n\u003C\u002Fdiv>\n\u003C\u002Fsection>\n\n\u003Cstyle>\n\u002F* host-link-override *\u002F\n.fmstr-cmp-ffh-code a { text-decoration: none !important; }\n.fmstr-cmp-ffh-code {\n--fmstr-cmp-ffh-code-bg-card: #ffffff;\n--fmstr-cmp-ffh-code-bg-code: #0f172a;\n--fmstr-cmp-ffh-code-bg-preview: #f7f7f9;\n--fmstr-cmp-ffh-code-fg-1: #101828;\n--fmstr-cmp-ffh-code-fg-2: #475467;\n--fmstr-cmp-ffh-code-fg-3: #697586;\n--fmstr-cmp-ffh-code-violet-500: #7f56d9;\n--fmstr-cmp-ffh-code-violet-600: #6941c6;\n--fmstr-cmp-ffh-code-tint: #f7f3ff;\n--fmstr-cmp-ffh-code-edge: #e4d7ff;\n--fmstr-cmp-ffh-code-border: #eaecf0;\n--fmstr-cmp-ffh-code-code-fg: #e2e8f0;\n--fmstr-cmp-ffh-code-code-tag: #f472b6;\n--fmstr-cmp-ffh-code-code-attr: #a5b4fc;\n--fmstr-cmp-ffh-code-code-str: #86efac;\n--fmstr-cmp-ffh-code-code-comment: #64748b;\n--fmstr-cmp-ffh-code-shadow: 0 4px 20px rgba(16,24,40,.06), 0 2px 6px rgba(16,24,40,.04);\n\nbackground: transparent; padding: 56px 24px;\nfont-family: inherit; color: var(--fmstr-cmp-ffh-code-fg-1);\n}\n.fmstr-cmp-ffh-code *, .fmstr-cmp-ffh-code *::before, .fmstr-cmp-ffh-code *::after { box-sizing: border-box; }\n.fmstr-cmp-ffh-code__container { max-width: 820px; margin: 0 auto; }\n.fmstr-cmp-ffh-code__head { max-width: 780px; margin: 0 0 32px; }\n.fmstr-cmp-ffh-code__eyebrow {\ndisplay: inline-block; padding: 5px 12px; border-radius: 9999px;\nbackground: var(--fmstr-cmp-ffh-code-tint); color: var(--fmstr-cmp-ffh-code-violet-600);\nfont-size: 12px; font-weight: 600; letter-spacing: .04em;\ntext-transform: uppercase; border: 1px solid var(--fmstr-cmp-ffh-code-edge); margin: 0 0 14px;\n}\n.fmstr-cmp-ffh-code__h2 { font-size: clamp(26px, 3vw, 36px); font-weight: 700; line-height: 1.15; letter-spacing: -.02em; margin: 0; }\n.fmstr-cmp-ffh-code__intro { color: var(--fmstr-cmp-ffh-code-fg-3); font-size: 17px; line-height: 1.6; margin: 14px 0 0; }\n\n.fmstr-cmp-ffh-code__grid {\ndisplay: grid; grid-template-columns: 1fr; gap: 0;\nbackground: var(--fmstr-cmp-ffh-code-bg-card);\nborder: 1px solid var(--fmstr-cmp-ffh-code-border);\nborder-radius: 20px; overflow: hidden;\nbox-shadow: var(--fmstr-cmp-ffh-code-shadow);\n}\n\n.fmstr-cmp-ffh-code__preview-pane {\nbackground: var(--fmstr-cmp-ffh-code-bg-preview);\npadding: 28px 24px;\ndisplay: flex; flex-direction: column; gap: 14px;\nborder-bottom: 1px solid var(--fmstr-cmp-ffh-code-border);\n}\n.fmstr-cmp-ffh-code__preview-label {\nfont-size: 11px; font-weight: 700; letter-spacing: .08em;\ntext-transform: uppercase; color: var(--fmstr-cmp-ffh-code-fg-3);\ndisplay: flex; align-items: center; gap: 8px;\n}\n.fmstr-cmp-ffh-code__preview-label::before {\ncontent: \"\"; width: 8px; height: 8px; border-radius: 50%;\nbackground: #22c55e; flex-shrink: 0;\n}\n.fmstr-cmp-ffh-code__preview-form {\nbackground: #fff; padding: 22px 20px; border-radius: 12px;\nbox-shadow: 0 2px 12px rgba(0,0,0,0.06);\ndisplay: flex; flex-direction: column; gap: 14px;\n}\n.fmstr-cmp-ffh-code__preview-h { font-size: 16px; font-weight: 700; text-align: center; margin: 0 0 4px; color: var(--fmstr-cmp-ffh-code-fg-1); }\n.fmstr-cmp-ffh-code__preview-field { display: flex; flex-direction: column; gap: 6px; }\n.fmstr-cmp-ffh-code__preview-label-row { font-size: 12.5px; font-weight: 600; color: var(--fmstr-cmp-ffh-code-fg-1); }\n.fmstr-cmp-ffh-code__preview-input {\nbackground: #fff; border: 1px solid #d0d0d6; border-radius: 8px;\npadding: 9px 11px; font-size: 12.5px; color: var(--fmstr-cmp-ffh-code-fg-3);\n}\n.fmstr-cmp-ffh-code__preview-input--focus { outline: 2px solid var(--fmstr-cmp-ffh-code-violet-500); outline-offset: 1px; border-color: var(--fmstr-cmp-ffh-code-violet-500); color: var(--fmstr-cmp-ffh-code-fg-1); }\n.fmstr-cmp-ffh-code__preview-select {\nbackground: #fff; border: 1px solid #d0d0d6; border-radius: 8px;\npadding: 9px 11px; font-size: 12.5px; color: var(--fmstr-cmp-ffh-code-fg-3);\ndisplay: flex; justify-content: space-between; align-items: center;\n}\n.fmstr-cmp-ffh-code__preview-textarea {\nbackground: #fff; border: 1px solid #d0d0d6; border-radius: 8px;\npadding: 9px 11px; font-size: 12.5px; color: var(--fmstr-cmp-ffh-code-fg-3);\nmin-height: 54px;\n}\n.fmstr-cmp-ffh-code__preview-btn {\nbackground: var(--fmstr-cmp-ffh-code-violet-500); color: #fff;\npadding: 10px; border-radius: 8px; text-align: center;\nfont-weight: 600; font-size: 13px; margin-top: 4px;\n}\n.fmstr-cmp-ffh-code__preview-caption {\nfont-size: 12px; color: var(--fmstr-cmp-ffh-code-fg-3); line-height: 1.5; margin: 4px 0 0;\n}\n\n.fmstr-cmp-ffh-code__code-pane {\nbackground: var(--fmstr-cmp-ffh-code-bg-code);\nposition: relative; max-height: 560px;\ndisplay: flex; flex-direction: column;\n}\n.fmstr-cmp-ffh-code__code-header {\ndisplay: flex; align-items: center; justify-content: space-between;\npadding: 14px 18px; border-bottom: 1px solid rgba(255,255,255,0.08);\ncolor: var(--fmstr-cmp-ffh-code-code-comment);\nfont-family: ui-monospace, Menlo, Monaco, monospace; font-size: 12px;\n}\n.fmstr-cmp-ffh-code__code-filename { display: flex; align-items: center; gap: 8px; }\n.fmstr-cmp-ffh-code__code-filename::before {\ncontent: \"\"; width: 10px; height: 10px; border-radius: 50%; background: #f87171;\nbox-shadow: 16px 0 0 #fbbf24, 32px 0 0 #34d399;\nmargin-right: 12px;\n}\n.fmstr-cmp-ffh-code__code-copy {\nbackground: rgba(127, 86, 217, 0.18) !important;\ncolor: #c4b5fd !important; border: 1px solid rgba(127, 86, 217, 0.4);\npadding: 6px 14px; border-radius: 6px; font-size: 12px; font-weight: 600;\ncursor: pointer; font-family: ui-monospace, Menlo, Monaco, monospace;\ndisplay: inline-flex; align-items: center; gap: 6px;\n}\n.fmstr-cmp-ffh-code__code-copy:hover { background: rgba(127, 86, 217, 0.28) !important; }\n.fmstr-cmp-ffh-code__code-body {\nmargin: 0; padding: 18px 20px;\nfont-family: ui-monospace, Menlo, Monaco, monospace;\nfont-size: 12.5px; line-height: 1.65;\ncolor: var(--fmstr-cmp-ffh-code-code-fg);\noverflow: auto; flex-grow: 1;\nwhite-space: pre;\nscrollbar-width: thin; scrollbar-color: rgba(167,139,250,.35) transparent;\n}\n.fmstr-cmp-ffh-code__code-body::-webkit-scrollbar { width: 10px; height: 10px; }\n.fmstr-cmp-ffh-code__code-body::-webkit-scrollbar-track { background: transparent; }\n.fmstr-cmp-ffh-code__code-body::-webkit-scrollbar-thumb { background: rgba(167,139,250,.3); border-radius: 5px; }\n.fmstr-cmp-ffh-code__code-body::-webkit-scrollbar-thumb:hover { background: rgba(167,139,250,.5); }\n.fmstr-cmp-ffh-code__code-body code { font-family: inherit; }\n.fmstr-cmp-ffh-code__tag { color: var(--fmstr-cmp-ffh-code-code-tag); }\n.fmstr-cmp-ffh-code__attr { color: var(--fmstr-cmp-ffh-code-code-attr); }\n.fmstr-cmp-ffh-code__str { color: var(--fmstr-cmp-ffh-code-code-str); }\n.fmstr-cmp-ffh-code__cmt { color: var(--fmstr-cmp-ffh-code-code-comment); font-style: italic; }\n\n.fmstr-cmp-ffh-code__foot {\nmargin: 20px auto 0; max-width: 780px; text-align: center;\ncolor: var(--fmstr-cmp-ffh-code-fg-3); font-size: 14.5px; line-height: 1.6;\n}\n.fmstr-cmp-ffh-code__foot a { color: var(--fmstr-cmp-ffh-code-violet-600) !important; font-weight: 600; }\n.fmstr-cmp-ffh-code__foot a:hover { text-decoration: underline !important; }\n\n@media (max-width: 760px) {\n.fmstr-cmp-ffh-code { padding: 40px 16px; }\n.fmstr-cmp-ffh-code__grid { border-radius: 16px; }\n.fmstr-cmp-ffh-code__preview-pane { padding: 22px 18px; }\n.fmstr-cmp-ffh-code__code-pane { max-height: 420px; }\n.fmstr-cmp-ffh-code__code-body { font-size: 11.5px; padding: 14px 16px; }\n.fmstr-cmp-ffh-code__intro { font-size: 15.5px; }\n}\n\u003C\u002Fstyle>\n\n\u003Csection class=\"fmstr-cmp-ffh-code\" aria-labelledby=\"fmstr-cmp-ffh-code-h2\">\n\u003Cdiv class=\"fmstr-cmp-ffh-code__container\">\n\u003Cdiv class=\"fmstr-cmp-ffh-code__head\">\n\u003Cspan class=\"fmstr-cmp-ffh-code__eyebrow\">Copy, paste, ship\u003C\u002Fspan>\n\u003Ch2 class=\"fmstr-cmp-ffh-code__h2\" id=\"fmstr-cmp-ffh-code-h2\">The complete feedback form, in one file\u003C\u002Fh2>\n\u003Cp class=\"fmstr-cmp-ffh-code__intro\">Structure, styling, and accessible JavaScript validation in a single working file. Save as \u003Ccode>feedback.html\u003C\u002Fcode>, swap the \u003Ccode>action\u003C\u002Fcode> URL, and the form is live.\u003C\u002Fp>\n\u003C\u002Fdiv>\n\n\u003Cdiv class=\"fmstr-cmp-ffh-code__grid\">\n\u003Cdiv class=\"fmstr-cmp-ffh-code__preview-pane\">\n\u003Cdiv class=\"fmstr-cmp-ffh-code__preview-label\">Live preview\u003C\u002Fdiv>\n\u003Cdiv class=\"fmstr-cmp-ffh-code__preview-form\">\n\u003Ch3 class=\"fmstr-cmp-ffh-code__preview-h\">Tell us what you think\u003C\u002Fh3>\n\u003Cdiv class=\"fmstr-cmp-ffh-code__preview-field\">\n\u003Cspan class=\"fmstr-cmp-ffh-code__preview-label-row\">Name\u003C\u002Fspan>\n\u003Cdiv class=\"fmstr-cmp-ffh-code__preview-input\">Jane Doe\u003C\u002Fdiv>\n\u003C\u002Fdiv>\n\u003Cdiv class=\"fmstr-cmp-ffh-code__preview-field\">\n\u003Cspan class=\"fmstr-cmp-ffh-code__preview-label-row\">Email\u003C\u002Fspan>\n\u003Cdiv class=\"fmstr-cmp-ffh-code__preview-input fmstr-cmp-ffh-code__preview-input--focus\">jane@example.com\u003C\u002Fdiv>\n\u003C\u002Fdiv>\n\u003Cdiv class=\"fmstr-cmp-ffh-code__preview-field\">\n\u003Cspan class=\"fmstr-cmp-ffh-code__preview-label-row\">How was your experience?\u003C\u002Fspan>\n\u003Cdiv class=\"fmstr-cmp-ffh-code__preview-select\">\u003Cspan>Loved it\u003C\u002Fspan>\u003Cspan>&#9662;\u003C\u002Fspan>\u003C\u002Fdiv>\n\u003C\u002Fdiv>\n\u003Cdiv class=\"fmstr-cmp-ffh-code__preview-field\">\n\u003Cspan class=\"fmstr-cmp-ffh-code__preview-label-row\">Your feedback\u003C\u002Fspan>\n\u003Cdiv class=\"fmstr-cmp-ffh-code__preview-textarea\">The dashboard is fast and the export to PDF saved my week.\u003C\u002Fdiv>\n\u003C\u002Fdiv>\n\u003Cdiv class=\"fmstr-cmp-ffh-code__preview-btn\">Send feedback\u003C\u002Fdiv>\n\u003C\u002Fdiv>\n\u003Cp class=\"fmstr-cmp-ffh-code__preview-caption\">Rendered output. Keyboard-accessible focus ring on the active field, inline error slot ready, mobile-friendly layout.\u003C\u002Fp>\n\u003C\u002Fdiv>\n\n\u003Cdiv class=\"fmstr-cmp-ffh-code__code-pane\">\n\u003Cdiv class=\"fmstr-cmp-ffh-code__code-header\">\n\u003Cspan class=\"fmstr-cmp-ffh-code__code-filename\">feedback.html\u003C\u002Fspan>\n\u003Cbutton type=\"button\" class=\"fmstr-cmp-ffh-code__code-copy\" aria-label=\"Copy code\">Copy\u003C\u002Fbutton>\n\u003C\u002Fdiv>\n\u003Cpre class=\"fmstr-cmp-ffh-code__code-body\">\u003Ccode>\u003Cspan class=\"fmstr-cmp-ffh-code__cmt\">&lt;!DOCTYPE html&gt;\u003C\u002Fspan>\n\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;html\u003C\u002Fspan> \u003Cspan class=\"fmstr-cmp-ffh-code__attr\">lang\u003C\u002Fspan>=\u003Cspan class=\"fmstr-cmp-ffh-code__str\">\"en\"\u003C\u002Fspan>\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&gt;\u003C\u002Fspan>\n\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;head&gt;\u003C\u002Fspan>\n\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;meta\u003C\u002Fspan> \u003Cspan class=\"fmstr-cmp-ffh-code__attr\">charset\u003C\u002Fspan>=\u003Cspan class=\"fmstr-cmp-ffh-code__str\">\"UTF-8\"\u003C\u002Fspan>\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&gt;\u003C\u002Fspan>\n\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;meta\u003C\u002Fspan> \u003Cspan class=\"fmstr-cmp-ffh-code__attr\">name\u003C\u002Fspan>=\u003Cspan class=\"fmstr-cmp-ffh-code__str\">\"viewport\"\u003C\u002Fspan> \u003Cspan class=\"fmstr-cmp-ffh-code__attr\">content\u003C\u002Fspan>=\u003Cspan class=\"fmstr-cmp-ffh-code__str\">\"width=device-width, initial-scale=1.0\"\u003C\u002Fspan>\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&gt;\u003C\u002Fspan>\n\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;title&gt;\u003C\u002Fspan>Feedback Form\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;\u002Ftitle&gt;\u003C\u002Fspan>\n\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;style&gt;\u003C\u002Fspan>\nbody { font-family: system-ui, sans-serif; background: #f7f7f9; padding: 40px 16px; }\nform { max-width: 480px; margin: 0 auto; background: #fff; padding: 24px; border-radius: 12px; }\n.field { margin-bottom: 16px; }\nlabel { display: block; font-weight: 600; margin-bottom: 6px; }\ninput, select, textarea { width: 100%; padding: 10px 12px; border: 1px solid #d0d0d6; border-radius: 8px; box-sizing: border-box; }\ninput:focus, select:focus, textarea:focus { outline: 2px solid #5b6cff; border-color: #5b6cff; }\n[aria-invalid=\"true\"] { border-color: #d33; }\n.error { display: block; color: #d33; font-size: 0.8rem; margin-top: 4px; }\nbutton { width: 100%; padding: 12px; background: #5b6cff; color: #fff; font-weight: 600; border: none; border-radius: 8px; cursor: pointer; }\n\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;\u002Fstyle&gt;\u003C\u002Fspan>\n\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;\u002Fhead&gt;\u003C\u002Fspan>\n\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;body&gt;\u003C\u002Fspan>\n\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;h1&gt;\u003C\u002Fspan>Tell us what you think\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;\u002Fh1&gt;\u003C\u002Fspan>\n\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;form\u003C\u002Fspan> \u003Cspan class=\"fmstr-cmp-ffh-code__attr\">id\u003C\u002Fspan>=\u003Cspan class=\"fmstr-cmp-ffh-code__str\">\"feedback-form\"\u003C\u002Fspan> \u003Cspan class=\"fmstr-cmp-ffh-code__attr\">action\u003C\u002Fspan>=\u003Cspan class=\"fmstr-cmp-ffh-code__str\">\"https:\u002F\u002Fapp.formester.com\u002Fapi\u002Fv1\u002Fforms\u002FYOUR_FORM_ID\u002Fsubmissions\"\u003C\u002Fspan> \u003Cspan class=\"fmstr-cmp-ffh-code__attr\">method\u003C\u002Fspan>=\u003Cspan class=\"fmstr-cmp-ffh-code__str\">\"post\"\u003C\u002Fspan> \u003Cspan class=\"fmstr-cmp-ffh-code__attr\">novalidate\u003C\u002Fspan>\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&gt;\u003C\u002Fspan>\n\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;div\u003C\u002Fspan> \u003Cspan class=\"fmstr-cmp-ffh-code__attr\">class\u003C\u002Fspan>=\u003Cspan class=\"fmstr-cmp-ffh-code__str\">\"field\"\u003C\u002Fspan>\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&gt;\u003C\u002Fspan>\n\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;label\u003C\u002Fspan> \u003Cspan class=\"fmstr-cmp-ffh-code__attr\">for\u003C\u002Fspan>=\u003Cspan class=\"fmstr-cmp-ffh-code__str\">\"name\"\u003C\u002Fspan>\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&gt;\u003C\u002Fspan>Name\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;\u002Flabel&gt;\u003C\u002Fspan>\n\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;input\u003C\u002Fspan> \u003Cspan class=\"fmstr-cmp-ffh-code__attr\">type\u003C\u002Fspan>=\u003Cspan class=\"fmstr-cmp-ffh-code__str\">\"text\"\u003C\u002Fspan> \u003Cspan class=\"fmstr-cmp-ffh-code__attr\">id\u003C\u002Fspan>=\u003Cspan class=\"fmstr-cmp-ffh-code__str\">\"name\"\u003C\u002Fspan> \u003Cspan class=\"fmstr-cmp-ffh-code__attr\">name\u003C\u002Fspan>=\u003Cspan class=\"fmstr-cmp-ffh-code__str\">\"name\"\u003C\u002Fspan> \u003Cspan class=\"fmstr-cmp-ffh-code__attr\">autocomplete\u003C\u002Fspan>=\u003Cspan class=\"fmstr-cmp-ffh-code__str\">\"name\"\u003C\u002Fspan> \u003Cspan class=\"fmstr-cmp-ffh-code__attr\">required\u003C\u002Fspan>\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&gt;\u003C\u002Fspan>\n\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;\u002Fdiv&gt;\u003C\u002Fspan>\n\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;div\u003C\u002Fspan> \u003Cspan class=\"fmstr-cmp-ffh-code__attr\">class\u003C\u002Fspan>=\u003Cspan class=\"fmstr-cmp-ffh-code__str\">\"field\"\u003C\u002Fspan>\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&gt;\u003C\u002Fspan>\n\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;label\u003C\u002Fspan> \u003Cspan class=\"fmstr-cmp-ffh-code__attr\">for\u003C\u002Fspan>=\u003Cspan class=\"fmstr-cmp-ffh-code__str\">\"email\"\u003C\u002Fspan>\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&gt;\u003C\u002Fspan>Email\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;\u002Flabel&gt;\u003C\u002Fspan>\n\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;input\u003C\u002Fspan> \u003Cspan class=\"fmstr-cmp-ffh-code__attr\">type\u003C\u002Fspan>=\u003Cspan class=\"fmstr-cmp-ffh-code__str\">\"email\"\u003C\u002Fspan> \u003Cspan class=\"fmstr-cmp-ffh-code__attr\">id\u003C\u002Fspan>=\u003Cspan class=\"fmstr-cmp-ffh-code__str\">\"email\"\u003C\u002Fspan> \u003Cspan class=\"fmstr-cmp-ffh-code__attr\">name\u003C\u002Fspan>=\u003Cspan class=\"fmstr-cmp-ffh-code__str\">\"email\"\u003C\u002Fspan> \u003Cspan class=\"fmstr-cmp-ffh-code__attr\">autocomplete\u003C\u002Fspan>=\u003Cspan class=\"fmstr-cmp-ffh-code__str\">\"email\"\u003C\u002Fspan> \u003Cspan class=\"fmstr-cmp-ffh-code__attr\">required\u003C\u002Fspan>\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&gt;\u003C\u002Fspan>\n\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;\u002Fdiv&gt;\u003C\u002Fspan>\n\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;div\u003C\u002Fspan> \u003Cspan class=\"fmstr-cmp-ffh-code__attr\">class\u003C\u002Fspan>=\u003Cspan class=\"fmstr-cmp-ffh-code__str\">\"field\"\u003C\u002Fspan>\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&gt;\u003C\u002Fspan>\n\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;label\u003C\u002Fspan> \u003Cspan class=\"fmstr-cmp-ffh-code__attr\">for\u003C\u002Fspan>=\u003Cspan class=\"fmstr-cmp-ffh-code__str\">\"rating\"\u003C\u002Fspan>\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&gt;\u003C\u002Fspan>How was your experience?\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;\u002Flabel&gt;\u003C\u002Fspan>\n\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;select\u003C\u002Fspan> \u003Cspan class=\"fmstr-cmp-ffh-code__attr\">id\u003C\u002Fspan>=\u003Cspan class=\"fmstr-cmp-ffh-code__str\">\"rating\"\u003C\u002Fspan> \u003Cspan class=\"fmstr-cmp-ffh-code__attr\">name\u003C\u002Fspan>=\u003Cspan class=\"fmstr-cmp-ffh-code__str\">\"rating\"\u003C\u002Fspan> \u003Cspan class=\"fmstr-cmp-ffh-code__attr\">required\u003C\u002Fspan>\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&gt;\u003C\u002Fspan>\n\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;option\u003C\u002Fspan> \u003Cspan class=\"fmstr-cmp-ffh-code__attr\">value\u003C\u002Fspan>=\u003Cspan class=\"fmstr-cmp-ffh-code__str\">\"\"\u003C\u002Fspan>\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&gt;\u003C\u002Fspan>Pick one\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;\u002Foption&gt;\u003C\u002Fspan>\n\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;option\u003C\u002Fspan> \u003Cspan class=\"fmstr-cmp-ffh-code__attr\">value\u003C\u002Fspan>=\u003Cspan class=\"fmstr-cmp-ffh-code__str\">\"5\"\u003C\u002Fspan>\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&gt;\u003C\u002Fspan>Loved it\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;\u002Foption&gt;\u003C\u002Fspan>\n\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;option\u003C\u002Fspan> \u003Cspan class=\"fmstr-cmp-ffh-code__attr\">value\u003C\u002Fspan>=\u003Cspan class=\"fmstr-cmp-ffh-code__str\">\"3\"\u003C\u002Fspan>\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&gt;\u003C\u002Fspan>Okay\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;\u002Foption&gt;\u003C\u002Fspan>\n\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;option\u003C\u002Fspan> \u003Cspan class=\"fmstr-cmp-ffh-code__attr\">value\u003C\u002Fspan>=\u003Cspan class=\"fmstr-cmp-ffh-code__str\">\"1\"\u003C\u002Fspan>\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&gt;\u003C\u002Fspan>Bad\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;\u002Foption&gt;\u003C\u002Fspan>\n\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;\u002Fselect&gt;\u003C\u002Fspan>\n\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;\u002Fdiv&gt;\u003C\u002Fspan>\n\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;div\u003C\u002Fspan> \u003Cspan class=\"fmstr-cmp-ffh-code__attr\">class\u003C\u002Fspan>=\u003Cspan class=\"fmstr-cmp-ffh-code__str\">\"field\"\u003C\u002Fspan>\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&gt;\u003C\u002Fspan>\n\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;label\u003C\u002Fspan> \u003Cspan class=\"fmstr-cmp-ffh-code__attr\">for\u003C\u002Fspan>=\u003Cspan class=\"fmstr-cmp-ffh-code__str\">\"message\"\u003C\u002Fspan>\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&gt;\u003C\u002Fspan>Your feedback\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;\u002Flabel&gt;\u003C\u002Fspan>\n\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;textarea\u003C\u002Fspan> \u003Cspan class=\"fmstr-cmp-ffh-code__attr\">id\u003C\u002Fspan>=\u003Cspan class=\"fmstr-cmp-ffh-code__str\">\"message\"\u003C\u002Fspan> \u003Cspan class=\"fmstr-cmp-ffh-code__attr\">name\u003C\u002Fspan>=\u003Cspan class=\"fmstr-cmp-ffh-code__str\">\"message\"\u003C\u002Fspan> \u003Cspan class=\"fmstr-cmp-ffh-code__attr\">rows\u003C\u002Fspan>=\u003Cspan class=\"fmstr-cmp-ffh-code__str\">\"5\"\u003C\u002Fspan> \u003Cspan class=\"fmstr-cmp-ffh-code__attr\">required\u003C\u002Fspan>\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&gt;&lt;\u002Ftextarea&gt;\u003C\u002Fspan>\n\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;\u002Fdiv&gt;\u003C\u002Fspan>\n\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;button\u003C\u002Fspan> \u003Cspan class=\"fmstr-cmp-ffh-code__attr\">type\u003C\u002Fspan>=\u003Cspan class=\"fmstr-cmp-ffh-code__str\">\"submit\"\u003C\u002Fspan>\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&gt;\u003C\u002Fspan>Send feedback\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;\u002Fbutton&gt;\u003C\u002Fspan>\n\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;\u002Fform&gt;\u003C\u002Fspan>\n\n\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;script&gt;\u003C\u002Fspan>\n\u003Cspan class=\"fmstr-cmp-ffh-code__cmt\">\u002F\u002F Accessible inline validation: aria-invalid, aria-describedby, focus management\u003C\u002Fspan>\nconst form = document.getElementById(\u003Cspan class=\"fmstr-cmp-ffh-code__str\">'feedback-form'\u003C\u002Fspan>);\nform.addEventListener(\u003Cspan class=\"fmstr-cmp-ffh-code__str\">'submit'\u003C\u002Fspan>, (e) =&gt; {\nlet firstInvalid = null;\n[...form.querySelectorAll(\u003Cspan class=\"fmstr-cmp-ffh-code__str\">'input, select, textarea'\u003C\u002Fspan>)].forEach((input) =&gt; {\nconst valid = input.value.trim() &amp;&amp; (input.type !== \u003Cspan class=\"fmstr-cmp-ffh-code__str\">'email'\u003C\u002Fspan> || \u002F^\\S+@\\S+\\.\\S+$\u002F.test(input.value));\ninput.setAttribute(\u003Cspan class=\"fmstr-cmp-ffh-code__str\">'aria-invalid'\u003C\u002Fspan>, valid ? \u003Cspan class=\"fmstr-cmp-ffh-code__str\">'false'\u003C\u002Fspan> : \u003Cspan class=\"fmstr-cmp-ffh-code__str\">'true'\u003C\u002Fspan>);\nif (!valid &amp;&amp; !firstInvalid) firstInvalid = input;\n});\nif (firstInvalid) { e.preventDefault(); firstInvalid.focus(); }\n});\n\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;\u002Fscript&gt;\u003C\u002Fspan>\n\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;\u002Fbody&gt;\u003C\u002Fspan>\n\u003Cspan class=\"fmstr-cmp-ffh-code__tag\">&lt;\u002Fhtml&gt;\u003C\u002Fspan>\u003C\u002Fcode>\u003C\u002Fpre>\n\u003C\u002Fdiv>\n\u003C\u002Fdiv>\n\n\u003Cp class=\"fmstr-cmp-ffh-code__foot\">The \u003Ccode>action\u003C\u002Fcode> URL above points to \u003Ca href=\"https:\u002F\u002Fformester.com\u002Ffeatures\u002Fhtml-form-backend\u002F\">Formester&rsquo;s HTML form backend\u003C\u002Fa>. Replace \u003Ccode>YOUR_FORM_ID\u003C\u002Fcode> with your form&rsquo;s ID, or point it at your own server. Everything else stays the same.\u003C\u002Fp>\n\u003C\u002Fdiv>\n\u003C\u002Fsection>\n\n\u003Csection class=\"fmstr-cmp-ffh-body\" aria-label=\"Common mistakes and variants\">\n\u003Cdiv class=\"fmstr-cmp-ffh-body__container\">\n\n\u003Ch2 class=\"fmstr-cmp-ffh-body__h2\">Common mistakes that break feedback forms\u003C\u002Fh2>\n\u003Cul>\n\u003Cli>\u003Cstrong>\u003Ccode>mailto:\u003C\u002Fcode> as the action.\u003C\u002Fstrong> Looks like the easy answer. Drops half your submissions because the user has to manually send the draft. Use a real backend.\u003C\u002Fli>\n\u003Cli>\u003Cstrong>Missing \u003Ccode>name\u003C\u002Fcode> attributes.\u003C\u002Fstrong> The form POSTs successfully but the server gets empty fields. \u003Ccode>id\u003C\u002Fcode> is for CSS and labels; \u003Ccode>name\u003C\u002Fcode> is what the server reads.\u003C\u002Fli>\n\u003Cli>\u003Cstrong>Removed focus outlines.\u003C\u002Fstrong> \u003Ccode>outline: none\u003C\u002Fcode> is the most copy-pasted CSS mistake on the web. It breaks keyboard navigation. Replace the outline; don't delete it.\u003C\u002Fli>\n\u003Cli>\u003Cstrong>Client-side validation only.\u003C\u002Fstrong> A user with DevTools open can submit anything. Validate on the server too.\u003C\u002Fli>\n\u003Cli>\u003Cstrong>No spam protection.\u003C\u002Fstrong> Public forms attract bots within hours. Add a honeypot field (a hidden input that bots fill and humans don't) or a CAPTCHA. \u003Ca href=\"https:\u002F\u002Fformester.com\u002Ffeatures\u002Fspam-protection\u002F\">Formester's backend\u003C\u002Fa> does this automatically.\u003C\u002Fli>\n\u003Cli>\u003Cstrong>No confirmation page or message.\u003C\u002Fstrong> The user submits, the page reloads, nothing visibly changes. They submit again. Add a \u003Ccode>&lt;p role=\"status\"&gt;Thanks, we got it&lt;\u002Fp&gt;\u003C\u002Fcode> or redirect to a thank-you page.\u003C\u002Fli>\n\u003C\u002Ful>\n\n\u003Ch2 class=\"fmstr-cmp-ffh-body__h2\">Variants of the feedback form\u003C\u002Fh2>\n\u003Cp>The base form covers most cases. Three common variants:\u003C\u002Fp>\n\u003Cdiv class=\"fmstr-cmp-ffh-body__variants\">\n\u003Cdiv class=\"fmstr-cmp-ffh-body__variant\">\n\u003Ch4>Customer feedback (with rating)\u003C\u002Fh4>\n\u003Cp>Add a 1-5 star scale instead of the dropdown. The \u003Ccode>&lt;input type=\"range\"&gt;\u003C\u002Fcode> works, but a row of radio buttons styled as stars is clearer for screen readers. The \u003Ca href=\"https:\u002F\u002Fformester.com\u002Ftemplates\u002Fcustomer-feedback-form-31840\u002F\">customer feedback form template\u003C\u002Fa> ships this layout pre-built.\u003C\u002Fp>\n\u003C\u002Fdiv>\n\u003Cdiv class=\"fmstr-cmp-ffh-body__variant\">\n\u003Ch4>Product feedback (with feature picker)\u003C\u002Fh4>\n\u003Cp>Add a checkbox group: \"Which features did you use?\" with options like Onboarding, Search, Reporting. Use \u003Ccode>&lt;fieldset&gt;&lt;legend&gt;\u003C\u002Fcode> around the group so screen readers announce it as one question. The \u003Ca href=\"https:\u002F\u002Fformester.com\u002Ftemplates\u002Fcategories\u002Ffeedback-forms\u002F\">feedback form templates library\u003C\u002Fa> has a fuller version.\u003C\u002Fp>\n\u003C\u002Fdiv>\n\u003Cdiv class=\"fmstr-cmp-ffh-body__variant\">\n\u003Ch4>Employee feedback (anonymous)\u003C\u002Fh4>\n\u003Cp>Drop the name and email fields entirely. Add a \"Department\" dropdown and a longer text area. If you collect this through Formester, turn off IP tracking in the form settings to keep submissions genuinely anonymous. The \u003Ca href=\"https:\u002F\u002Fformester.com\u002Ftemplates\u002Fcategories\u002Ffeedback-forms\u002F\">employee feedback templates\u003C\u002Fa> are preconfigured for this.\u003C\u002Fp>\n\u003C\u002Fdiv>\n\u003C\u002Fdiv>\n\n\u003C\u002Fdiv>\n\u003C\u002Fsection>\n\n\u003Cstyle>\n\u002F* host-link-override *\u002F\n.fmstr-cmp-ffh-a11y a { text-decoration: none !important; }\n.fmstr-cmp-ffh-a11y {\n--fmstr-cmp-ffh-a11y-bg-card: #ffffff;\n--fmstr-cmp-ffh-a11y-bg-code: #0f172a;\n--fmstr-cmp-ffh-a11y-fg-1: #101828;\n--fmstr-cmp-ffh-a11y-fg-2: #475467;\n--fmstr-cmp-ffh-a11y-fg-3: #697586;\n--fmstr-cmp-ffh-a11y-violet-500: #7f56d9;\n--fmstr-cmp-ffh-a11y-violet-600: #6941c6;\n--fmstr-cmp-ffh-a11y-tint: #f7f3ff;\n--fmstr-cmp-ffh-a11y-edge: #e4d7ff;\n--fmstr-cmp-ffh-a11y-border: #eaecf0;\n--fmstr-cmp-ffh-a11y-red-bg: #fef2f2;\n--fmstr-cmp-ffh-a11y-red-edge: #fecaca;\n--fmstr-cmp-ffh-a11y-red: #b91c1c;\n--fmstr-cmp-ffh-a11y-green-bg: #f0fdf4;\n--fmstr-cmp-ffh-a11y-green-edge: #bbf7d0;\n--fmstr-cmp-ffh-a11y-green: #15803d;\n--fmstr-cmp-ffh-a11y-shadow: 0 4px 20px rgba(16,24,40,.06), 0 2px 6px rgba(16,24,40,.04);\n\nbackground: transparent; padding: 56px 24px;\nfont-family: inherit; color: var(--fmstr-cmp-ffh-a11y-fg-1);\n}\n.fmstr-cmp-ffh-a11y *, .fmstr-cmp-ffh-a11y *::before, .fmstr-cmp-ffh-a11y *::after { box-sizing: border-box; }\n.fmstr-cmp-ffh-a11y__container { max-width: 820px; margin: 0 auto; }\n.fmstr-cmp-ffh-a11y__head { margin: 0 0 28px; }\n.fmstr-cmp-ffh-a11y__eyebrow {\ndisplay: inline-block; padding: 5px 12px; border-radius: 9999px;\nbackground: var(--fmstr-cmp-ffh-a11y-tint); color: var(--fmstr-cmp-ffh-a11y-violet-600);\nfont-size: 12px; font-weight: 600; letter-spacing: .04em;\ntext-transform: uppercase; border: 1px solid var(--fmstr-cmp-ffh-a11y-edge); margin: 0 0 14px;\n}\n.fmstr-cmp-ffh-a11y__h2 { font-size: clamp(26px, 3vw, 36px); font-weight: 700; line-height: 1.15; letter-spacing: -.02em; margin: 0; }\n.fmstr-cmp-ffh-a11y__intro { color: var(--fmstr-cmp-ffh-a11y-fg-3); font-size: 17px; line-height: 1.6; margin: 14px 0 0; }\n\n.fmstr-cmp-ffh-a11y__list { display: flex; flex-direction: column; gap: 16px; }\n.fmstr-cmp-ffh-a11y__item {\nbackground: var(--fmstr-cmp-ffh-a11y-bg-card);\nborder: 1px solid var(--fmstr-cmp-ffh-a11y-border);\nborder-radius: 16px; padding: 22px 24px;\ndisplay: grid; grid-template-columns: 44px 1fr 1fr; gap: 20px; align-items: start;\nbox-shadow: var(--fmstr-cmp-ffh-a11y-shadow);\n}\n.fmstr-cmp-ffh-a11y__num {\nwidth: 36px; height: 36px; border-radius: 10px;\nbackground: var(--fmstr-cmp-ffh-a11y-tint);\ncolor: var(--fmstr-cmp-ffh-a11y-violet-600);\ndisplay: grid; place-items: center;\nfont-weight: 700; font-size: 15px;\nborder: 1px solid var(--fmstr-cmp-ffh-a11y-edge);\n}\n\n.fmstr-cmp-ffh-a11y__copy h3 {\nfont-size: 17px; font-weight: 600; letter-spacing: -.01em;\ncolor: var(--fmstr-cmp-ffh-a11y-fg-1); margin: 0 0 6px;\n}\n.fmstr-cmp-ffh-a11y__copy p { color: var(--fmstr-cmp-ffh-a11y-fg-2); font-size: 14.5px; line-height: 1.6; margin: 0; }\n.fmstr-cmp-ffh-a11y__copy strong { color: var(--fmstr-cmp-ffh-a11y-fg-1); font-weight: 600; }\n\n.fmstr-cmp-ffh-a11y__pair { display: flex; flex-direction: column; gap: 10px; }\n.fmstr-cmp-ffh-a11y__codebox {\nbackground: var(--fmstr-cmp-ffh-a11y-bg-code);\nborder-radius: 8px; padding: 10px 12px;\nfont-family: ui-monospace, Menlo, Monaco, monospace;\nfont-size: 11.5px; line-height: 1.55;\ncolor: #e2e8f0; overflow-x: auto; margin: 0;\nwhite-space: pre; position: relative; padding-left: 50px;\n}\n.fmstr-cmp-ffh-a11y__codebox code { font-family: inherit; }\n.fmstr-cmp-ffh-a11y__codebox::before {\ncontent: \"\"; position: absolute; left: 10px; top: 11px;\nwidth: 14px; height: 14px; border-radius: 50%;\nbackground-repeat: no-repeat; background-position: center;\n}\n.fmstr-cmp-ffh-a11y__codebox--bad::before { background-color: var(--fmstr-cmp-ffh-a11y-red-bg); background-image: url(\"data:image\u002Fsvg+xml,%3Csvg xmlns='http:\u002F\u002Fwww.w3.org\u002F2000\u002Fsvg' width='8' height='8' viewBox='0 0 8 8' fill='none' stroke='%23b91c1c' stroke-width='2' stroke-linecap='round'%3E%3Cpath d='M1.5 1.5 L6.5 6.5 M6.5 1.5 L1.5 6.5'\u002F%3E%3C\u002Fsvg%3E\"); }\n.fmstr-cmp-ffh-a11y__codebox--good::before { background-color: var(--fmstr-cmp-ffh-a11y-green-bg); background-image: url(\"data:image\u002Fsvg+xml,%3Csvg xmlns='http:\u002F\u002Fwww.w3.org\u002F2000\u002Fsvg' width='9' height='9' viewBox='0 0 9 9' fill='none' stroke='%2315803d' stroke-width='2' stroke-linecap='round' stroke-linejoin='round'%3E%3Cpath d='M1.5 4.5 L3.5 6.5 L7 3'\u002F%3E%3C\u002Fsvg%3E\"); }\n.fmstr-cmp-ffh-a11y__codebox-label {\nposition: absolute; top: 11px; left: 28px;\nfont-size: 9px; font-weight: 700; letter-spacing: .08em;\ntext-transform: uppercase;\n}\n.fmstr-cmp-ffh-a11y__codebox--bad .fmstr-cmp-ffh-a11y__codebox-label { color: var(--fmstr-cmp-ffh-a11y-red); }\n.fmstr-cmp-ffh-a11y__codebox--good .fmstr-cmp-ffh-a11y__codebox-label { color: var(--fmstr-cmp-ffh-a11y-green); }\n\n.fmstr-cmp-ffh-a11y__codebox .t { color: #f472b6; }\n.fmstr-cmp-ffh-a11y__codebox .a { color: #a5b4fc; }\n.fmstr-cmp-ffh-a11y__codebox .s { color: #86efac; }\n\n.fmstr-cmp-ffh-a11y__foot {\nmargin: 28px auto 0; max-width: 760px; text-align: center;\ncolor: var(--fmstr-cmp-ffh-a11y-fg-3); font-size: 14.5px; line-height: 1.6;\n}\n.fmstr-cmp-ffh-a11y__foot a { color: var(--fmstr-cmp-ffh-a11y-violet-600) !important; font-weight: 600; }\n.fmstr-cmp-ffh-a11y__foot a:hover { text-decoration: underline !important; }\n\n@media (max-width: 880px) {\n.fmstr-cmp-ffh-a11y__item { grid-template-columns: 36px 1fr; gap: 16px; }\n.fmstr-cmp-ffh-a11y__pair { grid-column: 1 \u002F -1; }\n}\n@media (max-width: 760px) {\n.fmstr-cmp-ffh-a11y { padding: 40px 16px; }\n.fmstr-cmp-ffh-a11y__item { padding: 18px; border-radius: 14px; }\n.fmstr-cmp-ffh-a11y__intro { font-size: 15.5px; }\n.fmstr-cmp-ffh-a11y__codebox { font-size: 11px; }\n}\n\u003C\u002Fstyle>\n\n\u003Csection class=\"fmstr-cmp-ffh-a11y\" aria-labelledby=\"fmstr-cmp-ffh-a11y-h2\">\n\u003Cdiv class=\"fmstr-cmp-ffh-a11y__container\">\n\u003Cdiv class=\"fmstr-cmp-ffh-a11y__head\">\n\u003Cspan class=\"fmstr-cmp-ffh-a11y__eyebrow\">Five flags worth catching\u003C\u002Fspan>\n\u003Ch2 class=\"fmstr-cmp-ffh-a11y__h2\" id=\"fmstr-cmp-ffh-a11y-h2\">Accessibility checklist for an HTML feedback form\u003C\u002Fh2>\n\u003Cp class=\"fmstr-cmp-ffh-a11y__intro\">Every item below is something keyboard and screen-reader users actually hit. Skip these and a measurable chunk of your audience can&rsquo;t complete the form.\u003C\u002Fp>\n\u003C\u002Fdiv>\n\n\u003Cdiv class=\"fmstr-cmp-ffh-a11y__list\">\n\n\u003Carticle class=\"fmstr-cmp-ffh-a11y__item\">\n\u003Cdiv class=\"fmstr-cmp-ffh-a11y__num\">1\u003C\u002Fdiv>\n\u003Cdiv class=\"fmstr-cmp-ffh-a11y__copy\">\n\u003Ch3>Pair every label with its input\u003C\u002Fh3>\n\u003Cp>The label&rsquo;s \u003Ccode>for\u003C\u002Fcode> must match the input&rsquo;s \u003Ccode>id\u003C\u002Fcode>. Click the label, focus the input. Screen readers announce the label out loud. Skip this and the form fails WCAG 2.1 and loses keyboard users.\u003C\u002Fp>\n\u003C\u002Fdiv>\n\u003Cdiv class=\"fmstr-cmp-ffh-a11y__pair\">\n\u003Cpre class=\"fmstr-cmp-ffh-a11y__codebox fmstr-cmp-ffh-a11y__codebox--bad\">\u003Cspan class=\"fmstr-cmp-ffh-a11y__codebox-label\">No\u003C\u002Fspan>\u003Ccode>\u003Cspan class=\"t\">&lt;label&gt;\u003C\u002Fspan>Email\u003Cspan class=\"t\">&lt;\u002Flabel&gt;\u003C\u002Fspan>\n\u003Cspan class=\"t\">&lt;input\u003C\u002Fspan> \u003Cspan class=\"a\">type\u003C\u002Fspan>=\u003Cspan class=\"s\">\"email\"\u003C\u002Fspan>\u003Cspan class=\"t\">&gt;\u003C\u002Fspan>\u003C\u002Fcode>\u003C\u002Fpre>\n\u003Cpre class=\"fmstr-cmp-ffh-a11y__codebox fmstr-cmp-ffh-a11y__codebox--good\">\u003Cspan class=\"fmstr-cmp-ffh-a11y__codebox-label\">Yes\u003C\u002Fspan>\u003Ccode>\u003Cspan class=\"t\">&lt;label\u003C\u002Fspan> \u003Cspan class=\"a\">for\u003C\u002Fspan>=\u003Cspan class=\"s\">\"email\"\u003C\u002Fspan>\u003Cspan class=\"t\">&gt;\u003C\u002Fspan>Email\u003Cspan class=\"t\">&lt;\u002Flabel&gt;\u003C\u002Fspan>\n\u003Cspan class=\"t\">&lt;input\u003C\u002Fspan> \u003Cspan class=\"a\">id\u003C\u002Fspan>=\u003Cspan class=\"s\">\"email\"\u003C\u002Fspan> \u003Cspan class=\"a\">type\u003C\u002Fspan>=\u003Cspan class=\"s\">\"email\"\u003C\u002Fspan>\u003Cspan class=\"t\">&gt;\u003C\u002Fspan>\u003C\u002Fcode>\u003C\u002Fpre>\n\u003C\u002Fdiv>\n\u003C\u002Farticle>\n\n\u003Carticle class=\"fmstr-cmp-ffh-a11y__item\">\n\u003Cdiv class=\"fmstr-cmp-ffh-a11y__num\">2\u003C\u002Fdiv>\n\u003Cdiv class=\"fmstr-cmp-ffh-a11y__copy\">\n\u003Ch3>Connect errors with \u003Ccode>aria-describedby\u003C\u002Fcode>\u003C\u002Fh3>\n\u003Cp>An invalid field needs \u003Ccode>aria-invalid=\"true\"\u003C\u002Fcode> plus an \u003Ccode>aria-describedby\u003C\u002Fcode> that points at the visible error message. Screen readers then announce the error along with the field name on focus.\u003C\u002Fp>\n\u003C\u002Fdiv>\n\u003Cdiv class=\"fmstr-cmp-ffh-a11y__pair\">\n\u003Cpre class=\"fmstr-cmp-ffh-a11y__codebox fmstr-cmp-ffh-a11y__codebox--bad\">\u003Cspan class=\"fmstr-cmp-ffh-a11y__codebox-label\">No\u003C\u002Fspan>\u003Ccode>\u003Cspan class=\"t\">&lt;input\u003C\u002Fspan> \u003Cspan class=\"a\">id\u003C\u002Fspan>=\u003Cspan class=\"s\">\"email\"\u003C\u002Fspan>\u003Cspan class=\"t\">&gt;\u003C\u002Fspan>\n\u003Cspan class=\"t\">&lt;span&gt;\u003C\u002Fspan>Invalid email\u003Cspan class=\"t\">&lt;\u002Fspan&gt;\u003C\u002Fspan>\u003C\u002Fcode>\u003C\u002Fpre>\n\u003Cpre class=\"fmstr-cmp-ffh-a11y__codebox fmstr-cmp-ffh-a11y__codebox--good\">\u003Cspan class=\"fmstr-cmp-ffh-a11y__codebox-label\">Yes\u003C\u002Fspan>\u003Ccode>\u003Cspan class=\"t\">&lt;input\u003C\u002Fspan> \u003Cspan class=\"a\">id\u003C\u002Fspan>=\u003Cspan class=\"s\">\"email\"\u003C\u002Fspan>\n\u003Cspan class=\"a\">aria-invalid\u003C\u002Fspan>=\u003Cspan class=\"s\">\"true\"\u003C\u002Fspan>\n\u003Cspan class=\"a\">aria-describedby\u003C\u002Fspan>=\u003Cspan class=\"s\">\"email-error\"\u003C\u002Fspan>\u003Cspan class=\"t\">&gt;\u003C\u002Fspan>\n\u003Cspan class=\"t\">&lt;span\u003C\u002Fspan> \u003Cspan class=\"a\">id\u003C\u002Fspan>=\u003Cspan class=\"s\">\"email-error\"\u003C\u002Fspan>\u003Cspan class=\"t\">&gt;\u003C\u002Fspan>Invalid email\u003Cspan class=\"t\">&lt;\u002Fspan&gt;\u003C\u002Fspan>\u003C\u002Fcode>\u003C\u002Fpre>\n\u003C\u002Fdiv>\n\u003C\u002Farticle>\n\n\u003Carticle class=\"fmstr-cmp-ffh-a11y__item\">\n\u003Cdiv class=\"fmstr-cmp-ffh-a11y__num\">3\u003C\u002Fdiv>\n\u003Cdiv class=\"fmstr-cmp-ffh-a11y__copy\">\n\u003Ch3>Use \u003Ccode>autocomplete\u003C\u002Fcode> tokens\u003C\u002Fh3>\n\u003Cp>One line per field. Browsers prefill from saved info, password managers behave, and assistive tech recognizes the field&rsquo;s purpose. Measurable lift in completion rate on mobile.\u003C\u002Fp>\n\u003C\u002Fdiv>\n\u003Cdiv class=\"fmstr-cmp-ffh-a11y__pair\">\n\u003Cpre class=\"fmstr-cmp-ffh-a11y__codebox fmstr-cmp-ffh-a11y__codebox--bad\">\u003Cspan class=\"fmstr-cmp-ffh-a11y__codebox-label\">No\u003C\u002Fspan>\u003Ccode>\u003Cspan class=\"t\">&lt;input\u003C\u002Fspan> \u003Cspan class=\"a\">type\u003C\u002Fspan>=\u003Cspan class=\"s\">\"text\"\u003C\u002Fspan> \u003Cspan class=\"a\">name\u003C\u002Fspan>=\u003Cspan class=\"s\">\"name\"\u003C\u002Fspan>\u003Cspan class=\"t\">&gt;\u003C\u002Fspan>\n\u003Cspan class=\"t\">&lt;input\u003C\u002Fspan> \u003Cspan class=\"a\">type\u003C\u002Fspan>=\u003Cspan class=\"s\">\"email\"\u003C\u002Fspan> \u003Cspan class=\"a\">name\u003C\u002Fspan>=\u003Cspan class=\"s\">\"email\"\u003C\u002Fspan>\u003Cspan class=\"t\">&gt;\u003C\u002Fspan>\u003C\u002Fcode>\u003C\u002Fpre>\n\u003Cpre class=\"fmstr-cmp-ffh-a11y__codebox fmstr-cmp-ffh-a11y__codebox--good\">\u003Cspan class=\"fmstr-cmp-ffh-a11y__codebox-label\">Yes\u003C\u002Fspan>\u003Ccode>\u003Cspan class=\"t\">&lt;input\u003C\u002Fspan> \u003Cspan class=\"a\">type\u003C\u002Fspan>=\u003Cspan class=\"s\">\"text\"\u003C\u002Fspan> \u003Cspan class=\"a\">name\u003C\u002Fspan>=\u003Cspan class=\"s\">\"name\"\u003C\u002Fspan>\n\u003Cspan class=\"a\">autocomplete\u003C\u002Fspan>=\u003Cspan class=\"s\">\"name\"\u003C\u002Fspan>\u003Cspan class=\"t\">&gt;\u003C\u002Fspan>\n\u003Cspan class=\"t\">&lt;input\u003C\u002Fspan> \u003Cspan class=\"a\">type\u003C\u002Fspan>=\u003Cspan class=\"s\">\"email\"\u003C\u002Fspan> \u003Cspan class=\"a\">name\u003C\u002Fspan>=\u003Cspan class=\"s\">\"email\"\u003C\u002Fspan>\n\u003Cspan class=\"a\">autocomplete\u003C\u002Fspan>=\u003Cspan class=\"s\">\"email\"\u003C\u002Fspan>\u003Cspan class=\"t\">&gt;\u003C\u002Fspan>\u003C\u002Fcode>\u003C\u002Fpre>\n\u003C\u002Fdiv>\n\u003C\u002Farticle>\n\n\u003Carticle class=\"fmstr-cmp-ffh-a11y__item\">\n\u003Cdiv class=\"fmstr-cmp-ffh-a11y__num\">4\u003C\u002Fdiv>\n\u003Cdiv class=\"fmstr-cmp-ffh-a11y__copy\">\n\u003Ch3>Keep focus outlines visible\u003C\u002Fh3>\n\u003Cp>\u003Ccode>outline: none\u003C\u002Fcode> is the single most-copied CSS mistake on the web. It breaks keyboard navigation. Replace the default outline, never delete it. The visible ring is how a sighted keyboard user knows where they are.\u003C\u002Fp>\n\u003C\u002Fdiv>\n\u003Cdiv class=\"fmstr-cmp-ffh-a11y__pair\">\n\u003Cpre class=\"fmstr-cmp-ffh-a11y__codebox fmstr-cmp-ffh-a11y__codebox--bad\">\u003Cspan class=\"fmstr-cmp-ffh-a11y__codebox-label\">No\u003C\u002Fspan>\u003Ccode>input:focus { outline: none; }\u003C\u002Fcode>\u003C\u002Fpre>\n\u003Cpre class=\"fmstr-cmp-ffh-a11y__codebox fmstr-cmp-ffh-a11y__codebox--good\">\u003Cspan class=\"fmstr-cmp-ffh-a11y__codebox-label\">Yes\u003C\u002Fspan>\u003Ccode>input:focus {\noutline: 2px solid #5b6cff;\noutline-offset: 1px;\n}\u003C\u002Fcode>\u003C\u002Fpre>\n\u003C\u002Fdiv>\n\u003C\u002Farticle>\n\n\u003Carticle class=\"fmstr-cmp-ffh-a11y__item\">\n\u003Cdiv class=\"fmstr-cmp-ffh-a11y__num\">5\u003C\u002Fdiv>\n\u003Cdiv class=\"fmstr-cmp-ffh-a11y__copy\">\n\u003Ch3>Mark required fields semantically\u003C\u002Fh3>\n\u003Cp>The native \u003Ccode>required\u003C\u002Fcode> attribute does two jobs at once: it tells the browser to block submission and tells screen readers the field is required. Don&rsquo;t fake it with just a red asterisk in the label.\u003C\u002Fp>\n\u003C\u002Fdiv>\n\u003Cdiv class=\"fmstr-cmp-ffh-a11y__pair\">\n\u003Cpre class=\"fmstr-cmp-ffh-a11y__codebox fmstr-cmp-ffh-a11y__codebox--bad\">\u003Cspan class=\"fmstr-cmp-ffh-a11y__codebox-label\">No\u003C\u002Fspan>\u003Ccode>\u003Cspan class=\"t\">&lt;label&gt;\u003C\u002Fspan>Email \u003Cspan class=\"t\">&lt;span&gt;\u003C\u002Fspan>*\u003Cspan class=\"t\">&lt;\u002Fspan&gt;&lt;\u002Flabel&gt;\u003C\u002Fspan>\n\u003Cspan class=\"t\">&lt;input\u003C\u002Fspan> \u003Cspan class=\"a\">type\u003C\u002Fspan>=\u003Cspan class=\"s\">\"email\"\u003C\u002Fspan>\u003Cspan class=\"t\">&gt;\u003C\u002Fspan>\u003C\u002Fcode>\u003C\u002Fpre>\n\u003Cpre class=\"fmstr-cmp-ffh-a11y__codebox fmstr-cmp-ffh-a11y__codebox--good\">\u003Cspan class=\"fmstr-cmp-ffh-a11y__codebox-label\">Yes\u003C\u002Fspan>\u003Ccode>\u003Cspan class=\"t\">&lt;label\u003C\u002Fspan> \u003Cspan class=\"a\">for\u003C\u002Fspan>=\u003Cspan class=\"s\">\"email\"\u003C\u002Fspan>\u003Cspan class=\"t\">&gt;\u003C\u002Fspan>Email (required)\u003Cspan class=\"t\">&lt;\u002Flabel&gt;\u003C\u002Fspan>\n\u003Cspan class=\"t\">&lt;input\u003C\u002Fspan> \u003Cspan class=\"a\">id\u003C\u002Fspan>=\u003Cspan class=\"s\">\"email\"\u003C\u002Fspan> \u003Cspan class=\"a\">type\u003C\u002Fspan>=\u003Cspan class=\"s\">\"email\"\u003C\u002Fspan> \u003Cspan class=\"a\">required\u003C\u002Fspan>\u003Cspan class=\"t\">&gt;\u003C\u002Fspan>\u003C\u002Fcode>\u003C\u002Fpre>\n\u003C\u002Fdiv>\n\u003C\u002Farticle>\n\n\u003C\u002Fdiv>\n\n\u003Cp class=\"fmstr-cmp-ffh-a11y__foot\">For edge cases (fieldsets, error summaries, custom controls), the \u003Ca href=\"https:\u002F\u002Fdeveloper.mozilla.org\u002Fen-US\u002Fdocs\u002FWeb\u002FHTML\u002FReference\u002FElements\u002Fform\">MDN \u003Ccode>&lt;form&gt;\u003C\u002Fcode> reference\u003C\u002Fa> is the canonical source.\u003C\u002Fp>\n\u003C\u002Fdiv>\n\u003C\u002Fsection>\n\n\u003Cstyle>\n\u002F* host-link-override *\u002F\n.fmstr-cmp-ffh-faq a { text-decoration: none !important; }\n.fmstr-cmp-ffh-faq {\n--c-bg: #fafafb; --c-card: #ffffff;\n--c-fg-1: #101828; --c-fg-2: #475467;\n--c-violet-600: #6941c6; --c-tint: #f7f3ff; --c-edge: #e4d7ff;\n--c-border: #eaecf0; --c-chip-bg: #f4f4f7;\n--c-shadow: 0 1px 3px rgba(16,24,40,.05);\n\nbackground: transparent; padding: 56px 24px;\nfont-family: inherit;\ncolor: var(--c-fg-1);\n}\n.fmstr-cmp-ffh-faq *, .fmstr-cmp-ffh-faq *::before, .fmstr-cmp-ffh-faq *::after { box-sizing: border-box; }\n.fmstr-cmp-ffh-faq__container { max-width: 820px; margin: 0 auto; }\n.fmstr-cmp-ffh-faq__h2 { font-size: clamp(26px, 3vw, 36px); font-weight: 700; line-height: 1.15; letter-spacing: -.02em; margin: 0; color: var(--c-fg-1); }\n.fmstr-cmp-ffh-faq__intro { color: #697586; font-size: 17px; line-height: 1.6; margin: 14px 0 28px; max-width: 760px; }\n.fmstr-cmp-ffh-faq__list { display: flex; flex-direction: column; gap: 12px; }\n.fmstr-cmp-ffh-faq__item {\nbackground: var(--c-card); border: 1px solid var(--c-border);\nborder-radius: 14px; box-shadow: var(--c-shadow); overflow: hidden;\n}\n.fmstr-cmp-ffh-faq__item > summary {\npadding: 18px 22px; cursor: pointer; font-weight: 600; font-size: 16.5px;\ncolor: var(--c-fg-1); display: flex; align-items: center; gap: 14px;\nlist-style: none;\n}\n.fmstr-cmp-ffh-faq__item > summary::-webkit-details-marker { display: none; }\n.fmstr-cmp-ffh-faq__item > summary::before {\ncontent: \"\"; width: 28px; height: 28px; border-radius: 8px; flex-shrink: 0;\nbackground-color: var(--c-chip-bg);\nbackground-image: url(\"data:image\u002Fsvg+xml,%3Csvg xmlns='http:\u002F\u002Fwww.w3.org\u002F2000\u002Fsvg' width='14' height='14' viewBox='0 0 14 14' fill='none' stroke='%2375747f' stroke-width='2' stroke-linecap='round' stroke-linejoin='round'%3E%3Cpath d='M3 5l4 4 4-4'\u002F%3E%3C\u002Fsvg%3E\");\nbackground-repeat: no-repeat; background-position: center;\ntransition: transform .15s ease, background-color .15s ease;\n}\n.fmstr-cmp-ffh-faq__item[open] > summary::before { transform: rotate(180deg); background-color: var(--c-tint); }\n.fmstr-cmp-ffh-faq__item[open] > summary { color: var(--c-violet-600); }\n.fmstr-cmp-ffh-faq__answer { padding: 0 22px 22px 64px; color: var(--c-fg-2); font-size: 15.5px; line-height: 1.7; }\n.fmstr-cmp-ffh-faq__answer a { color: var(--c-violet-600) !important; text-decoration: none !important; }\n.fmstr-cmp-ffh-faq__answer a:hover { text-decoration: underline !important; }\n.fmstr-cmp-ffh-faq__answer code {\nbackground: var(--c-chip-bg); padding: 1px 6px; border-radius: 4px;\nfont-family: ui-monospace, Menlo, Monaco, monospace; font-size: 13.5px;\ncolor: var(--c-violet-600);\n}\n\n@media (max-width: 760px) {\n.fmstr-cmp-ffh-faq { padding: 40px 16px; }\n.fmstr-cmp-ffh-faq__intro { font-size: 15.5px; }\n.fmstr-cmp-ffh-faq__item > summary { padding: 16px 16px; font-size: 15.5px; gap: 12px; }\n.fmstr-cmp-ffh-faq__item > summary::before { width: 26px; height: 26px; }\n.fmstr-cmp-ffh-faq__answer { padding: 0 16px 18px 16px; font-size: 15px; line-height: 1.65; }\n}\n\u003C\u002Fstyle>\n\n\u003Csection class=\"fmstr-cmp-ffh-faq\" aria-labelledby=\"fmstr-cmp-ffh-faq-h2\">\n\u003Cdiv class=\"fmstr-cmp-ffh-faq__container\">\n\u003Ch2 class=\"fmstr-cmp-ffh-faq__h2\" id=\"fmstr-cmp-ffh-faq-h2\">HTML feedback form FAQ\u003C\u002Fh2>\n\u003Cp class=\"fmstr-cmp-ffh-faq__intro\">Answers that mirror the FAQPage JSON-LD on the live page.\u003C\u002Fp>\n\u003Cdiv class=\"fmstr-cmp-ffh-faq__list\">\n\n\u003Cdetails class=\"fmstr-cmp-ffh-faq__item\">\n\u003Csummary>How do you add a feedback form in HTML?\u003C\u002Fsummary>\n\u003Cdiv class=\"fmstr-cmp-ffh-faq__answer\">Use a \u003Ccode>&lt;form&gt;\u003C\u002Fcode> element with \u003Ccode>action\u003C\u002Fcode> set to your submission endpoint and \u003Ccode>method=\"post\"\u003C\u002Fcode>. Inside the form, add labeled \u003Ccode>&lt;input&gt;\u003C\u002Fcode> and \u003Ccode>&lt;textarea&gt;\u003C\u002Fcode> elements with \u003Ccode>name\u003C\u002Fcode> attributes. Style with CSS, validate with JavaScript, and point the \u003Ccode>action\u003C\u002Fcode> at a backend (your server, or a service like \u003Ca href=\"https:\u002F\u002Fformester.com\u002Ffeatures\u002Fhtml-form-backend\u002F\">Formester&rsquo;s HTML form backend\u003C\u002Fa>). The complete copy-paste example above is the shortest working version.\u003C\u002Fdiv>\n\u003C\u002Fdetails>\n\n\u003Cdetails class=\"fmstr-cmp-ffh-faq__item\">\n\u003Csummary>How do I create a feedback form?\u003C\u002Fsummary>\n\u003Cdiv class=\"fmstr-cmp-ffh-faq__answer\">Decide what to ask (name, email, rating, open-ended feedback are the standard four). Write the HTML using a \u003Ccode>&lt;form&gt;\u003C\u002Fcode> with one labeled input per question. Style it with CSS so it matches your site. Hook the \u003Ccode>action\u003C\u002Fcode> to a backend that stores submissions. The full process is the six steps above, or skip ahead to \u003Ca href=\"https:\u002F\u002Fformester.com\u002Ffeatures\u002Fdrag-and-drop-form-builder\u002F\">Formester&rsquo;s drag-and-drop builder\u003C\u002Fa> if you&rsquo;d rather not write code.\u003C\u002Fdiv>\n\u003C\u002Fdetails>\n\n\u003Cdetails class=\"fmstr-cmp-ffh-faq__item\">\n\u003Csummary>How do I create an inquiry form in HTML?\u003C\u002Fsummary>\n\u003Cdiv class=\"fmstr-cmp-ffh-faq__answer\">Same pattern as a feedback form, with different field labels. Swap \"How was your experience?\" for \"What are you interested in?\" and \"Your feedback\" for \"Your message.\" Keep the name, email, and submit-button structure identical. For a longer inquiry form with subject lines and contact preferences, the \u003Ca href=\"https:\u002F\u002Fformester.com\u002Fblog\u002Fcontact-form-design-tips-best-practices-and-examples\u002F\">contact form design best practices guide\u003C\u002Fa> covers the patterns.\u003C\u002Fdiv>\n\u003C\u002Fdetails>\n\n\u003Cdetails class=\"fmstr-cmp-ffh-faq__item\">\n\u003Csummary>How do you add a comment to a form in HTML?\u003C\u002Fsummary>\n\u003Cdiv class=\"fmstr-cmp-ffh-faq__answer\">Two meanings. (1) An HTML comment for developers: \u003Ccode>&lt;!-- this is the feedback section --&gt;\u003C\u002Fcode> between elements. (2) A user-facing comment field: a \u003Ccode>&lt;textarea&gt;\u003C\u002Fcode> with a label like \"Your comments.\" If you want comments to be optional, leave off the \u003Ccode>required\u003C\u002Fcode> attribute. Use \u003Ccode>rows\u003C\u002Fcode> and \u003Ccode>cols\u003C\u002Fcode> (or CSS height) to size the box.\u003C\u002Fdiv>\n\u003C\u002Fdetails>\n\n\u003Cdetails class=\"fmstr-cmp-ffh-faq__item\">\n\u003Csummary>How do I add CSS to a feedback form?\u003C\u002Fsummary>\n\u003Cdiv class=\"fmstr-cmp-ffh-faq__answer\">Two options. Inline \u003Ccode>&lt;style&gt;\u003C\u002Fcode> tags inside \u003Ccode>&lt;head&gt;\u003C\u002Fcode> work fine for one-off pages. For any real site, link an external stylesheet with \u003Ccode>&lt;link rel=\"stylesheet\" href=\"styles.css\"&gt;\u003C\u002Fcode>. Style the \u003Ccode>form\u003C\u002Fcode>, \u003Ccode>label\u003C\u002Fcode>, \u003Ccode>input\u003C\u002Fcode>, \u003Ccode>textarea\u003C\u002Fcode>, and \u003Ccode>button\u003C\u002Fcode> selectors directly. Step 3 above ships a complete starter stylesheet you can paste, including focus rings and inline error styles.\u003C\u002Fdiv>\n\u003C\u002Fdetails>\n\n\u003Cdetails class=\"fmstr-cmp-ffh-faq__item\">\n\u003Csummary>How do I add JavaScript validation without breaking accessibility?\u003C\u002Fsummary>\n\u003Cdiv class=\"fmstr-cmp-ffh-faq__answer\">Use \u003Ccode>aria-invalid=\"true\"\u003C\u002Fcode> on invalid fields, \u003Ccode>aria-describedby\u003C\u002Fcode> to point at the inline error message, and move focus to the first invalid field on submit failure. Avoid \u003Ccode>alert()\u003C\u002Fcode> boxes, they break screen-reader flow. The Step 4 JavaScript and the complete example above are accessibility-tested versions you can paste directly. Always re-validate on the server too, since a user with DevTools open can bypass client-side checks.\u003C\u002Fdiv>\n\u003C\u002Fdetails>\n\n\u003C\u002Fdiv>\n\u003C\u002Fdiv>\n\u003C\u002Fsection>\n\n\u003Cstyle>\n\u002F* host-link-override *\u002F\n.fmstr-cmp-ffh-vid a { text-decoration: none !important; }\n.fmstr-cmp-ffh-vid {\n--c-bg-card: #ffffff;\n--c-fg-1: #101828; --c-fg-2: #475467; --c-fg-3: #697586;\n--c-violet-500: #7f56d9; --c-violet-600: #6941c6;\n--c-tint: #f7f3ff; --c-edge: #e4d7ff; --c-border: #eaecf0;\n--c-shadow: 0 4px 20px rgba(16,24,40,.06), 0 2px 6px rgba(16,24,40,.04);\n\nbackground: transparent; padding: 56px 24px;\nfont-family: inherit;\ncolor: var(--c-fg-1);\n}\n.fmstr-cmp-ffh-vid *, .fmstr-cmp-ffh-vid *::before, .fmstr-cmp-ffh-vid *::after { box-sizing: border-box; }\n.fmstr-cmp-ffh-vid__container { max-width: 820px; margin: 0 auto; }\n.fmstr-cmp-ffh-vid__head { margin: 0 0 24px; }\n.fmstr-cmp-ffh-vid__eyebrow {\ndisplay: inline-block; padding: 5px 12px; border-radius: 9999px;\nbackground: var(--c-tint); color: var(--c-violet-600);\nfont-size: 12px; font-weight: 600; letter-spacing: .04em;\ntext-transform: uppercase; border: 1px solid var(--c-edge); margin: 0 0 14px;\n}\n.fmstr-cmp-ffh-vid__h2 { font-size: clamp(24px, 2.8vw, 32px); font-weight: 700; line-height: 1.15; letter-spacing: -.02em; margin: 0; color: var(--c-fg-1); }\n.fmstr-cmp-ffh-vid__sub { color: var(--c-fg-3); font-size: 16px; line-height: 1.6; margin: 12px 0 0; }\n.fmstr-cmp-ffh-vid__frame {\nposition: relative; aspect-ratio: 16 \u002F 9; border-radius: 20px; overflow: hidden;\nbackground: var(--c-tint); border: 1px solid var(--c-border); box-shadow: var(--c-shadow);\n}\n.fmstr-cmp-ffh-vid__frame iframe { position: absolute; inset: 0; width: 100%; height: 100%; border: 0; }\n.fmstr-cmp-ffh-vid__caption { color: var(--c-fg-3); font-size: 14px; line-height: 1.6; text-align: center; margin: 16px 0 0; }\n.fmstr-cmp-ffh-vid__caption a { color: var(--c-violet-600) !important; text-decoration: none !important; }\n.fmstr-cmp-ffh-vid__caption a:hover { text-decoration: underline !important; }\n.fmstr-cmp-ffh-vid__caption code {\nbackground: var(--c-tint); padding: 1px 6px; border-radius: 4px;\nfont-family: ui-monospace, Menlo, Monaco, monospace; font-size: 13px;\ncolor: var(--c-violet-600);\n}\n\n@media (max-width: 760px) {\n.fmstr-cmp-ffh-vid { padding: 40px 16px; }\n.fmstr-cmp-ffh-vid__sub { font-size: 15px; }\n.fmstr-cmp-ffh-vid__frame { border-radius: 16px; }\n.fmstr-cmp-ffh-vid__caption { font-size: 13.5px; }\n}\n\u003C\u002Fstyle>\n\n\u003Csection class=\"fmstr-cmp-ffh-vid\" aria-labelledby=\"fmstr-cmp-ffh-vid-h2\">\n\u003Cdiv class=\"fmstr-cmp-ffh-vid__container\">\n\u003Cdiv class=\"fmstr-cmp-ffh-vid__head\">\n\u003Cspan class=\"fmstr-cmp-ffh-vid__eyebrow\">Three-minute walkthrough\u003C\u002Fspan>\n\u003Ch2 class=\"fmstr-cmp-ffh-vid__h2\" id=\"fmstr-cmp-ffh-vid-h2\">Watch the full HTML feedback form built from scratch\u003C\u002Fh2>\n\u003Cp class=\"fmstr-cmp-ffh-vid__sub\">Structure, CSS, accessible validation, backend swap. All six steps in one short video.\u003C\u002Fp>\n\u003C\u002Fdiv>\n\u003Cdiv class=\"fmstr-cmp-ffh-vid__frame\">\n\u003Ciframe src=\"https:\u002F\u002Fwww.youtube.com\u002Fembed\u002F8FC3c5Cv5ew\" title=\"How to make a feedback form in HTML\" loading=\"lazy\" allow=\"accelerometer; autoplay; clipboard-write; encrypted-media; gyroscope; picture-in-picture; web-share\" referrerpolicy=\"strict-origin-when-cross-origin\" allowfullscreen>\u003C\u002Fiframe>\n\u003C\u002Fdiv>\n\u003Cp class=\"fmstr-cmp-ffh-vid__caption\">Prefer reading? The full tutorial is below with copy-paste blocks. To skip the backend setup entirely, point the form&rsquo;s \u003Ccode>action\u003C\u002Fcode> at \u003Ca href=\"https:\u002F\u002Fformester.com\u002Ffeatures\u002Fhtml-form-backend\u002F\">Formester&rsquo;s HTML form backend\u003C\u002Fa>.\u003C\u002Fp>\n\u003C\u002Fdiv>\n\u003C\u002Fsection>\n\n\u003Cstyle>\n\u002F* host-link-override *\u002F\n.fmstr-cmp-ffh-rel a { text-decoration: none !important; }\n.fmstr-cmp-ffh-rel {\n--c-bg: #f4f4f7; --c-card: #ffffff;\n--c-fg-1: #101828; --c-fg-2: #475467; --c-fg-3: #697586;\n--c-violet-500: #7f56d9; --c-violet-600: #6941c6;\n--c-tint: #f7f3ff; --c-edge: #e4d7ff; --c-border: #eaecf0;\n--c-shadow: 0 4px 20px rgba(16,24,40,.06);\n\nbackground: transparent; padding: 56px 24px;\nfont-family: inherit;\ncolor: var(--c-fg-1);\n}\n.fmstr-cmp-ffh-rel *, .fmstr-cmp-ffh-rel *::before, .fmstr-cmp-ffh-rel *::after { box-sizing: border-box; }\n.fmstr-cmp-ffh-rel__container { max-width: 820px; margin: 0 auto; }\n.fmstr-cmp-ffh-rel__head { margin: 0 0 28px; }\n.fmstr-cmp-ffh-rel__h2 { font-size: clamp(26px, 3vw, 36px); font-weight: 700; line-height: 1.15; letter-spacing: -.02em; margin: 0; }\n.fmstr-cmp-ffh-rel__intro { color: var(--c-fg-3); font-size: 17px; line-height: 1.6; margin: 14px 0 0; }\n.fmstr-cmp-ffh-rel__grid { display: grid; grid-template-columns: repeat(3, 1fr); gap: 16px; }\n.fmstr-cmp-ffh-rel__card {\nbackground: var(--c-card); border: 1px solid var(--c-border);\nborder-radius: 14px; padding: 18px 20px; display: flex; align-items: center; gap: 14px;\ntext-decoration: none !important; color: inherit !important; transition: all .15s ease;\n}\n.fmstr-cmp-ffh-rel__card:hover { border-color: var(--c-edge); box-shadow: var(--c-shadow); transform: translateY(-1px); }\n.fmstr-cmp-ffh-rel__icon { width: 40px; height: 40px; border-radius: 10px; background: var(--c-tint); display: grid; place-items: center; flex-shrink: 0; font-size: 18px; border: 1px solid var(--c-edge); }\n.fmstr-cmp-ffh-rel__text { flex-grow: 1; }\n.fmstr-cmp-ffh-rel__text h4 { font-size: 14.5px; font-weight: 600; color: var(--c-fg-1); margin: 0; }\n.fmstr-cmp-ffh-rel__text small { font-size: 12.5px; color: var(--c-fg-3); display: block; margin-top: 2px; }\n.fmstr-cmp-ffh-rel__arrow { color: var(--c-violet-500); font-size: 18px; }\n\n@media (max-width: 880px) { .fmstr-cmp-ffh-rel__grid { grid-template-columns: 1fr 1fr; gap: 12px; } }\n@media (max-width: 760px) {\n.fmstr-cmp-ffh-rel { padding: 40px 16px; }\n.fmstr-cmp-ffh-rel__intro { font-size: 15.5px; }\n.fmstr-cmp-ffh-rel__card { padding: 16px; gap: 12px; }\n}\n@media (max-width: 540px) { .fmstr-cmp-ffh-rel__grid { grid-template-columns: 1fr; gap: 12px; } }\n\u003C\u002Fstyle>\n\n\u003Csection class=\"fmstr-cmp-ffh-rel\" aria-labelledby=\"fmstr-cmp-ffh-rel-h2\">\n\u003Cdiv class=\"fmstr-cmp-ffh-rel__container\">\n\u003Cdiv class=\"fmstr-cmp-ffh-rel__head\">\n\u003Ch2 class=\"fmstr-cmp-ffh-rel__h2\" id=\"fmstr-cmp-ffh-rel-h2\">More from Formester on HTML forms and feedback\u003C\u002Fh2>\n\u003Cp class=\"fmstr-cmp-ffh-rel__intro\">Pair this tutorial with the backend features, ready-made templates, and adjacent how-tos.\u003C\u002Fp>\n\u003C\u002Fdiv>\n\u003Cdiv class=\"fmstr-cmp-ffh-rel__grid\">\n\n\u003Ca class=\"fmstr-cmp-ffh-rel__card\" href=\"https:\u002F\u002Fformester.com\u002Ffeatures\u002Fhtml-form-backend\u002F\">\n\u003Cdiv class=\"fmstr-cmp-ffh-rel__icon\" aria-hidden=\"true\">&#128229;\u003C\u002Fdiv>\n\u003Cdiv class=\"fmstr-cmp-ffh-rel__text\">\u003Ch4>HTML Form Backend\u003C\u002Fh4>\u003Csmall>One \u003Ccode>action\u003C\u002Fcode> swap, no server\u003C\u002Fsmall>\u003C\u002Fdiv>\n\u003Cspan class=\"fmstr-cmp-ffh-rel__arrow\" aria-hidden=\"true\">&rarr;\u003C\u002Fspan>\n\u003C\u002Fa>\n\n\u003Ca class=\"fmstr-cmp-ffh-rel__card\" href=\"https:\u002F\u002Fformester.com\u002Ffeatures\u002Fembed-forms\u002F\">\n\u003Cdiv class=\"fmstr-cmp-ffh-rel__icon\" aria-hidden=\"true\">&#128279;\u003C\u002Fdiv>\n\u003Cdiv class=\"fmstr-cmp-ffh-rel__text\">\u003Ch4>Embed Forms\u003C\u002Fh4>\u003Csmall>Drop a form into any HTML page\u003C\u002Fsmall>\u003C\u002Fdiv>\n\u003Cspan class=\"fmstr-cmp-ffh-rel__arrow\" aria-hidden=\"true\">&rarr;\u003C\u002Fspan>\n\u003C\u002Fa>\n\n\u003Ca class=\"fmstr-cmp-ffh-rel__card\" href=\"https:\u002F\u002Fformester.com\u002Ffeatures\u002Fspam-protection\u002F\">\n\u003Cdiv class=\"fmstr-cmp-ffh-rel__icon\" aria-hidden=\"true\">&#128737;\u003C\u002Fdiv>\n\u003Cdiv class=\"fmstr-cmp-ffh-rel__text\">\u003Ch4>Spam Protection\u003C\u002Fh4>\u003Csmall>Honeypot + reCAPTCHA built in\u003C\u002Fsmall>\u003C\u002Fdiv>\n\u003Cspan class=\"fmstr-cmp-ffh-rel__arrow\" aria-hidden=\"true\">&rarr;\u003C\u002Fspan>\n\u003C\u002Fa>\n\n\u003Ca class=\"fmstr-cmp-ffh-rel__card\" href=\"https:\u002F\u002Fformester.com\u002Ftemplates\u002Fcustomer-feedback-form-31840\u002F\">\n\u003Cdiv class=\"fmstr-cmp-ffh-rel__icon\" aria-hidden=\"true\">&#11088;\u003C\u002Fdiv>\n\u003Cdiv class=\"fmstr-cmp-ffh-rel__text\">\u003Ch4>Customer Feedback Form\u003C\u002Fh4>\u003Csmall>Pre-built template\u003C\u002Fsmall>\u003C\u002Fdiv>\n\u003Cspan class=\"fmstr-cmp-ffh-rel__arrow\" aria-hidden=\"true\">&rarr;\u003C\u002Fspan>\n\u003C\u002Fa>\n\n\u003Ca class=\"fmstr-cmp-ffh-rel__card\" href=\"https:\u002F\u002Fformester.com\u002Ftemplates\u002Fcategories\u002Ffeedback-forms\u002F\">\n\u003Cdiv class=\"fmstr-cmp-ffh-rel__icon\" aria-hidden=\"true\">&#128196;\u003C\u002Fdiv>\n\u003Cdiv class=\"fmstr-cmp-ffh-rel__text\">\u003Ch4>All Feedback Templates\u003C\u002Fh4>\u003Csmall>Customer, product, employee\u003C\u002Fsmall>\u003C\u002Fdiv>\n\u003Cspan class=\"fmstr-cmp-ffh-rel__arrow\" aria-hidden=\"true\">&rarr;\u003C\u002Fspan>\n\u003C\u002Fa>\n\n\u003Ca class=\"fmstr-cmp-ffh-rel__card\" href=\"https:\u002F\u002Fformester.com\u002Fai-form-generator\u002F\">\n\u003Cdiv class=\"fmstr-cmp-ffh-rel__icon\" aria-hidden=\"true\">&#10024;\u003C\u002Fdiv>\n\u003Cdiv class=\"fmstr-cmp-ffh-rel__text\">\u003Ch4>AI Form Generator\u003C\u002Fh4>\u003Csmall>The no-code alternative\u003C\u002Fsmall>\u003C\u002Fdiv>\n\u003Cspan class=\"fmstr-cmp-ffh-rel__arrow\" aria-hidden=\"true\">&rarr;\u003C\u002Fspan>\n\u003C\u002Fa>\n\n\u003Ca class=\"fmstr-cmp-ffh-rel__card\" href=\"https:\u002F\u002Fformester.com\u002Fblog\u002Fhow-to-send-contact-form-data-to-google-sheets-free\u002F\">\n\u003Cdiv class=\"fmstr-cmp-ffh-rel__icon\" aria-hidden=\"true\">&#128203;\u003C\u002Fdiv>\n\u003Cdiv class=\"fmstr-cmp-ffh-rel__text\">\u003Ch4>Send form data to Google Sheets\u003C\u002Fh4>\u003Csmall>Free, step-by-step\u003C\u002Fsmall>\u003C\u002Fdiv>\n\u003Cspan class=\"fmstr-cmp-ffh-rel__arrow\" aria-hidden=\"true\">&rarr;\u003C\u002Fspan>\n\u003C\u002Fa>\n\n\u003Ca class=\"fmstr-cmp-ffh-rel__card\" href=\"https:\u002F\u002Fformester.com\u002Fblog\u002Fcontact-form-design-tips-best-practices-and-examples\u002F\">\n\u003Cdiv class=\"fmstr-cmp-ffh-rel__icon\" aria-hidden=\"true\">&#127912;\u003C\u002Fdiv>\n\u003Cdiv class=\"fmstr-cmp-ffh-rel__text\">\u003Ch4>Contact form design tips\u003C\u002Fh4>\u003Csmall>Best practices and examples\u003C\u002Fsmall>\u003C\u002Fdiv>\n\u003Cspan class=\"fmstr-cmp-ffh-rel__arrow\" aria-hidden=\"true\">&rarr;\u003C\u002Fspan>\n\u003C\u002Fa>\n\n\u003Ca class=\"fmstr-cmp-ffh-rel__card\" href=\"https:\u002F\u002Fformester.com\u002Fblog\u002Fhow-to-build-spam-free-contact-forms-for-your-website\u002F\">\n\u003Cdiv class=\"fmstr-cmp-ffh-rel__icon\" aria-hidden=\"true\">&#129302;\u003C\u002Fdiv>\n\u003Cdiv class=\"fmstr-cmp-ffh-rel__text\">\u003Ch4>Build spam-free contact forms\u003C\u002Fh4>\u003Csmall>Stop bots before they hit your inbox\u003C\u002Fsmall>\u003C\u002Fdiv>\n\u003Cspan class=\"fmstr-cmp-ffh-rel__arrow\" aria-hidden=\"true\">&rarr;\u003C\u002Fspan>\n\u003C\u002Fa>\n\n\u003C\u002Fdiv>\n\u003C\u002Fdiv>\n\u003C\u002Fsection>\n","blog\u002Fblog\u002Fhow-to-make-feedback-form-in-html.md",{"text":69},"16 min read",{"title":71,"author":7,"authorImage":8,"authorProfile":9,"coverImg":72,"coverImgAlt":73,"createdAt":74,"description":75,"featured":14,"jsonld":76,"keywords":77,"metaDescription":78,"metaImage":79,"metaTitle":80,"publishedAt":81,"slug":82,"updatedAt":83,"__hash__":84,"body":85,"id":86,"coverImgWidth":87,"coverImgHeight":88,"readingStats":89},"8 Best Questionnaire Software in 2026: Compared","https:\u002F\u002Fformester-strapi.s3.ap-south-1.amazonaws.com\u002Fbest_questionnaire_software_d54438ac13.png","8 best questionnaire software compared for 2026","2026-07-09T14:52:44.671Z","8 top questionnaire tools ranked for HR, research, feedback, and intake. Formester, SurveyMonkey, Typeform, Jotform, Google Forms, Microsoft Forms, Fillout, Zoho Forms. Analytics + pricing compared.",[],"best questionnaire software, questionnaire builder, online questionnaire tool, questionnaire maker, questionnaire software 2026","The 8 best questionnaire tools in 2026 for HR, research, feedback, and intake. Pricing, templates, integrations, and which one fits your team.",[],"8 Best Questionnaire Software in 2026 | Formester","2026-08-20T05:14:54.996Z","best-questionnaire-software","2026-08-20T05:14:55.000Z","Q_WI6bpDIcH7WAl02Vb9uOcPNKjz0HuNct8kj_tseF4","![8 best questionnaire software compared for 2026](https:\u002F\u002Fformester-strapi.s3.ap-south-1.amazonaws.com\u002Fbest_questionnaire_software_d54438ac13.png)\n\n\u003Cdiv style=\"background:#F9FAFB;border-left:4px solid #7f56d9;padding:14px 18px;margin:0 0 24px 0;border-radius:6px;font-family:inherit;\">\n\u003Cp style=\"margin:0;font-size:14px;color:#475467;font-family:inherit;\">\u003Cstrong>How we verified this:\u003C\u002Fstrong> every figure on this page comes from the vendor's own pricing page or its public G2 profile. \u003Ca href=\"https:\u002F\u002Fdocs.google.com\u002Fdocument\u002Fd\u002F1rHjEeP9DZx43APmXrsMgXQaF_y5f6LFyr7wijvCYT9Y\u002Fedit?usp=sharing\" target=\"_blank\" rel=\"noopener\">You can check every source here\u003C\u002Fa>.\u003C\u002Fp>\n\u003C\u002Fdiv>\n\n\u003Ch2>Which questionnaire software should you choose?\u003C\u002Fh2>\n\n\u003Cp>A questionnaire is usually longer than a form and more structured than a survey. That length is what breaks tools: people abandon halfway. The logic gets tangled, and the response cap turns up sooner than planned.\u003C\u002Fp>\n\n\u003Cp>The eight tools below all handle question types and branching. Where they differ is what happens as the questionnaire grows: how many responses you can take and how the logic is built, plus what the whole thing costs once your team needs seats.\u003C\u002Fp>\n\n\u003Cdiv class=\"tldr\">\n\u003Cp>\u003Cstrong>The 60-second TL;DR\u003C\u002Fstrong>\u003C\u002Fp>\n\u003Cul>\n\u003Cli>\u003Cstrong>Best all-around:\u003C\u002Fstrong> Formester, unlimited responses on the free plan\u003C\u002Fli>\n\u003Cli>\u003Cstrong>Best for research rigour:\u003C\u002Fstrong> SurveyMonkey, from $30\u002Fuser\u002Fmo\u003C\u002Fli>\n\u003Cli>\u003Cstrong>Best for completion rates:\u003C\u002Fstrong> Typeform, from $39\u002Fmo\u003C\u002Fli>\n\u003Cli>\u003Cstrong>Best for question depth:\u003C\u002Fstrong> Jotform, 20,000+ templates, from $39\u002Fmo\u003C\u002Fli>\n\u003Cli>\u003Cstrong>Best free option:\u003C\u002Fstrong> Google Forms, free with any Google account\u003C\u002Fli>\n\u003Cli>\u003Cstrong>Best for Microsoft 365 teams:\u003C\u002Fstrong> Microsoft Forms, bundled with the suite\u003C\u002Fli>\n\u003Cli>\u003Cstrong>Best for Airtable and Notion teams:\u003C\u002Fstrong> Fillout, from $19\u002Fmo\u003C\u002Fli>\n\u003Cli>\u003Cstrong>Best for Zoho users:\u003C\u002Fstrong> Zoho Forms, from $10\u002Fmo billed annually\u003C\u002Fli>\n\u003C\u002Ful>\n\u003C\u002Fdiv>\n\n\u003Ch2>How the eight questionnaire tools compare at a glance\u003C\u002Fh2>\n\n\u003Cp>Here is the whole comparison in one place: what each free plan covers, where paid pricing starts on monthly billing, and what each tool is built for. Scan it, then read the review that matches your situation.\u003C\u002Fp>\n\n\u003Cdiv class=\"table-wrap\">\n\u003Ctable>\n\u003Cthead>\u003Ctr>\u003Cth>Tool\u003C\u002Fth>\u003Cth>Free plan\u003C\u002Fth>\u003Cth>Paid from (monthly)\u003C\u002Fth>\u003Cth>Built for\u003C\u002Fth>\u003Cth>G2 rating\u003C\u002Fth>\u003C\u002Ftr>\u003C\u002Fthead>\n\u003Ctbody>\n\u003Ctr>\u003Ctd>Formester\u003C\u002Ftd>\u003Ctd>Unlimited forms and responses\u003C\u002Ftd>\u003Ctd>$13\u002Fmo\u003C\u002Ftd>\u003Ctd>Long questionnaires without caps\u003C\u002Ftd>\u003Ctd>4.7\u002F5 (14 reviews)\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>SurveyMonkey\u003C\u002Ftd>\u003Ctd>Limited free tier\u003C\u002Ftd>\u003Ctd>$30\u002Fuser\u002Fmo\u003C\u002Ftd>\u003Ctd>Formal research\u003C\u002Ftd>\u003Ctd>4.4\u002F5 (23,901 reviews)\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Typeform\u003C\u002Ftd>\u003Ctd>10 responses\u002Fmo\u003C\u002Ftd>\u003Ctd>$39\u002Fmo\u003C\u002Ftd>\u003Ctd>Completion on long forms\u003C\u002Ftd>\u003Ctd>4.5\u002F5 (1,017 reviews)\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Jotform\u003C\u002Ftd>\u003Ctd>5 forms, 100 submissions\u002Fmo\u003C\u002Ftd>\u003Ctd>$39\u002Fmo\u003C\u002Ftd>\u003Ctd>Question type depth\u003C\u002Ftd>\u003Ctd>4.7\u002F5 (5,426 reviews)\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Google Forms\u003C\u002Ftd>\u003Ctd>Free with a Google account\u003C\u002Ftd>\u003Ctd>Bundled with Workspace\u003C\u002Ftd>\u003Ctd>Simple internal questionnaires\u003C\u002Ftd>\u003Ctd>No standalone profile\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Microsoft Forms\u003C\u002Ftd>\u003Ctd>200 responses\u002Fform\u003C\u002Ftd>\u003Ctd>Bundled with M365\u003C\u002Ftd>\u003Ctd>Microsoft organisations\u003C\u002Ftd>\u003Ctd>4.4\u002F5 (476 reviews)\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Fillout\u003C\u002Ftd>\u003Ctd>1,000 responses\u002Fmo\u003C\u002Ftd>\u003Ctd>$19\u002Fmo\u003C\u002Ftd>\u003Ctd>Airtable and Notion workflows\u003C\u002Ftd>\u003Ctd>4.6\u002F5 (30 reviews)\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Zoho Forms\u003C\u002Ftd>\u003Ctd>3 forms, 500 submissions\u002Fmo\u003C\u002Ftd>\u003Ctd>$10\u002Fmo\u003C\u002Ftd>\u003Ctd>Zoho ecosystem\u003C\u002Ftd>\u003Ctd>4.4\u002F5 (129 reviews)\u003C\u002Ftd>\u003C\u002Ftr>\n\u003C\u002Ftbody>\n\u003C\u002Ftable>\n\u003C\u002Fdiv>\n\n\u003Ch2>How we picked and ranked these eight tools\u003C\u002Fh2>\n\n\u003Cp>Everything here comes from the vendors' own pricing pages and plan limits, read in full. For questionnaires the response cap and the logic depth decide more than the editor does.\u003C\u002Fp>\n\n\u003Cp>The ranking weighs what each free plan allows and what a full team pays, plus how well the tool holds up as questions multiply. Several vendors advertise annual rates, so the monthly figures here run higher than the ones on their pricing pages.\u003C\u002Fp>\n\n\u003Ch2>1. Formester, best all-around\u003C\u002Fh2>\n\n\u003Cp>\u003Cimg src=\"https:\u002F\u002Fformester-strapi.s3.ap-south-1.amazonaws.com\u002Fformester_99e2a99609.png\" alt=\"Formester homepage hero screenshot\" style=\"width:100%;max-width:900px;height:auto;border-radius:8px;border:1px solid #e5e7eb;margin:16px 0;\" loading=\"lazy\" \u002F>\u003C\u002Fp>\n\n\u003Cp>Formester never counts responses, which matters more for questionnaires than for short forms. A study that runs longer than planned does not turn into an upgrade prompt.\u003C\u002Fp>\n\n\u003Cp>Question types cover the usual range, conditional logic arrives on the Personal plan, and quiz auto-scoring is included, which suits assessments and knowledge checks.\u003C\u002Fp>\n\n\u003Cp>Pricing stays flat as volume grows. Personal is $13 a month, Business is $49 with 25 seats and a custom domain, and neither adds a response allowance because there is not one.\u003C\u002Fp>\n\n\u003Cdiv class=\"table-wrap\">\n\u003Ctable>\n\u003Cthead>\u003Ctr>\u003Cth>Strengths\u003C\u002Fth>\u003Cth>Weaknesses\u003C\u002Fth>\u003C\u002Ftr>\u003C\u002Fthead>\n\u003Ctbody>\n\u003Ctr>\u003Ctd>Unlimited responses on every plan including free\u003C\u002Ftd>\u003Ctd>Conditional logic starts on the paid Personal plan\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Quiz auto-scoring included\u003C\u002Ftd>\u003Ctd>720 templates against Jotform's 20,000\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Drop-off analytics show where people abandon\u003C\u002Ftd>\u003Ctd>14 G2 reviews, a small sample\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Offline capture for field questionnaires\u003C\u002Ftd>\u003Ctd>No HIPAA on any tier\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>AI generation from a prompt or a PDF\u003C\u002Ftd>\u003Ctd>\u003C\u002Ftd>\u003C\u002Ftr>\n\u003C\u002Ftbody>\n\u003C\u002Ftable>\n\u003C\u002Fdiv>\n\n\u003Cdiv class=\"table-wrap\">\n\u003Ctable>\n\u003Cthead>\u003Ctr>\u003Cth>Plan\u003C\u002Fth>\u003Cth>What you get\u003C\u002Fth>\u003C\u002Ftr>\u003C\u002Fthead>\n\u003Ctbody>\n\u003Ctr>\u003Ctd>Free\u003C\u002Ftd>\u003Ctd>$0. Unlimited forms and responses, auto-scoring, drop-off analytics\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Personal\u003C\u002Ftd>\u003Ctd>$13\u002Fmo ($12\u002Fmo billed yearly). Adds conditional logic\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Business\u003C\u002Ftd>\u003Ctd>$49\u002Fmo ($45\u002Fmo billed yearly). Adds custom domain and 25 seats\u003C\u002Ftd>\u003C\u002Ftr>\n\u003C\u002Ftbody>\n\u003C\u002Ftable>\n\u003C\u002Fdiv>\n\n\u003Cp>\u003Cstrong>Best for:\u003C\u002Fstrong> long questionnaires where the response count is unpredictable.\u003C\u002Fp>\n\n\u003Cp>\u003Cstrong>The catch:\u003C\u002Fstrong> branching logic needs the Personal plan, so the free tier suits linear questionnaires better than adaptive ones.\u003C\u002Fp>\n\n\u003Cp>\u003Cstrong>G2 rating:\u003C\u002Fstrong> 4.7\u002F5, from 14 reviews. High score, small sample; read it as an early signal.\u003C\u002Fp>\n\n\u003Ch2>2. SurveyMonkey, best for research rigour\u003C\u002Fh2>\n\n\u003Cp>\u003Cimg src=\"https:\u002F\u002Fformester-strapi.s3.ap-south-1.amazonaws.com\u002Fsurveymonkey_3a2712fdfc.png\" alt=\"SurveyMonkey homepage hero screenshot\" style=\"width:100%;max-width:900px;height:auto;border-radius:8px;border:1px solid #e5e7eb;margin:16px 0;\" loading=\"lazy\" \u002F>\u003C\u002Fp>\n\n\u003Cp>SurveyMonkey is built for people whose questionnaires need to stand up to scrutiny. Its templates are reviewed by methodologists for question bias, and its benchmarking compares your results against industry data.\u003C\u002Fp>\n\n\u003Cp>For academic work, employee engagement studies, and market research, that structure is the product. Nothing else here brings the same statistical apparatus.\u003C\u002Fp>\n\n\u003Cp>Published pricing now covers team plans only: Team Advantage at $30 per user a month and Team Premier at $92, both with a three-seat minimum. Responses over your limit cost $0.15 each.\u003C\u002Fp>\n\n\u003Cdiv class=\"table-wrap\">\n\u003Ctable>\n\u003Cthead>\u003Ctr>\u003Cth>Strengths\u003C\u002Fth>\u003Cth>Weaknesses\u003C\u002Fth>\u003C\u002Ftr>\u003C\u002Fthead>\n\u003Ctbody>\n\u003Ctr>\u003Ctd>Methodologist-reviewed question bank\u003C\u002Ftd>\u003Ctd>Three-seat minimum makes the real entry price $90\u002Fmo\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Benchmarking against industry data\u003C\u002Ftd>\u003Ctd>$0.15 per response over the limit\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Advanced statistical analysis\u003C\u002Ftd>\u003Ctd>Individual plans are no longer published\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Recognised by academic and corporate reviewers\u003C\u002Ftd>\u003Ctd>Interface is dated in places\u003C\u002Ftd>\u003C\u002Ftr>\n\u003C\u002Ftbody>\n\u003C\u002Ftable>\n\u003C\u002Fdiv>\n\n\u003Cdiv class=\"table-wrap\">\n\u003Ctable>\n\u003Cthead>\u003Ctr>\u003Cth>Plan\u003C\u002Fth>\u003Cth>What you get\u003C\u002Fth>\u003C\u002Ftr>\u003C\u002Fthead>\n\u003Ctbody>\n\u003Ctr>\u003Ctd>Free\u003C\u002Ftd>\u003Ctd>Limited free tier with capped questions and responses\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Team Advantage\u003C\u002Ftd>\u003Ctd>$30\u002Fuser\u002Fmo, three-seat minimum\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Team Premier\u003C\u002Ftd>\u003Ctd>$92\u002Fuser\u002Fmo, three-seat minimum\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Enterprise\u003C\u002Ftd>\u003Ctd>Custom pricing\u003C\u002Ftd>\u003C\u002Ftr>\n\u003C\u002Ftbody>\n\u003C\u002Ftable>\n\u003C\u002Fdiv>\n\n\u003Cp>\u003Cstrong>Best for:\u003C\u002Fstrong> formal research where methodology has to be defensible.\u003C\u002Fp>\n\n\u003Cp>\u003Cstrong>The catch:\u003C\u002Fstrong> the three-seat minimum means the cheapest team plan is $90 a month, not $30.\u003C\u002Fp>\n\n\u003Cp>\u003Cstrong>G2 rating:\u003C\u002Fstrong> 4.4\u002F5, from 23,901 reviews. A very large base; the score reflects familiarity more than enthusiasm.\u003C\u002Fp>\n\n\u003Ch2>3. Typeform, best for completion rates\u003C\u002Fh2>\n\n\u003Cp>\u003Cimg src=\"https:\u002F\u002Fformester-strapi.s3.ap-south-1.amazonaws.com\u002Ftypeform_7aad7a2e5b.png\" alt=\"Typeform homepage hero screenshot\" style=\"width:100%;max-width:900px;height:auto;border-radius:8px;border:1px solid #e5e7eb;margin:16px 0;\" loading=\"lazy\" \u002F>\u003C\u002Fp>\n\n\u003Cp>Typeform shows one question at a time, which is exactly the format long questionnaires need. People who would abandon a page of thirty fields will often finish the same thirty questions delivered one by one.\u003C\u002Fp>\n\n\u003Cp>The trade is cost per response. Free covers 10 responses a month, Basic $39 covers 100, Plus $79 covers 1,000, and Business $129 covers 10,000.\u003C\u002Fp>\n\n\u003Cp>For a questionnaire sent to a few hundred people whose answers genuinely matter, that maths works. For a public questionnaire at scale, it does not.\u003C\u002Fp>\n\n\u003Cdiv class=\"table-wrap\">\n\u003Ctable>\n\u003Cthead>\u003Ctr>\u003Cth>Strengths\u003C\u002Fth>\u003Cth>Weaknesses\u003C\u002Fth>\u003C\u002Ftr>\u003C\u002Fthead>\n\u003Ctbody>\n\u003Ctr>\u003Ctd>Highest completion rates on long questionnaires\u003C\u002Ftd>\u003Ctd>Free plan covers only 10 responses a month\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Logic jumps between questions are simple to build\u003C\u002Ftd>\u003Ctd>Highest cost per response in this list\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Strong drop-off analytics\u003C\u002Ftd>\u003Ctd>Advertised prices are the annual rates\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>AI drafts a full questionnaire from a prompt\u003C\u002Ftd>\u003Ctd>Response caps apply on every tier\u003C\u002Ftd>\u003C\u002Ftr>\n\u003C\u002Ftbody>\n\u003C\u002Ftable>\n\u003C\u002Fdiv>\n\n\u003Cdiv class=\"table-wrap\">\n\u003Ctable>\n\u003Cthead>\u003Ctr>\u003Cth>Plan\u003C\u002Fth>\u003Cth>What you get\u003C\u002Fth>\u003C\u002Ftr>\u003C\u002Fthead>\n\u003Ctbody>\n\u003Ctr>\u003Ctd>Free\u003C\u002Ftd>\u003Ctd>$0. 10 responses\u002Fmo\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Basic\u003C\u002Ftd>\u003Ctd>$39\u002Fmo ($28\u002Fmo billed yearly). 100 responses\u002Fmo\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Plus\u003C\u002Ftd>\u003Ctd>$79\u002Fmo ($56\u002Fmo billed yearly). 1,000 responses\u002Fmo, 3 seats\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Business\u003C\u002Ftd>\u003Ctd>$129\u002Fmo ($91\u002Fmo billed yearly). 10,000 responses\u002Fmo, 5 seats\u003C\u002Ftd>\u003C\u002Ftr>\n\u003C\u002Ftbody>\n\u003C\u002Ftable>\n\u003C\u002Fdiv>\n\n\u003Cp>\u003Cstrong>Best for:\u003C\u002Fstrong> qualitative questionnaires where each completed response carries real value.\u003C\u002Fp>\n\n\u003Cp>\u003Cstrong>The catch:\u003C\u002Fstrong> price rises with volume faster than any other tool here, so model your expected response count before you commit.\u003C\u002Fp>\n\n\u003Cp>\u003Cstrong>G2 rating:\u003C\u002Fstrong> 4.5\u002F5, from 1,017 reviews. A large base, with cost the most common complaint.\u003C\u002Fp>\n\n\u003Ch2>4. Jotform, best for question depth\u003C\u002Fh2>\n\n\u003Cp>\u003Cimg src=\"https:\u002F\u002Fformester-strapi.s3.ap-south-1.amazonaws.com\u002Fjotform_52dafaf96f.png\" alt=\"Jotform homepage hero screenshot\" style=\"width:100%;max-width:900px;height:auto;border-radius:8px;border:1px solid #e5e7eb;margin:16px 0;\" loading=\"lazy\" \u002F>\u003C\u002Fp>\n\n\u003Cp>Jotform has the widest field inventory in this comparison, which matters when a questionnaire needs matrix questions, calculations, file uploads and signatures in the same flow.\u003C\u002Fp>\n\n\u003Cp>The 20,000+ template library also means most standard questionnaires already exist in some form, from patient intake to employee onboarding.\u003C\u002Fp>\n\n\u003Cp>Monthly billing runs $39 for Bronze, $49 for Silver, and $129 for Gold, above the advertised annual rates of $34, $39, and $99.\u003C\u002Fp>\n\n\u003Cdiv class=\"table-wrap\">\n\u003Ctable>\n\u003Cthead>\u003Ctr>\u003Cth>Strengths\u003C\u002Fth>\u003Cth>Weaknesses\u003C\u002Fth>\u003C\u002Ftr>\u003C\u002Fthead>\n\u003Ctbody>\n\u003Ctr>\u003Ctd>20,000+ templates covering standard questionnaires\u003C\u002Ftd>\u003Ctd>Submissions metered on every tier\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Widest range of question and field types\u003C\u002Ftd>\u003Ctd>Free plan covers 100 submissions a month\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Conditional logic and calculations on paid tiers\u003C\u002Ftd>\u003Ctd>Dense interface takes time to learn\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>HIPAA features from the Gold plan\u003C\u002Ftd>\u003Ctd>Advertised prices are the annual rates\u003C\u002Ftd>\u003C\u002Ftr>\n\u003C\u002Ftbody>\n\u003C\u002Ftable>\n\u003C\u002Fdiv>\n\n\u003Cdiv class=\"table-wrap\">\n\u003Ctable>\n\u003Cthead>\u003Ctr>\u003Cth>Plan\u003C\u002Fth>\u003Cth>What you get\u003C\u002Fth>\u003C\u002Ftr>\u003C\u002Fthead>\n\u003Ctbody>\n\u003Ctr>\u003Ctd>Starter (free)\u003C\u002Ftd>\u003Ctd>$0. 5 forms, 100 submissions\u002Fmo\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Bronze\u003C\u002Ftd>\u003Ctd>$39\u002Fmo ($34\u002Fmo billed yearly). 1,000 submissions\u002Fmo\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Silver\u003C\u002Ftd>\u003Ctd>$49\u002Fmo ($39\u002Fmo billed yearly). 2,500 submissions\u002Fmo\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Gold\u003C\u002Ftd>\u003Ctd>$129\u002Fmo ($99\u002Fmo billed yearly). 10,000 submissions\u002Fmo, HIPAA features\u003C\u002Ftd>\u003C\u002Ftr>\n\u003C\u002Ftbody>\n\u003C\u002Ftable>\n\u003C\u002Fdiv>\n\n\u003Cp>\u003Cstrong>Best for:\u003C\u002Fstrong> questionnaires that need unusual question types or a ready-made template.\u003C\u002Fp>\n\n\u003Cp>\u003Cstrong>The catch:\u003C\u002Fstrong> the response meter runs on every plan, so a successful questionnaire pushes you up the tiers.\u003C\u002Fp>\n\n\u003Cp>\u003Cstrong>G2 rating:\u003C\u002Fstrong> 4.7\u002F5, from 5,426 reviews, the largest base of any dedicated form tool here.\u003C\u002Fp>\n\n\u003Ch2>5. Google Forms, best free option\u003C\u002Fh2>\n\n\u003Cp>\u003Cimg src=\"https:\u002F\u002Fformester-strapi.s3.ap-south-1.amazonaws.com\u002Fgoogle_forms_1165c9a16e.png\" alt=\"Google Forms homepage hero screenshot\" style=\"width:100%;max-width:900px;height:auto;border-radius:8px;border:1px solid #e5e7eb;margin:16px 0;\" loading=\"lazy\" \u002F>\u003C\u002Fp>\n\n\u003Cp>Google Forms handles a straightforward questionnaire well enough, and it is free with any Google account, with no response cap worth planning around.\u003C\u002Fp>\n\n\u003Cp>Answers flow into Sheets, which is where most analysis happens anyway. For an internal questionnaire that ends in a pivot table, this is often the whole job.\u003C\u002Fp>\n\n\u003Cp>The limits show up as questionnaires get more sophisticated. Logic is skip-to-section only, so adaptive paths that depend on several earlier answers are not possible.\u003C\u002Fp>\n\n\u003Cdiv class=\"table-wrap\">\n\u003Ctable>\n\u003Cthead>\u003Ctr>\u003Cth>Strengths\u003C\u002Fth>\u003Cth>Weaknesses\u003C\u002Fth>\u003C\u002Ftr>\u003C\u002Fthead>\n\u003Ctbody>\n\u003Ctr>\u003Ctd>Free with any Google account\u003C\u002Ftd>\u003Ctd>Logic is skip-to-section only\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>No practical response cap\u003C\u002Ftd>\u003Ctd>Very limited design control\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Answers sync straight into Sheets\u003C\u002Ftd>\u003Ctd>No native payment collection\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Multiple people can edit at once\u003C\u002Ftd>\u003Ctd>Google branding stays on the form\u003C\u002Ftd>\u003C\u002Ftr>\n\u003C\u002Ftbody>\n\u003C\u002Ftable>\n\u003C\u002Fdiv>\n\n\u003Cdiv class=\"table-wrap\">\n\u003Ctable>\n\u003Cthead>\u003Ctr>\u003Cth>Plan\u003C\u002Fth>\u003Cth>What you get\u003C\u002Fth>\u003C\u002Ftr>\u003C\u002Fthead>\n\u003Ctbody>\n\u003Ctr>\u003Ctd>Free\u003C\u002Ftd>\u003Ctd>$0 with any Google account. Effectively unlimited responses\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Workspace Business Starter\u003C\u002Ftd>\u003Ctd>$7\u002Fuser\u002Fmo, annual basis\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Workspace Business Standard\u003C\u002Ftd>\u003Ctd>$14\u002Fuser\u002Fmo, annual basis\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Workspace Business Plus\u003C\u002Ftd>\u003Ctd>$22\u002Fuser\u002Fmo, annual basis\u003C\u002Ftd>\u003C\u002Ftr>\n\u003C\u002Ftbody>\n\u003C\u002Ftable>\n\u003C\u002Fdiv>\n\n\u003Cp>\u003Cstrong>Best for:\u003C\u002Fstrong> internal questionnaires inside a Google Workspace team.\u003C\u002Fp>\n\n\u003Cp>\u003Cstrong>The catch:\u003C\u002Fstrong> adaptive questionnaires are out of reach. Skip-to-section cannot branch on combinations of earlier answers.\u003C\u002Fp>\n\n\u003Cp>\u003Cstrong>G2 rating:\u003C\u002Fstrong> Google Forms has no standalone G2 profile. The 4.6\u002F5 from 48,175 reviews quoted elsewhere covers Google Workspace as a whole.\u003C\u002Fp>\n\n\u003Ch2>6. Microsoft Forms, best for Microsoft 365 teams\u003C\u002Fh2>\n\n\u003Cp>\u003Cimg src=\"https:\u002F\u002Fformester-strapi.s3.ap-south-1.amazonaws.com\u002Fmicrosoft_forms_6d1d2eb8e8.png\" alt=\"Microsoft Forms homepage hero screenshot\" style=\"width:100%;max-width:900px;height:auto;border-radius:8px;border:1px solid #e5e7eb;margin:16px 0;\" loading=\"lazy\" \u002F>\u003C\u002Fp>\n\n\u003Cp>Microsoft Forms covers the same ground as Google Forms for organisations on Microsoft 365, with results landing in Excel and the questionnaire available inside Teams.\u003C\u002Fp>\n\n\u003Cp>Its real advantage is compliance inheritance. A questionnaire built in a configured tenant sits inside the security posture your IT team already signed off, which shortens approval for anything touching employee or patient data.\u003C\u002Fp>\n\n\u003Cp>There is nothing extra to buy. Business Basic is $7 per user a month on annual billing, and Business Standard now bundles Copilot at $23.50.\u003C\u002Fp>\n\n\u003Cdiv class=\"table-wrap\">\n\u003Ctable>\n\u003Cthead>\u003Ctr>\u003Cth>Strengths\u003C\u002Fth>\u003Cth>Weaknesses\u003C\u002Fth>\u003C\u002Ftr>\u003C\u002Fthead>\n\u003Ctbody>\n\u003Ctr>\u003Ctd>No extra cost inside Microsoft 365\u003C\u002Ftd>\u003Ctd>Free accounts cap at 200 responses per form\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Inherits the tenant's compliance posture\u003C\u002Ftd>\u003Ctd>Branching is basic\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Results land in Excel\u003C\u002Ftd>\u003Ctd>Very limited design control\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Runs inside Teams for internal questionnaires\u003C\u002Ftd>\u003Ctd>Little value outside a Microsoft organisation\u003C\u002Ftd>\u003C\u002Ftr>\n\u003C\u002Ftbody>\n\u003C\u002Ftable>\n\u003C\u002Fdiv>\n\n\u003Cdiv class=\"table-wrap\">\n\u003Ctable>\n\u003Cthead>\u003Ctr>\u003Cth>Plan\u003C\u002Fth>\u003Cth>What you get\u003C\u002Fth>\u003C\u002Ftr>\u003C\u002Fthead>\n\u003Ctbody>\n\u003Ctr>\u003Ctd>Free\u003C\u002Ftd>\u003Ctd>$0 with a personal Microsoft account. 200 responses per form\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>M365 Business Basic\u003C\u002Ftd>\u003Ctd>$7\u002Fuser\u002Fmo, annual basis\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>M365 Business Standard with Copilot\u003C\u002Ftd>\u003Ctd>$23.50\u002Fuser\u002Fmo, annual basis\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>M365 Business Premium with Copilot\u003C\u002Ftd>\u003Ctd>$32\u002Fuser\u002Fmo, annual basis\u003C\u002Ftd>\u003C\u002Ftr>\n\u003C\u002Ftbody>\n\u003C\u002Ftable>\n\u003C\u002Fdiv>\n\n\u003Cp>\u003Cstrong>Best for:\u003C\u002Fstrong> internal questionnaires in organisations already on Microsoft 365.\u003C\u002Fp>\n\n\u003Cp>\u003Cstrong>The catch:\u003C\u002Fstrong> the 200-response cap on free accounts arrives quickly, and outside a tenant the tool has little to offer.\u003C\u002Fp>\n\n\u003Cp>\u003Cstrong>G2 rating:\u003C\u002Fstrong> 4.4\u002F5, from 476 reviews, at the lower end here, which matches its internal focus.\u003C\u002Fp>\n\n\u003Ch2>7. Fillout, best for Airtable and Notion teams\u003C\u002Fh2>\n\n\u003Cp>\u003Cimg src=\"https:\u002F\u002Fformester-strapi.s3.ap-south-1.amazonaws.com\u002Ffillout_d14627e722.png\" alt=\"Fillout homepage hero screenshot\" style=\"width:100%;max-width:900px;height:auto;border-radius:8px;border:1px solid #e5e7eb;margin:16px 0;\" loading=\"lazy\" \u002F>\u003C\u002Fp>\n\n\u003Cp>Fillout suits questionnaires whose answers need to live in a database rather than a spreadsheet. It writes into Airtable and Notion records and updates existing rows, which turns a questionnaire into a data-entry workflow.\u003C\u002Fp>\n\n\u003Cp>Multi-step forms with progress bars are the default, which is the right shape for anything long, and the free plan covers 1,000 responses a month with unlimited seats.\u003C\u002Fp>\n\n\u003Cp>Monthly pricing runs $19 for Starter, $49 for Pro, and $89 for Business, or $15, $40, and $75 when billed yearly.\u003C\u002Fp>\n\n\u003Cdiv class=\"table-wrap\">\n\u003Ctable>\n\u003Cthead>\u003Ctr>\u003Cth>Strengths\u003C\u002Fth>\u003Cth>Weaknesses\u003C\u002Fth>\u003C\u002Ftr>\u003C\u002Fthead>\n\u003Ctbody>\n\u003Ctr>\u003Ctd>Writes back into Airtable and Notion records\u003C\u002Ftd>\u003Ctd>The main advantage only applies to Airtable and Notion users\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>1,000 responses a month free\u003C\u002Ftd>\u003Ctd>Advertised prices are the annual rates\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Multi-step questionnaires by default\u003C\u002Ftd>\u003Ctd>30 G2 reviews, a small sample\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Unlimited seats on every plan\u003C\u002Ftd>\u003Ctd>Analytics are lighter than Typeform's\u003C\u002Ftd>\u003C\u002Ftr>\n\u003C\u002Ftbody>\n\u003C\u002Ftable>\n\u003C\u002Fdiv>\n\n\u003Cdiv class=\"table-wrap\">\n\u003Ctable>\n\u003Cthead>\u003Ctr>\u003Cth>Plan\u003C\u002Fth>\u003Cth>What you get\u003C\u002Fth>\u003C\u002Ftr>\u003C\u002Fthead>\n\u003Ctbody>\n\u003Ctr>\u003Ctd>Free\u003C\u002Ftd>\u003Ctd>$0. 1,000 responses\u002Fmo, unlimited seats\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Starter\u003C\u002Ftd>\u003Ctd>$19\u002Fmo ($15\u002Fmo billed yearly, $180\u002Fyear)\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Pro\u003C\u002Ftd>\u003Ctd>$49\u002Fmo ($40\u002Fmo billed yearly, $480\u002Fyear)\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Business\u003C\u002Ftd>\u003Ctd>$89\u002Fmo ($75\u002Fmo billed yearly, $900\u002Fyear)\u003C\u002Ftd>\u003C\u002Ftr>\n\u003C\u002Ftbody>\n\u003C\u002Ftable>\n\u003C\u002Fdiv>\n\n\u003Cp>\u003Cstrong>Best for:\u003C\u002Fstrong> teams whose questionnaire answers belong in Airtable or Notion.\u003C\u002Fp>\n\n\u003Cp>\u003Cstrong>The catch:\u003C\u002Fstrong> outside those two databases the write-back is irrelevant, and several tools here do questionnaires just as well.\u003C\u002Fp>\n\n\u003Cp>\u003Cstrong>G2 rating:\u003C\u002Fstrong> 4.6\u002F5, from 30 reviews. A small base, consistent with a newer product.\u003C\u002Fp>\n\n\u003Ch2>8. Zoho Forms, best for Zoho users\u003C\u002Fh2>\n\n\u003Cp>\u003Cimg src=\"https:\u002F\u002Fformester-strapi.s3.ap-south-1.amazonaws.com\u002Fzoho_forms_2e42a5d231.png\" alt=\"Zoho Forms homepage hero screenshot\" style=\"width:100%;max-width:900px;height:auto;border-radius:8px;border:1px solid #e5e7eb;margin:16px 0;\" loading=\"lazy\" \u002F>\u003C\u002Fp>\n\n\u003Cp>Zoho Forms makes sense when the questionnaire feeds a Zoho system. Responses become CRM records in one click, and the rest of the suite picks them up without extra plumbing.\u003C\u002Fp>\n\n\u003Cp>For questionnaires collected in the field, the native iOS and Android apps work offline and sync later, which few tools here offer.\u003C\u002Fp>\n\n\u003Cp>Pricing is the lowest in this list: Basic $10 a month, Standard $25, Professional $50, and Premium $90, each per month billed annually, above a free plan of 3 forms and 500 submissions.\u003C\u002Fp>\n\n\u003Cdiv class=\"table-wrap\">\n\u003Ctable>\n\u003Cthead>\u003Ctr>\u003Cth>Strengths\u003C\u002Fth>\u003Cth>Weaknesses\u003C\u002Fth>\u003C\u002Ftr>\u003C\u002Fthead>\n\u003Ctbody>\n\u003Ctr>\u003Ctd>One-click sync into Zoho CRM\u003C\u002Ftd>\u003Ctd>Little reason to use it outside Zoho\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Native offline apps for iOS and Android\u003C\u002Ftd>\u003Ctd>Interface feels dated\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Cheapest paid entry point here\u003C\u002Ftd>\u003Ctd>Free plan covers 3 forms\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Approval workflows on paid tiers\u003C\u002Ftd>\u003Ctd>Prices are the annual-billed rates\u003C\u002Ftd>\u003C\u002Ftr>\n\u003C\u002Ftbody>\n\u003C\u002Ftable>\n\u003C\u002Fdiv>\n\n\u003Cdiv class=\"table-wrap\">\n\u003Ctable>\n\u003Cthead>\u003Ctr>\u003Cth>Plan\u003C\u002Fth>\u003Cth>What you get\u003C\u002Fth>\u003C\u002Ftr>\u003C\u002Fthead>\n\u003Ctbody>\n\u003Ctr>\u003Ctd>Free\u003C\u002Ftd>\u003Ctd>$0. 3 forms, 500 submissions\u002Fmo\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Basic\u003C\u002Ftd>\u003Ctd>$10\u002Fmo billed annually. 10,000 submissions\u002Fmo\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Standard\u003C\u002Ftd>\u003Ctd>$25\u002Fmo billed annually. 25 forms, approval workflows\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Professional\u003C\u002Ftd>\u003Ctd>$50\u002Fmo billed annually. Unlimited forms, payment integrations\u003C\u002Ftd>\u003C\u002Ftr>\n\u003Ctr>\u003Ctd>Premium\u003C\u002Ftd>\u003Ctd>$90\u002Fmo billed annually. HIPAA compliance, Salesforce integration\u003C\u002Ftd>\u003C\u002Ftr>\n\u003C\u002Ftbody>\n\u003C\u002Ftable>\n\u003C\u002Fdiv>\n\n\u003Cp>\u003Cstrong>Best for:\u003C\u002Fstrong> teams already inside the Zoho suite.\u003C\u002Fp>\n\n\u003Cp>\u003Cstrong>The catch:\u003C\u002Fstrong> every strength depends on the surrounding Zoho products. On its own it is an unremarkable builder with a dated interface.\u003C\u002Fp>\n\n\u003Cp>\u003Cstrong>G2 rating:\u003C\u002Fstrong> 4.4\u002F5, from 129 reviews, at the lower end of this list.\u003C\u002Fp>\n\n\u003Cdiv style=\"background: #F5F3FF; border: 1px solid #E9D5FF; border-radius: 24px; padding: clamp(28px, 5vw, 56px) clamp(20px, 4vw, 48px); margin: 40px 0; text-align: center; font-family: inherit;\">\n\u003Cdiv style=\"display: inline-block; background: #FFFFFF; border: 1px solid #E9D5FF; border-radius: 9999px; padding: 6px 16px; font-size: 12px; font-weight: 700; color: #6941C6; letter-spacing: 0.06em; text-transform: uppercase; margin-bottom: 22px;\">Formester\u003C\u002Fdiv>\n\u003Ch3 style=\"color: #0F172A !important; font-size: clamp(24px, 3.4vw, 36px); line-height: 1.2; font-weight: 700; margin: 0 auto 14px; max-width: 720px; font-family: inherit;\">Run questionnaires without response caps\u003C\u002Fh3>\n\u003Cp style=\"color: #475467; font-size: clamp(15px, 1.5vw, 17px); line-height: 1.55; margin: 0 auto 28px; max-width: 600px; font-family: inherit;\">Unlimited responses and drop-off analysis, with all field types on the free plan. No cap on questions or forms.\u003C\u002Fp>\n\u003Cp style=\"margin: 0;\">\u003Ca href=\"https:\u002F\u002Fapp.formester.com\u002Fusers\u002Fsign_up\" style=\"display: inline-block; background: #7f56d9 !important; color: #ffffff !important; text-decoration: none !important; padding: 14px 28px; border-radius: 9999px; font-weight: 600; font-size: 16px; font-family: inherit;\">Try Formester free \u003Cspan aria-hidden=\"true\" style=\"margin-left: 4px;\">&rarr;\u003C\u002Fspan>\u003C\u002Fa>\u003C\u002Fp>\n\u003Cp style=\"margin: 22px 0 0; font-size: 13px; color: #697586; font-family: inherit;\">Free forever plan \u003Cspan style=\"color: #C4B5FD;\">&bull;\u003C\u002Fspan> No credit card \u003Cspan style=\"color: #C4B5FD;\">&bull;\u003C\u002Fspan> Setup in 2 minutes\u003C\u002Fp>\n\u003C\u002Fdiv>\n\n\u003Ch2>How to pick the right questionnaire software\u003C\u002Fh2>\n\n\u003Cp>Two questions settle most of this. First, how many responses do you expect, and how confident are you in that number? Unpredictable volume points to Formester, which never meters. Predictable low volume opens up the free tiers of Google Forms and Microsoft Forms.\u003C\u002Fp>\n\n\u003Cp>Second, how much does methodology matter? If your results will be scrutinised by researchers or a board, SurveyMonkey's reviewed templates and benchmarking earn their price. If completion rate is the priority instead, Typeform is the specialist.\u003C\u002Fp>\n\n\u003Cp>Everything else follows your existing stack: Airtable or Notion points to Fillout, Zoho to Zoho Forms, while a Microsoft or Google tenant points to the form tool you already own.\u003C\u002Fp>\n\n\u003Ch2>Common questions about questionnaire software\u003C\u002Fh2>\n\n\u003Cdetails>\u003Csummary>What is questionnaire software?\u003C\u002Fsummary>\u003Cdiv>Questionnaire software is a tool for building structured sets of questions, distributing them, then collecting the answers for analysis. It differs from basic form software in its handling of branching logic and question types, plus response analysis over longer sets of questions.\u003C\u002Fdiv>\u003C\u002Fdetails>\n\n\u003Cdetails>\u003Csummary>What is the best free questionnaire software?\u003C\u002Fsummary>\u003Cdiv>The best free questionnaire software is Formester if you need unlimited responses and auto-scoring, or Google Forms if your team already works in Google Workspace. Fillout's free plan allows 1,000 responses a month with unlimited seats.\u003C\u002Fdiv>\u003C\u002Fdetails>\n\n\u003Cdetails>\u003Csummary>How many responses can I collect for free?\u003C\u002Fsummary>\u003Cdiv>Response limits vary widely on free plans. Formester and Google Forms place no practical cap, Fillout allows 1,000 a month, Zoho Forms 500, Microsoft Forms 200 per form, Jotform 100, while Typeform allows 10.\u003C\u002Fdiv>\u003C\u002Fdetails>\n\n\u003Cdetails>\u003Csummary>Which questionnaire tool has the best branching logic?\u003C\u002Fsummary>\u003Cdiv>Jotform and Fillout offer the deepest branching, with conditions that combine several earlier answers. Formester includes conditional logic from the Personal plan at $13 a month. Google Forms and Microsoft Forms only support skip-to-section behaviour.\u003C\u002Fdiv>\u003C\u002Fdetails>\n\n\u003Cdetails>\u003Csummary>Can questionnaire software score answers automatically?\u003C\u002Fsummary>\u003Cdiv>Yes, several tools score answers automatically. Formester includes quiz auto-scoring on its free plan, Jotform supports calculations and scoring on paid tiers, and Microsoft Forms scores quizzes natively inside Microsoft 365.\u003C\u002Fdiv>\u003C\u002Fdetails>\n\n\u003Cdetails>\u003Csummary>Which tool is best for academic research?\u003C\u002Fsummary>\u003Cdiv>For academic research, SurveyMonkey offers methodologist-reviewed templates and benchmarking data that stand up to review. Typeform suits qualitative studies where completion rate matters, though neither replaces a dedicated research platform for complex study designs.\u003C\u002Fdiv>\u003C\u002Fdetails>\n\n\u003Cdetails>\u003Csummary>Do these tools work offline?\u003C\u002Fsummary>\u003Cdiv>Three tools here collect questionnaire responses offline: Formester, whose forms install as an app and sync when connectivity returns, Jotform through its mobile app, and Zoho Forms through its iOS and Android apps.\u003C\u002Fdiv>\u003C\u002Fdetails>\n\n\u003Cdetails>\u003Csummary>Which questionnaire software is HIPAA compliant?\u003C\u002Fsummary>\u003Cdiv>Among these tools, Jotform offers HIPAA features from the Gold plan and Zoho Forms from Premium, while Microsoft Forms supports it through a configured Microsoft 365 tenant. Formester does not offer HIPAA on any tier.\u003C\u002Fdiv>\u003C\u002Fdetails>\n\n\u003Cstyle>\n\n.fmstr-cmp-qns-exit {\n--p-bg-card: #ffffff;\n--p-bg-violet-25: #f7f3ff;\n--p-bg-pill: #f4ebff;\n--p-fg-1: #101828;\n--p-fg-2: #475467;\n--p-fg-3: #697586;\n--p-violet-500: #7f56d9;\n--p-violet-600: #6941c6;\n--p-violet-700: #5925dc;\n--p-border-light: #eaecf0;\n--p-border-violet: #9777e0;\n\nposition: fixed;\ninset: 0;\nz-index: 2147483000;\ndisplay: none;\nalign-items: center;\njustify-content: center;\npadding: 24px;\nfont-family: inherit;\ncolor: var(--p-fg-1);\n}\n.fmstr-cmp-qns-exit *, .fmstr-cmp-qns-exit *::before, .fmstr-cmp-qns-exit *::after { box-sizing: border-box; }\n.fmstr-cmp-qns-exit.is-open { display: flex; }\n\n.fmstr-cmp-qns-exit__backdrop {\nposition: absolute; inset: 0;\nbackground: rgba(16, 10, 40, 0.55);\nbackdrop-filter: blur(3px);\nopacity: 0;\ntransition: opacity 220ms ease;\n}\n.fmstr-cmp-qns-exit.is-open .fmstr-cmp-qns-exit__backdrop { opacity: 1; }\n\n.fmstr-cmp-qns-exit__card {\nposition: relative;\nwidth: 100%;\nmax-width: 520px;\nbackground: var(--p-bg-card);\nborder: 1px solid var(--p-border-light);\nborder-radius: 20px;\npadding: 36px 36px 30px;\nbox-shadow: 0 32px 80px rgba(16, 10, 40, 0.32);\nopacity: 0;\ntransform: translateY(14px) scale(0.985);\ntransition: opacity 260ms ease, transform 260ms cubic-bezier(0.22, 1, 0.36, 1);\n}\n.fmstr-cmp-qns-exit.is-open .fmstr-cmp-qns-exit__card { opacity: 1; transform: none; }\n\n.fmstr-cmp-qns-exit__close {\nposition: absolute;\ntop: 12px; right: 12px;\nwidth: 40px; height: 40px;\ndisplay: inline-flex; align-items: center; justify-content: center;\nbackground: transparent;\nborder: 0;\nborder-radius: 50%;\ncolor: var(--p-fg-3);\ncursor: pointer;\ntransition: background-color 150ms ease, color 150ms ease;\n}\n.fmstr-cmp-qns-exit__close:hover { background: #f2f4f7; color: var(--p-fg-1); }\n.fmstr-cmp-qns-exit__close:focus { outline: none; }\n.fmstr-cmp-qns-exit__close:focus-visible { outline: 2px solid var(--p-border-violet); outline-offset: 2px; }\n.fmstr-cmp-qns-exit__cta:focus-visible,\n.fmstr-cmp-qns-exit__dismiss:focus-visible { outline: 2px solid var(--p-border-violet); outline-offset: 2px; border-radius: 9999px; }\n\n.fmstr-cmp-qns-exit__eyebrow {\ndisplay: inline-block;\npadding: 5px 13px 7px;\nbackground: var(--p-bg-pill);\ncolor: var(--p-violet-600);\nborder-radius: 9999px;\nfont-size: 12px;\nfont-weight: 700;\nline-height: 1;\nletter-spacing: 0.08em;\ntext-transform: uppercase;\nmargin-bottom: 16px;\nmax-width: calc(100% - 46px);\n}\n\n.fmstr-cmp-qns-exit__heading {\nmargin: 0 0 12px;\nfont-size: 27px;\nline-height: 1.22;\nfont-weight: 800;\nletter-spacing: -0.02em;\n}\n.fmstr-cmp-qns-exit__heading em { font-style: normal; color: var(--p-violet-600); }\n\n.fmstr-cmp-qns-exit__sub {\nmargin: 0 0 24px;\nfont-size: 15px;\nline-height: 1.55;\ncolor: var(--p-fg-2);\n}\n\n.fmstr-cmp-qns-exit__list { list-style: none; margin: 0 0 28px; padding: 0; display: flex; flex-direction: column; gap: 16px; }\n.fmstr-cmp-qns-exit__item { display: flex; align-items: flex-start; gap: 14px; }\n.fmstr-cmp-qns-exit__ic {\nwidth: 38px; height: 38px; flex-shrink: 0;\nborder-radius: 10px;\nbackground: var(--p-bg-violet-25);\ncolor: var(--p-violet-600);\ndisplay: inline-flex; align-items: center; justify-content: center;\n}\n.fmstr-cmp-qns-exit__ic svg { display: block; }\n.fmstr-cmp-qns-exit__item-title { margin: 0; font-size: 15px; line-height: 1.4; font-weight: 700; }\n.fmstr-cmp-qns-exit__item-body { margin: 3px 0 0; font-size: 14px; line-height: 1.45; color: var(--p-fg-3); }\n\n.fmstr-cmp-qns-exit__cta {\ndisplay: block;\nwidth: 100%;\npadding: 15px 24px 16px;\nbackground: var(--p-violet-600) !important;\ncolor: #ffffff !important;\nborder-radius: 9999px;\nfont-size: 16px;\nfont-weight: 700;\nline-height: 1;\ntext-align: center;\ntext-decoration: none;\nbox-shadow: 0 8px 24px rgba(105, 65, 198, 0.26);\ntransition: background-color 150ms ease, transform 150ms ease;\n}\n.fmstr-cmp-qns-exit__cta:hover { background: var(--p-violet-700) !important; color: #ffffff !important; transform: translateY(-1px); }\n\n.fmstr-cmp-qns-exit__dismiss {\ndisplay: block;\nwidth: 100%;\nmargin-top: 10px;\npadding: 12px;\nbackground: transparent;\nborder: 0;\ncolor: var(--p-fg-3);\nfont-family: inherit;\nfont-size: 14px;\nfont-weight: 600;\ncursor: pointer;\n}\n.fmstr-cmp-qns-exit__dismiss:hover { color: var(--p-fg-1); }\n\n.fmstr-cmp-qns-exit__meta {\nmargin: 6px 0 0;\ntext-align: center;\nfont-size: 12px;\nfont-weight: 500;\ncolor: var(--p-fg-3);\n}\n\n@media (max-width: 560px) {\n.fmstr-cmp-qns-exit { padding: 16px; align-items: flex-end; }\n.fmstr-cmp-qns-exit__card { padding: 28px 22px 22px; border-radius: 18px; }\n.fmstr-cmp-qns-exit__heading { font-size: 23px; }\n.fmstr-cmp-qns-exit__list { gap: 14px; margin-bottom: 24px; }\n}\n\n@media (prefers-reduced-motion: reduce) {\n.fmstr-cmp-qns-exit__backdrop,\n.fmstr-cmp-qns-exit__card { transition: none; }\n.fmstr-cmp-qns-exit__card { transform: none; }\n}\n\u003C\u002Fstyle>\n\n\u003Cdiv class=\"fmstr-cmp-qns-exit\" id=\"fmstr-qns-exit\" role=\"dialog\" aria-modal=\"true\" aria-labelledby=\"fmstr-qns-exit-heading\" aria-hidden=\"true\">\n\u003Cdiv class=\"fmstr-cmp-qns-exit__backdrop\" data-fmstr-exit-close>\u003C\u002Fdiv>\n\u003Cdiv class=\"fmstr-cmp-qns-exit__card\">\n\u003Cbutton type=\"button\" class=\"fmstr-cmp-qns-exit__close\" data-fmstr-exit-close aria-label=\"Close\">\n\u003Csvg width=\"20\" height=\"20\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2.2\" stroke-linecap=\"round\" stroke-linejoin=\"round\" aria-hidden=\"true\">\u003Cline x1=\"18\" y1=\"6\" x2=\"6\" y2=\"18\"\u002F>\u003Cline x1=\"6\" y1=\"6\" x2=\"18\" y2=\"18\"\u002F>\u003C\u002Fsvg>\n\u003C\u002Fbutton>\n\u003Cspan class=\"fmstr-cmp-qns-exit__eyebrow\">Before you build the logic\u003C\u002Fspan>\n\u003Ch2 id=\"fmstr-qns-exit-heading\" class=\"fmstr-cmp-qns-exit__heading\">Branching is where questionnaire tools \u003Cem>start charging\u003C\u002Fem>\u003C\u002Fh2>\n\u003Cp class=\"fmstr-cmp-qns-exit__sub\">SurveyMonkey and Typeform put genuinely useful logic behind their middle tiers. That is the line to compare on.\u003C\u002Fp>\n\u003Cul class=\"fmstr-cmp-qns-exit__list\">\n\u003Cli class=\"fmstr-cmp-qns-exit__item\">\n\u003Cspan class=\"fmstr-cmp-qns-exit__ic\" aria-hidden=\"true\">\u003Csvg width=\"19\" height=\"19\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"1.8\" stroke-linecap=\"round\" stroke-linejoin=\"round\" aria-hidden=\"true\">\u003Ccircle cx=\"6\" cy=\"6\" r=\"3\"\u002F>\u003Ccircle cx=\"6\" cy=\"18\" r=\"3\"\u002F>\u003Cpath d=\"M6 9v6\"\u002F>\u003Cpath d=\"M18 9a9 9 0 0 1-9 9\"\u002F>\u003Ccircle cx=\"18\" cy=\"6\" r=\"3\"\u002F>\u003C\u002Fsvg>\u003C\u002Fspan>\n\u003Cspan>\n\u003Ch3 class=\"fmstr-cmp-qns-exit__item-title\">Conditional logic from $12 a month\u003C\u002Fh3>\n\u003Cp class=\"fmstr-cmp-qns-exit__item-body\">Personal tier, billed annually\u003C\u002Fp>\n\u003C\u002Fspan>\n\u003C\u002Fli>\n\u003Cli class=\"fmstr-cmp-qns-exit__item\">\n\u003Cspan class=\"fmstr-cmp-qns-exit__ic\" aria-hidden=\"true\">\u003Csvg width=\"19\" height=\"19\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"1.8\" stroke-linecap=\"round\" stroke-linejoin=\"round\" aria-hidden=\"true\">\u003Cpath d=\"m12 14 4-4\"\u002F>\u003Cpath d=\"M3.34 19a10 10 0 1 1 17.32 0\"\u002F>\u003C\u002Fsvg>\u003C\u002Fspan>\n\u003Cspan>\n\u003Ch3 class=\"fmstr-cmp-qns-exit__item-title\">Unlimited questions and responses\u003C\u002Fh3>\n\u003Cp class=\"fmstr-cmp-qns-exit__item-body\">No question limit, no response cap, any tier\u003C\u002Fp>\n\u003C\u002Fspan>\n\u003C\u002Fli>\n\u003Cli class=\"fmstr-cmp-qns-exit__item\">\n\u003Cspan class=\"fmstr-cmp-qns-exit__ic\" aria-hidden=\"true\">\u003Csvg width=\"19\" height=\"19\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"1.8\" stroke-linecap=\"round\" stroke-linejoin=\"round\" aria-hidden=\"true\">\u003Cpath d=\"M17.5 19a4.5 4.5 0 1 0 0-9h-1.8A7 7 0 1 0 4 14.9\"\u002F>\u003Cpath d=\"M12 12v9\"\u002F>\u003Cpath d=\"m8 17 4 4 4-4\"\u002F>\u003C\u002Fsvg>\u003C\u002Fspan>\n\u003Cspan>\n\u003Ch3 class=\"fmstr-cmp-qns-exit__item-title\">Field questionnaires without signal\u003C\u002Fh3>\n\u003Cp class=\"fmstr-cmp-qns-exit__item-body\">Offline forms sync when connectivity returns\u003C\u002Fp>\n\u003C\u002Fspan>\n\u003C\u002Fli>\n\u003C\u002Ful>\n\u003Ca href=\"https:\u002F\u002Fapp.formester.com\u002Fusers\u002Fsign_up\" class=\"fmstr-cmp-qns-exit__cta\">Try Formester free\u003C\u002Fa>\n\u003Cbutton type=\"button\" class=\"fmstr-cmp-qns-exit__dismiss\" data-fmstr-exit-close>Keep reading the comparison\u003C\u002Fbutton>\n\u003Cp class=\"fmstr-cmp-qns-exit__meta\">Free forever plan &middot; No credit card &middot; 56,000+ teams\u003C\u002Fp>\n\u003C\u002Fdiv>\n\u003C\u002Fdiv>\n\u003Cscript>\n(function () {\nif (window.__fmstrExitInit_qns) { return; }\nwindow.__fmstrExitInit_qns = true;\n\nvar KEY = 'fmstr_qns_exit_seen_v1';\nvar SCROLL_TRIGGER = 0.6;\nvar MIN_DWELL_MS = 12000;\nvar started = Date.now();\nvar root = document.getElementById('fmstr-qns-exit');\nif (!root) { return; }\n\nfunction alreadySeen() {\ntry { return window.sessionStorage.getItem(KEY) === '1'; } catch (e) { return false; }\n}\nfunction markSeen() {\ntry { window.sessionStorage.setItem(KEY, '1'); } catch (e) {}\n}\nif (alreadySeen()) { return; }\n\nvar opened = false;\nvar prevOverflow = '';\n\nfunction open() {\nif (opened || alreadySeen()) { return; }\nif (!root.isConnected) { return; }\nif (Date.now() - started \u003C MIN_DWELL_MS) { return; }\nopened = true;\nmarkSeen();\nroot.classList.add('is-open');\nroot.setAttribute('aria-hidden', 'false');\nprevOverflow = document.documentElement.style.overflow;\ndocument.documentElement.style.overflow = 'hidden';\nvar closeBtn = root.querySelector('.fmstr-cmp-qns-exit__close');\nif (closeBtn) { closeBtn.focus(); }\ndetach();\n}\n\nfunction close() {\nroot.classList.remove('is-open');\nroot.setAttribute('aria-hidden', 'true');\ndocument.documentElement.style.overflow = prevOverflow;\ndocument.removeEventListener('keydown', onKey);\n}\n\nfunction onScroll() {\nvar doc = document.documentElement;\nvar height = Math.max(doc.scrollHeight, document.body ? document.body.scrollHeight : 0);\nif (height \u003C= window.innerHeight) { return; }\nvar seen = (window.pageYOffset + window.innerHeight) \u002F height;\nif (seen >= SCROLL_TRIGGER) { open(); }\n}\n\nfunction onMouseOut(e) {\nif (e.relatedTarget || e.toElement) { return; }\nif (e.clientY > 4) { return; }\nopen();\n}\n\nfunction onKey(e) {\nif (e.key === 'Escape' || e.keyCode === 27) { close(); }\n}\n\nfunction detach() {\nwindow.removeEventListener('scroll', onScroll);\ndocument.removeEventListener('mouseout', onMouseOut);\n}\n\nwindow.addEventListener('scroll', onScroll, { passive: true });\nvar finePointer = true;\ntry { finePointer = window.matchMedia('(pointer: fine)').matches; } catch (e) {}\nif (finePointer) { document.addEventListener('mouseout', onMouseOut); }\ndocument.addEventListener('keydown', onKey);\n\nroot.addEventListener('click', function (e) {\nvar t = e.target;\nwhile (t && t !== root) {\nif (t.hasAttribute && t.hasAttribute('data-fmstr-exit-close')) { close(); return; }\nt = t.parentNode;\n}\n});\n})();\n\u003C\u002Fscript>\n\n\n","blog\u002Fblog\u002Fbest-questionnaire-software.md",2400,1350,{"text":90},"14 min read",{"title":92,"author":7,"authorImage":8,"authorProfile":9,"coverImg":93,"coverImgAlt":94,"createdAt":95,"description":96,"featured":14,"jsonld":97,"keywords":98,"metaDescription":96,"metaImage":99,"metaTitle":100,"publishedAt":101,"slug":102,"updatedAt":103,"__hash__":104,"body":105,"id":106,"coverImgWidth":25,"coverImgHeight":26,"readingStats":107},"Automate Expense Reimbursement with Smart Online Forms","https:\u002F\u002Fformester-strapi.s3.ap-south-1.amazonaws.com\u002FHow_to_Make_User_Research_Survey_56_b194e46254.png","a blog post cover about automating expense reimbursement ","2025-12-22T02:18:01.378Z","Automate your expense reimbursement process with smart forms. Track submissions, approvals, and payments efficiently while reducing errors and delays.",[],"expense reimbursement, \nexpense reimbursement form,\nexpense reimbursement automation,",[],"How to Automate Expense Reimbursement With Online Forms?","2025-12-22T02:18:06.946Z","automate-expense-reimbursement-with-forms","2026-01-28T04:50:43.507Z","08a8bs2ayyZOWJq_2l8XOYdnrXPTu6E0VowMxC77tVg","![a blog post cover about automating expense reimbursement ](https:\u002F\u002Fformester-strapi.s3.ap-south-1.amazonaws.com\u002FHow_to_Make_User_Research_Survey_56_b194e46254.png)\nExpense reimbursement is an essential process for any organization, but it can be time-consuming and error-prone when handled manually. Employees submit paper forms or spreadsheets, managers follow up via emails, and finance teams struggle to track approvals and payments. Delays, lost receipts, and missed submissions are common problems.\n\nAutomated **[expense reimbursement forms](\u002Ftemplates\u002Fcategories\u002Femployee-management\u002F)** solve these challenges. By digitizing the process and adding automation, you can streamline submissions, approvals, and tracking, making the workflow faster, more accurate, and fully transparent.\n\n## Manual vs Automated Expense Reimbursement\n\n\u003Ctable style=\"width:100%; border-collapse: collapse; font-family: Arial, sans-serif; background-color: white;\">\n  \u003Cthead>\n    \u003Ctr style=\"background-color: #6a0dad; color: white; text-align: left;\">\n      \u003Cth style=\"padding: 10px; border: 1px solid #ddd;\">Manual Reimbursement\u003C\u002Fth>\n      \u003Cth style=\"padding: 10px; border: 1px solid #ddd;\">Automated Forms\u003C\u002Fth>\n    \u003C\u002Ftr>\n  \u003C\u002Fthead>\n  \u003Ctbody>\n    \u003Ctr>\n      \u003Ctd style=\"padding: 10px; border: 1px solid #ddd;\">Involves paper or spreadsheet forms\u003C\u002Ftd>\n      \u003Ctd style=\"padding: 10px; border: 1px solid #ddd;\">Employees submit expenses online\u003C\u002Ftd>\n    \u003C\u002Ftr>\n    \u003Ctr>\n      \u003Ctd style=\"padding: 10px; border: 1px solid #ddd;\">Emailing or printing forms\u003C\u002Ftd>\n      \u003Ctd style=\"padding: 10px; border: 1px solid #ddd;\">Validation rules prevent errors\u003C\u002Ftd>\n    \u003C\u002Ftr>\n    \u003Ctr>\n      \u003Ctd style=\"padding: 10px; border: 1px solid #ddd;\">Waiting for managers and finance teams to review\u003C\u002Ftd>\n      \u003Ctd style=\"padding: 10px; border: 1px solid #ddd;\">Notifications alert managers and finance teams\u003C\u002Ftd>\n    \u003C\u002Ftr>\n    \u003Ctr>\n      \u003Ctd style=\"padding: 10px; border: 1px solid #ddd;\">Lost or unclear receipts\u003C\u002Ftd>\n      \u003Ctd style=\"padding: 10px; border: 1px solid #ddd;\">Automatic receipt verification \u002F clarity checks\u003C\u002Ftd>\n    \u003C\u002Ftr>\n    \u003Ctr>\n      \u003Ctd style=\"padding: 10px; border: 1px solid #ddd;\">Delayed approvals\u003C\u002Ftd>\n      \u003Ctd style=\"padding: 10px; border: 1px solid #ddd;\">Instant manager notifications upon submission\u003C\u002Ftd>\n    \u003C\u002Ftr>\n    \u003Ctr>\n      \u003Ctd style=\"padding: 10px; border: 1px solid #ddd;\">Confusion over submission status\u003C\u002Ftd>\n      \u003Ctd style=\"padding: 10px; border: 1px solid #ddd;\">Real-time status tracking for submissions\u003C\u002Ftd>\n    \u003C\u002Ftr>\n    \u003Ctr>\n      \u003Ctd style=\"padding: 10px; border: 1px solid #ddd;\">Difficulty tracking workflow progress\u003C\u002Ftd>\n      \u003Ctd style=\"padding: 10px; border: 1px solid #ddd;\">Partial submission tracking for progress monitoring\u003C\u002Ftd>\n    \u003C\u002Ftr>\n  \u003C\u002Ftbody>\n\u003C\u002Ftable>\n\n### Creating the Expense Reimbursement Form\n![a screenshot of ai form builder](https:\u002F\u002Fformester-strapi.s3.ap-south-1.amazonaws.com\u002Fa_screenshot_of_ai_form_builder_c3d709b26a.png)\n\nStart by building your form. Using Formester’s **[AI Form Generator](\u002Fai-form-generator\u002F)**, you can quickly create a professional expense reimbursement form.\n\n### Important steps:\n\n- **Add essential fields:** employee name, department, expense date, expense type, amount, payment method, and receipt upload.\n\n\n- Set up validation rules: mark fields as required, and set amount limits.\n\n\n- Configure **[email validation](\u002Ffeatures\u002Femail-verification\u002F)** so employees enter correct addresses for notifications.\n\n\n- Test the form to ensure all fields and validations work as expected.\n\n\nWith these steps, your form is ready for employees to submit expense requests confidently.\n\n### Sharing or Embedding the Form\n![a screenshot of form embedding options in formester](https:\u002F\u002Fformester-strapi.s3.ap-south-1.amazonaws.com\u002Fa_screenshot_of_form_embedding_options_in_formester_2ece230a58.png)\nOnce your form is ready, share it with employees effectively:\n\n- **[Generate a unique submission URL](\u002Ffeatures\u002Fgenerate-unique-form-submission-url-for-each-respondent\u002F)** for each employee to track submissions individually.\n\n- Partial submission tracking lets you monitor progress, so you know who has started, completed, or abandoned a request.\n\n\n- **[Embed the form](\u002Ffeatures\u002Fembed-forms\u002F)** on an internal portal or intranet for easy access.\n\nThis ensures that managers and finance teams can view submission progress without sending constant reminders.\n\n### Manager Approval\n\nManager review is the first approval stage in the workflow. This is wow the automation will work:\n\n- When a new submission is created, managers receive a notification automatically.\n\n- After reviewing the submission, managers can update the form inline to approve or request corrections.\n\n\n### How to set this up in Make:\n![a screenshot of formester form webhook integration](https:\u002F\u002Fformester-strapi.s3.ap-south-1.amazonaws.com\u002Fa_screenshot_of_formester_form_webhook_integration_4860c95cc7.png)\n\n- Open Make and create a new scenario.\n\n- Add a webhook module, copy the **[webhook URL](\u002Fblog\u002Fhow-to-use-webhooks-in-formester\u002F)**.\n\n- **Go back to Formester** → **Automate** → **Webhooks**, create a new webhook, paste the URL, and select submission created. Save it.\n\n- Submit a test submission in Formester.\n\n- Go back to Make, add Gmail or Slack as a new app, and configure the notification to managers. Add recipients as needed.\n\nTo allow managers to approve, invite them as **[team members in Formester](\u002Ffeatures\u002Fcollaborative-forms\u002F)**: go to **Teams → Send Invite**. Managers can now access the organization and approve submissions. This will make sure that the manager approval process is fast, traceable, and fully automated.\n\n### Finance Team Approval\n\nOnce the manager approves, the finance team needs to verify and process the reimbursement. This is how the automation will work:\n\n- Upon an update from the manager, the finance team receives a notification.\n\n- Finance verifies receipts, checks tax and budget compliance, and marks the expense ready for payroll.\n\n\n### How to set this up in Make:\n![a screenshot of make workflow](https:\u002F\u002Fformester-strapi.s3.ap-south-1.amazonaws.com\u002Fa_screenshot_of_make_workflow_1818b3eb05.png)\n\n- Create a new webhook in Make and copy the URL.\n\n- In Formester, create a new webhook, paste the URL, and select **submission.updated.** Save it.\n\n- Make an edit to the test submission to trigger the workflow.\n\n- In Make, add Gmail or Slack as the notification app.\n\n- Add a filter between the webhook and notification module.\n\n**Condition**: Manager Review column contains verified. This ensures finance is notified only when the manager has approved.\n\nTo prevent multiple notifications for the same submission, add a Sleep (delay) module after the filter. Set the delay to **300 seconds (5 minutes)**. You can clone this delay if needed for further staging. This setup will make sure that the finance team is notified only when necessary and prevents duplicate alerts.\n\n### Conclusion\n\n**By automating expense reimbursement:**\n\n- Approvals happen faster at both the manager and finance levels.\n\n- Errors and lost receipts are minimized.\n\n- Submission progress is tracked in real time.\n\n- Manual follow-ups are eliminated, saving time and effort.\n\n\n**Next steps:**\n- Implement automated expense forms using Formester.\n\n- Configure Make to handle manager and finance notifications and approvals.\n\n- Monitor and optimize workflow rules to ensure smooth reimbursement processes.\n\n\n**Automation transforms expense reimbursement** into a transparent, efficient, and reliable workflow for employees, managers, and finance teams.\n\n","blog\u002Fblog\u002Fautomate-expense-reimbursement-with-forms.md",{"text":28},1788439056423]