Пример #1
0
void process_squareDist(Distortion *t, fixedp *x) { 
	Uint32 n;
	
	if(t->fdb != 0) {
	
		for(n = 0; n < PROCESS_SIZE; n++) {
			t->prev = qadd(qmul(x[n], t->gain), qmul(t->prev, t->fdb));

			if (t->prev > 0)
				t->prev = t->lvl1;
			else if (t->prev < 0)
				t->prev = -t->lvl2;

			x[n] = t->prev;
		}

	}
	else {
		for(n = 0; n < PROCESS_SIZE; n++) {
			t->prev = qmul(x[n], t->gain);

			if (t->prev > 0)
				t->prev = t->lvl1;
			else if (t->prev < 0)
				t->prev = -t->lvl2;

			x[n] = t->prev;
		}
	}
}
Пример #2
0
void process_thunderFuzz( Distortion *t, fixedp *x ) {
	Uint32 n;
	
	// remember to keep sample from previous cycle. :) keep in structure. disttruc
	if(t->fdb) {
		for(n=0; n < PROCESS_SIZE; n++) {
			t->prev = qadd(qmul(x[n],t->gain), qmul(t->prev, t->fdb));
		
			if (t->prev > t->lvl1) 
				t->prev = t->lvl1;
			else if (t->prev < -t->lvl2)
				t->prev = -t->lvl2;

			x[n] = qabs(t->prev);
		}
	}
	else {
		for(n=0; n < PROCESS_SIZE; n++) {
			t->prev = qmul(x[n],t->gain);

			if (t->prev > t->lvl1) 
				t->prev = t->lvl1;
			else if (t->prev < -t->lvl2)
				t->prev = -t->lvl2;
			

			x[n] = qabs(t->prev);
		}
	}
}
Пример #3
0
fixedp getExp(fixedp base) {
	Int32 pos;
	if (base > EXP_POS_MAX)
		return posExp[EXP_TABLE_SIZE-1];								
	else if (base < EXP_NEG_MAX)
		return negExp[EXP_TABLE_SIZE-1];
	else if (base > 0) {
		// måste anpassas till fixt tal så rätt element i tabellen anropas
		pos = q2int(qmul(base, EXP_POS_POS_MUL));
		if (pos < 0) {
			return posExp[0];
		}
		return posExp[pos];
	}
	else if (base < 0) {
		// samma här, VIKTIGT: LÄGG TILL AVRUNDNING, DERO HERO 
		pos = q2int(qmul(qabs(base), EXP_NEG_POS_MUL));
		if(pos < 0) {
			return negExp[0];
		}
		return negExp[pos];
	}
	
	return 1;
}
Пример #4
0
void qrot_vec(vec dest, quat *q, vec x) {
	quat qc, qx, tmpdest;
	memcpy(&qc, q, sizeof(quat));
	qconj(&qc);
	
	qx.s = 0;
	memcpy(qx.v, x, sizeof(vec));
	
	qmul(&tmpdest, q, &qx);
	qmul(&qx, &tmpdest, &qc);
	
	memcpy(dest, qx.v, sizeof(vec));
}
Пример #5
0
inline fixedp dLinTerp(fixedp x1, fixedp x2, fixedp y1, fixedp y2, fixedp x)
{
	fixedp dx, result, denom;
	denom = qsub(x2, x1);
	if(denom == 0)
		return y1; // should not ever happen

	// calculate decimal position of x
	dx = qdiv(qsub(x, x1), denom);

	// use weighted sum method of interpolating
	result = qadd( qmul( dx, y2 ), qmul( qsub( short2q(1), dx ), y1 ));

	return result;
}
Пример #6
0
/*
** ドラッグ中
**   マウスのドラッグ中に実行する
*/
void trackballMotion(int x, int y)
{
  if (drag) {
    double dx, dy, a;
    
    /* マウスポインタの位置のドラッグ開始位置からの変位 */
    dx = (x - cx) * sx;
    dy = (y - cy) * sy;
    //dy = 0;
    /* マウスポインタの位置のドラッグ開始位置からの距離 */
    a = sqrt(dx * dx + dy * dy);
    
    if (a != 0.0) {
      double ar = a * SCALE * 0.5;
      double as = sin(ar) / a;
      double dq[4] = { cos(ar), dy * as, dx * as, 0.0 };
      
      /* クォータニオンを掛けて回転を合成 */
      qmul(tq, dq, cq);
      
      /* クォータニオンから回転の変換行列を求める */
      qrot(rt, tq);
    }
  }
}
Пример #7
0
void
multiply_numbers(void)
{
	double a, b;

	if (isrational(stack[tos - 1]) && isrational(stack[tos - 2])) {
		qmul();
		return;
	}

	save();

	p2 = pop();
	p1 = pop();

	if (isdouble(p1))
		a = p1->u.d;
	else
		a = convert_rational_to_double(p1);

	if (isdouble(p2))
		b = p2->u.d;
	else
		b = convert_rational_to_double(p2);

	push_double(a * b);

	restore();
}
Пример #8
0
void qball(Rectangle r, Mouse *m, Quaternion *result, void (*redraw)(void), Quaternion *ap){
	Quaternion q, down;
	Point rad;
	axis=ap;
	ctlcen=divpt(addpt(r.min, r.max), 2);
	rad=divpt(subpt(r.max, r.min), 2);
	ctlrad=(rad.x<rad.y?rad.x:rad.y)-BORDER;
	down=qinv(mouseq(m->xy));
	q=*result;
	for(;;){
		*m=emouse();
		if(!m->buttons) break;
		*result=qmul(q, qmul(down, mouseq(m->xy)));
		(*redraw)();
	}
}
Пример #9
0
void init_3band_state(EQSTATE* es, int lowfreq, int highfreq, int mixfreq)
{
  // Clear state 

  memset(es,0,sizeof(EQSTATE));

  // Set Low/Mid/High gains to unity

  es->lg = 1.0;
  es->mg = 1.0;
  es->hg = 1.0;

  // Calculate filter cutoff frequencies

  es->lf = qmul(Q2, qsin(qmul(QPI, qdiv(int2q(lowfreq), int2q(mixfreq))))); 
  es->hf = qmul(Q2, qsin(qmul(QPI, qdiv(int2q(highfreq), int2q(mixfreq)))));
}
/*
 * Multiply a complex number by a real number.
 */
COMPLEX *
cmulq(COMPLEX *c, NUMBER *q)
{
	COMPLEX *r;

	if (qiszero(q))
		return clink(&_czero_);
	if (qisone(q))
		return clink(c);
	if (qisnegone(q))
		return cneg(c);
	r = comalloc();
	qfree(r->real);
	qfree(r->imag);
	r->real = qmul(c->real, q);
	r->imag = qmul(c->imag, q);
	return r;
}
/*
 * Multiply two complex numbers.
 * This saves one multiplication over the obvious algorithm by
 * trading it for several extra additions, as follows.	Let
 *	q1 = (a + b) * (c + d)
 *	q2 = a * c
 *	q3 = b * d
 * Then (a+bi) * (c+di) = (q2 - q3) + (q1 - q2 - q3)i.
 */
COMPLEX *
cmul(COMPLEX *c1, COMPLEX *c2)
{
	COMPLEX *r;
	NUMBER *q1, *q2, *q3, *q4;

	if (ciszero(c1) || ciszero(c2))
		return clink(&_czero_);
	if (cisone(c1))
		return clink(c2);
	if (cisone(c2))
		return clink(c1);
	if (cisreal(c2))
		return cmulq(c1, c2->real);
	if (cisreal(c1))
		return cmulq(c2, c1->real);
	/*
	 * Need to do the full calculation.
	 */
	r = comalloc();
	q2 = qqadd(c1->real, c1->imag);
	q3 = qqadd(c2->real, c2->imag);
	q1 = qmul(q2, q3);
	qfree(q2);
	qfree(q3);
	q2 = qmul(c1->real, c2->real);
	q3 = qmul(c1->imag, c2->imag);
	q4 = qqadd(q2, q3);
	qfree(r->real);
	r->real = qsub(q2, q3);
	qfree(r->imag);
	r->imag = qsub(q1, q4);
	qfree(q1);
	qfree(q2);
	qfree(q3);
	qfree(q4);
	return r;
}
Пример #12
0
int main( int argc, char **argv ) {
    (void) argc;
    (void) argv;

    // init
    srand((unsigned int)time(NULL)); // might break in 2038

    aa_test_ulimit();

    cross();
    qmul();
    qrot();
    tfmul();
    duqumul();
}
Пример #13
0
void process_isr(void) 
{
	int i;
	// buffer switching
	// input -> process
	// process -> output
	// output -> input
	tmp = output;
	output = process;
	process = input;
	input = output;
	

	// DO PROCESSING
	pGain = (fixedp)(*(unsigned volatile int *)GAINADRESS);
	for(i = 0; i < N; i++) {
		result = (short)qmul(process[i],pGain);
		process[i] = result;
	}
	return;
}
Пример #14
0
void Trackball::motion(int x, int y)
{
	if (dragged) {
		double dx, dy, a;

		dx = (x - cx) * sx;
		dy = (y - cy) * sy;

		a = sqrt(dx * dx + dy * dy);

		if (a != 0.0)
		{
			double ar = a * SCALE * 0.5;
			double as = sin(ar) / a;
			double dq[4] = { cos(ar), dy * as, dx * as, 0.0 };

			qmul(tq, dq, cq);

			qrot(rt, tq);
		}
	}
}
/*
 * Square a complex number.
 */
COMPLEX *
csquare(COMPLEX *c)
{
	COMPLEX *r;
	NUMBER *q1, *q2;

	if (ciszero(c))
		return clink(&_czero_);
	if (cisrunit(c))
		return clink(&_cone_);
	if (cisiunit(c))
		return clink(&_cnegone_);
	r = comalloc();
	if (cisreal(c)) {
		qfree(r->real);
		r->real = qsquare(c->real);
		return r;
	}
	if (cisimag(c)) {
		qfree(r->real);
		q1 = qsquare(c->imag);
		r->real = qneg(q1);
		qfree(q1);
		return r;
	}
	q1 = qsquare(c->real);
	q2 = qsquare(c->imag);
	qfree(r->real);
	r->real = qsub(q1, q2);
	qfree(q1);
	qfree(q2);
	qfree(r->imag);
	q1 = qmul(c->real, c->imag);
	r->imag = qscale(q1, 1L);
	qfree(q1);
	return r;
}
Пример #16
0
/*
 * Add an opcode to the current function being compiled.
 * Note: This can change the curfunc global variable when the
 * function needs expanding.
 */
void
addop(long op)
{
    register FUNC *fp;		/* current function */
    NUMBER *q, *q1, *q2;
    unsigned long count;
    BOOL cut;
    int diff;

    fp = curfunc;
    count = fp->f_opcodecount;
    cut = TRUE;
    diff = 2;
    q = NULL;
    if ((count + 5) >= maxopcodes) {
        maxopcodes += OPCODEALLOCSIZE;
        fp = (FUNC *) malloc(funcsize(maxopcodes));
        if (fp == NULL) {
            math_error("cannot malloc function");
            /*NOTREACHED*/
        }
        memcpy((char *) fp, (char *) curfunc,
               funcsize(curfunc->f_opcodecount));
        if (curfunc != functemplate)
            free(curfunc);
        curfunc = fp;
    }

    /*
     * Check the current opcode against the previous opcode and try to
     * slightly optimize the code depending on the various combinations.
     */
    switch (op) {
    case OP_GETVALUE:
        switch (oldop) {
        case OP_NUMBER:
        case OP_ZERO:
        case OP_ONE:
        case OP_IMAGINARY:
        case OP_GETEPSILON:
        case OP_SETEPSILON:
        case OP_STRING:
        case OP_UNDEF:
        case OP_GETCONFIG:
        case OP_SETCONFIG:
            return;
        case OP_DUPLICATE:
            diff = 1;
            oldop = OP_DUPVALUE;
            break;
        case OP_FIADDR:
            diff = 1;
            oldop = OP_FIVALUE;
            break;
        case OP_GLOBALADDR:
            diff = 1 + PTR_SIZE;
            oldop = OP_GLOBALVALUE;
            break;
        case OP_LOCALADDR:
            oldop = OP_LOCALVALUE;
            break;
        case OP_PARAMADDR:
            oldop = OP_PARAMVALUE;
            break;
        case OP_ELEMADDR:
            oldop = OP_ELEMVALUE;
            break;
        default:
            cut = FALSE;

        }
        if (cut) {
            fp->f_opcodes[count - diff] = oldop;
            return;
        }
        break;
    case OP_POP:
        switch (oldop) {
        case OP_ASSIGN:
            fp->f_opcodes[count-1] = OP_ASSIGNPOP;
            oldop = OP_ASSIGNPOP;
            return;
        case OP_NUMBER:
        case OP_IMAGINARY:
            q = constvalue(fp->f_opcodes[count-1]);
            qfree(q);
            break;
        case OP_STRING:
            sfree(findstring((long)fp->f_opcodes[count-1]));
            break;
        case OP_LOCALADDR:
        case OP_PARAMADDR:
            break;
        case OP_GLOBALADDR:
            diff = 1 + PTR_SIZE;
            break;
        case OP_UNDEF:
            fp->f_opcodecount -= 1;
            oldop = OP_NOP;
            oldoldop = OP_NOP;
            return;
        default:
            cut = FALSE;
        }
        if (cut) {
            fp->f_opcodecount -= diff;
            oldop = OP_NOP;
            oldoldop = OP_NOP;
            fprintf(stderr,
                    "Line %ld: unused value ignored\n",
                    linenumber());
            return;
        }
        break;
    case OP_NEGATE:
        if (oldop == OP_NUMBER) {
            q = constvalue(fp->f_opcodes[count-1]);
            fp->f_opcodes[count-1] = addqconstant(qneg(q));
            qfree(q);
            return;
        }
    }
    if (oldop == OP_NUMBER) {
        if (oldoldop == OP_NUMBER) {
            q1 = constvalue(fp->f_opcodes[count - 3]);
            q2 = constvalue(fp->f_opcodes[count - 1]);
            switch (op) {
            case OP_DIV:
                if (qiszero(q2)) {
                    cut = FALSE;
                    break;
                }
                q = qqdiv(q1,q2);
                break;
            case OP_MUL:
                q = qmul(q1,q2);
                break;
            case OP_ADD:
                q = qqadd(q1,q2);
                break;
            case OP_SUB:
                q = qsub(q1,q2);
                break;
            case OP_POWER:
                if (qisfrac(q2) || qisneg(q2))
                    cut = FALSE;
                else
                    q = qpowi(q1,q2);
                break;
            default:
                cut = FALSE;
            }
            if (cut) {
                qfree(q1);
                qfree(q2);
                fp->f_opcodes[count - 3] = addqconstant(q);
                fp->f_opcodecount -= 2;
                oldoldop = OP_NOP;
                return;
            }
        } else if (op != OP_NUMBER) {
            q = constvalue(fp->f_opcodes[count - 1]);
            if (op == OP_POWER) {
                if (qcmpi(q, 2L) == 0) {
                    fp->f_opcodecount--;
                    fp->f_opcodes[count - 2] = OP_SQUARE;
                    qfree(q);
                    oldop = OP_SQUARE;
                    return;
                }
                if (qcmpi(q, 4L) == 0) {
                    fp->f_opcodes[count - 2] = OP_SQUARE;
                    fp->f_opcodes[count - 1] = OP_SQUARE;
                    qfree(q);
                    oldop = OP_SQUARE;
                    return;
                }
            }
            if (qiszero(q)) {
                qfree(q);
                fp->f_opcodes[count - 2] = OP_ZERO;
                fp->f_opcodecount--;
            } else if (qisone(q)) {
                qfree(q);
                fp->f_opcodes[count - 2] = OP_ONE;
                fp->f_opcodecount--;
            }
        }
    }
    /*
     * No optimization possible, so store the opcode.
     */
    fp->f_opcodes[fp->f_opcodecount] = op;
    fp->f_opcodecount++;
    oldoldop = oldop;
    oldop = op;
}
Пример #17
0
// Minimal c++11 implementation of dual quaternion as style agnostic as possible.  
// Assumes there is a float4 struct defined the obvious xyzw way and usual support quat functions.
// This implementation just uses 4x2 matrix where the second ([1]) column is the dual part.
// Feel free to convert to your own design/style preferences and struct names.
// The Pose class is just a position,orientation (vec3,quat) pair defined the obvious way.
// The functions dqmake/dqpose convert Pose to/from dual quat representation.
// 
float4x2 dqmul(const float4x2 &a, float4x2 &b) { return{ qmul(a[0], b[0]), qmul(a[0], b[1]) + qmul(a[1], b[0]) }; }
Пример #18
0
Pose     dqpose(const float4x2 &d) { return{ qmul(d[1], qconj(d[0])).xyz()*2.0f, d[0] }; }
/*
 * Divide two complex numbers.
 */
COMPLEX *
cdiv(COMPLEX *c1, COMPLEX *c2)
{
	COMPLEX *r;
	NUMBER *q1, *q2, *q3, *den;

	if (ciszero(c2)) {
		math_error("Division by zero");
		/*NOTREACHED*/
	}
	if ((c1->real == c2->real) && (c1->imag == c2->imag))
		return clink(&_cone_);
	r = comalloc();
	if (cisreal(c1) && cisreal(c2)) {
		qfree(r->real);
		r->real = qqdiv(c1->real, c2->real);
		return r;
	}
	if (cisimag(c1) && cisimag(c2)) {
		qfree(r->real);
		r->real = qqdiv(c1->imag, c2->imag);
		return r;
	}
	if (cisimag(c1) && cisreal(c2)) {
		qfree(r->imag);
		r->imag = qqdiv(c1->imag, c2->real);
		return r;
	}
	if (cisreal(c1) && cisimag(c2)) {
		qfree(r->imag);
		q1 = qqdiv(c1->real, c2->imag);
		r->imag = qneg(q1);
		qfree(q1);
		return r;
	}
	if (cisreal(c2)) {
		qfree(r->real);
		qfree(r->imag);
		r->real = qqdiv(c1->real, c2->real);
		r->imag = qqdiv(c1->imag, c2->real);
		return r;
	}
	q1 = qsquare(c2->real);
	q2 = qsquare(c2->imag);
	den = qqadd(q1, q2);
	qfree(q1);
	qfree(q2);
	q1 = qmul(c1->real, c2->real);
	q2 = qmul(c1->imag, c2->imag);
	q3 = qqadd(q1, q2);
	qfree(q1);
	qfree(q2);
	qfree(r->real);
	r->real = qqdiv(q3, den);
	qfree(q3);
	q1 = qmul(c1->real, c2->imag);
	q2 = qmul(c1->imag, c2->real);
	q3 = qsub(q2, q1);
	qfree(q1);
	qfree(q2);
	qfree(r->imag);
	r->imag = qqdiv(q3, den);
	qfree(q3);
	qfree(den);
	return r;
}
Пример #20
0
fixedp do_3band(EQSTATE* es, fixedp sample)
{
  // Locals

  fixedp  l,m,h;      // Low / Mid / High - Sample Values

  // Filter #1 (lowpass)

  es->f1p0  = qadd(es->f1p0, qmul(es->lf, qsub(sample,   es->f1p0)));//  + vsa; might need this but i dont think so. who knows?
  es->f1p1  = qadd(es->f1p1, qmul(es->lf, qsub(es->f1p0, es->f1p1)));
  es->f1p2  = qadd(es->f1p2, qmul(es->lf, qsub(es->f1p1, es->f1p2)));
  es->f1p3  = qadd(es->f1p3, qmul(es->lf, qsub(es->f1p2, es->f1p3)));

  l          = es->f1p3;

  // Filter #2 (highpass)
  
  es->f2p0  = qadd(es->f2p0,qmul(es->hf, qsub(sample   , es->f2p0))); // + vsa;
  es->f2p1  = qadd(es->f2p1,qmul(es->hf, qsub(es->f2p0 , es->f2p1)));
  es->f2p2  = qadd(es->f2p2,qmul(es->hf, qsub(es->f2p1 , es->f2p2)));
  es->f2p3  = qadd(es->f2p3,qmul(es->hf, qsub(es->f2p2 , es->f2p3)));

  h          = qsub(es->sdm3, es->f2p3);

  // Calculate midrange (signal - (low + high))

  m          = qsub(es->sdm3, qadd(h, l));

  // Scale, Combine and store

  l         = qmul(l, es->lg);
  m         = qmul(m, es->mg);
  h         = qmul(h, es->hg);

  // Shuffle history buffer 

  es->sdm3   = es->sdm2;
  es->sdm2   = es->sdm1;
  es->sdm1   = sample;                

  // Return result

  return(qadd(l, qadd(m, h)));
}
Пример #21
0
int main(int argc, char *argv[]) try
{
	std::cout << "TestDQ\n";
	Pose camera = { { 0, 0, 8 }, { 0, 0, 0, 1 } };
	bool showaxis = true;
	float3 focuspoint(0, 0, 0);
	float3 mousevec_prev;
	float4 model_orientation(0, 0, 0, 1);
	Pose p0 = { { -3, 0, 0 }, { 0, 0, 0, 1 } };
	Pose p1 = { {  3, 0, 0 }, { 0, 0, sqrtf(0.5f),sqrtf(0.5f) } };
	float dt = 0.01f, t = 0;
	Pose *selected = NULL;
	std::vector<float4> planes = { { 1, 0, 0, 0 }, { 0, 1, 0, 0 }, { 0, 0, 1, 0 }, { -1, 0, 0, 0 }, { 0, -1, 0, 0 }, { 0, 0, -1, 0 } };
	for (auto &p : planes)
		p.w = -0.25f;

	GLWin glwin("Dual Quaternion Pose Interpolation");
	glwin.keyboardfunc = [&](int key, int, int)
	{
		showaxis = key == 'a' != showaxis;
	};
	while (glwin.WindowUp())
	{
		t = t + dt;  // advance our global time    t is in 0..1
		if (t > 1.0f)
			t = 0.0f;

		Pose pt  = dqinterp(p0,p1,t);     // And here we show our dual quaterion usage

		// some extras to help visualize the axis of rotation, not the best math to get the result, but oh well
		float4 aq = qmul(dot(p0.orientation, p1.orientation) < 0 ? -p1.orientation : p1.orientation, qconj(p0.orientation));
		float3 axis = normalize(aq.xyz()*(aq.w < 0 ? -1.0f : 1.0f));  // direction of the axis of rotation
		float3 axisp = cross(axis, p1.position - p0.position) / 2.0f * sqrtf(1/dot(aq.xyz(),aq.xyz())-1);  // origin projected onto the axis of rotation
		// user interaction: 
		float3 ray = qrot(camera.orientation, normalize(glwin.MouseVector));   // for mouse selection
		float3 v1 = camera.position + ray*100.0f;
		if (!glwin.MouseState)  // note that we figure out what is being selected only when the mouse is up
		{
			selected = NULL;
			for (Pose *p : { &p0, &p1 })
			{
				if (auto h = ConvexHitCheck(planes, *p, camera.position, v1))
				{
					selected = p;
					v1 = h.impact;
				}
			}
		}
		else // if (glwin.MouseState)  
		{
			if (selected)
				selected->orientation = qmul(VirtualTrackBall(camera.position, selected->position, qrot(camera.orientation, mousevec_prev), qrot(camera.orientation, glwin.MouseVector)), selected->orientation);
			else
				camera.orientation = qmul(camera.orientation, qconj(VirtualTrackBall(float3(0, 0, 1), float3(0, 0, 0), mousevec_prev, glwin.MouseVector))); // equation is non-typical we are orbiting the camera, not rotating the object
		}
		camera.position = focuspoint + qzdir(camera.orientation)*magnitude(camera.position - focuspoint);
		camera.position -= focuspoint;
		camera.position *= powf(1.1f, (float)glwin.mousewheel);
		camera.position += focuspoint;
		mousevec_prev = glwin.MouseVector;

		// Render the scene
		glPushAttrib(GL_ALL_ATTRIB_BITS); 
		glViewport(0, 0, glwin.Width, glwin.Height); // Set up the viewport
		glClearColor(0.1f, 0.1f, 0.15f, 1);
		glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
		glMatrixMode(GL_PROJECTION);
		glPushMatrix(); glLoadIdentity();
		gluPerspective(glwin.ViewAngle, (double)glwin.Width / glwin.Height, 0.25, 250);
		glMatrixMode(GL_MODELVIEW);
		glPushMatrix(); glLoadIdentity();
		glMultMatrixf(camera.Inverse().Matrix());

		glDisable(GL_LIGHTING); 
		glAxis();  
		glGridxy(4.0f);
		if (showaxis)
		{
			glPushAttrib(GL_ALL_ATTRIB_BITS);
			glLineWidth(3.0f);
			glBegin(GL_LINES);
			glColor3f(1, 1, 1);
			for (auto p : { p0.position, p1.position, pt.position ,axisp})
				glVertex3fv(p - axis*0.5f), glVertex3fv(p + axis*0.5f);  // note the comma
			glEnd();
			glPopAttrib();
			glColor3f(1, 1, 0);
			glBegin(GL_LINES);
			glVertex3fv(axisp + axis*dot(axis, p0.position)), glVertex3fv(axisp + axis*dot(axis, p1.position));
			glVertex3fv(axisp + axis*dot(axis, p0.position)), glVertex3fv(p0.position);
			glVertex3fv(axisp + axis*dot(axis, p1.position)), glVertex3fv(p1.position);
			glVertex3fv(axisp + axis*dot(axis, pt.position)), glVertex3fv(pt.position);
			glEnd();
		}

		glEnable(GL_LIGHTING); glEnable(GL_LIGHT0); glEnable(GL_COLOR_MATERIAL);
		for (auto p : { p0, p1, pt })
			glcolorbox(0.25f, p);

		glPopMatrix();  //should be currently in modelview mode
		glMatrixMode(GL_PROJECTION);
		glPopMatrix();
		glMatrixMode(GL_MODELVIEW);
		glPopAttrib();// Restore state

		glwin.PrintString({ 0, 0 }, "ESC to quit.");
		glwin.PrintString({ 0, 1 }, "'a' show axis (%s)", showaxis ? "on" : "off");
		glwin.PrintString({ 0, 2 }, "%selected: %s", glwin.MouseState?"S":"s", (selected) ? ((selected==&p0)?"box0":"box1") : "none");
		glwin.SwapBuffers();
	}
	std::cout << "\n";
	return 0;
}
catch (std::exception e)
{
	std::cerr << e.what() << "\n";
}
Пример #22
0
void process_overdrive(Distortion *t, fixedp *x) {
	
	Uint32 n;
	fixedp denom, tmp, a, b, numerator, denom1, denom2;

	// kom ihåg förra processens sampel?
	/*if(t->fdb) {
		for(n = 0; n < PROCESS_SIZE; n++) {
			t->prev = qadd( qmul( x[n],t->gain ), qmul( qmul(t->prev, t->gain), t->fdb ) );
			
	
			// 6554 = 0.2
			numeratorLvl1 = qmul(t->lvl1, qexp(qmul(t->prev, qadd(Q1, qmul(6554, qsub(Q1, t->lvl1))))));
			numeratorLvl2 = qmul(t->lvl2, qexp(qmul(-t->prev, qadd(Q1, qmul(6554, qsub(Q1, t->lvl2))))));
			denom = qadd(qexp(t->prev), qexp(-t->prev));
			x[n] = qdiv(qsub(numeratorLvl1, numeratorLvl2), denom);
		}
	} 
	else {*/
		for(n = 0; n < PROCESS_SIZE; n++) {

			t->prev = qmul(x[n],t->gain);
			


			a = qadd(Q1,qmul(3254,qsub(Q1,t->lvl1)));
			b = qadd(Q1,qmul(3254,qsub(Q1,t->lvl2)));
			tmp = qmul(-t->prev, qadd(a,b));
			
			if(tmp > short2q(32)) tmp = short2q(32);
			if(tmp < short2q(-32)) tmp = short2q(-32);
			
			tmp = qexp(tmp);
			numerator = qsub(t->lvl1, qmul(t->lvl2, tmp));
			
			tmp = qmul(t->prev, qsub(Q1, a));

			if(tmp > short2q(32)) tmp = short2q(32);
			if(tmp < short2q(-32)) tmp = short2q(-32);
			denom1 = qexp(tmp);

			tmp = qmul(-t->prev, qadd(Q1, a));

			if(tmp > short2q(32)) tmp = short2q(32);
			if(tmp < short2q(-32)) tmp = short2q(-32);
			denom2 = qexp(tmp);
			
			denom = qadd(denom1, denom2);
			tmp = qdiv(numerator, denom);
			
			if (tmp > AUDIOMAX) {
				// nu är tmp större än 32767
				tmp = AUDIOMAX;
			} else if (tmp < AUDIOMIN) {
				tmp = AUDIOMIN;
			}

			x[n] = tmp;
		}
	//}
}
Пример #23
0
void phaseVocoder_process(PhaseVocoder *t, fixedp *x) {
	// Läs från buffern
	Int32 n, q;
	Int32 rpi, start;
	
	start = segmentIndex * HOP_SIZE;
	for(n=start; n < HOP_SIZE; n++) {
		INPUT_BUFFER_N[start++] = x[n];
		if(start >= 1024) start = 0;
	}
	
	if(++segmentIndex >= 4) segmentIndex = 0;
	
	start = segmentIndex * HOP_SIZE;
	for(n=0; n < FRAME_SIZE; n++) {
		frank[n].r = qmul(INPUT_BUFFER_N[start], HANN[n]);
		frank[n].i = 0;
		start += 1;
		if(start >= 1024) start = 0;
	}
	
	// input buffern är full, 
	process_Segment(t, frank);

	start = segmentIndex * HOP_SIZE;
	for(n = 0; n < 256; n++) {
		x[n] = frank[start+n].r;
		if(start >= 1024) start = 0;
	}

	/*
	for(n = 0; n < FRAME_SIZE; n++) {
		q = t->hopOutIndex+n;
		if( q > BUFFER_SIZE) {
			q -= BUFFER_SIZE;
		}

		if ( n < FRAME_SIZE-(t->hopSizeOut)) {
			OUTPUT_BUFFER_N[q] = qadd(OUTPUT_BUFFER_N[q], qmul(outputFrame[n].r, HANN[n]));
		}
		else {
			OUTPUT_BUFFER_N[q] = qmul(outputFrame[n].r, HANN[n]);  //, 31, FIXED_FRACBITS, FIXED_FRACBITS);
		}
	}

	t->hopOutIndex = t->hopOutIndex + t->hopSizeOut;
	if (t->hopOutIndex >= BUFFER_SIZE) t->hopOutIndex -= BUFFER_SIZE;
	
	rpi = qipart(t->rp);
	for(n=0;n<256;n++) {
		
		x[n] = OUTPUT_BUFFER_N[rpi];
		
		t->rp += t->pShift;
		rpi = qipart(t->rp);
		if(rpi >= 1024) { 
			t->rp -= int2q(1024);
		}
	}*/

	return;
}
Пример #24
0
			inline this_type XM_CALLCONV operator * (const this_type rhs) const
			{
				this_type ret; 
				ret.v = qmul(this->v, rhs.v);
				return ret;
			}
Пример #25
0
main()
{
char s[80];
double fabs(), floor();
#if EXPSCALE || EXPSC2
double exp();
#endif
double sqrt();	/* required to compute rms error */
int i, j, k;
long m, n;

dprec();	/* set up floating point coprocessor */
merror = 0;
/*aiconf = -1;*/	/* configure Airy function */
x = 1.0;
z = x * x;
qclear( qmax );
qtoasc( qmax, strmax, 4 );
qclear( qrmsa );
qclear( qave );

#if 1
printf(" Start at random number #:" );
gets( s );
sscanf( s, "%ld", &n );
printf("%ld\n", n );
#else
n = 0;
#endif

for( m=0; m<n; m++ )
	drand( &x );
n = 0;
m = 0;
x = floor( x );

loop:

for( i=0; i<100; i++ )
{
n++;
m++;

/* make random number in desired range */
drand( &x );
x = WIDTH *  ( x - 1.0 )  +  LOW;
#if EXPSCALE
x = exp(x);
drand( &a );
a = 1.0e-13 * x * a;
if( x > 0.0 )
	x -= a;
else
	x += a;
#endif
#if ONEINT
k = x;
x = k;
#endif
etoq( &x, q1 );		/* double number to q type */

/* do again if second argument required */

#if TWOARG || THREEARG || FOURARG
drand( &a );
a = WIDTHA *  ( a - 1.0 )  +  LOWA;
/*a /= 50.0;*/
#if EXPSC2
a = exp(a);
drand( &y2 );
y2 = 1.0e-13 * y2 * a;
if( a > 0.0 )
	a -= y2;
else
	a += y2;
#endif
#if TWOINT || THREEINT
k = a + 0.25;
a = k;
#endif
etoq( &a, qy4 );
#endif


#if THREEARG || FOURARG
drand( &b );
#if PROB
/*
b = b - 1.0;
b = a * b;
*/
b = WIDTHA *  ( b - 1.0 )  +  LOWA;

/* Half-integer a and b */
/*a = 0.5*floor(2.0*a+1.0);*/
a = 0.5;
b = 0.5*floor(2.0*b+1.0);
etoq( &a, qy4 );
/*x = (a / (a+b));*/

#else
b = WIDTHA *  ( b - 1.0 )  +  LOWA;
#endif
#if THREEINT
j = b + 0.25;
b = j;
#endif
etoq( &b, qb );
#endif

#if FOURARG
drand( &c );
c = WIDTHA *  ( c - 1.0 )  +  LOWA;
/* for hyp2f1 to ensure c-a-b > -1 */
/*
z = c-a-b;
if( z < -1.0 )
	c -= 1.6 * z;
*/
etoq( &c, qc );
#endif

/*printf("%.16E %.16E\n", a, x);*/

/* compute function under test */
#if ONEARG
#if FOURANS
/*FUNC( x, &z, &y2, &y3, &y4 );*/
FUNC( x, &y4, &y2, &y3, &z );
#else
#if TWOANS
FUNC( x, &z, &y2 );
/*FUNC( x, &y2, &z );*/
#else
#if ONEINT
z = FUNC( k );
#else
z = FUNC( x );
#endif
#endif
#endif
#endif

#if TWOARG
#if TWOINT
/*z = FUNC( k, x );*/
/*z = FUNC( x, k );*/
z = FUNC( a, x );
#else
#if FOURANS
FUNC( a, x, &z, &y2, &y3, &y4 );
#else
z = FUNC( a, x );
#endif
#endif
#endif

#if THREEARG
#if THREEINT
z = FUNC( j, k, x );
#else
z = FUNC( a, b, x );
#endif
#endif

#if FOURARG
z = FUNC( a, b, c, x );
#endif

etoq( &z, q2 );

/* handle detected overflow */
if( (z == MAXNUM) || (z == -MAXNUM) )
	{
	printf("detected overflow ");
#if FOURARG
	printf("%.4E %.4E %.4E %.4E %.4E %6ld \n",
		a, b, c, x, y, n);
#else
	printf("%.16E %.4E %.4E %6ld \n", x, a, z, n);
#endif
	e = 0.0;
	m -= 1;
	goto endlup;
	}
/* Skip high precision if underflow.  */
if( merror == UNDERFLOW )
  goto underf;

/* compute high precision function */
#if ONEARG
#if FOURANS
/*QFUNC( q1, qz, qy2, qy3, qy4 );*/
QFUNC( q1, qy4, qy2, qy3, qz );
#else
#if TWOANS
QFUNC( q1, qz, qy2 );
/*QFUNC( q1, qy2, qz );*/
#else
/*qclear( qy4 );*/
/*qmov( qone, qy4 );*/
/*QFUNC( qy4, q1, qz );*/
/*QFUNC( 1, q1, qz );*/
QFUNC( q1, qz );  /* normal */
#endif
#endif
#endif

#if TWOARG
#if TWOINT
/*QFUNC( k, q1, qz );*/
/*QFUNC( q1, qy4, qz );*/
QFUNC( qy4, q1, qz );
#else
#if FOURANS
QFUNC( qy4, q1, qz, qy2, qy3, qc );
#else
/*qclear( qy4 );*/
/*qmov( qone, qy4 );*/
QFUNC( qy4, q1, qz );
#endif
#endif
#endif

#if THREEARG
#if THREEINT
QFUNC( j, k, q1, qz );
#else
QFUNC( qy4, qb, q1, qz );
#endif
#endif

#if FOURARG
QFUNC( qy4, qb, qc, q1, qz );
#endif

qtoe( qz, &y ); /* correct answer, in double precision */


/* get absolute error, in extended precision */
qsub( qz, q2, qe );
qtoe( qe, &e );		/* the error in double precision */

/*  handle function result equal to zero
    or underflowed. */
if( qz[1] < 3 || merror == UNDERFLOW || fabs(z) < underthresh )
	{
underf:
	  merror = 0;
/* Don't bother to print anything.  */
#if 0
	printf("ans 0 ");
#if ONEARG
	printf("%.8E %.8E %.4E %6ld \n", x, y, e, n);
#endif

#if TWOARG
#if TWOINT
	printf("%d %.8E %.8E %.4E %6ld \n", k, x, y, e, n);
#else
	printf("%.6E %.6E %.6E %.4E %6ld \n", a, x, y, e, n);
#endif
#endif

#if THREEARG
	printf("%.6E %.6E %.6E %.6E %.4E %6ld \n", a, b, x, y, e, n);
#endif

#if FOURARG
	printf("%.4E %.4E %.4E %.4E %.4E %.4E %6ld \n",
		a, b, c, x, y, e, n);
#endif
#endif /* 0 */
	qclear( qe );
	e = 0.0;
	m -= 1;
	goto endlup;
	}

else

/*	relative error	*/

/* comment out the following two lines if absolute accuracy report */

#if RELERR
	qdiv( qz, qe, qe );
#else
	{
	qmov( qz, q2 );
	q2[0] = 0;
	if( qcmp( q2, qone ) > 0 )
		qdiv( qz, qe, qe );
	}
#endif

qadd( qave, qe, qave );
/* absolute value of error */
qe[0] = 0;

/* peak detect the error */
if( qcmp(qe, qmax) > 0 )
	{
	qmov( qe, qmax );
	qtoasc( qmax, strmax, 4 );
#if ONEARG
	printf("%.8E %.8E %s %6ld \n", x, y, strmax, n);
#endif
#if TWOARG
#if TWOINT
	printf("%d %.8E %.8E %s %6ld \n", k, x, y, strmax, n);
#else
	printf("%.6E %.6E %.6E %s %6ld \n", a, x, y, strmax, n);
#endif
#endif
#if THREEARG
	printf("%.6E %.6E %.6E %.6E %s %6ld \n", a, b, x, y, strmax, n);
#endif
#if FOURARG
	printf("%.4E %.4E %.4E %.4E %.4E %s %6ld \n",
		a, b, c, x, y, strmax, n);
#endif
	}

/* accumulate rms error	*/
/* rmsa += e * e;  accumulate the square of the error */
qmul( qe, qe, q2 );
qadd( q2, qrmsa, qrmsa );
endlup:
	;
}

/* report every 100 trials */
/* rms = sqrt( rmsa/m ); */
ltoq( &m, q1 );
qdiv( q1, qrmsa, q2 );
qsqrt( q2, q2 );
qtoasc( q2, strrms, 4 );

qdiv( q1, qave, q2 );
qtoasc( q2, strave, 4 );
/*
printf("%6ld   max = %s   rms = %s  ave = %s \n", m, strmax, strrms, strave );
*/
printf("%6ld   max = %s   rms = %s  ave = %s \r", m, strmax, strrms, strave );
fflush(stdout);
goto loop;
}
Пример #26
0
BiQuad* BiQuad_create() {
	BiQuad* filter = (BiQuad*)malloc(sizeof(BiQuad));
	return filter;
}

void BiQuad_FlushDelays(BiQuad* filter) {
	filter->xz1 = short2q(0);
	filter->xz2 = short2q(0);
	filter->yz1 = short2q(0);
	filter->yz2 = short2q(0);
}

// Do the filter: given input xn, calculate output yn and return it
fixedp BiQuad_do(BiQuad* this, fixedp xn) {
	// just do the difference equation: y(n) = a0x(n) + a1x(n-1) + a2x(n-2) - b1y(n-1) - b2y(n-2)
	fixedp a0 = qmul(this->a0, xn);
	fixedp a1 = qmul(this->a1, this->xz1);
	fixedp yn = qadd(a0, a1);
	a1 = qmul(this->a2, this->xz2);
	yn = qadd(yn, a1);
	a1 = qmul(this->b1, this->yz1);
	yn = qsub(yn, a1);
	a1 = qmul(this->b2, this->yz2);
	yn = qsub(yn, a1);
	//float yn = this->a0*xn + this->a1*this->xz1 + this->a2*this->xz2 - this->b1*this->yz1 - this->b2*this->yz2;

	// underflow check
	
	if(yn > 0.0 && yn < FLT_MIN_PLUS) yn = 0;
	if(yn < 0.0 && yn > FLT_MIN_MINUS) yn = 0;