windows-nt/Source/XPSP1/NT/base/mvdm/wow16/write/addprm.c
2020-09-26 16:20:57 +08:00

433 lines
13 KiB
C
Raw Blame History

This file contains invisible Unicode characters

This file contains invisible Unicode characters that are indistinguishable to humans but may be processed differently by a computer. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

/************************************************************/
/* Windows Write, Copyright 1985-1992 Microsoft Corporation */
/************************************************************/
/* AddPrm.c -- Routines to add prms and sprms to docs */
#define NOGDICAPMASKS
#define NOVIRTUALKEYCODES
#define NOWINMESSAGES
#define NOWINSTYLES
#define NOSYSMETRICS
#define NOMENUS
#define NOKEYSTATE
#define NOSYSCOMMANDS
#define NORASTEROPS
#define NOSHOWWINDOW
#define NOSYSMETRICS
#define NOATOM
#define NOBITMAP
#define NOBRUSH
#define NOPEN
#define NOCLIPBOARD
#define NOCOLOR
#define NOCTLMGR
#define NOWNDCLASS
#define NODRAWTEXT
#define NOFONT
#define NOGDI
#define NOHDC
#define NOMB
#define NOMENUS
#define NOMETAFILE
#define NOMSG
#define NOTEXTMETRIC
#define NOSOUND
#define NOSCROLL
#define NOCOMM
/* no everything except MEMMGR */
#include <windows.h>
#include "mw.h"
#include "cmddefs.h"
#include "code.h"
#include "ch.h"
#include "docdefs.h"
#include "editdefs.h"
#include "str.h"
#include "prmdefs.h"
#include "propdefs.h"
#include "filedefs.h"
#include "stcdefs.h"
#include "fkpdefs.h"
#include "macro.h"
#include "dispdefs.h"
/* E X T E R N A L S */
extern int docCur;
extern struct SEL selCur;
extern struct DOD (**hpdocdod)[];
extern struct UAB vuab;
extern int vfSysFull;
extern CHAR dnsprm[];
extern struct CHP vchpSel;
extern typeCP vcpLimParaCache;
extern typeCP cpMacCur;
extern typeCP CpLimNoSpaces();
extern int ferror;
/* G L O B A L S */
struct FPRM fprmCache = { 0 };
struct PRM prmCache = {0,0,0,0};
/* A D D O N E S P R M */
/* applies sprm at psprm to the current selection. Take care of
undoing, invalidation, special endmark cases, and extension of selection
to paragraph boundaries */
void AddOneSprm(psprm, fSetUndo)
CHAR *psprm;
int fSetUndo; /* True if we need to set up the undo buffer */
{
int cch;
int fParaSprm = fFalse;
typeCP cpFirst, cpLim, dcp;
if (!FWriteOk( fwcNil ))
return;
if ((dnsprm[*psprm] & ESPRM_sgc) != sgcChar)
{
typeCP dcpExtraPara = cp0;
cpFirst = CpFirstSty( selCur.cpFirst, styPara );
CachePara( docCur, CpMax( selCur.cpLim - 1, selCur.cpFirst ) );
cpLim = vcpLimParaCache;
dcp = cpLim - cpFirst;
/* Check for para following selection that has no Eol */
if (cpLim < cpMacCur)
{
/* Note that in this case only, dcp (the # of cp's affected
by the change) does not equal (cpLim - cpFirst)
(the # of cp's to which the sprm should apply) */
CachePara( docCur, cpLim );
dcpExtraPara = vcpLimParaCache - cpLim;
}
if (cpFirst + dcp + dcpExtraPara > cpMacCur)
{ /* Last para affected has no Eol -- add one */
struct SEL selSave;
dcp += dcpExtraPara;
Assert( cpFirst + dcp == cpMacCur + (typeCP) ccpEol);
if (fSetUndo)
{
SetUndo( uacReplNS, docCur, cpFirst, dcp,
docNil, cpNil, dcp - ccpEol, 0 );
fSetUndo = fFalse;
}
/* Add an eol. Save the current selection so
it does not get adjusted */
selSave = selCur;
InsertEolInsert(docCur,cpMacCur);
selCur = selSave;
}
}
else
{ /* Char sprm -- eliminate trailing spaces from the
affected region, so we don't underline spaces after words. */
cpFirst = selCur.cpFirst;
cpLim = CpLimNoSpaces(selCur.cpFirst, selCur.cpLim);
dcp = cpLim - cpFirst;
if (dcp == 0)
{ /* Doing character looks to the insert point... */
if (fSetUndo)
SetUndo(uacReplNS, docCur, cpFirst, cp0,
docNil, cp0, cp0, 0);
DoSprm(&vchpSel, 0, *psprm, psprm + 1);
return;
}
}
if (fSetUndo)
SetUndo(uacReplNS, docCur, cpFirst, dcp, docNil, cpNil, dcp, 0);
if (ferror) /* not enough memory to store info for undo operation */
{
NoUndo();
return;
}
AddSprmCps(psprm, docCur, cpFirst, cpLim);
AdjustCp( docCur, cpFirst, dcp, dcp );
}
/* E X P A N D C U R S E L */
ExpandCurSel(pselSave)
struct SEL *pselSave;
{
*pselSave = selCur;
selCur.cpFirst = CpFirstSty(selCur.cpFirst, styPara);
CachePara(docCur, CpMax(selCur.cpLim - 1, selCur.cpFirst));
selCur.cpLim = vcpLimParaCache;
}
/* E N D L O O K S E L */
EndLookSel(pselSave, fPara)
struct SEL *pselSave; BOOL fPara;
{
typeCP cpLim, cpFirst, dcp;
dcp = (cpLim = selCur.cpLim) - (cpFirst = selCur.cpFirst);
if (fPara)
{
TrashCache();
if (cpLim <= cpMacCur)
{
CachePara(docCur, selCur.cpLim);
if (vcpLimParaCache > cpMacCur) /* Last (partial) paragraph */
dcp = cpMacCur - cpFirst + 1;
}
}
AdjustCp(docCur, cpFirst, dcp, dcp);
selCur = *pselSave;
}
/* A D D S P R M */
AddSprm(psprm)
CHAR *psprm;
{ /* Add a single property modifier to the pieces contained in selCur. */
AddSprmCps(psprm, docCur, selCur.cpFirst, selCur.cpLim);
}
/* A D D S P R M C P S */
AddSprmCps(char *psprm, int doc, typeCP cpFirst, typeCP cpLim)
{
struct PCTB **hpctb;
int ipcdFirst, ipcdLim, ipcd;
struct DOD *pdod;
int cch;
struct PCD *ppcd;
/* First get address of piece table and split off desired pieces. */
pdod = &(**hpdocdod)[doc];
hpctb = pdod->hpctb;
pdod->fFormatted = fTrue;
ipcdFirst = IpcdSplit(hpctb, cpFirst);
ipcdLim = IpcdSplit(hpctb, cpLim);
if (ferror)
/* Ran out of memory trying to expand piece table */
return;
/* Now just add this sprm to the pieces. */
FreezeHp();
for (ipcd = ipcdFirst, ppcd = &(**hpctb).rgpcd[ipcdFirst];
ipcd < ipcdLim && !vfSysFull; ++ipcd, ++ppcd)
ppcd->prm = PrmAppend(ppcd->prm, psprm);
MeltHp();
}
/* P R M A P P E N D */
struct PRM PrmAppend(struct PRM prm, CHAR *psprm)
{ /* Append <sprm, val> to the chain of sprm's in prm. Return new prm. */
struct FPRM *pfprmOld;
CHAR *pfsprm;
CHAR *pfsprmOld;
int sprm = *psprm;
int sprmOld;
register int esprm = dnsprm[sprm];
register int esprmOld;
int cchNew = (esprm & ESPRM_cch);
int cchOld;
int sgc = (esprm & ESPRM_sgc);
int spr = (esprm & ESPRM_spr);
int fSame = (esprm & ESPRM_fSame);
int fClobber = (esprm & ESPRM_fClobber);
int dval = 0;
int cch;
int cchT;
typeFC fcPrm;
struct FPRM fprm;
if (cchNew == 0) cchNew = CchPsprm(psprm);
pfsprm = fprm.grpfsprm;
if (prm.fComplex)
{ /* Get the old list of sprm's from scratch file; copy it to fprm. */
pfprmOld = (struct FPRM *) PchFromFc(fnScratch,
//(typeFC)(unsigned)(((struct PRMX *) &prm)->bfprm << 1), &cch);
fcSCRATCHPRM(prm), &cch);
pfsprmOld = pfprmOld->grpfsprm;
cchT = cch = pfprmOld->cch;
while (cchT)
{ /* Copy grpsprm, removing ones which we will clobber */
sprmOld = *pfsprmOld;
esprmOld = dnsprm[sprmOld];
if ((cchOld = (esprmOld & ESPRM_cch)) == 0)
cchOld = CchPsprm(pfsprmOld);
#ifdef DEBUG
if (cchOld == 0)
panic();
#endif
if (sprmOld == sprm && fSame ||
(esprmOld & ESPRM_sgc) == sgc &&
(esprmOld & ESPRM_spr) <= spr && fClobber)
{
/* make sure we properly coalesce change
size prms */
if (sprm == sprmOld && sprm == sprmCChgHps)
dval += *(pfsprmOld + 1);
cch -= cchOld;
}
/* CHps overrides CChgHps */
else if (sprmOld == sprmCChgHps && sprm == sprmCHps)
{
cch -= cchOld;
}
else
pfsprm = (CHAR *)bltbyte(pfsprmOld, pfsprm, cchOld);
pfsprmOld += cchOld;
cchT -= cchOld;
}
}
else
{ /* No file entry yet; convert simple prm to fsprm */
int valOld = prm.val;
sprmOld = prm.sprm;
esprmOld = dnsprm[sprmOld];
if (bPRMNIL(prm) ||
sprmOld == sprm && fSame ||
(esprmOld & ESPRM_sgc) == sgc &&
(esprmOld & ESPRM_spr) <= spr && fClobber)
{
/* make sure we are combinning consecutive sprmCChgHps */
if (sprm == sprmOld && sprm == sprmCChgHps)
dval += valOld;
cch = 0;
}
/* CHps overrides CChgHps */
else if (sprmOld == sprmCChgHps && sprm == sprmCHps)
{
cch = 0;
}
else
{ /* Save old sprm */
*pfsprm++ = sprmOld;
if ((cch = (esprmOld & ESPRM_cch)) == 2)
*pfsprm++ = valOld;
}
}
/* we have: cch = length of old prm after removal of clobbered/etc. entries.
cchNew: length of the entry to be appended.
dval: correction for 2nd byte of new entry
pfsprm: where 1st byte of new entry will go
*/
bltbyte((CHAR *) psprm, pfsprm, imin(cchNew, cchMaxGrpfsprm - cch));
*(pfsprm + 1) += dval;
if (cch == 0 && cchNew <= 2)
{ /* Pack sprm and val into a prm word. */
struct PRM prmT;
prmT.dummy=0;
bltbyte(pfsprm, (CHAR *) &prmT, cchNew);
prmT.fComplex = false;
prmT.sprm = *pfsprm;
return (prmT);
}
if ((cch += cchNew) > cchMaxGrpfsprm)
{
int fSave = ferror;
Error(IDPMT2Complex);
ferror = fSave;
return (prm);
}
if (vfSysFull)
return prm; /* Assume disk full message already given */
fprm.cch = cch;
/* Check newly created prm to see if same as previous */
if (CchDiffer(&fprmCache, &fprm, cch + 1) == 0)
return prmCache;
bltbyte(&fprm, &fprmCache, cch + 1);
AlignFn(fnScratch, cch = ((cch >> 1) + 1) << 1, fTrue);
prm.fComplex = fTrue;
//((struct PRMX)prm).bfprm = FcWScratch((CHAR *) &fprm, cch) >> 1;
fcPrm = FcWScratch((CHAR *) &fprm, cch) >> 1;
((struct PRMX *)&prm)->bfprm_hi = (fcPrm >> 16) & 0x7F;
((struct PRMX *)&prm)->bfprm_low = fcPrm & 0xFFFF;
prmCache = prm;
return prm;
}
/* A P P L Y C L O O K S */
/* character looks. val is a 1 char value */
ApplyCLooks(pchp, sprm, val)
struct CHP *pchp;
int sprm, val;
{
/* Assemble sprm */
CHAR rgbSprm[1 + cchINT];
CHAR *pch = &rgbSprm[0];
*pch++ = sprm;
*pch = val;
if (pchp == 0)
{
/* apply looks to current selection */
AddOneSprm(rgbSprm, fTrue);
vuab.uac = uacChLook;
SetUndoMenuStr(IDSTRUndoLook);
}
else
{
/* apply looks to pchp */
DoSprm(pchp, 0, sprm, pch);
}
}
/* A P P L Y L O O K S P A R A S */
/* val is a char value */
ApplyLooksParaS(pchp, sprm, val)
struct CHP *pchp;
int sprm, val;
{
int valT = 0;
CHAR *pch = (CHAR *)&valT;
*pch = val;
/* all the above is just to prepare bltbyte later gets the right byte order */
ApplyLooksPara(pchp, sprm, valT);
}
/* A P P L Y L O O K S P A R A */
/* val is an integer value. Char val's must have been bltbyte'd into val */
ApplyLooksPara(pchp, sprm, val)
struct CHP *pchp;
int sprm, val;
{
if (FWriteOk(fwcNil)) /* Check for out-of-memory/ read-only */
{
CHAR rgbSprm[1 + cchINT];
CHAR *pch = &rgbSprm[0];
*pch++ = sprm;
bltbyte(&val, pch, cchINT);
AddOneSprm(rgbSprm, fTrue);
vuab.uac = uacChLook;
SetUndoMenuStr(IDSTRUndoLook);
}
}