Type: bug
Ionic Version: 1.x
Platform: all
It's a duplicate of my previous issue that was closed. I'm sorry @danbucholtz for late reply, but in latest build(1.3.1) the issue still exists.
Here is pens: 1.1.1, 1.2.1, 1.3.1.
You can notice that in 1.1.x $ionicView.%%eventName%% events catchable in any controller that bound to the state, in 1.2.x its only catchable in last one. Maybe this is a bug or issue like i think but this change is not mantioned in docs. Thank you.
Hi @Kopleman,
Can you explain what your issue is in a little more detail and keep it simple?
In 1.3.1, I changed the way life cycle events work so they reliably emit (bubble up) from the correct scope. In previous releases, this was all over the map. We wrote several thousand lines of test code to verify this. I am happy to help, just want to understand when you're seeing the issue.
This is the commit with the changes and the test code.
https://github.com/driftyco/ionic/commit/d63733350b73c0084f99fe285dda96f0204b2cd7#diff-82d6d3da2a7bb1d17947d4e25aa93923
Thanks,
Dan
Hi @danbucholtz , thank you for help.I've simplified pens: 1.1.1, 1.2.1, 1.3.1.
There you will find a state app with two views in it main,menu each with its own controller - MainCtrl for main and MenuCtrl for menu, they are quite equal.
Inside each controller i want to catch $ionicView.enter ($ionicParentView.enter for 1.3.x) event.
In 1.1.1 it works as entend I mean i can catch it in both controllers. In later versions event is catchable only in one. If I understood right it depends on the position of <ion-nav-view> in DOM. Event is catchable in controller that associated with last <ion-nav-view>.
I'll hope that will be hellpfull. Thank you and sorry for my bad english skills.
I'll check it out tonight. Thanks!
Hi @Kopleman,
It might be a couple days. I am really swamped right now. I will keep you posted.
Thanks,
Dan
Hi all,
We are also having issues with the new way the events work. To our opinion it is not working as we would expect or think is understandable. Maybe someone can have a look and tell us what we are doing wrong or if something else is wrong.
I have created a CodePen, which can be found here: http://codepen.io/mark-veenstra/pen/oLLXpZ?#
To explain the situation:
$ionicView.afterLeave is FIRED from ContactController! and $ionicParentView.afterLeave is FIRED from ContactController!. Why is the $ionicParentView fired?$ionicView.afterLeave is FIRED from ContactDetailController! and $ionicParentView.afterLeave is FIRED from ContactDetailController! Why is the $ionicParentView.afterLeave fired?If you chane the ionic bundle in the CodePen to use version 1.2.1 all did work as expected.
/cc @danbucholtz
Regards,
Mark
Hi, been very busy with V2 stuff lately. I will take a look at this now.
Hi @Kopleman,
$ionicParentView.enter, etc is only for when you are broadcast events downward. In 99% of the cases, you'll want to use $ionicView.enter and have the event emit upwards.
I am looking at the way your navigation logic is structured and see some issues. The two scopes listening for the event are not in the same "hierarchy".
<ion-side-menus>
<ion-side-menu-content nav-router animation="slide-left-right">
<ion-nav-bar class="bar-positive">
</ion-nav-bar>
<ion-nav-view name="main"></ion-nav-view>
</ion-side-menu-content>
<ion-side-menu side="left" id="side-menu-left-content">
<ion-nav-view name="menu"></ion-nav-view>
</ion-side-menu>
</ion-side-menus>
The two ion-nav-views are not parents to each other. They are peers. Thus, they cannot emit events up to each other, or broadcast events down to each other. Your best bet would be listening for those two events on $rootscope, or re-designing your hierarchy.
I updated the controller logic to look like this.
.controller('MainCtrl', function($scope, $rootScope, $state) {
$scope.message = 'Foo';
$rootScope.$on('$ionicView.enter', () => {
console.log("Main Ctrl");
$scope.message += ' Bar';
});
})
.controller('MenuCtrl', function($scope, $rootScope, $state) {
$scope.message = 'Foo';
$rootScope.$on('$ionicView.enter', () => {
console.log("Menu Ctrl");
$scope.message += ' Bar';
});
})
and it works fine.
Thanks,
Dan
@mark-veenstra, looking at your issue now. I'll reply in this thread even though I closed @Kopleman's issue.
@mark-veenstra,
You found a legit bug.
$ionicParentView.enter and other parent-based life cycle events should not be used often. They are to be used exclusively when a child-view needs to know about a state change that it otherwise wouldn't be privy to knowing about since emitted events bubble up. Typically, you'll want to just use $ionicView.xyz.
Now go ahead and click "Click to go detail page" again. So we are back on that state. But now instead of using the "< BACK" we will navigate to a different tab, for example click on the third tab. Why there is now no event fired at all? Why is this different then using the back button? I would expect to see the $ionicView.afterLeave been fired
As far as the above, this is a bug. The issue is this line of code. In your case, the prefixes are not entirely the same. I need to give some thought to how to make since work nicely. Nav is _really_ complicated with ui-router.
For now, let's keep this issue open. I'll give it some thought and update when I have a solution.
Thanks,
Dan
@@mark-veenstra, how far into your app development are you? As of right now, I am honestly not sure if we can fix this easily. You may need to listen on $rootScope for the event in this case.
I'll keep thinking about it. So far, my attempts to fix have broken other tests.
Here are our changes in Ionic 1.3.1 to life cycle events. There are some pretty significant unit tests in place as you can see. We test a lot of scenarios. https://github.com/driftyco/ionic/commit/d63733350b73c0084f99fe285dda96f0204b2cd7#diff-82d6d3da2a7bb1d17947d4e25aa93923
Thanks a lot @danbucholtz.
@danbucholtz
You may need to listen on $rootScope for the event in this case.
We have tried this, but event is never fired even not when listening on $rootScope
Hi @mark-veenstra,
I figured out your issue. The details view should be app.tab.contactDetail instead of app.tab.contact.detail since app.tab.contact is not an abstract view. That's why you didn't receive the event correctly.
See the commit here with the changes I made to your project.
https://github.com/danbucholtz/ionic_6790/commit/7d5f1214d3c25a3c923baa78b15941ce01d9e248
Thanks,
Dan
Dan,
This is not how ui-router works to our opinion. I have updated the CodePen ( http://codepen.io/mark-veenstra/pen/oLLXpZ?#) and added a deeper route.
The "BACK" button needs to go back one page and not go back to the "app.tab.contact". Each dot in a route let's ui-router know that it is a child route. Therefore ui-router knows how to route back. You can also see it in the definition of the routes, where you can see that the url only get's configured with the part of the URL that is needed for that route. ui-router, resolves all the rest of the URL based on the parents etc.
So for example if you navigate to http://ui-router). If we would use your suggestion we would have issues with:
Also see next docs / videos saying you should use the dot notation:
Also our application really needs these nested routes. On each route we do a resolve of the data. If the routes are nested like we do, all the parent states are resolved also (which can be necessary for your child state).
For example also if you add some permission checking to your route, you could say on a parent route check for permission X. If permission X is not met, you can't view this state. When you hit a child state, you do not need to check this permission again, because the parent state does this check already. If you can't visit a parent, you may certainly not visit the childs or grandchilds.
I consider your finding more like a workaround for the real issue, but to our opinion it is not the correct solution.
Mark
Hi @mark-veenstra 馃槃 ,
Thanks for the detailed explanation. At this time, I don't think we're going to make any changes to the framework. Navigation is very tricky in V1, so we are hesitant to make any changes there. The solution I provided should solve the problem for you.
Thanks,
Dan
Most helpful comment
Hi @danbucholtz , thank you for help.I've simplified pens: 1.1.1, 1.2.1, 1.3.1.
There you will find a state
appwith two views in itmain,menueach with its own controller -MainCtrlformainandMenuCtrlformenu, they are quite equal.Inside each controller i want to catch
$ionicView.enter($ionicParentView.enterfor 1.3.x) event.In 1.1.1 it works as entend I mean i can catch it in both controllers. In later versions event is catchable only in one. If I understood right it depends on the position of
<ion-nav-view>in DOM. Event is catchable in controller that associated with last<ion-nav-view>.I'll hope that will be hellpfull. Thank you and sorry for my bad english skills.