Compiling modal window content in AngularJS can lead to the creation of controllers that are left disconnected

I implemented a modal window triggered by fancybox in my project. Once the modal is displayed, fancybox triggers a "modalShown" event that is listened for by AppController. In this listener, $compile is called on the modal content to create the ModalController, interpolate, and bind events on the view.

However, I'm facing an issue where even after closing the modal, the modal element is removed from the DOM but its bound ModalController instance remains somewhere in the app. Consequently, every time a new modal is opened, a new controller is created, leading to multiple orphaned controllers responding to events within the modal window.

My main concern is regarding cleaning up these unused controllers scattered throughout my application, as $compile doesn't provide a reference to the newly created controller.

Snippet of relevant code (written in CoffeeScript)...

Fancybox Directive

# Setting up fancybox on elements triggering the modal...
# <a href="#" fancybox="templateToLoad.html">Trigger Modal</a>
@app.directive 'fancybox', ["$templateCache", "$compile", ($templateCache, $compile) ->
  (scope, element, attrs) ->
    options =
      afterShow : ->
          scope.$root.$broadcast 'modalShown', scope
    element.fancybox options

modal.html

<div class="fancybox-skin">
  <div class="fancybox-outer">
    <div class="fancybox-inner ng-scope">
      <div ng-controller="ModalController" style="..." class="ng-scope">
        <a href="#" ng-click="someAction()">Some Action in ModalController</a>
      </div>
    </div>
  </div>
</div>

ModalController

app.controller 'ModalController', [
  '$scope', '$rootScope',($scope, $rootScope) ->

    # Tracking controllers for debugging
    window.globalCounter ||= 0
    $scope.localCounter = window.globalCounter++

    someAction = () ->
        console.log 'action'

AppController

@app.controller "AppController", [
  "$scope", "$rootScope", "$compile", ($scope, $rootScope, $compile) ->
       $scope.$on 'modalShown', (e, localScope) ->
            console.log('compiling modal contents')
            $compile($('.fancybox-inner'))(localScope)
            $rootScope.$apply() 

Answer №1

The role of the ModalController is simply to initialize functions on its corresponding $scope, then fade into the background. Any lingering functionality may be residing on the scope or leaking from the controller, requiring cleanup within a

$scope.$on('$destroy', function() { ... })
block.

If functionalities are tied to $watch or $on events in the scope, Angular should handle cleanup automatically upon scope destruction. Persistence indicates that the modal closure did not trigger scope destruction.

By passing in the parent scope manually via

$compile($('.fancybox-inner'))(localScope)
, using localScope.$new() allows for safe execution of .$destroy() on the new scope post-modal closure.

In addition, consider consolidating AppController features into your fancybox directive to avoid broadcasts altogether. Directives provide a more seamless environment for DOM manipulations and compilations, offering better scope management for any new scopes required.

Similar questions

If you have not found the answer to your question or you are interested in this topic, then look at other similar questions below or use the search

Having difficulties parsing JSON data in JavaScript

So I've got this script embedded in my HTML code $(document).ready(function() { type :'GET', url :'MapleLeafs2011.json', dataType :'json', success :processTeam, error :function() { alert(&apo ...

What is preventing targeting a class in React?

I'm having trouble targeting className in react. I attempted to target it using div className="navbar"> and .navbar { align-items: center; } but it's not working. div{ display: block; background-color: rgb(211, 57, 57); ...

decoding json field containing forward slashes using javascript

Seems easy enough, but I'm having trouble figuring it out. let data="[{name:\"House\",id:\"1\"},{name:\"House and Land\",id:\"5\"},{name:\"Land\",id:\"6\"},{name:\"Terrace\",id:&bs ...

Automatically save changes to the database using angular and Node.js

I am currently in the process of transitioning an MS Access database to a web application. My tech stack includes Angular JS, Node JS with express framework, and MySQL as the database. One unique feature of MS Access is that any edits made take effect ins ...

Issue: Unable to set headers after they have been sent while using express-fileupload in the application

app.post('/profile', function(req, res) { // save file if (req.files) { let sampleFile = req.files.sampleFile; sampleFile.mv('/somewhere/on/your/server/filename.jpg', function(err) { if (err) ...

A fresh perspective on incorporating setInterval with external scripts in Angular 7

Incorporating the header and footer of my application from external JavaScript files is essential. The next step involves converting it to HTML format and appending it to the head of an HTML file. private executeScript() { const dynamicScripts = [this.app ...

JavaScript quiz featuring randomized questions with selectable radio buttons

I need assistance in creating a feature on my webpage where users can select the number of questions they want to answer (ranging from 1 to 10). The selected number of questions should then be displayed randomly, without any duplicates. I am not very famil ...

Ways to transfer a value from ng-Init to the following controller

Upon loading the Index page, a userName is retrieved. Controller Action in MVC public ActionResult Index() { string userName = "Current User" return View((object)userName); } Subsequently, an attempt is made to store this value using ng-init. Ind ...

Transform your .obj files into .glb files effortlessly with npm and Laravel

I've hit a roadblock for 2 days now and can't seem to find a solution. Could someone lend me a hand with this? Query: What's the best way to convert a .obj file to .glb? I attempted using obj2gltf npm package but integrating it with Larav ...

Breaking down an Express app into modules: incorporating a function, a class, and req.pipe

Below are two servers and two gqlServers, each with different functionalities. All combinations of them work. The task at hand is to enhance express with predefined code patterns that can be shared across various apps through additional methods. What com ...

Guide on incorporating typed components into module federation in React

I've been encountering an issue with setting the type of a custom component exposed through Webpack module federation. Though I have successfully exposed and used the component, Typescript is flagging an error regarding its type. The situation invol ...

Problem with the "md-open-on-focus" behavior in the Angular-Material's "md-datepicker" directive

When testing the functionality of the fiddle, an inconsistency issue was observed with multiple openings of the md-datepicker while using md-open-on-focus. The problem arises after the first successful opening and closing - subsequent attempts to open it ...

The attempt to perform a Diffie-Hellman key exchange between Python and Node has hit a roadblock, as an error stating that

Currently, I am attempting to establish a DH key exchange between a Python 3.6 client and a Node server deployed in a Docker container with the latest node image (Node version: v13.10.1). On the client side, I am utilizing the cryptography.io library (v2. ...

Accessing configuration properties from a JavaScript file in AngularJS version 1.5.X

Looking to retrieve configuration values based on environment. The config.js file contains the following entries: config.js: baseUrl='/home', abcUrl='/abc' I am attempting to access the baseUrl and abcUrl within one of my services us ...

Is it possible for a JWT generated using RS256 to be decoded on the jwt.io platform?

After setting up my first Express server and implementing user authentication with jwt, I'm now searching for a method to encrypt the jwt in order to prevent users from viewing the payload on the website. I am curious if anyone is aware of an encryp ...

Adjusting the label on the Formik toggler

I have successfully implemented a switcher using Formik that changes the label accordingly with a boolean value. However, I now need to make the label reflect a string value instead of just "true/false." For example, I want it to display "Text1/Text2" inst ...

Updating attribute values with jQuery

How do you use jQuery to change the attributes ng-click and Create to Update of the following HTML element? <a class="btn pull-right btn-link" ng-click="create()" ng-class="{'btn-link-disabled':isSaveAndContinue,'btn-link':!isSaveAn ...

Save the webpage source code to a file using JavaScript and Grunt

I am facing an issue and need assistance with my project. I have developed an app using GruntJs and now I need to download the source code of a webpage using GruntJs. For instance, let's assume I have a webpage at: example.com/index.html. What I wou ...

The React Modal component seems to be malfunctioning within the context of Nextjs

Out of the blue, this issue popped up and I'm puzzled about why it's happening. I have two modals (with different names) that are identical in structure but only one is functioning properly. Both modals use the React-Modal library. The first moda ...

Can a Unicode character be overwritten using a specific method?

Is there a way to display a number on top of the unicode character '♤' without using images? I have over 200 ♤ symbols each with a unique number, and using images would take up too much space. The characters will need to be different sizes, a ...