📄 richtexthandling.c
字号:
return eus_SUCCESS;
} //eus_ActionHotspotJustBefore(
/** us_RetreatCursor( ***
Moves the given rich-text cursor one CD record back, taking into account the
rich-text field environment. Note that making a cursor go backwards is much
more processing expensive than making it go forward.
--- parameters & return ----
pt_crsr: Input & Output. Address of the cursor to be backed up. Output is
either an backed-up cursor or a cursor whose item pointer is nullified to
indicate that no previous CD records are available. If cursor could not be
retreated, its pt_item member is guaranteed to be null.
pt_CTX: Optional Input. Address of a structure describing the rich-text
environment being navigated. If null, the cursor cannot be backed up to a
previous item, nor will virtuality be taken into account.
pf_itmLockd: Optional. Address of the flag in which to store whether a
rich-text item was newly locked in the course of this procedure. If null,
the procedure will ignore this functionality.
RETURN: !eus_SUCCESS if an error occurred in determining the boundary between
actuality and virtuality; else eus_SUCCESS
--- side effect ------------
The rich-text environment information pointed to by pt_crsr or pt_CTX may be
adjusted due to cursor advancement.
--- revision history -------
9/6/02 PR: created */
static STATUS us_RetreatCursor( CdRecordCursor *const pt_crsr,
const RtfTrackingInfo *const pt_CTX,
BOOL *const pf_itmLockd) {
ItemInfo * pt_itm;
BOOL f_itmLockd = FALSE;
CdRecordCursor t_crsr = {NULL, NULL, NULL};
STATUS us_err = eus_SUCCESS;
_ASSERTE( pt_crsr && pt_crsr->puc_location && pt_crsr->pt_item &&
pt_crsr->pt_item->puc_start);
if (pf_itmLockd)
*pf_itmLockd = FALSE;
//if the item holding pointed-to location is virutal or if there's no
// virtuality involved in the given context...
if (!( pt_crsr->pt_item->i_type == mi_ACTUAL && pt_CTX->pt_endVirtual))
//if beginning of the item precedes the pointed-to location...
if (pt_crsr->pt_item->puc_start < pt_crsr->puc_location)
//move from there to the preceding CD record
CreateCursorAtRcrdPrior( pt_crsr->pt_item, NULL,
pt_crsr->puc_location, &t_crsr, NULL);
//else the preceding CD record is to be found on a preceding item...
else {
//if no item precedes the item containing the pointed-to location,
// short-circuit indicating no preceding CD record could be found
pt_itm = pt_CTX->pt_Actuality;
while (pt_itm) {
if (pt_itm->pt_next == pt_crsr->pt_item)
break;
pt_itm = pt_itm->pt_next;
}
if (!pt_itm)
goto errJump;
//locate the last CD record in the preceding item
CreateCursorAtRcrdPrior( pt_itm, NULL, NULL, &t_crsr, &f_itmLockd);
} //if (pt_crsr->pt_item->puc_start < pt_crsr->puc_location)
//else we're working in a context where the pointed-to location resides in
// actuality, but the rich-text context involves virtuality...
else {
const BYTE * puc;
//if the actual location which virtuality is currently flowing into
// (the "actual frontier") is on the same rich-text item as the
// pointed-to location...
if (!f_LocateAbsoluteOffset( pt_CTX->ul_ActualFrontier,
pt_CTX->pt_Actuality, &pt_itm,
&puc, NULL, &f_itmLockd)) {
us_err = !eus_SUCCESS;
goto errJump;
}
if (pt_itm == pt_crsr->pt_item) {
//if the pointed-to location is the same as the actual frontier...
_ASSERTE( !f_itmLockd);
if (puc == pt_crsr->puc_location) {
//move to the last virtualized CD record
CreateCursorAtRcrdPrior( pt_CTX->pt_endVirtual, NULL, NULL,
&t_crsr, &f_itmLockd);
//else if the pointed-to location follows the actual frontier...
}else if (puc < pt_crsr->puc_location)
//starting from the frontier, move to the preceding CD record
CreateCursorAtRcrdPrior( pt_crsr->pt_item, puc,
pt_crsr->puc_location, &t_crsr, NULL);
//Else the pointed-to location is, oddly, within the actuality
// slated to be overwritten by the current virtuality. If the
// beginning of the item holding the pointed-to location precedes
// the pointed-to location...
else if (pt_itm->puc_start < pt_crsr->puc_location)
//move from there to the preceding CD record
CreateCursorAtRcrdPrior( pt_itm, NULL, pt_crsr->puc_location,
&t_crsr, NULL);
//else the preceding CD record is to be found on a preceding item...
else {
//if no item precedes the item holding the pointed-to location,
// short-circuit indicating no preceding CD record could be
// found
pt_itm = pt_CTX->pt_Actuality;
while (pt_itm) {
if (pt_itm->pt_next == pt_crsr->pt_item)
break;
pt_itm = pt_itm->pt_next;
}
if (!pt_itm)
goto errJump;
//locate the last CD record in the preceding item
CreateCursorAtRcrdPrior( pt_itm, NULL, NULL, &t_crsr,
&f_itmLockd);
} //if (puc == pt_crsr->puc_location)
//else if the beginning of the item holding the pointed-to location
// precedes the pointed-to location...
}else if (pt_crsr->pt_item->puc_start < pt_crsr->puc_location)
//move from there to the preceding CD record
CreateCursorAtRcrdPrior( pt_crsr->pt_item, NULL,
pt_crsr->puc_location, &t_crsr, NULL);
//else the preceding item will hold preceding CD record...
else {
//if no item precedes the item containing the pointed-to location,
// short-circuit indicating no preceding CD record could be found
ItemInfo * pt_item = pt_CTX->pt_Actuality;
while (pt_item) {
if (pt_item->pt_next == pt_crsr->pt_item)
break;
pt_item = pt_item->pt_next;
}
if (!pt_item)
goto errJump;
//if the preceding item is the same item the actual frontier is
// located on...
if (pt_item == pt_itm)
//starting from the actual frontier, locate the last CD record
// in the item
CreateCursorAtRcrdPrior( pt_crsr->pt_item, puc,
pt_crsr->puc_location, &t_crsr, NULL);
//else locate the last CD record in the preceding item
else
CreateCursorAtRcrdPrior( pt_item, NULL, NULL, &t_crsr,
&f_itmLockd);
} //if (pt_itm == pt_crsr->pt_item)
} //if (!( pt_crsr->pt_item->i_type == mi_ACTUAL &&
//give caller the results
*pt_crsr = t_crsr;
if (pf_itmLockd && f_itmLockd)
*pf_itmLockd = TRUE;
return eus_SUCCESS;
errJump:
//signify to caller that no immediately previous CD record was located, and
// whether an error occurred
pt_crsr->pt_item = NULL;
return us_err;
} //us_RetreatCursor(
/** CreateCursorAtRcrdPrior( ***
Provided that all inputs relate to a single rich-text item, manufactures a
rich-text cursor at the CD record immediately preceding a given CD record.
--- parameters ----------
pt_itm: Input & Output. Address of structure describing the rich-text item to
be operated on. If item content must be locked in order to be accessed, the
structure will be updated to reflect the event.
puc_STRT: Optional. Address of CD record at which the rich-text traverse will
begin. If null, traverse will begin at the start of the rich-text item.
puc_END: Optional. Address of CD record that immediately follows the CD record
for which a rich-text cursor is to be manufactured. If null, the rich-text
cursor will be manufactured to point to the last CD record in the rich-text
item.
pt_crsr: Output. Address of the rich-text cursor structure to be set to point
to the "immediately preceding" CD record.
pf_itmLockd: Optional Output. Address of the flag in which to store whether the
rich-text item provided via the pt_itm input had to be locked in order for
its contents to be accessed. If null, this output will be ignored.
--- revision history ----
9/6/02 PR: created */
static void CreateCursorAtRcrdPrior( ItemInfo *const pt_itm,
const BYTE *const puc_STRT,
const BYTE *const puc_END,
CdRecordCursor *const pt_crsr,
BOOL *const pf_itmLockd) {
const BYTE * puc_end = puc_END, * puc, * puc_;
BOOL f_itmLockd = FALSE;
USHORT us;
_ASSERTE( pt_itm && pt_crsr && (puc_STRT || puc_END ? pt_itm->puc_start &&
(puc_STRT ? pt_itm->puc_start <=
puc_STRT && puc_STRT < pt_itm->puc_start +
pt_itm->ul_length : TRUE) && (puc_END ?
pt_itm->puc_start <= puc_END && puc_END <
pt_itm->puc_start + pt_itm->ul_length :
TRUE) && (puc_STRT && puc_END ? puc_STRT <
puc_END : TRUE) : TRUE));
memset( pt_crsr, NULL, sizeof( CdRecordCursor));
if (pf_itmLockd)
*pf_itmLockd = FALSE;
//if the end-boundary isn't known yet, determine it
if (!puc_end) {
if (!pt_itm->puc_start) {
pt_itm->puc_start = OSLockBlock( BYTE, pt_itm->bid_contents);
f_itmLockd = TRUE;
}
puc_end = pt_itm->puc_start + pt_itm->ul_length;
} //if (!puc_end)
//locate the preceding CD record
us = us_getCdRecLength( puc = puc_ = puc_STRT ? puc_STRT :
pt_itm->puc_start + sizeof( WORD));
_ASSERTE( us);
while ((puc_ += us + us % 2) < puc_end) {
puc = puc_;
us = us_getCdRecLength( puc);
}
//output result, suppressing "different 'const' qualifiers" compiler warning
#pragma warning( disable : 4090)
pt_crsr->puc_location = puc;
#pragma warning( default : 4090)
pt_crsr->pt_item = pt_itm;
pt_crsr->us_recLength = us;
if (f_itmLockd && pf_itmLockd)
*pf_itmLockd = TRUE;
} //CreateCursorAtRcrdPrior(
/** ef_CursorToAttachmentHotspot( ***
Purpose is to find and provide information about the next file-attachment in
the rich-text field being navigated by the passed-in cursor.
--- parameters & return ----
pt_crsr: Input & Output. Address of the rich-text cursor positioned to the
point at which the search for the next file-attachment hotspot should
commence. This cursor is then used when advancing through CD records. If
the procedure is successful, the cursor will finish at the end-hotspot CD
record if a file-attachment hotspot is found, else it will be nullified
because it will have travelled through the entire available rich-text
context.
pt_CTXT: Optional. Address of environment information about the rich-text field
being navigated. If passed in null, the rich-text cursor being used will be
unable to move from virtuality to actuality.
f_BUMP_FORWARD_FIRST: Flag telling whether the passed-in starting cursor should
be moved to the next CD record before initiating the search for
file-attachment hotspots. Usually when starting at the beginning of the
rich-text field, the flag will be set to FALSE so that the first CD record
may be checked as to whether it's a file-attachment hotspot. Ensuing calls
might then set the flag to TRUE to move to the next CD record since the
current CD record (an end-hotspot record) is already known.
pt_span: Optional Output. Address of the structure to hold information about
where a found file-attachment hotspot begins and ends within the rich-text
field. The "begins" member will point to the hotspot-begin CD record; the
"ends" member will point to the CD record immediately following the
hotspot-end record. Feature is ignored if the pointer passed in is null.
ppc_fileNm: Optional Output. Address of the string pointer that should be set
to the name Notes is using for the file attachment associated with the
hotspot. Feature is ignored if the pointer passed in is null. The
pointed-to memory is owned by the note; the caller should not free the
pointer.
ppc_objNm: Optional Output. Pointer to the string pointer that should be set to
the name of the file the user attached to the note. Feature is ignored if
the pointer passed in is null. The pointed-to memory is owned by the note;
the caller should not free the pointer.
RETURN: TRUE if no error situation was encountered; FALSE otherwise.
--- side effect -------------
The rich-text environment information pointed to through pt_crsr or pt_CTXT
may be adjusted due to cursor advancement. If the enhancement suggested below
is implemented, this side effect would be eliminated.
--- suggested enhancement ----
9/6/02 PR: change return to a STATUS so eus_ERR_INVLD_ARG can be returned
11/10/98 PR: The starting memory-lock state should be restored upon function
exit, but no good mechanism is yet available with which to accomplish this.
See this module's suggested-enhancement note for a description of the
problem and proposed solution.
--- revision history ---------
9/6/02 PR
+ fixed logic error where pt_crsr output was not set properly if a pt_span
output was requested
+ listing format adjustment, minor token renaming
9/16/00 PR
+ allowed a return of success if given cursor seems to already be at the end
of all rich-text content
+ token renaming
3/20/00 PR
+ Adjusted "span" output so that the "end" member points to the CD record
immediately following the attachment's hotspot-end CD record. Done to
facilitate a potential ensuing call to remove the attachment hotspot
altogether.
+ factored out functionality for locating the hotspot-end CD record
corresponding to a provided hotspot-begin record: f_CursorToHotspotEnd()
+ documentation adjustment
12/11/98 PR: created */
BOOL ef_CursorToAttachmentHotspot( CdRecordCursor *const pt_crsr,
const RtfTrackingInfo *const pt_CTX,
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -