DZUtils.c

/*
 *  File:       DZUtils.c
 *
 *  Copyright © 1996 Apple Computer, Inc.
 */
 
#include <assert.h>
 
#include <Resources.h>
#include <Types.h>
 
#include <QD3D.h>
#include <QD3DGroup.h>
#include <QD3DIO.h>
#include <QD3DStorage.h>
 
#include "DZUtils.h"
 
 
/*******************************************************************************
 *  CheckVersionNumber
 *
 *  Returns true if the given version number is compatible with (i. e not older
 *  than) version inMajor.inMinor.inBug.
 ******************************************************************************/
Boolean CheckVersionNumber(
    const NumVersion*       inVersion,
    UInt8                   inMajor,
    UInt8                   inMinor,
    UInt8                   inBug)
{
    if (inVersion->majorRev != inMajor)
    {
        return inVersion->majorRev > inMajor;
    }
    else
    {
        return inVersion->minorAndBugRev >= inMinor << 4 | inBug;
    }
}
 
 
/* =============================================================================
 *      Get3DMFResource (external)
 *
 *  Gets the '3DMF' resource with the given ID, and reads it using QD3D, and
 *  returns a reference to anything drawable in it.  NULL is returned if a
 *  problem occurs.
 * ========================================================================== */
TQ3Object Get3DMFResource(
    short               inResourceID)
{
    Handle              resource;
    TQ3Object           result;
    TQ3Object           object;
    TQ3Object           group;
    TQ3StorageObject    storage;
    TQ3FileObject       file;
    TQ3FileMode         mode;
    
    resource    = NULL;
    result      = NULL;
    object      = NULL;
    group       = NULL;
    storage     = NULL;
    file        = NULL;
    
    // Grab the resource
    resource = GetResource('3DMF', inResourceID);
    if (resource == NULL || ResError() != noErr)  goto bail;
    
    // Set up for reading
    storage = Q3HandleStorage_New(resource, GetHandleSize(resource));
    if (storage == NULL)  goto bail;
    
    file = Q3File_New();
    if (file == NULL)  goto bail;
    
    if (Q3File_SetStorage(file, storage) != kQ3Success)  goto bail;
    
    if (Q3File_OpenRead(file, &mode) != kQ3Success)  goto bail;
    
    // Read the objects
    group = NULL;
    
    while (!Q3File_IsEndOfFile(file))
    {
        object = Q3File_ReadObject(file);
        if (object != NULL)
        {
            if (Q3Object_IsDrawable(object))
            {
                if (result == NULL)
                {
                    // This is the first object
                    result = Q3Shared_GetReference(object);
                }
                else
                {
                    // Make sure we have a group to add it to
                    if (group == NULL)
                    {
                        // Create the new group
                        group = Q3DisplayGroup_New();
                        Q3Group_AddObject(group, result);
                        
                        Q3Object_Dispose(result);
                        result = Q3Shared_GetReference(group);
                    }
                    
                    // Add it to the group
                    assert(group == result);
                    Q3Group_AddObject(result, object);
                }
            }
            
            Q3Object_Dispose(object);
            object = NULL;
        }
    }
    
    // Get rid of the group reference
    if (group != NULL)
    {
        Q3Object_Dispose(group);
        group = NULL;
    }
    
    // Finish reading
    Q3File_Close(file);
    
    Q3Object_Dispose(file);
    file = NULL;
    
    Q3Object_Dispose(storage);
    storage = NULL;
    
    // Release the resource
    ReleaseResource(resource);
    
    return result;
    
    // Error exit
    bail:
    
    if (resource != NULL)
    {
        ReleaseResource(resource);
        resource = NULL;
    }
    
    if (result != NULL)
    {
        Q3Object_Dispose(result);
        result = NULL;
    }
    
    if (object != NULL)
    {
        Q3Object_Dispose(object);
        object = NULL;
    }
    
    if (group != NULL)
    {
        Q3Object_Dispose(group);
        group = NULL;
    }
    
    if (result != NULL)
    {
        Q3Object_Dispose(result);
        result = NULL;
    }
    
    if (storage != NULL)
    {
        Q3Object_Dispose(storage);
        storage = NULL;
    }
    
    if (file != NULL)
    {
        Q3Object_Dispose(file);
        file = NULL;
    }
    
    return NULL;
}