201 lines
5.1 KiB
C++
201 lines
5.1 KiB
C++
//+---------------------------------------------------------------------------
|
|
//
|
|
// Microsoft Windows
|
|
// Copyright (C) Microsoft Corporation, 1992 - 1997.
|
|
//
|
|
// File: psavtrak.hxx
|
|
//
|
|
// Contents: A pure virtual class to indicate progress in a save content-index
|
|
// operation. The save consists of two parts:
|
|
//
|
|
// 1. Merge Operation
|
|
// 2. Copying the index data
|
|
//
|
|
// This class also permits communicating an aout
|
|
// Classes: PSaveProgressTracker
|
|
//
|
|
// History: 3-18-97 srikants Created
|
|
//
|
|
//----------------------------------------------------------------------------
|
|
|
|
#pragma once
|
|
|
|
//+---------------------------------------------------------------------------
|
|
//
|
|
// Class: PSaveProgressTracker
|
|
//
|
|
// Purpose: A pure virtual class for indicating progress and communicating
|
|
// abort of a long operation.
|
|
//
|
|
// History: 3-18-97 srikants Created
|
|
//
|
|
//----------------------------------------------------------------------------
|
|
|
|
class PSaveProgressTracker
|
|
{
|
|
|
|
public:
|
|
|
|
virtual void UpdateMergeProgress( ULONG ulNumerator, ULONG ulDenominator ) = 0;
|
|
|
|
virtual void UpdateCopyProgress( ULONG ulNumerator, ULONG ulDenominator ) = 0;
|
|
|
|
virtual void GetProgress( ULONG & ulNumerator, ULONG & ulDenominator ) = 0;
|
|
|
|
virtual void SetAbort() = 0;
|
|
|
|
virtual BOOL IsAbort() = 0;
|
|
};
|
|
|
|
//+---------------------------------------------------------------------------
|
|
//
|
|
// Class: CProgressTracker
|
|
//
|
|
// Purpose: An implementation of the PSaveProgressTracker using the
|
|
// IProgressNotify interface.
|
|
//
|
|
// History: 3-20-97 srikants Created
|
|
//
|
|
//----------------------------------------------------------------------------
|
|
|
|
class CProgressTracker : public PSaveProgressTracker
|
|
{
|
|
|
|
public:
|
|
|
|
CProgressTracker()
|
|
: _fAbort(FALSE),
|
|
_fTracking(FALSE),
|
|
_ulNumerator(0),
|
|
_ulDenominator(1),
|
|
_pfClientAbort(0),
|
|
_pProgressNotify(0)
|
|
{
|
|
_evt.Set();
|
|
}
|
|
|
|
~CProgressTracker()
|
|
{
|
|
Win4Assert( 0 == _pfClientAbort );
|
|
Win4Assert( 0 == _pProgressNotify );
|
|
Win4Assert( !_fTracking );
|
|
}
|
|
|
|
//
|
|
// Assuming that it will be called from within an outer lock.
|
|
//
|
|
void LokStartTracking( IProgressNotify * pNotify = 0,
|
|
BOOL const * pfClientAbort = 0 )
|
|
{
|
|
_pProgressNotify = pNotify;
|
|
|
|
if ( 0 == pfClientAbort )
|
|
_pfClientAbort = &_fAbort;
|
|
else _pfClientAbort = pfClientAbort;
|
|
|
|
_ulNumerator = 0;
|
|
_ulDenominator = 1;
|
|
|
|
_fAbort = FALSE;
|
|
_fTracking = TRUE;
|
|
|
|
_evt.Reset();
|
|
}
|
|
|
|
//
|
|
// Assuming that it will be called from within an outer lock.
|
|
//
|
|
void LokStopTracking()
|
|
{
|
|
_pProgressNotify = 0;
|
|
_pfClientAbort = 0;
|
|
_fTracking = FALSE;
|
|
_fAbort = FALSE;
|
|
|
|
_evt.Set();
|
|
}
|
|
|
|
BOOL LokIsTracking() const
|
|
{
|
|
return _fTracking;
|
|
}
|
|
|
|
void WaitForCompletion()
|
|
{
|
|
_evt.Wait();
|
|
}
|
|
|
|
//
|
|
// I have assumed that merge and copy are 50% each. If we see that
|
|
// Merge is a much bigger portion, we have to adjust these numbers.
|
|
//
|
|
virtual void UpdateMergeProgress( ULONG ulNumerator, ULONG ulDenominator )
|
|
{
|
|
//
|
|
// Assume that Merge is half the work.
|
|
//
|
|
_UpdateProgress( ulNumerator, ulDenominator * 2 );
|
|
}
|
|
|
|
virtual void UpdateCopyProgress( ULONG ulNumerator, ULONG ulDenominator )
|
|
{
|
|
//
|
|
// Progress = num/(2*denom) + 1/2
|
|
// = (num + denom)/2*denom
|
|
|
|
_UpdateProgress( (ulNumerator+ulDenominator) , 2*ulDenominator );
|
|
}
|
|
|
|
virtual void GetProgress( ULONG & ulNumerator, ULONG & ulDenominator )
|
|
{
|
|
ulNumerator = _ulNumerator;
|
|
ulDenominator = _ulDenominator;
|
|
}
|
|
|
|
virtual void SetAbort()
|
|
{
|
|
_fAbort = TRUE;
|
|
}
|
|
|
|
virtual BOOL IsAbort()
|
|
{
|
|
return _fAbort || (*_pfClientAbort);
|
|
}
|
|
|
|
private:
|
|
|
|
BOOL _fAbort; // Abort controlled by us.
|
|
BOOL _fTracking; // Is there an active tracking
|
|
|
|
ULONG _ulNumerator;
|
|
ULONG _ulDenominator;
|
|
CEventSem _evt;
|
|
|
|
BOOL const * _pfClientAbort; // Abort controlled by the client
|
|
IProgressNotify * _pProgressNotify;
|
|
|
|
void _UpdateProgress( ULONG ulNumerator, ULONG ulDenominator )
|
|
{
|
|
Win4Assert( _fTracking );
|
|
Win4Assert( 0 != ulDenominator );
|
|
|
|
_ulNumerator = ulNumerator;
|
|
_ulDenominator = ulDenominator;
|
|
ciDebugOut(( DEB_ERROR,
|
|
"Save Progress = %d percent\n",
|
|
(_ulNumerator*100)/_ulDenominator ));
|
|
|
|
if ( _pProgressNotify )
|
|
{
|
|
_pProgressNotify->OnProgress(
|
|
(DWORD) _ulNumerator,
|
|
(DWORD) _ulDenominator,
|
|
FALSE, // Not accurate
|
|
FALSE // Ownership of Blocking Behavior
|
|
);
|
|
|
|
}
|
|
}
|
|
};
|
|
|