mirror of
https://github.com/kevinbentley/Descent3.git
synced 2025-01-22 11:28:56 +00:00
Hog Utilities
This commit is contained in:
parent
9782e2b138
commit
81cd1066ca
144
hogedit/DirDialog.cpp
Normal file
144
hogedit/DirDialog.cpp
Normal file
@ -0,0 +1,144 @@
|
||||
///////////////////////////////////////////////////////////////////////////
|
||||
// DirDialog.cpp: implementation of the CDirDialog class.
|
||||
//////////////////////////////////////////////////////////////////////
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "DirDialog.h"
|
||||
#include "shlobj.h"
|
||||
|
||||
#ifdef _DEBUG
|
||||
#undef THIS_FILE
|
||||
static char THIS_FILE[]=__FILE__;
|
||||
#define new DEBUG_NEW
|
||||
#endif
|
||||
|
||||
// Callback function called by SHBrowseForFolder's browse control
|
||||
// after initialization and when selection changes
|
||||
int __stdcall CDirDialog::BrowseCtrlCallback(HWND hwnd, UINT uMsg, LPARAM lParam, LPARAM lpData)
|
||||
{
|
||||
CDirDialog* pDirDialogObj = (CDirDialog*)lpData;
|
||||
if (uMsg == BFFM_INITIALIZED )
|
||||
{
|
||||
if( ! pDirDialogObj->m_strSelDir.IsEmpty() )
|
||||
::SendMessage(hwnd, BFFM_SETSELECTION, TRUE, (LPARAM)(LPCTSTR)(pDirDialogObj->m_strSelDir));
|
||||
if( ! pDirDialogObj->m_strWindowTitle.IsEmpty() )
|
||||
::SetWindowText(hwnd, (LPCTSTR) pDirDialogObj->m_strWindowTitle);
|
||||
}
|
||||
else if( uMsg == BFFM_SELCHANGED )
|
||||
{
|
||||
LPITEMIDLIST pidl = (LPITEMIDLIST) lParam;
|
||||
char selection[MAX_PATH];
|
||||
if( ! ::SHGetPathFromIDList(pidl, selection) )
|
||||
selection[0] = '\0';
|
||||
|
||||
CString csStatusText;
|
||||
BOOL bOk = pDirDialogObj->SelChanged(selection, csStatusText);
|
||||
|
||||
if( pDirDialogObj->m_bStatus )
|
||||
::SendMessage(hwnd, BFFM_SETSTATUSTEXT , 0, (LPARAM)(LPCSTR)csStatusText);
|
||||
|
||||
::SendMessage(hwnd, BFFM_ENABLEOK, 0, bOk);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
//////////////////////////////////////////////////////////////////////
|
||||
// Construction/Destruction
|
||||
//////////////////////////////////////////////////////////////////////
|
||||
|
||||
CDirDialog::CDirDialog()
|
||||
{
|
||||
m_bStatus = FALSE;
|
||||
}
|
||||
|
||||
CDirDialog::~CDirDialog()
|
||||
{
|
||||
}
|
||||
|
||||
BOOL CDirDialog::DoBrowse(CWnd *pwndParent)
|
||||
{
|
||||
|
||||
if( ! m_strSelDir.IsEmpty() )
|
||||
{
|
||||
m_strSelDir.TrimRight();
|
||||
if( m_strSelDir.Right(1) == "\\" || m_strSelDir.Right(1) == "//" )
|
||||
m_strSelDir = m_strSelDir.Left(m_strSelDir.GetLength() - 1);
|
||||
}
|
||||
|
||||
LPMALLOC pMalloc;
|
||||
if (SHGetMalloc (&pMalloc)!= NOERROR)
|
||||
return FALSE;
|
||||
|
||||
BROWSEINFO bInfo;
|
||||
LPITEMIDLIST pidl;
|
||||
ZeroMemory ( (PVOID) &bInfo,sizeof (BROWSEINFO));
|
||||
|
||||
if (!m_strInitDir.IsEmpty ())
|
||||
{
|
||||
OLECHAR olePath[MAX_PATH];
|
||||
ULONG chEaten;
|
||||
ULONG dwAttributes;
|
||||
HRESULT hr;
|
||||
LPSHELLFOLDER pDesktopFolder;
|
||||
//
|
||||
// Get a pointer to the Desktop's IShellFolder interface.
|
||||
//
|
||||
if (SUCCEEDED(SHGetDesktopFolder(&pDesktopFolder)))
|
||||
{
|
||||
//
|
||||
// IShellFolder::ParseDisplayName requires the file name be in Unicode.
|
||||
//
|
||||
MultiByteToWideChar(CP_ACP, MB_PRECOMPOSED, m_strInitDir.GetBuffer(MAX_PATH), -1,
|
||||
olePath, MAX_PATH);
|
||||
|
||||
m_strInitDir.ReleaseBuffer (-1);
|
||||
//
|
||||
// Convert the path to an ITEMIDLIST.
|
||||
//
|
||||
hr = pDesktopFolder->ParseDisplayName(NULL,
|
||||
NULL,
|
||||
olePath,
|
||||
&chEaten,
|
||||
&pidl,
|
||||
&dwAttributes);
|
||||
if (FAILED(hr))
|
||||
{
|
||||
pMalloc ->Free (pidl);
|
||||
pMalloc ->Release ();
|
||||
return FALSE;
|
||||
}
|
||||
bInfo.pidlRoot = pidl;
|
||||
|
||||
}
|
||||
}
|
||||
bInfo.hwndOwner = pwndParent == NULL ? NULL : pwndParent->GetSafeHwnd();
|
||||
bInfo.pszDisplayName = m_strPath.GetBuffer (MAX_PATH);
|
||||
bInfo.lpszTitle = (m_strTitle.IsEmpty()) ? "Open" : m_strTitle;
|
||||
bInfo.ulFlags = BIF_RETURNFSANCESTORS
|
||||
| BIF_RETURNONLYFSDIRS
|
||||
| (m_bStatus ? BIF_STATUSTEXT : 0);
|
||||
|
||||
bInfo.lpfn = BrowseCtrlCallback; // address of callback function
|
||||
bInfo.lParam = (LPARAM)this; // pass address of object to callback function
|
||||
|
||||
if ((pidl = ::SHBrowseForFolder(&bInfo)) == NULL)
|
||||
{
|
||||
return FALSE;
|
||||
}
|
||||
m_strPath.ReleaseBuffer();
|
||||
m_iImageIndex = bInfo.iImage;
|
||||
|
||||
if (::SHGetPathFromIDList(pidl, m_strPath.GetBuffer(MAX_PATH)) == FALSE)
|
||||
{
|
||||
pMalloc ->Free(pidl);
|
||||
pMalloc ->Release();
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
m_strPath.ReleaseBuffer();
|
||||
|
||||
pMalloc ->Free(pidl);
|
||||
pMalloc ->Release();
|
||||
|
||||
return TRUE;
|
||||
}
|
36
hogedit/DirDialog.h
Normal file
36
hogedit/DirDialog.h
Normal file
@ -0,0 +1,36 @@
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// DirDialog.h: interface for the CDirDialog class.
|
||||
//////////////////////////////////////////////////////////////////////
|
||||
|
||||
#if !defined(AFX_DIRDIALOG_H__62FFAC92_1DEE_11D1_B87A_0060979CDF6D__INCLUDED_)
|
||||
#define AFX_DIRDIALOG_H__62FFAC92_1DEE_11D1_B87A_0060979CDF6D__INCLUDED_
|
||||
|
||||
#if _MSC_VER >= 1000
|
||||
#pragma once
|
||||
#endif // _MSC_VER >= 1000
|
||||
|
||||
class CDirDialog
|
||||
{
|
||||
public:
|
||||
|
||||
CDirDialog();
|
||||
virtual ~CDirDialog();
|
||||
|
||||
BOOL DoBrowse(CWnd *pwndParent = NULL);
|
||||
|
||||
CString m_strWindowTitle;
|
||||
CString m_strPath;
|
||||
CString m_strInitDir;
|
||||
CString m_strSelDir;
|
||||
CString m_strTitle;
|
||||
int m_iImageIndex;
|
||||
BOOL m_bStatus;
|
||||
|
||||
private:
|
||||
|
||||
virtual BOOL SelChanged(LPCSTR lpcsSelection, CString& csStatusText) { return TRUE; };
|
||||
static int __stdcall CDirDialog::BrowseCtrlCallback(HWND hwnd, UINT uMsg, LPARAM lParam, LPARAM lpData);
|
||||
};
|
||||
|
||||
#endif // !defined(AFX_DIRDIALOG_H__62FFAC92_1DEE_11D1_B87A_0060979CDF6D__INCLUDED_)
|
||||
|
365
hogedit/HogEdit.cpp
Normal file
365
hogedit/HogEdit.cpp
Normal file
@ -0,0 +1,365 @@
|
||||
/*
|
||||
* $Logfile: /DescentIII/Main/hogedit/HogEdit.cpp $
|
||||
* $Revision: 1.1.1.1 $
|
||||
* $Date: 2003-08-26 03:57:56 $
|
||||
* $Author: kevinb $
|
||||
*
|
||||
*
|
||||
*
|
||||
* $Log: not supported by cvs2svn $
|
||||
*
|
||||
* 11 10/30/98 11:15a Nate
|
||||
* Added support for modification of hog files.
|
||||
*
|
||||
* 10 10/28/98 11:24a Nate
|
||||
* Added command line auto-processing (create hog from a rib)
|
||||
*
|
||||
* 9 10/27/98 5:55p Nate
|
||||
* Added command line processing
|
||||
*
|
||||
* 8 10/15/98 2:53p Nate
|
||||
* Added mem_Init()
|
||||
*
|
||||
* 7 8/16/98 4:22p Nate
|
||||
* Added message deferal and new hog info dialog
|
||||
*
|
||||
* 6 8/14/98 4:38p Nate
|
||||
* Added number of files field to status bar.
|
||||
*
|
||||
* 5 8/14/98 4:38p Nate
|
||||
* Fixed a few minor bugs and added better error reporting
|
||||
*
|
||||
* 4 8/14/98 1:01p Nate
|
||||
* Added better error reporting for the HogEditor
|
||||
*
|
||||
* 3 7/22/98 2:38p Nate
|
||||
* Added Modified File prompt when exiting
|
||||
*
|
||||
* 2 7/15/98 12:31p Nate
|
||||
* Initial version
|
||||
*
|
||||
* $NoKeywords: $
|
||||
*/
|
||||
|
||||
// HogEdit.cpp : Defines the class behaviors for the application.
|
||||
//
|
||||
|
||||
#include "stdafx.h"
|
||||
#include <afxtempl.h>
|
||||
#include "HogEdit.h"
|
||||
|
||||
#include "MainFrm.h"
|
||||
#include "hogfile.h"
|
||||
#include "HogEditDoc.h"
|
||||
#include "listvwex.h"
|
||||
#include "HogEditView.h"
|
||||
#include "mem.h"
|
||||
|
||||
#ifdef _DEBUG
|
||||
#define new DEBUG_NEW
|
||||
#undef THIS_FILE
|
||||
static char THIS_FILE[] = __FILE__;
|
||||
#endif
|
||||
|
||||
CStatusBar *MainStatusBar; // pointer to the main status bar of the app
|
||||
|
||||
// globals for automated hog processing
|
||||
CString AutoRibFilename;
|
||||
CString AutoHogFilename;
|
||||
bool DoAutoProcess;
|
||||
bool UseCurrentHogFilename;
|
||||
|
||||
// globals for command line processing
|
||||
#define MAX_CMDLINE_ARGS 3
|
||||
#define MAX_CMDLINE_ARG_SIZE 512
|
||||
char *app_argv[MAX_CMDLINE_ARGS];
|
||||
int app_argc;
|
||||
|
||||
// Command line parsing function prototype
|
||||
int ParseAppCommandLine(char *cmdline, char **argv, int max_args);
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// CHogEditApp
|
||||
|
||||
BEGIN_MESSAGE_MAP(CHogEditApp, CWinApp)
|
||||
//{{AFX_MSG_MAP(CHogEditApp)
|
||||
ON_COMMAND(ID_APP_ABOUT, OnAppAbout)
|
||||
// NOTE - the ClassWizard will add and remove mapping macros here.
|
||||
// DO NOT EDIT what you see in these blocks of generated code!
|
||||
//}}AFX_MSG_MAP
|
||||
// Standard file based document commands
|
||||
ON_COMMAND(ID_FILE_NEW, CWinApp::OnFileNew)
|
||||
ON_COMMAND(ID_FILE_OPEN, CWinApp::OnFileOpen)
|
||||
END_MESSAGE_MAP()
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// CHogEditApp construction
|
||||
|
||||
CHogEditApp::CHogEditApp()
|
||||
{
|
||||
// TODO: add construction code here,
|
||||
WaitCursor=NULL;
|
||||
DoAutoProcess=FALSE;
|
||||
// Place all significant initialization in InitInstance
|
||||
}
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// The one and only CHogEditApp object
|
||||
|
||||
CHogEditApp theApp;
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// CHogEditApp initialization
|
||||
|
||||
BOOL CHogEditApp::InitInstance()
|
||||
{
|
||||
int k;
|
||||
|
||||
AfxEnableControlContainer();
|
||||
|
||||
// Standard initialization
|
||||
// If you are not using these features and wish to reduce the size
|
||||
// of your final executable, you should remove from the following
|
||||
// the specific initialization routines you do not need.
|
||||
|
||||
#ifdef _AFXDLL
|
||||
Enable3dControls(); // Call this when using MFC in a shared DLL
|
||||
#else
|
||||
Enable3dControlsStatic(); // Call this when linking to MFC statically
|
||||
#endif
|
||||
|
||||
// Change the registry key under which our settings are stored.
|
||||
// You should modify this string to be something appropriate
|
||||
// such as the name of your company or organization.
|
||||
SetRegistryKey(_T("Local AppWizard-Generated Applications"));
|
||||
|
||||
LoadStdProfileSettings(); // Load standard INI file options (including MRU)
|
||||
|
||||
|
||||
// Allocate mem for cmd line args
|
||||
for(k=0;k<MAX_CMDLINE_ARGS;k++)
|
||||
app_argv[k]=new char[MAX_CMDLINE_ARG_SIZE+1];
|
||||
|
||||
// Get the command line arguments
|
||||
app_argc=ParseAppCommandLine(m_lpCmdLine,app_argv,MAX_CMDLINE_ARGS);
|
||||
|
||||
// See if user wants to do auto-processing of hog
|
||||
DoAutoProcess=FALSE;
|
||||
if(app_argc==2) {
|
||||
AutoRibFilename=app_argv[0];
|
||||
AutoHogFilename=app_argv[1];
|
||||
DoAutoProcess=TRUE;
|
||||
/*
|
||||
AfxMessageBox(AutoRibFilename);
|
||||
AfxMessageBox(AutoHogFilename);
|
||||
*/
|
||||
}
|
||||
UseCurrentHogFilename=FALSE;
|
||||
OutputDebugString("Parsing command line...\n");
|
||||
|
||||
// Delete mem for cmd line args
|
||||
for(k=0;k<MAX_CMDLINE_ARGS;k++)
|
||||
delete[] app_argv[k];
|
||||
app_argc=0;
|
||||
|
||||
|
||||
// Register the application's document templates. Document templates
|
||||
// serve as the connection between documents, frame windows and views.
|
||||
|
||||
CSingleDocTemplate* pDocTemplate;
|
||||
pDocTemplate = new CSingleDocTemplate(
|
||||
IDR_MAINFRAME,
|
||||
RUNTIME_CLASS(CHogEditDoc),
|
||||
RUNTIME_CLASS(CMainFrame), // main SDI frame window
|
||||
RUNTIME_CLASS(CHogEditView));
|
||||
AddDocTemplate(pDocTemplate);
|
||||
|
||||
// Parse command line for standard shell commands, DDE, file open
|
||||
CCommandLineInfo cmdInfo;
|
||||
//ParseCommandLine(cmdInfo);
|
||||
|
||||
// Dispatch commands specified on the command line
|
||||
if (!ProcessShellCommand(cmdInfo))
|
||||
return FALSE;
|
||||
|
||||
|
||||
// The one and only window has been initialized, so show and update it.
|
||||
m_pMainWnd->ShowWindow(SW_SHOW);
|
||||
m_pMainWnd->UpdateWindow();
|
||||
|
||||
// Initialize the memory library
|
||||
mem_Init();
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// CAboutDlg dialog used for App About
|
||||
|
||||
class CAboutDlg : public CDialog
|
||||
{
|
||||
public:
|
||||
CAboutDlg();
|
||||
|
||||
// Dialog Data
|
||||
//{{AFX_DATA(CAboutDlg)
|
||||
enum { IDD = IDD_ABOUTBOX };
|
||||
//}}AFX_DATA
|
||||
|
||||
// ClassWizard generated virtual function overrides
|
||||
//{{AFX_VIRTUAL(CAboutDlg)
|
||||
protected:
|
||||
virtual void DoDataExchange(CDataExchange* pDX); // DDX/DDV support
|
||||
//}}AFX_VIRTUAL
|
||||
|
||||
// Implementation
|
||||
protected:
|
||||
//{{AFX_MSG(CAboutDlg)
|
||||
// No message handlers
|
||||
//}}AFX_MSG
|
||||
DECLARE_MESSAGE_MAP()
|
||||
};
|
||||
|
||||
CAboutDlg::CAboutDlg() : CDialog(CAboutDlg::IDD)
|
||||
{
|
||||
//{{AFX_DATA_INIT(CAboutDlg)
|
||||
//}}AFX_DATA_INIT
|
||||
}
|
||||
|
||||
void CAboutDlg::DoDataExchange(CDataExchange* pDX)
|
||||
{
|
||||
CDialog::DoDataExchange(pDX);
|
||||
//{{AFX_DATA_MAP(CAboutDlg)
|
||||
//}}AFX_DATA_MAP
|
||||
}
|
||||
|
||||
BEGIN_MESSAGE_MAP(CAboutDlg, CDialog)
|
||||
//{{AFX_MSG_MAP(CAboutDlg)
|
||||
// No message handlers
|
||||
//}}AFX_MSG_MAP
|
||||
END_MESSAGE_MAP()
|
||||
|
||||
// App command to run the dialog
|
||||
void CHogEditApp::OnAppAbout()
|
||||
{
|
||||
CAboutDlg aboutDlg;
|
||||
aboutDlg.DoModal();
|
||||
}
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// CHogEditApp commands
|
||||
|
||||
|
||||
// Displays the "are you sure?" dialog
|
||||
int ModifiedPrompt(CWnd *caller)
|
||||
{
|
||||
// If current file has been modified, check with user first...
|
||||
if(!DocModified) return(IDYES);
|
||||
if(caller->MessageBox("Your current file will be lost. Proceed?",
|
||||
"File Has Been Modified",
|
||||
MB_YESNO)==IDYES) return(IDYES);
|
||||
return(IDNO);
|
||||
}
|
||||
|
||||
// Checks if there are any messages and translates and dispatches them
|
||||
#define MAX_MESSAGES 25
|
||||
void ProcessMessages(void)
|
||||
{
|
||||
MSG msg;
|
||||
int MsgCount;
|
||||
|
||||
for ( MsgCount = MAX_MESSAGES;
|
||||
MsgCount && PeekMessage( &msg, NULL, 0, 0, PM_REMOVE );
|
||||
MsgCount--) {
|
||||
TranslateMessage( &msg );
|
||||
DispatchMessage( &msg );
|
||||
}
|
||||
}
|
||||
|
||||
// Updates the total files indicator
|
||||
void UpdateTotalFiles(int num_files)
|
||||
{
|
||||
char msg[256];
|
||||
|
||||
sprintf(msg,"Total Files: %d", num_files);
|
||||
MainStatusBar->SetPaneText(1,msg,TRUE);
|
||||
ProcessMessages();
|
||||
}
|
||||
|
||||
// Updates the status bar with the given message
|
||||
CWaitCursor *WaitCursor;
|
||||
void UpdateStatusBar(char *msg)
|
||||
{
|
||||
if(msg==NULL) return;
|
||||
|
||||
MainStatusBar->SetPaneText(0,msg,TRUE);
|
||||
ProcessMessages();
|
||||
|
||||
// If the WaitCursor is not null, restore it
|
||||
if(WaitCursor!=NULL)
|
||||
WaitCursor->Restore();
|
||||
}
|
||||
|
||||
// Parses the given command line into a list of arguments
|
||||
#define MAX_CMDLINE_SIZE 1024
|
||||
int ParseAppCommandLine(char *cmdline, char **argv, int max_args)
|
||||
{
|
||||
int i, argc, done;
|
||||
char *s, *q;
|
||||
char line[MAX_CMDLINE_SIZE+1];
|
||||
|
||||
// make working copy of command line
|
||||
strncpy(line,cmdline,MAX_CMDLINE_SIZE);
|
||||
line[MAX_CMDLINE_SIZE]='\0';
|
||||
|
||||
// Init arglist to empty
|
||||
for(i=0;i<max_args;i++)
|
||||
argv[i][0]='\0';
|
||||
|
||||
argc=0;
|
||||
s=line;
|
||||
done=FALSE;
|
||||
|
||||
// Get the arguments
|
||||
while(!done && argc<max_args) {
|
||||
|
||||
// strip off leading whitespace
|
||||
while(isspace(*s)) s++;
|
||||
|
||||
// if it's the end of the line, we're done
|
||||
if(strlen(s)==0) {
|
||||
done=TRUE;
|
||||
continue;
|
||||
}
|
||||
|
||||
// process the argument
|
||||
if((*s)=='\"') { // handle quoted arguments
|
||||
s++; // skip to char after quote
|
||||
|
||||
q=strchr(s,'\"'); // find ending quote
|
||||
if(q==NULL) {
|
||||
strcpy(argv[argc],s);
|
||||
s+=strlen(argv[argc]);
|
||||
}
|
||||
else {
|
||||
(*q)='\0';
|
||||
strcpy(argv[argc],s);
|
||||
s=q+1;
|
||||
}
|
||||
}
|
||||
else { // handle whitespace delimited args
|
||||
q=s;
|
||||
while(!isspace(*q) && (*q)!='\0') q++;
|
||||
if((*q)!='\0') {
|
||||
(*q)='\0';
|
||||
q++;
|
||||
}
|
||||
strcpy(argv[argc],s);
|
||||
s=q;
|
||||
}
|
||||
|
||||
argc++;
|
||||
}
|
||||
|
||||
return(argc);
|
||||
}
|
107
hogedit/HogEdit.h
Normal file
107
hogedit/HogEdit.h
Normal file
@ -0,0 +1,107 @@
|
||||
/*
|
||||
* $Logfile: /DescentIII/Main/hogedit/HogEdit.h $
|
||||
* $Revision: 1.1.1.1 $
|
||||
* $Date: 2003-08-26 03:57:56 $
|
||||
* $Author: kevinb $
|
||||
*
|
||||
*
|
||||
*
|
||||
* $Log: not supported by cvs2svn $
|
||||
*
|
||||
* 10 10/30/98 11:15a Nate
|
||||
* Added support for modification of hog files.
|
||||
*
|
||||
* 9 10/28/98 11:24a Nate
|
||||
* Added command line auto-processing (create hog from a rib)
|
||||
*
|
||||
* 8 9/17/98 4:29p Nate
|
||||
* Added Import Directory option.
|
||||
*
|
||||
* 7 8/16/98 4:22p Nate
|
||||
* Added message deferal and new hog info dialog
|
||||
*
|
||||
* 6 8/14/98 6:04p Nate
|
||||
* Added number of files field to status bar.
|
||||
*
|
||||
* 5 8/14/98 4:38p Nate
|
||||
* Fixed a few minor bugs and added better error reporting
|
||||
*
|
||||
* 4 8/14/98 1:01p Nate
|
||||
* Added better error reporting for the HogEditor
|
||||
*
|
||||
* 3 7/22/98 2:38p Nate
|
||||
* Added Modified File prompt when exiting
|
||||
*
|
||||
* 2 7/15/98 12:31p Nate
|
||||
* Initial version
|
||||
*
|
||||
* $NoKeywords: $
|
||||
*/
|
||||
|
||||
// HogEdit.h : main header file for the HOGEDIT application
|
||||
//
|
||||
|
||||
#if !defined(AFX_HOGEDIT_H__48BE52B8_172F_11D2_8CBC_00A0C96ED60D__INCLUDED_)
|
||||
#define AFX_HOGEDIT_H__48BE52B8_172F_11D2_8CBC_00A0C96ED60D__INCLUDED_
|
||||
|
||||
#if _MSC_VER >= 1000
|
||||
#pragma once
|
||||
#endif // _MSC_VER >= 1000
|
||||
|
||||
#ifndef __AFXWIN_H__
|
||||
#error include 'stdafx.h' before including this file for PCH
|
||||
#endif
|
||||
|
||||
#include "resource.h" // main symbols
|
||||
|
||||
#define HOG_EDIT_TITLE "The Hog Farmer v1.0"
|
||||
|
||||
int ModifiedPrompt(CWnd *caller);
|
||||
void ProcessMessages(void);
|
||||
void UpdateTotalFiles(int num_files);
|
||||
void UpdateStatusBar(char *msg);
|
||||
|
||||
extern bool DocModified; // is document modified.
|
||||
extern CStatusBar *MainStatusBar; // pointer to the main status bar
|
||||
extern CWaitCursor *WaitCursor; // pointer to a remote wait cursor
|
||||
|
||||
// Globals for automated hog file creation (from a given rib file)
|
||||
extern CString AutoRibFilename;
|
||||
extern CString AutoHogFilename;
|
||||
extern bool DoAutoProcess;
|
||||
extern bool UseCurrentHogFilename;
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// CHogEditApp:
|
||||
// See HogEdit.cpp for the implementation of this class
|
||||
//
|
||||
|
||||
class CHogEditApp : public CWinApp
|
||||
{
|
||||
public:
|
||||
CHogEditApp();
|
||||
|
||||
// Overrides
|
||||
// ClassWizard generated virtual function overrides
|
||||
//{{AFX_VIRTUAL(CHogEditApp)
|
||||
public:
|
||||
virtual BOOL InitInstance();
|
||||
//}}AFX_VIRTUAL
|
||||
|
||||
// Implementation
|
||||
|
||||
//{{AFX_MSG(CHogEditApp)
|
||||
afx_msg void OnAppAbout();
|
||||
// NOTE - the ClassWizard will add and remove member functions here.
|
||||
// DO NOT EDIT what you see in these blocks of generated code !
|
||||
//}}AFX_MSG
|
||||
DECLARE_MESSAGE_MAP()
|
||||
};
|
||||
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
//{{AFX_INSERT_LOCATION}}
|
||||
// Microsoft Developer Studio will insert additional declarations immediately before the previous line.
|
||||
|
||||
#endif // !defined(AFX_HOGEDIT_H__48BE52B8_172F_11D2_8CBC_00A0C96ED60D__INCLUDED_)
|
418
hogedit/HogEdit.rc
Normal file
418
hogedit/HogEdit.rc
Normal file
@ -0,0 +1,418 @@
|
||||
//Microsoft Developer Studio generated resource script.
|
||||
//
|
||||
#include "resource.h"
|
||||
|
||||
#define APSTUDIO_READONLY_SYMBOLS
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Generated from the TEXTINCLUDE 2 resource.
|
||||
//
|
||||
#include "afxres.h"
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
#undef APSTUDIO_READONLY_SYMBOLS
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// English (U.S.) resources
|
||||
|
||||
#if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_ENU)
|
||||
#ifdef _WIN32
|
||||
LANGUAGE LANG_ENGLISH, SUBLANG_ENGLISH_US
|
||||
#pragma code_page(1252)
|
||||
#endif //_WIN32
|
||||
|
||||
#ifdef APSTUDIO_INVOKED
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// TEXTINCLUDE
|
||||
//
|
||||
|
||||
1 TEXTINCLUDE DISCARDABLE
|
||||
BEGIN
|
||||
"resource.h\0"
|
||||
END
|
||||
|
||||
2 TEXTINCLUDE DISCARDABLE
|
||||
BEGIN
|
||||
"#include ""afxres.h""\r\n"
|
||||
"\0"
|
||||
END
|
||||
|
||||
3 TEXTINCLUDE DISCARDABLE
|
||||
BEGIN
|
||||
"#define _AFX_NO_SPLITTER_RESOURCES\r\n"
|
||||
"#define _AFX_NO_OLE_RESOURCES\r\n"
|
||||
"#define _AFX_NO_TRACKER_RESOURCES\r\n"
|
||||
"#define _AFX_NO_PROPERTY_RESOURCES\r\n"
|
||||
"\r\n"
|
||||
"#if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_ENU)\r\n"
|
||||
"#ifdef _WIN32\r\n"
|
||||
"LANGUAGE 9, 1\r\n"
|
||||
"#pragma code_page(1252)\r\n"
|
||||
"#endif\r\n"
|
||||
"#include ""res\\HogEdit.rc2"" // non-Microsoft Visual C++ edited resources\r\n"
|
||||
"#include ""afxres.rc"" // Standard components\r\n"
|
||||
"#endif\0"
|
||||
END
|
||||
|
||||
#endif // APSTUDIO_INVOKED
|
||||
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Icon
|
||||
//
|
||||
|
||||
// Icon with lowest ID value placed first to ensure application icon
|
||||
// remains consistent on all systems.
|
||||
IDR_MAINFRAME ICON DISCARDABLE "res\\HogEdit.ico"
|
||||
IDR_HOGEDITYPE ICON DISCARDABLE "res\\HogEditDoc.ico"
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Bitmap
|
||||
//
|
||||
|
||||
IDR_MAINFRAME BITMAP MOVEABLE PURE "res\\Toolbar.bmp"
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Toolbar
|
||||
//
|
||||
|
||||
IDR_MAINFRAME TOOLBAR DISCARDABLE 16, 15
|
||||
BEGIN
|
||||
BUTTON ID_FILE_NEW
|
||||
BUTTON ID_FILE_OPEN
|
||||
BUTTON ID_FILE_SAVE
|
||||
SEPARATOR
|
||||
BUTTON ID_ACTION_IMPORT
|
||||
BUTTON ID_ACTION_INSERT
|
||||
BUTTON ID_ACTION_DELETE
|
||||
BUTTON ID_ACTION_UPDATE
|
||||
BUTTON ID_ACTION_EXTRACT
|
||||
BUTTON ID_ACTION_CREATE
|
||||
SEPARATOR
|
||||
BUTTON ID_APP_ABOUT
|
||||
END
|
||||
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Menu
|
||||
//
|
||||
|
||||
IDR_MAINFRAME MENU PRELOAD DISCARDABLE
|
||||
BEGIN
|
||||
POPUP "&File"
|
||||
BEGIN
|
||||
MENUITEM "&New\tCtrl+N", ID_FILE_NEW
|
||||
MENUITEM "&Open...\tCtrl+O", ID_FILE_OPEN
|
||||
MENUITEM "&Save\tCtrl+S", ID_FILE_SAVE
|
||||
MENUITEM "Save &As...", ID_FILE_SAVE_AS
|
||||
MENUITEM SEPARATOR
|
||||
MENUITEM "E&xit", ID_APP_EXIT
|
||||
END
|
||||
POPUP "&Action"
|
||||
BEGIN
|
||||
MENUITEM "Import Directory...", ID_ACTION_IMPORT
|
||||
MENUITEM "&Add File(s)...", ID_ACTION_INSERT
|
||||
MENUITEM "&Remove Selected File(s)", ID_ACTION_DELETE
|
||||
MENUITEM SEPARATOR
|
||||
MENUITEM "&Update File List", ID_ACTION_UPDATE
|
||||
MENUITEM "&Extract File", ID_ACTION_EXTRACT
|
||||
MENUITEM SEPARATOR
|
||||
MENUITEM "&Create Hog File", ID_ACTION_CREATE
|
||||
END
|
||||
POPUP "&View"
|
||||
BEGIN
|
||||
MENUITEM "&Toolbar", ID_VIEW_TOOLBAR
|
||||
MENUITEM "&Status Bar", ID_VIEW_STATUS_BAR
|
||||
MENUITEM "&Full Row Selection", ID_VIEW_FULL_ROW
|
||||
END
|
||||
POPUP "&Help"
|
||||
BEGIN
|
||||
MENUITEM "&About HogEdit...", ID_APP_ABOUT
|
||||
END
|
||||
END
|
||||
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Accelerator
|
||||
//
|
||||
|
||||
IDR_MAINFRAME ACCELERATORS PRELOAD MOVEABLE PURE
|
||||
BEGIN
|
||||
"C", ID_EDIT_COPY, VIRTKEY, CONTROL, NOINVERT
|
||||
"N", ID_FILE_NEW, VIRTKEY, CONTROL, NOINVERT
|
||||
"O", ID_FILE_OPEN, VIRTKEY, CONTROL, NOINVERT
|
||||
"S", ID_FILE_SAVE, VIRTKEY, CONTROL, NOINVERT
|
||||
"V", ID_EDIT_PASTE, VIRTKEY, CONTROL, NOINVERT
|
||||
VK_BACK, ID_EDIT_UNDO, VIRTKEY, ALT, NOINVERT
|
||||
VK_DELETE, ID_ACTION_DELETE, VIRTKEY, NOINVERT
|
||||
VK_DELETE, ID_EDIT_CUT, VIRTKEY, SHIFT, NOINVERT
|
||||
VK_F6, ID_NEXT_PANE, VIRTKEY, NOINVERT
|
||||
VK_F6, ID_PREV_PANE, VIRTKEY, SHIFT, NOINVERT
|
||||
VK_INSERT, ID_EDIT_COPY, VIRTKEY, CONTROL, NOINVERT
|
||||
VK_INSERT, ID_EDIT_PASTE, VIRTKEY, SHIFT, NOINVERT
|
||||
"X", ID_EDIT_CUT, VIRTKEY, CONTROL, NOINVERT
|
||||
"Z", ID_EDIT_UNDO, VIRTKEY, CONTROL, NOINVERT
|
||||
END
|
||||
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Dialog
|
||||
//
|
||||
|
||||
IDD_ABOUTBOX DIALOG DISCARDABLE 0, 0, 217, 55
|
||||
STYLE DS_MODALFRAME | WS_POPUP | WS_CAPTION | WS_SYSMENU
|
||||
CAPTION "About HogEdit"
|
||||
FONT 8, "MS Sans Serif"
|
||||
BEGIN
|
||||
ICON IDR_MAINFRAME,IDC_STATIC,11,17,21,20
|
||||
LTEXT "HogEdit Version 1.0",IDC_STATIC,40,10,119,8,SS_NOPREFIX
|
||||
LTEXT "Copyright (C) 1998",IDC_STATIC,40,34,119,8
|
||||
DEFPUSHBUTTON "OK",IDOK,178,6,32,14,WS_GROUP
|
||||
LTEXT "Outrage Entertainment",IDC_STATIC,40,22,72,8
|
||||
END
|
||||
|
||||
IDD_HOGINFO DIALOG DISCARDABLE 0, 0, 290, 117
|
||||
STYLE DS_MODALFRAME | WS_POPUP | WS_CAPTION | WS_SYSMENU
|
||||
CAPTION "Hog File Creation"
|
||||
FONT 8, "MS Sans Serif"
|
||||
BEGIN
|
||||
DEFPUSHBUTTON "Create HOG",IDOK,79,95,50,14
|
||||
PUSHBUTTON "Cancel",IDCANCEL,159,95,50,14
|
||||
LTEXT "File(s):",IDC_STATIC,15,20,40,8
|
||||
LTEXT "Total Size:",IDC_STATIC,15,40,40,8
|
||||
LTEXT "Location:",IDC_STATIC,15,70,40,8
|
||||
LTEXT "0",IDC_HOGINFO_FILES,65,20,211,8
|
||||
LTEXT "0 bytes",IDC_HOGINFO_SIZE_BYTES,65,40,212,8
|
||||
GROUPBOX "HOG file properties:",IDC_STATIC,7,5,276,80
|
||||
LTEXT "(0 MB)",IDC_HOGINFO_SIZE_MB,65,50,210,8
|
||||
LTEXT "None",IDC_HOGINFO_LOCATION,65,70,210,8
|
||||
END
|
||||
|
||||
|
||||
#ifndef _MAC
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Version
|
||||
//
|
||||
|
||||
VS_VERSION_INFO VERSIONINFO
|
||||
FILEVERSION 1,0,0,1
|
||||
PRODUCTVERSION 1,0,0,1
|
||||
FILEFLAGSMASK 0x3fL
|
||||
#ifdef _DEBUG
|
||||
FILEFLAGS 0x1L
|
||||
#else
|
||||
FILEFLAGS 0x0L
|
||||
#endif
|
||||
FILEOS 0x4L
|
||||
FILETYPE 0x1L
|
||||
FILESUBTYPE 0x0L
|
||||
BEGIN
|
||||
BLOCK "StringFileInfo"
|
||||
BEGIN
|
||||
BLOCK "040904B0"
|
||||
BEGIN
|
||||
VALUE "CompanyName", "\0"
|
||||
VALUE "FileDescription", "HogEdit MFC Application\0"
|
||||
VALUE "FileVersion", "1, 0, 0, 1\0"
|
||||
VALUE "InternalName", "HogEdit\0"
|
||||
VALUE "LegalCopyright", "Copyright (C) 1998\0"
|
||||
VALUE "LegalTrademarks", "\0"
|
||||
VALUE "OriginalFilename", "HogEdit.EXE\0"
|
||||
VALUE "ProductName", "HogEdit Application\0"
|
||||
VALUE "ProductVersion", "1, 0, 0, 1\0"
|
||||
END
|
||||
END
|
||||
BLOCK "VarFileInfo"
|
||||
BEGIN
|
||||
VALUE "Translation", 0x409, 1200
|
||||
END
|
||||
END
|
||||
|
||||
#endif // !_MAC
|
||||
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// DESIGNINFO
|
||||
//
|
||||
|
||||
#ifdef APSTUDIO_INVOKED
|
||||
GUIDELINES DESIGNINFO DISCARDABLE
|
||||
BEGIN
|
||||
IDD_ABOUTBOX, DIALOG
|
||||
BEGIN
|
||||
LEFTMARGIN, 7
|
||||
RIGHTMARGIN, 210
|
||||
TOPMARGIN, 6
|
||||
BOTTOMMARGIN, 48
|
||||
END
|
||||
|
||||
IDD_HOGINFO, DIALOG
|
||||
BEGIN
|
||||
LEFTMARGIN, 7
|
||||
RIGHTMARGIN, 283
|
||||
TOPMARGIN, 7
|
||||
BOTTOMMARGIN, 110
|
||||
END
|
||||
END
|
||||
#endif // APSTUDIO_INVOKED
|
||||
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// String Table
|
||||
//
|
||||
|
||||
STRINGTABLE PRELOAD DISCARDABLE
|
||||
BEGIN
|
||||
IDR_MAINFRAME "HogEdit v1.0\n\nHogEdi\n\n\nHogEdit.Document\nHogEdi Document"
|
||||
END
|
||||
|
||||
STRINGTABLE PRELOAD DISCARDABLE
|
||||
BEGIN
|
||||
AFX_IDS_APP_TITLE "HogEdit"
|
||||
AFX_IDS_IDLEMESSAGE "Ready"
|
||||
END
|
||||
|
||||
STRINGTABLE DISCARDABLE
|
||||
BEGIN
|
||||
ID_INDICATOR_EXT "EXT"
|
||||
ID_INDICATOR_CAPS "CAP"
|
||||
ID_INDICATOR_NUM "NUM"
|
||||
ID_INDICATOR_SCRL "SCRL"
|
||||
ID_INDICATOR_OVR "OVR"
|
||||
ID_INDICATOR_REC "REC"
|
||||
END
|
||||
|
||||
STRINGTABLE DISCARDABLE
|
||||
BEGIN
|
||||
ID_FILE_NEW "Create a new document\nNew"
|
||||
ID_FILE_OPEN "Open an existing document\nOpen"
|
||||
ID_FILE_CLOSE "Close the active document\nClose"
|
||||
ID_FILE_SAVE "Save the active document\nSave"
|
||||
ID_FILE_SAVE_AS "Save the active document with a new name\nSave As"
|
||||
END
|
||||
|
||||
STRINGTABLE DISCARDABLE
|
||||
BEGIN
|
||||
ID_APP_ABOUT "Display program information, version number and copyright\nAbout"
|
||||
ID_APP_EXIT "Quit the application; prompts to save documents\nExit"
|
||||
END
|
||||
|
||||
STRINGTABLE DISCARDABLE
|
||||
BEGIN
|
||||
ID_FILE_MRU_FILE1 "Open this document"
|
||||
ID_FILE_MRU_FILE2 "Open this document"
|
||||
ID_FILE_MRU_FILE3 "Open this document"
|
||||
ID_FILE_MRU_FILE4 "Open this document"
|
||||
ID_FILE_MRU_FILE5 "Open this document"
|
||||
ID_FILE_MRU_FILE6 "Open this document"
|
||||
ID_FILE_MRU_FILE7 "Open this document"
|
||||
ID_FILE_MRU_FILE8 "Open this document"
|
||||
ID_FILE_MRU_FILE9 "Open this document"
|
||||
ID_FILE_MRU_FILE10 "Open this document"
|
||||
ID_FILE_MRU_FILE11 "Open this document"
|
||||
ID_FILE_MRU_FILE12 "Open this document"
|
||||
ID_FILE_MRU_FILE13 "Open this document"
|
||||
ID_FILE_MRU_FILE14 "Open this document"
|
||||
ID_FILE_MRU_FILE15 "Open this document"
|
||||
ID_FILE_MRU_FILE16 "Open this document"
|
||||
END
|
||||
|
||||
STRINGTABLE DISCARDABLE
|
||||
BEGIN
|
||||
ID_NEXT_PANE "Switch to the next window pane\nNext Pane"
|
||||
ID_PREV_PANE "Switch back to the previous window pane\nPrevious Pane"
|
||||
END
|
||||
|
||||
STRINGTABLE DISCARDABLE
|
||||
BEGIN
|
||||
ID_WINDOW_SPLIT "Split the active window into panes\nSplit"
|
||||
END
|
||||
|
||||
STRINGTABLE DISCARDABLE
|
||||
BEGIN
|
||||
ID_EDIT_CLEAR "Erase the selection\nErase"
|
||||
ID_EDIT_CLEAR_ALL "Erase everything\nErase All"
|
||||
ID_EDIT_COPY "Copy the selection and put it on the Clipboard\nCopy"
|
||||
ID_EDIT_CUT "Cut the selection and put it on the Clipboard\nCut"
|
||||
ID_EDIT_FIND "Find the specified text\nFind"
|
||||
ID_EDIT_PASTE "Insert Clipboard contents\nPaste"
|
||||
ID_EDIT_REPEAT "Repeat the last action\nRepeat"
|
||||
ID_EDIT_REPLACE "Replace specific text with different text\nReplace"
|
||||
ID_EDIT_SELECT_ALL "Select the entire document\nSelect All"
|
||||
ID_EDIT_UNDO "Undo the last action\nUndo"
|
||||
ID_EDIT_REDO "Redo the previously undone action\nRedo"
|
||||
END
|
||||
|
||||
STRINGTABLE DISCARDABLE
|
||||
BEGIN
|
||||
ID_VIEW_TOOLBAR "Show or hide the toolbar\nToggle ToolBar"
|
||||
ID_VIEW_STATUS_BAR "Show or hide the status bar\nToggle StatusBar"
|
||||
END
|
||||
|
||||
STRINGTABLE DISCARDABLE
|
||||
BEGIN
|
||||
AFX_IDS_SCSIZE "Change the window size"
|
||||
AFX_IDS_SCMOVE "Change the window position"
|
||||
AFX_IDS_SCMINIMIZE "Reduce the window to an icon"
|
||||
AFX_IDS_SCMAXIMIZE "Enlarge the window to full size"
|
||||
AFX_IDS_SCNEXTWINDOW "Switch to the next document window"
|
||||
AFX_IDS_SCPREVWINDOW "Switch to the previous document window"
|
||||
AFX_IDS_SCCLOSE "Close the active window and prompts to save the documents"
|
||||
END
|
||||
|
||||
STRINGTABLE DISCARDABLE
|
||||
BEGIN
|
||||
AFX_IDS_SCRESTORE "Restore the window to normal size"
|
||||
AFX_IDS_SCTASKLIST "Activate Task List"
|
||||
IDS_STRING61204 "ID"
|
||||
ID_INDICATOR_FILES "Total Files: XXXXXX"
|
||||
END
|
||||
|
||||
STRINGTABLE DISCARDABLE
|
||||
BEGIN
|
||||
ID_ACTION_INSERT "Add files to the list\nAdd File(s)"
|
||||
ID_ACTION_DELETE "Removes selected file(s) from the file list\nRemove file(s)"
|
||||
ID_ACTION_UPDATE "Updates the list with current file info (.rib's only)\nUpdate List"
|
||||
ID_ACTION_BUILD "Builds the Hog file and saves it to disk"
|
||||
ID_ACTION_CREATE "Creates a Hog file and saves it to disk\nCreate Hog File"
|
||||
ID_VIEW_FULL_ROW "Turn on full row selection"
|
||||
ID_ACTION_EXTRACT "Extracts the selected file from the current .hog file\nExtract File"
|
||||
ID_ACTION_IMPORT "Imports all files contained within the specified directory.\nImport Directory"
|
||||
END
|
||||
|
||||
#endif // English (U.S.) resources
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
|
||||
|
||||
#ifndef APSTUDIO_INVOKED
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Generated from the TEXTINCLUDE 3 resource.
|
||||
//
|
||||
#define _AFX_NO_SPLITTER_RESOURCES
|
||||
#define _AFX_NO_OLE_RESOURCES
|
||||
#define _AFX_NO_TRACKER_RESOURCES
|
||||
#define _AFX_NO_PROPERTY_RESOURCES
|
||||
|
||||
#if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_ENU)
|
||||
#ifdef _WIN32
|
||||
LANGUAGE 9, 1
|
||||
#pragma code_page(1252)
|
||||
#endif
|
||||
#include "res\HogEdit.rc2" // non-Microsoft Visual C++ edited resources
|
||||
#include "afxres.rc" // Standard components
|
||||
#endif
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
#endif // not APSTUDIO_INVOKED
|
||||
|
965
hogedit/HogEditDoc.cpp
Normal file
965
hogedit/HogEditDoc.cpp
Normal file
@ -0,0 +1,965 @@
|
||||
/*
|
||||
* $Logfile: /DescentIII/Main/hogedit/HogEditDoc.cpp $
|
||||
* $Revision: 1.1.1.1 $
|
||||
* $Date: 2003-08-26 03:57:56 $
|
||||
* $Author: kevinb $
|
||||
*
|
||||
*
|
||||
*
|
||||
* $Log: not supported by cvs2svn $
|
||||
*
|
||||
* 10 5/05/99 12:53p Nate
|
||||
* Added support for multiple file extraction
|
||||
*
|
||||
* 9 10/30/98 11:15a Nate
|
||||
* Added support for modification of hog files.
|
||||
*
|
||||
* 8 10/09/98 4:50p Nate
|
||||
*
|
||||
* 7 9/17/98 4:29p Nate
|
||||
* Added Import Directory option.
|
||||
*
|
||||
* 6 8/14/98 4:38p Nate
|
||||
* Fixed a few minor bugs and added better error reporting
|
||||
*
|
||||
* 5 8/14/98 1:01p Nate
|
||||
* Added better error reporting for the HogEditor
|
||||
*
|
||||
* 4 7/22/98 2:38p Nate
|
||||
* Added Modified File prompt when exiting
|
||||
*
|
||||
* 3 7/20/98 3:35p Nate
|
||||
* Added more Editing functionality
|
||||
*
|
||||
* 2 7/15/98 12:31p Nate
|
||||
* Initial version
|
||||
*
|
||||
* $NoKeywords: $
|
||||
*/
|
||||
|
||||
// HogEditDoc.cpp : implementation of the CHogEditDoc class
|
||||
//
|
||||
|
||||
#include "stdafx.h"
|
||||
#include <afxtempl.h>
|
||||
#include <sys\stat.h>
|
||||
#include "HogEdit.h"
|
||||
|
||||
#include "hogfile.h"
|
||||
#include "HogEditDoc.h"
|
||||
#include <io.h>
|
||||
|
||||
#ifdef _DEBUG
|
||||
#define new DEBUG_NEW
|
||||
#undef THIS_FILE
|
||||
static char THIS_FILE[] = __FILE__;
|
||||
#endif
|
||||
|
||||
|
||||
bool DocModified; // is document modified.
|
||||
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// CHogEditDoc
|
||||
|
||||
IMPLEMENT_DYNCREATE(CHogEditDoc, CDocument)
|
||||
|
||||
BEGIN_MESSAGE_MAP(CHogEditDoc, CDocument)
|
||||
//{{AFX_MSG_MAP(CHogEditDoc)
|
||||
ON_UPDATE_COMMAND_UI(ID_ACTION_INSERT, OnUpdateActionInsert)
|
||||
ON_UPDATE_COMMAND_UI(ID_ACTION_CREATE, OnUpdateActionCreate)
|
||||
ON_UPDATE_COMMAND_UI(ID_FILE_SAVE, OnUpdateFileSave)
|
||||
ON_UPDATE_COMMAND_UI(ID_FILE_SAVE_AS, OnUpdateFileSaveAs)
|
||||
ON_UPDATE_COMMAND_UI(ID_ACTION_UPDATE, OnUpdateActionUpdate)
|
||||
ON_UPDATE_COMMAND_UI(ID_ACTION_IMPORT, OnUpdateActionImport)
|
||||
//}}AFX_MSG_MAP
|
||||
END_MESSAGE_MAP()
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// CHogEditDoc construction/destruction
|
||||
|
||||
CHogEditDoc::CHogEditDoc()
|
||||
{
|
||||
// TODO: add one-time construction code here
|
||||
|
||||
}
|
||||
|
||||
CHogEditDoc::~CHogEditDoc()
|
||||
{
|
||||
}
|
||||
|
||||
BOOL CHogEditDoc::OnNewDocument()
|
||||
{
|
||||
if (!CDocument::OnNewDocument())
|
||||
return FALSE;
|
||||
|
||||
// TODO: add reinitialization code here
|
||||
// (SDI documents will reuse this document)
|
||||
NewDocument();
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// CHogEditDoc serialization
|
||||
|
||||
void CHogEditDoc::Serialize(CArchive& ar)
|
||||
{
|
||||
if (ar.IsStoring())
|
||||
{
|
||||
// TODO: add storing code here
|
||||
}
|
||||
else
|
||||
{
|
||||
// TODO: add loading code here
|
||||
}
|
||||
}
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// CHogEditDoc diagnostics
|
||||
|
||||
#ifdef _DEBUG
|
||||
void CHogEditDoc::AssertValid() const
|
||||
{
|
||||
CDocument::AssertValid();
|
||||
}
|
||||
|
||||
void CHogEditDoc::Dump(CDumpContext& dc) const
|
||||
{
|
||||
CDocument::Dump(dc);
|
||||
}
|
||||
#endif //_DEBUG
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// CHogEditDoc commands
|
||||
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////////
|
||||
// These functions perform most of the meaty tasks of this interface.
|
||||
|
||||
|
||||
// creates a new (and empty) hog library.
|
||||
void CHogEditDoc::NewDocument()
|
||||
{
|
||||
// Initialize the hog library structure
|
||||
Library.filename[0]='\0';
|
||||
Library.flags=0;
|
||||
Library.num_entries=0;
|
||||
|
||||
// clear out all lists
|
||||
Library.filelist.RemoveAll();
|
||||
|
||||
// mark as not modified.
|
||||
DocModified = FALSE;
|
||||
m_StaticHog = FALSE;
|
||||
m_DocumentName = "Untitled.rib";
|
||||
m_NoNameChosen = TRUE;
|
||||
}
|
||||
|
||||
|
||||
// loads a RIB file or HOG file.
|
||||
int CHogEditDoc::LoadDocument(CString& name)
|
||||
{
|
||||
char *ascii_name;
|
||||
char ext[_MAX_EXT];
|
||||
int res;
|
||||
|
||||
// Get ascii string from name
|
||||
ascii_name=name.GetBuffer(0);
|
||||
|
||||
// extract file extension from name
|
||||
_splitpath(ascii_name, NULL, NULL, NULL, ext);
|
||||
|
||||
// load either .rib or .hog file
|
||||
if (strcmpi(ext, ".rib") == 0) {
|
||||
res=LoadRib(ascii_name);
|
||||
if(res) m_StaticHog = false;
|
||||
}
|
||||
else {
|
||||
res=LoadHog(ascii_name);
|
||||
if(res) m_StaticHog = true;
|
||||
}
|
||||
|
||||
// Set the new document name
|
||||
if(res) m_DocumentName = name;
|
||||
|
||||
return(res);
|
||||
}
|
||||
|
||||
// saves a RIB file
|
||||
int CHogEditDoc::SaveDocument(CString& name)
|
||||
{
|
||||
char *ascii_name;
|
||||
char ext[_MAX_EXT];
|
||||
int res;
|
||||
|
||||
ascii_name=name.GetBuffer(0);
|
||||
|
||||
// name dialog
|
||||
_splitpath(ascii_name, NULL, NULL, NULL, ext);
|
||||
|
||||
// load either .rib or .hog file
|
||||
if (strcmpi(ext, ".rib") == 0) {
|
||||
res=SaveRib(ascii_name);
|
||||
if(res) m_StaticHog = false;
|
||||
}
|
||||
else {
|
||||
res=SaveHog(ascii_name);
|
||||
if(res) m_StaticHog = true;
|
||||
}
|
||||
return(res);
|
||||
}
|
||||
|
||||
// loads a RIB file
|
||||
int CHogEditDoc::LoadRib(const char *pathname)
|
||||
{
|
||||
hog_library_entry entry;
|
||||
FILE *rib_fp;
|
||||
char tag[10];
|
||||
int j;
|
||||
|
||||
// open the file
|
||||
rib_fp = fopen( pathname, "rb" );
|
||||
if ( rib_fp == NULL ) {
|
||||
OutputDebugString("Could not open file.\n");
|
||||
return false;
|
||||
}
|
||||
|
||||
// write the tag
|
||||
if (!fread(tag, strlen(RIB_TAG_STR), 1, rib_fp )) {
|
||||
fclose(rib_fp);
|
||||
return false;
|
||||
}
|
||||
|
||||
// Make tag string null terminated
|
||||
tag[strlen(RIB_TAG_STR)]='\0';
|
||||
|
||||
// Check if string has a valid tag
|
||||
if(strcmp(tag,RIB_TAG_STR)!=0) {
|
||||
OutputDebugString("File is not a RIB file!\n");
|
||||
fclose(rib_fp);
|
||||
return false;
|
||||
}
|
||||
|
||||
// Read in the hog filename
|
||||
if(!fread(Library.filename,sizeof(char),PSPATHNAME_LEN,rib_fp)) {
|
||||
fclose(rib_fp);
|
||||
return false;
|
||||
}
|
||||
|
||||
// Read in the hog file flags
|
||||
if(!fread(&Library.flags,sizeof(Library.flags),1,rib_fp)) {
|
||||
fclose(rib_fp);
|
||||
return false;
|
||||
}
|
||||
|
||||
// Read the number of file entries
|
||||
if (!fread(&Library.num_entries, sizeof(Library.num_entries), 1, rib_fp )) {
|
||||
fclose(rib_fp);
|
||||
return false;
|
||||
}
|
||||
|
||||
// read the hogfile entries
|
||||
for(j=0;j<Library.num_entries;j++) {
|
||||
if(!ReadHogLibEntry(rib_fp,&entry)) {
|
||||
fclose(rib_fp);
|
||||
return false;
|
||||
}
|
||||
Library.filelist.AddTail(entry);
|
||||
}
|
||||
|
||||
fclose(rib_fp);
|
||||
|
||||
char str[256];
|
||||
sprintf(str,"Read %d entries from %s.\n",Library.num_entries,pathname);
|
||||
OutputDebugString(str);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
// loads a HOG file.
|
||||
int CHogEditDoc::LoadHog(const char *pathname)
|
||||
{
|
||||
int i;
|
||||
int table_pos;
|
||||
FILE *hog_fp;
|
||||
tHogHeader header;
|
||||
tHogFileEntry file_entry;
|
||||
hog_library_entry lib_entry;
|
||||
char tag[10];
|
||||
int offset;
|
||||
|
||||
// open the file
|
||||
hog_fp = fopen( pathname, "rb" );
|
||||
if ( hog_fp == NULL ) {
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
// read the tag
|
||||
if (!fread(tag, strlen(HOG_TAG_STR), 1, hog_fp )) {
|
||||
fclose(hog_fp);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
// Make tag string null terminated
|
||||
tag[strlen(HOG_TAG_STR)]='\0';
|
||||
|
||||
// Check if string has a valid tag
|
||||
if(strcmp(tag,HOG_TAG_STR)!=0) {
|
||||
OutputDebugString("File is not a HOG file!\n");
|
||||
fclose(hog_fp);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
// Get number of entries
|
||||
if (!fread(&header.nfiles,sizeof(header.nfiles),1,hog_fp)) {
|
||||
fclose(hog_fp);
|
||||
return FALSE;
|
||||
}
|
||||
Library.num_entries=header.nfiles;
|
||||
|
||||
// Get the file data offset
|
||||
if (!fread(&header.file_data_offset,sizeof(header.file_data_offset),1,hog_fp)) {
|
||||
fclose(hog_fp);
|
||||
return FALSE;
|
||||
}
|
||||
offset=header.file_data_offset;
|
||||
|
||||
// Calculate file position of index table
|
||||
table_pos = strlen(HOG_TAG_STR) + HOG_HDR_SIZE;
|
||||
|
||||
// Scan ahead to start of entry table
|
||||
fseek(hog_fp,table_pos,SEEK_SET);
|
||||
|
||||
// Read in the entries and store them in the Library list
|
||||
for (i = 0; i < Library.num_entries; i++)
|
||||
{
|
||||
if (!ReadHogEntry(hog_fp, &file_entry)) {
|
||||
fclose(hog_fp);
|
||||
return FALSE;
|
||||
}
|
||||
strcpy(lib_entry.path, "N/A");
|
||||
strcpy(lib_entry.name, file_entry.name);
|
||||
lib_entry.length=file_entry.len;
|
||||
lib_entry.timestamp=file_entry.timestamp;
|
||||
lib_entry.flags=file_entry.flags;
|
||||
lib_entry.offset=offset;
|
||||
|
||||
offset+=lib_entry.length; // get offset for next file
|
||||
|
||||
Library.filelist.AddTail(lib_entry);
|
||||
}
|
||||
|
||||
// cleanup
|
||||
fclose(hog_fp);
|
||||
|
||||
char str[256];
|
||||
sprintf(str,"Read %d entries from %s.\n",Library.num_entries,pathname);
|
||||
OutputDebugString(str);
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
// saves a HOG file.
|
||||
int CHogEditDoc::SaveHog(const char *pathname)
|
||||
{
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
// saves a RIB file
|
||||
int CHogEditDoc::SaveRib(const char *pathname)
|
||||
{
|
||||
FILE *rib_fp;
|
||||
POSITION pos;
|
||||
hog_library_entry entry;
|
||||
|
||||
|
||||
// create new file
|
||||
rib_fp = fopen( pathname, "wb" );
|
||||
if ( rib_fp == NULL ) {
|
||||
OutputDebugString("Could not open file.\n");
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
// write the tag
|
||||
if (!fwrite(RIB_TAG_STR, strlen(RIB_TAG_STR), 1, rib_fp )) {
|
||||
OutputDebugString("Could not write header tag.\n");
|
||||
fclose(rib_fp);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
// write out the hog filename
|
||||
if(!fwrite(Library.filename,sizeof(char),PSPATHNAME_LEN,rib_fp)) {
|
||||
fclose(rib_fp);
|
||||
return false;
|
||||
}
|
||||
|
||||
// write out the hog file flags
|
||||
if(!fwrite(&Library.flags,sizeof(Library.flags),1,rib_fp)) {
|
||||
fclose(rib_fp);
|
||||
return false;
|
||||
}
|
||||
|
||||
// write out the number of entries
|
||||
Library.num_entries=Library.filelist.GetCount();
|
||||
if(!fwrite(&Library.num_entries,sizeof(Library.num_entries),1,rib_fp)) {
|
||||
fclose(rib_fp);
|
||||
return false;
|
||||
}
|
||||
|
||||
// write out the hogfile entries
|
||||
pos = Library.filelist.GetHeadPosition();
|
||||
while (pos)
|
||||
{
|
||||
entry = Library.filelist.GetNext(pos);
|
||||
if(!WriteHogLibEntry(rib_fp,&entry)) {
|
||||
fclose(rib_fp);
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
fclose(rib_fp);
|
||||
|
||||
char str[256];
|
||||
sprintf(str,"Writing %d entries to %s...\n",Library.num_entries,pathname);
|
||||
OutputDebugString(str);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
// Fills given entry structure with given file's data, and adds entry to Library list
|
||||
int CHogEditDoc::AddFile(const char *pathname, hog_library_entry *entry)
|
||||
{
|
||||
struct _stat filestat;
|
||||
char temp_filename[PSPATHNAME_LEN];
|
||||
char test_filename[PSPATHNAME_LEN];
|
||||
char filename[PSFILENAME_LEN+1];
|
||||
char ext[_MAX_EXT];
|
||||
unsigned length;
|
||||
long timestamp;
|
||||
POSITION pos;
|
||||
char path[PSPATHNAME_LEN];
|
||||
char drive[PSPATHNAME_LEN];
|
||||
char newpath[PSPATHNAME_LEN];
|
||||
hog_library_entry temp_entry;
|
||||
|
||||
// Get file info
|
||||
if (_stat(pathname, &filestat) != 0) {
|
||||
return ADDFILE_STAT_ERROR;
|
||||
}
|
||||
|
||||
// Get just the filename
|
||||
_splitpath(pathname, NULL, NULL, temp_filename, ext);
|
||||
|
||||
|
||||
// Check if filename is too big
|
||||
sprintf(test_filename, "%s%s", temp_filename, ext);
|
||||
if( strlen(test_filename) > PSFILENAME_LEN )
|
||||
return ADDFILE_LONG_FNAME_ERROR;
|
||||
|
||||
sprintf(filename, "%s%s", temp_filename, ext);
|
||||
|
||||
length=filestat.st_size;
|
||||
timestamp=filestat.st_mtime;
|
||||
|
||||
_splitpath(pathname, drive, path, NULL, NULL);
|
||||
sprintf(newpath, "%s%s", drive, path);
|
||||
strcpy(path, filename);
|
||||
|
||||
// See if this entry is already in the library
|
||||
pos = Library.filelist.GetHeadPosition();
|
||||
while (pos)
|
||||
{
|
||||
temp_entry = Library.filelist.GetNext(pos);
|
||||
if (!strcmpi(temp_entry.name, filename) /*&& !strcmpi(temp_entry.path, newpath)*/)
|
||||
return ADDFILE_DUP_FILE_ERROR;
|
||||
}
|
||||
|
||||
// this is a new entry, so set it up and add it to the list!
|
||||
strcpy(entry->path, newpath);
|
||||
strcpy(entry->name, filename);
|
||||
entry->length = length;
|
||||
entry->timestamp = timestamp;
|
||||
entry->offset = -1; // Entry was not read in from a hogfile
|
||||
|
||||
Library.filelist.AddTail(*entry);
|
||||
DocModified=true;
|
||||
|
||||
return ADDFILE_OK;
|
||||
}
|
||||
|
||||
|
||||
// Checks to see if file has been modified, and updates entry accordingly
|
||||
int CHogEditDoc::UpdatedFileCheck(hog_library_entry *entry)
|
||||
{
|
||||
struct _stat filestat;
|
||||
char full_name[PSPATHNAME_LEN];
|
||||
|
||||
sprintf(full_name,"%s%s",entry->path,entry->name);
|
||||
|
||||
// Get file info
|
||||
if (_stat(full_name, &filestat) != 0)
|
||||
return FILE_IS_GONE;
|
||||
|
||||
// has file changed?
|
||||
if(entry->timestamp == filestat.st_mtime)
|
||||
return FILE_IS_SAME;
|
||||
|
||||
// update entries
|
||||
entry->length=filestat.st_size;
|
||||
entry->timestamp=filestat.st_mtime;
|
||||
|
||||
return FILE_HAS_CHANGED;
|
||||
}
|
||||
|
||||
|
||||
// Loads a Hog library entry structure
|
||||
bool CHogEditDoc::ReadHogLibEntry(FILE *fp, hog_library_entry *entry)
|
||||
{
|
||||
int res=0;
|
||||
res = fread(entry->path, sizeof(char), PSPATHNAME_LEN, fp);
|
||||
res = fread(entry->name, sizeof(char), PSFILENAME_LEN+1, fp);
|
||||
res = fread(&entry->flags, sizeof(entry->flags), 1, fp);
|
||||
res = fread(&entry->length, sizeof(entry->length), 1, fp);
|
||||
res = fread(&entry->timestamp, sizeof(entry->timestamp), 1, fp);
|
||||
|
||||
entry->offset = -1; // Entry was not read in from a hogfile
|
||||
|
||||
if (res)
|
||||
return TRUE;
|
||||
else
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
|
||||
// Saves a Hog library entry structure
|
||||
bool CHogEditDoc::WriteHogLibEntry(FILE *fp, hog_library_entry *entry)
|
||||
{
|
||||
int res=0;
|
||||
res = fwrite(entry->path, sizeof(char), PSPATHNAME_LEN, fp);
|
||||
res = fwrite(entry->name, sizeof(char), PSFILENAME_LEN+1, fp);
|
||||
res = fwrite(&entry->flags, sizeof(entry->flags), 1, fp);
|
||||
res = fwrite(&entry->length, sizeof(entry->length), 1, fp);
|
||||
res = fwrite(&entry->timestamp, sizeof(entry->timestamp), 1, fp);
|
||||
|
||||
if (res)
|
||||
return TRUE;
|
||||
else
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
// Allocates and fills the hog library filenames list
|
||||
bool CHogEditDoc::CreateFilenameList(char ***filenames)
|
||||
{
|
||||
char full_name[PSPATHNAME_LEN];
|
||||
POSITION pos;
|
||||
hog_library_entry temp_entry;
|
||||
int j;
|
||||
|
||||
// Get the number of filenames
|
||||
Library.num_entries=Library.filelist.GetCount();
|
||||
|
||||
// Allocate the list of filename pointers
|
||||
*filenames=new (char (*[Library.num_entries]));
|
||||
if(*filenames==NULL) return FALSE;
|
||||
|
||||
// Allocate and store each filename in the Library
|
||||
j=0;
|
||||
pos=Library.filelist.GetHeadPosition();
|
||||
while (pos!=NULL)
|
||||
{
|
||||
temp_entry = Library.filelist.GetNext(pos);
|
||||
|
||||
// Only include the path if it's added from a rib file
|
||||
if(temp_entry.offset==-1)
|
||||
sprintf(full_name,"%s%s",temp_entry.path,temp_entry.name);
|
||||
else
|
||||
sprintf(full_name,"%s",temp_entry.name);
|
||||
|
||||
(*filenames)[j]=new char[strlen(full_name)+1];
|
||||
if((*filenames)[j]==NULL) {OutputDebugString("Outta memory!\n");return FALSE;}
|
||||
|
||||
strcpy((*filenames)[j],full_name);
|
||||
|
||||
/*
|
||||
sprintf(full_name,"%d - %s\n",j,(*filenames)[j]);
|
||||
OutputDebugString(full_name);
|
||||
*/
|
||||
j++;
|
||||
}
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
// Comparison function for qsort
|
||||
int compare( const void *arg1, const void *arg2 )
|
||||
{
|
||||
char filename1[PSPATHNAME_LEN];
|
||||
char filename2[PSPATHNAME_LEN];
|
||||
char ext1[_MAX_EXT];
|
||||
char ext2[_MAX_EXT];
|
||||
|
||||
// Isolate just the filenames (w/extensions) for the compare
|
||||
_splitpath(* (char **)arg1, NULL, NULL, filename1, ext1);
|
||||
_splitpath(* (char **)arg2, NULL, NULL, filename2, ext2);
|
||||
strcat(filename1,ext1);
|
||||
strcat(filename2,ext2);
|
||||
|
||||
// Do a case-insensitive, asending order comparison
|
||||
return _stricmp(filename1, filename2);
|
||||
}
|
||||
|
||||
// Quicksort the list of filenames
|
||||
void CHogEditDoc::SortFilenameList(char **filenames)
|
||||
{
|
||||
int count;
|
||||
|
||||
count=Library.num_entries;
|
||||
qsort((void *)filenames,(size_t)count,sizeof(char *),compare);
|
||||
}
|
||||
|
||||
// Deallocates the hog library filenames list (Library.num_entries must be valid!)
|
||||
bool CHogEditDoc::DeleteFilenameList(char **filenames)
|
||||
{
|
||||
int j;
|
||||
|
||||
// Delete each filename
|
||||
for(j=0;j<Library.num_entries;j++)
|
||||
delete[] filenames[j];
|
||||
|
||||
// Delete the list of pointers
|
||||
delete[] filenames;
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
// Return estimate (in bytes) of the final Hog File Size
|
||||
unsigned int CHogEditDoc::CalcHogFileSize(void)
|
||||
{
|
||||
unsigned int total;
|
||||
POSITION pos;
|
||||
hog_library_entry temp_entry;
|
||||
|
||||
total=0;
|
||||
|
||||
// Add header and file table sizes
|
||||
total += strlen(HOG_TAG_STR);
|
||||
total += HOG_HDR_SIZE;
|
||||
total +=(sizeof(tHogFileEntry) * Library.filelist.GetCount());
|
||||
|
||||
// Add file lengths
|
||||
pos=Library.filelist.GetHeadPosition();
|
||||
while (pos!=NULL)
|
||||
{
|
||||
temp_entry = Library.filelist.GetNext(pos);
|
||||
total += temp_entry.length;
|
||||
}
|
||||
|
||||
return(total);
|
||||
}
|
||||
|
||||
// Extracts a file from the current hog file
|
||||
bool CHogEditDoc::ExtractFile(int file_pos, unsigned file_len, char *out_fname)
|
||||
{
|
||||
FILE *hog_fp, *out_fp;
|
||||
|
||||
// If current file isn't a hog file, get outta here
|
||||
if(!m_StaticHog) return FALSE;
|
||||
|
||||
// Open input (hog) file
|
||||
hog_fp = fopen( m_DocumentName, "rb" );
|
||||
if ( hog_fp == NULL ) {
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
// Open output file
|
||||
out_fp = fopen( out_fname, "wb" );
|
||||
if ( out_fp == NULL ) {
|
||||
fclose(hog_fp);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
// Seek to correct place in hog file
|
||||
if(fseek(hog_fp,file_pos,SEEK_SET)!=0) {
|
||||
fclose(hog_fp);
|
||||
fclose(out_fp);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
// Copy out the file
|
||||
if(!FileCopy(out_fp,hog_fp,file_len)) {
|
||||
fclose(hog_fp);
|
||||
fclose(out_fp);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
// Close em up
|
||||
fclose(out_fp);
|
||||
fclose(hog_fp);
|
||||
|
||||
return(TRUE);
|
||||
}
|
||||
|
||||
// Opens and returns a pointer to the file (matching the given entry name)
|
||||
// within the current hog file, returns NULL if file is not in the hog
|
||||
FILE *CHogEditDoc::FindFileInHog(char *hog_fname,tHogFileEntry *table_entry)
|
||||
{
|
||||
FILE *hog_fp;
|
||||
POSITION pos;
|
||||
hog_library_entry entry;
|
||||
bool found_in_hog;
|
||||
|
||||
// If current file isn't a hog, get outta here
|
||||
if(!m_StaticHog) return(NULL);
|
||||
|
||||
// Search the current entry list for the given filename
|
||||
pos = Library.filelist.GetHeadPosition();
|
||||
found_in_hog=FALSE;
|
||||
while (pos!=NULL)
|
||||
{
|
||||
entry = Library.filelist.GetNext(pos);
|
||||
if (!strcmpi(entry.name, table_entry->name)) {
|
||||
found_in_hog=TRUE;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
// If the filename wasn't in the list, get outta here
|
||||
if(!found_in_hog) return(NULL);
|
||||
|
||||
// If the found file is actually an "external" file, get outta here
|
||||
if(entry.offset == -1) return(NULL);
|
||||
|
||||
// fill in the entry data for this file
|
||||
table_entry->flags = entry.flags;
|
||||
table_entry->len = entry.length;
|
||||
table_entry->timestamp = entry.timestamp;
|
||||
|
||||
// open the source hog file
|
||||
hog_fp = fopen( hog_fname, "rb" );
|
||||
if ( hog_fp == NULL ) {
|
||||
return(NULL);
|
||||
}
|
||||
|
||||
// Seek to correct place in hog file
|
||||
if(fseek(hog_fp,entry.offset,SEEK_SET)!=0) {
|
||||
fclose(hog_fp);
|
||||
return(NULL);
|
||||
}
|
||||
|
||||
// Return pointer to file's position within the hog
|
||||
return(hog_fp);
|
||||
}
|
||||
|
||||
|
||||
// This is a function to specifically handle the creation of a new hog
|
||||
// file from the currently loaded (and presumedly altered) hog file.
|
||||
// This one also takes a pointer to a function that will perform
|
||||
// progress updates (for the user)
|
||||
#define TEMP_HOG_FILENAME "TempHogFile.thf"
|
||||
int CHogEditDoc::CreateNewHogFromCurrentHog(char *src_hog_fname, char *target_hog_fname,
|
||||
int nfiles, const char **filenames,
|
||||
void(* UpdateFunction)(char *))
|
||||
{
|
||||
unsigned i;
|
||||
int table_pos;
|
||||
FILE *hog_fp;
|
||||
tHogHeader header;
|
||||
tHogFileEntry *table;
|
||||
char ext[_MAX_EXT];
|
||||
char dest_hog_fname[PSPATHNAME_LEN+1];
|
||||
|
||||
// If the source and target hog filenames are the same,
|
||||
// then make the destination a temporary file
|
||||
if(!stricmp(src_hog_fname,target_hog_fname))
|
||||
strcpy(dest_hog_fname,TEMP_HOG_FILENAME);
|
||||
else
|
||||
strcpy(dest_hog_fname,target_hog_fname);
|
||||
|
||||
hogerr_filename[0]='\0';
|
||||
|
||||
// allocate file table
|
||||
if (nfiles <= 0)
|
||||
return HOGMAKER_ERROR;
|
||||
|
||||
table = new tHogFileEntry[nfiles];
|
||||
if (!table)
|
||||
return HOGMAKER_MEMORY;
|
||||
|
||||
// create new file
|
||||
hog_fp = fopen( dest_hog_fname, "wb" );
|
||||
if ( hog_fp == NULL ) {
|
||||
delete[] table;
|
||||
strcpy(hogerr_filename,dest_hog_fname);
|
||||
return HOGMAKER_OPENOUTFILE;
|
||||
}
|
||||
|
||||
//write the tag
|
||||
if (!fwrite(HOG_TAG_STR, strlen(HOG_TAG_STR), 1, hog_fp )) {
|
||||
delete[] table;
|
||||
fclose(hog_fp);
|
||||
strcpy(hogerr_filename,dest_hog_fname);
|
||||
return HOGMAKER_OUTFILE;
|
||||
}
|
||||
|
||||
//write number of files
|
||||
ubyte filler = 0xff;
|
||||
header.nfiles = (unsigned)nfiles;
|
||||
header.file_data_offset = strlen(HOG_TAG_STR) + HOG_HDR_SIZE + (sizeof(tHogFileEntry) * header.nfiles);
|
||||
|
||||
if (!fwrite(&header.nfiles,sizeof(header.nfiles),1,hog_fp)) {
|
||||
delete[] table;
|
||||
fclose(hog_fp);
|
||||
strcpy(hogerr_filename,dest_hog_fname);
|
||||
return HOGMAKER_OUTFILE;
|
||||
}
|
||||
if (!fwrite(&header.file_data_offset,sizeof(header.file_data_offset),1,hog_fp)) {
|
||||
delete[] table;
|
||||
fclose(hog_fp);
|
||||
strcpy(hogerr_filename,dest_hog_fname);
|
||||
return HOGMAKER_OUTFILE;
|
||||
}
|
||||
|
||||
// write out filler
|
||||
for(i=0; i < HOG_HDR_SIZE-sizeof(tHogHeader); i++)
|
||||
if (!fwrite(&filler,sizeof(ubyte),1,hog_fp)) {
|
||||
delete[] table;
|
||||
fclose(hog_fp);
|
||||
strcpy(hogerr_filename,dest_hog_fname);
|
||||
return HOGMAKER_OUTFILE;
|
||||
}
|
||||
|
||||
// save file position of index table and write out dummy table
|
||||
table_pos = strlen(HOG_TAG_STR) + HOG_HDR_SIZE;
|
||||
|
||||
memset(&table[0], 0, sizeof(table[0]));
|
||||
|
||||
for (i = 0; i < header.nfiles; i++)
|
||||
{
|
||||
if (!WRITE_FILE_ENTRY(hog_fp, &table[0])) {
|
||||
delete[] table;
|
||||
fclose(hog_fp);
|
||||
strcpy(hogerr_filename,dest_hog_fname);
|
||||
return HOGMAKER_OUTFILE;
|
||||
}
|
||||
}
|
||||
|
||||
// write files (& build index)
|
||||
for (i=0;i<header.nfiles;i++)
|
||||
{
|
||||
FILE *ifp;
|
||||
struct _stat mystat;
|
||||
|
||||
// Get JUST the name of the file (with extension)
|
||||
_splitpath(filenames[i],NULL,NULL,table[i].name,ext);
|
||||
strcat(table[i].name,ext);
|
||||
|
||||
// See if the file is in the hog, and, if it is, get the file position
|
||||
// it starts at
|
||||
ifp=FindFileInHog(src_hog_fname,&table[i]);
|
||||
|
||||
// If file isn't in the hog, then process it as an "external" file
|
||||
if(ifp == NULL) {
|
||||
ifp = fopen(filenames[i],"rb");
|
||||
if ( ifp == NULL ) {
|
||||
delete[] table;
|
||||
fclose(hog_fp);
|
||||
strcpy(hogerr_filename,filenames[i]);
|
||||
return HOGMAKER_INFILE;
|
||||
}
|
||||
|
||||
_fstat(fileno(ifp), &mystat);
|
||||
|
||||
table[i].flags = 0;
|
||||
table[i].len = _filelength(_fileno(ifp));
|
||||
table[i].timestamp = mystat.st_mtime;
|
||||
}
|
||||
|
||||
if (!FileCopy(hog_fp,ifp,table[i].len)) {
|
||||
delete[] table;
|
||||
fclose(hog_fp);
|
||||
fclose(ifp);
|
||||
strcpy(hogerr_filename,filenames[i]);
|
||||
return HOGMAKER_COPY;
|
||||
}
|
||||
|
||||
fclose(ifp);
|
||||
|
||||
// Setup the update message and send it
|
||||
char msg[256];
|
||||
int ipct = int(100.0*(double(i)/double(header.nfiles)));
|
||||
sprintf(msg,"Creating Hog File... (%d%% done)",ipct);
|
||||
UpdateFunction(msg);
|
||||
}
|
||||
|
||||
// now write the real index
|
||||
fseek(hog_fp,table_pos,SEEK_SET);
|
||||
|
||||
for (i = 0; i < header.nfiles; i++)
|
||||
{
|
||||
if (!WRITE_FILE_ENTRY(hog_fp, &table[i])) {
|
||||
delete[] table;
|
||||
fclose(hog_fp);
|
||||
strcpy(hogerr_filename,dest_hog_fname);
|
||||
return HOGMAKER_OUTFILE;
|
||||
}
|
||||
}
|
||||
|
||||
// cleanup
|
||||
fclose( hog_fp );
|
||||
delete[] table;
|
||||
|
||||
// Setup the update message and send it
|
||||
char msg[256];
|
||||
sprintf(msg,"Done Creating Hog File.");
|
||||
UpdateFunction(msg);
|
||||
|
||||
// If new hog was written to temp file, delete the original and
|
||||
// rename the temp to be the original
|
||||
if(!stricmp(dest_hog_fname,TEMP_HOG_FILENAME)) {
|
||||
DeleteFile(target_hog_fname);
|
||||
rename(TEMP_HOG_FILENAME,target_hog_fname);
|
||||
}
|
||||
|
||||
return HOGMAKER_OK;
|
||||
}
|
||||
|
||||
|
||||
// Update menu items
|
||||
void CHogEditDoc::OnUpdateActionInsert(CCmdUI* pCmdUI)
|
||||
{
|
||||
// TODO: Add your command update UI handler code here
|
||||
/*pCmdUI->Enable(!m_StaticHog);*/
|
||||
}
|
||||
|
||||
void CHogEditDoc::OnUpdateActionCreate(CCmdUI* pCmdUI)
|
||||
{
|
||||
// TODO: Add your command update UI handler code here
|
||||
pCmdUI->Enable(!m_StaticHog && Library.filelist.GetCount()>0);
|
||||
}
|
||||
|
||||
void CHogEditDoc::OnUpdateFileSave(CCmdUI* pCmdUI)
|
||||
{
|
||||
// TODO: Add your command update UI handler code here
|
||||
pCmdUI->Enable(/*!m_StaticHog &&*/ DocModified);
|
||||
}
|
||||
|
||||
void CHogEditDoc::OnUpdateFileSaveAs(CCmdUI* pCmdUI)
|
||||
{
|
||||
// TODO: Add your command update UI handler code here
|
||||
/*pCmdUI->Enable(!m_StaticHog);*/
|
||||
}
|
||||
|
||||
void CHogEditDoc::OnUpdateActionUpdate(CCmdUI* pCmdUI)
|
||||
{
|
||||
// TODO: Add your command update UI handler code here
|
||||
pCmdUI->Enable(!m_StaticHog && Library.filelist.GetCount()>0);
|
||||
}
|
||||
|
||||
void CHogEditDoc::OnUpdateActionImport(CCmdUI* pCmdUI)
|
||||
{
|
||||
// TODO: Add your command update UI handler code here
|
||||
//pCmdUI->Enable(!m_StaticHog);
|
||||
}
|
169
hogedit/HogEditDoc.h
Normal file
169
hogedit/HogEditDoc.h
Normal file
@ -0,0 +1,169 @@
|
||||
/*
|
||||
* $Logfile: /DescentIII/Main/hogedit/HogEditDoc.h $
|
||||
* $Revision: 1.1.1.1 $
|
||||
* $Date: 2003-08-26 03:57:56 $
|
||||
* $Author: kevinb $
|
||||
*
|
||||
*
|
||||
*
|
||||
* $Log: not supported by cvs2svn $
|
||||
*
|
||||
* 9 5/05/99 12:53p Nate
|
||||
* Added support for multiple file extraction
|
||||
*
|
||||
* 8 10/30/98 11:15a Nate
|
||||
* Added support for modification of hog files.
|
||||
*
|
||||
* 7 9/17/98 4:29p Nate
|
||||
* Added Import Directory option.
|
||||
*
|
||||
* 6 8/14/98 4:38p Nate
|
||||
* Fixed a few minor bugs and added better error reporting
|
||||
*
|
||||
* 5 8/14/98 1:01p Nate
|
||||
* Added better error reporting for the HogEditor
|
||||
*
|
||||
* 4 7/22/98 2:38p Nate
|
||||
* Added Modified File prompt when exiting
|
||||
*
|
||||
* 3 7/20/98 3:35p Nate
|
||||
* Added more Editing functionality
|
||||
*
|
||||
* 2 7/15/98 12:31p Nate
|
||||
* Initial version
|
||||
*
|
||||
* $NoKeywords: $
|
||||
*/
|
||||
|
||||
// HogEditDoc.h : interface of the CHogEditDoc class
|
||||
//
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
#if !defined(AFX_HOGEDITDOC_H__48BE52BE_172F_11D2_8CBC_00A0C96ED60D__INCLUDED_)
|
||||
#define AFX_HOGEDITDOC_H__48BE52BE_172F_11D2_8CBC_00A0C96ED60D__INCLUDED_
|
||||
|
||||
#if _MSC_VER >= 1000
|
||||
#pragma once
|
||||
#endif // _MSC_VER >= 1000
|
||||
|
||||
#include "pstypes.h"
|
||||
|
||||
#define FILE_IS_SAME 0
|
||||
#define FILE_HAS_CHANGED 1
|
||||
#define FILE_IS_GONE 2
|
||||
|
||||
#define RIB_TAG_STR "RIB_ID"
|
||||
|
||||
#define DEFAULT_NEW_FILENAME "Untitled.rib"
|
||||
|
||||
#define ADDFILE_OK 0
|
||||
#define ADDFILE_LONG_FNAME_ERROR 1
|
||||
#define ADDFILE_DUP_FILE_ERROR 2
|
||||
#define ADDFILE_STAT_ERROR 3
|
||||
|
||||
// the following structures are slightly modified versions of the CFILE hog structs
|
||||
typedef struct hog_library_entry
|
||||
{
|
||||
char path[PSPATHNAME_LEN]; // location of data file (filename not included)
|
||||
char name[PSFILENAME_LEN+1]; // just the filename
|
||||
unsigned length; // length of this file
|
||||
long timestamp; // time and date of file
|
||||
int flags; // misc flags
|
||||
int offset; // file offset in hog (or -1 if in .rib file)
|
||||
} hog_library_entry;
|
||||
|
||||
// the hog library structure
|
||||
typedef struct hog_library
|
||||
{
|
||||
char filename[PSPATHNAME_LEN]; // full hog file path (including filename)
|
||||
int flags; // misc flags for the hog file
|
||||
int num_entries; // number of entries in the hog file
|
||||
CList <hog_library_entry, hog_library_entry&> filelist;
|
||||
}
|
||||
hog_library;
|
||||
|
||||
// Comparison function for sorting filenames
|
||||
int compare( const void *arg1, const void *arg2 );
|
||||
|
||||
// HogEdit Doc class
|
||||
class CHogEditDoc : public CDocument
|
||||
{
|
||||
protected: // create from serialization only
|
||||
CHogEditDoc();
|
||||
DECLARE_DYNCREATE(CHogEditDoc)
|
||||
|
||||
// Attributes
|
||||
public:
|
||||
CString m_DocumentName; // name of hog document
|
||||
bool m_StaticHog; // is library a loaded hogfile or a lite hogfile(only names)
|
||||
bool m_NoNameChosen; // Isn't set until user specifies name for a new file
|
||||
hog_library Library; // stores the list of entries
|
||||
|
||||
// Operations
|
||||
public:
|
||||
int LoadDocument(CString& name); // loads a hog or rib
|
||||
int SaveDocument(CString& name); // saves a hog or rib
|
||||
void NewDocument(); // creates a new document (entry list)
|
||||
|
||||
int LoadHog(const char *pathname); // loads a Hog file
|
||||
int SaveHog(const char *pathname); // saves a Hog file
|
||||
int LoadRib(const char *pathname); // loads a Rib file.
|
||||
int SaveRib(const char *pathname); // saves a Rib file.
|
||||
|
||||
int AddFile(const char *pathname, hog_library_entry *entry); // adds a file to the file list.
|
||||
|
||||
bool ReadHogLibEntry(FILE *fp, hog_library_entry *entry);
|
||||
bool WriteHogLibEntry(FILE *fp, hog_library_entry *entry);
|
||||
|
||||
bool CreateFilenameList(char ***filenames);
|
||||
void SortFilenameList(char **filenames);
|
||||
bool DeleteFilenameList(char **filenames);
|
||||
|
||||
int UpdatedFileCheck(hog_library_entry *entry);
|
||||
bool ExtractFile(int file_pos, unsigned file_len, char *out_fname);
|
||||
|
||||
unsigned int CalcHogFileSize(void);
|
||||
|
||||
FILE *FindFileInHog(char *hog_fname,tHogFileEntry *table_entry);
|
||||
|
||||
int CreateNewHogFromCurrentHog(char *src_hog_fname, char *target_hog_fname,
|
||||
int nfiles, const char **filenames,
|
||||
void(* UpdateFunction)(char *));
|
||||
|
||||
// Overrides
|
||||
// ClassWizard generated virtual function overrides
|
||||
//{{AFX_VIRTUAL(CHogEditDoc)
|
||||
public:
|
||||
virtual BOOL OnNewDocument();
|
||||
virtual void Serialize(CArchive& ar);
|
||||
//}}AFX_VIRTUAL
|
||||
|
||||
// Implementation
|
||||
public:
|
||||
virtual ~CHogEditDoc();
|
||||
#ifdef _DEBUG
|
||||
virtual void AssertValid() const;
|
||||
virtual void Dump(CDumpContext& dc) const;
|
||||
#endif
|
||||
|
||||
protected:
|
||||
|
||||
// Generated message map functions
|
||||
protected:
|
||||
//{{AFX_MSG(CHogEditDoc)
|
||||
afx_msg void OnUpdateActionInsert(CCmdUI* pCmdUI);
|
||||
afx_msg void OnUpdateActionCreate(CCmdUI* pCmdUI);
|
||||
afx_msg void OnUpdateFileSave(CCmdUI* pCmdUI);
|
||||
afx_msg void OnUpdateFileSaveAs(CCmdUI* pCmdUI);
|
||||
afx_msg void OnUpdateActionUpdate(CCmdUI* pCmdUI);
|
||||
afx_msg void OnUpdateActionImport(CCmdUI* pCmdUI);
|
||||
//}}AFX_MSG
|
||||
DECLARE_MESSAGE_MAP()
|
||||
};
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
//{{AFX_INSERT_LOCATION}}
|
||||
// Microsoft Developer Studio will insert additional declarations immediately before the previous line.
|
||||
|
||||
#endif // !defined(AFX_HOGEDITDOC_H__48BE52BE_172F_11D2_8CBC_00A0C96ED60D__INCLUDED_)
|
1211
hogedit/HogEditView.cpp
Normal file
1211
hogedit/HogEditView.cpp
Normal file
File diff suppressed because it is too large
Load Diff
153
hogedit/HogEditView.h
Normal file
153
hogedit/HogEditView.h
Normal file
@ -0,0 +1,153 @@
|
||||
/*
|
||||
* $Logfile: /DescentIII/Main/hogedit/HogEditView.h $
|
||||
* $Revision: 1.1.1.1 $
|
||||
* $Date: 2003-08-26 03:57:56 $
|
||||
* $Author: kevinb $
|
||||
*
|
||||
*
|
||||
*
|
||||
* $Log: not supported by cvs2svn $
|
||||
*
|
||||
* 11 10/28/98 11:24a Nate
|
||||
* Added command line auto-processing (create hog from a rib)
|
||||
*
|
||||
* 10 9/17/98 4:29p Nate
|
||||
* Added Import Directory option.
|
||||
*
|
||||
* 9 8/16/98 4:22p Nate
|
||||
* Added message deferal and new hog info dialog
|
||||
*
|
||||
* 8 8/14/98 7:47p Nate
|
||||
* Removed "duplicate file" error message (upon File Inserts)
|
||||
*
|
||||
* 7 8/14/98 6:04p Nate
|
||||
* Added number of files field to status bar.
|
||||
*
|
||||
* 6 8/14/98 4:38p Nate
|
||||
* Fixed a few minor bugs and added better error reporting
|
||||
*
|
||||
* 5 8/14/98 1:01p Nate
|
||||
* Added better error reporting for the HogEditor
|
||||
*
|
||||
* 4 7/22/98 2:38p Nate
|
||||
* Added Modified File prompt when exiting
|
||||
*
|
||||
* 3 7/20/98 3:35p Nate
|
||||
* Added more Editing functionality
|
||||
*
|
||||
* 2 7/15/98 12:31p Nate
|
||||
* Initial version
|
||||
*
|
||||
* $NoKeywords: $
|
||||
*/
|
||||
|
||||
// HogEditView.h : interface of the CHogEditView class
|
||||
//
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
#if !defined(AFX_HOGEDITVIEW_H__48BE52C0_172F_11D2_8CBC_00A0C96ED60D__INCLUDED_)
|
||||
#define AFX_HOGEDITVIEW_H__48BE52C0_172F_11D2_8CBC_00A0C96ED60D__INCLUDED_
|
||||
|
||||
#if _MSC_VER >= 1000
|
||||
#pragma once
|
||||
#endif // _MSC_VER >= 1000
|
||||
|
||||
// HogEdit Window Constants
|
||||
#define FILE_NAME_COLUMN 0
|
||||
#define FILE_TYPE_COLUMN 1
|
||||
#define FILE_DIR_COLUMN 2
|
||||
#define FILE_SIZE_COLUMN 3
|
||||
#define FILE_TIME_COLUMN 4
|
||||
|
||||
#define FILE_NAME_TITLE "Filename"
|
||||
#define FILE_TYPE_TITLE "Type"
|
||||
#define FILE_DIR_TITLE "Directory"
|
||||
#define FILE_SIZE_TITLE "Size"
|
||||
#define FILE_TIME_TITLE "Timestamp"
|
||||
|
||||
#define FILE_NAME_COLUMN_WIDTH 0.20
|
||||
#define FILE_TYPE_COLUMN_WIDTH 0.18
|
||||
#define FILE_DIR_COLUMN_WIDTH 0.35
|
||||
#define FILE_SIZE_COLUMN_WIDTH 0.07
|
||||
#define FILE_TIME_COLUMN_WIDTH 0.20
|
||||
|
||||
// The size of the buffer to hold the list of "to-be-added" filenames
|
||||
#define MAX_FILENAME_BUFFER 120000
|
||||
|
||||
class CHogEditView : public CListViewEx
|
||||
{
|
||||
protected: // create from serialization only
|
||||
CHogEditView();
|
||||
DECLARE_DYNCREATE(CHogEditView)
|
||||
|
||||
// Attributes
|
||||
public:
|
||||
CHogEditDoc* GetDocument();
|
||||
|
||||
// Operations
|
||||
public:
|
||||
void SetColumnWidths(void);
|
||||
void GetFileType(char *type, char *filename);
|
||||
bool InsertItem(int index, hog_library_entry *entry);
|
||||
void UpdateList(void);
|
||||
void UpdateTitle(CString &path, bool mod_flag);
|
||||
|
||||
// Overrides
|
||||
// ClassWizard generated virtual function overrides
|
||||
//{{AFX_VIRTUAL(CHogEditView)
|
||||
public:
|
||||
virtual void OnDraw(CDC* pDC); // overridden to draw this view
|
||||
virtual BOOL PreCreateWindow(CREATESTRUCT& cs);
|
||||
protected:
|
||||
virtual void OnInitialUpdate(); // called first time after construct
|
||||
//}}AFX_VIRTUAL
|
||||
|
||||
// Implementation
|
||||
public:
|
||||
virtual ~CHogEditView();
|
||||
#ifdef _DEBUG
|
||||
virtual void AssertValid() const;
|
||||
virtual void Dump(CDumpContext& dc) const;
|
||||
#endif
|
||||
|
||||
protected:
|
||||
|
||||
// Generated message map functions
|
||||
protected:
|
||||
//{{AFX_MSG(CHogEditView)
|
||||
afx_msg void OnFileNew();
|
||||
afx_msg void OnActionInsert();
|
||||
afx_msg void OnFileOpen();
|
||||
afx_msg void OnFileSave();
|
||||
afx_msg void OnFileSaveAs();
|
||||
afx_msg void OnActionDelete();
|
||||
afx_msg void OnActionCreate();
|
||||
afx_msg void OnViewFullRow();
|
||||
afx_msg void OnUpdateViewFullRow(CCmdUI* pCmdUI);
|
||||
afx_msg void OnActionUpdate();
|
||||
afx_msg void OnActionExtract();
|
||||
afx_msg void OnUpdateActionDelete(CCmdUI* pCmdUI);
|
||||
afx_msg void OnUpdateActionExtract(CCmdUI* pCmdUI);
|
||||
afx_msg void OnColumnclick(NMHDR* pNMHDR, LRESULT* pResult);
|
||||
afx_msg void OnActionImport();
|
||||
afx_msg LONG OnStraightToFileOpen(UINT, LONG);
|
||||
//}}AFX_MSG
|
||||
DECLARE_MESSAGE_MAP()
|
||||
};
|
||||
|
||||
// pass this message to myself when initializing if I should go straight to the
|
||||
// update dialog
|
||||
#define WM_STRAIGHT_TO_FILE_OPEN (WM_USER + 10)
|
||||
|
||||
|
||||
#ifndef _DEBUG // debug version in HogEditView.cpp
|
||||
inline CHogEditDoc* CHogEditView::GetDocument()
|
||||
{ return (CHogEditDoc*)m_pDocument; }
|
||||
#endif
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
//{{AFX_INSERT_LOCATION}}
|
||||
// Microsoft Developer Studio will insert additional declarations immediately before the previous line.
|
||||
|
||||
#endif // !defined(AFX_HOGEDITVIEW_H__48BE52C0_172F_11D2_8CBC_00A0C96ED60D__INCLUDED_)
|
74
hogedit/HogInfo.cpp
Normal file
74
hogedit/HogInfo.cpp
Normal file
@ -0,0 +1,74 @@
|
||||
/*
|
||||
* $Logfile: /DescentIII/Main/hogedit/HogInfo.cpp $
|
||||
* $Revision: 1.1.1.1 $
|
||||
* $Date: 2003-08-26 03:57:56 $
|
||||
* $Author: kevinb $
|
||||
*
|
||||
*
|
||||
*
|
||||
* $Log: not supported by cvs2svn $
|
||||
*
|
||||
* 2 8/16/98 4:22p Nate
|
||||
* Added message deferal and new hog info dialog
|
||||
*
|
||||
* $NoKeywords: $
|
||||
*/
|
||||
|
||||
// HogInfo.cpp : implementation file
|
||||
//
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "hogedit.h"
|
||||
#include "HogInfo.h"
|
||||
|
||||
#ifdef _DEBUG
|
||||
#define new DEBUG_NEW
|
||||
#undef THIS_FILE
|
||||
static char THIS_FILE[] = __FILE__;
|
||||
#endif
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// CHogInfo dialog
|
||||
|
||||
|
||||
CHogInfo::CHogInfo(CWnd* pParent /*=NULL*/)
|
||||
: CDialog(CHogInfo::IDD, pParent)
|
||||
{
|
||||
//{{AFX_DATA_INIT(CHogInfo)
|
||||
m_NumFiles = _T("");
|
||||
m_Location = _T("");
|
||||
m_SizeBytes = _T("");
|
||||
m_SizeMB = _T("");
|
||||
//}}AFX_DATA_INIT
|
||||
}
|
||||
|
||||
|
||||
void CHogInfo::DoDataExchange(CDataExchange* pDX)
|
||||
{
|
||||
CDialog::DoDataExchange(pDX);
|
||||
//{{AFX_DATA_MAP(CHogInfo)
|
||||
DDX_Text(pDX, IDC_HOGINFO_FILES, m_NumFiles);
|
||||
DDX_Text(pDX, IDC_HOGINFO_LOCATION, m_Location);
|
||||
DDX_Text(pDX, IDC_HOGINFO_SIZE_BYTES, m_SizeBytes);
|
||||
DDX_Text(pDX, IDC_HOGINFO_SIZE_MB, m_SizeMB);
|
||||
//}}AFX_DATA_MAP
|
||||
}
|
||||
|
||||
|
||||
BEGIN_MESSAGE_MAP(CHogInfo, CDialog)
|
||||
//{{AFX_MSG_MAP(CHogInfo)
|
||||
//}}AFX_MSG_MAP
|
||||
END_MESSAGE_MAP()
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// CHogInfo message handlers
|
||||
|
||||
BOOL CHogInfo::OnInitDialog()
|
||||
{
|
||||
CDialog::OnInitDialog();
|
||||
|
||||
// TODO: Add extra initialization here
|
||||
|
||||
return TRUE; // return TRUE unless you set the focus to a control
|
||||
// EXCEPTION: OCX Property Pages should return FALSE
|
||||
}
|
65
hogedit/HogInfo.h
Normal file
65
hogedit/HogInfo.h
Normal file
@ -0,0 +1,65 @@
|
||||
/*
|
||||
* $Logfile: /DescentIII/Main/hogedit/HogInfo.h $
|
||||
* $Revision: 1.1.1.1 $
|
||||
* $Date: 2003-08-26 03:57:56 $
|
||||
* $Author: kevinb $
|
||||
*
|
||||
*
|
||||
*
|
||||
* $Log: not supported by cvs2svn $
|
||||
*
|
||||
* 2 8/16/98 4:22p Nate
|
||||
* Added message deferal and new hog info dialog
|
||||
*
|
||||
* $NoKeywords: $
|
||||
*/
|
||||
|
||||
#if !defined(AFX_HOGINFO_H__2BF70B62_351D_11D2_8CBD_00A0C96ED60D__INCLUDED_)
|
||||
#define AFX_HOGINFO_H__2BF70B62_351D_11D2_8CBD_00A0C96ED60D__INCLUDED_
|
||||
|
||||
#if _MSC_VER >= 1000
|
||||
#pragma once
|
||||
#endif // _MSC_VER >= 1000
|
||||
// HogInfo.h : header file
|
||||
//
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// CHogInfo dialog
|
||||
|
||||
class CHogInfo : public CDialog
|
||||
{
|
||||
// Construction
|
||||
public:
|
||||
CHogInfo(CWnd* pParent = NULL); // standard constructor
|
||||
|
||||
// Dialog Data
|
||||
//{{AFX_DATA(CHogInfo)
|
||||
enum { IDD = IDD_HOGINFO };
|
||||
CString m_NumFiles;
|
||||
CString m_Location;
|
||||
CString m_SizeBytes;
|
||||
CString m_SizeMB;
|
||||
//}}AFX_DATA
|
||||
|
||||
|
||||
// Overrides
|
||||
// ClassWizard generated virtual function overrides
|
||||
//{{AFX_VIRTUAL(CHogInfo)
|
||||
protected:
|
||||
virtual void DoDataExchange(CDataExchange* pDX); // DDX/DDV support
|
||||
//}}AFX_VIRTUAL
|
||||
|
||||
// Implementation
|
||||
protected:
|
||||
|
||||
// Generated message map functions
|
||||
//{{AFX_MSG(CHogInfo)
|
||||
virtual BOOL OnInitDialog();
|
||||
//}}AFX_MSG
|
||||
DECLARE_MESSAGE_MAP()
|
||||
};
|
||||
|
||||
//{{AFX_INSERT_LOCATION}}
|
||||
// Microsoft Developer Studio will insert additional declarations immediately before the previous line.
|
||||
|
||||
#endif // !defined(AFX_HOGINFO_H__2BF70B62_351D_11D2_8CBD_00A0C96ED60D__INCLUDED_)
|
152
hogedit/MainFrm.cpp
Normal file
152
hogedit/MainFrm.cpp
Normal file
@ -0,0 +1,152 @@
|
||||
/*
|
||||
* $Logfile: /DescentIII/Main/hogedit/MainFrm.cpp $
|
||||
* $Revision: 1.1.1.1 $
|
||||
* $Date: 2003-08-26 03:57:56 $
|
||||
* $Author: kevinb $
|
||||
*
|
||||
*
|
||||
*
|
||||
* $Log: not supported by cvs2svn $
|
||||
*
|
||||
* 6 8/14/98 6:04p Nate
|
||||
* Added number of files field to status bar.
|
||||
*
|
||||
* 5 8/14/98 4:38p Nate
|
||||
* Fixed a few minor bugs and added better error reporting
|
||||
*
|
||||
* 4 8/14/98 1:01p Nate
|
||||
* Added better error reporting for the HogEditor
|
||||
*
|
||||
* 3 7/22/98 2:38p Nate
|
||||
* Added Modified File prompt when exiting
|
||||
*
|
||||
* 2 7/15/98 12:31p Nate
|
||||
* Initial version
|
||||
*
|
||||
* $NoKeywords: $
|
||||
*/
|
||||
|
||||
// MainFrm.cpp : implementation of the CMainFrame class
|
||||
//
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "HogEdit.h"
|
||||
|
||||
#include "MainFrm.h"
|
||||
|
||||
#ifdef _DEBUG
|
||||
#define new DEBUG_NEW
|
||||
#undef THIS_FILE
|
||||
static char THIS_FILE[] = __FILE__;
|
||||
#endif
|
||||
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// CMainFrame
|
||||
|
||||
IMPLEMENT_DYNCREATE(CMainFrame, CFrameWnd)
|
||||
|
||||
BEGIN_MESSAGE_MAP(CMainFrame, CFrameWnd)
|
||||
//{{AFX_MSG_MAP(CMainFrame)
|
||||
ON_WM_CREATE()
|
||||
ON_WM_CLOSE()
|
||||
//}}AFX_MSG_MAP
|
||||
END_MESSAGE_MAP()
|
||||
|
||||
static UINT indicators[] =
|
||||
{
|
||||
ID_SEPARATOR, // status line indicator
|
||||
//ID_INDICATOR_CAPS,
|
||||
//ID_INDICATOR_NUM,
|
||||
//ID_INDICATOR_SCRL,
|
||||
ID_INDICATOR_FILES
|
||||
};
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// CMainFrame construction/destruction
|
||||
|
||||
CMainFrame::CMainFrame()
|
||||
{
|
||||
// TODO: add member initialization code here
|
||||
|
||||
}
|
||||
|
||||
CMainFrame::~CMainFrame()
|
||||
{
|
||||
}
|
||||
|
||||
int CMainFrame::OnCreate(LPCREATESTRUCT lpCreateStruct)
|
||||
{
|
||||
if (CFrameWnd::OnCreate(lpCreateStruct) == -1)
|
||||
return -1;
|
||||
|
||||
if (!m_wndToolBar.Create(this) ||
|
||||
!m_wndToolBar.LoadToolBar(IDR_MAINFRAME))
|
||||
{
|
||||
TRACE0("Failed to create toolbar\n");
|
||||
return -1; // fail to create
|
||||
}
|
||||
|
||||
if (!m_wndStatusBar.Create(this) ||
|
||||
!m_wndStatusBar.SetIndicators(indicators,
|
||||
sizeof(indicators)/sizeof(UINT)))
|
||||
{
|
||||
TRACE0("Failed to create status bar\n");
|
||||
return -1; // fail to create
|
||||
}
|
||||
|
||||
// Get pointer to status bar so we can set it elsewhere
|
||||
MainStatusBar=&m_wndStatusBar;
|
||||
MainStatusBar->SetPaneText(1,"Total Files: 0",TRUE);
|
||||
|
||||
// TODO: Remove this if you don't want tool tips or a resizeable toolbar
|
||||
m_wndToolBar.SetBarStyle(m_wndToolBar.GetBarStyle() |
|
||||
CBRS_TOOLTIPS | CBRS_FLYBY | CBRS_SIZE_DYNAMIC);
|
||||
|
||||
// TODO: Delete these three lines if you don't want the toolbar to
|
||||
// be dockable
|
||||
m_wndToolBar.EnableDocking(CBRS_ALIGN_ANY);
|
||||
EnableDocking(CBRS_ALIGN_ANY);
|
||||
DockControlBar(&m_wndToolBar);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
BOOL CMainFrame::PreCreateWindow(CREATESTRUCT& cs)
|
||||
{
|
||||
// TODO: Modify the Window class or styles here by modifying
|
||||
// the CREATESTRUCT cs
|
||||
cs.cx=MAIN_WINDOW_WIDTH;
|
||||
cs.cy=MAIN_WINDOW_HEIGHT;
|
||||
cs.lpszName=HOG_EDIT_TITLE;
|
||||
cs.style=WS_OVERLAPPEDWINDOW;
|
||||
|
||||
return CFrameWnd::PreCreateWindow(cs);
|
||||
}
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// CMainFrame diagnostics
|
||||
|
||||
#ifdef _DEBUG
|
||||
void CMainFrame::AssertValid() const
|
||||
{
|
||||
CFrameWnd::AssertValid();
|
||||
}
|
||||
|
||||
void CMainFrame::Dump(CDumpContext& dc) const
|
||||
{
|
||||
CFrameWnd::Dump(dc);
|
||||
}
|
||||
|
||||
#endif //_DEBUG
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// CMainFrame message handlers
|
||||
|
||||
void CMainFrame::OnClose()
|
||||
{
|
||||
// TODO: Add your message handler code here and/or call default
|
||||
if(ModifiedPrompt(this)==IDNO) return;
|
||||
|
||||
CFrameWnd::OnClose();
|
||||
}
|
89
hogedit/MainFrm.h
Normal file
89
hogedit/MainFrm.h
Normal file
@ -0,0 +1,89 @@
|
||||
/*
|
||||
* $Logfile: /DescentIII/Main/hogedit/MainFrm.h $
|
||||
* $Revision: 1.1.1.1 $
|
||||
* $Date: 2003-08-26 03:57:56 $
|
||||
* $Author: kevinb $
|
||||
*
|
||||
*
|
||||
*
|
||||
* $Log: not supported by cvs2svn $
|
||||
*
|
||||
* 6 8/14/98 6:04p Nate
|
||||
* Added number of files field to status bar.
|
||||
*
|
||||
* 5 8/14/98 4:38p Nate
|
||||
* Fixed a few minor bugs and added better error reporting
|
||||
*
|
||||
* 4 8/14/98 1:01p Nate
|
||||
* Added better error reporting for the HogEditor
|
||||
*
|
||||
* 3 7/22/98 2:38p Nate
|
||||
* Added Modified File prompt when exiting
|
||||
*
|
||||
* 2 7/15/98 12:31p Nate
|
||||
* Initial version
|
||||
*
|
||||
* $NoKeywords: $
|
||||
*/
|
||||
|
||||
// MainFrm.h : interface of the CMainFrame class
|
||||
//
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
#if !defined(AFX_MAINFRM_H__48BE52BC_172F_11D2_8CBC_00A0C96ED60D__INCLUDED_)
|
||||
#define AFX_MAINFRM_H__48BE52BC_172F_11D2_8CBC_00A0C96ED60D__INCLUDED_
|
||||
|
||||
#if _MSC_VER >= 1000
|
||||
#pragma once
|
||||
#endif // _MSC_VER >= 1000
|
||||
|
||||
// Starting Window Dimensions
|
||||
#define MAIN_WINDOW_WIDTH 800
|
||||
#define MAIN_WINDOW_HEIGHT 600
|
||||
|
||||
|
||||
class CMainFrame : public CFrameWnd
|
||||
{
|
||||
protected: // create from serialization only
|
||||
CMainFrame();
|
||||
DECLARE_DYNCREATE(CMainFrame)
|
||||
|
||||
// Attributes
|
||||
public:
|
||||
|
||||
// Operations
|
||||
public:
|
||||
|
||||
// Overrides
|
||||
// ClassWizard generated virtual function overrides
|
||||
//{{AFX_VIRTUAL(CMainFrame)
|
||||
virtual BOOL PreCreateWindow(CREATESTRUCT& cs);
|
||||
//}}AFX_VIRTUAL
|
||||
|
||||
// Implementation
|
||||
public:
|
||||
virtual ~CMainFrame();
|
||||
#ifdef _DEBUG
|
||||
virtual void AssertValid() const;
|
||||
virtual void Dump(CDumpContext& dc) const;
|
||||
#endif
|
||||
|
||||
protected: // control bar embedded members
|
||||
CStatusBar m_wndStatusBar;
|
||||
CToolBar m_wndToolBar;
|
||||
|
||||
// Generated message map functions
|
||||
protected:
|
||||
//{{AFX_MSG(CMainFrame)
|
||||
afx_msg int OnCreate(LPCREATESTRUCT lpCreateStruct);
|
||||
afx_msg void OnClose();
|
||||
//}}AFX_MSG
|
||||
DECLARE_MESSAGE_MAP()
|
||||
};
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
//{{AFX_INSERT_LOCATION}}
|
||||
// Microsoft Developer Studio will insert additional declarations immediately before the previous line.
|
||||
|
||||
#endif // !defined(AFX_MAINFRM_H__48BE52BC_172F_11D2_8CBC_00A0C96ED60D__INCLUDED_)
|
81
hogedit/ReadMe.txt
Normal file
81
hogedit/ReadMe.txt
Normal file
@ -0,0 +1,81 @@
|
||||
========================================================================
|
||||
MICROSOFT FOUNDATION CLASS LIBRARY : hogedit
|
||||
========================================================================
|
||||
|
||||
|
||||
AppWizard has created this hogedit application for you. This application
|
||||
not only demonstrates the basics of using the Microsoft Foundation classes
|
||||
but is also a starting point for writing your application.
|
||||
|
||||
This file contains a summary of what you will find in each of the files that
|
||||
make up your hogedit application.
|
||||
|
||||
hogedit.h
|
||||
This is the main header file for the application. It includes other
|
||||
project specific headers (including Resource.h) and declares the
|
||||
CHogeditApp application class.
|
||||
|
||||
hogedit.cpp
|
||||
This is the main application source file that contains the application
|
||||
class CHogeditApp.
|
||||
|
||||
hogedit.rc
|
||||
This is a listing of all of the Microsoft Windows resources that the
|
||||
program uses. It includes the icons, bitmaps, and cursors that are stored
|
||||
in the RES subdirectory. This file can be directly edited in Microsoft
|
||||
Developer Studio.
|
||||
|
||||
res\hogedit.ico
|
||||
This is an icon file, which is used as the application's icon. This
|
||||
icon is included by the main resource file hogedit.rc.
|
||||
|
||||
res\hogedit.rc2
|
||||
This file contains resources that are not edited by Microsoft
|
||||
Developer Studio. You should place all resources not
|
||||
editable by the resource editor in this file.
|
||||
|
||||
hogedit.clw
|
||||
This file contains information used by ClassWizard to edit existing
|
||||
classes or add new classes. ClassWizard also uses this file to store
|
||||
information needed to create and edit message maps and dialog data
|
||||
maps and to create prototype member functions.
|
||||
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
AppWizard creates one dialog class:
|
||||
|
||||
hogeditDlg.h, hogeditDlg.cpp - the dialog
|
||||
These files contain your CHogeditDlg class. This class defines
|
||||
the behavior of your application's main dialog. The dialog's
|
||||
template is in hogedit.rc, which can be edited in Microsoft
|
||||
Developer Studio.
|
||||
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
Other standard files:
|
||||
|
||||
StdAfx.h, StdAfx.cpp
|
||||
These files are used to build a precompiled header (PCH) file
|
||||
named hogedit.pch and a precompiled types file named StdAfx.obj.
|
||||
|
||||
Resource.h
|
||||
This is the standard header file, which defines new resource IDs.
|
||||
Microsoft Developer Studio reads and updates this file.
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
Other notes:
|
||||
|
||||
AppWizard uses "TODO:" to indicate parts of the source code you
|
||||
should add to or customize.
|
||||
|
||||
If your application uses MFC in a shared DLL, and your application is
|
||||
in a language other than the operating system's current language, you
|
||||
will need to copy the corresponding localized resources MFC40XXX.DLL
|
||||
from the Microsoft Visual C++ CD-ROM onto the system or system32 directory,
|
||||
and rename it to be MFCLOC.DLL. ("XXX" stands for the language abbreviation.
|
||||
For example, MFC40DEU.DLL contains resources translated to German.) If you
|
||||
don't do this, some of the UI elements of your application will remain in the
|
||||
language of the operating system.
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
34
hogedit/Resource.h
Normal file
34
hogedit/Resource.h
Normal file
@ -0,0 +1,34 @@
|
||||
//{{NO_DEPENDENCIES}}
|
||||
// Microsoft Developer Studio generated include file.
|
||||
// Used by HogEdit.rc
|
||||
//
|
||||
#define IDD_ABOUTBOX 100
|
||||
#define IDR_MAINFRAME 128
|
||||
#define IDR_HOGEDITYPE 129
|
||||
#define IDD_HOGINFO 130
|
||||
#define IDC_HOGINFO_FILES 1000
|
||||
#define IDC_HOGINFO_SIZE_BYTES 1001
|
||||
#define IDC_HOGINFO_LOCATION 1002
|
||||
#define IDC_HOGINFO_SIZE_MB 1003
|
||||
#define ID_ACTION_INSERT 32771
|
||||
#define ID_ACTION_DELETE 32772
|
||||
#define ID_ACTION_UPDATE 32773
|
||||
#define ID_ACTION_BUILD 32776
|
||||
#define ID_ACTION_CREATE 32777
|
||||
#define ID_VIEW_FULL_ROW 32778
|
||||
#define ID_ACTION_EXTRACT 32779
|
||||
#define ID_ACTION_IMPORT 32782
|
||||
#define IDS_STRING61204 61204
|
||||
#define ID_INDICATOR_FILES 61205
|
||||
|
||||
// Next default values for new objects
|
||||
//
|
||||
#ifdef APSTUDIO_INVOKED
|
||||
#ifndef APSTUDIO_READONLY_SYMBOLS
|
||||
#define _APS_3D_CONTROLS 1
|
||||
#define _APS_NEXT_RESOURCE_VALUE 131
|
||||
#define _APS_NEXT_COMMAND_VALUE 32784
|
||||
#define _APS_NEXT_CONTROL_VALUE 1004
|
||||
#define _APS_NEXT_SYMED_VALUE 101
|
||||
#endif
|
||||
#endif
|
6
hogedit/StdAfx.cpp
Normal file
6
hogedit/StdAfx.cpp
Normal file
@ -0,0 +1,6 @@
|
||||
// stdafx.cpp : source file that includes just the standard includes
|
||||
// HogEdit.pch will be the pre-compiled header
|
||||
// stdafx.obj will contain the pre-compiled type information
|
||||
|
||||
#include "stdafx.h"
|
||||
|
27
hogedit/StdAfx.h
Normal file
27
hogedit/StdAfx.h
Normal file
@ -0,0 +1,27 @@
|
||||
// stdafx.h : include file for standard system include files,
|
||||
// or project specific include files that are used frequently, but
|
||||
// are changed infrequently
|
||||
//
|
||||
|
||||
#if !defined(AFX_STDAFX_H__48BE52BA_172F_11D2_8CBC_00A0C96ED60D__INCLUDED_)
|
||||
#define AFX_STDAFX_H__48BE52BA_172F_11D2_8CBC_00A0C96ED60D__INCLUDED_
|
||||
|
||||
#if _MSC_VER >= 1000
|
||||
#pragma once
|
||||
#endif // _MSC_VER >= 1000
|
||||
|
||||
#define VC_EXTRALEAN // Exclude rarely-used stuff from Windows headers
|
||||
|
||||
#include <afxwin.h> // MFC core and standard components
|
||||
#include <afxext.h> // MFC extensions
|
||||
#include <afxcview.h>
|
||||
#include <afxdisp.h> // MFC OLE automation classes
|
||||
#ifndef _AFX_NO_AFXCMN_SUPPORT
|
||||
#include <afxcmn.h> // MFC support for Windows Common Controls
|
||||
#endif // _AFX_NO_AFXCMN_SUPPORT
|
||||
|
||||
|
||||
//{{AFX_INSERT_LOCATION}}
|
||||
// Microsoft Developer Studio will insert additional declarations immediately before the previous line.
|
||||
|
||||
#endif // !defined(AFX_STDAFX_H__48BE52BA_172F_11D2_8CBC_00A0C96ED60D__INCLUDED_)
|
454
hogedit/listvwex.cpp
Normal file
454
hogedit/listvwex.cpp
Normal file
@ -0,0 +1,454 @@
|
||||
// ListVwEx.cpp : implementation of the CListViewEx class
|
||||
//
|
||||
// This is a part of the Microsoft Foundation Classes C++ library.
|
||||
// Copyright (C) 1992-1997 Microsoft Corporation
|
||||
// All rights reserved.
|
||||
//
|
||||
// This source code is only intended as a supplement to the
|
||||
// Microsoft Foundation Classes Reference and related
|
||||
// electronic documentation provided with the library.
|
||||
// See these sources for detailed information regarding the
|
||||
// Microsoft Foundation Classes product.
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "ListVwEx.h"
|
||||
|
||||
#ifdef _DEBUG
|
||||
#define new DEBUG_NEW
|
||||
#undef THIS_FILE
|
||||
static char THIS_FILE[] = __FILE__;
|
||||
#endif
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// CListViewEx
|
||||
|
||||
IMPLEMENT_DYNCREATE(CListViewEx, CListView)
|
||||
|
||||
BEGIN_MESSAGE_MAP(CListViewEx, CListView)
|
||||
//{{AFX_MSG_MAP(CListViewEx)
|
||||
ON_WM_SIZE()
|
||||
ON_WM_PAINT()
|
||||
ON_WM_SETFOCUS()
|
||||
ON_WM_KILLFOCUS()
|
||||
//}}AFX_MSG_MAP
|
||||
ON_MESSAGE(LVM_SETIMAGELIST, OnSetImageList)
|
||||
ON_MESSAGE(LVM_SETTEXTCOLOR, OnSetTextColor)
|
||||
ON_MESSAGE(LVM_SETTEXTBKCOLOR, OnSetTextBkColor)
|
||||
ON_MESSAGE(LVM_SETBKCOLOR, OnSetBkColor)
|
||||
END_MESSAGE_MAP()
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// CListViewEx construction/destruction
|
||||
|
||||
CListViewEx::CListViewEx()
|
||||
{
|
||||
m_bFullRowSel = TRUE;
|
||||
m_bClientWidthSel = TRUE;
|
||||
|
||||
m_cxClient = 0;
|
||||
m_cxStateImageOffset = 0;
|
||||
|
||||
m_clrText = ::GetSysColor(COLOR_WINDOWTEXT);
|
||||
m_clrTextBk = ::GetSysColor(COLOR_WINDOW);
|
||||
m_clrBkgnd = ::GetSysColor(COLOR_WINDOW);
|
||||
}
|
||||
|
||||
CListViewEx::~CListViewEx()
|
||||
{
|
||||
}
|
||||
|
||||
BOOL CListViewEx::PreCreateWindow(CREATESTRUCT& cs)
|
||||
{
|
||||
// default is report view and full row selection
|
||||
cs.style &= ~LVS_TYPEMASK;
|
||||
cs.style |= LVS_REPORT | LVS_OWNERDRAWFIXED;
|
||||
m_bFullRowSel = TRUE;
|
||||
|
||||
return(CListView::PreCreateWindow(cs));
|
||||
}
|
||||
|
||||
BOOL CListViewEx::SetFullRowSel(BOOL bFullRowSel)
|
||||
{
|
||||
// no painting during change
|
||||
LockWindowUpdate();
|
||||
|
||||
m_bFullRowSel = bFullRowSel;
|
||||
|
||||
BOOL bRet;
|
||||
|
||||
if (m_bFullRowSel)
|
||||
bRet = ModifyStyle(0L, LVS_OWNERDRAWFIXED);
|
||||
else
|
||||
bRet = ModifyStyle(LVS_OWNERDRAWFIXED, 0L);
|
||||
|
||||
// repaint window if we are not changing view type
|
||||
if (bRet && (GetStyle() & LVS_TYPEMASK) == LVS_REPORT)
|
||||
Invalidate();
|
||||
|
||||
// repaint changes
|
||||
UnlockWindowUpdate();
|
||||
|
||||
return(bRet);
|
||||
}
|
||||
|
||||
BOOL CListViewEx::GetFullRowSel()
|
||||
{
|
||||
return(m_bFullRowSel);
|
||||
}
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// CListViewEx drawing
|
||||
|
||||
// offsets for first and other columns
|
||||
#define OFFSET_FIRST 2
|
||||
#define OFFSET_OTHER 6
|
||||
|
||||
void CListViewEx::DrawItem(LPDRAWITEMSTRUCT lpDrawItemStruct)
|
||||
{
|
||||
CListCtrl& ListCtrl=GetListCtrl();
|
||||
CDC* pDC = CDC::FromHandle(lpDrawItemStruct->hDC);
|
||||
CRect rcItem(lpDrawItemStruct->rcItem);
|
||||
UINT uiFlags = ILD_TRANSPARENT;
|
||||
CImageList* pImageList;
|
||||
int nItem = lpDrawItemStruct->itemID;
|
||||
BOOL bFocus = (GetFocus() == this);
|
||||
COLORREF clrTextSave, clrBkSave;
|
||||
COLORREF clrImage = m_clrBkgnd;
|
||||
static _TCHAR szBuff[MAX_PATH];
|
||||
LPCTSTR pszText;
|
||||
|
||||
// get item data
|
||||
|
||||
LV_ITEM lvi;
|
||||
lvi.mask = LVIF_TEXT | LVIF_IMAGE | LVIF_STATE;
|
||||
lvi.iItem = nItem;
|
||||
lvi.iSubItem = 0;
|
||||
lvi.pszText = szBuff;
|
||||
lvi.cchTextMax = sizeof(szBuff);
|
||||
lvi.stateMask = 0xFFFF; // get all state flags
|
||||
ListCtrl.GetItem(&lvi);
|
||||
|
||||
BOOL bSelected = (bFocus || (GetStyle() & LVS_SHOWSELALWAYS)) && lvi.state & LVIS_SELECTED;
|
||||
bSelected = bSelected || (lvi.state & LVIS_DROPHILITED);
|
||||
|
||||
// set colors if item is selected
|
||||
|
||||
CRect rcAllLabels;
|
||||
ListCtrl.GetItemRect(nItem, rcAllLabels, LVIR_BOUNDS);
|
||||
|
||||
CRect rcLabel;
|
||||
ListCtrl.GetItemRect(nItem, rcLabel, LVIR_LABEL);
|
||||
|
||||
rcAllLabels.left = rcLabel.left;
|
||||
if (m_bClientWidthSel && rcAllLabels.right<m_cxClient)
|
||||
rcAllLabels.right = m_cxClient;
|
||||
|
||||
if (bSelected)
|
||||
{
|
||||
clrTextSave = pDC->SetTextColor(::GetSysColor(COLOR_HIGHLIGHTTEXT));
|
||||
clrBkSave = pDC->SetBkColor(::GetSysColor(COLOR_HIGHLIGHT));
|
||||
|
||||
pDC->FillRect(rcAllLabels, &CBrush(::GetSysColor(COLOR_HIGHLIGHT)));
|
||||
}
|
||||
else
|
||||
pDC->FillRect(rcAllLabels, &CBrush(m_clrTextBk));
|
||||
|
||||
// set color and mask for the icon
|
||||
|
||||
if (lvi.state & LVIS_CUT)
|
||||
{
|
||||
clrImage = m_clrBkgnd;
|
||||
uiFlags |= ILD_BLEND50;
|
||||
}
|
||||
else if (bSelected)
|
||||
{
|
||||
clrImage = ::GetSysColor(COLOR_HIGHLIGHT);
|
||||
uiFlags |= ILD_BLEND50;
|
||||
}
|
||||
|
||||
// draw state icon
|
||||
|
||||
UINT nStateImageMask = lvi.state & LVIS_STATEIMAGEMASK;
|
||||
if (nStateImageMask)
|
||||
{
|
||||
int nImage = (nStateImageMask>>12) - 1;
|
||||
pImageList = ListCtrl.GetImageList(LVSIL_STATE);
|
||||
if (pImageList)
|
||||
{
|
||||
pImageList->Draw(pDC, nImage,
|
||||
CPoint(rcItem.left, rcItem.top), ILD_TRANSPARENT);
|
||||
}
|
||||
}
|
||||
|
||||
// draw normal and overlay icon
|
||||
|
||||
CRect rcIcon;
|
||||
ListCtrl.GetItemRect(nItem, rcIcon, LVIR_ICON);
|
||||
|
||||
pImageList = ListCtrl.GetImageList(LVSIL_SMALL);
|
||||
if (pImageList)
|
||||
{
|
||||
UINT nOvlImageMask=lvi.state & LVIS_OVERLAYMASK;
|
||||
if (rcItem.left<rcItem.right-1)
|
||||
{
|
||||
ImageList_DrawEx(pImageList->m_hImageList, lvi.iImage,
|
||||
pDC->m_hDC,rcIcon.left,rcIcon.top, 16, 16,
|
||||
m_clrBkgnd, clrImage, uiFlags | nOvlImageMask);
|
||||
}
|
||||
}
|
||||
|
||||
// draw item label
|
||||
|
||||
ListCtrl.GetItemRect(nItem, rcItem, LVIR_LABEL);
|
||||
rcItem.right -= m_cxStateImageOffset;
|
||||
|
||||
pszText = MakeShortString(pDC, szBuff,
|
||||
rcItem.right-rcItem.left, 2*OFFSET_FIRST);
|
||||
|
||||
rcLabel = rcItem;
|
||||
rcLabel.left += OFFSET_FIRST;
|
||||
rcLabel.right -= OFFSET_FIRST;
|
||||
|
||||
pDC->DrawText(pszText,-1,rcLabel,DT_LEFT | DT_SINGLELINE | DT_NOPREFIX | DT_NOCLIP | DT_VCENTER);
|
||||
|
||||
// draw labels for extra columns
|
||||
|
||||
LV_COLUMN lvc;
|
||||
lvc.mask = LVCF_FMT | LVCF_WIDTH;
|
||||
|
||||
for(int nColumn = 1; ListCtrl.GetColumn(nColumn, &lvc); nColumn++)
|
||||
{
|
||||
rcItem.left = rcItem.right;
|
||||
rcItem.right += lvc.cx;
|
||||
|
||||
int nRetLen = ListCtrl.GetItemText(nItem, nColumn,
|
||||
szBuff, sizeof(szBuff));
|
||||
if (nRetLen == 0)
|
||||
continue;
|
||||
|
||||
pszText = MakeShortString(pDC, szBuff,
|
||||
rcItem.right - rcItem.left, 2*OFFSET_OTHER);
|
||||
|
||||
UINT nJustify = DT_LEFT;
|
||||
|
||||
if(pszText == szBuff)
|
||||
{
|
||||
switch(lvc.fmt & LVCFMT_JUSTIFYMASK)
|
||||
{
|
||||
case LVCFMT_RIGHT:
|
||||
nJustify = DT_RIGHT;
|
||||
break;
|
||||
case LVCFMT_CENTER:
|
||||
nJustify = DT_CENTER;
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
rcLabel = rcItem;
|
||||
rcLabel.left += OFFSET_OTHER;
|
||||
rcLabel.right -= OFFSET_OTHER;
|
||||
|
||||
pDC->DrawText(pszText, -1, rcLabel,
|
||||
nJustify | DT_SINGLELINE | DT_NOPREFIX | DT_NOCLIP | DT_VCENTER);
|
||||
}
|
||||
|
||||
// draw focus rectangle if item has focus
|
||||
|
||||
if (lvi.state & LVIS_FOCUSED && bFocus)
|
||||
pDC->DrawFocusRect(rcAllLabels);
|
||||
|
||||
// set original colors if item was selected
|
||||
|
||||
if (bSelected)
|
||||
{
|
||||
pDC->SetTextColor(clrTextSave);
|
||||
pDC->SetBkColor(clrBkSave);
|
||||
}
|
||||
}
|
||||
|
||||
LPCTSTR CListViewEx::MakeShortString(CDC* pDC, LPCTSTR lpszLong, int nColumnLen, int nOffset)
|
||||
{
|
||||
static const _TCHAR szThreeDots[] = _T("...");
|
||||
|
||||
int nStringLen = lstrlen(lpszLong);
|
||||
|
||||
if(nStringLen == 0 ||
|
||||
(pDC->GetTextExtent(lpszLong, nStringLen).cx + nOffset) <= nColumnLen)
|
||||
{
|
||||
return(lpszLong);
|
||||
}
|
||||
|
||||
static _TCHAR szShort[MAX_PATH];
|
||||
|
||||
lstrcpy(szShort,lpszLong);
|
||||
int nAddLen = pDC->GetTextExtent(szThreeDots,sizeof(szThreeDots)).cx;
|
||||
|
||||
for(int i = nStringLen-1; i > 0; i--)
|
||||
{
|
||||
szShort[i] = 0;
|
||||
if((pDC->GetTextExtent(szShort, i).cx + nOffset + nAddLen)
|
||||
<= nColumnLen)
|
||||
{
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
lstrcat(szShort, szThreeDots);
|
||||
return(szShort);
|
||||
}
|
||||
|
||||
void CListViewEx::RepaintSelectedItems()
|
||||
{
|
||||
CListCtrl& ListCtrl = GetListCtrl();
|
||||
CRect rcItem, rcLabel;
|
||||
|
||||
// invalidate focused item so it can repaint properly
|
||||
|
||||
int nItem = ListCtrl.GetNextItem(-1, LVNI_FOCUSED);
|
||||
|
||||
if(nItem != -1)
|
||||
{
|
||||
ListCtrl.GetItemRect(nItem, rcItem, LVIR_BOUNDS);
|
||||
ListCtrl.GetItemRect(nItem, rcLabel, LVIR_LABEL);
|
||||
rcItem.left = rcLabel.left;
|
||||
|
||||
InvalidateRect(rcItem, FALSE);
|
||||
}
|
||||
|
||||
// if selected items should not be preserved, invalidate them
|
||||
|
||||
if(!(GetStyle() & LVS_SHOWSELALWAYS))
|
||||
{
|
||||
for(nItem = ListCtrl.GetNextItem(-1, LVNI_SELECTED);
|
||||
nItem != -1; nItem = ListCtrl.GetNextItem(nItem, LVNI_SELECTED))
|
||||
{
|
||||
ListCtrl.GetItemRect(nItem, rcItem, LVIR_BOUNDS);
|
||||
ListCtrl.GetItemRect(nItem, rcLabel, LVIR_LABEL);
|
||||
rcItem.left = rcLabel.left;
|
||||
|
||||
InvalidateRect(rcItem, FALSE);
|
||||
}
|
||||
}
|
||||
|
||||
// update changes
|
||||
|
||||
UpdateWindow();
|
||||
}
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// CListViewEx diagnostics
|
||||
|
||||
#ifdef _DEBUG
|
||||
|
||||
void CListViewEx::Dump(CDumpContext& dc) const
|
||||
{
|
||||
CListView::Dump(dc);
|
||||
|
||||
dc << "m_bFullRowSel = " << (UINT)m_bFullRowSel;
|
||||
dc << "\n";
|
||||
dc << "m_cxStateImageOffset = " << m_cxStateImageOffset;
|
||||
dc << "\n";
|
||||
}
|
||||
|
||||
#endif //_DEBUG
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// CListViewEx message handlers
|
||||
|
||||
LRESULT CListViewEx::OnSetImageList(WPARAM wParam, LPARAM lParam)
|
||||
{
|
||||
if( (int) wParam == LVSIL_STATE)
|
||||
{
|
||||
int cx, cy;
|
||||
|
||||
if(::ImageList_GetIconSize((HIMAGELIST)lParam, &cx, &cy))
|
||||
m_cxStateImageOffset = cx;
|
||||
else
|
||||
m_cxStateImageOffset = 0;
|
||||
}
|
||||
|
||||
return(Default());
|
||||
}
|
||||
|
||||
LRESULT CListViewEx::OnSetTextColor(WPARAM wParam, LPARAM lParam)
|
||||
{
|
||||
m_clrText = (COLORREF)lParam;
|
||||
return(Default());
|
||||
}
|
||||
|
||||
LRESULT CListViewEx::OnSetTextBkColor(WPARAM wParam, LPARAM lParam)
|
||||
{
|
||||
m_clrTextBk = (COLORREF)lParam;
|
||||
return(Default());
|
||||
}
|
||||
|
||||
LRESULT CListViewEx::OnSetBkColor(WPARAM wParam, LPARAM lParam)
|
||||
{
|
||||
m_clrBkgnd = (COLORREF)lParam;
|
||||
return(Default());
|
||||
}
|
||||
|
||||
void CListViewEx::OnSize(UINT nType, int cx, int cy)
|
||||
{
|
||||
m_cxClient = cx;
|
||||
CListView::OnSize(nType, cx, cy);
|
||||
}
|
||||
|
||||
void CListViewEx::OnPaint()
|
||||
{
|
||||
// in full row select mode, we need to extend the clipping region
|
||||
// so we can paint a selection all the way to the right
|
||||
if (m_bClientWidthSel &&
|
||||
(GetStyle() & LVS_TYPEMASK) == LVS_REPORT &&
|
||||
GetFullRowSel())
|
||||
{
|
||||
CRect rcAllLabels;
|
||||
GetListCtrl().GetItemRect(0, rcAllLabels, LVIR_BOUNDS);
|
||||
|
||||
if(rcAllLabels.right < m_cxClient)
|
||||
{
|
||||
// need to call BeginPaint (in CPaintDC c-tor)
|
||||
// to get correct clipping rect
|
||||
CPaintDC dc(this);
|
||||
|
||||
CRect rcClip;
|
||||
dc.GetClipBox(rcClip);
|
||||
|
||||
rcClip.left = min(rcAllLabels.right-1, rcClip.left);
|
||||
rcClip.right = m_cxClient;
|
||||
|
||||
InvalidateRect(rcClip, FALSE);
|
||||
// EndPaint will be called in CPaintDC d-tor
|
||||
}
|
||||
}
|
||||
|
||||
CListView::OnPaint();
|
||||
}
|
||||
|
||||
void CListViewEx::OnSetFocus(CWnd* pOldWnd)
|
||||
{
|
||||
CListView::OnSetFocus(pOldWnd);
|
||||
|
||||
// check if we are getting focus from label edit box
|
||||
if(pOldWnd!=NULL && pOldWnd->GetParent()==this)
|
||||
return;
|
||||
|
||||
// repaint items that should change appearance
|
||||
if(m_bFullRowSel && (GetStyle() & LVS_TYPEMASK)==LVS_REPORT)
|
||||
RepaintSelectedItems();
|
||||
}
|
||||
|
||||
void CListViewEx::OnKillFocus(CWnd* pNewWnd)
|
||||
{
|
||||
CListView::OnKillFocus(pNewWnd);
|
||||
|
||||
// check if we are losing focus to label edit box
|
||||
if(pNewWnd != NULL && pNewWnd->GetParent() == this)
|
||||
return;
|
||||
|
||||
// repaint items that should change appearance
|
||||
if(m_bFullRowSel && (GetStyle() & LVS_TYPEMASK) == LVS_REPORT)
|
||||
RepaintSelectedItems();
|
||||
}
|
82
hogedit/listvwex.h
Normal file
82
hogedit/listvwex.h
Normal file
@ -0,0 +1,82 @@
|
||||
// ListVwEx.h : interface of the CListViewEx class
|
||||
//
|
||||
// This class provedes a full row selection mode for the report
|
||||
// mode list view control.
|
||||
//
|
||||
// This is a part of the Microsoft Foundation Classes C++ library.
|
||||
// Copyright (C) 1992-1997 Microsoft Corporation
|
||||
// All rights reserved.
|
||||
//
|
||||
// This source code is only intended as a supplement to the
|
||||
// Microsoft Foundation Classes Reference and related
|
||||
// electronic documentation provided with the library.
|
||||
// See these sources for detailed information regarding the
|
||||
// Microsoft Foundation Classes product.
|
||||
|
||||
class CListViewEx : public CListView
|
||||
{
|
||||
DECLARE_DYNCREATE(CListViewEx)
|
||||
|
||||
// Construction
|
||||
public:
|
||||
CListViewEx();
|
||||
|
||||
// Attributes
|
||||
protected:
|
||||
BOOL m_bFullRowSel;
|
||||
|
||||
public:
|
||||
BOOL SetFullRowSel(BOOL bFillRowSel);
|
||||
BOOL GetFullRowSel();
|
||||
|
||||
BOOL m_bClientWidthSel;
|
||||
|
||||
// Overrides
|
||||
protected:
|
||||
virtual void DrawItem(LPDRAWITEMSTRUCT lpDrawItemStruct);
|
||||
|
||||
// ClassWizard generated virtual function overrides
|
||||
//{{AFX_VIRTUAL(CListViewEx)
|
||||
public:
|
||||
virtual BOOL PreCreateWindow(CREATESTRUCT& cs);
|
||||
protected:
|
||||
//}}AFX_VIRTUAL
|
||||
|
||||
// Implementation
|
||||
public:
|
||||
virtual ~CListViewEx();
|
||||
#ifdef _DEBUG
|
||||
virtual void Dump(CDumpContext& dc) const;
|
||||
#endif
|
||||
|
||||
protected:
|
||||
static LPCTSTR MakeShortString(CDC* pDC, LPCTSTR lpszLong, int nColumnLen, int nOffset);
|
||||
void RepaintSelectedItems();
|
||||
|
||||
// Implementation - client area width
|
||||
int m_cxClient;
|
||||
|
||||
// Implementation - state icon width
|
||||
int m_cxStateImageOffset;
|
||||
afx_msg LRESULT OnSetImageList(WPARAM wParam, LPARAM lParam);
|
||||
|
||||
// Implementation - list view colors
|
||||
COLORREF m_clrText;
|
||||
COLORREF m_clrTextBk;
|
||||
COLORREF m_clrBkgnd;
|
||||
afx_msg LRESULT OnSetTextColor(WPARAM wParam, LPARAM lParam);
|
||||
afx_msg LRESULT OnSetTextBkColor(WPARAM wParam, LPARAM lParam);
|
||||
afx_msg LRESULT OnSetBkColor(WPARAM wParam, LPARAM lParam);
|
||||
|
||||
// Generated message map functions
|
||||
protected:
|
||||
//{{AFX_MSG(CListViewEx)
|
||||
afx_msg void OnSize(UINT nType, int cx, int cy);
|
||||
afx_msg void OnPaint();
|
||||
afx_msg void OnSetFocus(CWnd* pOldWnd);
|
||||
afx_msg void OnKillFocus(CWnd* pNewWnd);
|
||||
//}}AFX_MSG
|
||||
DECLARE_MESSAGE_MAP()
|
||||
};
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
BIN
hogedit/res/HogEdit.ico
Normal file
BIN
hogedit/res/HogEdit.ico
Normal file
Binary file not shown.
After Width: | Height: | Size: 3.2 KiB |
BIN
hogedit/res/HogEdit.rc2
Normal file
BIN
hogedit/res/HogEdit.rc2
Normal file
Binary file not shown.
BIN
hogedit/res/HogEditDoc.ico
Normal file
BIN
hogedit/res/HogEditDoc.ico
Normal file
Binary file not shown.
After Width: | Height: | Size: 1.1 KiB |
BIN
hogedit/res/Toolbar.bmp
Normal file
BIN
hogedit/res/Toolbar.bmp
Normal file
Binary file not shown.
After Width: | Height: | Size: 1.3 KiB |
259
hogmaker/hog.cpp
Normal file
259
hogmaker/hog.cpp
Normal file
@ -0,0 +1,259 @@
|
||||
/*
|
||||
* $Logfile: /DescentIII/Main/hogmaker/hog.cpp $
|
||||
* $Revision: 1.1.1.1 $
|
||||
* $Date: 2003-08-26 03:57:56 $
|
||||
* $Author: kevinb $
|
||||
*
|
||||
*
|
||||
*
|
||||
* $Log: not supported by cvs2svn $
|
||||
*
|
||||
* 2 3/31/98 6:13p Samir
|
||||
* new hogfile format.
|
||||
*
|
||||
* 1 3/31/98 5:15p Samir
|
||||
* new hog file read and write module.
|
||||
*
|
||||
* $NoKeywords: $
|
||||
*/
|
||||
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <io.h>
|
||||
#include <sys/stat.h>
|
||||
|
||||
#include "hogfile.h"
|
||||
#include "pstypes.h"
|
||||
#include "macros.h"
|
||||
|
||||
|
||||
/* HOG FILE FORMAT v2.0
|
||||
|
||||
HOG_TAG_STR [strlen()]
|
||||
NFILES [int32]
|
||||
HDRINFO [HOG_HDR_SIZE]
|
||||
FILE_TABLE [sizeof(FILE_ENTRY) * NFILES]
|
||||
FILE 0 [filelen(FILE 0)]
|
||||
FILE 1 [filelen(FILE 1)]
|
||||
.
|
||||
.
|
||||
.
|
||||
FILE NFILES-1 [filelen(NFILES -1)]
|
||||
*/
|
||||
|
||||
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
bool CopyFile(FILE *ofp,FILE *ifp,int length)
|
||||
{
|
||||
#define BUFFER_SIZE (1024*1024) // 1 meg
|
||||
|
||||
char *buffer;
|
||||
|
||||
buffer = (char *)malloc(BUFFER_SIZE);
|
||||
if (!buffer)
|
||||
return false;
|
||||
|
||||
while (length)
|
||||
{
|
||||
size_t n,read_len;
|
||||
|
||||
read_len = min(length,(int)BUFFER_SIZE);
|
||||
|
||||
n = fread( buffer, 1, read_len, ifp );
|
||||
if ( n != read_len ) {
|
||||
free(buffer);
|
||||
return false;
|
||||
}
|
||||
|
||||
if (fwrite( buffer, 1, read_len, ofp) != read_len ) {
|
||||
free(buffer);
|
||||
return false;
|
||||
}
|
||||
|
||||
length -= read_len;
|
||||
}
|
||||
|
||||
free(buffer);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
bool ReadHogHeader(FILE *fp, tHogHeader *header)
|
||||
{
|
||||
int res=0;
|
||||
res = fread(&header->nfiles, sizeof(header->nfiles), 1, fp);
|
||||
res = fwrite(&header->file_data_offset, sizeof(header->file_data_offset), 1, fp);
|
||||
|
||||
if (res)
|
||||
return true;
|
||||
else
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
bool ReadHogEntry(FILE *fp, tHogFileEntry *entry)
|
||||
{
|
||||
int res=0;
|
||||
res = fread(entry->name, strlen(entry->name), 1, fp);
|
||||
res = fread(&entry->flags, sizeof(entry->flags), 1, fp);
|
||||
res = fread(&entry->len, sizeof(entry->len), 1, fp);
|
||||
res = fread(&entry->timestamp, sizeof(entry->timestamp), 1, fp);
|
||||
|
||||
if (res)
|
||||
return true;
|
||||
else
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
inline bool WRITE_FILE_ENTRY(FILE *fp, tHogFileEntry *entry)
|
||||
{
|
||||
int res=0;
|
||||
res = fwrite(entry->name, strlen(entry->name), 1, fp);
|
||||
res = fwrite(&entry->flags, sizeof(entry->flags), 1, fp);
|
||||
res = fwrite(&entry->len, sizeof(entry->len), 1, fp);
|
||||
res = fwrite(&entry->timestamp, sizeof(entry->timestamp), 1, fp);
|
||||
|
||||
if (res)
|
||||
return true;
|
||||
else
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// create new hog file
|
||||
|
||||
#define HOGMAKER_ERROR 0
|
||||
#define HOGMAKER_OK 1
|
||||
#define HOGMAKER_MEMORY 2
|
||||
#define HOGMAKER_OUTFILE 3
|
||||
#define HOGMAKER_INFILE 4
|
||||
#define HOGMAKER_COPY 5
|
||||
|
||||
int NewHogFile(const char *hogname, int nfiles, const char **filenames)
|
||||
{
|
||||
unsigned i;
|
||||
int table_pos;
|
||||
FILE *hog_fp;
|
||||
tHogHeader header;
|
||||
tHogFileEntry *table;
|
||||
char ext[_MAX_EXT];
|
||||
|
||||
// allocate file table
|
||||
if (nfiles <= 0)
|
||||
return HOGMAKER_ERROR;
|
||||
|
||||
table = new tHogFileEntry[nfiles];
|
||||
if (!table)
|
||||
return HOGMAKER_MEMORY;
|
||||
|
||||
// create new file
|
||||
hog_fp = fopen( hogname, "wb" );
|
||||
if ( hog_fp == NULL ) {
|
||||
delete[] table;
|
||||
return HOGMAKER_OUTFILE;
|
||||
}
|
||||
|
||||
//write the tag
|
||||
if (!fwrite(HOG_TAG_STR, strlen(HOG_TAG_STR), 1, hog_fp )) {
|
||||
delete[] table;
|
||||
fclose(hog_fp);
|
||||
return HOGMAKER_OUTFILE;
|
||||
}
|
||||
|
||||
//write number of files
|
||||
ubyte filler = 0xff;
|
||||
header.nfiles = (unsigned)nfiles;
|
||||
header.file_data_offset = strlen(HOG_TAG_STR) + HOG_HDR_SIZE + (sizeof(tHogFileEntry) * header.nfiles);
|
||||
|
||||
if (!fwrite(&header.nfiles,sizeof(header.nfiles),1,hog_fp)) {
|
||||
delete[] table;
|
||||
fclose(hog_fp);
|
||||
return HOGMAKER_OUTFILE;
|
||||
}
|
||||
if (!fwrite(&header.file_data_offset,sizeof(header.file_data_offset),1,hog_fp)) {
|
||||
delete[] table;
|
||||
fclose(hog_fp);
|
||||
return HOGMAKER_OUTFILE;
|
||||
}
|
||||
if (!fwrite(&filler,sizeof(ubyte),HOG_HDR_SIZE-sizeof(tHogHeader),hog_fp)) {
|
||||
delete[] table;
|
||||
fclose(hog_fp);
|
||||
return HOGMAKER_OUTFILE;
|
||||
}
|
||||
|
||||
//save file position of index table and write out dummy table
|
||||
table_pos = strlen(HOG_TAG_STR) + HOG_HDR_SIZE;
|
||||
|
||||
memset(&table[0], 0, sizeof(table[0]));
|
||||
|
||||
for (i = 0; i < header.nfiles; i++)
|
||||
{
|
||||
if (!WRITE_FILE_ENTRY(hog_fp, &table[0])) {
|
||||
delete[] table;
|
||||
fclose(hog_fp);
|
||||
return HOGMAKER_OUTFILE;
|
||||
}
|
||||
}
|
||||
|
||||
//write files (& build index)
|
||||
for (i=0;i<header.nfiles;i++)
|
||||
{
|
||||
FILE *ifp;
|
||||
struct _stat mystat;
|
||||
|
||||
ifp = fopen(filenames[i],"rb");
|
||||
if ( ifp == NULL ) {
|
||||
delete[] table;
|
||||
fclose(hog_fp);
|
||||
return HOGMAKER_INFILE;
|
||||
}
|
||||
|
||||
_splitpath(filenames[i],NULL,NULL,table[i].name,ext);
|
||||
_fstat(fileno(ifp), &mystat);
|
||||
|
||||
strcat(table[i].name,ext);
|
||||
table[i].flags = 0;
|
||||
table[i].len = _filelength(_fileno(ifp));
|
||||
table[i].timestamp = mystat.st_mtime;
|
||||
|
||||
if (!CopyFile(hog_fp,ifp,table[i].len)) {
|
||||
delete[] table;
|
||||
fclose(hog_fp);
|
||||
return HOGMAKER_COPY;
|
||||
}
|
||||
|
||||
fclose(ifp);
|
||||
}
|
||||
|
||||
//now write the real index
|
||||
fseek(hog_fp,table_pos,SEEK_SET);
|
||||
|
||||
for (i = 0; i < header.nfiles; i++)
|
||||
{
|
||||
if (!WRITE_FILE_ENTRY(hog_fp, &table[i])) {
|
||||
delete[] table;
|
||||
fclose(hog_fp);
|
||||
return HOGMAKER_OUTFILE;
|
||||
}
|
||||
}
|
||||
|
||||
// cleanup
|
||||
fclose( hog_fp );
|
||||
delete[] table;
|
||||
|
||||
return HOGMAKER_OK;
|
||||
}
|
||||
|
||||
|
||||
|
||||
/* CopyFile
|
||||
used to copy one file to another.
|
||||
*/
|
||||
|
493
hogmaker/hogmaker.c
Normal file
493
hogmaker/hogmaker.c
Normal file
@ -0,0 +1,493 @@
|
||||
#include <dos.h>
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <io.h>
|
||||
#include <ctype.h>
|
||||
#include <time.h>
|
||||
#include <sys\stat.h>
|
||||
#include <sys\utime.h>
|
||||
|
||||
//#include "mvlfile.h" //for old D2 movie libraries
|
||||
#include "hogfile.h" //new D3 hogs
|
||||
|
||||
#define BUFFER_SIZE (1024*1024*5) //5 MB
|
||||
|
||||
typedef struct {
|
||||
char name[LIB_FILENAME_LEN]; //just the filename part
|
||||
int offset; //offset into library file
|
||||
int length; //length of this file
|
||||
long timestamp; //time and date of file
|
||||
int flags; //misc flags
|
||||
} library_entry;
|
||||
|
||||
typedef struct {
|
||||
int nfiles;
|
||||
library_entry *table;
|
||||
FILE *fp;
|
||||
} library;
|
||||
|
||||
library *open_hogfile(char *hogname)
|
||||
{
|
||||
FILE *fp;
|
||||
int id;
|
||||
int i,offset,t;
|
||||
library *hogfile;
|
||||
index_entry *index;
|
||||
|
||||
fp = fopen( hogname, "rb" );
|
||||
if ( fp == NULL )
|
||||
return NULL;
|
||||
|
||||
fread( &id, 4, 1, fp );
|
||||
if ( strncmp( (char *) &id, LIBRARY_TAG, strlen(LIBRARY_TAG) ) ) {
|
||||
printf("Invalid library file <%s>\n",hogname);
|
||||
exit(11);
|
||||
}
|
||||
|
||||
hogfile = malloc(sizeof(*hogfile));
|
||||
|
||||
hogfile->fp = fp;
|
||||
|
||||
fread(&hogfile->nfiles,4,1,hogfile->fp); //get number of files
|
||||
|
||||
hogfile->table = malloc(sizeof(library_entry)*hogfile->nfiles);
|
||||
|
||||
offset = 4+4+hogfile->nfiles*(13+4); //id + nfiles + nfiles * (filename + size)
|
||||
|
||||
//allocate index
|
||||
index = malloc(sizeof(index_entry) * hogfile->nfiles);
|
||||
|
||||
//read in index table
|
||||
t = fread( index, sizeof(*index), hogfile->nfiles, hogfile->fp );
|
||||
if ( t != hogfile->nfiles ) { //eof here is ok
|
||||
fclose(fp);
|
||||
return 0; //CF_BAD_LIB;
|
||||
}
|
||||
|
||||
//copy disk index to our internal structure
|
||||
for (i=0;i<hogfile->nfiles;i++) {
|
||||
|
||||
strcpy(hogfile->table[i].name, index[i].name);
|
||||
hogfile->table[i].length = index[i].len;
|
||||
hogfile->table[i].offset = offset;
|
||||
offset += hogfile->table[i].length;
|
||||
|
||||
#if LIB_HAS_DATE
|
||||
hogfile->table[i].timestamp = index[i].timestamp;
|
||||
#else
|
||||
hogfile->table[i].timestamp = 0;
|
||||
#endif
|
||||
|
||||
#if LIB_HAS_FLAGS
|
||||
hogfile->table[i].flags = index[i].flags;
|
||||
#else
|
||||
hogfile->table[i].flags = 0;
|
||||
#endif
|
||||
}
|
||||
|
||||
return hogfile;
|
||||
}
|
||||
|
||||
void close_hogfile(library *hogfile)
|
||||
{
|
||||
fclose(hogfile->fp);
|
||||
free(hogfile->table);
|
||||
free(hogfile);
|
||||
}
|
||||
|
||||
copy_file(FILE *ofp,FILE *ifp,int length)
|
||||
{
|
||||
char *buffer;
|
||||
|
||||
buffer = malloc(BUFFER_SIZE);
|
||||
if (!buffer) {
|
||||
printf("Error allocating buffer\n");
|
||||
exit(10);
|
||||
}
|
||||
|
||||
while (length) {
|
||||
size_t n,read_len;
|
||||
|
||||
read_len = min(length,(int)BUFFER_SIZE);
|
||||
|
||||
n = fread( buffer, 1, read_len, ifp );
|
||||
if ( n != read_len ) {
|
||||
printf( "Error reading file\n");
|
||||
free(buffer);
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (fwrite( buffer, 1, read_len, ofp) != read_len ) {
|
||||
printf("Error writing file\n");
|
||||
free(buffer);
|
||||
return 0;
|
||||
}
|
||||
|
||||
length -= read_len;
|
||||
}
|
||||
|
||||
free(buffer);
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
//returns 1 if extracted ok
|
||||
int extract_file_by_index(library *hogfile,int index)
|
||||
{
|
||||
int length;
|
||||
FILE *ofp;
|
||||
|
||||
ofp = fopen( hogfile->table[index].name, "wb" );
|
||||
if ( ofp == NULL ) {
|
||||
printf( "Error opening '%s'\n", hogfile->table[index].name );
|
||||
return 0;
|
||||
}
|
||||
|
||||
length = hogfile->table[index].length;
|
||||
|
||||
fseek(hogfile->fp,hogfile->table[index].offset,SEEK_SET);
|
||||
|
||||
copy_file(ofp,hogfile->fp,hogfile->table[index].length);
|
||||
|
||||
fclose(ofp);
|
||||
|
||||
#ifdef LIB_HAS_DATE
|
||||
{
|
||||
struct _utimbuf mytimbuf;
|
||||
ofp = fopen(hogfile->table[index].name, "r+b");
|
||||
mytimbuf.actime = mytimbuf.modtime = hogfile->table[index].timestamp;
|
||||
_futime(fileno(ofp),&mytimbuf);
|
||||
fclose(ofp);
|
||||
}
|
||||
#endif
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
void extract_file_by_name(char *hogname,char *filename)
|
||||
{
|
||||
library *hogfile;
|
||||
int i;
|
||||
|
||||
hogfile = open_hogfile(hogname);
|
||||
|
||||
if (!hogfile) {
|
||||
printf("Error opening library <%s>\n",hogname);
|
||||
exit(7);
|
||||
}
|
||||
|
||||
for (i=0;i<hogfile->nfiles;i++)
|
||||
if (!stricmp(filename,hogfile->table[i].name)) {
|
||||
int ok;
|
||||
printf(" Extracting %s\n",hogfile->table[i].name);
|
||||
ok = extract_file_by_index(hogfile,i);
|
||||
if (!ok) {
|
||||
printf("Error extracting <%s> from <%s>\n",hogfile->table[i].name,hogname);
|
||||
exit(1);
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
if (i==hogfile->nfiles)
|
||||
printf("Error: couldn't find file <%s> in <%s>\n",filename,hogname);
|
||||
|
||||
close_hogfile(hogfile);
|
||||
}
|
||||
|
||||
void extract_all_files(char *hogname)
|
||||
{
|
||||
library *hogfile;
|
||||
int i;
|
||||
|
||||
hogfile = open_hogfile(hogname);
|
||||
|
||||
if (!hogfile) {
|
||||
printf("Error opening library <%s>\n",hogname);
|
||||
exit(7);
|
||||
}
|
||||
|
||||
for (i=0;i<hogfile->nfiles;i++) {
|
||||
int ok;
|
||||
|
||||
printf(" Extracting %s\n",hogfile->table[i].name);
|
||||
ok = extract_file_by_index(hogfile,i);
|
||||
|
||||
if (!ok) {
|
||||
printf("Error extracting <%s> from <%s>\n",hogfile->table[i].name,hogname);
|
||||
exit(1);
|
||||
}
|
||||
}
|
||||
|
||||
close_hogfile(hogfile);
|
||||
}
|
||||
|
||||
#define YEAR(t) (((t & 0xFE000000) >> 25) + 80)
|
||||
#define MONTH(t) ((t & 0x01E00000) >> 21)
|
||||
#define DAY(t) ((t & 0x001F0000) >> 16)
|
||||
#define HOUR(t) ((t & 0x0000F800) >> 11)
|
||||
#define MINUTE(t) ((t & 0x000007E0) >> 5)
|
||||
#define SECOND(t) ((t & 0x0000001F) << 1)
|
||||
|
||||
void list_files(char *hogname)
|
||||
{
|
||||
library *hogfile;
|
||||
int i;
|
||||
|
||||
hogfile = open_hogfile(hogname);
|
||||
|
||||
if (!hogfile) {
|
||||
printf("Error opening library <%s>\n",hogname);
|
||||
exit(7);
|
||||
}
|
||||
|
||||
printf("Contents of %s:\n",hogname);
|
||||
|
||||
printf(" Name Size Date/Time Flags\n");
|
||||
printf(" -------------- ----- ------------------------ -------\n");
|
||||
|
||||
for (i=0;i<hogfile->nfiles;i++) {
|
||||
printf(" %-12s %7d",hogfile->table[i].name,hogfile->table[i].length);
|
||||
|
||||
if (hogfile->table[i].timestamp) {
|
||||
long t = hogfile->table[i].timestamp;
|
||||
char *timestring;
|
||||
//printf(" %2d/%02d/%02d %2d:%02d:%02d",MONTH(t),DAY(t),YEAR(t),HOUR(t),MINUTE(t),SECOND(t));
|
||||
timestring = ctime(&t);
|
||||
timestring[24] = 0; //kill newline
|
||||
printf(" %s",timestring);
|
||||
}
|
||||
else
|
||||
printf(" ");
|
||||
|
||||
printf(" %8x\n",hogfile->table[i].flags);
|
||||
}
|
||||
|
||||
close_hogfile(hogfile);
|
||||
}
|
||||
|
||||
#define REMOVE_EOL(s) remove_char((s),'\n')
|
||||
#define REMOVE_COMMENTS(s) remove_char((s),';')
|
||||
#define REMOVE_DOTS(s) remove_char((s),'.')
|
||||
|
||||
void remove_char( char * s, char c )
|
||||
{
|
||||
char *p;
|
||||
p = strchr(s,c);
|
||||
if (p) *p = '\0';
|
||||
}
|
||||
|
||||
#define MAX_LINE_LEN 160
|
||||
|
||||
int parse_listfile(char *listfile_name,char ***filenames_ptr)
|
||||
{
|
||||
FILE *fp;
|
||||
char inputline[MAX_LINE_LEN+1];
|
||||
int count;
|
||||
char **filenames;
|
||||
|
||||
fp = fopen( listfile_name, "rt" );
|
||||
|
||||
if (!fp) {
|
||||
printf("Error: can't open file list <%s>\n",listfile_name);
|
||||
exit(3);
|
||||
}
|
||||
|
||||
count = 0;
|
||||
|
||||
while (fgets(inputline, MAX_LINE_LEN, fp )) {
|
||||
char filename[MAX_LINE_LEN+1];
|
||||
REMOVE_EOL(inputline);
|
||||
REMOVE_COMMENTS(inputline);
|
||||
if (strlen(inputline) > 0) {
|
||||
sscanf( inputline, " %s ", filename );
|
||||
if ( strlen( filename ) > 0 )
|
||||
count++;
|
||||
}
|
||||
}
|
||||
|
||||
fseek(fp,0,SEEK_SET);
|
||||
|
||||
filenames = malloc(sizeof(*filenames) * count);
|
||||
|
||||
count = 0;
|
||||
|
||||
while (fgets(inputline, MAX_LINE_LEN, fp )) {
|
||||
char filename[MAX_LINE_LEN+1];
|
||||
REMOVE_EOL(inputline);
|
||||
REMOVE_COMMENTS(inputline);
|
||||
if (strlen(inputline) > 0) {
|
||||
sscanf( inputline, " %s ", filename );
|
||||
if ( strlen( filename ) > 0 ) {
|
||||
filenames[count] = malloc(strlen(filename)+1);
|
||||
strcpy(filenames[count],filename);
|
||||
count++;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fclose(fp);
|
||||
|
||||
*filenames_ptr = filenames;
|
||||
|
||||
return count;
|
||||
}
|
||||
|
||||
void create_new_library(char *hogname, int nfiles, char **filenames)
|
||||
{
|
||||
int i,table_pos;
|
||||
FILE *hog_fp;
|
||||
index_entry *index;
|
||||
char ext[_MAX_EXT];
|
||||
|
||||
index = malloc(sizeof(index_entry) * nfiles);
|
||||
if (!index) {
|
||||
printf("Error allocating index table\n");
|
||||
exit(9);
|
||||
}
|
||||
|
||||
//open the new file
|
||||
hog_fp = fopen( hogname, "wb" );
|
||||
if ( hog_fp == NULL ) {
|
||||
printf( "Error opening file <%s>\n",hogname);
|
||||
exit(1);
|
||||
}
|
||||
|
||||
//write the tag
|
||||
if (fwrite( LIBRARY_TAG, strlen(LIBRARY_TAG), 1, hog_fp )!=1) {
|
||||
printf("Error writing tag tp file <%s>\n",hogname);
|
||||
fclose( hog_fp );
|
||||
exit(1);
|
||||
}
|
||||
|
||||
//write number of files
|
||||
if (fwrite(&nfiles,sizeof(int),1,hog_fp)!=1) {
|
||||
printf("Error writing count to file <%s>\n",hogname);
|
||||
fclose( hog_fp );
|
||||
exit(1);
|
||||
}
|
||||
|
||||
//save file position of index table
|
||||
table_pos = ftell(hog_fp);
|
||||
|
||||
//write dummy index
|
||||
if ((int) fwrite(index,sizeof(*index),nfiles,hog_fp) != nfiles) {
|
||||
printf("Error writing index to file <%s>\n",hogname);
|
||||
fclose( hog_fp );
|
||||
exit(1);
|
||||
}
|
||||
|
||||
//write files (& build index)
|
||||
for (i=0;i<nfiles;i++) {
|
||||
FILE *ifp;
|
||||
|
||||
ifp = fopen(filenames[i],"rb");
|
||||
if ( ifp == NULL ) {
|
||||
printf( "Error opening input file <%s>\n",filenames[i]);
|
||||
fclose(hog_fp);
|
||||
exit(10);
|
||||
}
|
||||
|
||||
_splitpath(filenames[i],NULL,NULL,index[i].name,ext);
|
||||
strcat(index[i].name,ext);
|
||||
index[i].len = filelength(fileno(ifp));
|
||||
|
||||
#ifdef LIB_HAS_DATE
|
||||
{
|
||||
struct _stat mystat;
|
||||
_fstat(fileno(ifp), &mystat);
|
||||
index[i].timestamp = mystat.st_mtime;
|
||||
}
|
||||
#endif
|
||||
|
||||
#ifdef LIB_HAS_FLAGS
|
||||
index[i].flags = 0;
|
||||
#endif
|
||||
|
||||
copy_file(hog_fp,ifp,index[i].len);
|
||||
}
|
||||
|
||||
//now write the real index
|
||||
fseek(hog_fp,table_pos,SEEK_SET);
|
||||
if ((int) fwrite(index,sizeof(*index),nfiles,hog_fp) != nfiles) {
|
||||
printf("Error writing index to file <%s>\n",hogname);
|
||||
fclose( hog_fp );
|
||||
exit(1);
|
||||
}
|
||||
|
||||
fclose( hog_fp );
|
||||
}
|
||||
|
||||
void add_files(char *hogname, int argc, char *argv[])
|
||||
{
|
||||
library *hogfile;
|
||||
int nfiles,i;
|
||||
char **filenames;
|
||||
|
||||
hogfile = open_hogfile(hogname);
|
||||
|
||||
if (hogfile) {
|
||||
printf("Sorry, cannot add files to existing library <%s>\n",hogname);
|
||||
exit(4);
|
||||
}
|
||||
|
||||
//hog doesn't exist, so create new one
|
||||
|
||||
if (argc != 1) {
|
||||
printf("Error: input for add files must be a listfile\n");
|
||||
exit(2);
|
||||
}
|
||||
|
||||
nfiles = parse_listfile(argv[0],&filenames);
|
||||
|
||||
create_new_library(hogname,nfiles,filenames);
|
||||
|
||||
//now free filename list
|
||||
for (i=0;i<nfiles;i++)
|
||||
free(filenames[i]);
|
||||
free(filenames);
|
||||
}
|
||||
|
||||
|
||||
void show_help()
|
||||
{
|
||||
printf( "Usage: mvlutil command hogfile [file1 [file2] [...]]\n" );
|
||||
printf( "Valid commands:\n");
|
||||
printf( " a add files\n");
|
||||
printf( " l list files\n");
|
||||
printf( " x extract files\n");
|
||||
}
|
||||
|
||||
int main(int argc, char * argv[] )
|
||||
{
|
||||
char command;
|
||||
char *hogname;
|
||||
|
||||
if ( argc < 3 ) {
|
||||
show_help();
|
||||
exit(1);
|
||||
}
|
||||
|
||||
hogname = argv[2];
|
||||
command = tolower(argv[1][0]);
|
||||
|
||||
if (command == 'a') {
|
||||
add_files(hogname,argc-3,argv+3);
|
||||
}
|
||||
else if (command == 'l') {
|
||||
list_files(hogname);
|
||||
}
|
||||
else if (command == 'x') {
|
||||
if (argv[1][1])
|
||||
extract_file_by_name(hogname,&argv[1][1]);
|
||||
else
|
||||
extract_all_files(hogname);
|
||||
}
|
||||
else {
|
||||
show_help();
|
||||
exit(2);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
481
hogmaker/hogmaker.cpp
Normal file
481
hogmaker/hogmaker.cpp
Normal file
@ -0,0 +1,481 @@
|
||||
#include <dos.h>
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <io.h>
|
||||
#include <ctype.h>
|
||||
|
||||
//#include "mvlfile.h" //for old D2 movie libraries
|
||||
#include "hogfile.h" //new D3 hogs
|
||||
|
||||
/*
|
||||
#define BUFFER_SIZE (1024*1024*5) //5 MB
|
||||
|
||||
typedef struct {
|
||||
char name[LIB_FILENAME_LEN]; //just the filename part
|
||||
int offset; //offset into library file
|
||||
int length; //length of this file
|
||||
long timestamp; //time and date of file
|
||||
int flags; //misc flags
|
||||
} library_entry;
|
||||
|
||||
typedef struct {
|
||||
int nfiles;
|
||||
library_entry *table;
|
||||
FILE *fp;
|
||||
} library;
|
||||
|
||||
library *open_hogfile(char *hogname)
|
||||
{
|
||||
FILE *fp;
|
||||
int id;
|
||||
int i,offset,t;
|
||||
library *hogfile;
|
||||
index_entry *index;
|
||||
|
||||
fp = fopen( hogname, "rb" );
|
||||
if ( fp == NULL )
|
||||
return NULL;
|
||||
|
||||
fread( &id, 4, 1, fp );
|
||||
if ( strncmp( (char *) &id, LIBRARY_TAG, strlen(LIBRARY_TAG) ) ) {
|
||||
printf("Invalid library file <%s>\n",hogname);
|
||||
exit(11);
|
||||
}
|
||||
|
||||
hogfile = malloc(sizeof(*hogfile));
|
||||
|
||||
hogfile->fp = fp;
|
||||
|
||||
fread(&hogfile->nfiles,4,1,hogfile->fp); //get number of files
|
||||
|
||||
hogfile->table = malloc(sizeof(library_entry)*hogfile->nfiles);
|
||||
|
||||
offset = 4+4+hogfile->nfiles*(13+4); //id + nfiles + nfiles * (filename + size)
|
||||
|
||||
//allocate index
|
||||
index = malloc(sizeof(index_entry) * hogfile->nfiles);
|
||||
|
||||
//read in index table
|
||||
t = fread( index, sizeof(*index), hogfile->nfiles, hogfile->fp );
|
||||
if ( t != hogfile->nfiles ) { //eof here is ok
|
||||
fclose(fp);
|
||||
return 0; //CF_BAD_LIB;
|
||||
}
|
||||
|
||||
//copy disk index to our internal structure
|
||||
for (i=0;i<hogfile->nfiles;i++) {
|
||||
|
||||
strcpy(hogfile->table[i].name, index[i].name);
|
||||
hogfile->table[i].length = index[i].len;
|
||||
hogfile->table[i].offset = offset;
|
||||
offset += hogfile->table[i].length;
|
||||
|
||||
#if LIB_HAS_DATE
|
||||
hogfile->table[i].timestamp = index[i].timestamp;
|
||||
#else
|
||||
hogfile->table[i].timestamp = 0;
|
||||
#endif
|
||||
|
||||
#if LIB_HAS_FLAGS
|
||||
hogfile->table[i].flags = index[i].flags;
|
||||
#else
|
||||
hogfile->table[i].flags = 0;
|
||||
#endif
|
||||
}
|
||||
|
||||
return hogfile;
|
||||
}
|
||||
|
||||
void close_hogfile(library *hogfile)
|
||||
{
|
||||
fclose(hogfile->fp);
|
||||
free(hogfile->table);
|
||||
free(hogfile);
|
||||
}
|
||||
|
||||
copy_file(FILE *ofp,FILE *ifp,int length)
|
||||
{
|
||||
char *buffer;
|
||||
|
||||
buffer = malloc(BUFFER_SIZE);
|
||||
if (!buffer) {
|
||||
printf("Error allocating buffer\n");
|
||||
exit(10);
|
||||
}
|
||||
|
||||
while (length) {
|
||||
int n,read_len;
|
||||
|
||||
read_len = min(length,BUFFER_SIZE);
|
||||
|
||||
n = fread( buffer, 1, read_len, ifp );
|
||||
if ( n != read_len ) {
|
||||
printf( "Error reading file\n");
|
||||
free(buffer);
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (fwrite( buffer, 1, read_len, ofp) != read_len ) {
|
||||
printf("Error writing file\n");
|
||||
free(buffer);
|
||||
return 0;
|
||||
}
|
||||
|
||||
length -= read_len;
|
||||
}
|
||||
|
||||
free(buffer);
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
//returns 1 if extracted ok
|
||||
int extract_file_by_index(library *hogfile,int index)
|
||||
{
|
||||
int length;
|
||||
FILE *ofp;
|
||||
|
||||
ofp = fopen( hogfile->table[index].name, "wb" );
|
||||
if ( ofp == NULL ) {
|
||||
printf( "Error opening '%s'\n", hogfile->table[index].name );
|
||||
return 0;
|
||||
}
|
||||
|
||||
length = hogfile->table[index].length;
|
||||
|
||||
fseek(hogfile->fp,hogfile->table[index].offset,SEEK_SET);
|
||||
|
||||
copy_file(ofp,hogfile->fp,hogfile->table[index].length);
|
||||
|
||||
fclose(ofp);
|
||||
|
||||
#ifdef LIB_HAS_DATE
|
||||
ofp = fopen(hogfile->table[index].name, "r+b");
|
||||
_dos_setftime(fileno(ofp),(hogfile->table[index].timestamp>>16),(hogfile->table[index].timestamp&0xFFFF));
|
||||
fclose(ofp);
|
||||
#endif
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
extract_file_by_name(char *hogname,char *filename)
|
||||
{
|
||||
library *hogfile;
|
||||
int i;
|
||||
|
||||
hogfile = open_hogfile(hogname);
|
||||
|
||||
if (!hogfile) {
|
||||
printf("Error opening library <%s>\n",hogname);
|
||||
exit(7);
|
||||
}
|
||||
|
||||
for (i=0;i<hogfile->nfiles;i++)
|
||||
if (!stricmp(filename,hogfile->table[i].name)) {
|
||||
int ok;
|
||||
printf(" Extracting %s\n",hogfile->table[i].name);
|
||||
ok = extract_file_by_index(hogfile,i);
|
||||
if (!ok) {
|
||||
printf("Error extracting <%s> from <%s>\n",hogfile->table[i].name,hogname);
|
||||
exit(1);
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
if (i==hogfile->nfiles)
|
||||
printf("Error: couldn't find file <%s> in <%s>\n",filename,hogname);
|
||||
|
||||
close_hogfile(hogfile);
|
||||
}
|
||||
|
||||
extract_all_files(char *hogname)
|
||||
{
|
||||
library *hogfile;
|
||||
int i;
|
||||
|
||||
hogfile = open_hogfile(hogname);
|
||||
|
||||
if (!hogfile) {
|
||||
printf("Error opening library <%s>\n",hogname);
|
||||
exit(7);
|
||||
}
|
||||
|
||||
for (i=0;i<hogfile->nfiles;i++) {
|
||||
int ok;
|
||||
|
||||
printf(" Extracting %s\n",hogfile->table[i].name);
|
||||
ok = extract_file_by_index(hogfile,i);
|
||||
|
||||
if (!ok) {
|
||||
printf("Error extracting <%s> from <%s>\n",hogfile->table[i].name,hogname);
|
||||
exit(1);
|
||||
}
|
||||
}
|
||||
|
||||
close_hogfile(hogfile);
|
||||
}
|
||||
|
||||
#define YEAR(t) (((t & 0xFE000000) >> 25) + 80)
|
||||
#define MONTH(t) ((t & 0x01E00000) >> 21)
|
||||
#define DAY(t) ((t & 0x001F0000) >> 16)
|
||||
#define HOUR(t) ((t & 0x0000F800) >> 11)
|
||||
#define MINUTE(t) ((t & 0x000007E0) >> 5)
|
||||
#define SECOND(t) ((t & 0x0000001F) << 1)
|
||||
|
||||
list_files(char *hogname)
|
||||
{
|
||||
library *hogfile;
|
||||
int i;
|
||||
|
||||
hogfile = open_hogfile(hogname);
|
||||
|
||||
if (!hogfile) {
|
||||
printf("Error opening library <%s>\n",hogname);
|
||||
exit(7);
|
||||
}
|
||||
|
||||
printf("Contents of %s:\n",hogname);
|
||||
|
||||
printf(" Name Size Date/Time Flags\n");
|
||||
printf(" -------------- ----- ------------------ -------\n");
|
||||
|
||||
for (i=0;i<hogfile->nfiles;i++) {
|
||||
printf(" %-12s %7d",hogfile->table[i].name,hogfile->table[i].length);
|
||||
|
||||
if (hogfile->table[i].timestamp) {
|
||||
long t = hogfile->table[i].timestamp;
|
||||
printf(" %2d/%02d/%02d %2d:%02d:%02d",MONTH(t),DAY(t),YEAR(t),HOUR(t),MINUTE(t),SECOND(t));
|
||||
}
|
||||
else
|
||||
printf(" ");
|
||||
|
||||
printf(" %8x\n",hogfile->table[i].flags);
|
||||
}
|
||||
|
||||
close_hogfile(hogfile);
|
||||
}
|
||||
|
||||
#define REMOVE_EOL(s) remove_char((s),'\n')
|
||||
#define REMOVE_COMMENTS(s) remove_char((s),';')
|
||||
#define REMOVE_DOTS(s) remove_char((s),'.')
|
||||
|
||||
void remove_char( char * s, char c )
|
||||
{
|
||||
char *p;
|
||||
p = strchr(s,c);
|
||||
if (p) *p = '\0';
|
||||
}
|
||||
|
||||
#define MAX_LINE_LEN 160
|
||||
|
||||
int parse_listfile(char *listfile_name,char ***filenames_ptr)
|
||||
{
|
||||
FILE *fp;
|
||||
char inputline[MAX_LINE_LEN+1];
|
||||
int count;
|
||||
char **filenames;
|
||||
|
||||
fp = fopen( listfile_name, "rt" );
|
||||
|
||||
if (!fp) {
|
||||
printf("Error: can't open file list <%s>\n",listfile_name);
|
||||
exit(3);
|
||||
}
|
||||
|
||||
count = 0;
|
||||
|
||||
while (fgets(inputline, MAX_LINE_LEN, fp )) {
|
||||
char filename[MAX_LINE_LEN+1];
|
||||
REMOVE_EOL(inputline);
|
||||
REMOVE_COMMENTS(inputline);
|
||||
if (strlen(inputline) > 0) {
|
||||
sscanf( inputline, " %s ", filename );
|
||||
if ( strlen( filename ) > 0 )
|
||||
count++;
|
||||
}
|
||||
}
|
||||
|
||||
fseek(fp,0,SEEK_SET);
|
||||
|
||||
filenames = malloc(sizeof(*filenames) * count);
|
||||
|
||||
count = 0;
|
||||
|
||||
while (fgets(inputline, MAX_LINE_LEN, fp )) {
|
||||
char filename[MAX_LINE_LEN+1];
|
||||
REMOVE_EOL(inputline);
|
||||
REMOVE_COMMENTS(inputline);
|
||||
if (strlen(inputline) > 0) {
|
||||
sscanf( inputline, " %s ", filename );
|
||||
if ( strlen( filename ) > 0 ) {
|
||||
filenames[count] = malloc(strlen(filename)+1);
|
||||
strcpy(filenames[count],filename);
|
||||
count++;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fclose(fp);
|
||||
|
||||
*filenames_ptr = filenames;
|
||||
|
||||
return count;
|
||||
}
|
||||
|
||||
create_new_library(char *hogname, int nfiles, char **filenames)
|
||||
{
|
||||
int i,table_pos;
|
||||
FILE *hog_fp;
|
||||
index_entry *index;
|
||||
char ext[_MAX_EXT];
|
||||
|
||||
index = malloc(sizeof(index_entry) * nfiles);
|
||||
if (!index) {
|
||||
printf("Error allocating index table\n");
|
||||
exit(9);
|
||||
}
|
||||
|
||||
//open the new file
|
||||
hog_fp = fopen( hogname, "wb" );
|
||||
if ( hog_fp == NULL ) {
|
||||
printf( "Error opening file <%s>\n",hogname);
|
||||
exit(1);
|
||||
}
|
||||
|
||||
//write the tag
|
||||
if (fwrite( LIBRARY_TAG, strlen(LIBRARY_TAG), 1, hog_fp )!=1) {
|
||||
printf("Error writing tag tp file <%s>\n",hogname);
|
||||
fclose( hog_fp );
|
||||
exit(1);
|
||||
}
|
||||
|
||||
//write number of files
|
||||
if (fwrite(&nfiles,sizeof(int),1,hog_fp)!=1) {
|
||||
printf("Error writing count to file <%s>\n",hogname);
|
||||
fclose( hog_fp );
|
||||
exit(1);
|
||||
}
|
||||
|
||||
//save file position of index table
|
||||
table_pos = ftell(hog_fp);
|
||||
|
||||
//write dummy index
|
||||
if (fwrite(index,sizeof(*index),nfiles,hog_fp)!=nfiles) {
|
||||
printf("Error writing index to file <%s>\n",hogname);
|
||||
fclose( hog_fp );
|
||||
exit(1);
|
||||
}
|
||||
|
||||
//write files (& build index)
|
||||
for (i=0;i<nfiles;i++) {
|
||||
FILE *ifp;
|
||||
unsigned short date,time;
|
||||
|
||||
ifp = fopen(filenames[i],"rb");
|
||||
if ( ifp == NULL ) {
|
||||
printf( "Error opening input file <%s>\n",filenames[i]);
|
||||
fclose(hog_fp);
|
||||
exit(10);
|
||||
}
|
||||
|
||||
_splitpath(filenames[i],NULL,NULL,index[i].name,ext);
|
||||
strcat(index[i].name,ext);
|
||||
index[i].len = filelength(fileno(ifp));
|
||||
|
||||
#ifdef LIB_HAS_DATE
|
||||
_dos_getftime(fileno(ifp), &date,&time);
|
||||
index[i].timestamp = (date << 16) + time;
|
||||
#endif
|
||||
|
||||
#ifdef LIB_HAS_FLAGS
|
||||
index[i].flags = 0;
|
||||
#endif
|
||||
|
||||
copy_file(hog_fp,ifp,index[i].len);
|
||||
}
|
||||
|
||||
//now write the real index
|
||||
fseek(hog_fp,table_pos,SEEK_SET);
|
||||
if (fwrite(index,sizeof(*index),nfiles,hog_fp)!=nfiles) {
|
||||
printf("Error writing index to file <%s>\n",hogname);
|
||||
fclose( hog_fp );
|
||||
exit(1);
|
||||
}
|
||||
|
||||
fclose( hog_fp );
|
||||
}
|
||||
|
||||
add_files(char *hogname, int argc, char *argv[])
|
||||
{
|
||||
library *hogfile;
|
||||
int nfiles,i;
|
||||
char **filenames;
|
||||
|
||||
hogfile = open_hogfile(hogname);
|
||||
|
||||
if (hogfile) {
|
||||
printf("Sorry, cannot add files to existing library <%s>\n",hogname);
|
||||
exit(4);
|
||||
}
|
||||
|
||||
//hog doesn't exist, so create new one
|
||||
|
||||
if (argc != 1) {
|
||||
printf("Error: input for add files must be a listfile\n");
|
||||
exit(2);
|
||||
}
|
||||
|
||||
nfiles = parse_listfile(argv[0],&filenames);
|
||||
|
||||
create_new_library(hogname,nfiles,filenames);
|
||||
|
||||
//now free filename list
|
||||
for (i=0;i<nfiles;i++)
|
||||
free(filenames[i]);
|
||||
free(filenames);
|
||||
}
|
||||
|
||||
|
||||
show_help()
|
||||
{
|
||||
printf( "Usage: mvlutil command hogfile [file1 [file2] [...]]\n" );
|
||||
printf( "Valid commands:\n");
|
||||
printf( " a add files\n");
|
||||
printf( " l list files\n");
|
||||
printf( " x extract files\n");
|
||||
}
|
||||
*/
|
||||
int main(int argc, char * argv[] )
|
||||
{
|
||||
/* char command;
|
||||
char *hogname;
|
||||
|
||||
if ( argc < 3 ) {
|
||||
show_help();
|
||||
exit(1);
|
||||
}
|
||||
|
||||
hogname = argv[2];
|
||||
command = tolower(argv[1][0]);
|
||||
|
||||
if (command == 'a') {
|
||||
add_files(hogname,argc-3,argv+3);
|
||||
}
|
||||
else if (command == 'l') {
|
||||
list_files(hogname);
|
||||
}
|
||||
else if (command == 'x') {
|
||||
if (argv[1][1])
|
||||
extract_file_by_name(hogname,&argv[1][1]);
|
||||
else
|
||||
extract_all_files(hogname);
|
||||
}
|
||||
else {
|
||||
show_help();
|
||||
exit(2);
|
||||
}
|
||||
*/
|
||||
return 0;
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user