Power Apps Form UX Mastery: Input Restrictions, Validation, and Error Handling
Learn how to enforce data entry rules, validate form fields, manage submission errors, and prevent accidental data loss in canvas apps.
More than just data capture, a well-designed canvas app form influences how quickly users complete their work and how likely they are to trust the tool. Small UX details — like preventing invalid keystrokes, showing clear error messages, and protecting unsaved edits — dramatically reduce mistakes and frustration.
This article builds a real scenario: an Equipment Inventory app for tracking office hardware. We’ll walk through five concrete improvements: restricting control input, validating data before submission, handling server‑side errors, preventing accidental loss of changes, and reusing a single form for view, edit, and create modes.
All examples reference a SharePoint list or Dataverse table called EquipmentInventory with the following fields:
| Field | Data Type | Constraints |
|---|---|---|
EquipmentName | Text | Required |
SerialNumber | Text (max 30) | Required, unique |
PurchaseDate | Date | Required, not future |
PurchaseCost | Currency | Required, ≤ 100,000 |
AssignedTo | Person/User | Optional |
Status | Choice (Active/Retired) | Default “Active” |
Notes | Multi‑line text | Optional |
Step 1: Configuring Text Inputs for Accuracy
Set the Format property of a Text input to Number when the field expects numeric data only. For PurchaseCost, this immediately blocks any non‑numeric characters.
Similarly, use the MaxLength property to match the maximum length defined in the data source. For SerialNumber (30 characters), either set a static value or retrieve it dynamically:
MaxLength:
If(
IsBlank(DataSourceInfo(EquipmentInventory, DataSourceInfo.MaxLength, "SerialNumber")),
30,
DataSourceInfo(EquipmentInventory, DataSourceInfo.MaxLength, "SerialNumber")
)DataSourceInfo may not be available for all connectors. When it returns blank, fall back to a hard‑coded number that matches your back‑end constraint.
For fields with complex patterns (phone numbers, postal codes), replace a plain Text input with the Masked input control to show format placeholders while the user types.
Step 2: Validating the Form Before Submission
Client‑side validation gives immediate feedback. You can check each field on the change event or run all checks when the user presses Submit. A combined approach works best:
- Display a list of errors at the top of the form.
- Highlight invalid fields with a red border.
- Keep the submit button enabled but show why it will fail.
The following Submit button OnSelect gathers errors and either submits or notifies:
// Clear previous errors
Set(varErrors, "");
// Check required fields
If(IsBlank(TextInput_EquipmentName.Text),
Set(varErrors, varErrors & "Equipment Name is required." & Char(10))
);
If(IsBlank(TextInput_SerialNumber.Text),
Set(varErrors, varErrors & "Serial Number is required." & Char(10))
);
If(IsBlank(DatePicker_PurchaseDate.SelectedDate),
Set(varErrors, varErrors & "Purchase Date is required." & Char(10))
);
// Check length and range
If(Len(TextInput_SerialNumber.Text) > 30,
Set(varErrors, varErrors & "Serial Number must be 30 characters or less." & Char(10))
);
If(Value(TextInput_PurchaseCost.Text) > 100000,
Set(varErrors, varErrors & "Purchase Cost cannot exceed 100,000." & Char(10))
);
// Submit if no errors, else display them
If(varErrors = "",
SubmitForm(Form1),
Notify("Please fix the following issues:" & Char(10) & varErrors, NotificationType.Error)
)To mark individual controls, switch their BorderColor based on the error variable — for example, If(IsBlank(TextInput_EquipmentName.Text) && varErrors <> "", Color.Red, Color.Black).
Do not disable the submit button until all fields are valid. The Smashing Magazine article linked in the references explains why disabled buttons hide the reason for failure and frustrate users. Instead, always show the validation errors and let the user know what needs fixing.
Step 3: Graceful Error Handling After Submission
Never assume a form submitted successfully. Server‑side errors (e.g. duplicate keys, permission failures) can happen even when client validation passes. If you use the Form control, trap errors in OnSuccess and OnFailure:
// OnSuccess
Set(varSubmitSuccess, true);
Notify("Record saved.", NotificationType.Success);
Navigate(InventoryScreen); // or refresh your gallery
// OnFailure
Set(varLastError, First(Errors(Form1)).Message);
Notify("Submission failed: " & varLastError, NotificationType.Error);For Patch‑based forms (no form control), wrap the Patch call with an IfError function:
IfError(
Patch(EquipmentInventory, Gallery1.Selected, {EquipmentName: TextInput_EquipmentName.Text}),
Notify("Update failed: " & FirstError.Message, NotificationType.Error),
Notify("Update succeeded.", NotificationType.Success)
)Always include a fallback that prevents the user from navigating away until the error is resolved. This can be a simple Set(varSubmitAttempted, false) check in the screen OnHidden.
Step 4: Guarding Against Accidental Data Loss
A user may accidentally navigate away while the form contains unsaved edits. The Unsaved property of the form control returns true when changes have not been committed.
Add this check to the screen’s OnHidden or to a Back button:
Set(varShowDiscard, Form1.Unsaved); If(varShowDiscard, Set(varShowDiscardDialog, true), Navigate(PreviousScreen) )
When varShowDiscardDialog becomes true, show an overlay with two buttons: Continue editing (hides the dialog) and Discard changes (cancels the form and navigates). Use a Group control or Dialog component for the pop‑up. Clear the form with ResetForm(Form1) before leaving if the user chooses discard.
Step 5: Reusing a Single Form for All Interactions
Maintaining three separate forms (create, edit, view) for the same data source is unnecessary. Use one form control and switch its mode with NewForm, EditForm, and ViewForm. This reduces code duplication and ensures a consistent layout.
- View mode: show all controls with
DisplayMode.View. - Edit mode: allow edits.
- Create mode: same as edit, but starts with a blank record.
Pass the selected record from a gallery to the form:
Set(varSelectedRecord, Gallery_Equipment.Selected); EditForm(Form1);
Set(varSelectedRecord, Gallery_Equipment.Selected); ViewForm(Form1);
For Patch‑based forms you must manually toggle the DisplayMode of every control. Consider wrapping that logic in a simple Set(varFormMode, "Edit") variable and setting each control’s DisplayMode to If(varFormMode = "View", DisplayMode.View, DisplayMode.Edit).
Security and Performance Considerations
- Client validation is never a substitute for server rules. Power Apps enforces data source constraints on submission, but always use appropriate permissions and column validation in SharePoint or Dataverse.
- DataSourceInfo is not delegated. It returns metadata from the source when the app starts, not during a large batch. Use it sparingly and fall back to static values for performance‑critical screens.
- Heavy formulas in
OnChangecan cause sluggish typing. For real‑time character counting or length checks, stick to simpleLen(…)comparisons.
Common Pitfalls and How to Avoid Them
| Mistake | Solution |
|---|---|
| Errors not appearing after submission | Check that Errors(Form1) is not empty and that OnFailure is wired correctly. |
| Disabled submit button without explanation | Use Notify or a label to show why the button is disabled while keeping it enabled. |
| Forgetting to reset validation variables on a new form | Set(varErrors, "") at the start of NewForm or ResetForm. |
| Unsaved changes dialog not showing | Verify Form.Unsaved is being checked on the correct screen event (OnHidden, not OnVisible). |
| Single form shows empty fields on initial gallery select | Call EditForm or ViewForm after setting the selected record, not before. |
Final Thoughts
Great form UX is built by combining small but intentional checks: restrict what users can type, validate before submitting, handle errors gracefully, protect unsaved work, and reuse the same form to stay consistent. These patterns are easy to implement and pay off immediately in user confidence and data quality.
Start with the equipment inventory scenario in this article, adapt the validation rules to your own data, and watch your app move from functional to delightful.
References
- Original article: Power Apps Form Design & UX Guidelines by Matthew Devaney
- Smashing Magazine – Why disabled buttons are frustrating
- Microsoft Learn: Text input control (placeholder)
- Microsoft Learn: Form control properties (Unsaved, OnSuccess, OnFailure) (placeholder)
- Microsoft Learn: IfError function (placeholder)
Learn how small coding practices—like using descriptive names, flattening conditions, and simplifying logic—can make your apps easier to update and less error-prone.
Move past the gallery and discover the hidden patterns for validation, navigation, and smart submission handling in your data entry forms.
PowerShell unlocks admin capabilities that the Power Platform admin center simply doesn’t offer—from recovering deleted apps to blocking trial licenses. Here’s how to wield them safely.