home *** CD-ROM | disk | FTP | other *** search
Text File | 1995-10-22 | 7.6 KB | 356 lines | [TEXT/CWIE] |
- /*
- CLookupDocument.cp
-
- Copyright © 1995 Alastair Rankine.
- All Rights Reserved.
- */
-
- #include "CLookupDocument.h"
- #include "CLookupApplication.h"
- #include "ResourceIDs.h"
- #include "MessageIDs.h"
- #include "CEntry.h"
-
- #include <LWindow.h>
- #include <LFile.h>
- #include <LPrintout.h>
- #include <LPlaceHolder.h>
- #include <UMemoryMgr.h>
- #include <UWindows.h>
- #include <UAEGizmos.h>
- #include <String_Utils.h>
- #include <strstream>
-
- CLookupDocument::CLookupDocument(LCommander * inSuper, FSSpec * inFileSpec)
- : LSingleDoc(inSuper)
- , mDirty(false)
- {
- // The record list is our submodel list...
- mSubModels = &mEntryList;
-
- // First we need to see if it's a stationary file...
- // ...
-
- Str255 title;
-
- if (inFileSpec == nil) {
- // Set name of untitled window
- NameUntitled(title);
-
- } else {
- // Create a new File object, read the entire File contents,
- // put the contents into the text view, and set the Window
- // title to the name of the File.
-
- Try_ {
- mFile = new LFile(*inFileSpec);
- mFile->OpenDataFork(fsRdWrPerm);
-
- ReadFile();
-
- mIsSpecified = true;
-
- ::CopyPStr(inFileSpec->name, title);
- }
-
- Catch_(inErr) {
- delete this;
- Throw_(inErr);
-
- } EndCatch_
- }
-
- // Create window for our document
- mWindow = LWindow::CreateWindow(WIND_LookupWindow, this);
- mWindow->SetDescriptor(title);
-
- BroadcastMessage(msg_Reverted, 0);
- }
-
-
- void CLookupDocument::NameUntitled(StringPtr outTitle)
- {
- // Start with the default name ("untitled")
- ::GetIndString(outTitle, STRx_Untitled, 1);
-
- long num = 0;
- while (UWindows::FindNamedWindow(outTitle) != nil) {
-
- // An existing window has the current name
- // Increment counter and try again
-
- ::GetIndString(outTitle, STRx_Untitled, 2);
- num++;
- Str15 numStr;
- ::NumToString(num, numStr);
- ConcatPStr(outTitle, numStr);
- }
- }
-
-
- void CLookupDocument::ReadFile()
- {
- if(mEntryList.GetCount())
- mEntryList.RemoveItemsAt(mEntryList.GetCount(), 1);
-
- Handle dataH = mFile->ReadDataFork();
- {
- StHandleLocker dataHlock(dataH);
-
- istrstream stream(*dataH, ::GetHandleSize(dataH));
- while(stream.good())
- {
- CEntry * rec = new CEntry;
- stream >> *rec;
-
- // This will insert the record into the list as well as set the super model.
- rec->SetSuperModel(this);
- }
- }
- ::DisposeHandle(dataH);
- }
-
-
-
- Boolean CLookupDocument::IsModified()
- {
- return mDirty;
- }
-
-
- void CLookupDocument::DoAESave(FSSpec & inFileSpec, OSType inFileType)
- {
- delete mFile; // Kill existing file
-
- mFile = new LFile(inFileSpec); // Make new file object
-
- OSType fileType = 'TEXT'; // Find proper file type
- if (inFileType != fileType_Default) {
- fileType = inFileType;
- }
- // Make new file on disk
- mFile->CreateNewDataFile(CLookupApplication::kSignature, kFileType, 0);
- mFile->OpenDataFork(fsRdWrPerm);
- DoSave(); // Write out data
- // Change window name
- mWindow->SetDescriptor(inFileSpec.name);
- mIsSpecified = true; // Document now has a specified file
- }
-
-
- void CLookupDocument::DoSave()
- {
- // Get text and write to file
- ostrstream stream;
-
- CListIterator<CEntry> iterator(mEntryList, iterate_FromStart);
- CEntry * theEntry;
- while (iterator.Next(theEntry))
- stream << *theEntry;
-
- stream << ends;
-
- mFile->WriteDataFork(stream.str(), stream.pcount());
-
- mDirty = false; // Saving makes doc un-dirty
- }
-
-
- void CLookupDocument::DoRevert()
- {
- ReadFile();
- BroadcastMessage(msg_Reverted, 0);
- }
-
-
- void
- CLookupDocument::DoPrint()
- {
- /*
- LPrintout *thePrintout = LPrintout::CreatePrintout(prto_TextDoc);
- thePrintout->SetPrintRecord(mPrintRecordH);
- LPlaceHolder *textPlace = (LPlaceHolder*)
- thePrintout->FindPaneByID('TBox');
- textPlace->InstallOccupant(mTextView, atNone);
-
- thePrintout->DoPrintJob();
- delete thePrintout;
- */
- }
-
- const CEntry & CLookupDocument::GetEntryAt(EntryIndex row) const
- {
- const CEntry * rec = GetEntryPtrAt(row);
- Assert_(rec);
-
- return *rec;
- }
-
- EntryIndex CLookupDocument::GetEntryCount() const
- {
- return mEntryList.GetCount();
- }
-
- void CLookupDocument::NotifyEntryChanged(CEntry * rec)
- {
- Int32 listPosition = mEntryList.IndexOf(rec);
- Assert_(listPosition != arrayIndex_Bad);
-
- EntryIndex row = listPosition - 1;
- BroadcastMessage(msg_EntryChanged, &row);
- }
-
- const CEntry * CLookupDocument::GetEntryPtrAt(EntryIndex row) const
- {
- return mEntryList.ItemAt(row + 1);
- }
-
- LModelObject* CLookupDocument::HandleCreateElementEvent(DescType inElemClass,
- DescType inInsertPosition, LModelObject * inTargetObject, const AppleEvent & inAppleEvent,
- AppleEvent & outAEReply)
- {
- LModelObject * rval = nil;
-
- if(inElemClass == CEntry::kModelID)
- {
- CEntry * rec = new CEntry(this);
-
- LAESubDesc aeSubDesc(inAppleEvent);
-
- // Set the initial properties:
- LAESubDesc properties = aeSubDesc.KeyedItem(keyAEPropData);
- if(properties.GetType() != typeNull)
- {
- StAEDescriptor propDesc;
- properties.ToDesc(propDesc);
-
- StAEDescriptor bogusReply;
- rec->SetAEProperty(pContents, propDesc, bogusReply.mDesc);
- }
-
- // Until we can read it from the AE:
- EntryIndex insertion = 0;
-
- switch(inInsertPosition)
- {
- case kAEBeginning:
- default:
- // Insertion position is fine - don't do anything
- break;
-
- case kAEBefore:
- insertion = mEntryList.IndexOf((CEntry *)inTargetObject) - 1;
- break;
-
- case kAEAfter:
- insertion = mEntryList.IndexOf((CEntry *)inTargetObject);
- break;
-
- case kAEEnd:
- insertion = mEntryList.GetCount();
- break;
- }
-
- // This inserts where we want to be in the list. Stupid AddSubModel() inserts it at
- // the end - we need to move it to where it should be.
- mEntryList.RemoveItemsAt(1, arrayIndex_Last);
- mEntryList.InsertAt(1, insertion + 1, rec);
-
- // Tell the view to update itself.
- BroadcastMessage(msg_EntryInserted, &insertion);
-
- mDirty = true;
-
- rval = rec;
- }
- else
- {
- LSingleDoc::HandleCreateElementEvent(inElemClass, inInsertPosition, inTargetObject,
- inAppleEvent, outAEReply);
- }
-
- return rval;
- }
-
- void CLookupDocument::DeleteEntry(CEntry * rec)
- {
- Int32 idx = mEntryList.IndexOf(rec);
- Assert_(idx);
-
- // This will remove the record from the list...
- delete rec;
-
- EntryIndex row = idx - 1;
- BroadcastMessage(msg_EntryDeleted, &row);
-
- mDirty = true;
- }
-
- void CLookupDocument::FindCommandStatus(CommandT inCommand, Boolean & outEnabled,
- Boolean & outUsesMark, Char16 & outMark, Str255 outName)
- {
- switch (inCommand) {
-
- case cmd_Print:
- case cmd_PrintOne:
- outEnabled = true;
- break;
-
- default:
- LSingleDoc::FindCommandStatus(inCommand, outEnabled, outUsesMark, outMark, outName);
- break;
- }
- }
-
-
- void CLookupDocument::GetSubModelByComplexKey(DescType inModelID, DescType inKeyForm,
- const AEDesc & inKeyData, AEDesc & outToken) const
- {
- if(inKeyForm == formRange)
- {
- LAESubDesc keyData(inKeyData, typeRangeDescriptor);
-
- LAESubDesc startDesc = keyData.KeyedItem(keyAERangeStart);
- LAESubDesc endDesc = keyData.KeyedItem(keyAERangeStop);
-
- LModelObject * startModel = startDesc.ToModelObject();
- LModelObject * endModel = endDesc.ToModelObject();
-
- Assert_(mSubModels);
- Int32 startIdx = mSubModels->FetchIndexOf(&startModel);
- Int32 endIdx = mSubModels->FetchIndexOf(&endModel);
-
- // Validate the range...
- Assert_(startIdx != arrayIndex_Bad);
- Assert_(endIdx != arrayIndex_Bad);
- if(startIdx > endIdx)
- Throw_(errAEImpossibleRange);
-
- LAEStream out;
-
- out.OpenList();
- for (Int32 i = startIdx; i <= endIdx; i++) {
- StAEDescriptor subToken;
-
- PutInToken(mEntryList.ItemAt(i), subToken.mDesc);
- out.WriteDesc(subToken.mDesc);
- }
- out.CloseList();
- out.Close(&outToken);
- }
- else
- LSingleDoc::GetSubModelByComplexKey(inModelID, inKeyForm, inKeyData, outToken);
- }
-
- CLookupDocument::~CLookupDocument()
- {
- // Don't let the LModelObject destructor get it's hands on the mSubModel list...
- mSubModels = nil;
- }
-
-
-
-
-
-
-