Solved

Getting object from parent window, top frame, or opener.

Posted on 2010-09-15
10
1,146 Views
Last Modified: 2013-12-08
I have an application which involves a lot of scripting. The application opens other windows (in new tabs or new windows) as well.
I want to create a 'global' object in the main window, and reuse that object in every window being opened from the main window.

I created an object in the main window which will have a reference of all other windows being opened.
The object itself holds a lot of other information (like translations which are get via a handler), methods and controls. (See the code snippet.)

The newly opened windows will have this piece of code (except for creating the object if it cannot be found (I want to load it via external js library, but for now to have a mere understanding of what I want to achieve, I included it in the snippet)).

So every window will get the main object from the parent window, top frame, the window which opened a modal dialog, etc.
And every window will register itself in that object by : MainObject.Windows.Add(top);

All works well, I know exactly what window I have open, if I have a new translation in one of the (many) opened 'child windows', it will be available in the global object and thus in every child window. Exactly what I wanted.

But I have one problem; it happens in IE (which is (unfortunately) the target to build this for) and it is as follows.

From the main window I click a link which opens a new tab and in that 'child-window' I have the MainObject available.
Now when I want to have a new instance of lets say the DummyObject, the statement is :

var dummyObject = new MainObject.UI.Controls.DummyObject();

Open in new window


I get the following error : Invalid procedure call or argument.
In FireFox I have no problem.

Any ideas of what can be wrong?
Advice on how to handle such thing is very welcome as well !

Thanks in advance...
(function (window) {
	var MainObject;

	if (top == self && typeof (MainObject) == "undefined") {
		if (window.dialogArguments && window.dialogArguments.MainObject)
			window.MainObject = window.dialogArguments.MainObject;
		else if (window.opener != null && typeof (window.opener) == "object")
			window.MainObject = window.opener.MainObject;
		else {
			// Create the main object (TODO load external js library)
			MainObject = {
				Tools: {
					Translate: function (resource) {
						if (typeof (MainObject.Tools.Translations[resource]) == "undefined") {
							var trans = $.ajax({ url: "/Shared/Handlers/Translate.ashx?resource=" + resource, async: false, cache: false }).responseText;
							// replace \n as text with \\n
							MainObject.Tools.Translations[resource] = trans.replace(/(\\n)/g, "\n");
						}
						return MainObject.Tools.Translations[resource];
					},
					Translations: {}
				},
				UI: {
					Controls: {
						DummyObject: function () {
							this.Dummy = "";
						}
					}
				},
				Windows: {
					Windows: [],
					Add: function (win) {
						MainObject.Windows.Windows.push(win);
					},
					Delete: function (win) {
						if(typeof (win) != "object")
							win = MainObject.Windows.Windows[win];

						for (var x = this.Windows.length - 1; x >= 0; x--) {
							var w = this.Windows[x];
							if (w == win) {
								MainObject.Windows.Windows.splice(x, 1);
								break;
							}
						}
					},
					Close: function (win) {
						if (typeof (win) != "object")
							win = MainObject.Windows.Windows[win];

						var oWin = win.open(win.location.href, '_top');
						oWin.close();
					},
					Focus: function (win) {
						if (typeof (win) != "object")
							win = MainObject.Windows.Windows[win];

						win.focus();
					}
				}
			};
			window.MainObject = MainObject;
		}
	} else
		window.MainObject = top.MainObject;
})(window);

Open in new window

0
Comment
Question by:Albert Van Halen
  • 6
  • 3
10 Comments
 
LVL 75

Expert Comment

by:Michel Plungjan
ID: 33689417
Well, the first thing that springs to mind is that you may pass an incomplete object

Can you debug a little:

alert(window.dialogArguments); // should alert [OBJECT]
if (window.dialogArguments && window.dialogArguments.MainObject)
  alert(window.dialogArguments.MainObject); // should alert something too
                    window.MainObject = window.dialogArguments.MainObject;

Also try IE8's built-in debugger or add script debugger to IE6/7 if that is where you have the issue
            
0
 
LVL 75

Expert Comment

by:Michel Plungjan
ID: 33689422
Ah

try


UI: {
  Controls: {
    DummyObject: function () {
      this.Dummy = "";
      return this.Dummy;
    }
  }
},

Open in new window

0
 
LVL 19

Author Comment

by:Albert Van Halen
ID: 33690806
Hi michel

Try what, return the property ? That doesn't help (tried it)
I do have the MainObject in my child window; the only thing I cannot do (from within IE) is the following
var d = new MainObject.UI.Controls.DummyObject() - it fails with the error I mentioned...

But consider this
[code]
UI: {
  Controls: {
    NewDummyObject : function() { return new this.DummyObject(); },
    DummyObject: function () {
      this.Dummy = "";
      return this.Dummy;
    }
  }
}
[/code]

Now if I state
var d = MainObject.UI.Controls.NewDummyObject();
all goes well.

Still haven't got a clue...
0
Gigs: Get Your Project Delivered by an Expert

Select from freelancers specializing in everything from database administration to programming, who have proven themselves as experts in their field. Hire the best, collaborate easily, pay securely and get projects done right.

 
LVL 75

Expert Comment

by:Michel Plungjan
ID: 33691023
d = new somethingThatReturnsAnObject();
d = somethingThatDoesSomethingAndReturnsSomethingOrNot

is what I expect

Your dummy function sets "this" which is in the main object and not in the function
0
 
LVL 19

Author Comment

by:Albert Van Halen
ID: 33695339
Ok

Please check the following files.
1 js file which is a short version of the main object and 2 html pages :
MainWindow.html is the 'main' page in which the object is being created. It has a link in it which opens the second window page.
SecondWindow.html is the page in which the object is set via window.opener, thus referencing the object from the main window.

In both windows a new instance of the DummyObject is being created and the description is being alerted either by getting the Description property and executing the Ask method.

Please open the MainWindow.html; see that the object is being created, a new instance of the DummyObject is created and it alerts the Description.
Click on the link that opens the child window. See that there is no alert that the object is being created and that there is an alert of the DummyObject instance.

See that everything works in at least FireFox but fails in IE.

Note that setting this.Description in the DummyObject function is set in the DummyObject not the main object.
MainWindow.html
SecondWindow.html
MainObject.js
0
 
LVL 75

Expert Comment

by:Michel Plungjan
ID: 33695614
I will have to do this tomorrow. I only have Macs at home
0
 
LVL 75

Expert Comment

by:Michel Plungjan
ID: 33956561
I think you need to consider this kind of construct (could not make it work immediately)



(function (window) {
  if (top == self && typeof (MainObject) == "undefined") {
    if (window.dialogArguments && window.dialogArguments.MainObject) {
      return window.dialogArguments.MainObject;
    }
    else if (window.opener != null && typeof (window.opener) == "object") {
      return window.opener.MainObject;
    }
    else {
      // Create the main object (TODO load external js library)
      return {
        UI: {
          Controls: {
            DummyObject : function () {
              this.Description = "I'm a dummy object";
              alert('called');
              this.Ask = function() {
                return this.Description;
              }
            }
          }
        }
      };
    }
  } else
    return top.MainObject;
})(window);

Open in new window

0
 
LVL 75

Accepted Solution

by:
Michel Plungjan earned 500 total points
ID: 33964371
Please feel free to delete this.
I do not want a "C" grade.

Thanks
0
 
LVL 19

Author Closing Comment

by:Albert Van Halen
ID: 33987426
Well here you are...
No solution really; IE is still trouble...
0

Featured Post

Live: Real-Time Solutions, Start Here

Receive instant 1:1 support from technology experts, using our real-time conversation and whiteboard interface. Your first 5 minutes are always free.

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

I recently found myself in a Corporate Situation where the client had requested blocking access to any and all websites except his own Domain? Easy? I am sure this would be your answer but their requirement was, this has to be done without using…
SSL stands for “Secure Sockets Layer” and an SSL certificate is a critical component to keeping your website safe, secured, and compliant. Any ecommerce website must have an SSL certificate to ensure the safe handling of sensitive information like…
This Micro Tutorial will demonstrate how nuggets on the Web are formatted by using Chrome Developer Tools. These tools would not only view the site's CSS but it can also modify it and save the CSS to use on your own site.
How to create a custom search shortcut to site-search Experts Exchange using Google in the Firefox browser. This eliminates the need to type out site:experts-exchange.com whenever you want to search the site. Launch your Bookmark Menu: Press 'Ctrl +…

813 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question

Need Help in Real-Time?

Connect with top rated Experts

8 Experts available now in Live!

Get 1:1 Help Now