|
This is patch to bug #723
titled "AbiWord crashes when trying to change printing preferences on HP
710"
The bug happens on Windows95 and probably on
Windows98, with printer driver made by HP. The driver is made to work with
Windows 3.1, Windows95 and Windows98. the bug does not happen on WindowsNT, it
is a different driver.
Abiword, with my HP Deskjet 692C printer had the
same problem.
During testing, I found that if you define a
printer to print to a file, it raised an assertion when the file name chooser
dialog was cancelled. Since it is the user privilege to cancel, I replaced the
assertion with an "if" structure.
I tested the patch on Windows95 and
WindowsNT.
Gilles Saint-Denis
|
Index: abi/src/af/util/win/ut_Win32Timer.cpp
===================================================================
RCS file: /cvsroot/abi/src/af/util/win/ut_Win32Timer.cpp,v
retrieving revision 1.8
diff -u -r1.8 ut_Win32Timer.cpp
--- abi/src/af/util/win/ut_Win32Timer.cpp 1999/02/22 18:51:39 1.8
+++ abi/src/af/util/win/ut_Win32Timer.cpp 2000/10/16 23:55:19
@@ -44,6 +44,8 @@
GR_Win32Graphics * pWinG = static_cast<GR_Win32Graphics *>(pG);
m_hWnd = ((pWinG) ? pWinG->getHwnd() : 0);
+
+ setIdentifier(_createIdentifier());
}
@@ -69,11 +71,18 @@
{
// set the freq and start firing events.
- // NOTE: Win95 does not support TimerProc. WinNT does support TimerProc.
- // NOTE: I'm going to pass enough information so that we should be able
- // NOTE: to get back to our timer callback regardless of the OS.
+ // WinNT support TimerProc. Win95 also use it, but the documentation
+ // say it also need a message dispatch procedure for WM_TIMER.
+ // I'm going to pass enough information so that we should be able
+ // to get back to our timer callback regardless of the OS.
+ // SetTimer return the timer identifier. When we create a new timer
+ // and the window handle is zero, the function generate an id
+ // regardless of the one supplied.
+ // Identifier need to be 16 bits because certains printers drivers are
+ // made to work with "Windows 3.1" ! Theses drivers filter out bits
+ // higher than 16.
- UINT idTimer = SetTimer(m_hWnd, (UINT)this, iMilliseconds, (TIMERPROC)
Global_Win32TimerProc);
+ UINT idTimer = SetTimer(m_hWnd, (UINT) getIdentifier(), iMilliseconds,
+(TIMERPROC) Global_Win32TimerProc);
if (idTimer == 0)
return -1;
@@ -105,4 +114,47 @@
if (!m_bStarted)
set(m_iMilliseconds);
+}
+
+int UT_Win32Timer::_compareIdentifiers(const void* p1, const void* p2)
+{
+ UT_Win32Timer** ppTimer1 = (UT_Win32Timer**) p1;
+ UT_Win32Timer** ppTimer2 = (UT_Win32Timer**) p2;
+
+ if ((*ppTimer1)->getIdentifier() < (*ppTimer2)->getIdentifier())
+ {
+ return -1;
+ }
+
+ if ((*ppTimer1)->getIdentifier() > (*ppTimer2)->getIdentifier())
+ {
+ return 1;
+ }
+
+ return 0;
+}
+
+UT_uint32 UT_Win32Timer::_createIdentifier(void)
+{
+ UT_Timer::static_vecTimers.qsort(UT_Win32Timer::_compareIdentifiers);
+
+ // Take the first unused identifier number different from zero
+ UT_uint32 iIdentifier = 0;
+ UT_uint32 count = static_vecTimers.getItemCount();
+ for (UT_uint32 i=0; i<count; i++, iIdentifier++)
+ {
+ UT_Timer* pTimer = (UT_Timer*) static_vecTimers.getNthItem(i);
+ UT_ASSERT(pTimer);
+
+ UT_uint32 iTimerId = pTimer->getIdentifier();
+ if (iTimerId && iTimerId != iIdentifier)
+ {
+ break;
+ }
+ }
+
+ // Should be 16 bits maximum
+ UT_ASSERT((iIdentifier & 0xFFFF0000) == 0);
+
+ return iIdentifier;
}
Index: abi/src/af/util/win/ut_Win32Timer.h
===================================================================
RCS file: /cvsroot/abi/src/af/util/win/ut_Win32Timer.h,v
retrieving revision 1.8
diff -u -r1.8 ut_Win32Timer.h
--- abi/src/af/util/win/ut_Win32Timer.h 1999/02/22 18:51:39 1.8
+++ abi/src/af/util/win/ut_Win32Timer.h 2000/10/16 23:55:19
@@ -38,6 +38,8 @@
UT_sint32 m_iMilliseconds;
UT_Bool m_bStarted;
HWND m_hWnd;
+ static int _compareIdentifiers(const void* p1, const void* p2);
+ UT_uint32 _createIdentifier(void);
};
VOID CALLBACK Global_Win32TimerProc(HWND hwnd,
Index: abi/src/hello/ap/win/ap_Win32Frame.cpp
===================================================================
RCS file: /cvsroot/abi/src/hello/ap/win/ap_Win32Frame.cpp,v
retrieving revision 1.3
diff -u -r1.3 ap_Win32Frame.cpp
--- abi/src/hello/ap/win/ap_Win32Frame.cpp 2000/07/07 23:46:52 1.3
+++ abi/src/hello/ap/win/ap_Win32Frame.cpp 2000/10/16 23:55:38
@@ -612,11 +612,9 @@
case WM_TIMER:
{
- // Timers are handled differently on Win95 and WinNT.
TIMERPROC * pfn = (TIMERPROC *)lParam;
- UT_Win32Timer * pTimer = (UT_Win32Timer *)wParam;
UT_ASSERT( (void *)(pfn) == (void *)(Global_Win32TimerProc) );
- Global_Win32TimerProc(hwnd,WM_TIMER, pTimer->getIdentifier(),NULL);
+ Global_Win32TimerProc(hwnd,WM_TIMER,(UINT)wParam,NULL);
return 0;
}
Index: abi/src/wp/ap/win/ap_Win32Frame.cpp
===================================================================
RCS file: /cvsroot/abi/src/wp/ap/win/ap_Win32Frame.cpp,v
retrieving revision 1.59
diff -u -r1.59 ap_Win32Frame.cpp
--- abi/src/wp/ap/win/ap_Win32Frame.cpp 2000/09/05 09:01:32 1.59
+++ abi/src/wp/ap/win/ap_Win32Frame.cpp 2000/10/16 23:56:13
@@ -1065,12 +1065,9 @@
case WM_TIMER:
{
- // Timers are handled differently on Win95 and WinNT.
- // TMN: If so, what are those differences?
TIMERPROC * pfn = (TIMERPROC *)lParam;
- UT_Win32Timer * pTimer = (UT_Win32Timer *)wParam;
UT_ASSERT( (void *)(pfn) == (void *)(Global_Win32TimerProc) );
- Global_Win32TimerProc(hwnd,WM_TIMER, pTimer->getIdentifier(),NULL);
+ Global_Win32TimerProc(hwnd,WM_TIMER,(UINT)wParam,NULL);
return 0;
}
Index: abi/src/wp/ap/xp/ap_EditMethods.cpp
===================================================================
RCS file: /cvsroot/abi/src/wp/ap/xp/ap_EditMethods.cpp,v
retrieving revision 1.242
diff -u -r1.242 ap_EditMethods.cpp
--- abi/src/wp/ap/xp/ap_EditMethods.cpp 2000/10/05 01:22:19 1.242
+++ abi/src/wp/ap/xp/ap_EditMethods.cpp 2000/10/16 23:56:52
@@ -3701,36 +3701,36 @@
const char *pDocName = ((doc->getFilename()) ? doc->getFilename() :
pFrame->getTempNameFromTitle());
- UT_Bool bStarted = pGraphics->startPrint();
- UT_ASSERT(bStarted);
-
- if (bCollate)
+ if(pGraphics->startPrint())
{
- for (j=1; (j <= nCopies); j++)
- for (k=nFromPage; (k <= nToPage); k++)
- {
- // NB we will need a better way to calc
- // pGraphics->m_iRasterPosition when
- // iHeight is allowed to vary page to page
- pGraphics->m_iRasterPosition = (k-1)*iHeight;
- pGraphics->startPage(pDocName, k, UT_TRUE,
iWidth, iHeight);
- pPrintView->draw(k-1, &da);
- }
- }
- else
- {
- for (k=nFromPage; (k <= nToPage); k++)
+ if (bCollate)
+ {
for (j=1; (j <= nCopies); j++)
- {
- // NB we will need a better way to calc
- // pGraphics->m_iRasterPosition when
- // iHeight is allowed to vary page to page
- pGraphics->m_iRasterPosition = (k-1)*iHeight;
- pGraphics->startPage(pDocName, k, UT_TRUE,
iWidth, iHeight);
- pPrintView->draw(k-1, &da);
- }
+ for (k=nFromPage; (k <= nToPage); k++)
+ {
+ // NB we will need a better way to
+calc
+ // pGraphics->m_iRasterPosition when
+ // iHeight is allowed to vary page to
+page
+ pGraphics->m_iRasterPosition =
+(k-1)*iHeight;
+ pGraphics->startPage(pDocName, k,
+UT_TRUE, iWidth, iHeight);
+ pPrintView->draw(k-1, &da);
+ }
+ }
+ else
+ {
+ for (k=nFromPage; (k <= nToPage); k++)
+ for (j=1; (j <= nCopies); j++)
+ {
+ // NB we will need a better way to calc
+ // pGraphics->m_iRasterPosition when
+ // iHeight is allowed to vary page to
+page
+ pGraphics->m_iRasterPosition =
+(k-1)*iHeight;
+ pGraphics->startPage(pDocName, k,
+UT_TRUE, iWidth, iHeight);
+ pPrintView->draw(k-1, &da);
+ }
+ }
+ pGraphics->endPrint();
}
- pGraphics->endPrint();
delete pDocLayout;
delete pPrintView;
