home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
The World of Computer Software
/
World_Of_Computer_Software-02-385-Vol-1of3.iso
/
i
/
iritsm3s.zip
/
cagd_lib
/
cagdcmpt.c
< prev
next >
Wrap
C/C++ Source or Header
|
1991-10-09
|
4KB
|
127 lines
/******************************************************************************
* CagdCmpt.c - Make objects compatible. *
*******************************************************************************
* Written by Gershon Elber, Sep. 91. *
******************************************************************************/
#ifdef __MSDOS__
#include <stdlib.h>
#include <string.h>
#include <alloc.h>
#endif /* __MSDOS__ */
#include "cagd_loc.h"
/******************************************************************************
* Given two curves, make the compatible by: *
* 1. Coercing their point type to be the same. *
* 2. Make them have the same curve type. *
* 3. Raising the degree of the lower one to be the same. *
* 4. Refine them to a common knot vector (If Bspline). *
* Note 3 is preformed if SameOrder TRUE, 4 if SameKV TRUE. *
* Returns TRUE if succesfull. Both Curves are modified IN PLACE. *
******************************************************************************/
CagdBType CagdMakeCrvsCompatible(CagdCrvStruct **Crv1, CagdCrvStruct **Crv2,
CagdBType SameOrder, CagdBType SameKV)
{
int i, KV1Len, KV2Len, RefLen;
CagdRType *KV1, *KV2, *RefKV;
CagdCrvStruct *TCrv;
CagdPointType
CommonPType = CagdMergePointType((*Crv1) -> PType, (*Crv2) -> PType);
/* Make the point types compatible. */
if (CommonPType != (*Crv1) -> PType) {
TCrv = CagdCoerceCrvTo(*Crv1, CommonPType);
CagdCrvFree(*Crv1);
*Crv1 = TCrv;
}
if (CommonPType != (*Crv2) -> PType) {
TCrv = CagdCoerceCrvTo(*Crv2, CommonPType);
CagdCrvFree(*Crv2);
*Crv2 = TCrv;
}
/* If incompatible curve type - make it the same as well. */
if ((*Crv1) -> GType != (*Crv2) -> GType) {
/* If power basis - promote to bezier: */
if ((*Crv1) -> GType == CAGD_CPOWER_TYPE) {
TCrv = CnvrtPower2BezierCrv(*Crv1);
CagdCrvFree(*Crv1);
*Crv1 = TCrv;
}
if ((*Crv2) -> GType == CAGD_CPOWER_TYPE) {
TCrv = CnvrtPower2BezierCrv(*Crv2);
CagdCrvFree(*Crv2);
*Crv2 = TCrv;
}
/* Now both curves may be either bezier or bspline curves. */
if ((*Crv1) -> GType != (*Crv2) -> GType) {
/* If bezier basis - promote to bspline: */
if ((*Crv1) -> GType == CAGD_CBEZIER_TYPE) {
TCrv = CnvrtBezier2BsplineCrv(*Crv1);
CagdCrvFree(*Crv1);
*Crv1 = TCrv;
}
if ((*Crv2) -> GType == CAGD_CBEZIER_TYPE) {
TCrv = CnvrtBezier2BsplineCrv(*Crv2);
CagdCrvFree(*Crv2);
*Crv2 = TCrv;
}
}
}
if (SameOrder) {
/* Raise the degree of the lower one. */
for (i = (*Crv1) -> Order; i < (*Crv2) -> Order; i++) {
TCrv = CagdCrvDegreeRaise(*Crv1);
CagdCrvFree(*Crv1);
*Crv1 = TCrv;
}
for (i = (*Crv2) -> Order; i < (*Crv1) -> Order; i++) {
TCrv = CagdCrvDegreeRaise(*Crv2);
CagdCrvFree(*Crv2);
*Crv2 = TCrv;
}
}
if (SameKV) {
/* If bspline curve - make sure knot vectors are the same. */
if ((*Crv1) -> GType == CAGD_CBSPLINE_TYPE) {
KV1 = (*Crv1) -> KnotVector;
KV2 = (*Crv2) -> KnotVector;
KV1Len = (*Crv1) -> Length + (*Crv1) -> Order;
KV2Len = (*Crv2) -> Length + (*Crv2) -> Order;
/* Affine map second knot vector to span same parametric domain. */
BspKnotAffineTrans(KV2, KV2Len, KV1[0] - KV2[0],
(KV1[KV1Len - 1] - KV1[0]) /
(KV2[KV2Len - 1] - KV2[0]));
/* Find knots in KV2 which are not in KV1 and refine Crv1 there. */
RefKV = BspKnotSubtrTwo(KV2, KV2Len, KV1, KV1Len, &RefLen);
if (RefLen > 0) {
TCrv = CagdCrvRefineAtParams(*Crv1, FALSE, RefKV, RefLen);
CagdCrvFree(*Crv1);
*Crv1 = TCrv;
KV1 = (*Crv1) -> KnotVector;
KV1Len = (*Crv1) -> Length + (*Crv1) -> Order;
}
CagdFree((VoidPtr) RefKV);
/* Find knots in KV1 which are not in KV2 and refine Crv2 there. */
RefKV = BspKnotSubtrTwo(KV1, KV1Len, KV2, KV2Len, &RefLen);
if (RefLen > 0) {
TCrv = CagdCrvRefineAtParams(*Crv2, FALSE, RefKV, RefLen);
CagdCrvFree(*Crv2);
*Crv2 = TCrv;
}
CagdFree((VoidPtr) RefKV);
}
}
return TRUE;
}