home *** CD-ROM | disk | FTP | other *** search
- /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 2 -*-
- *
- * The contents of this file are subject to the Netscape Public License
- * Version 1.0 (the "NPL"); you may not use this file except in
- * compliance with the NPL. You may obtain a copy of the NPL at
- * http://www.mozilla.org/NPL/
- *
- * Software distributed under the NPL is distributed on an "AS IS" basis,
- * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the NPL
- * for the specific language governing rights and limitations under the
- * NPL.
- *
- * The Initial Developer of this code under the NPL is Netscape
- * Communications Corporation. Portions created by Netscape are
- * Copyright (C) 1998 Netscape Communications Corporation. All Rights
- * Reserved.
- */
-
- // RDFLiner Implementation. Created by Dave Hyatt.
-
- #include "stdafx.h"
- #include "mainfrm.h"
- #include "hiddenfr.h"
- #include "rdf.h"
- #include "htrdf.h"
- #include "rdfliner.h"
- #include "shcut.h"
- #include "shcutdlg.h"
- #include "prefapi.h"
- #include "netsvw.h"
- #include "cxsave.h"
- #include "fegui.h"
- #include "nethelp.h"
- #include "time.h"
-
- CMapStringToPtr CHTFEData::m_LocalFileCache(40);
- CMapStringToPtr CHTFEData::m_CustomURLCache(20);
-
- extern "C" {
- #include "xpgetstr.h"
- extern int XP_BKMKS_LESS_THAN_ONE_HOUR_AGO;
- extern int XP_BKMKS_DAYS_AGO;
- extern int XP_BKMKS_HOURS_AGO;
- };
-
- // Some tooltip stuff
- #define TIP_WAITING 1
- #define TIP_SHOWING 2
- #define TIP_SHOWN 3
- #define TIP_HEARTBEAT 100
- #define TIP_DELAY 250
-
- // Focus/timer stuff for edit wnds
- #define IDT_EDITFOCUS 16412
- #define IDT_SPRINGLOAD 16413
- #define IDT_DRAGRECT 16414
-
- #define EDIT_DELAY 500
- #define SPRINGLOAD_DELAY 300
- #define RDF_DRAG_HEARTBEAT 125 // Faster than COutliner's DRAG_HEARTBEAT
-
- // Click location stuff
- #define CLICKED_BACKGROUND 0
- #define CLICKED_TRIGGER 1
- #define CLICKED_LINE 2
-
- // Used in painting
- #define COL_LEFT_MARGIN ((m_cxChar+1)/2)
- #define OUTLINE_TEXT_OFFSET 8
-
- #define HTFE_USE_CUSTOM_IMAGE -1
- #define HTFE_LOCAL_FILE -2
-
- #define HT_NO_SORT -1
- #define HT_SORT_ASCENDING 1
- #define HT_SORT_DESCENDING 0
-
- // Function to make a pretty date string
- #define SECONDS_PER_DAY 86400L
- void FormatDateTime( CTime &tmDate, CString &csFormatDate )
- {
- //
- // Get locale info
- //
- static char cName[] = "intl" ;
- TCHAR szSepDate[2], szSepTime[2];
- GetProfileString( cName, "sDate", "/", szSepDate, sizeof(szSepDate) );
- GetProfileString( cName, "sTime", ":", szSepTime, sizeof(szSepTime) );
-
- TCHAR szAM[9], szPM[9];
- GetProfileString( cName, "s1159", "AM", szAM, sizeof(szAM) );
- GetProfileString( cName, "s2359", "PM", szPM, sizeof(szPM) );
-
- int iDate = GetProfileInt( cName, "iDate", 0 );
- int iTime = GetProfileInt( cName, "iTime", 0 );
-
- TCHAR szBuffer[64];
- switch( iDate )
- {
- default:
- case 0: // Month-Day-Year
- {
- wsprintf( szBuffer, "%d%s%d%s%d", tmDate.GetMonth(), szSepDate, tmDate.GetDay(), szSepDate, tmDate.GetYear() );
- break;
- }
-
- case 1: // Day-Month-Year
- {
- wsprintf( szBuffer, "%d%s%d%s%d", tmDate.GetDay(), szSepDate, tmDate.GetMonth(), szSepDate, tmDate.GetYear() );
- break;
- }
-
- case 2: // Year-Month-Day
- {
- wsprintf( szBuffer, "%d%s%d%s%d", tmDate.GetYear(), szSepDate, tmDate.GetMonth(), szSepDate, tmDate.GetDay() );
- break;
- }
- }
-
- _tcscat( szBuffer, " " );
-
- TCHAR *pszTime = &szBuffer[_tcslen( szBuffer )];
-
- switch( iTime )
- {
- default:
- case 0: // AM/PM 12-hour
- {
- BOOL bPM = FALSE;
- int iHour = tmDate.GetHour();
- if( iHour > 11 )
- {
- bPM = TRUE;
- iHour -= 12;
- }
-
- iHour = iHour ? iHour : 12;
-
- wsprintf( pszTime, "%d%s%.2d %s", iHour, szSepTime, tmDate.GetMinute(), (TCHAR *)(bPM ? szPM : szAM) );
- break;
- }
-
- case 1: // 24-hour
- {
- wsprintf( pszTime, "%d%s%.2d", tmDate.GetHour(), szSepTime, tmDate.GetMinute() );
- break;
- }
- }
-
- csFormatDate = (const char *)szBuffer;
- }
-
-
- void HTFE_MakePrettyDate(char* buffer, time_t lastVisited)
- {
- buffer[0] = 0;
- time_t today = XP_TIME();
- int elapsed = today - lastVisited;
-
- if (elapsed < SECONDS_PER_DAY)
- {
- int32 hours = (elapsed + 1800L) / 3600L;
- if (hours < 1)
- {
- strcpy(buffer, XP_GetString(XP_BKMKS_LESS_THAN_ONE_HOUR_AGO));
- }
- sprintf(buffer, XP_GetString(XP_BKMKS_HOURS_AGO), hours);
- }
- else if (elapsed < (SECONDS_PER_DAY * 31))
- {
- sprintf(buffer, XP_GetString(XP_BKMKS_DAYS_AGO),
- (elapsed + (SECONDS_PER_DAY / 2)) / SECONDS_PER_DAY);
- }
- else
- {
- CString csFormatDate;
- CTime ctDate( lastVisited );
- FormatDateTime( ctDate, csFormatDate );
- _tcscpy( buffer, (const char *)csFormatDate );
- }
- }
-
- BEGIN_MESSAGE_MAP(CRDFOutliner, COutliner)
- //{{AFX_MSG_MAP(CMainFrame)
- // NOTE - the ClassWizard will add and remove mapping macros here.
- // DO NOT EDIT what you see in these blocks of generated code !
- ON_WM_PAINT()
- ON_WM_SETFOCUS()
- ON_WM_KILLFOCUS()
- ON_WM_LBUTTONDOWN()
- ON_WM_LBUTTONUP()
- ON_WM_MOUSEMOVE()
- ON_WM_RBUTTONDOWN()
- ON_WM_RBUTTONUP()
- ON_WM_CREATE()
- ON_WM_TIMER()
- //}}AFX_MSG_MAP
- END_MESSAGE_MAP()
-
- CRDFOutliner::CRDFOutliner (HT_Pane thePane, HT_View theView, CRDFOutlinerParent* theParent)
- :m_pAncestor(NULL), m_Pane(thePane), m_View(theView), m_Parent(theParent), m_EditField(NULL),
- m_nSortType(HT_NO_SORT), m_nSortColumn(HT_NO_SORT), m_hEditTimer(0), m_hDragRectTimer(0),
- m_bNeedToClear(FALSE), m_nSelectedColumn(0), m_bDoubleClick(FALSE), m_Node(NULL),
- m_bDataSourceInWindow(FALSE), m_NavMenuBar(NULL)
- {
- ApiApiPtr(api);
- m_pUnkUserImage = api->CreateClassInstance(APICLASS_IMAGEMAP,NULL,(APISIGNATURE)IDB_BOOKMARKS);
- if (m_pUnkUserImage) {
- m_pUnkUserImage->QueryInterface(IID_IImageMap,(LPVOID*)&m_pIUserImage);
- ASSERT(m_pIUserImage);
- if (!m_pIUserImage->GetResourceID())
- m_pIUserImage->Initialize(IDB_BOOKMARKS,16,16);
- }
- }
-
- CRDFOutliner::~CRDFOutliner ()
- {
- if (m_pUnkUserImage) {
- if (m_pIUserImage)
- m_pUnkUserImage->Release();
- }
-
- delete m_pAncestor;
- }
-
- int CRDFOutliner::OnCreate(LPCREATESTRUCT lpCreateStruct)
- {
- int iRetVal = COutliner::OnCreate(lpCreateStruct);
- DragAcceptFiles(FALSE);
- return iRetVal;
- }
-
- void CRDFOutliner::HandleEvent(HT_Notification ns, HT_Resource n, HT_Event whatHappened)
- {
- if (whatHappened == HT_EVENT_NODE_OPENCLOSE_CHANGED)
- {
- FinishExpansion(HT_GetNodeIndex(m_View, n));
- }
- else if (whatHappened == HT_EVENT_NODE_SELECTION_CHANGED)
- {
- int i = HT_GetNodeIndex(m_View, n);
- InvalidateLine(i);
- }
- else if (whatHappened == HT_EVENT_NODE_ADDED)
- {
- HT_Resource par = HT_GetParent(n);
- int toggle = -1;
-
- if (par != NULL)
- toggle = HT_GetNodeIndex(m_View, par);
-
- FinishExpansion(toggle);
- }
- else if (whatHappened == HT_EVENT_VIEW_SORTING_CHANGED)
- {
- if (m_Node)
- {
- int index = HT_GetNodeIndex(m_View, m_Node);
- m_iFocus = index;
- }
- Invalidate();
- }
- else if (whatHappened == HT_EVENT_NODE_EDIT)
- {
- m_Node = n;
- m_iSelection = m_iFocus = HT_GetNodeIndex(m_View, n);
- m_nSelectedColumn = GetColumnAtPos(0);
-
- AddTextEdit();
-
- }
- else if (whatHappened == HT_EVENT_NODE_DELETED_DATA ||
- whatHappened == HT_EVENT_NODE_DELETED_NODATA)
- {
- m_iFocus = -1;
- }
- else if (whatHappened == HT_EVENT_VIEW_REFRESH)
- {
- SetTotalLines(HT_GetItemListCount(m_View));
- Invalidate();
- UpdateWindow();
- }
- else if (whatHappened == HT_EVENT_NODE_VPROP_CHANGED)
- {
- // Invalidate a single line
- if (n)
- {
- int index = HT_GetNodeIndex(m_View, n);
- InvalidateLine(index);
- }
- }
- }
-
-
- LPCTSTR CRDFOutliner::GetColumnText ( UINT iColumn, void * pLineData )
- {
- void* nodeData;
- time_t dateVal;
- struct tm* time;
-
- HT_Resource pEntry = (HT_Resource)pLineData;
- CRDFCommandMap& map = m_Parent->GetColumnCommandMap();
- CRDFColumn* theColumn = (CRDFColumn*)(map.GetCommand(iColumn));
-
- if (pEntry && HT_GetNodeData(pEntry, theColumn->GetToken(), theColumn->GetDataType(), &nodeData)
- && nodeData)
- {
- char* buffer = theColumn->GetStorageBuffer();
- switch (theColumn->GetDataType())
- {
- case HT_COLUMN_DATE_STRING:
- if ((dateVal = (time_t)atol((char *)nodeData)) == 0) break;
- if ((time = localtime(&dateVal)) == NULL) break;
- HTFE_MakePrettyDate(buffer, dateVal);
- break;
- case HT_COLUMN_DATE_INT:
- if ((time = localtime((time_t *) &nodeData)) == NULL) break;
- HTFE_MakePrettyDate(buffer, (time_t)nodeData);
- break;
- case HT_COLUMN_INT:
- sprintf(buffer,"%d",(int)nodeData);
- break;
- case HT_COLUMN_STRING:
- strcpy(buffer, (char*)nodeData);
- break;
- }
-
- return buffer;
- }
- return NULL;
- }
-
- void * CRDFOutliner::AcquireLineData ( int iLine )
- {
- // Grab this resource
- if (GetTotalLines() <= iLine)
- return NULL;
-
- HT_Resource r = HT_GetNthItem(m_View, iLine);
-
- if (r != NULL)
- {
- int indent = HT_GetItemIndentation(r);
- BOOL hasPrev = HT_ItemHasBackwardSibling(r);
- BOOL hasNext = HT_ItemHasForwardSibling(r);
-
- if (m_bPaintingFirstObject || indent > m_nSizeOfAncestorArray)
- {
- OutlinerAncestorInfo* oldInfo = m_pAncestor;
-
- if (m_bPaintingFirstObject)
- {
- m_nSizeOfAncestorArray = indent;
- oldInfo = NULL;
- }
-
- m_pAncestor = new OutlinerAncestorInfo[indent];
-
- // Fill in the ancestor values.
- copyAncestorValues(r, m_nSizeOfAncestorArray, oldInfo, m_pAncestor);
- m_nSizeOfAncestorArray = indent;
-
- delete []oldInfo;
- }
-
-
- m_pAncestor[indent-1].has_next = hasNext;
- m_pAncestor[indent-1].has_prev = hasPrev;
- }
-
- return r;
- }
-
- void CRDFOutliner::ReleaseLineData ( void * pLineData )
- {
- }
-
- void CRDFOutliner::GetTreeInfo( int iLine, uint32 * pFlags, int * iDepth,
- OutlinerAncestorInfo ** pAncestor )
- {
- HT_Resource r = HT_GetNthItem(m_View, iLine);
- if (r == NULL)
- return;
-
- if (pFlags)
- *pFlags = (uint32)HT_IsContainer(r);
- if (iDepth)
- *iDepth = HT_GetItemIndentation(r)-1;
-
- if (pAncestor)
- *pAncestor = m_pAncestor;
- }
-
- void CRDFOutliner::copyAncestorValues(HT_Resource r, int numItems, OutlinerAncestorInfo* oldInfo, OutlinerAncestorInfo* newInfo)
- {
- if (oldInfo != NULL)
- {
- for (int i = 0; i < numItems; i++)
- {
- newInfo[i].has_next = oldInfo[i].has_next;
- newInfo[i].has_prev = oldInfo[i].has_prev;
- }
- }
- else
- {
- // Have to acquire ALL the data.
- HT_Resource currNode = r;
- for (int i = numItems-1; i >= 0; i--)
- {
- newInfo[i].has_next = HT_ItemHasForwardSibling(currNode);
- newInfo[i].has_prev = HT_ItemHasBackwardSibling(currNode);
- currNode = HT_GetParent(currNode);
- }
- }
- }
-
- BOOL CRDFOutliner::IsSelected(int iLine)
- {
- HT_Resource r = HT_GetNthItem(m_View, iLine);
- return (r != NULL) && (HT_IsSelected(r));
- }
-
- HFONT CRDFOutliner::GetLineFont ( void * pLineData )
- {
- // Will need to hack this for aliases/shortcuts? (italics!)
- /*HT_Resource r = (HT_Resource)pLineData;
- char* url = HT_GetNodeURL(r);
-
- if (url && !IsLocalFile(url))
- return m_hItalFont;
- */
-
- return m_hRegFont;
- }
-
- int CRDFOutliner::TranslateIcon ( void * pData )
- {
- HT_Resource data = (HT_Resource)pData;
- char* pURL = HT_GetNodeSmallIconURL(data);
-
- //TRACE("%s\n", pURL);
-
- if (strncmp("icon", pURL, 4) == 0)
- {
- // Icon URL
- if ((strcmp("icon/small:folder/closed", pURL) == 0) ||
- (strcmp("icon/small:folder,history/closed", pURL) == 0))
- return IDX_BOOKMARKCLOSED;
-
- if ((strcmp("icon/small:folder/open", pURL) == 0) ||
- (strcmp("icon/small:folder,history/open", pURL) == 0))
- return IDX_BOOKMARKOPEN;
-
- if (strcmp("icon/small:url", pURL) == 0)
- return IDX_BOOKMARK;
-
- if ((strcmp("icon/small:file/local", pURL) == 0) ||
- (strcmp("icon/small:folder/local,closed", pURL) == 0) ||
- (strcmp("icon/small:folder/local,open", pURL) == 0))
- return HTFE_LOCAL_FILE;
-
- // Catchall code for unknown ICON urls
- if (HT_IsContainer(data))
- {
- if (HT_IsContainerOpen(data))
- return IDX_BOOKMARKOPEN;
- else return IDX_BOOKMARKCLOSED;
- }
-
- return IDX_BOOKMARK;
- }
-
- // Handle the arbitrary URL case
- return HTFE_USE_CUSTOM_IMAGE;
- }
-
- int CRDFOutliner::TranslateIconFolder( void *pData )
- {
- HT_Resource data = (HT_Resource)pData;
-
- if (data)
- {
- if (HT_IsContainer(data))
- {
- if (HT_IsContainerOpen(data))
- {
- return OUTLINER_OPENFOLDER;
- }
- else
- {
- return OUTLINER_CLOSEDFOLDER;
- }
- }
- }
-
- return OUTLINER_ITEM;
- }
-
- void CRDFOutliner::LoadComplete(HT_Resource pResource)
- {
- InvalidateLine(HT_GetNodeIndex(m_View, pResource));
- }
-
- // Functions used to draw custom images (either local file system icons or arbitrary image URLs)
- HICON DrawLocalFileIcon(HT_Resource r, int left, int top, HDC hDC)
- {
- char* pLocalName = NULL;
- HICON hIcon = FetchLocalFileIcon(r);
-
- if (hIcon)
- {
- // Now we draw this bad boy.
- DrawIconEx(hDC, left, top, hIcon, 0, 0, 0, NULL, DI_NORMAL);
- }
-
- return hIcon;
- }
-
- NSNavCenterImage* DrawArbitraryURL(HT_Resource r, int left, int top, int imageWidth, int imageHeight, HDC hDC, COLORREF bkColor,
- CCustomImageObject* pObject, BOOL largeIcon)
- {
- NSNavCenterImage* pImage = FetchCustomIcon(r, pObject, largeIcon);
- if (pImage && pImage->CompletelyLoaded())
- {
- // Now we draw this bad boy.
- if (pImage->m_BadImage)
- {
- // display broken icon.
- HDC tempDC = ::CreateCompatibleDC(hDC);
- HBITMAP hOldBmp = (HBITMAP)::SelectObject(tempDC, NSNavCenterImage::m_hBadImageBitmap);
- ::StretchBlt(hDC,
- left, top,
- imageWidth, imageHeight,
- tempDC, 0, 0,
- imageWidth, imageHeight, SRCCOPY);
- ::SelectObject(tempDC, hOldBmp);
- ::DeleteDC(tempDC);
- }
- else if (pImage->bits )
- {
- // Center the image.
- long width = pImage->bmpInfo->bmiHeader.biWidth;
- long height = pImage->bmpInfo->bmiHeader.biHeight;
- int xoffset = (imageWidth-width)/2;
- int yoffset = (imageHeight-height)/2;
- if (xoffset < 0) xoffset = 0;
- if (yoffset < 0) yoffset = 0;
- if (width > imageWidth) width = imageWidth;
- if (height > imageHeight) height = imageHeight;
-
- HPALETTE hPal = WFE_GetUIPalette(NULL);
- HPALETTE hOldPal = ::SelectPalette(hDC, hPal, TRUE);
-
- ::RealizePalette(hDC);
-
- if (pImage->maskbits)
- {
- WFE_StretchDIBitsWithMask(hDC, TRUE, NULL,
- left+xoffset, top+xoffset,
- width, height,
- 0, 0, width, height,
- pImage->bits, pImage->bmpInfo,
- pImage->maskbits, FALSE, bkColor);
- }
- else
- {
- ::StretchDIBits(hDC,
- left+xoffset, top+xoffset,
- width, height,
- 0, 0, width, height, pImage->bits, pImage->bmpInfo, DIB_RGB_COLORS,
- SRCCOPY);
- }
-
- ::SelectPalette(hDC, hOldPal, TRUE);
- }
- }
-
- return pImage;
- }
-
- BOOL IsLocalFile(const char* pURL)
- {
- return strncmp(pURL, "file:", 5) == 0;
- }
-
- BOOL IsExecutableURL(const char* pURL)
- {
- char* pLocalName = NULL;
- if (!XP_ConvertUrlToLocalFile(pURL, &pLocalName))
- return FALSE;
-
- pLocalName = NET_UnEscape(pLocalName);
-
- // Do a FindExecutable. If the filenames match, we win.
- char execName[_MAX_PATH];
- if (FEU_FindExecutable(pLocalName, execName, FALSE))
- {
- // Well, there's at least SOMETHING.
- // See if it matches us.
- char answerString[_MAX_PATH];
- strcpy(answerString, pLocalName);
- char execString[_MAX_PATH];
- strcpy(execString, execName);
-
- #ifdef _WIN32
- GetShortPathName(pLocalName, answerString, _MAX_PATH);
- GetShortPathName(execName, execString, _MAX_PATH);
- #endif // _WIN32
-
- if (!stricmp(answerString, execString))
- return TRUE;
- }
-
- if (pLocalName)
- XP_FREE(pLocalName);
-
- return FALSE;
- }
-
- // The expansion handler
- int CRDFOutliner::ToggleExpansion (int iLine)
- {
- PRBool openp;
- HT_Resource pEntry = HT_GetNthItem(m_View, iLine);
- if (pEntry && HT_IsContainer(pEntry))
- {
- HT_GetOpenState(pEntry, &openp);
- HT_SetOpenState(pEntry, (PRBool)(!openp));
- }
- return 0;
- }
-
- HICON FetchLocalFileIcon(HT_Resource r)
- {
- HICON hIcon = NULL;
- CString hashString(HT_GetNodeURL(r));
-
- if (hashString.GetLength() < 12) // Hack. It's a disk volume.
- {
- // Hash disk drives based on URL.
- }
- else if (HT_IsContainer(r))
- {
- // We're a directory.
- if (HT_IsContainerOpen(r))
- hashString = "open folder";
- else hashString = "closed folder";
- }
- else
- {
- // We're a file.
- int index = hashString.ReverseFind('.');
- if (index == -1)
- hashString = "no extension";
- else hashString = hashString.Right(hashString.GetLength() - index);
- }
-
- void* hashPtr;
- char* pLocalName = NULL;
- if (CHTFEData::m_LocalFileCache.Lookup(hashString, hashPtr))
- {
- // We found an icon in the icon cache.
- hIcon = (HICON)hashPtr;
- }
- else
- {
- XP_ConvertUrlToLocalFile(HT_GetNodeURL(r), &pLocalName);
- pLocalName = NET_UnEscape(pLocalName);
-
- SHFILEINFO shInfo;
- shInfo.hIcon = NULL;
-
- if (HT_IsContainer(r) && HT_IsContainerOpen(r))
- SHGetFileInfo(pLocalName, 0, &shInfo, sizeof(shInfo), SHGFI_OPENICON | SHGFI_ICON | SHGFI_SMALLICON);
- else SHGetFileInfo(pLocalName, 0, &shInfo, sizeof(shInfo), SHGFI_ICON | SHGFI_SMALLICON);
-
- if(shInfo.hIcon)
- {
- hIcon = shInfo.hIcon;
-
- // Add to the local file cache.
- CHTFEData::m_LocalFileCache.SetAt(hashString, (void*)hIcon);
- }
-
- if (pLocalName)
- XP_FREE(pLocalName);
- }
-
- return hIcon;
- }
-
- NSNavCenterImage* FetchCustomIcon(HT_Resource r, CCustomImageObject* imageObject, BOOL largeIcon)
- {
- NSNavCenterImage* pImage = NULL;
- CString hashString;
- if (largeIcon)
- hashString = HT_GetNodeLargeIconURL(r);
- else hashString = HT_GetNodeSmallIconURL(r);
-
- if (strncmp("icon/large:workspace", hashString, 20) == 0)
- {
- char name[8];
- int ret = sscanf(hashString, "icon/large:workspace,%s", name);
- if (ret != 0)
- hashString = CString("about:") + name + ".gif";
- }
- else if (strncmp("icon/large:folder", hashString, 17) == 0)
- {
- hashString = "about:personal.gif";
- }
-
- // Find the image.
- void* pData;
- if (CHTFEData::m_CustomURLCache.Lookup(hashString, pData))
- {
- pImage = (NSNavCenterImage*)pData;
-
- // Add ourselves to the callback list if the image hasn't completely loaded.
- if (!pImage->CompletelyLoaded())
- {
- // The image is currently loading. Register ourselves with the image so that we will get called
- // when the image finishes loading.
- CIconCallbackInfo* iconCallbackInfo = new CIconCallbackInfo(imageObject, r);
- pImage->resourceList.AddHead(iconCallbackInfo);
- }
- }
- else
- {
- // Create a new NavCenter image.
- CIconCallbackInfo* iconCallbackInfo = new CIconCallbackInfo(imageObject, r);
- pImage = new NSNavCenterImage((char*)(const char*)hashString, iconCallbackInfo);
- CHTFEData::m_CustomURLCache.SetAt(hashString, pImage);
- }
-
- return pImage;
- }
-
-
- IconType DetermineIconType(HT_Resource pNode, BOOL largeIcon)
- {
- IconType returnValue;
- if (pNode != NULL)
- {
- char* pURL = largeIcon? HT_GetNodeLargeIconURL(pNode) : HT_GetNodeSmallIconURL(pNode);
- TRACE("%s\n", pURL);
- if (strncmp("icon", pURL, 4) != 0)
- {
- // Time to load a custom image.
- returnValue = ARBITRARY_URL;
- }
- else if ((strncmp("icon/large:workspace", pURL, 20) == 0) ||
- (strncmp("icon/large:folder", pURL, 17) == 0))
- {
- returnValue = ARBITRARY_URL;
- }
- else if (IsLocalFile(HT_GetNodeURL(pNode)))
- {
- returnValue = LOCAL_FILE;
- }
- else returnValue = BUILTIN_BITMAP;
- }
- else returnValue = BUILTIN_BITMAP;
-
- return returnValue;
- }
-
- // The callback for finishing the expansion
- void CRDFOutliner::FinishExpansion(int toggleIndex)
- {
- int iCount = GetTotalLines();
- int newCount = HT_GetItemListCount(m_View);
- SetTotalLines(newCount); // Update the outliner's visible lines
-
- int iDelta = newCount - iCount;
- int iSel = GetFocusLine();
- if (iSel > toggleIndex) {
- if (iDelta > 0) {
- iSel += iDelta;
- } else {
- if (iSel < (toggleIndex - iDelta)) {
- iSel = toggleIndex;
- } else {
- iSel += iDelta;
- }
- }
- if (iSel != GetFocusLine())
- {
- m_iFocus = m_iSelection = iSel;
- InvalidateLine(m_iFocus);
- }
- }
-
- if ( iDelta > 0 )
- {
- iDelta = iDelta > m_iPaintLines - 2 ? m_iPaintLines - 2 : iDelta;
-
- if (!m_bDataSourceInWindow) // Springloading folders go haywire if we shift lines around, so don't do it
- EnsureVisible( toggleIndex + iDelta );
- }
-
- Invalidate();
- }
-
- void CRDFOutliner::SelectItem(int iSel,int mode,UINT flags)
- {
- int oldColumn = GetSelectedColumn();
-
- if (m_iColHit == -1)
- return;
-
- UINT command = m_pColumn[ m_iColHit ]->iCommand;
-
- RemoveTextEdit();
-
- m_Node = HT_GetNthItem(m_View, iSel);
-
- if (!m_Node)
- {
- HT_SetSelectionAll(m_View, (PRBool)FALSE);
-
- if (mode != OUTLINER_RBUTTONDOWN)
- return;
-
- m_Node = HT_TopNode(m_View);
- iSel = -1;
-
- }
-
- switch (mode)
- {
- case OUTLINER_RETURN:
- case OUTLINER_LBUTTONDBLCLK:
- OnSelDblClk(iSel);
- m_bDoubleClick = TRUE;
- if (m_hEditTimer)
- {
- KillTimer(m_hEditTimer);
- m_hEditTimer = 0;
- }
- break;
- case OUTLINER_LBUTTONUP:
- if (m_bNeedToClear)
- {
- HT_SetSelection(m_Node);
- if (m_bNeedToEdit && !m_bDoubleClick)
- {
-
- CRDFCommandMap& map = m_Parent->GetColumnCommandMap();
- CRDFColumn* theColumn = (CRDFColumn*)(map.GetCommand(m_nSelectedColumn));
-
- BOOL isEditable = HT_IsNodeDataEditable(m_Node, theColumn->GetToken(),
- theColumn->GetDataType());
-
- // Get down.... get down... time for a column edit.
- if (isEditable)
- m_hEditTimer = SetTimer(IDT_EDITFOCUS, EDIT_DELAY, NULL);
- }
- }
- m_bNeedToClear = FALSE;
- m_bNeedToEdit = FALSE;
- m_bDoubleClick = FALSE;
- break;
- case OUTLINER_LBUTTONDOWN:
- case OUTLINER_KEYDOWN:
- case OUTLINER_SET:
- m_iFocus = iSel;
- m_bNeedToClear = FALSE;
- m_bNeedToEdit = FALSE;
- SetSelectedColumn((int)command);
-
- if (flags & MK_CONTROL)
- {
- // Causes a selection toggle.
- HT_ToggleSelection(m_Node);
- }
- else if (flags & MK_SHIFT)
- {
- // A range of items is being selected.
- HT_Resource node = HT_GetNthItem(m_View, m_iSelection);
- if (node != NULL)
- {
- HT_SetSelectionRange(node, m_Node);
- }
- }
- else
- {
- m_iSelection = iSel;
-
- if (!IsSelected(m_iFocus))
- {
- HT_SetSelection(m_Node);
-
- //if (!HT_IsContainer(m_Node) && !HT_IsSeparator(m_Node) && IsDocked())
- // DisplayURL(); For now do double-click behavior
- }
- else
- {
- m_bNeedToClear = TRUE;
- if (oldColumn == m_nSelectedColumn)
- m_bNeedToEdit = TRUE;
- }
- }
- break;
-
- case OUTLINER_RBUTTONDOWN:
- m_iFocus = iSel;
- SetSelectedColumn((int)command);
- m_iSelection = iSel;
-
- if (m_iFocus >= 0 && !IsSelected(m_iFocus))
- {
- HT_SetSelection(m_Node);
- }
- break;
- default:
- break;
- }
- }
-
- BOOL CRDFOutliner::DeleteItem(int iSel)
- {
- HT_DoMenuCmd(m_Pane, HT_CMD_CUT);
- return TRUE;
- }
-
- BOOL CRDFOutliner::IsDocked()
- {
- CGenericFrame* theFrame = (CGenericFrame*)FEU_GetLastActiveFrame();
-
- if (theFrame == NULL)
- return FALSE;
-
- return theFrame->IsChild(this);
- }
-
- void CRDFOutliner::OnSelDblClk(int iLine)
- {
- if (m_Node)
- {
- if (HT_IsContainer(m_Node))
- {
- ToggleExpansion(iLine);
- }
- else if (!HT_IsSeparator(m_Node))// && !IsDocked()) For now always do double-click behavior
- {
- DisplayURL();
- }
- }
- }
-
- void CRDFOutliner::DisplayURL()
- {
- char* url = HT_GetNodeURL(m_Node);
- if (IsExecutableURL(url))
- {
- // Shell Execute
- #ifdef _WIN32
- char* pLocalName = NULL;
- XP_ConvertUrlToLocalFile(url, &pLocalName);
- pLocalName = NET_UnEscape(pLocalName);
-
- SHELLEXECUTEINFO sei;
-
- // Use ShellExecuteEx to launch
- sei.cbSize = sizeof(sei);
- sei.fMask = SEE_MASK_FLAG_NO_UI | SEE_MASK_NOCLOSEPROCESS;
- sei.hwnd = NULL;
- sei.lpVerb = NULL; // default to Open
- sei.lpFile = pLocalName;
- sei.lpParameters = NULL;
- sei.lpDirectory = NULL;
- sei.nShow = SW_SHOW;
- ShellExecuteEx(&sei);
- int uSpawn = (UINT)sei.hInstApp;
- if(uSpawn <= 32)
- {
- char szMsg[80];
- switch(uSpawn)
- {
- case 0:
- case 8:
- sprintf(szMsg, szLoadString(IDS_WINEXEC_0_8));
- break;
- case 2:
- case 3:
- sprintf(szMsg, szLoadString(IDS_WINEXEC_2_3));
- break;
- case 10:
- case 11:
- case 12:
- case 13:
- case 14:
- case 15:
- sprintf(szMsg, szLoadString(IDS_WINEXEC_10_THRU_15));
- break;
- case 16:
- sprintf(szMsg, szLoadString(IDS_WINEXEC_16));
- break;
- case 21:
- sprintf(szMsg, szLoadString(IDS_WINEXEC_21));
- break;
- default:
- sprintf(szMsg, szLoadString(IDS_WINEXEC_XX), uSpawn);
- break;
- }
-
- CString s;
- if (s.LoadString( IDS_BOOKMARK_ADDRESSPROPERTIES ))
- {
- ::MessageBox(GetParentFrame()->m_hWnd, szMsg, s, MB_OK | MB_APPLMODAL);
- }
- }
- if (pLocalName)
- XP_FREE(pLocalName);
- #endif // _WIN32
- }
- else
- {
- CAbstractCX * pCX = FEU_GetLastActiveFrameContext();
- ASSERT(pCX != NULL);
- if (pCX != NULL)
- {
- if (!strncmp(url, "nes:", 4))
- pCX->NormalGetUrl((LPTSTR)&url[4]);
- else
- pCX->NormalGetUrl((LPTSTR) url);
- }
- }
- }
-
- BOOL CRDFOutliner::TestRowCol(POINT point, int &iRow, int &iCol)
- {
- RECT rcClient;
- GetClientRect(&rcClient);
- BOOL answer = TRUE;
-
- if (::PtInRect(&rcClient, point))
- {
- void *pLineData = NULL;
- int iSel = point.y / m_itemHeight;
- int iNewSel = m_iTopLine + iSel;
- if ( ( pLineData = AcquireLineData ( iNewSel ) ) != NULL )
- {
- ReleaseLineData( pLineData );
- iRow = iNewSel;
- }
- else answer = FALSE;
-
- int i, offset;
- int y = iSel * m_itemHeight;
-
- for ( i = 0, offset = 0; i < m_iVisColumns; i++ )
- {
- CRect rect ( offset, y,
- offset + m_pColumn[ i ]->iCol, y + m_itemHeight );
-
- if ( rect.PtInRect(point) )
- {
- iCol = i;
- m_rcHit = rect;
- return answer;
- }
-
- offset += m_pColumn[ i ]->iCol;
- }
- }
- return FALSE;
- }
-
- int CRDFOutliner::DetermineClickLocation(CPoint point)
- {
- // TestRowCol returns FALSE if the row clicked on contains no data. We must have clicked on the background
- // in this case.
- int iRow, iCol;
-
- if ( !TestRowCol( point, iRow, iCol ) )
- return CLICKED_BACKGROUND;
-
- // We clicked on a row/column with data. Update our member variables to reflect our hit.
- m_iRowHit = iRow;
- m_iColHit = iCol;
-
- // Get the text rectangle corresponding to the hit column.
- CRect textRect = GetColumnRect(iRow, (int)(m_pColumn[iCol]->iCommand));
-
- // Double-check and make sure we have line data. (We should, but let's be safe.)
- void * pLineData;
- if ( ( pLineData = AcquireLineData ( iRow ) ) == NULL)
- return CLICKED_BACKGROUND;
- int iDepth;
- GetTreeInfo ( iRow, NULL, &iDepth, NULL );
- HT_Resource r = (HT_Resource)pLineData;
- ReleaseLineData ( pLineData );
-
- // If the user clicked on the image column, they might have struck the trigger. Check for this.
- if ( m_pColumn[ iCol ]->iCommand == m_idImageCol )
- {
- int iImageWidth = m_pIImage->GetImageWidth ( );
- RECT rcToggle = m_rcHit;
- rcToggle.left += iDepth * iImageWidth;
- rcToggle.right = rcToggle.left + iImageWidth;
-
- // If the data is a container and if the point is inside the toggle rect, the user clicked the
- // trigger.
- if ( ::PtInRect( &rcToggle, point ) && HT_IsContainer(r))
- return CLICKED_TRIGGER;
-
- // If the user clicked to the left of the trigger on a container, then treat as a background click.
- // If the user clicked where the trigger would have been (or to the left of the trigger) on a non-
- // container, then treat that as a background click also.
- if ((point.x < rcToggle.left && HT_IsContainer(r)) ||
- (point.x < rcToggle.right && !HT_IsContainer(r)))
- return CLICKED_BACKGROUND;
- }
-
- // See if the user clicked on the column text.
- const char* text = GetColumnText(m_pColumn[ iCol ]->iCommand, r);
- if (!text)
- return CLICKED_BACKGROUND; // Column has no text. User has to have clicked on the background.
-
- // All this code just determines our text rectangle.
- CClientDC dc(this);
- CString theString(text);
- CRect bgRect;
- dc.SelectObject( GetLineFont( r ) );
- UINT dwDTFormat = DT_NOCLIP | DT_NOPREFIX | DT_SINGLELINE | DT_VCENTER;
- switch (m_pColumn[ iCol ]->alignment)
- {
- case AlignCenter:
- dwDTFormat |= DT_CENTER;
- break;
- case AlignRight:
- dwDTFormat |= DT_RIGHT;
- break;
- case AlignLeft:
- default:
- dwDTFormat |= DT_LEFT;
- }
-
- dc.DrawText(theString, theString.GetLength(), &bgRect, DT_CALCRECT | dwDTFormat);
- int w = bgRect.Width() + 2*COL_LEFT_MARGIN;
- if (w > textRect.Width())
- w = textRect.Width();
- bgRect.left = textRect.left;
- bgRect.top = textRect.top;
- bgRect.right = bgRect.left + w;
- bgRect.bottom = textRect.bottom;
-
- if ( m_pColumn[ iCol ]->iCommand == m_idImageCol )
- bgRect.left -= (m_pIUserImage->GetImageWidth() + OUTLINE_TEXT_OFFSET);
-
- // Now that we've set up the rect, see if the user clicked in it. If they didn't, it's a background
- // click.
- if (!bgRect.PtInRect(point))
- return CLICKED_BACKGROUND;
-
- // User jumped through all our hoops. Must have clicked on some actual data.
- return CLICKED_LINE;
- }
-
- void CRDFOutliner::OnLButtonDown ( UINT nFlags, CPoint point )
- {
- // Reset drag rect info
- m_bCheckForDragRect = FALSE;
- m_LastDragRect = CRect(0,0,0,0);
- m_nRectYDisplacement = 0;
-
- Default();
- TipHide();
-
- SetFocus();
-
- m_ptHit = point;
-
- m_iRowHit = -1;
- m_iColHit = -1;
-
- int clickResult = DetermineClickLocation(point);
-
- if (clickResult == CLICKED_TRIGGER)
- DoToggleExpansion(m_iRowHit);
- else if (clickResult == CLICKED_LINE)
- {
- if ( ColumnCommand( m_pColumn[ m_iColHit ]->iCommand, m_iRowHit) )
- return;
-
- SetCapture();
-
- SelectItem( m_iRowHit, OUTLINER_LBUTTONDOWN, nFlags );
- }
- else
- {
- // user clicked on the background
- m_bCheckForDragRect = TRUE;
- SetCapture();
- m_iFocus = -1;
- if (m_iColHit != -1)
- {
- SetSelectedColumn(m_pColumn[ m_iColHit ]->iCommand);
- }
- HT_SetSelectionAll(m_View, (PRBool)FALSE);
- }
- }
-
- void CRDFOutliner::OnLButtonUp(UINT nFlags, CPoint point)
- {
- if (GetCapture() == this) {
- ReleaseCapture();
- if (m_LastDragRect != CRect(0,0,0,0))
- {
- // Dragging happened
- CClientDC dc(this);
- EraseDragRect(&dc, m_LastDragRect);
-
- if (m_hDragRectTimer)
- {
- KillTimer(m_hDragRectTimer);
- m_hDragRectTimer = 0;
- }
- }
- else SelectItem( m_iSelection, OUTLINER_LBUTTONUP, nFlags );
- }
- }
-
- void CRDFOutliner::OnRButtonDown ( UINT nFlags, CPoint point )
- {
- // Update our column hit, since we draw selected columns.
- m_iRowHit = -1;
- m_iColHit = -1;
-
- int clickResult = DetermineClickLocation(point);
-
- if (clickResult == CLICKED_LINE)
- {
- // user clicked on the item. We will go ahead and select.
- SelectItem( m_iRowHit, OUTLINER_RBUTTONDOWN, nFlags );
- }
- else
- {
- // user clicked on the background... deselect everything.
- m_iFocus = -1;
- HT_SetSelectionAll(m_View, (PRBool)FALSE);
- }
-
- /*
- int iRow, iCol;
- if ( TestRowCol( point, iRow, iCol ) ){
- HT_Resource pEntry = HT_GetNthItem(m_View, iRow);
- CExportRDF exportDlg;
-
- if (exportDlg.DoModal() == IDOK) {
- FILE* mcfStr;
- mcfStr = fopen(exportDlg.m_csAns, "w");
- outputMCFTree(RDF_GetNavCenterDB(), stdPrint, mcfStr, HT_GetRDFResource(pEntry));
- fclose(mcfStr);
- }
- }
- */
- }
-
- void CRDFOutliner::OnRButtonUp( UINT nFlags, CPoint point )
- {
- m_ptHit = point;
- int iSel = m_iTopLine + (point.y / m_itemHeight);
-
- int clickResult = DetermineClickLocation(point);
- PropertyMenu( iSel, clickResult );
- }
-
- void CRDFOutliner::DragRectScroll( BOOL bBackwards )
- {
- int oldLine = m_iTopLine;
- OnVScroll(bBackwards ? SB_LINEUP : SB_LINEDOWN, 0, 0);
- m_nRectYDisplacement += (oldLine - m_iTopLine)*m_itemHeight;
- if (m_nRectYDisplacement != 0)
- {
- OnMouseMove(0, m_MovePoint);
- }
- }
-
- CRect CRDFOutliner::ConstructDragRect(const CPoint& pt1, const CPoint& pt2)
- {
- int left = pt1.x < pt2.x ? pt1.x : pt2.x;
- int right = pt1.x > pt2.x ? pt1.x : pt2.x;
-
- int top = pt1.y < pt2.y ? pt1.y : pt2.y;
- int bottom = pt1.y > pt2.y ? pt1.y : pt2.y;
-
- return CRect(left, top, right, bottom);
- }
-
- void CRDFOutliner::EraseDragRect(CDC* pDC, CRect rect)
- {
- #ifdef XP_WIN32
- CRgn rgnLast, rgnOutside, rgnInside;
-
- // set up regions and rects for drag rect with border of size (1,1)
- rgnLast.CreateRectRgn(0, 0, 0, 0);
- rgnOutside.CreateRectRgnIndirect(&rect);
- CRect rect2 = rect;
- rect.InflateRect(-1, -1);
- rect.IntersectRect(rect, rect2);
- rgnInside.CreateRectRgnIndirect(&rect);
- rgnLast.CombineRgn(&rgnOutside, &rgnInside, RGN_XOR);
-
- // Do the erase
- pDC->SelectClipRgn(&rgnLast);
- pDC->GetClipBox(&rect);
- CBrush* pBrushLast = CDC::GetHalftoneBrush();
- CBrush* pBrushOld = pDC->SelectObject(pBrushLast);
- pDC->PatBlt(rect.left, rect.top, rect.Width(), rect.Height(), PATINVERT);
- pDC->SelectObject(pBrushOld);
- pDC->SelectClipRgn(NULL);
- #endif
- }
-
- void CRDFOutliner::OnMouseMove(UINT nFlags, CPoint point)
- {
- if (GetCapture() == this)
- {
- #ifdef XP_WIN32
- if (m_bCheckForDragRect)
- {
- CRect rect;
- GetClientRect(&rect);
-
- // We're dragging a rectangle, baby.
- if (point.x < 0) // HACK so hit test works
- point.x = 0;
-
- if (point.y < 0)
- point.y = 0;
-
- if (point.y > rect.bottom)
- point.y = rect.bottom;
-
- m_MovePoint = point;
-
- if ( point.y < m_itemHeight )
- {
- m_hDragRectTimer = SetTimer(IDT_DRAGRECT, GetDragHeartbeat(), NULL);
- }
- else if ( point.y > (rect.bottom - m_itemHeight) )
- {
- m_hDragRectTimer = SetTimer(IDT_DRAGRECT, GetDragHeartbeat(), NULL);
- }
- else if (m_hDragRectTimer)
- {
- KillTimer(m_hDragRectTimer);
- m_hDragRectTimer = 0;
- }
-
- CClientDC dc(this);
- CRect newRect = ConstructDragRect(m_ptHit, point);
-
- // Determine the new selection state
- if (m_LastDragRect == CRect(0,0,0,0))
- dc.DrawDragRect(&newRect, CSize(1,1), NULL, CSize(1,1));
- else
- {
- // Displace the rects to account for scrolling
- m_LastDragRect.OffsetRect(0, m_nRectYDisplacement);
- newRect.OffsetRect(0, m_nRectYDisplacement);
-
- if (m_nRectYDisplacement > 0)
- newRect.top += m_nRectYDisplacement;
- else newRect.bottom -= m_nRectYDisplacement;
-
- // Reset the displacement for future scroll events
- m_nRectYDisplacement = 0;
-
- // Potential to add selection.
- CPoint testPoint1 = m_LastDragRect.TopLeft();
- CPoint testPoint2 = newRect.TopLeft();
- if (m_LastDragRect.bottom != newRect.bottom)
- {
- testPoint1 = CPoint(m_LastDragRect.left,
- m_LastDragRect.bottom);
- testPoint2 = CPoint(newRect.left, newRect.bottom);
- }
- int iRow = -1;
- int iCol = -1;
- int otherRow = -1;
- int otherCol = -1;
- TestRowCol(testPoint1, iRow, iCol);
- TestRowCol(testPoint2, otherRow, otherCol);
-
- // Both over selections.
- if (iRow != otherRow)
- {
- // Erase the old drag rect
- EraseDragRect(&dc, m_LastDragRect);
- UpdateWindow();
-
- // Add or remove selection...
- int start;
- int end;
- BOOL select;
-
- if (iRow == -1)
- iRow = otherRow+1;
- else if (otherRow == -1)
- otherRow = iRow+1;
-
- if (m_LastDragRect.bottom < newRect.bottom)
- {
- start = iRow+1;
- end = otherRow+1;
- select = TRUE;
- }
- else if (m_LastDragRect.bottom > newRect.bottom)
- {
- start = otherRow+1;
- end = iRow+1;
- select = FALSE;
- }
- else if (m_LastDragRect.top > newRect.top)
- {
- start = otherRow;
- end = iRow;
- select = TRUE;
- }
- else if (m_LastDragRect.top < newRect.top)
- {
- start = iRow;
- end = otherRow;
- select = FALSE;
- }
-
- // Going from start to end, performing selection
- for (int i = start; i < end; i++)
- {
- HT_Resource r = HT_GetNthItem(m_View, i);
- if (r)
- HT_SetSelectedState(r, (PRBool)select);
- }
-
- UpdateWindow();
-
- // Draw the new rect
- dc.DrawDragRect(&newRect, CSize(1,1), NULL, CSize(1,1));
-
- }
- else
- dc.DrawDragRect(&newRect, CSize(1,1), &m_LastDragRect, CSize(1,1));
-
- }
- m_LastDragRect = newRect;
- }
- else
- #endif // XP_WIN32
-
- // See if the mouse has moved far enough to start
- // a drag operation
- if ((abs(point.x - m_ptHit.x) > 3)
- || (abs(point.y - m_ptHit.y) > 3))
- {
- // release the mouse capture
-
- ReleaseCapture();
- InitiateDragDrop();
-
- m_bClearOnRelease = FALSE;
- m_bSelectOnRelease = FALSE;
- SelectItem( m_iSelection, OUTLINER_LBUTTONUP, nFlags );
- }
- }
- if (m_iTipState != TIP_SHOWING)
- m_iTipState = TIP_WAITING;
- HandleMouseMove( point );
- }
-
-
- void CRDFOutliner::PropertyMenu(int iLine, UINT flags)
- {
- // Grab the resource
- BOOL backgroundCommands = (flags == CLICKED_BACKGROUND);
-
- CMenu popup;
- if (popup.CreatePopupMenu() != 0)
- {
- // We have a node and a menu. Fetch those commands.
- // Remove the elements from the last property menu we pulled up.
- m_MenuCommandMap.Clear();
- HT_Cursor theCursor = HT_NewContextualMenuCursor(m_View, (PRBool)FALSE, (PRBool)backgroundCommands);
- if (theCursor != NULL)
- {
- // We have a cursor. Attempt to iterate
- HT_MenuCmd theCommand;
- while (HT_NextContextMenuItem(theCursor, &theCommand))
- {
- char* menuName = HT_GetMenuCmdName(theCommand);
- if (theCommand == HT_CMD_SEPARATOR)
- popup.AppendMenu(MF_SEPARATOR);
- else
- {
- // Add the command to our command map
- CRDFMenuCommand* rdfCommand = new CRDFMenuCommand(menuName, theCommand);
- int index = m_MenuCommandMap.AddCommand(rdfCommand);
- popup.AppendMenu(MF_ENABLED, index+FIRST_HT_MENU_ID, menuName);
- }
- }
- HT_DeleteCursor(theCursor);
- }
-
- // Track the popup now.
- POINT pt = m_ptHit;
- ClientToScreen(&pt);
- popup.TrackPopupMenu( TPM_LEFTALIGN | TPM_RIGHTBUTTON, pt.x, pt.y, this, NULL );
-
- // Cleanup
- popup.DestroyMenu();
- }
- }
-
- BOOL CRDFOutliner::OnCommand(UINT wParam, LONG lParam)
- {
- if (wParam >= FIRST_HT_MENU_ID && wParam <= LAST_HT_MENU_ID)
- {
- // A selection was made from the context menu.
- // Use the menu map to get the HT command value
- CRDFMenuCommand* theCommand = (CRDFMenuCommand*)(m_MenuCommandMap.GetCommand((int)wParam-FIRST_HT_MENU_ID));
- if (theCommand)
- {
- HT_MenuCmd htCommand = theCommand->GetHTCommand();
- HT_DoMenuCmd(m_Pane, htCommand);
- }
- }
-
- return TRUE;
- }
-
- void CRDFOutliner::OnSetFocus ( CWnd * pOldWnd )
- {
- // Update the context's stored RDF Info. Hack for the back end. Needs to go away eventually.
- theApp.m_pRDFCX->TrackRDFWindow(this);
-
- Default();
-
- if (m_iSelection >= 0)
- for (int i =0; i < (m_iTopLine+m_iPaintLines); i++)
- if (IsSelected(i))
- InvalidateLine(i);
-
- FocusCheck(pOldWnd, TRUE);
- }
-
- void CRDFOutliner::OnKillFocus ( CWnd * pNewWnd )
- {
- CWnd::OnKillFocus ( pNewWnd );
- if (m_iSelection >= 0)
- for (int i =0; i < (m_iTopLine+m_iPaintLines); i++)
- if (IsSelected(i))
- InvalidateLine(i);
-
- ((COutlinerParent*)GetParent())->UpdateFocusFrame();
-
- FocusCheck(pNewWnd, FALSE);
- }
-
- void CRDFOutliner::FocusCheck(CWnd* pWnd, BOOL gotFocus)
- {
- if (m_NavMenuBar)
- {
- if (gotFocus)
- m_NavMenuBar->NotifyFocus(TRUE);
- else
- {
- CFrameWnd* pFrame = GetParentFrame();
- if (pFrame && !pFrame->IsChild(pWnd))
- {
- // Invalidate for a redraw
- m_NavMenuBar->NotifyFocus(FALSE);
- }
- }
- }
- }
-
- COLORREF Darken(COLORREF r)
- {
- COLORREF ref = GetSysColor(COLOR_WINDOW);
- float x = GetRValue(ref);
- float y = GetGValue(ref);
- float z = GetBValue(ref);
-
- x = 0.75f*(x+1);
- y = 0.75f*(y+1);
- z = 0.75f*(z+1);
-
- BYTE newR = (BYTE)(int)x;
- BYTE newG = (BYTE)(int)y;
- BYTE newB = (BYTE)(int)z;
-
- return RGB(newR, newG, newB);
- }
-
- COLORREF Brighten(COLORREF r)
- {
- COLORREF ref = GetSysColor(COLOR_WINDOW);
- float x = GetRValue(ref);
- float y = GetGValue(ref);
- float z = GetBValue(ref);
-
- x = x + 0.25f*(256 - x);
- y = y + 0.25f*(256 - y);
- z = z + 0.25f*(256 - z);
-
- if (x > 255.0f) x = 255.0f;
- if (y > 255.0f) y = 255.0f;
- if (z > 255.0f) z = 255.0f;
-
- BYTE newR = (BYTE)(int)x;
- BYTE newG = (BYTE)(int)y;
- BYTE newB = (BYTE)(int)z;
-
- return RGB(newR, newG, newB);
- }
-
- void CRDFOutliner::OnPaint()
- {
- m_bPaintingFirstObject = TRUE;
-
- RECT rcClient;
- GetClientRect(&rcClient);
- CPaintDC pdc ( this );
-
- COLORREF bgColor = GetSysColor(COLOR_WINDOW);
- COLORREF textColor = GetSysColor(COLOR_WINDOWTEXT);
- COLORREF sortColor;
- if (GetRValue(bgColor) == 255 && GetGValue(bgColor) == 255 && GetBValue(bgColor) == 255
- && sysInfo.m_iBitsPerPixel > 8)
- {
- // Translate white to gray (HACK TO SATISFY THE MIGHTY GUHA)
- sortColor = RGB(192,192,192);
- bgColor = RGB(224,224,224);
- textColor = RGB(0,0,0);
- }
- else
- {
- if (((GetRValue(textColor) + GetGValue(textColor) + GetBValue(textColor))/3) > 128)
- sortColor = Darken(bgColor);
- else sortColor = Brighten(bgColor);
- }
-
- HPALETTE hPalette = WFE_GetUIPalette(GetParentFrame());
- HPALETTE pOldPalette = ::SelectPalette(pdc.m_hDC, hPalette, TRUE);
- /*
- if (sysInfo.m_iBitsPerPixel <= 8)
- {
- PALETTEENTRY paletteColors[1];
-
- UINT index;
-
- index = ::GetNearestPaletteIndex(hPalette, sortColor);
- ::GetPaletteEntries(hPalette, index, 1, paletteColors);
- sortColor = RGB(paletteColors[0].peRed, paletteColors[0].peGreen, paletteColors[0].peBlue);
-
- index = ::GetNearestPaletteIndex(hPalette, bgColor);
- ::GetPaletteEntries(hPalette, index, 1, paletteColors);
- bgColor = RGB(paletteColors[0].peRed, paletteColors[0].peGreen, paletteColors[0].peBlue);
-
- index = ::GetNearestPaletteIndex(hPalette, textColor);
- ::GetPaletteEntries(hPalette, index, 1, paletteColors);
- textColor = RGB(paletteColors[0].peRed, paletteColors[0].peGreen, paletteColors[0].peBlue);
- }
- */
- HBRUSH hRegBrush = (HBRUSH) ::CreateSolidBrush(bgColor);
- HPEN hRegPen = (HPEN)::CreatePen( PS_SOLID, 0, bgColor);
-
- HBRUSH hHighBrush = ::CreateSolidBrush( GetSysColor( COLOR_HIGHLIGHT ) );
- HPEN hHighPen = ::CreatePen( PS_SOLID, 0, GetSysColor ( COLOR_HIGHLIGHT ) );
-
- HBRUSH hOldBrush = (HBRUSH) pdc.SelectObject ( hRegBrush );
- HPEN hOldPen = (HPEN) pdc.SelectObject ( hRegPen );
- COLORREF cOldText = pdc.SetTextColor ( textColor );
- COLORREF cOldBk = pdc.SetBkColor ( bgColor );
-
- int i;
- for ( i = pdc.m_ps.rcPaint.top / m_itemHeight;
- i < ( pdc.m_ps.rcPaint.bottom / m_itemHeight ) + 1; i++ )
- {
-
- int index = i + m_iTopLine;
-
- PaintLine ( i, pdc.m_hDC, &pdc.m_ps.rcPaint, sortColor, hHighBrush, hHighPen );
-
- if (m_bPaintingFirstObject)
- m_bPaintingFirstObject = FALSE;
- }
-
- pdc.SetTextColor ( cOldText );
- pdc.SetBkColor ( cOldBk );
- pdc.SelectObject ( hOldPen );
- pdc.SelectObject ( hOldBrush );
-
- ::SelectPalette(pdc.m_hDC, pOldPalette, FALSE);
-
- VERIFY(DeleteObject( hRegBrush ));
- VERIFY(DeleteObject( hRegPen ));
- VERIFY(DeleteObject( hHighBrush ));
- VERIFY(DeleteObject( hHighPen ));
- }
-
- void CRDFOutliner::PaintLine ( int iLineNo, HDC hdc, LPRECT lpPaintRect, COLORREF sortColor,
- HBRUSH hHighlightBrush,
- HPEN hHighlightPen )
- {
- void * pLineData;
- int iImageWidth = m_pIImage->GetImageWidth ( );
- CRect WinRect;
- GetClientRect(&WinRect);
-
- int y = m_itemHeight * iLineNo;
-
- int iColumn, offset;
- CRect rectColumn, rectInter;
-
- rectColumn.top = y;
- rectColumn.bottom = y + m_itemHeight;
-
- if ( !( pLineData = AcquireLineData( iLineNo + m_iTopLine )) )
- {
- EraseLine ( iLineNo, hdc, lpPaintRect );
- if (ViewerHasFocus() && HasFocus(iLineNo + m_iTopLine))
- {
- rectColumn.left = WinRect.left;
- rectColumn.right = WinRect.right;
- DrawFocusRect ( hdc, &rectColumn );
- }
-
- // Draw the column rect
- for ( int iColumn = offset = 0; iColumn < m_iVisColumns; iColumn++ )
- {
- rectColumn.left = offset;
- rectColumn.right = offset + m_pColumn[ iColumn ]->iCol;
-
- if (iColumn == GetSortColumn())
- {
- // Draw the sort rect (Yes, I know this is inefficient.)
- HBRUSH hSortBrush = (HBRUSH)::CreateSolidBrush(sortColor);
- HBRUSH pOldBrush = (HBRUSH) ::SelectObject(hdc, hSortBrush);
- ::FillRect(hdc, &rectColumn, (HBRUSH) GetCurrentObject(hdc, OBJ_BRUSH));
- ::SelectObject(hdc, pOldBrush);
- VERIFY(DeleteObject(hSortBrush));
- }
-
- offset += m_pColumn[ iColumn ]->iCol;
- }
- return;
- }
-
- HFONT hOldFont =(HFONT) ::SelectObject ( hdc, GetLineFont ( pLineData ) );
-
- for ( iColumn = offset = 0; iColumn < m_iVisColumns; iColumn++ )
- {
- rectColumn.left = offset;
- rectColumn.right = offset + m_pColumn[ iColumn ]->iCol;
-
- if ( rectInter.IntersectRect ( &rectColumn, lpPaintRect ) )
- {
- HBRUSH pOldBrush;
- COLORREF cOldBk;
- HPEN pOldPen;
- HPEN hRegPen;
- HBRUSH hSortBrush;
- if (iColumn == GetSortColumn())
- {
- hSortBrush = (HBRUSH)::CreateSolidBrush(sortColor);
- pOldBrush = (HBRUSH) ::SelectObject(hdc, hSortBrush);
- cOldBk = ::SetBkColor ( hdc, sortColor );
- hRegPen = (HPEN)::CreatePen( PS_SOLID, 0, sortColor);
- pOldPen = (HPEN)::SelectObject(hdc, hRegPen);
- }
-
- ::FillRect(hdc, &rectColumn, (HBRUSH) GetCurrentObject(hdc, OBJ_BRUSH));
-
- if ( m_pColumn[ iColumn ]->iCommand == m_idImageCol )
- {
- rectColumn.left = DrawPipes ( iLineNo, iColumn, offset, hdc, pLineData );
- rectColumn.left += OUTLINE_TEXT_OFFSET;
- }
- PaintColumn ( iLineNo, iColumn, rectColumn, hdc, pLineData, hHighlightBrush,
- hHighlightPen );
-
- if (iColumn == GetSortColumn())
- {
- ::SelectObject(hdc, pOldBrush);
- ::SetBkColor(hdc, cOldBk);
- ::SelectObject(hdc, pOldPen);
- VERIFY(DeleteObject(hRegPen));
- VERIFY(DeleteObject(hSortBrush));
- }
- }
-
- offset += m_pColumn[ iColumn ]->iCol;
- }
-
- rectColumn.left = offset;
- rectColumn.right = WinRect.right;
-
- ::FillRect(hdc, &rectColumn, (HBRUSH) GetCurrentObject(hdc, OBJ_BRUSH));
- PaintColumn ( iLineNo, iColumn, rectColumn, hdc, pLineData, hHighlightBrush, hHighlightPen );
-
- rectColumn.left = WinRect.left;
- rectColumn.right = WinRect.right;
-
- // if we are dragging we and we don't highlight we need to draw the drag line
- if(m_iDragSelection == m_iTopLine + iLineNo && !HighlightIfDragging() && GetSortColumn() == -1
- && m_iCurrentDropAction != DROPEFFECT_NONE)
- PaintDragLine(hdc, rectColumn);
-
- ::SelectObject ( hdc, hOldFont );
- ReleaseLineData ( pLineData );
- }
-
- void CRDFOutliner::PaintColumn(int iLineNo, int iColumn, LPRECT lpColumnRect,
- HDC hdc, void * pLineData, HBRUSH hHighlightBrush,
- HPEN hHighlightPen)
- {
- if (iColumn < m_iVisColumns)
- {
- const char* lpsz = GetColumnText (m_pColumn[ iColumn ]->iCommand,pLineData);
- HT_Resource theNode = (HT_Resource)pLineData;
- if (theNode && HT_IsSeparator(theNode))
- {
- // Alter the column text name.
- lpsz = NULL;
- }
-
- if ( !RenderData( m_pColumn[iColumn]->iCommand, CRect(lpColumnRect),
- *CDC::FromHandle( hdc ), lpsz) )
- {
- BOOL hasFocus = FALSE;
-
- if (theNode && HT_IsSeparator(theNode))
- {
- // Draw the horizontal line.
- CPen separatorPen;
- separatorPen.CreatePen(PS_SOLID, 1, GetSysColor ( COLOR_WINDOWTEXT ));
-
- HPEN sepPen = (HPEN)separatorPen.GetSafeHandle();
-
- HPEN usePen = IsSelected(iLineNo) ? hHighlightPen : sepPen;
-
- HPEN pOldPen = (HPEN)(::SelectObject(hdc, usePen)); //separatorPen.GetSafeHandle()));
- ::MoveToEx(hdc, lpColumnRect->left, lpColumnRect->top+m_itemHeight/2, NULL);
- ::LineTo(hdc, lpColumnRect->right, lpColumnRect->top+m_itemHeight/2);
- ::SelectObject(hdc, pOldPen);
- }
-
- if (lpsz)
- {
- if ((IsSelected(iLineNo + m_iTopLine) ||
- ((m_iDragSelection == m_iTopLine + iLineNo) && HighlightIfDragging())) &&
- IsSelectedColumn(iColumn))
- {
- hasFocus = HasFocus(iLineNo + m_iTopLine);
-
- if (ViewerHasFocus())
- {
- HBRUSH pOldBrush = (HBRUSH)(::SelectObject ( hdc, hHighlightBrush ));
- HPEN pOldPen = (HPEN)(::SelectObject ( hdc, hHighlightPen ));
- COLORREF cOldText = ::SetTextColor ( hdc, GetSysColor ( COLOR_HIGHLIGHTTEXT ) );
- COLORREF oldColor = ::SetBkColor ( hdc, GetSysColor ( COLOR_HIGHLIGHT ) );
- DrawColumn ( hdc, lpColumnRect, lpsz,
- m_pColumn[ iColumn ]->cropping,
- m_pColumn[ iColumn ]->alignment, hHighlightBrush, hasFocus );
- ::SelectObject(hdc, pOldBrush);
- ::SelectObject(hdc, pOldPen);
- ::SetTextColor ( hdc, cOldText );
- ::SetBkColor ( hdc, oldColor );
-
- }
- else DrawColumn ( hdc, lpColumnRect, lpsz,
- m_pColumn[ iColumn ]->cropping,
- m_pColumn[ iColumn ]->alignment, hHighlightBrush, hasFocus );
- }
- else DrawColumn ( hdc, lpColumnRect, lpsz,
- m_pColumn[ iColumn ]->cropping,
- m_pColumn[ iColumn ]->alignment);
-
- }
- }
- }
- }
-
- void CRDFOutliner::DrawColumn(HDC hdc, LPRECT lpColumnRect, LPCTSTR lpszString,
- CropType_t cropping, AlignType_t alignment, HBRUSH theBrush,
- BOOL hasFocus)
- {
- if (!(lpColumnRect->right - lpColumnRect->left))
- return;
- ASSERT(lpszString);
- int iLength = _tcslen(lpszString);
- if (!iLength)
- return;
-
- UINT dwDTFormat = DT_NOCLIP | DT_NOPREFIX | DT_SINGLELINE | DT_VCENTER;
- switch (alignment) {
- case AlignCenter:
- dwDTFormat |= DT_CENTER;
- break;
- case AlignRight:
- dwDTFormat |= DT_RIGHT;
- break;
- case AlignLeft:
- default:
- dwDTFormat |= DT_LEFT;
- }
-
- UINT dwMoreFormat = 0;
- switch (cropping) {
- case CropCenter:
- dwMoreFormat |= WFE_DT_CROPCENTER;
- break;
- case CropLeft:
- dwMoreFormat |= WFE_DT_CROPLEFT;
- break;
- case CropRight:
- default:
- dwMoreFormat |= WFE_DT_CROPRIGHT;
- break;
- }
-
- CRect textRect(*lpColumnRect);
- CRect bgRect;
- CString theString(lpszString);
-
- // Compute background rectangle
- DrawText(hdc, theString, theString.GetLength(), &bgRect, DT_CALCRECT | dwDTFormat);
- int w = bgRect.Width() + 2*COL_LEFT_MARGIN;
- if (w > textRect.Width())
- w = textRect.Width();
- bgRect.left = textRect.left;
- bgRect.top = textRect.top;
- bgRect.right = bgRect.left + w;
- bgRect.bottom = textRect.bottom;
-
- // Fill the background with the current brush (or frame if we don't have focus)
- if (ViewerHasFocus())
- ::FillRect(hdc, &bgRect, (HBRUSH) GetCurrentObject(hdc, OBJ_BRUSH));
- else if (theBrush)
- ::FrameRect( hdc, &bgRect, theBrush);
-
- // Adjust the text rectangle for the left and right margins
- textRect.left += COL_LEFT_MARGIN;
- textRect.right -= COL_LEFT_MARGIN;
-
- WFE_DrawTextEx( m_iCSID, hdc, (LPTSTR) lpszString, iLength, &textRect, dwDTFormat, dwMoreFormat );
-
- if (hasFocus)
- {
- DrawFocusRect ( hdc, &bgRect );
- }
- }
-
- int CRDFOutliner::DrawPipes ( int iLineNo, int iColNo, int offset, HDC hdc, void * pLineData )
- {
- int iImageWidth = m_pIImage->GetImageWidth ( );
- int iMaxX = offset + m_pColumn[ iColNo ]->iCol;
- int idx;
-
- int iDepth;
- uint32 flags;
- OutlinerAncestorInfo * pAncestor;
- GetTreeInfo ( m_iTopLine + iLineNo, &flags, &iDepth, &pAncestor );
-
- RECT rect;
- rect.left = offset;
- rect.right = rect.left + iImageWidth;
- rect.top = iLineNo * m_itemHeight;
- rect.bottom = rect.top + m_itemHeight;
-
- if ( m_bHasPipes )
- {
- for ( int i = 0; i < iDepth; i++ )
- {
- if ( rect.right <= iMaxX )
- {
- if ( pAncestor && pAncestor[ i ].has_next )
- {
- m_pIImage->DrawTransImage( IDX_VERTPIPE, rect.left, rect.top, hdc );
- }
- else
- {
- ::FillRect(hdc, &rect, (HBRUSH) GetCurrentObject(hdc, OBJ_BRUSH));
- }
- }
- rect.left += iImageWidth;
- rect.right += iImageWidth;
- }
-
- if ( rect.right <= iMaxX ) {
- idx = 0;
- if ( pAncestor ) {
- idx = GetPipeIndex ( pLineData, iDepth, &pAncestor[iDepth] );
- }
- if ( idx ) {
- m_pIImage->DrawTransImage( idx, rect.left, rect.top, hdc );
- } else {
- ::FillRect(hdc, &rect, (HBRUSH) GetCurrentObject(hdc, OBJ_BRUSH));
- }
- }
- rect.left += iImageWidth;
- rect.right += iImageWidth;
- }
- if ( rect.right <= iMaxX ) {
- idx = TranslateIcon (pLineData);
- HT_Resource r = (HT_Resource)pLineData;
- if (idx == HTFE_USE_CUSTOM_IMAGE)
- DrawArbitraryURL(r, rect.left, rect.top, 16, 16, hdc, ::GetBkColor(hdc), this, FALSE);
- else if (idx == HTFE_LOCAL_FILE)
- DrawLocalFileIcon(r, rect.left, rect.top, hdc);
- else m_pIUserImage->DrawTransImage ( idx, rect.left, rect.top, hdc );
- }
- return rect.right;
- }
-
-
- void CRDFOutliner::ColumnsSwapped()
- {
- SetImageColumn(m_pColumn[0]->iCommand);
- }
-
- CRect CRDFOutliner::GetColumnRect(int iLine, int column)
- {
- CRect rectColumn;
- rectColumn.top = (iLine-m_iTopLine) * m_itemHeight;
- rectColumn.bottom = rectColumn.top + m_itemHeight;
- rectColumn.left = rectColumn.right = 0;
-
- int iColumn, offset;
- int iDepth;
- uint32 flags;
- OutlinerAncestorInfo * pAncestor;
- GetTreeInfo ( iLine, &flags, &iDepth, &pAncestor );
-
- for (iColumn = offset = 0; iColumn < m_iVisColumns; iColumn++)
- {
- if (m_pColumn[iColumn]->iCommand == m_idImageCol)
- {
- // Handle the image column (where the indentation is)
- int iImageWidth = m_pIImage->GetImageWidth ( );
- rectColumn.left = (iImageWidth * (iDepth+1)) + OUTLINE_TEXT_OFFSET + m_pIUserImage->GetImageWidth();
- }
- else rectColumn.left = offset;
-
- rectColumn.right = offset + m_pColumn[ iColumn ]->iCol;
-
- if (m_pColumn[iColumn]->iCommand == (UINT)column)
- break;
-
- offset += m_pColumn[ iColumn ]->iCol;
- }
-
- return rectColumn;
- }
-
- char * CRDFOutliner::GetTextEditText(void)
- {
- char str[1000];
-
- if(m_EditField)
- {
- int size = m_EditField->GetWindowText(str, 1000);
- if(size > 0)
- {
- char *newStr = new char[size + 1];
- strcpy(newStr, str);
- return newStr;
- }
- }
-
- return NULL;
-
- }
-
- // Edit window routines
- void CRDFOutliner::EditTextChanged(char* text)
- {
- if (text != NULL)
- {
- // Do stuff
-
- CRDFCommandMap& map = m_Parent->GetColumnCommandMap();
- CRDFColumn* theColumn = (CRDFColumn*)(map.GetCommand(m_nSelectedColumn));
-
- HT_SetNodeData(m_Node, theColumn->GetToken(), theColumn->GetDataType(), text);
-
- delete []text;
- }
- }
-
- void CRDFOutliner::AddTextEdit()
- {
- BOOL bRtn = TRUE;
- if(!m_EditField)
- {
- m_EditField = new CRDFEditWnd(this);
- bRtn = m_EditField->Create(WS_BORDER | ES_AUTOHSCROLL, CRect(0,0,0,0), this, 0);
- }
-
- CRect rect;
- HDC hDC = ::GetDC(m_hWnd);
- HFONT hFont = WFE_GetUIFont(hDC);
- HFONT hOldFont = (HFONT)::SelectObject(hDC, hFont);
- TEXTMETRIC tm;
-
- GetTextMetrics(hDC, &tm);
- int height = tm.tmHeight;
- ::SelectObject(hDC, hOldFont);
- ::ReleaseDC(m_hWnd, hDC);
-
- rect = GetColumnRect(m_iSelection, m_nSelectedColumn);
- rect.bottom+=2; // Adjustment, since the default is a little too small
-
- if (rect.left == rect.right)
- bRtn = FALSE;
-
- if(!bRtn)
- {
- delete m_EditField;
- m_EditField = NULL;
- }
- else
- {
- m_EditField->MoveWindow(rect);
- m_EditField->ShowWindow(SW_SHOW);
- HDC hDC = ::GetDC(m_hWnd);
- HFONT hFont = WFE_GetUIFont(hDC);
- CFont *font = (CFont*) CFont::FromHandle(hFont);
- m_EditField->SetFont(font);
- ::ReleaseDC(m_hWnd, hDC);
- m_EditField->SetFocus();
-
- char* pText = (char*)GetColumnText(m_nSelectedColumn, HT_GetNthItem(m_View, m_iSelection));
-
- if (pText)
- {
- m_EditField->ReplaceSel(pText);
- m_EditField->SetSel(0, strlen(pText), TRUE);
- }
- }
- }
-
- void CRDFOutliner::RemoveTextEdit()
- {
- if(m_EditField)
- {
- m_EditField->ShowWindow(SW_HIDE);
- }
- }
-
- void CRDFOutliner::MoveToNextColumn()
- {
- int oldPos = GetColumnPos((UINT)m_nSelectedColumn);
- oldPos++;
- if (oldPos < (int)GetVisibleColumns())
- {
- m_nSelectedColumn = GetColumnAtPos(oldPos);
- RemoveTextEdit();
- }
- else
- {
- m_nSelectedColumn = GetColumnAtPos(0);
- RemoveTextEdit();
- HT_Resource r = HT_GetNthItem(m_View, m_iSelection);
- if (r)
- HT_SetSelectedState(r, (PRBool)FALSE);
- m_iSelection++;
- m_iFocus = m_iSelection;
- HT_Resource r2 = HT_GetNthItem(m_View, m_iSelection);
- if (!r2)
- {
- m_iFocus = -1;
- m_iSelection = -1;
- m_Node = NULL;
- return;
- }
-
- CRDFCommandMap& map = m_Parent->GetColumnCommandMap();
- CRDFColumn* theColumn = (CRDFColumn*)(map.GetCommand(m_nSelectedColumn));
-
- BOOL isEditable = HT_IsNodeDataEditable(r2, theColumn->GetToken(),
- theColumn->GetDataType());
- if (!isEditable)
- {
- m_iFocus = -1;
- m_iSelection = -1;
- m_Node = NULL;
- return;
- }
-
- HT_SetSelectedState(r2, (PRBool)TRUE);
-
- m_Node = r2;
- }
-
- AddTextEdit();
- }
-
-
- void CRDFOutliner::OnTimer(UINT nID)
- {
- COutliner::OnTimer(nID);
- if (nID == IDT_EDITFOCUS)
- {
- if (m_hEditTimer != 0)
- {
- KillTimer(m_hEditTimer);
- m_hEditTimer = 0;
- }
- AddTextEdit();
- }
- else if (nID == IDT_SPRINGLOAD)
- {
- if (m_hSpringloadTimer != 0)
- {
- KillTimer(m_hSpringloadTimer);
- m_hSpringloadTimer = 0;
-
- if (m_iDragSelection == m_iSpringloadSelection)
- {
- // Open the folder
- HT_Resource r = HT_GetNthItem(m_View, m_iDragSelection);
- if (r != NULL)
- {
- // Pop it open
- HT_SetOpenState(r, (PRBool)TRUE);
-
- // Add this folder to our list of springloaded folders
- m_SpringloadStack.AddHead((void*)r);
- }
- }
- }
- }
- else if (nID == IDT_DRAGRECT)
- {
- if (m_hDragRectTimer != 0)
- {
- KillTimer(m_hDragRectTimer);
- m_hDragRectTimer = 0;
-
- CRect rect;
- GetClientRect(&rect);
-
- if (m_MovePoint.y < m_itemHeight)
- {
- DragRectScroll(TRUE);
- m_hDragRectTimer = SetTimer(IDT_DRAGRECT, GetDragHeartbeat(), NULL);
- }
-
- else if (m_MovePoint.y > rect.bottom - m_itemHeight)
- {
- DragRectScroll(FALSE);
- m_hDragRectTimer = SetTimer(IDT_DRAGRECT, GetDragHeartbeat(), NULL);
- }
- }
- }
- }
-
- // DRAG AND DROP ROUTINES
- int CRDFOutliner::GetDragHeartbeat()
- {
- return RDF_DRAG_HEARTBEAT;
- }
-
- COleDataSource * CRDFOutliner::GetDataSource()
- {
- m_bNeedToClear = FALSE; // Hack. Just leave it here, and don't worry about it.
-
- COleDataSource * pDataSource = new COleDataSource;
-
- HANDLE hString = GlobalAlloc(GMEM_MOVEABLE|GMEM_DDESHARE,1);
- pDataSource->CacheGlobalData(m_cfHTNode, hString);
-
- // The view is sufficient
- RDFGLOBAL_BeginDrag(pDataSource, m_View);
-
- return pDataSource;
- }
-
- void RDFGLOBAL_BeginDrag(COleDataSource* pDataSource, HT_View pView)
- {
- CLIPFORMAT cfBookmark = (CLIPFORMAT) RegisterClipboardFormat( NETSCAPE_HTNODE_FORMAT );
- HGLOBAL hBookmark = GlobalAlloc( GMEM_DDESHARE | GMEM_ZEROINIT, sizeof(HT_View) );
- if( hBookmark )
- {
- HT_View* pBookmark = (HT_View*) GlobalLock( hBookmark );
- *pBookmark = pView;
- GlobalUnlock( hBookmark);
- pDataSource->CacheGlobalData( cfBookmark, hBookmark );
- }
-
- // Get the selected items and set up internet shortcut
- // drag if the item is not a container or separator.
- int selCount = 0;
- HT_Resource r = HT_GetNextSelection(pView, NULL);
- while (r != NULL)
- {
- if (!HT_IsContainer(r) && !HT_IsSeparator(r))
- selCount++;
- r = HT_GetNextSelection(pView, r);
- }
-
- CString* titleArray = new CString[selCount];
- CString* urlArray = new CString[selCount];
- int i = -1;
- r = HT_GetNextSelection(pView, NULL);
- while (r != NULL)
- {
- if (!HT_IsContainer(r) && !HT_IsSeparator(r))
- {
- i++; // Found one
- titleArray[i] = HT_GetNodeName(r);
- urlArray[i] = HT_GetNodeURL(r);
- }
- r = HT_GetNextSelection(pView, r);
- }
- DragMultipleShortcuts(pDataSource, titleArray, urlArray, selCount);
- delete []titleArray;
- delete []urlArray;
- }
-
- void RDFGLOBAL_DragTitleAndURL( COleDataSource *pDataSource, LPCSTR title, LPCSTR url )
- {
- CLIPFORMAT cfBookmark = (CLIPFORMAT) RegisterClipboardFormat( NETSCAPE_BOOKMARK_FORMAT );
- HGLOBAL hBookmark = GlobalAlloc( GMEM_DDESHARE | GMEM_ZEROINIT, sizeof(BOOKMARKITEM) );
- if( hBookmark ) {
- LPBOOKMARKITEM pBookmark = (LPBOOKMARKITEM) GlobalLock( hBookmark );
- PR_snprintf( pBookmark->szAnchor, sizeof(pBookmark->szAnchor),"%s", url );
- PR_snprintf( pBookmark->szText, sizeof(pBookmark->szText),"%s", title );
- GlobalUnlock( hBookmark);
-
- pDataSource->CacheGlobalData( cfBookmark, hBookmark );
- }
-
- HGLOBAL hString = GlobalAlloc( GMEM_MOVEABLE|GMEM_DDESHARE, strlen( url ) + 1 );
- if ( hString ) {
- LPSTR lpszString = (LPSTR) GlobalLock( hString );
- strcpy( lpszString, url );
- GlobalUnlock( hString );
-
- pDataSource->CacheGlobalData( CF_TEXT, hString );
- }
-
- // Do an internet shortcut drag
- DragInternetShortcut(pDataSource, title, url);
- }
-
-
- COutlinerDropTarget* CRDFOutliner::CreateDropTarget()
- {
- return new CRDFDropTarget(this);
- }
-
- BOOL CRDFOutliner::HighlightIfDragging(void)
- {
- if(m_iDragSelection != -1)
- {
- HT_Resource r = HT_GetNthItem(m_View, m_iDragSelection);
- if (r != NULL && HT_IsContainer(r) && (m_iDragSelectionLineThird == 2 || (GetSortColumn() != -1)))
- return TRUE;
- }
- return FALSE;
- }
-
- void CRDFOutliner::PaintDragLine(HDC hdc, CRect &rectColumn)
- {
- HPEN pen = ::CreatePen(PS_SOLID, 1, GetSysColor(COLOR_BTNSHADOW));
- HPEN pOldPen = (HPEN)::SelectObject(hdc, pen);
-
- if(m_iDragSelectionLineThird == 1) {
- #ifdef XP_WIN32
- MoveToEx(hdc, rectColumn.left, rectColumn.top, NULL);
- #else
- MoveTo(hdc, rectColumn.left, rectColumn.top);
- #endif
- LineTo(hdc, rectColumn.right, rectColumn.top);
- }
- else if(m_iDragSelectionLineThird == 3){
- #ifdef XP_WIN32
- MoveToEx(hdc, rectColumn.left, rectColumn.bottom -1, NULL);
- #else
- MoveTo(hdc, rectColumn.left, rectColumn.bottom - 1);
- #endif
- LineTo(hdc, rectColumn.right, rectColumn.bottom - 1);
- }
-
- ::SelectObject(hdc, pOldPen);
- ::DeleteObject(pen);
- }
-
- void CRDFOutliner::AcceptDrop( int iLineNo, COleDataObject *pDataObject, DROPEFFECT dropEffect )
- {
- HT_Resource theNode = NULL;
- if (iLineNo >= 0)
- theNode = HT_GetNthItem(m_View, iLineNo);
- if (theNode == NULL)
- theNode = HT_TopNode(m_View);
-
- RDFGLOBAL_PerformDrop(pDataObject, theNode, m_iDragSelectionLineThird);
-
- m_SpringloadStack.RemoveAll();
- }
-
- void RDFGLOBAL_PerformDrop(COleDataObject* pDataObject, HT_Resource theNode, int dragFraction)
- {
- if(!pDataObject)
- return;
-
- CLIPFORMAT cfHTNode = (CLIPFORMAT)RegisterClipboardFormat(NETSCAPE_HTNODE_FORMAT);
- CLIPFORMAT cfBookmark = (CLIPFORMAT)RegisterClipboardFormat(NETSCAPE_BOOKMARK_FORMAT);
-
- if(!pDataObject->IsDataAvailable(CF_TEXT) &&
- !pDataObject->IsDataAvailable(cfHTNode) &&
- !pDataObject->IsDataAvailable(cfBookmark) &&
- !pDataObject->IsDataAvailable(CF_HDROP))
- return;
-
- if(pDataObject->IsDataAvailable(cfHTNode))
- {
- HT_View pView = NULL;
-
- HGLOBAL hBookmark = pDataObject->GetGlobalData(cfHTNode);
- HT_View* pBookmark = (HT_View*)GlobalLock(hBookmark);
- ASSERT(pBookmark);
- pView = *pBookmark;
- GlobalUnlock(hBookmark);
-
- DropPosition dropPosition = RDFGLOBAL_TranslateDropPosition(theNode, dragFraction);
-
- HT_Resource node = NULL;
- while (node = (HT_GetNextSelection(pView, node)))
- {
- if (dropPosition == DROP_BEFORE)
- HT_DropHTRAtPos(theNode, node, (PRBool)TRUE);
- else if (dropPosition == DROP_AFTER)
- HT_DropHTRAtPos(theNode, node, (PRBool)FALSE);
- else if (dropPosition == DROP_ON)
- HT_DropHTROn(theNode, node);
- else HT_DropHTROn(HT_GetParent(theNode), node);
- }
- }
- else if(pDataObject->IsDataAvailable(cfBookmark))
- {
- HGLOBAL hBookmark = pDataObject->GetGlobalData(cfBookmark);
- LPBOOKMARKITEM pBookmark = (LPBOOKMARKITEM)GlobalLock(hBookmark);
- ASSERT(pBookmark);
- CString title(pBookmark->szText);
- CString url(pBookmark->szAnchor);
-
- GlobalUnlock(hBookmark);
-
- DropPosition dropPosition = RDFGLOBAL_TranslateDropPosition(theNode, dragFraction);
- if (dropPosition == DROP_BEFORE)
- HT_DropURLAndTitleAtPos(theNode, (char*)(const char*)url, (char*)(const char*)title, (PRBool)TRUE);
- else if (dropPosition == DROP_AFTER)
- HT_DropURLAndTitleAtPos(theNode, (char*)(const char*)url, (char*)(const char*)title, (PRBool)FALSE);
- else if (dropPosition == DROP_ON)
- HT_DropURLAndTitleOn(theNode, (char*)(const char*)url, (char*)(const char*)title);
- else HT_DropURLAndTitleOn(HT_GetParent(theNode), (char*)(const char*)url, (char*)(const char*)title);
- }
- else if (pDataObject->IsDataAvailable(CF_HDROP))
- {
- HGLOBAL hGlobal = pDataObject->GetGlobalData(CF_HDROP);
- HDROP hDropInfo = (HDROP)hGlobal;
-
- // Get the number of files dropped
- int i_num = ::DragQueryFile(hDropInfo, (UINT)-1, NULL, 0);
-
- char ca_drop[_MAX_PATH];
- CString csUnescapedUrl, csEscapedUrl;
-
- int i_loop;
- for(i_loop = 0; i_loop < i_num; i_loop++)
- {
- ::DragQueryFile(hDropInfo, i_loop, ca_drop, _MAX_PATH);
-
- // Convert to an acceptable URL.
- WFE_ConvertFile2Url(csUnescapedUrl, ca_drop);
- csEscapedUrl = WFE_EscapeURL(csUnescapedUrl);
-
- // Tell HT about the drop
- DropPosition dropPosition = RDFGLOBAL_TranslateDropPosition(theNode, dragFraction);
- if (dropPosition == DROP_BEFORE)
- HT_DropURLAtPos(theNode, (char*)(const char*)csEscapedUrl, (PRBool)TRUE);
- else if (dropPosition == DROP_AFTER)
- HT_DropURLAtPos(theNode, (char*)(const char*)csEscapedUrl, (PRBool)FALSE);
- else if (dropPosition == DROP_ON)
- HT_DropURLOn(theNode, (char*)(const char*)csEscapedUrl);
- else HT_DropURLOn(HT_GetParent(theNode), (char*)(const char*)csEscapedUrl);
- }
- GlobalUnlock(hGlobal);
- }
- else if (pDataObject->IsDataAvailable(CF_TEXT))
- {
- HGLOBAL hString = pDataObject->GetGlobalData(CF_TEXT);
- char * pAddress = (char*)GlobalLock(hString);
- CString url(pAddress);
- GlobalUnlock(hString);
-
- DropPosition dropPosition = RDFGLOBAL_TranslateDropPosition(theNode, dragFraction);
- if (dropPosition == DROP_BEFORE)
- HT_DropURLAtPos(theNode, (char*)(const char*)url, (PRBool)TRUE);
- else if (dropPosition == DROP_AFTER)
- HT_DropURLAtPos(theNode, (char*)(const char*)url, (PRBool)FALSE);
- else if (dropPosition == DROP_ON)
- HT_DropURLOn(theNode, (char*)(const char*)url);
- else HT_DropURLOn(HT_GetParent(theNode), (char*)(const char*)url);
- }
-
- }
-
- void CRDFOutliner::InitializeClipFormats(void)
- {
- m_cfHTNode = (CLIPFORMAT)RegisterClipboardFormat(NETSCAPE_HTNODE_FORMAT);
- m_cfBookmark = (CLIPFORMAT)RegisterClipboardFormat(NETSCAPE_BOOKMARK_FORMAT);
-
- m_clipFormatArray[0] = m_cfHTNode;
- m_clipFormatArray[1] = m_cfBookmark;
- m_clipFormatArray[2] = CF_HDROP;
- m_clipFormatArray[3] = CF_TEXT;
- m_clipFormatArray[4] = 0;
- }
-
- CLIPFORMAT * CRDFOutliner::GetClipFormatList(void)
- {
- return m_clipFormatArray;
- }
-
- DROPEFFECT CRDFOutliner::DropSelect(int iLineNo, COleDataObject *object)
- {
- HT_Resource r = NULL;
- if (iLineNo >= 0)
- r = HT_GetNthItem(m_View, iLineNo);
- if (r == NULL)
- r = HT_TopNode(m_View);
-
- DROPEFFECT answer = RDFGLOBAL_TranslateDropAction(r, object,
- HT_IsContainer(r) ? m_iDragSelectionLineThird : m_iDragSelectionLineHalf);
-
- m_iCurrentDropAction = answer;
-
- if (iLineNo == m_iDragSelection && !m_bDragSectionChanged)
- return answer;
-
- if (m_iDragSelection != -1)
- InvalidateLine (m_iDragSelection);
-
- m_iDragSelection = iLineNo;
- InvalidateLine (m_iDragSelection);
-
- // Start the hover timer for folder springloading
-
- if (m_iDragSelection != -1)
- {
- if (r != NULL && HT_IsContainer(r) && !HT_IsContainerOpen(r) && m_iCurrentDropAction != DROPEFFECT_NONE)
- {
- m_iSpringloadSelection = m_iDragSelection;
- m_hSpringloadTimer = SetTimer(IDT_SPRINGLOAD, SPRINGLOAD_DELAY, NULL);
- }
- }
-
- // Check for springload closing time
- if (!m_SpringloadStack.IsEmpty())
- {
- // There are some springloaded folders that might need to be closed.
- POSITION p = m_SpringloadStack.GetHeadPosition();
- HT_Resource r = (HT_Resource)m_SpringloadStack.GetNext(p);
-
- int count = (int)HT_GetCountVisibleChildren(r);
- int index = (int)HT_GetNodeIndex(m_View, r);
-
- if (m_iDragSelection < index ||
- m_iDragSelection == -1 ||
- m_iDragSelection > index + count)
- {
- m_SpringloadStack.RemoveHead();
- HT_SetOpenState(r, (PRBool)FALSE);
-
- if (m_iDragSelection > index + count)
- m_iDragSelection -= count;
- }
- }
- return answer;
- }
-
- DropPosition RDFGLOBAL_TranslateDropPosition(HT_Resource dropTarget, int position)
- {
- HT_Resource targetParent = HT_GetParent(dropTarget);
-
- BOOL sortImposed = !HT_ContainerSupportsNaturalOrderSort(targetParent); // Is a sort imposed on the parent?
-
- DropPosition res;
- if (targetParent == NULL) // Top Node of the view. Can't drop before or after.
- res = DROP_ON;
- else if (!sortImposed) // Can only drop/before or after if sort is not imposed on the view.
- {
- if (position == 1)
- {
- // Drop before
- res = DROP_BEFORE; // In upper half of selection (for non-containers) or bottom third
- // of selection (for containers). Drop before.
- }
- else if (position == 3 || (position == 2 && !HT_IsContainer(dropTarget)))
- {
- // Drop after if we're in the bottom half (for non-containers) or bottom third (for containers)
- res = DROP_AFTER; // In lower third of selection. Drop after.
- }
- else res = DROP_ON; // We're a container and right in the middle of selection. Drop on.
- }
- else if (HT_IsContainer(dropTarget))
- {
- res = DROP_ON; // If a sort is imposed and we're over a container, drop into that.
- }
- else res = DROP_ON_PARENT; // Otherwise, we'll drop into the parent container and let the sort
- // put it where it's supposed to go.
-
- return res;
- }
-
- DROPEFFECT RDFGLOBAL_TranslateDropAction(HT_Resource dropTarget, COleDataObject* pDataObject,
- int position)
- {
- HT_DropAction res;
- CLIPFORMAT cfHTNode = (CLIPFORMAT)RegisterClipboardFormat(NETSCAPE_HTNODE_FORMAT);
- CLIPFORMAT cfBookmark = (CLIPFORMAT)RegisterClipboardFormat(NETSCAPE_BOOKMARK_FORMAT);
-
- if (dropTarget == NULL)
- return DROPEFFECT_NONE;
-
- DropPosition dropPosition = RDFGLOBAL_TranslateDropPosition(dropTarget, position);
-
- if(pDataObject->IsDataAvailable(cfHTNode))
- {
- HT_View pView = NULL;
-
- HGLOBAL hBookmark = pDataObject->GetGlobalData(cfHTNode);
- HT_View* pBookmark = (HT_View*)GlobalLock(hBookmark);
- ASSERT(pBookmark);
- pView = *pBookmark;
- GlobalUnlock(hBookmark);
-
- HT_Resource node = HT_GetNextSelection(pView, NULL);
- while (node != NULL)
- {
- HT_DropAction res2;
- if (dropPosition == DROP_BEFORE)
- res2 = HT_CanDropHTRAtPos(dropTarget, node, (PRBool)TRUE);
- else if (dropPosition == DROP_AFTER)
- res2 = HT_CanDropHTRAtPos(dropTarget, node, (PRBool)FALSE);
- else if (dropPosition == DROP_ON)
- res2 = HT_CanDropHTROn(dropTarget, node);
- else res2 = HT_CanDropHTROn(HT_GetParent(dropTarget), node);
-
- if (res2 == DROP_NOT_ALLOWED)
- {
- res = DROP_NOT_ALLOWED;
- break;
- }
-
- res = res2;
-
- node = HT_GetNextSelection(pView, node);
- }
- }
- else if (pDataObject->IsDataAvailable(cfBookmark))
- {
- HGLOBAL hBookmark = pDataObject->GetGlobalData(cfBookmark);
- LPBOOKMARKITEM pBookmark = (LPBOOKMARKITEM)GlobalLock(hBookmark);
- ASSERT(pBookmark);
- CString title(pBookmark->szText);
- CString url(pBookmark->szAnchor);
-
- GlobalUnlock(hBookmark);
-
- if (dropPosition == DROP_BEFORE)
- res = HT_CanDropURLAtPos(dropTarget, (char*)(const char*)url, (PRBool)TRUE);
- else if (dropPosition == DROP_AFTER)
- res = HT_CanDropURLAtPos(dropTarget, (char*)(const char*)url, (PRBool)FALSE);
- else if (dropPosition == DROP_ON)
- res = HT_CanDropURLOn(dropTarget, (char*)(const char*)url);
- else res = HT_CanDropURLOn(HT_GetParent(dropTarget), (char*)(const char*)url);
- }
- else if (pDataObject->IsDataAvailable(CF_HDROP))
- {
- HGLOBAL hGlobal = pDataObject->GetGlobalData(CF_HDROP);
- HDROP hDropInfo = (HDROP)hGlobal;
-
- // Get the number of files dropped
- int i_num = ::DragQueryFile(hDropInfo, (UINT)-1, NULL, 0);
-
- char ca_drop[_MAX_PATH];
- CString csUnescapedUrl, csEscapedUrl;
-
- int i_loop;
- HT_DropAction res2;
- for(i_loop = 0; i_loop < i_num; i_loop++)
- {
- ::DragQueryFile(hDropInfo, i_loop, ca_drop, _MAX_PATH);
-
- // Convert to an acceptable URL.
- WFE_ConvertFile2Url(csUnescapedUrl, ca_drop);
- csEscapedUrl = WFE_EscapeURL(csUnescapedUrl);
-
- // Tell HT about the drop
- if (dropPosition == DROP_BEFORE)
- res2 = HT_CanDropURLAtPos(dropTarget, (char*)(const char*)csEscapedUrl, (PRBool)TRUE);
- else if (dropPosition == DROP_AFTER)
- res2 = HT_CanDropURLAtPos(dropTarget, (char*)(const char*)csEscapedUrl, (PRBool)FALSE);
- else if (dropPosition == DROP_ON)
- res2 = HT_CanDropURLOn(dropTarget, (char*)(const char*)csEscapedUrl);
- else res2 = HT_CanDropURLOn(HT_GetParent(dropTarget), (char*)(const char*)csEscapedUrl);
-
- if (res2 == DROP_NOT_ALLOWED)
- {
- res = DROP_NOT_ALLOWED;
- break;
- }
-
- res = res2;
- }
- GlobalUnlock(hGlobal);
- }
- else if (pDataObject->IsDataAvailable(CF_TEXT))
- {
- HGLOBAL hString = pDataObject->GetGlobalData(CF_TEXT);
- char * pAddress = (char*)GlobalLock(hString);
- CString url(pAddress);
- GlobalUnlock(hString);
-
- if (dropPosition == DROP_BEFORE)
- res = HT_CanDropURLAtPos(dropTarget, (char*)(const char*)url, (PRBool)TRUE);
- else if (dropPosition == DROP_AFTER)
- res = HT_CanDropURLAtPos(dropTarget, (char*)(const char*)url, (PRBool)FALSE);
- else if (dropPosition == DROP_ON)
- res = HT_CanDropURLOn(dropTarget, (char*)(const char*)url);
- else res = HT_CanDropURLOn(HT_GetParent(dropTarget), (char*)(const char*)url);
- }
-
- switch (res)
- {
- case DROP_NOT_ALLOWED:
- return DROPEFFECT_NONE;
- case COPY_MOVE_CONTENT:
- case COPY_MOVE_LINK:
- return DROPEFFECT_MOVE;
- default:
- return DROPEFFECT_COPY;
- }
- }
-
- // RDFDropTarget Overridden Funcs
-
- BOOL CRDFDropTarget::OnDrop(
- CWnd* pWnd, COleDataObject* pDataObject, DROPEFFECT dropEffect, CPoint point)
- {
- m_dwOldTicks = 0;
-
- CRDFOutliner* pOutliner = (CRDFOutliner*)m_pOutliner;
-
- if(!pDataObject || !pOutliner)
- return(FALSE);
-
- if (!pOutliner->RecognizedFormat(pDataObject))
- return FALSE;
-
- pOutliner->m_ptHit = point;
-
- pOutliner->AcceptDrop( point.y < 0 ? -1 : pOutliner->GetDropLine(), pDataObject, dropEffect);
- pOutliner->EndDropSelect();
-
- return(TRUE);
- }
-
- DROPEFFECT CRDFDropTarget::OnDragEnter(
- CWnd* pWnd, COleDataObject* pDataObject, DWORD dwKeyState, CPoint point)
- {
- DROPEFFECT res = OnDragOver(pWnd, pDataObject, dwKeyState, point);
-
- CRDFOutliner* pOutliner = (CRDFOutliner*)m_pOutliner;
- pOutliner->m_bDataSourceInWindow = TRUE;
-
- if ( res != DROPEFFECT_NONE && point.y >= 0) {
- m_pOutliner->Invalidate();
- m_pOutliner->UpdateWindow();
- }
-
- return res;
- }
-
- DROPEFFECT CRDFDropTarget::OnDragOver(
- CWnd* pWnd, COleDataObject* pDataObject, DWORD dwKeyState, CPoint point)
- {
- DROPEFFECT effect = DROPEFFECT_NONE;
- CRDFOutliner* pOutliner = (CRDFOutliner*)m_pOutliner;
-
- if (pOutliner->RecognizedFormat(pDataObject)) {
- RECT rect;
- pWnd->GetClientRect(&rect);
-
- if ( point.y < pOutliner->m_itemHeight && point.y >= 0) {
- DragScroll(TRUE);
- effect |= DROPEFFECT_SCROLL;
- } else if ( point.y > ( rect.bottom - pOutliner->m_itemHeight ) ) {
- DragScroll(FALSE);
- effect |= DROPEFFECT_SCROLL;
- } else {
- m_dwOldTicks = 0;
- }
-
- pOutliner->m_ptHit = point;
-
- effect |= pOutliner->DropSelect(point.y < 0 ? -1 : pOutliner->LineFromPoint(point), pDataObject);
-
- // Default is to move
- if ( ( effect & DROPEFFECT_MOVE) && (dwKeyState & MK_CONTROL) )
- effect = (effect & ~DROPEFFECT_MOVE) | DROPEFFECT_COPY;
- }
- return effect;
- }
-
- void CRDFDropTarget::OnDragLeave(CWnd* pWnd)
- {
- CRDFOutliner* pOutliner = (CRDFOutliner*)m_pOutliner;
- for (POSITION p = pOutliner->m_SpringloadStack.GetHeadPosition(); p != NULL; )
- {
- HT_Resource r = (HT_Resource)(pOutliner->m_SpringloadStack.GetNext(p));
- HT_SetOpenState(r, (PRBool)FALSE);
- }
-
- pOutliner->m_SpringloadStack.RemoveAll();
-
- pOutliner->m_bDataSourceInWindow = FALSE;
-
- pOutliner->m_iDragSelection = -1;
-
- pOutliner->Invalidate();
- pOutliner->UpdateWindow();
- }
-
- // ========================================================================
-
- BEGIN_MESSAGE_MAP(CRDFOutlinerParent,COutlinerParent)
- ON_WM_DESTROY()
- END_MESSAGE_MAP()
-
- CRDFOutlinerParent::CRDFOutlinerParent(HT_Pane thePane, HT_View theView)
- {
- CRDFOutliner* theOutliner = new CRDFOutliner(thePane, theView, this);
- m_pOutliner = theOutliner;
- }
-
- BOOL CRDFOutlinerParent::PreCreateWindow(CREATESTRUCT& cs)
- {
- BOOL bRet = CWnd::PreCreateWindow(cs);
-
- //#ifdef XP_WIN32
- // cs.dwExStyle |= WS_EX_CLIENTEDGE;
- //#endif
- return bRet;
- }
-
- void CRDFOutlinerParent::OnDestroy()
- {
- // Save prefs might happen here...
- COutlinerParent::OnDestroy();
- }
-
- COutliner* CRDFOutlinerParent::GetOutliner ( )
- {
- return m_pOutliner;
- }
-
- void CRDFOutlinerParent::CreateColumns ( void )
- {
- // Retrieve the columns from RDF
- CRDFOutliner* theOutliner = (CRDFOutliner*)m_pOutliner;
- HT_View theView = theOutliner->GetHTView();
-
- HT_Cursor columnCursor = HT_NewColumnCursor(theView);
- char* columnName;
- uint32 columnWidth;
- void* token;
- uint32 tokenType;
- UINT index = 0;
- while (HT_GetNextColumn(columnCursor, &columnName, &columnWidth, &token, &tokenType))
- {
- // We have retrieved a new column. Contruct a front end column object
- CRDFColumn* newColumn = new CRDFColumn(columnName, columnWidth, token, tokenType);
- index = (UINT)columnMap.AddCommand(newColumn);
- m_pOutliner->AddColumn(columnName, index, 5000, 10000, ColumnVariable, 3000);
- }
- HT_DeleteColumnCursor(columnCursor);
- m_pOutliner->SetVisibleColumns(1); // For now... TODO: Get visible/invisible info!
- m_pOutliner->SetImageColumn(0);
- }
-
- BOOL CRDFOutlinerParent::RenderData( int iColumn, CRect & rect, CDC &dc, LPCTSTR text )
- {
- CRDFOutliner *pOutliner = (CRDFOutliner *)m_pOutliner;
-
- if( !pOutliner )
- {
- return FALSE;
- }
-
- if( pOutliner->GetSortType() == HT_NO_SORT)
- {
- return FALSE;
- }
-
- MSG_COMMAND_CHECK_STATE sortType = (iColumn == pOutliner->GetSortColumn()) ? MSG_Checked : MSG_Unchecked;
-
- if( sortType != MSG_Checked )
- {
- return FALSE;
- }
-
- int idxImage = (pOutliner->GetSortType() % 2) ? IDX_SORTINDICATORUP : IDX_SORTINDICATORDOWN;
-
- UINT dwDTFormat = DT_NOCLIP | DT_NOPREFIX | DT_SINGLELINE | DT_VCENTER;
- RECT rectText = rect;
- rectText.left += 4;
- rectText.right -= 5;
-
- rectText.right -= 22;
- m_pIImage->DrawTransImage( idxImage,
- rectText.right + 4,
- (rect.top + rect.bottom) / 2 - 4,
- &dc );
-
- WFE_DrawTextEx( 0, dc.m_hDC, (LPTSTR) text, -1,
- &rectText, dwDTFormat, WFE_DT_CROPRIGHT );
-
- return TRUE;
- }
-
- BOOL CRDFOutlinerParent::ColumnCommand( int iColumn )
- {
- CRDFOutliner *pOutliner = (CRDFOutliner *)m_pOutliner;
-
- int enSortType = pOutliner->GetSortType();
- if (pOutliner->GetSortColumn() != iColumn)
- {
- // May need to resort in back end (not sure)
- enSortType = HT_NO_SORT;
- }
-
- if (enSortType == HT_SORT_ASCENDING)
- enSortType = HT_SORT_DESCENDING;
- else if (enSortType == HT_SORT_DESCENDING)
- enSortType = HT_NO_SORT;
- else enSortType = HT_SORT_ASCENDING;
-
- pOutliner->SetSortType( enSortType );
-
- if (enSortType == HT_NO_SORT)
- pOutliner->SetSortColumn(-1);
- else pOutliner->SetSortColumn( iColumn );
-
- CRDFColumn* theColumn = (CRDFColumn*)(columnMap.GetCommand(iColumn));
-
- BOOL sort = TRUE;
- if (enSortType == HT_SORT_ASCENDING)
- sort = FALSE;
-
- pOutliner->SetSelectedColumn(pOutliner->m_pColumn[ iColumn ]->iCommand);
-
- Invalidate();
-
- HT_SetSortColumn(pOutliner->GetHTView(),
- enSortType == HT_NO_SORT ? NULL : theColumn->GetToken(),
- theColumn->GetDataType(), (PRBool)sort);
-
- return TRUE;
- }
-
- void CRDFOutlinerParent::Initialize()
- {
- CreateColumns ( );
-
- CRDFOutliner* theOutliner = (CRDFOutliner*)m_pOutliner;
- m_pOutliner->SetTotalLines( HT_GetItemListCount(theOutliner->GetHTView()) );
- }
-
- // =======================================================================
- // RDFEditWnd - Class that controls the in-place editing of column values
- // =======================================================================
-
- BOOL CRDFEditWnd::PreTranslateMessage ( MSG * msg )
- {
- if ( msg->message == WM_KEYDOWN)
- {
- switch(msg->wParam)
- {
- case VK_RETURN:
- {
- m_pOwner->EditTextChanged(m_pOwner->GetTextEditText());
- m_pOwner->RemoveTextEdit();
- return TRUE;
-
- }
- case VK_ESCAPE:
- m_pOwner->RemoveTextEdit();
- break;
- case VK_TAB:
- m_pOwner->EditTextChanged(m_pOwner->GetTextEditText());
- m_pOwner->MoveToNextColumn();
- return TRUE;
- }
- }
-
- return CEdit::PreTranslateMessage ( msg );
- }
-
- //////////////////////////////////////////////////////////////////////////
- // Messages for CRDFEditWnd
- //////////////////////////////////////////////////////////////////////////
-
- BEGIN_MESSAGE_MAP(CRDFEditWnd, CEdit)
- //{{AFX_MSG_MAP(CWnd)
- ON_WM_DESTROY()
- ON_WM_SETFOCUS()
- ON_WM_KILLFOCUS()
- //}}AFX_MSG_MAP
- END_MESSAGE_MAP()
-
- void CRDFEditWnd::OnDestroy( )
- {
- delete this;
-
- }
-
- void CRDFEditWnd::OnSetFocus(CWnd* pOldWnd)
- {
- CEdit::OnSetFocus(pOldWnd);
- }
-
- void CRDFEditWnd::OnKillFocus( CWnd* pNewWnd )
- {
- CEdit::OnKillFocus(pNewWnd);
- m_pOwner->FocusCheck(pNewWnd, FALSE);
- m_pOwner->RemoveTextEdit();
- }
-
- // =========================================================================
- // RDF Content View
- IMPLEMENT_DYNAMIC(CRDFContentView, CContentView)
- BEGIN_MESSAGE_MAP(CRDFContentView, CContentView)
- //{{AFX_MSG_MAP(CMainFrame)
- // NOTE - the ClassWizard will add and remove mapping macros here.
- // DO NOT EDIT what you see in these blocks of generated code !
- ON_MESSAGE(WM_NAVCENTER_QUERYPOSITION, OnNavCenterQueryPosition)
- ON_WM_CREATE()
- ON_WM_SIZE()
- ON_WM_SETFOCUS()
- //}}AFX_MSG_MAP
- END_MESSAGE_MAP()
-
- LRESULT CRDFContentView::OnNavCenterQueryPosition(WPARAM wParam, LPARAM lParam)
- {
- NAVCENTPOS *pPos = (NAVCENTPOS *)lParam;
-
- // We like being in the middle.
- pPos->m_iYDisposition = 0;
-
- // We like being this many units in size.
- pPos->m_iYVector = 200;
-
- // Handled.
- return(NULL);
- }
-
- BOOL CRDFContentView::PreCreateWindow(CREATESTRUCT& cs)
- {
- cs.style |= WS_CLIPSIBLINGS | WS_CLIPCHILDREN;
-
- return CContentView::PreCreateWindow(cs);
- }
-
- void CRDFContentView::OnDraw ( CDC * pDC )
- {
- }
-
- int CRDFContentView::OnCreate ( LPCREATESTRUCT lpCreateStruct )
- {
- int iRetVal = CContentView::OnCreate ( lpCreateStruct );
- LPCTSTR lpszClass = AfxRegisterWndClass( CS_VREDRAW, ::LoadCursor(NULL, IDC_ARROW));
- m_pOutlinerParent->Create( lpszClass, _T("NSOutlinerParent"),
- WS_VISIBLE|WS_CHILD|WS_CLIPCHILDREN,
- CRect(0,0,100,100), this, 101 );
- return iRetVal;
- }
-
- void CRDFContentView::OnSize ( UINT nType, int cx, int cy )
- {
- CView::OnSize ( nType, cx, cy );
- if (IsWindow(m_pOutlinerParent->m_hWnd))
- {
- m_pOutlinerParent->MoveWindow ( 0, 0, cx, cy );
- }
- }
-
- void CRDFContentView::InvalidateOutlinerParent()
- {
- // COutliner* outliner = m_pOutlinerParent->GetOutliner();
- // outliner->SqueezeColumns(-1, 0, TRUE);
- }
-
- void CRDFContentView::OnSetFocus ( CWnd * pOldWnd )
- {
- m_pOutlinerParent->SetFocus ( );
- }
-
- // Functionality for the RDF Tree Embedded in HTML (Added 3/10/98 by Dave Hyatt).
-
- // The event handler. Only cares about tree events, so we'll just pass everything to the
- // tree view.
- void embeddedTreeNotifyProcedure (HT_Notification ns, HT_Resource n, HT_Event whatHappened)
- {
- CRDFOutliner* theOutliner = (CRDFOutliner*)HT_GetViewFEData(HT_GetView(n));
- if (theOutliner)
- theOutliner->HandleEvent(ns, n, whatHappened);
- }
-
- void CRDFContentView::DisplayRDFTree(CWnd* pParent, int width, int height, RDF_Resource rdfResource)
- {
- HT_Notification ns = new HT_NotificationStruct;
- ns->notifyProc = embeddedTreeNotifyProcedure;
- ns->data = NULL;
-
- // Construct the pane and give it our notification struct
- HT_Pane thePane = HT_PaneFromResource(rdfResource, ns, PR_FALSE);
-
- // Build our FE windows.
- CRDFOutlinerParent* newParent = new CRDFOutlinerParent(thePane, HT_GetSelectedView(thePane));
- CRDFContentView* newView = new CRDFContentView(newParent);
-
- // Create the windows
- CRect rClient(0, 0, width, height);
- newView->Create( NULL, "", WS_CHILD | WS_VISIBLE, rClient, pParent, NC_IDW_OUTLINER);
-
- // Initialize the columns, etc.
- newParent->Initialize();
-
- // Set our FE data to be the outliner.
- HT_SetViewFEData(HT_GetSelectedView(thePane), newParent->GetOutliner());
- }
-
- // Function to grab an RDF context
-
- extern "C" MWContext* FE_GetRDFContext(void)
- {
- MWContext *pRetval = NULL;
-
- if(theApp.m_pRDFCX)
- {
- pRetval = theApp.m_pRDFCX->GetContext();
- }
-
- return(pRetval);
- }
-
-
- // The context's GetDialogOwner() function.
- CWnd* CRDFCX::GetDialogOwner() const
- {
- if (m_pCurrentRDFWindow == NULL)
- return CWnd::GetDesktopWindow();
- return m_pCurrentRDFWindow->GetTopLevelFrame();
- }
-
-
- /////////////////////////////////////////////////////////////////////////////
- /////////////////////////////////////////////////////////////////////////////
- /////////////////////////////////////////////////////////////////////////////
- // CDialogPRMT dialog
-
- void stdPrint (void* data, char* str) {
- fprintf((FILE*)data, str);
- }
-
- CExportRDF::CExportRDF(CWnd* pParent /*=NULL*/)
- : CDialog(CExportRDF::IDD, pParent)
- {
- m_csTitle = _T("");
-
- //{{AFX_DATA_INIT(CDialogPRMT)
- m_csAns = "";
- //}}AFX_DATA_INIT
- }
-
- void CExportRDF::DoDataExchange(CDataExchange* pDX)
- {
- CDialog::DoDataExchange(pDX);
- //{{AFX_DATA_MAP(CDialogPRMT)
- DDX_Text(pDX, IDC_PROMPT_ANS, m_csAns);
- //}}AFX_DATA_MAP
- }
-
- BEGIN_MESSAGE_MAP(CExportRDF, CDialog)
- //{{AFX_MSG_MAP(CDialogPRMT)
- // NOTE: the ClassWizard will add message map macros here
- //}}AFX_MSG_MAP
- END_MESSAGE_MAP()
-