NativeScript / nativescript-angular

Integrating NativeScript with Angular
http://docs.nativescript.org/angular/tutorial/ng-chapter-0
Apache License 2.0
1.21k stars 241 forks source link

ngOnInit not running in a modal component until interacting with modal #1014

Closed vcooley closed 7 years ago

vcooley commented 7 years ago

I have run into a problem where I am trying to display inputs for a form on a modal component. I have not been able to reproduce this in a sample app, and I'm not quite sure why.

In my code, I am instantiating a form whose content I am displaying statically as text, then I have button that can be tapped in order that the content may be edited. I am passing a reference to the form through the context object which I am attaching to the modal params.

When I tap the button to open the modal, it opens and I see empty TextFields. When I put a log into the ngOnInit, it does not show anything, which indicates that it does not run properly.

When I do eventually tap a TextField, all of the data is displayed in all of the fields as I expect to happen on load. At this time the log in ngOnInit shows in my console.

Please let me know if any more information is required or if anyone else has run into this issue.

tsonevn commented 7 years ago

Hi @vcooley,

Thank you for the provided description on the problem. I investigated it and was unable to recreate an issue with the execution of ngOnInit event. For testing, I used nativescript-sdk-example-ng project and the example with the modal page. To verify, whether the event is executed I set up an alert. As you could see in the GIF files, the event is executed properly.

Regarding that, could you provide some more info about your environment(NativeScript CLI, nativescript-angular, tns-core-modules version)? Also, it would help if you could provide a sample project or at least the code for the modal page. screencast 2017-09-29 at 10 27 40 am screencast 2017-09-29 at 10 28 22 am

vcooley commented 7 years ago

@tsonevn I have also tried to replicate this issue to no avail, and I'm not really sure where to start as far as isolating the problem. I have tried removing as much as possible from both the parent page and the modal, and I am still facing this issue.

I am using tns-cli 3.2.0 and here is my package.json:

{
  "description": "NativeScript Application",
  "license": "SEE LICENSE IN <your-license-filename>",
  "readme": "NativeScript Application",
  "repository": "<fill-your-repository-here>",
  "nativescript": {
    "id": "org.nativescript.sample",
    "tns-ios": {
      "version": "3.1.0"
    },
    "tns-android": {
      "version": "3.1.0"
    }
  },
  "scripts": {
    "lint": "tslint 'app/**/*.ts?(x)'",
    "test.ios": "tns test ios",
    "test.android": "tns test android",
    "config.dev": "gulp config:development",
    "config.prod": "gulp config:production"
  },
  "dependencies": {
    "@angular/animations": "~4.2.0",
    "@angular/common": "~4.2.0",
    "@angular/compiler": "~4.2.0",
    "@angular/core": "~4.2.0",
    "@angular/forms": "~4.2.0",
    "@angular/http": "~4.2.0",
    "@angular/platform-browser": "~4.2.0",
    "@angular/platform-browser-dynamic": "~4.2.0",
    "@angular/router": "~4.2.0",
    "card-validator": "^4.1.0",
    "chai": "^3.5.0",
    "chai-as-promised": "^6.0.0",
    "codelyzer": "^3.0.0-beta.4",
    "crypto-js": "^3.1.9-1",
    "datasets-us-states-names": "^1.0.0",
    "datasets-us-states-names-abbr": "^1.0.0",
    "fuzzball": "^0.13.1",
    "lodash": "^4.17.4",
    "nativescript-advanced-webview": "^1.1.3",
    "nativescript-angular": "~4.2.0",
    "nativescript-async": "^1.0.2",
    "nativescript-drop-down": "^3.1.0",
    "nativescript-floatingactionbutton": "^3.0.0",
    "nativescript-geolocation": "^3.0.0",
    "nativescript-iqkeyboardmanager": "^1.1.0",
    "nativescript-plugin-firebase": "^4.0.6",
    "nativescript-telerik-ui-pro": "^3.0.3",
    "nativescript-theme-core": "^1.0.4",
    "nativescript-unit-test-runner": "^0.3.4",
    "nock": "^9.0.13",
    "reflect-metadata": "~0.1.8",
    "rxjs": "~5.4.3",
    "squel": "^5.8.0",
    "tns-core-modules": "~3.1.0",
    "tslib": "^1.6.1",
    "zone.js": "~0.8.10"
  },
  "devDependencies": {
    "@angular/language-service": "~4.2.0",
    "@types/jasmine": "^2.5.47",
    "@types/lodash": "^4.14.74",
    "babel-traverse": "6.24.1",
    "babel-types": "6.24.1",
    "babylon": "6.17.0",
    "chai": "^3.5.0",
    "del": "^2.2.2",
    "gulp": "^3.9.1",
    "gulp-mocha": "^4.3.1",
    "gulp-shell": "^0.6.3",
    "jasmine": "^2.5.3",
    "karma": "^1.5.0",
    "karma-chai": "^0.1.0",
    "karma-jasmine": "^1.1.0",
    "karma-junit-reporter": "^1.2.0",
    "karma-mocha": "^1.3.0",
    "karma-nativescript-launcher": "^0.4.0",
    "karma-sinon": "^1.0.5",
    "karma-spec-reporter": "0.0.30",
    "lazy": "1.0.11",
    "mocha": "^3.2.0",
    "mocha-jenkins-reporter": "^0.3.7",
    "mocha-typescript": "^1.0.23",
    "nativescript-dev-android-snapshot": "^0.*.*",
    "nativescript-dev-typescript": "~0.4.2",
    "q": "^1.5.0",
    "sinon": "^2.1.0",
    "tns-platform-declarations": "^3.0.1",
    "tslint": "^4.5.1",
    "typescript": "~2.4.2",
    "vinyl-paths": "^2.1.0",
    "wd": "^1.2.0"
  }
}
tsonevn commented 7 years ago

Hi @vcooley, I am attaching sample project, which I used for testing and you could use it as starting point. Please review it and verify, what are the differences between the both projects. You could also make the needed changes in the sample, which will allow us to recreate this behavior on our side.

Archive.zip

coolgoel22 commented 6 years ago

I am also facing the same issue. Until i interact with any of the input field, ngOnInit is not getting executed. Because of this it seams like change detection is not working.

I am attaching the package.json file for your reference.

package.json { "name": "gavyasidh-guide", "version": "0.0.0", "license": "MIT", "scripts": { "ng": "ng", "start": "ng serve", "build": "ng build --prod", "test": "ng test", "lint": "ng lint", "e2e": "ng e2e" }, "private": true, "dependencies": { "@angular/animations": "^5.2.11", "@angular/common": "^5.2.11", "@angular/compiler": "^5.2.11", "@angular/core": "^5.2.11", "@angular/forms": "^5.2.11", "@angular/http": "^5.2.11", "@angular/platform-browser": "^5.2.11", "@angular/platform-browser-dynamic": "^5.2.11", "@angular/router": "^5.2.11", "@ionic-native/camera": "^4.8.0", "core-js": "^2.5.7", "font-awesome": "^4.7.0", "nativescript-advanced-webview": "^1.1.3", "nativescript-angular": "~4.2.0", "nativescript-async": "^1.0.2", "ng2-order-pipe": "^0.1.5", "ng2-search-filter": "^0.4.7", "ngx-cookie-service": "^1.0.10", "reflect-metadata": "~0.1.8", "rxjs": "^5.5.11", "zone.js": "^0.8.26" }, "devDependencies": { "@angular/cli": "~6.0.8", "@angular/compiler-cli": "^5.2.11", "@angular/language-service": "^5.2.11", "@types/jasmine": "^2.8.8", "@types/jasminewd2": "~2.0.2", "@types/node": "^6.0.113", "codelyzer": "^4.4.1", "jasmine-core": "~2.8.0", "jasmine-spec-reporter": "~4.2.1", "karma": "^2.0.4", "karma-chrome-launcher": "~2.2.0", "karma-coverage-istanbul-reporter": "^1.4.3", "karma-jasmine": "^1.1.2", "karma-jasmine-html-reporter": "^0.2.2", "nativescript-dev-android-snapshot": "^0..", "protractor": "~5.1.2", "ts-node": "~4.1.0", "tslint": "~5.9.1", "typescript": "~2.5.3", "@angular-devkit/build-angular": "~0.6.8" } }

tsonevn commented 6 years ago

HI @coolgoel22, Try to upgrade all dependencies to the latest available ones, while following the below-attached sample package.json file.

{
    "description": "NativeScript Application",
    "license": "SEE LICENSE IN <your-license-filename>",
    "readme": "NativeScript Application",
    "repository": "<fill-your-repository-here>",
    "nativescript": {
        "id": "org.nativescript.testtt"
    },
    "dependencies": {
        "@angular/animations": "~6.0.0",
        "@angular/common": "~6.0.0",
        "@angular/compiler": "~6.0.0",
        "@angular/core": "~6.0.0",
        "@angular/forms": "~6.0.0",
        "@angular/http": "~6.0.0",
        "@angular/platform-browser": "~6.0.0",
        "@angular/platform-browser-dynamic": "~6.0.0",
        "@angular/router": "~6.0.0",
        "nativescript-angular": "~6.0.0",
        "nativescript-theme-core": "~1.0.4",
        "reflect-metadata": "~0.1.8",
        "rxjs": "~6.1.0",
        "tns-core-modules": "~4.1.0",
        "zone.js": "^0.8.26"
    },
    "devDependencies": {
        "nativescript-dev-typescript": "~0.7.0",
        "typescript": "~2.7.2"
    }
}

Then delete node_modules, platforms and hooks folders and rebuild the app again. If the issue persists, please send us sample project, which can be used for debugging.

erkanarslan commented 6 years ago

I also have this problem.

I show a modal after an http request when app starts. When I put the app to background and bring it back to foreground, I send another http request and then show the data in the modal. In the first one it works nicely. However, after putting app to background and bringing back to foreground ngOnInit is not called until I touch a button on the modal. I have nativescript 4.1. It is very hard to find why I get this behavior.

erkanarslan commented 6 years ago

I solved the problem.

In my case, I was trying to open the modal when app comes back from background. I listen to lifecycle events of the nativescript. However, those events aren't a part of Angular and Angular cannot know I am changing something related to itself in this case. To notify Angular, I run my code in a zone like this:


constructor(
    private zone : NgZone
) {}

ngOnInit() {
    this.appResumed.subscribe(() => {
        this.zone.run(() => {
            // code goes here
        });
    });
}

appResumed is a subject that notifies when app comes to foreground.

joshcomley commented 5 years ago

I am experiencing this issue with the latest NS packages installed. All my modals do not fire ngOnInit (or any lifecycle event), and the only hack I can get is to set a timeout with [ChangeDetectorRef].detectChanges().

joshcomley commented 5 years ago

After some investigation I have found that the lifecycle hooks are tiggered when and only when the ViewContainerRef used is the root one. As such I use a service to track the root ViewContainerRef (configured in app.component.ts) and then use that whenever I am instantiating a modal.

But this is a workaround, and I'm sure the bug lies somewhere in nativescript-angular, so I'd recommend re-opening this issue.

I have found this issue to be consistent across multiple projects.

jnorkus commented 5 years ago

Please reopen. Whenever a modal is instantiated using a child vcRef, change detection does not work.

tsonevn commented 5 years ago

Hi @jnorkus, Can you provide a sample project, which demonstrates the issue, you are facing?

jnorkus commented 5 years ago

@tsonevn I think it's best to move on to this issue: https://github.com/NativeScript/nativescript-angular/issues/1217

With earlier version of Angular the vcRef was the only change detection problem with modals. With latest Angular change detection doesn't work at all when app.component is set to ChangeDetectionStrategy.OnPush, no matter what vcRef is used.

joshcomley commented 5 years ago

This is still an issue, almost one year on

luiswill commented 4 years ago

Still an issue with Nativescript "nativescript-angular": "~8.21.0", and "@angular/compiler-cli": "~8.2.0",

My question on StackOverflow : https://stackoverflow.com/questions/61579251/data-binding-not-working-when-opening-modal-in-side-navigation-template-nativesc/61580050#61580050

Workaround is detecting manually changes.

houssammehdi commented 4 years ago

How is this still an issue... ngOnInit doesn't run before interacting with textfield. Running all latest versions.

gwhi94 commented 4 years ago

Still an issue, had to workaround by calling setTimeout(() => { this.zone.run(() => this.myFunc()) });

and then placing all my code that I need to run onInit inside of myFunc()

andrewm-mitchells commented 3 years ago

Has this ever been fixed? I'm experiencing the same symptoms in my app. I have multiple blocks in the modal that I show/hide on a button tap and the last step has a countdown from 5 to 0 that is not showing up on the page unless I interact with the view (swipe up/down a bit).

Adar-Dagan commented 2 years ago

This is still an issue. Why is it marked as closed?

Javarome commented 1 year ago

Had the same issue (ngOnInit or other callbacks were not called until I pressed some key) and only NgZone.run(whatIWantedToDoInNgOnInit) could workaround it. Note that this occurred is a pure Angular app, so I don't think the issue is NativeScript-specific.

Mmoks commented 1 year ago

@Adar-Dagan @Javarome I faced with the same issue only when I provided viewContainerRef in MatDialogConfig. I resolved that issue by providing Injector in injector field instead of viewContainerRef

edusperoni commented 1 year ago

@Mmoks what version are you using? Are you by any chance opening a modal inside a OnPush component?

More often than not you don't need to specify a viewContaineRef, but if you need providers not in root then you might need to specify the injector. Specifying the viewContaineRef will make the angular view live hierarchically inside that vcRef (meaning it'll be change detected when that vcRef is CDed), so things like OnPush will prevent CD to happen, whereas passing the injector will render that modal in the root (attached directly to ApplicationRef, a sibling to your AppComponent). This should be all documented under the new Dialog (NativeDialogService) API.

Mmoks commented 1 year ago

@edusperoni thanks for the explanation, now that behaviour makes sense for me!