mirror of
https://github.com/leozide/leocad
synced 2024-12-30 22:23:45 +01:00
695 lines
16 KiB
C++
695 lines
16 KiB
C++
#include "lc_global.h"
|
|
#include "leocad.h"
|
|
#include "LibDlg.h"
|
|
#include "GroupDlg.h"
|
|
#include "Print.h"
|
|
#include "Tools.h"
|
|
#include "texdlg.h"
|
|
#include "ProgDlg.h"
|
|
#include "project.h"
|
|
#include "pieceinf.h"
|
|
#include "globals.h"
|
|
#include "system.h"
|
|
#include "library.h"
|
|
#include "lc_application.h"
|
|
|
|
#ifdef _DEBUG
|
|
#define new DEBUG_NEW
|
|
#undef THIS_FILE
|
|
static char THIS_FILE[] = __FILE__;
|
|
#endif
|
|
|
|
// Function to sort the list control.
|
|
static int CALLBACK ListCompare(LPARAM lP1, LPARAM lP2, LPARAM lParamSort)
|
|
{
|
|
int ret;
|
|
|
|
if ((lP1 < 0) || (lP2 < 0))
|
|
return 0;
|
|
|
|
if ((lParamSort & ~0xF0) == 0)
|
|
ret = strcmpi(((PieceInfo*)lP1)->m_strDescription, ((PieceInfo*)lP2)->m_strDescription);
|
|
else
|
|
ret = strcmpi(((PieceInfo*)lP1)->m_strName, ((PieceInfo*)lP2)->m_strName);
|
|
|
|
return ret;
|
|
}
|
|
|
|
/////////////////////////////////////////////////////////////////////////////
|
|
// CLibraryDlg dialog
|
|
|
|
CLibraryDlg::CLibraryDlg(CWnd* pParent /*=NULL*/)
|
|
: CDialog(CLibraryDlg::IDD, pParent)
|
|
{
|
|
m_SortColumn = 0;
|
|
|
|
//{{AFX_DATA_INIT(CLibraryDlg)
|
|
// NOTE: the ClassWizard will add member initialization here
|
|
//}}AFX_DATA_INIT
|
|
}
|
|
|
|
CLibraryDlg::~CLibraryDlg()
|
|
{
|
|
}
|
|
|
|
void CLibraryDlg::DoDataExchange(CDataExchange* pDX)
|
|
{
|
|
CDialog::DoDataExchange(pDX);
|
|
//{{AFX_DATA_MAP(CLibraryDlg)
|
|
DDX_Control(pDX, IDC_LIBDLG_TREE, m_Tree);
|
|
DDX_Control(pDX, IDC_LIBDLG_LIST, m_List);
|
|
//}}AFX_DATA_MAP
|
|
}
|
|
|
|
|
|
BEGIN_MESSAGE_MAP(CLibraryDlg, CDialog)
|
|
//{{AFX_MSG_MAP(CLibraryDlg)
|
|
ON_NOTIFY(TVN_SELCHANGED, IDC_LIBDLG_TREE, OnSelChangedTree)
|
|
ON_NOTIFY(LVN_COLUMNCLICK, IDC_LIBDLG_LIST, OnListColumnClick)
|
|
//}}AFX_MSG_MAP
|
|
ON_NOTIFY_EX_RANGE(TTN_NEEDTEXTW, 0, 0xFFFF, OnToolTipText)
|
|
ON_NOTIFY_EX_RANGE(TTN_NEEDTEXTA, 0, 0xFFFF, OnToolTipText)
|
|
END_MESSAGE_MAP()
|
|
|
|
/////////////////////////////////////////////////////////////////////////////
|
|
// CLibraryDlg message handlers
|
|
|
|
BOOL CLibraryDlg::OnInitDialog()
|
|
{
|
|
CDialog::OnInitDialog();
|
|
|
|
// Add the ToolBar.
|
|
if (!m_wndToolBar.Create(this) || !m_wndToolBar.LoadToolBar(IDR_LIBRARY))
|
|
{
|
|
TRACE0("Failed to create toolbar\n");
|
|
return -1; // fail to create
|
|
}
|
|
|
|
m_wndToolBar.SetBarStyle(m_wndToolBar.GetBarStyle() | CBRS_TOOLTIPS | CBRS_FLYBY);
|
|
|
|
// We need to resize the dialog to make room for control bars.
|
|
// First, figure out how big the control bars are.
|
|
CRect rcClientStart;
|
|
CRect rcClientNow;
|
|
GetClientRect(rcClientStart);
|
|
RepositionBars(AFX_IDW_CONTROLBAR_FIRST, AFX_IDW_CONTROLBAR_LAST, 0, reposQuery, rcClientNow);
|
|
|
|
// Now move all the controls so they are in the same relative
|
|
// position within the remaining client area as they would be
|
|
// with no control bars.
|
|
CPoint ptOffset(rcClientNow.left - rcClientStart.left, rcClientNow.top - rcClientStart.top);
|
|
|
|
CRect rcChild;
|
|
CWnd* pwndChild = GetWindow(GW_CHILD);
|
|
while (pwndChild)
|
|
{
|
|
pwndChild->GetWindowRect(rcChild);
|
|
ScreenToClient(rcChild);
|
|
rcChild.OffsetRect(ptOffset);
|
|
pwndChild->MoveWindow(rcChild, FALSE);
|
|
pwndChild = pwndChild->GetNextWindow();
|
|
}
|
|
|
|
// Adjust the dialog window dimensions
|
|
CRect rcWindow;
|
|
GetWindowRect(rcWindow);
|
|
rcWindow.right += rcClientStart.Width() - rcClientNow.Width();
|
|
rcWindow.bottom += rcClientStart.Height() - rcClientNow.Height();
|
|
MoveWindow(rcWindow, FALSE);
|
|
|
|
// And position the control bars
|
|
RepositionBars(AFX_IDW_CONTROLBAR_FIRST, AFX_IDW_CONTROLBAR_LAST, 0);
|
|
|
|
m_TreeImages.Create(IDB_PARTICONS, 16, 0, RGB (0,128,128));
|
|
m_Tree.SetImageList(&m_TreeImages, TVSIL_NORMAL);
|
|
|
|
RECT rect;
|
|
m_List.GetWindowRect(&rect);
|
|
m_List.InsertColumn(0, "Name", LVCFMT_LEFT, rect.right - rect.left - GetSystemMetrics(SM_CXVSCROLL) - 4 - 60, 0);
|
|
m_List.InsertColumn(1, "Number", LVCFMT_LEFT, 60, 1);
|
|
|
|
UpdateList();
|
|
UpdateTree();
|
|
|
|
return TRUE;
|
|
}
|
|
|
|
bool CLibraryDlg::ImportPieces(const ObjArray<String>& FileList)
|
|
{
|
|
char file1[LC_MAXPATH], file2[LC_MAXPATH];
|
|
PiecesLibrary* Library = lcGetPiecesLibrary();
|
|
lcDiskFile DiskIdx, DiskBin;
|
|
|
|
strcpy(file1, Library->GetLibraryPath());
|
|
strcat(file1, "pieces.idx");
|
|
strcpy(file2, Library->GetLibraryPath());
|
|
strcat(file2, "pieces.bin");
|
|
|
|
if ((!DiskIdx.Open(file1, "rb")) || (!DiskBin.Open(file2, "rb")))
|
|
return false;
|
|
|
|
lcMemFile IdxFile1, IdxFile2, BinFile1, BinFile2;
|
|
|
|
IdxFile1.CopyFrom(DiskIdx);
|
|
DiskIdx.Close();
|
|
BinFile1.CopyFrom(DiskBin);
|
|
DiskBin.Close();
|
|
|
|
lcMemFile* NewIdx = &IdxFile1;
|
|
lcMemFile* NewBin = &BinFile1;
|
|
lcMemFile* OldIdx = &IdxFile2;
|
|
lcMemFile* OldBin = &BinFile2;
|
|
|
|
CProgressDlg Dlg("Importing pieces");
|
|
Dlg.Create(this);
|
|
Dlg.SetRange(0, FileList.GetSize());
|
|
|
|
for (int i = 0; i < FileList.GetSize(); i++)
|
|
{
|
|
char* Name = FileList[i];
|
|
char* Slash = strrchr(Name, '\\');
|
|
if (Slash > Name)
|
|
Name = Slash+1;
|
|
|
|
Slash = strrchr(Name, '/');
|
|
if (Slash > Name)
|
|
Name = Slash+1;
|
|
|
|
Dlg.SetStatus(Name);
|
|
Dlg.StepIt();
|
|
|
|
lcMemFile* TmpFile;
|
|
|
|
TmpFile = NewBin;
|
|
NewBin = OldBin;
|
|
OldBin = TmpFile;
|
|
NewBin->SetLength(0);
|
|
|
|
TmpFile = NewIdx;
|
|
NewIdx = OldIdx;
|
|
OldIdx = TmpFile;
|
|
NewIdx->SetLength(0);
|
|
|
|
lcGetPiecesLibrary()->ImportLDrawPiece(FileList[i], NewIdx, NewBin, OldIdx, OldBin);
|
|
|
|
if (Dlg.CheckCancelButton())
|
|
if (AfxMessageBox(IDS_CANCEL_PROMPT, MB_YESNO) == IDYES)
|
|
break;
|
|
}
|
|
|
|
if ((!DiskIdx.Open(file1, "wb")) || (!DiskBin.Open(file2, "wb")))
|
|
{
|
|
AfxMessageBox("Failed to open file for writing.", MB_ICONERROR | MB_OK);
|
|
return false;
|
|
}
|
|
|
|
strcpy(file1, Library->GetLibraryPath());
|
|
strcat(file1, "pieces-b.old");
|
|
remove(file1);
|
|
strcpy(file2, Library->GetLibraryPath());
|
|
strcat(file2, "pieces.bin");
|
|
rename(file2, file1);
|
|
|
|
strcpy(file1, Library->GetLibraryPath());
|
|
strcat(file1, "pieces-i.old");
|
|
remove(file1);
|
|
strcpy(file2, Library->GetLibraryPath());
|
|
strcat(file2, "pieces.idx");
|
|
rename(file2, file1);
|
|
|
|
DiskBin.CopyFrom(*NewBin);
|
|
DiskIdx.CopyFrom(*NewIdx);
|
|
|
|
UpdateList();
|
|
|
|
return true;
|
|
}
|
|
|
|
BOOL CLibraryDlg::OnCommand(WPARAM wParam, LPARAM lParam)
|
|
{
|
|
switch (LOWORD(wParam))
|
|
{
|
|
case ID_LIBDLG_FILE_OPEN:
|
|
{
|
|
lcGetPiecesLibrary()->LoadCategories(NULL);
|
|
UpdateTree();
|
|
return TRUE;
|
|
}
|
|
|
|
case ID_LIBDLG_FILE_SAVE:
|
|
{
|
|
lcGetPiecesLibrary()->DoSaveCategories(false);
|
|
return TRUE;
|
|
}
|
|
|
|
case ID_LIBDLG_FILE_SAVEAS:
|
|
{
|
|
lcGetPiecesLibrary()->DoSaveCategories(true);
|
|
return TRUE;
|
|
}
|
|
|
|
case ID_LIBDLG_FILE_PRINTCATALOG:
|
|
{
|
|
PRINT_PARAMS* param = (PRINT_PARAMS*)malloc(sizeof(PRINT_PARAMS));
|
|
param->pParent = this;
|
|
param->pMainFrame = (CFrameWndEx*)AfxGetMainWnd();
|
|
AfxBeginThread(PrintCatalogFunction, param);
|
|
|
|
return TRUE;
|
|
}
|
|
|
|
case ID_LIBDLG_FILE_MERGEUPDATE:
|
|
{
|
|
LC_FILEOPENDLG_OPTS opts;
|
|
|
|
strcpy(opts.path, "");
|
|
opts.type = LC_FILEOPENDLG_LUP;
|
|
|
|
if (SystemDoDialog(LC_DLG_FILE_OPEN, &opts))
|
|
{
|
|
lcGetPiecesLibrary()->LoadUpdate((char*)opts.filenames);
|
|
|
|
free(opts.filenames);
|
|
|
|
UpdateTree();
|
|
}
|
|
|
|
return TRUE;
|
|
}
|
|
|
|
case ID_FILE_IMPORTPIECE:
|
|
{
|
|
LC_FILEOPENDLG_OPTS opts;
|
|
|
|
strcpy(opts.path, Sys_ProfileLoadString ("Default", "LDraw Pieces Path", ""));
|
|
opts.type = LC_FILEOPENDLG_DAT;
|
|
|
|
if (SystemDoDialog (LC_DLG_FILE_OPEN, &opts))
|
|
{
|
|
ObjArray<String> FileList;
|
|
|
|
for (int i = 0; i < opts.numfiles; i++)
|
|
{
|
|
FileList.Add(opts.filenames[i]);
|
|
free (opts.filenames[i]);
|
|
}
|
|
|
|
free (opts.filenames);
|
|
|
|
ImportPieces(FileList);
|
|
|
|
Sys_ProfileSaveString ("Default", "LDraw Pieces Path", opts.path);
|
|
|
|
UpdateList();
|
|
}
|
|
|
|
return TRUE;
|
|
}
|
|
|
|
|
|
case ID_FILE_IMPORTFOLDER:
|
|
{
|
|
LC_DLG_DIRECTORY_BROWSE_OPTS Opts;
|
|
|
|
Opts.Title = "Select Folder";
|
|
strcpy(Opts.Path, Sys_ProfileLoadString ("Default", "LDraw Pieces Path", ""));
|
|
|
|
if (!SystemDoDialog(LC_DLG_DIRECTORY_BROWSE, &Opts))
|
|
return TRUE;
|
|
|
|
ObjArray<String> FileList;
|
|
|
|
WIN32_FIND_DATA FindData;
|
|
HANDLE Find = INVALID_HANDLE_VALUE;
|
|
|
|
int Len = strlen(Opts.Path);
|
|
|
|
if (Opts.Path[Len-1] != '\\' && Opts.Path[Len-1] != '/')
|
|
strcat(Opts.Path, "\\");
|
|
|
|
char Dir[MAX_PATH];
|
|
strcpy(Dir, Opts.Path);
|
|
strcat(Dir, "*.dat");
|
|
|
|
Find = FindFirstFile(Dir, &FindData);
|
|
|
|
if (Find == INVALID_HANDLE_VALUE)
|
|
{
|
|
SystemDoMessageBox("No files found.", LC_MB_OK | LC_MB_ICONERROR);
|
|
return TRUE;
|
|
}
|
|
|
|
do
|
|
{
|
|
if (FindData.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY)
|
|
continue;
|
|
|
|
char File[MAX_PATH];
|
|
strcpy(File, Opts.Path);
|
|
strcat(File, FindData.cFileName);
|
|
FileList.Add(File);
|
|
}
|
|
while (FindNextFile(Find, &FindData) != 0);
|
|
|
|
FindClose(Find);
|
|
|
|
lcGetPiecesLibrary()->DeleteAllPieces();
|
|
ImportPieces(FileList);
|
|
|
|
Sys_ProfileSaveString("Default", "LDraw Pieces Path", Opts.Path);
|
|
|
|
return TRUE;
|
|
}
|
|
|
|
case ID_LIBDLG_FILE_TEXTURES:
|
|
{
|
|
CTexturesDlg dlg;
|
|
dlg.DoModal();
|
|
} break;
|
|
|
|
case ID_LIBDLG_CATEGORY_RESET:
|
|
{
|
|
if (SystemDoMessageBox("Are you sure you want to reset the categories?", LC_MB_YESNO | LC_MB_ICONQUESTION) == LC_YES)
|
|
{
|
|
lcGetPiecesLibrary()->ResetCategories();
|
|
|
|
UpdateList();
|
|
UpdateTree();
|
|
}
|
|
|
|
return TRUE;
|
|
}
|
|
|
|
case ID_LIBDLG_CATEGORY_NEW:
|
|
{
|
|
LC_CATEGORYDLG_OPTS Opts;
|
|
Opts.Name = "New Category";
|
|
Opts.Keywords = "";
|
|
|
|
if (SystemDoDialog(LC_DLG_EDITCATEGORY, &Opts))
|
|
{
|
|
lcGetPiecesLibrary()->AddCategory(Opts.Name, Opts.Keywords);
|
|
}
|
|
|
|
UpdateTree();
|
|
|
|
return TRUE;
|
|
}
|
|
|
|
case ID_LIBDLG_CATEGORY_REMOVE:
|
|
{
|
|
HTREEITEM Item = m_Tree.GetSelectedItem();
|
|
|
|
if (Item == NULL)
|
|
break;
|
|
|
|
PiecesLibrary* Lib = lcGetPiecesLibrary();
|
|
CString CategoryName = m_Tree.GetItemText(Item);
|
|
int Index = Lib->FindCategoryIndex((const char*)CategoryName);
|
|
|
|
if (Index == -1)
|
|
break;
|
|
|
|
char Msg[1024];
|
|
String Name = Lib->GetCategoryName(Index);
|
|
sprintf(Msg, "Are you sure you want to remove the %s category?", Name);
|
|
|
|
if (SystemDoMessageBox(Msg, LC_MB_YESNO | LC_MB_ICONQUESTION) == LC_YES)
|
|
{
|
|
Lib->RemoveCategory(Index);
|
|
}
|
|
|
|
UpdateTree();
|
|
|
|
return TRUE;
|
|
}
|
|
|
|
case ID_LIBDLG_CATEGORY_EDIT:
|
|
{
|
|
HTREEITEM Item = m_Tree.GetSelectedItem();
|
|
|
|
if (Item == NULL)
|
|
break;
|
|
|
|
PiecesLibrary* Lib = lcGetPiecesLibrary();
|
|
CString CategoryName = m_Tree.GetItemText(Item);
|
|
int Index = Lib->FindCategoryIndex((const char*)CategoryName);
|
|
|
|
if (Index == -1)
|
|
break;
|
|
|
|
LC_CATEGORYDLG_OPTS Opts;
|
|
Opts.Name = Lib->GetCategoryName(Index);
|
|
Opts.Keywords = Lib->GetCategoryKeywords(Index);
|
|
|
|
if (SystemDoDialog(LC_DLG_EDITCATEGORY, &Opts))
|
|
{
|
|
String OldName = Lib->GetCategoryName(Index);
|
|
Lib->SetCategory(Index, Opts.Name, Opts.Keywords);
|
|
}
|
|
|
|
UpdateTree();
|
|
|
|
return TRUE;
|
|
}
|
|
|
|
case ID_LIBDLG_PIECE_NEW:
|
|
{
|
|
return TRUE;
|
|
}
|
|
|
|
case ID_LIBDLG_PIECE_EDIT:
|
|
{
|
|
return TRUE;
|
|
}
|
|
|
|
case ID_LIBDLG_PIECE_DELETE:
|
|
{
|
|
PtrArray<const char> Pieces;
|
|
|
|
for (int i = 0; i < m_List.GetItemCount(); i++)
|
|
{
|
|
if (m_List.GetItemState(i, LVIS_SELECTED))
|
|
{
|
|
PieceInfo* Info = (PieceInfo*)m_List.GetItemData(i);
|
|
Pieces.Add(Info->m_strName);
|
|
}
|
|
}
|
|
|
|
if (Pieces.GetSize() == 0)
|
|
return TRUE;
|
|
|
|
if (SystemDoMessageBox ("Are you sure you want to permanently delete the selected pieces?", LC_MB_YESNO|LC_MB_ICONQUESTION) != LC_YES)
|
|
return TRUE;
|
|
|
|
lcGetPiecesLibrary()->DeletePieces(Pieces);
|
|
|
|
UpdateList();
|
|
|
|
return TRUE;
|
|
}
|
|
}
|
|
|
|
return CDialog::OnCommand(wParam, lParam);
|
|
}
|
|
|
|
void CLibraryDlg::UpdateList()
|
|
{
|
|
m_List.DeleteAllItems();
|
|
m_List.SetRedraw(FALSE);
|
|
|
|
PiecesLibrary *Lib = lcGetPiecesLibrary();
|
|
|
|
HTREEITEM CategoryItem = m_Tree.GetSelectedItem();
|
|
CString CategoryName = m_Tree.GetItemText(CategoryItem);
|
|
int CategoryIndex = Lib->FindCategoryIndex((const char*)CategoryName);
|
|
|
|
if (CategoryIndex != -1)
|
|
{
|
|
PtrArray<PieceInfo> SinglePieces, GroupedPieces;
|
|
|
|
Lib->GetCategoryEntries(CategoryIndex, false, SinglePieces, GroupedPieces);
|
|
|
|
for (int i = 0; i < SinglePieces.GetSize(); i++)
|
|
{
|
|
PieceInfo* Info = SinglePieces[i];
|
|
|
|
LVITEM lvi;
|
|
lvi.mask = LVIF_TEXT | LVIF_PARAM;
|
|
lvi.iItem = 0;
|
|
lvi.iSubItem = 0;
|
|
lvi.lParam = (LPARAM)Info;
|
|
lvi.pszText = Info->m_strDescription;
|
|
int idx = m_List.InsertItem(&lvi);
|
|
|
|
m_List.SetItemText(idx, 1, Info->m_strName);
|
|
}
|
|
}
|
|
else
|
|
{
|
|
if (CategoryName == "Unassigned")
|
|
{
|
|
// Test each piece against all categories.
|
|
for (int i = 0; i < Lib->GetPieceCount(); i++)
|
|
{
|
|
PieceInfo* Info = Lib->GetPieceInfo(i);
|
|
int j;
|
|
|
|
for (j = 0; j < Lib->GetNumCategories(); j++)
|
|
{
|
|
if (Lib->PieceInCategory(Info, Lib->GetCategoryKeywords(j)))
|
|
break;
|
|
}
|
|
|
|
if (j == Lib->GetNumCategories())
|
|
{
|
|
LVITEM lvi;
|
|
lvi.mask = LVIF_TEXT | LVIF_PARAM;
|
|
lvi.iItem = 0;
|
|
lvi.iSubItem = 0;
|
|
lvi.lParam = (LPARAM)Info;
|
|
lvi.pszText = Info->m_strDescription;
|
|
int idx = m_List.InsertItem(&lvi);
|
|
|
|
m_List.SetItemText(idx, 1, Info->m_strName);
|
|
}
|
|
}
|
|
}
|
|
else if (CategoryName == "Pieces")
|
|
{
|
|
for (int i = 0; i < Lib->GetPieceCount(); i++)
|
|
{
|
|
PieceInfo* Info = Lib->GetPieceInfo(i);
|
|
|
|
LVITEM lvi;
|
|
lvi.mask = LVIF_TEXT | LVIF_PARAM;
|
|
lvi.iItem = 0;
|
|
lvi.iSubItem = 0;
|
|
lvi.lParam = (LPARAM)Info;
|
|
lvi.pszText = Info->m_strDescription;
|
|
int idx = m_List.InsertItem(&lvi);
|
|
|
|
m_List.SetItemText(idx, 1, Info->m_strName);
|
|
}
|
|
}
|
|
}
|
|
|
|
m_List.SortItems((PFNLVCOMPARE)ListCompare, m_SortColumn);
|
|
m_List.SetRedraw(TRUE);
|
|
}
|
|
|
|
void CLibraryDlg::UpdateTree()
|
|
{
|
|
m_Tree.SetRedraw(FALSE);
|
|
m_Tree.DeleteAllItems();
|
|
|
|
HTREEITEM Root = m_Tree.InsertItem(TVIF_IMAGE|TVIF_SELECTEDIMAGE|TVIF_TEXT, "Pieces", 0, 1, 0, 0, 0, TVI_ROOT, TVI_SORT);
|
|
|
|
PiecesLibrary *Lib = lcGetPiecesLibrary();
|
|
for (int i = 0; i < Lib->GetNumCategories(); i++)
|
|
m_Tree.InsertItem(TVIF_IMAGE|TVIF_SELECTEDIMAGE|TVIF_PARAM|TVIF_TEXT, Lib->GetCategoryName(i), 0, 1, 0, 0, 0, Root, TVI_SORT);
|
|
|
|
m_Tree.InsertItem(TVIF_IMAGE|TVIF_SELECTEDIMAGE|TVIF_PARAM|TVIF_TEXT, "Unassigned", 0, 1, 0, 0, 0, Root, TVI_LAST);
|
|
|
|
m_Tree.Expand(Root, TVE_EXPAND);
|
|
m_Tree.SetRedraw(TRUE);
|
|
m_Tree.Invalidate();
|
|
}
|
|
|
|
void CLibraryDlg::OnSelChangedTree(NMHDR* pNMHDR, LRESULT* pResult)
|
|
{
|
|
NM_TREEVIEW* pNMTreeView = (NM_TREEVIEW*)pNMHDR;
|
|
UpdateList();
|
|
*pResult = 0;
|
|
}
|
|
|
|
void CLibraryDlg::OnCancel()
|
|
{
|
|
// Check if it's ok to close the dialog
|
|
if (!lcGetPiecesLibrary()->SaveCategories())
|
|
return;
|
|
|
|
CDialog::OnCancel();
|
|
}
|
|
|
|
void CLibraryDlg::OnOK()
|
|
{
|
|
// Check if it's ok to close the dialog
|
|
if (!lcGetPiecesLibrary()->SaveCategories())
|
|
return;
|
|
|
|
CDialog::OnOK();
|
|
}
|
|
|
|
BOOL CLibraryDlg::ContinueModal()
|
|
{
|
|
HTREEITEM h = m_Tree.GetSelectedItem();
|
|
BOOL bValid = (h != m_Tree.GetRootItem()) && (h != NULL);
|
|
|
|
EnableControl(ID_LIBDLG_GROUP_RENAME, bValid);
|
|
EnableControl(ID_LIBDLG_GROUP_DELETE, bValid);
|
|
|
|
return CDialog::ContinueModal();
|
|
}
|
|
|
|
void CLibraryDlg::EnableControl(UINT nID, BOOL bEnable)
|
|
{
|
|
GetMenu()->GetSubMenu(1)->EnableMenuItem(nID, MF_BYCOMMAND | (bEnable ? MF_ENABLED : (MF_DISABLED | MF_GRAYED)));
|
|
int state = m_wndToolBar.GetToolBarCtrl().GetState(nID) & ~TBSTATE_ENABLED;
|
|
if (bEnable)
|
|
state |= TBSTATE_ENABLED;
|
|
m_wndToolBar.GetToolBarCtrl().SetState(nID, state);
|
|
}
|
|
|
|
BOOL CLibraryDlg::OnToolTipText(UINT, NMHDR* pNMHDR, LRESULT* pResult)
|
|
{
|
|
ASSERT(pNMHDR->code == TTN_NEEDTEXTA || pNMHDR->code == TTN_NEEDTEXTW);
|
|
|
|
// allow top level routing frame to handle the message
|
|
if (GetRoutingFrame() != NULL)
|
|
return FALSE;
|
|
|
|
// need to handle both ANSI and UNICODE versions of the message
|
|
TOOLTIPTEXTA* pTTTA = (TOOLTIPTEXTA*)pNMHDR;
|
|
TOOLTIPTEXTW* pTTTW = (TOOLTIPTEXTW*)pNMHDR;
|
|
CString cstTipText;
|
|
UINT nID = pNMHDR->idFrom;
|
|
|
|
if (pNMHDR->code == TTN_NEEDTEXTA && (pTTTA->uFlags & TTF_IDISHWND) ||
|
|
pNMHDR->code == TTN_NEEDTEXTW && (pTTTW->uFlags & TTF_IDISHWND))
|
|
{
|
|
// idFrom is actually the HWND of the tool
|
|
nID = ((UINT)(WORD)::GetDlgCtrlID((HWND)nID));
|
|
}
|
|
|
|
if (nID != 0) // will be zero on a separator
|
|
{
|
|
cstTipText.LoadString(nID);
|
|
}
|
|
|
|
// Non-UNICODE Strings only are shown in the tooltip window...
|
|
if (pNMHDR->code == TTN_NEEDTEXTA)
|
|
lstrcpyn(pTTTA->szText, cstTipText, (sizeof(pTTTA->szText)/sizeof(pTTTA->szText[0])));
|
|
else
|
|
_mbstowcsz(pTTTW->szText, cstTipText, (sizeof(pTTTW->szText)/sizeof(pTTTW->szText[0])));
|
|
|
|
*pResult = 0;
|
|
|
|
// bring the tooltip window above other popup windows
|
|
::SetWindowPos(pNMHDR->hwndFrom, HWND_TOP, 0, 0, 0, 0,
|
|
SWP_NOACTIVATE|SWP_NOSIZE|SWP_NOMOVE);
|
|
|
|
return TRUE; // message was handled
|
|
}
|
|
|
|
void CLibraryDlg::OnListColumnClick(NMHDR* pNMHDR, LRESULT* pResult)
|
|
{
|
|
NM_LISTVIEW* pNMListView = (NM_LISTVIEW*)pNMHDR;
|
|
|
|
// Save the column index.
|
|
m_SortColumn = pNMListView->iSubItem;
|
|
|
|
m_List.SortItems((PFNLVCOMPARE)ListCompare, m_SortColumn);
|
|
|
|
*pResult = 0;
|
|
}
|