⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 dmtxregion.c

📁 Datamatrix二维码库和测试程序,运行于linux,仔细研究可以很容易转化成VC程序,有这就没必要化钱买个控件了,本人libdmtx-0.3版本转化过,的确可行,现在把找到该版本的libdmtx
💻 C
📖 第 1 页 / 共 4 页
字号:
{   int i;   int sign;   int offset;   DmtxFollow follow;   follow.loc = reg->flowBegin.loc;   offset = dmtxImageGetOffset(dec->image, follow.loc.X, follow.loc.Y);   assert(offset != DMTX_BAD_OFFSET);   follow.step = 0;   follow.ptr = &(dec->image->cache[offset]);   follow.neighbor = *follow.ptr;   sign = (seek > 0) ? +1 : -1;   for(i = 0; i != seek; i += sign) {      follow = FollowStep(dec, reg, follow, sign);      assert(follow.ptr != NULL);      assert(abs(follow.step) <= reg->stepsTotal);   }   return follow;}/** * * */static DmtxFollowFollowSeekLoc(DmtxDecode *dec, DmtxPixelLoc loc){   int offset;   DmtxFollow follow;   follow.loc = loc;   offset = dmtxImageGetOffset(dec->image, follow.loc.X, follow.loc.Y);   assert(offset != DMTX_BAD_OFFSET);   follow.step = 0;   follow.ptr = &(dec->image->cache[offset]);   follow.neighbor = *follow.ptr;   return follow;}/** * * */static DmtxFollowFollowStep(DmtxDecode *dec, DmtxRegion *reg, DmtxFollow followBeg, int sign){   int offset;   int patternIdx;   int stepMod;   int factor;   DmtxFollow follow;   assert(abs(sign) == 1);   assert((int)(followBeg.neighbor & 0x40) != 0x00);   factor = reg->stepsTotal + 1;   if(sign > 0)      stepMod = (factor + (followBeg.step % factor)) % factor;   else      stepMod = (factor - (followBeg.step % factor)) % factor;   /* End of positive trail -- magic jump */   if(sign > 0 && stepMod == reg->jumpToNeg) {      follow.loc = reg->finalNeg;   }   /* End of negative trail -- magic jump */   else if(sign < 0 && stepMod == reg->jumpToPos) {      follow.loc = reg->finalPos;   }   /* Trail in progress -- normal jump */   else {      patternIdx = (sign < 0) ? followBeg.neighbor & 0x07 : ((followBeg.neighbor & 0x38) >> 3);      follow.loc.X = followBeg.loc.X + dmtxPatternX[patternIdx];      follow.loc.Y = followBeg.loc.Y + dmtxPatternY[patternIdx];      follow.loc.status = DMTX_RANGE_GOOD;   }   offset = dmtxImageGetOffset(dec->image, follow.loc.X, follow.loc.Y);   assert(offset != DMTX_BAD_OFFSET);   follow.step = followBeg.step + sign;   follow.ptr = &(dec->image->cache[offset]);   follow.neighbor = *follow.ptr;   return follow;}/** * * */static DmtxFollowFollowStep2(DmtxDecode *dec, DmtxRegion *reg, DmtxFollow followBeg, int sign){   int offset;   int patternIdx;   DmtxFollow follow;   assert(abs(sign) == 1);   assert((int)(followBeg.neighbor & 0x40) != 0x00);   patternIdx = (sign < 0) ? followBeg.neighbor & 0x07 : ((followBeg.neighbor & 0x38) >> 3);   follow.loc.X = followBeg.loc.X + dmtxPatternX[patternIdx];   follow.loc.Y = followBeg.loc.Y + dmtxPatternY[patternIdx];   follow.loc.status = DMTX_RANGE_GOOD;   offset = dmtxImageGetOffset(dec->image, follow.loc.X, follow.loc.Y);   assert(offset != DMTX_BAD_OFFSET);   follow.step = followBeg.step + sign;   follow.ptr = &(dec->image->cache[offset]);   follow.neighbor = *follow.ptr;   return follow;}/** * vaiiiooo * -------- * 0x80 v = visited bit * 0x40 a = assigned bit * 0x38 u = 3 bits points upstream 0-7 * 0x07 d = 3 bits points downstream 0-7 */static intTrailBlazeContinuous(DmtxDecode *dec, DmtxRegion *reg, DmtxPointFlow flowBegin, int maxDiagonal){   int posAssigns, negAssigns, clears;   int sign;   int steps;   int offset;   unsigned char *cache, *cacheNext, *cacheBeg;   DmtxPointFlow flow, flowNext;   DmtxPixelLoc boundMin, boundMax;   /* check offset before starting */   offset = dmtxImageGetOffset(dec->image, flowBegin.loc.X, flowBegin.loc.Y);   if(offset == DMTX_BAD_OFFSET)      return DMTX_FAILURE;   boundMin = boundMax = flowBegin.loc;   cacheBeg = &(dec->image->cache[offset]);   *cacheBeg = (0x80 | 0x40); /* Mark location as visited and assigned */   reg->flowBegin = flowBegin;   posAssigns = negAssigns = 0;   for(sign = 1; sign >= -1; sign -= 2) {      flow = flowBegin;      cache = cacheBeg;      for(steps = 0; ; steps++) {         if(maxDiagonal != -1 && (boundMax.X - boundMin.X > maxDiagonal ||               boundMax.Y - boundMin.Y > maxDiagonal))            break;         /* Find the strongest eligible neighbor */         flowNext = FindStrongestNeighbor(dec, flow, sign);         if(flowNext.mag < 50)            break;         offset = dmtxImageGetOffset(dec->image, flowNext.loc.X, flowNext.loc.Y);         if(offset == DMTX_BAD_OFFSET)            break;         /* Get the neighbor's cache location */         cacheNext = &(dec->image->cache[offset]);         assert(!(*cacheNext & 0x80));         /* Mark departure from current location. If flowing downstream          * (sign < 0) then departure vector here is the arrival vector          * of the next location. Upstream flow uses the opposite rule. */         *cache |= (sign < 0) ? flowNext.arrive : flowNext.arrive << 3;         /* Mark known direction for next location */         /* If testing downstream (sign < 0) then next upstream is opposite of next arrival */         /* If testing upstream (sign > 0) then next downstream is opposite of next arrival */         *cacheNext = (sign < 0) ? (((flowNext.arrive + 4)%8) << 3) : ((flowNext.arrive + 4)%8);         *cacheNext |= (0x80 | 0x40); /* Mark location as visited and assigned */         if(sign > 0)            posAssigns++;         else            negAssigns++;         cache = cacheNext;         flow = flowNext;         if(flow.loc.X > boundMax.X)            boundMax.X = flow.loc.X;         else if(flow.loc.X < boundMin.X)            boundMin.X = flow.loc.X;         if(flow.loc.Y > boundMax.Y)            boundMax.Y = flow.loc.Y;         else if(flow.loc.Y < boundMin.Y)            boundMin.Y = flow.loc.Y;/*       CALLBACK_POINT_PLOT(flow.loc, (sign > 0) ? 2 : 3, 1, DMTX_DISPLAY_POINT); */      }      if(sign > 0) {         reg->finalPos = flow.loc;         reg->jumpToNeg = steps;      }      else {         reg->finalNeg = flow.loc;         reg->jumpToPos = steps;      }   }   reg->stepsTotal = reg->jumpToPos + reg->jumpToNeg;   reg->boundMin = boundMin;   reg->boundMax = boundMax;   /* Clear "visited" bit from trail */   clears = TrailClear(dec, reg, 0x80);   assert(posAssigns + negAssigns == clears - 1);   /* XXX clean this up ... redundant test above */   if(maxDiagonal != -1 && (boundMax.X - boundMin.X > maxDiagonal ||         boundMax.Y - boundMin.Y > maxDiagonal))      return DMTX_FAILURE;   return DMTX_SUCCESS;}/** * recives bresline, and follows strongest neighbor unless it involves * ratcheting bresline inward or backward (although back + outward is allowed). * */static intTrailBlazeGapped(DmtxDecode *dec, DmtxRegion *reg, DmtxBresLine line, int streamDir){   unsigned char *beforeCache, *afterCache;   int err;   int onEdge;   int distSq, distSqMax;   int travel, outward;   int xDiff, yDiff;   int steps;   int stepDir, dirMap[] = { 0, 1, 2, 7, 8, 3, 6, 5, 4 };   DmtxPixelLoc beforeStep, afterStep;   DmtxPointFlow flow, flowNext;   DmtxPixelLoc loc0;   int xStep, yStep;   loc0 = line.loc;   flow = GetPointFlow(dec, reg->flowBegin.plane, loc0, dmtxNeighborNone);   distSqMax = (line.xDelta * line.xDelta) + (line.yDelta * line.yDelta);   steps = 0;   onEdge = 1;   beforeStep = loc0;   beforeCache = GetCacheAddress(dec, loc0.X, loc0.Y);   if(beforeCache == NULL)      return DMTX_FAILURE;   else      *beforeCache = 0x00; /* probably should just overwrite one direction */   do {      if(onEdge != 0) {         flowNext = FindStrongestNeighbor(dec, flow, streamDir);         if(flowNext.mag == -1)            break;         err = BresLineGetStep(line, flowNext.loc, &travel, &outward);         if(flowNext.mag < 50 || outward < 0 || (outward == 0 && travel < 0)) {            onEdge = 0;         }         else {            BresLineStep(&line, travel, outward);            flow = flowNext;         }      }      if(!onEdge) {         BresLineStep(&line, 1, 0);         flow = GetPointFlow(dec, reg->flowBegin.plane, line.loc, dmtxNeighborNone);         if(flow.mag > 50)            onEdge = 1;      }      afterStep = line.loc;      afterCache = GetCacheAddress(dec, afterStep.X, afterStep.Y);      if(afterCache == NULL)         break;      /* Determine step direction using pure magic */      xStep = afterStep.X - beforeStep.X;      yStep = afterStep.Y - beforeStep.Y;      assert(abs(xStep) <= 1 && abs(yStep) <= 1);      stepDir = dirMap[3 * yStep + xStep + 4];      assert(stepDir != 8);      if(streamDir < 0) {         *beforeCache |= (0x40 | stepDir);         *afterCache = (((stepDir + 4)%8) << 3);      }      else {         *beforeCache |= (0x40 | (stepDir << 3));         *afterCache = ((stepDir + 4)%8);      }      /* Guaranteed to have taken one step since top of loop */      xDiff = line.loc.X - loc0.X;      yDiff = line.loc.Y - loc0.Y;      distSq = (xDiff * xDiff) + (yDiff * yDiff);      beforeStep = line.loc;      beforeCache = afterCache;      steps++;   } while(distSq < distSqMax);   return steps;}/** * * */static intTrailClear(DmtxDecode *dec, DmtxRegion *reg, int clearMask){   int clears;   DmtxFollow follow;   assert((clearMask | 0xff) == 0xff);   /* Clear "visited" bit from trail */   clears = 0;   follow = FollowSeek(dec, reg, 0);   while(abs(follow.step) <= reg->stepsTotal) {      assert((int)(*follow.ptr & clearMask) != 0x00);      *follow.ptr &= (clearMask ^ 0xff);      follow = FollowStep(dec, reg, follow, +1);      clears++;   }   return clears;}/** * * */static DmtxBestLineFindBestSolidLine(DmtxDecode *dec, DmtxRegion *reg, int step0, int step1, int streamDir, int houghAvoid){   int hough[3][DMTX_HOUGH_RES] = { { 0 } };   int houghMin, houghMax;   char houghTest[DMTX_HOUGH_RES];   int i;   int step;   int sign;   int tripSteps;   int angleBest;   int hOffset, hOffsetBest;   int xDiff, yDiff;   int dH;   DmtxRay2 rH;   DmtxFollow follow;   DmtxBestLine line;   DmtxPixelLoc rHp;   memset(&line, 0x00, sizeof(DmtxBestLine));   memset(&rH, 0x00, sizeof(DmtxRay2));   angleBest = 0;   hOffset = hOffsetBest = 0;   /* Always follow path flowing away from the trail start */   if(step0 != 0) {      if(step0 > 0) {         sign = +1;         tripSteps = (step1 - step0 + reg->stepsTotal) % reg->stepsTotal;      }      else {         sign = -1;         tripSteps = (step0 - step1 + reg->stepsTotal) % reg->stepsTotal;      }      if(tripSteps == 0)         tripSteps = reg->stepsTotal;   }   else if(step1 != 0) {      sign = (step1 > 0) ? +1 : -1;      tripSteps = abs(step1);   }   else if(step1 == 0) {      sign = +1;      tripSteps = reg->stepsTotal;   }   assert(sign == streamDir);   follow = FollowSeek(dec, reg, step0);   rHp = follow.loc;   line.stepBeg = line.stepPos = line.stepNeg = step0;   line.locBeg = follow.loc;   line.locPos = follow.loc;   line.locNeg = follow.loc;   /* Predetermine which angles to test */   for(i = 0; i < DMTX_HOUGH_RES; i++) {      if(houghAvoid == -1) {         houghTest[i] = 1;      }      else {         houghMin = (houghAvoid + DMTX_HOUGH_RES/6) % DMTX_HOUGH_RES;         houghMax = (houghAvoid - DMTX_HOUGH_RES/6 + DMTX_HOUGH_RES) % DMTX_HOUGH_RES;         if(houghMin > houghMax)            houghTest[i] = (i > houghMin || i < houghMax) ? 1 : 0;         else            houghTest[i] = (i > houghMin && i < houghMax) ? 1 : 0;      }   }   /* Test each angle for steps along path */   for(step = 0; step < tripSteps; step++) {      xDiff = follow.loc.X - rHp.X;      yDiff = follow.loc.Y - rHp.Y;      /* Increment Hough accumulator */      for(i = 0; i < DMTX_HOUGH_RES; i++) {         if((int)houghTest[i] == 0)            continue;         dH = (rHvX[i] * yDiff) - (rHvY[i] * xDiff);         if(dH >= -384 && dH <= 384) {            if(dH > 128)               hOffset = 2;            else if(dH >= -128)               hOffset = 1;            else               hOffset = 0;            hough[hOffset][i]++;            /* New angle takes over lead */            if(hough[hOffset][i] > hough[hOffsetBest][angleBest]) {               angleBest = i;               hOffsetBest = hOffset;            }         }      }/*    CALLBACK_POINT_PLOT(follow.loc, (sign > 1) ? 4 : 3, 1, DMTX_DISPLAY_POINT); */      follow = FollowStep(dec, reg, follow, sign);   }   line.angle = angleBest;   line.hOffset = hOffsetBest;   line.mag = hough[hOffsetBest][angleBest];   return line;}/** * * */static DmtxBestLineFindBestSolidLine2(DmtxDecode *dec, DmtxRegion *reg, DmtxPixelLoc loc0, int tripSteps, int sign, int houghAvoid){   int hough[3][DMTX_HOUGH_RES] = { { 0 } };   int houghMin, houghMax;   char houghTest[DMTX_HOUGH_RES];   int i;   int step;   int angleBest;   int hOffset, hOffsetBest;   int xDiff, yDiff;   int dH;   DmtxRay2 rH;   DmtxBestLine line;   DmtxPixelLoc rHp;   DmtxFollow follow;   memset(&line, 0x00, sizeof(DmtxBestLine));   memset(&rH, 0x00, sizeof(DmtxRay2));

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -