AngularJS中如何用用户输入值作为其他字段正则验证的一部分
Absolutely, you can dynamically link one model's value to another field's regex validation in AngularJS—here's how to do it properly.
The key thing to note is that ng-pattern expects a RegExp object (or a string that can be converted to one), but you can't directly interpolate a model value like {{emp.empId}} into the pattern string in the template. Instead, you need to construct the regex dynamically in your controller whenever the dependent model changes.
Step-by-Step Implementation
1. Set Up Your Controller
First, create a watcher on your emp.empId model to update the validation pattern whenever the ID changes. We'll also include a helper function to escape regex special characters (like ., *, or +) in case your Employee ID contains them—this ensures those characters are treated literally instead of as regex operators.
angular.module('employeeApp', []) .controller('EmployeeController', function($scope) { // Initialize your model $scope.emp = { empId: '', empFile: '' }; // Helper function to escape regex special characters function escapeRegExp(string) { return string.replace(/[.*+?^${}()|[\]\\]/g, '\\$&'); } // Watch for changes to empId and update the validation pattern $scope.$watch('emp.empId', function(newEmpId) { if (newEmpId) { // For your original pattern: ^[empId]-\d{3}\.(xls|xlsx)$ const escapedId = escapeRegExp(newEmpId); $scope.filePattern = new RegExp(`^${escapedId}-\\d{3}\\.(xls|xlsx)$`, 'i'); // For the simpler case you mentioned: ^[empId]\.(xls|xlsx)$ // $scope.filePattern = new RegExp(`^${escapedId}\\.xls$`, 'i'); } else { // If empId is empty, set a pattern that either fails or disables validation // Here, we use a pattern that only matches empty strings $scope.filePattern = /^$/; } }); });
2. Update Your Template
Bind the dynamic filePattern to the ng-pattern attribute of your file input. You can also add validation messages to inform the user of the required format.
<div ng-app="employeeApp" ng-controller="EmployeeController"> <form name="empForm"> <label>Employee ID:</label> <input type="text" ng-model="emp.empId" name="empId" required> <label>Employee File:</label> <input type="text" ng-model="emp.empFile" name="empFile" ng-pattern="filePattern" required> <!-- Show validation error if the file doesn't match the pattern --> <div ng-show="empForm.empFile.$error.pattern && empForm.empId.$valid"> Invalid file format! It should be: {{emp.empId}}-XXX.xls or {{emp.empId}}-XXX.xlsx (XXX = 3 digits) </div> </form> </div>
Key Notes
- Dynamic Updates: The watcher ensures that every time the Employee ID changes, the validation pattern for the file input updates immediately.
- Regex Escaping: The
escapeRegExpfunction is crucial if your Employee ID might include characters that have special meaning in regex (like.or*). Without it, those characters would match any character instead of their literal value. - Validation Logic: We added
empForm.empId.$validto the error message condition so the user only sees the file format error once they've entered a valid Employee ID.
Alternative: Using a Function
If you prefer, you can use a scope function to generate the pattern instead of a watcher. This is simpler for small apps but runs on every digest cycle:
$scope.getFilePattern = function() { if (!$scope.emp.empId) return /^$/; const escapedId = escapeRegExp($scope.emp.empId); return new RegExp(`^${escapedId}-\\d{3}\\.(xls|xlsx)$`, 'i'); };
Then in your template:
<input type="text" ng-model="emp.empFile" name="empFile" ng-pattern="getFilePattern()" required>
内容的提问来源于stack exchange,提问作者Satyadharma Trivikram

