2

I need to dynamically make an input field required (or not) and would like to set this value in a directive. I know there is the ng-required directive and can be set as ng-required="datamodel.required" but ultimately, I want to pull a settings object in the directive and turn on/off the required parameter based on that config. The config is in a service and I don't want to inject the service for each of my form controller - hence why I am needing to set this up in a directive.

Here is a JSFiddle starting point: http://jsfiddle.net/hm2b771z/2/

app.directive('requiredConfig', function($compile){
    return {
        link: function(scope, element, attrs){
            console.log(attrs.requiredConfig);
            console.log(attrs.ngRequired);
            attrs.ngRequired = (attrs.requiredConfig == "true") ? true : false;
            $compile( element.contents() )( scope );
            console.log(attrs.ngRequired);
            console.log('_______________________');
        }
    }
});

What I expect is the field that is the first field option to be required while the second one remains optional.

Thanks!

snazzyHawk
  • 45
  • 1
  • 7
  • Found my answer here: http://stackoverflow.com/questions/21687925/angular-directive-how-to-add-an-attribute-to-the-element – snazzyHawk Nov 24 '14 at 04:25
  • 2
    If your questions is a duplicate, I suggest deleting it. Otherwise, it's better to answer your own question with how you would want someone else to answer it for you. (i.e. not just with a link) – New Dev Nov 24 '14 at 04:53

2 Answers2

0

Instead of

attrs.required = (attrs.requiredConfig == "true") ? true : false;

Use

if (attrs.requiredConfig == "true"){
    element.attr('required', 'true');
}
SM Adnan
  • 555
  • 2
  • 10
0

Here's what I ended up doing thanks to Angular directive how to add an attribute to the element?:

angular.module( 'app' )
.directive
(
    'requiredByConfig',
    function( $compile, Utils ){
        var directive = {
            terminal: true,
            priority: 1001,
            compile: function( element, scope ){
                var configKey = element.attr( 'required-by-config' );
                var req = Utils.getRequiredFromConfig(configKey) // Injected;

                // Remove this directive in order to avoid infinite compile loop.
                element.removeAttr( 'required-by-config' );

                // Add the required directive with the required value.
                element.attr( 'ng-required', req );

                // Compile the new directive
                $compile( element.contents() )( scope );

                var fn = $compile( element );
                return function( scope ){
                    fn( scope );
                };
            }
        };

        return directive;
    }
);

However, a much better solution was to use a filter:

angular.module( 'app' ).filter
( 'requiredByConfig',
    function( Utils ){
        return function( initialValue, configKey, visible ){
            if( angular.isDefined( visible ) && !visible ){
                // If the input is hidden, we don't want to require it.
                return false;
            }

            // Get the config setting. If available, overwrite the default.
            if( angular.isDefined( Utils.SETTINGS[ configKey ] ) ){
                // A config exists for this field. Return the value of the config.
                return Utils.getBoolean( Utils.SETTINGS[ configKey ] );
            } else {
                // Return the initial required value
                return initialValue;
            }
        }
    }
)
Community
  • 1
  • 1
snazzyHawk
  • 45
  • 1
  • 7