📄 outline.cpp
字号:
//////////////////////////////////////////////////////////////////////// outline.c// // Constructs the data structures that contain the head outline.//////////////////////////////////////////////////////////////////////// includes#include <stdlib.h> // malloc()#include <stdio.h> // sprintf()#include <memory.h> // memset()#include <math.h>#include "outline.h"/////////////////////////////////////////////////////////////////////////////// Given an outline whose perimeter and bounding box (halfsize_[x,y])// have been determined, this function allocates and constructs the mask.// Returns the number of pixels in the mask.static int MakeMask(OUTLINE *outline){ unsigned char *ptrmask; short *ptrperim; int *mins, *maxs; int *ptrmin, *ptrmax; int x, y; int i, j; int sizex = 2*(outline->halfsize_x)+1; int sizey = 2*(outline->halfsize_y)+1; int n_pixels = 0; mins = (int *) malloc(sizey * sizeof(int)); maxs = (int *) malloc(sizey * sizeof(int)); outline->mask = (unsigned char *) malloc(sizex * sizey * sizeof(char)); // initialize mins and maxs ptrmin = mins; ptrmax = maxs; for (i = 0 ; i < sizey ; i++) { *ptrmin++ = 999; *ptrmax++ = -999; } // initialize mask to zero memset(outline->mask, 0, sizex*sizey); // fill in max and min vectors ptrperim = outline->perim; x = outline->halfsize_x + *ptrperim++; y = outline->halfsize_y + *ptrperim++; ptrmax = maxs + y; ptrmin = mins + y; *ptrmax = x; *ptrmin = x; for (i = 1 ; i < outline->perim_length ; i++) { x += *ptrperim++; ptrmax += *ptrperim; ptrmin += *ptrperim++; if (x > *ptrmax) *ptrmax = x; if (x < *ptrmin) *ptrmin = x; } // use max and min vectors to fill in mask // the interior of the object is filled in, but not the perimeter ptrmin = mins; ptrmax = maxs; for (i = 0 ; i < sizey ; i++) { ptrmask = (outline->mask) + i * sizex; if (*ptrmin < *ptrmax) { ptrmask += *ptrmin + 1; for (j = *ptrmin + 1 ; j < *ptrmax ; j++) { *ptrmask++ = 255; n_pixels++; } } ptrmin++; ptrmax++; } return n_pixels;}//////////////////////////////////////////////////////////////////////// makeEllipticalOutline// // Creates an elliptical outline, used as a model for the head. // // INPUTS// xrad, yrad: length of the minor and major axes, respectively,// of the ellipse (in pixels).// // NOTES// xrad < yrad//////////////////////////////////////////////////////////////////////void MakeEllipticalOutline(OUTLINE *outline, int xrad, int yrad){ short *ptr; float *ptrn; int xradsq = xrad * xrad; int yradsq = yrad * yrad; double ratio = ((double) xradsq) / ((double) yradsq); int xradbkpt = (int) (xradsq / sqrt((double) xradsq + yradsq)); int yradbkpt = (int) (yradsq / sqrt((double) xradsq + yradsq)); int x, y; // x & y are in image coordinates int curx, cury; // count # of iterations in loops below outline->perim_length = 4 * xradbkpt + 4 * yradbkpt + 4; outline->perim = (short *) malloc(2 * (outline->perim_length) * sizeof(short)); outline->normals = (float *) malloc(2 * (outline->perim_length) * sizeof(float)); ptr = outline->perim; ptrn = outline->normals; *(ptr)++ = curx = 0; // perimeter starts at top and proceeds clockwise *(ptr)++ = cury = - yrad; *ptrn++ = 0.0f; *ptrn++ = -1.0f; // from 0 to 45 degrees, measured cw from top for (x = 1; x <= xradbkpt ; x++) { y = (int) (-yrad * sqrt(1 - ((double) x / xrad)*((double) x / xrad))); *(ptr)++ = x - curx; *(ptr)++ = y - cury; *ptrn++ = (float) ( x / sqrt(x*x + ratio*y*y)); *ptrn++ = (float) ((ratio*y) / sqrt(x*x + ratio*y*y)); curx = x; cury = y; } // from 45 to 135 degrees (including right axis) for (y = - yradbkpt ; y <= yradbkpt ; y++) { x = (int) (xrad * sqrt(1 - ((double) y / yrad)*((double) y / yrad))); *(ptr)++ = x - curx; *(ptr)++ = y - cury; *ptrn++ = (float) ( x / sqrt(x*x + ratio*y*y)); *ptrn++ = (float) ((ratio*y) / sqrt(x*x + ratio*y*y)); curx = x; cury = y; } // from 135 to 225 degrees (including down axis) for (x = xradbkpt ; x >= - xradbkpt ; x--) { y = (int) (yrad * sqrt(1 - ((double) x / xrad)*((double) x / xrad))); *(ptr)++ = x - curx; *(ptr)++ = y - cury; *ptrn++ = (float) ( x / sqrt(x*x + ratio*y*y)); *ptrn++ = (float) ((ratio*y) / sqrt(x*x + ratio*y*y)); curx = x; cury = y; } // from 225 to 315 degrees (including left axis) for (y = yradbkpt ; y >= - yradbkpt ; y--) { x = (int) (-xrad * sqrt(1 - ((double) y / yrad)*((double) y / yrad))); *(ptr)++ = x - curx; *(ptr)++ = y - cury; *ptrn++ = (float) ( x / sqrt(x*x + ratio*y*y)); *ptrn++ = (float) ((ratio*y) / sqrt(x*x + ratio*y*y)); curx = x; cury = y; } // from 315 to 360 degrees for (x = - xradbkpt ; x < 0 ; x++) { y = (int) (-yrad * sqrt(1 - ((double) x / xrad)*((double) x / xrad))); *(ptr)++ = x - curx; *(ptr)++ = y - cury; *ptrn++ = (float) ( x / sqrt(x*x + ratio*y*y)); *ptrn++ = (float) ((ratio*y) / sqrt(x*x + ratio*y*y)); curx = x; cury = y; } outline->halfsize_x = xrad; outline->halfsize_y = yrad; outline->area = MakeMask(outline);}// Prints the perimeter of an outlinevoid print_perim(OUTLINE *outline){ int i; int x, y; int incx, incy; short *ptr; char msg[80]; ptr = outline->perim; x = 50; y = 50; for (i = 0 ; i < outline->perim_length ; i++) { incx = *ptr++; incy = *ptr++; x += incx; y += incy; sprintf(msg, "inc: (%d %d), loc: (%d %d)", incx, incy, x, y);// avpPutMessage(msg); }}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -