📄 mcbmain.c
字号:
(LPARAM)(LPTV_INSERTSTRUCT)&insert);
free(lpszText);
break;
/*
*********************************************************************
* If we have a Clear node.
*********************************************************************
*/
case eNodeClear:
insert.item.mask = TVIF_TEXT | TVIF_IMAGE | TVIF_SELECTEDIMAGE |
TVIF_PARAM;
insert.item.iImage = McbCLEARBMP;
insert.item.iSelectedImage = McbCLEARBMP;
pClear = pChild->node.pClear;
cbName = pClear->lpszOpenTag ? _tcslen(pClear->lpszOpenTag) : 0;
cbValue = pClear->lpszValue ? _tcslen(pClear->lpszValue) : 0;
cb = pClear->lpszCloseTag ? _tcslen(pClear->lpszCloseTag) : 0;
insert.item.lParam = (LPARAM)MAKELONG((WORD)
pChild->nStringOffset, (WORD)cbName);
cbText = cbName + cbValue + cb;
assert(cbText);
lpszText = (LPTSTR)malloc((cbText+1) * sizeof(TCHAR));
lpszMarker = lpszText;
if (cbName)
{
_tcscpy(lpszMarker, pClear->lpszOpenTag);
lpszMarker += cbName;
}
if (cbValue)
{
_tcscpy(lpszMarker, pClear->lpszValue);
lpszMarker += cbValue;
}
if (cb)
{
_tcscpy(lpszMarker, pClear->lpszCloseTag);
}
insert.item.pszText = lpszText;
insert.item.cchTextMax = cbText;
McbReplaceNonPrintableChars(insert.item.pszText);
/*
*****************************************************************
* Insert node into the tree
*****************************************************************
*/
SendMessage(hWndTree, TVM_INSERTITEM, 0,
(LPARAM)(LPTV_INSERTSTRUCT)&insert);
free(lpszText);
}
}
}/* McbBuildTree */
/**
****************************************************************************
* <P> Helper function to obtain windows text in allocated memory. </P>
*
* @methodName McbGetWindowText
*
* @param hWnd
*
* @return LPTSTR
*
* @exception none
*
* @author Martyn C Brown
*
* @changeHistory
* 4th February 2002 - (V1.0) Creation (MCB)
****************************************************************************
*/
LPTSTR McbGetWindowText(HWND hWnd)
{
LPTSTR lpszResult = NULL;
LONG cbText;
/*
*************************************************************************
* Obtain text from the window
*************************************************************************
*/
cbText = SendMessage(hWnd, WM_GETTEXTLENGTH, 0, 0);
if (cbText)
{
lpszResult = (LPTSTR)malloc((cbText+1) * sizeof(TCHAR));
cbText = SendMessage(hWnd, WM_GETTEXT, (WPARAM)cbText+1,
(LPARAM)lpszResult);
if (!cbText)
{
free(lpszResult);
lpszResult = NULL;
}
}
return lpszResult;
}/* McbGetWindowText */
/**
****************************************************************************
* <P> Count characters in an edit box to find number of character offset for
* a specified line. </P>
*
* @methodName McbCountCharsUpdateLine
*
* @param hWndRich
* @param nLines
*
* @return int
*
* @exception none
*
* @author Martyn C Brown
*
* @changeHistory
* 4th February 2002 - (V1.0) Creation (MCB)
****************************************************************************
*/
int McbCountCharsUpdateLine(HWND hWndRich, int nLines)
{
int nResult = 0;
int nLine;
LPTSTR lpszText;
int cbText;
int nChar;
lpszText = McbGetWindowText(hWndRich);
if (lpszText)
{
cbText = _tcslen(lpszText);
nLine = 0;
for (nChar = 0; nLine < nLines && nChar < cbText; nChar++)
{
nResult++;
if (lpszText[nChar] == _T('\n'))
{
nLine++;
}
}
free(lpszText);
}
return nResult;
}/* McbCountCharsUpdateLine */
/**
****************************************************************************
* <P> Create formatted XML with tabs and carriage returns. </P>
*
* @methodName McbFormatXML
*
* @param lpszXML
*
* @return LPTSTR
*
* @exception none
*
* @author Martyn C Brown
*
* @changeHistory
* 5th February 2002 - (V1.0) Creation (MCB)
****************************************************************************
*/
LPTSTR McbFormatXML(LPCTSTR lpszXML)
{
LPTSTR lpszResult = NULL;
McbXMLElement * pRoot;
McbXMLResults results;
/*
*************************************************************************
* Parse the XML into the tree structure
*************************************************************************
*/
pRoot = McbParseXML(lpszXML, &results);
if (pRoot)
{
lpszResult = McbCreateXMLString(pRoot, 1, 0);
/*
*********************************************************************
* Cleanup
*********************************************************************
*/
McbDeleteRoot(pRoot);
}
return lpszResult;
}/* McbFormatXML */
/**
****************************************************************************
* <P> Does exactly what it says on the tin. </P>
*
* @methodName McbParseXMLIntoTree
*
* @param hWndStatus
* @param hWndTree
* @param lpszXML
*
* @return int
*
* @exception none
*
* @author Martyn C Brown
*
* @changeHistory
* 4th February 2002 - (V1.0) Creation (MCB)
****************************************************************************
*/
int McbParseXMLIntoTree(HWND hWndRich, HWND hWndStatus, HWND hWndTree,
LPCTSTR lpszXML)
{
int nResult = FALSE;
int nCharsOffset;
CHARRANGE range;
McbXMLNode node;
McbXMLElement * pRoot;
McbXMLResults results;
/*
*************************************************************************
* Clear the tree control.
*************************************************************************
*/
TreeView_DeleteAllItems(hWndTree);
/*
*************************************************************************
* Parse the XML into the tree structure
*************************************************************************
*/
pRoot = McbParseXML(lpszXML, &results);
if (pRoot)
{
/*
*********************************************************************
* Build the tree control
*********************************************************************
*/
node.node.pElement = pRoot;
node.type = eNodeElement;
node.nStringOffset = 0;
McbBuildTree(hWndTree, &node, NULL);
if (pRoot->nSize == 0)
{
McbSETSTATUS(hWndStatus, _T("Document contains no elements"), 0);
}
else
{
McbSETSTATUS(hWndStatus, _T("No errors"), 0);
}
/*
*********************************************************************
* Cleanup
*********************************************************************
*/
McbDeleteRoot(pRoot);
nResult = TRUE;
}
/*
*************************************************************************
* If we failed to parse the XML
*************************************************************************
*/
else
{
/*
*********************************************************************
* Update the status
*********************************************************************
*/
TCHAR szBuffer[200];
_stprintf(szBuffer, _T("Error at line: %d, Column: %d - %s"),
results.nLine, results.nColumn-1, McbGetError(results.error));
McbSETSTATUS(hWndStatus, szBuffer, 0);
/*
*********************************************************************
* Calculate the offset in the edit box, set the range to the error
* line and scroll to the position
*********************************************************************
*/
nCharsOffset = McbCountCharsUpdateLine(hWndRich, results.nLine - 1);
nCharsOffset += results.nColumn-1;
range.cpMin = nCharsOffset > 0 ? nCharsOffset - 1 : nCharsOffset;
range.cpMax = range.cpMin + 1;
SendMessage(hWndRich, EM_EXSETSEL, 0, (LPARAM)&range);
SendMessage(hWndRich, EM_SCROLLCARET, 0, 0);
SetFocus(hWndRich);
}
return nResult;
}/* McbParseXMLIntoTree */
/**
****************************************************************************
* <P> Obtain a filename from the punter and attempt to load it as XML. </P>
*
* @methodName McbGetFileNameAndLoadXML
*
* @param hWnd
* @param hWndRich
* @param hWndStatus
* @param hWndTree
* @param *pOptions
*
* @return int
*
* @exception none
*
* @author Martyn C Brown
*
* @changeHistory
* 4th February 2002 - (V1.0) Creation (MCB)
****************************************************************************
*/
int McbGetFileNameAndLoadXML(HWND hWnd, HWND hWndRich, HWND hWndStatus,
HWND hWndTree, McbOptions *pOptions)
{
int nResult = FALSE;
LPTSTR lpszXML;
TCHAR szFile[_MAX_PATH+1];
TCHAR szFileTitle[_MAX_PATH+1];
TCHAR szStartDir[_MAX_PATH+1];
TCHAR szDrive[_MAX_DRIVE+1];
TCHAR szDir[_MAX_DIR+1];
TCHAR szExt[_MAX_EXT+1];
TCHAR szFname[_MAX_FNAME+1];
OPENFILENAME openName;
openName.lStructSize = sizeof(OPENFILENAME);
openName.hwndOwner = hWnd;
openName.hInstance = g_hInst;
openName.lpstrFilter = _T("XML Files (*.xml)\0*.xml\0Text Files (*.txt)")
_T("\0*.txt\0All Files (*.*)\0*.*\0\0");
openName.lpstrCustomFilter = NULL;
openName.nMaxCustFilter = 0;
openName.nFilterIndex = pOptions->nFilterIndex;
openName.lpstrFile = szFile;
openName.nMaxFile = _MAX_PATH;
openName.lpstrFileTitle = szFileTitle;
openName.nMaxFileTitle = _MAX_PATH;
openName.lpstrInitialDir = NULL;
openName.lpstrTitle = _T("Load XML file");
openName.Flags = OFN_EXPLORER | OFN_FILEMUSTEXIST | OFN_PATHMUSTEXIST |
OFN_HIDEREADONLY;
openName.nFileOffset = 0;
openName.nFileExtension = 0;
openName.lpstrDefExt = NULL;
openName.lCustData = 0;
openName.lpfnHook = NULL;
openName.lpTemplateName = NULL;
if (*pOptions->szLastFile)
{
_tsplitpath(pOptions->szLastFile, szDrive, szDir, szFname, szExt);
_tcscpy(szStartDir, szDrive);
_tcscpy(szStartDir + _tcslen(szDrive), szDir);
openName.lpstrInitialDir = szStartDir;
_tcscpy(szFile, szFname);
_tcscpy(szFile + _tcslen(szFname), szExt);
}
else
{
szFile[0] = 0;
}
/*
*************************************************************************
* Obtain the file name and attempt to load it
*************************************************************************
*/
if (GetOpenFileName(&openName))
{
lpszXML = McbLoadFile(szFile);
if (lpszXML)
{
/*
*****************************************************************
* Update the rich text window and attempt to parse the XML and
* build the tree.
*****************************************************************
*/
SetWindowText(hWndRich, lpszXML);
McbParseXMLIntoTree(hWndRich, hWndStatus, hWndTree, lpszXML);
pOptions->nFilterIndex = openName.nFilterIndex;
_tcscpy(pOptions->szLastFile, szFile);
nResult = TRUE;
free(lpszXML);
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -