
#import "NewWindow.h"

@implementation NewWindow

- setUp
{
	spanel = [SavePanel new];
	[newwindow setDelegate:self];
	[contentText setDelegate:self];
	[outputTitleText setDelegate:self];
	return self;
}

- setOutputTitleField:anObject
{
	outputTitleField = anObject;
	[outputTitleText setDelegate: self];
	[outputTitleField setDrawRotation:(NXCoord)90.0];
	[[outputTitleField setVertScrollerRequired:NO] display];
	return self;
}

- setContentField:anObject
{
	contentField = anObject;
	[contentText setDelegate: self];
	[[contentField setVertScrollerRequired:NO] display];
	return self;
}

- setFilename:(const char *) aFilename
{
	if (filename) free(filename);
	filename = malloc(strlen(aFilename)+1);
	strcpy(filename, aFilename);
	[newwindow setTitleAsFilename:aFilename];
	return self;
}

- contentfield
{
	return contentField;
}

- outputtitlefield
{
	return outputTitleField;
}

- group
{
	return group;
}

- window
{
	return newwindow;
}

- loadFile:(const char *)fileName
{
	NXStream *theStream = NXMapFile(fileName,NX_READONLY);

	if (theStream) {
		id ret = self;
		[newwindow setTitle:"Loading..."];

		NX_DURING

		[contentText readRichText: theStream];
		[outputTitleText readRichText: theStream];

		[self setFilename:fileName];

		// Exception handler is skipped if no exception is raised.
		
		NX_HANDLER
		  switch(NXLocalHandler.code){
			case NX_illegalWrite:
			  NXRunAlertPanel(0,"Illegal write on stream",
					  							0,0,0);
			  ret = nil;
			  break;
			case NX_illegalRead:
			  NXRunAlertPanel(0,"Illegal read on stream",
												0,0,0);
			  ret = nil;
			  break;
			case NX_illegalSeek:
			  NXRunAlertPanel(0,"Illegal seek on stream",
												0,0,0);
			  ret = nil;
			  break;
			case NX_illegalStream:
			  NXRunAlertPanel(0,"invalid stream",0,0,0);
			  ret = nil;
			  break;
			case NX_streamVMError:
			  NXRunAlertPanel(0,"VM error on stream",
					  							0,0,0, fileName);
			  ret = nil;
			  break;
		}
		NX_ENDHANDLER							// end of handler

		NXCloseMemory(theStream, NX_FREEBUFFER);
		
		return ret;
	}
	return nil;
}


// save: saves the current window under its default name (found in
// the title bar). Note that if the title bar is empty or the default title
// is "Untitled" then save: will put up a save panel, giving the user
// a chance to specify a real title.

- save:sender
{

	int fd;
	NXStream *theStream;
    
	if (filename == 0) return [self saveAs: sender];
	[newwindow setTitle: "Saving..."];
	
	fd = open(filename, O_WRONLY|O_CREAT|O_TRUNC,0666);
	if (fd<0) {
		NXRunAlertPanel(0, "Cannot save file: %s",
												0, 0, 0, strerror(errno));
		return self;
	}
	
	theStream = NXOpenFile(fd, NX_WRITEONLY);

	[contentText writeRichText: theStream];
	[outputTitleText writeRichText: theStream];

	NXClose(theStream);
	close(fd);
	
	[newwindow setTitleAsFilename: filename];
	[newwindow setDocEdited:NO];
	return self;
}


// saveAs: gives the user a chance to save the current window under a new name. 

- saveAs:sender
{

	id panel;
	const char *dir;
	char *file;
	const char *const types[2] = {[stringSet valueForStringKey:"extension"],
    				  NULL};

  // prompt user for file name and save to that file

	if (filename == 0) {
		// no filename; set up defaults
		dir = NXHomeDirectory();
		file = (char *)[newwindow title];
	}
	else {
		file = rindex(filename, '/');
		if (file) {
			dir = filename;
			*file = 0;
			file++;
		}
		else {
			dir = filename;
			file = (char *)[newwindow title];
		}
	}
	
	panel = [SavePanel new];
	
	[panel setRequiredFileType: types[0]];
	if ([panel 	runModalForDirectory: dir 
						file: file]) {
		[self setFilename: [panel filename] ];

		return [self save: sender];
	}
	return nil; // didn't save
}


// textDidGetKeys: is called every time a key is pressed
// if the window is marked dirty, we don't do anything 
// -- if it's not dirty, we set it to dirty

- textDidGetKeys:sender isEmpty:(BOOL)flag
{
	// if window is not dirty, then set it to dirty
	if ([newwindow isDocEdited] == NO)
			[newwindow setDocEdited:YES];
		
	return self;
}


- windowWillClose:sender
{
	if ([sender isDocEdited]) {
		const char *fname;
		int q;
		
		fname = filename ? filename : [sender title];
		if (rindex(fname,'/'))
			fname = rindex(fname,'/') + 1;
		
		q = NXRunAlertPanel
			("Save",
			"Save changes to %s?\n",
			"Save",
			"Don't Save",
			"Cancel", fname);

		if (q==1) {
			if (![self save:nil]) {
				return nil;
			}
		}
		if (q==-1) {
			return nil;
		}
	}
	
	[sender setDelegate:nil];
	
	// The freeing of the window has been setup in InterfaceBuilder 
	// as "Free when closed [x]"! -- If not, uncomment the following...
	// [self free];
	
	return self;
}

@end
