/****************************************
   Frame tree structure display script
written by Mark Wilton-Jones 19-21/6/2002
*****************************************

Please see http://www.howtocreate.co.uk/jslibs/ for details of this script
Please see http://www.howtocreate.co.uk/jslibs/termsOfUse.html for terms of use

This script displays the full structure of even the most complicated framesets.
Unlike many scripts of its type, it will display the name of the frame to help
diagnose targetting problems. Also, it is possible to specify a subset of the
frameset to show the structure for.

The structure is shown in an output window that will update every time a new page
is loaded (if that page is set up as shown below).

To use:
_______________________________________________________________________________________

Inbetween the <head> tags of all pages contained within framesets, put:

	<script src="PATH TO SCRIPT/frametree.js" type="text/javascript" language="javascript1.2"></script>
	<script type="text/javascript" language="javascript1.2"><!--
dumpFrameTree( REFERENCE_TO_A_FRAME_OR_WINDOW_USUALLY_window.top, true );
	//--></script>

The second argument is optional. If specified, errors or warning will be displayed in the
status bar and as an alert. If it is not specified, no alerts will be given, but errors
and warnings will still be displayed in the status bar.
_______________________________________________________________________________________

Notes on bugs:

Many browsers will fail to give access to a frame whose only content is, for example,
an image or a flash animation. Most will not give access to a page from a different
domain. Even attempting to access these will cause JavaScript errors. There is no way
to detect if an error will occur first. This script calmly deals with errors,
displaying a warning and showing in the structure window where the error occurred.
Further structure cannot be displayed.

Some versions of Netscape 4 will display a blank output window (because of bugs in the
browser) when the frameset is loaded. When a page is changed in the frameset, the output
window will display properly if the page is set up as shown above.
_______________________________________________________________________________________*/

function dumpFrameTree( oOb, alWarn ) {
	if( !window.oWinOut ) {
		//topmost frame, setup the output window
		if( !oOb || !oOb.location || !oOb.navigator ) { window.defaultStatus = 'Non-fatal error: Frame Tree Script was not passed a valid window object.'; if( alWarn ) { alert( window.defaultStatus ); } return; }
		window.defaultStatus = ''; window.onfalWarn = alWarn; window.frameNameList = ['_blank','_self','_parent','_top','_media','_search','_content'];
		window.onerror = function () {
			//handle 'access denied' errors caused by browser security or handling of non-HTML frames
			oWinOut.document.writeln( '<li><font color="#ff0000"><b>Access violation error ocurred attempting to access this frame<br>Could not complete - frames span multiple domains or a frame did not contain an HTML based document.<br>------------ Script forced to abort ------------</b></font></li>\n</table></body></html>' );
			oWinOut.document.close();
			window.defaultStatus = 'Fatal error: Frame Tree Script aborted with \'access denied\' errors. Further scripts may not run.';
			if( window.onfalWarn ) { alert( window.defaultStatus ); }
			return true;
		}
		window.oWinOut = window.open('','frtroutwin','menus=0,scrollbars=1,toolbar=0,status=1,resizable=1');
		window.top.focus(); var onBase = true; oWinOut.document.open();
		oWinOut.document.writeln( '<html><head><title>Frame structure</title><style type="text/css"><!--\na { color: #7777ff; text-decoration: none; }\ntd { background-color:#000000;color:#ffffff; }\n--></style></head><body bgcolor="#770000" text="#ffffff"><table border="0" cellpadding="4" cellspacing="0"><tr><td>\n<hr>\n<h1>Frame structure</h1>\n<ul>' );
	} else { var onBase = false; }
	var isDup = false;
	if( oOb.name ) {
		for( var x = 0; x < window.frameNameList.length; x++ ) {
			if( window.frameNameList[x] == oOb.name ) {
				window.defaultStatus = 'WARNING: Frame Tree Script detected duplicate or invalid frame name: ' + oOb.name; var isDup = true; if( window.onfalWarn ) { alert( window.defaultStatus ); } break;
			} }
		window.frameNameList[window.frameNameList.length] = oOb.name;
	}
	//write details of the frame
	oWinOut.document.writeln( '<li>' + ( isDup ? 'Warning - duplicate or invalid name detected! ' : '' ) + ( oOb.name ? 'Frame named \'' + oOb.name + '\'' + ( ( oOb == window.top ) ? 'or \'_top\'' : '' ) : ( oOb == window.top ) ? 'Frame named \'_top\'' : 'Unnamed frame' ) + ' containing <a href="' + oOb.location.href + '" title="' + oOb.location.href + '" target="_blank">' + ( ( oOb.document && oOb.document.title ) ? 'document titled \'' + oOb.document.title + '\'</a>.</li>' : 'unnamed document</a>.</li>' ) );
	if( oOb.frames && oOb.frames.length ) {
		//if the page contains further frames, show their sructure
		oWinOut.document.writeln( '<ul>' );
		for( var x = 0; x < oOb.frames.length; x++ ) { dumpFrameTree( oOb.frames[x] ); }
		oWinOut.document.writeln( '</ul>' );
	}
	if( onBase ) {
		//finished, close overything up
		oWinOut.document.writeln( '</ul>\n<hr>\n</td></tr></table></body></html>' );
		oWinOut.document.close(); window.oWinOut = false; window.onerror = function () {};
	}
}