4

So I have a SPA using AngularJS/UI-Router and I have a section where I need to change states from a select/option. I originally had links in an ng-repeat like this:

<ul class="unstyled">
    <li data-ng-repeat="course in courses">
        <a data-ui-sref=".materials({ courseCode:course.CourseCode })">{{course.Title}}</a>
    </li>
</ul>

The issue is that I am going to have upwards of 50 different courses to choose from, so I want to put them into a select/option setup something like this:

<select style="padding:3px 1px; width:100%;" data-ng-model="placeholder" data-ng-options="course.Title for course in courses track by course.CourseCode"></select>

Now, I know I can change the scope with the above by setting up an ng-repeat and just using that ng-model="placeholder", but I need the ability to change states from that select/option. Basically, I have a check that occurs on state change that will either deny or allow access based on a permissions check. If I can do the permissions check from this state, I am more than open to that as an option, but it seemed easier to switch states and do the check on that.

As always, thank you in advance!

Edit: So I looked some more into this and found that I might be able to do something with ng-switch and UI-Router's $state.go. Here is what I have come up with so far:

The controller:

.controller('CoursesTrackCtrl', function ($scope, $stateParams, $http, $log, $state) {
    $scope.changeState = function (course) {
        $state.go('.materials({ courseCode:course.CourseCode })');
    }
});

The state with the select:

<select style="padding:3px 1px; width:100%;" data-ng-model="course" data-ng-options="course.Title for course in courses" data-ng-change="changeState(course)">
    <option value="">-- Select a Course --</option>
</select>

I am getting an undefined is not a function when I change the option in the select menu. I can get an alert to pop and pass through pieces of the courses so I know that course is being passed through the scope just fine. I made sure that $state had been added to the controller, but it seems like $state.go isn't going anywhere and I am still not even sure if that would be the correct syntax to actually pass through $stateParams like I would with a normal ui-sref.

Solution:

With the help of David Spence, I was able to solve the error I was having. I was both injecting $state into the controller and using it as a parameter so it was throwing an error. Thank you!

As for the solution, this was the final section of code for the controller:

.controller('CoursesTrackCtrl', function ($scope, $stateParams, $http, $log, $state) {
    $scope.changeState = function (course) {
        $state.go('courses.track.materials', { courseCode: course.CourseCode });
    }
});

The big change here was the syntax for $state.go, which needed to resolve the full path of the state (courses.track.materials vs. just .materials) and the syntax for the parameters differed from the normal ui-sref syntax so it had to be setup as a { parameter : value }.

And for the state itself:

<select style="padding:3px 1px; width:100%;" data-ng-model="course" data-ng-options="course.Title for course in courses" data-ng-change="changeState(course)">
    <option value="">-- Select a Course --</option>
</select>

This had been mostly unchanged, but the big thing was to ensure that course was being passed through the scope.

Hope this helps someone else too!

1 Answer 1

1

The only thing I can see that is wrong is that $state is being passed as a parameter the changeState method instead of being injected into the controller. See example below without any errors. Just check the state name is correct you are changing to. Looks a bit odd the way it starts with a dot...

function BasicController($scope) {

    $scope.changeState = function(course) {
        console.log(course.Title);
        // todo: transition!
    }

    $scope.courses = [{
        Title: 'maths'
    }, {
        Title: 'science'
    }];

}

DEMO

Sign up to request clarification or add additional context in comments.

2 Comments

The syntax for state.go is different that if you're using ui-sref on an anchor. Instead, the first parameter is the state name and the second are the parameters. In your case, something like: $state.go('.materials', { courseCode: course.CourseCode });. Check the docs and does your state name really begin with a dot?
You're the man. I just posted a full answer above, but I will credit you since that is exactly what I ended up doing. Thank you for your help!

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.