Not logged in.  Login/Logout/Register | List snippets | | Create snippet | Upload image | Upload data

155
LINES

< > BotCompany Repo | #1027225 // MultiLevelRecognizer1 - finds a single prototype image

JavaX fragment (include) [tags: use-pretranspiled]

Uses 108K of libraries. Click here for Pure Java version (10773L/76K).

// complexity is number of assumed heights * number of widths
sclass MultiLevelRecognizer1 {
  // how big do we think the prototype is in the whole image
  // (percentage by height)
  transient L<Double> assumedPrototypeHeightPercentages =
 ll(70.0, 70.0/sqrt(2), 35.0, 35.0/sqrt(2), 17.0);
  
  // widths to scale camera image to
  transient L<Int> widths = ll(32, 64, 128);
  
  transient JTabbedPane tabs; // initialize if you want visualization
  transient ImageSurface bestImageSurface;
  transient JLabel bestLabel;
  
  transient BWIntegralImage baseImage;
  transient BWImage prototypeImage;
  transient new L<IBWIntegralImage> integralImages;
  transient new L<Chain> chains; // one per assumed height
  
  // chain of recognizers for one assumed height
  class Chain {
    double assumedHeightPercentage;
    new L<OneLevel> levels; // recognizers for each granularity
    
    *(double *assumedHeightPercentage) { make(); }

    void make {
      for (int w : widths) {
        IBWIntegralImage ii = scaledIBWIntegralImage(baseImage, w);
        integralImages.add(ii);
        OneLevel lvl = new(this, ii);
        levels.add(lvl);
        if (tabs != null && eq(w, last(widths))) {
          lvl.is = jPixelatedZoomedImageSurface(
            doubleRatio(baseImage.getWidth(), w), iBWIntegralImageToBWImage(ii));
          addTab(tabs, iround(assumedHeightPercentage) + ":" + w, northAndCenterWithMargins(
            lvl.infoLabel = jcenteredlabel(), jFullCenterScroll(lvl.is)));
        }
      }
    }

    Steppable makeSteppable() {
      ret iteratorToSteppable(roundRobinCombinedIterator(lambdaMap steppableToIterator(levels)));
    }
    
    Scored<Rect> bestResult() {
      ret last(levels).scoredBestRescaled();
    }
  }

  class OneLevel extends SteppableAndBest<Rect> {
    Chain chain;
    IBWIntegralImage ii; // scaled integral image
    BWImage image;       // scaled image
    BWImage prototype;   // scaled prototype
    float minSimilarity = 0.5f;
    
    ImageSurface is;
    JLabel infoLabel;

    // candidates are top-left corner of rect to try in our coordinates
    L<Pt> candidatesQueue = syncLinkedList();
    new Set<Pt> candidatesTried;
    Iterator<Pt> candidatesStream;

    *(Chain *chain, IBWIntegralImage *ii) {
      image = iBWIntegralImageToBWImage(ii);
      // get assumed height of prototype in scaled-down image
      int ph = iround(ii.getHeight()*chain.assumedHeightPercentage/100.0);
      // resize prototype
      prototype = bwResizeToHeightSmooth(prototypeImage, ph);
      /*addTab(tabs, "proto " + ii.getWidth(),
 jFullCenterScroll(jPixelatedZoomedImageSurface(4.0, prototype)));
*/
      candidatesStream = mapI rectTopLeftCorner(allSubRectsOfSizeIterator(prototype.getWidth(), prototype.getHeight(),
        imageRect(image)));
    }
    
    public bool step() {
      Pt p = nextCandidate();
      if (p != null) ret true with tryCandidate(p);
      false;
    }

    Pt nextCandidate() {
      try object Pt p = popFirst(candidatesQueue);
      ret nextFromIterator(candidatesStream);
    }

    void tryCandidate(Pt p) {
      if (!candidatesTried.add(p)) ret;

      int x = p.x, y = p.y, wp = prototype.getWidth(), hp = prototype.getHeight();

      float maxError = (1f-minSimilarity)*wp*hp;
      float diff = bwImageSectionsSimilarity(image, prototype, x, y, maxError);
      if (diff <= maxError)
        best.put(new Rect(x, y, wp, hp), 1-diff/(wp*hp));
    }

    void showBest() {
      setImageSurfaceSelection(is, best!);
      setText(infoLabel, best);
    }
    
    // best rect in original image coordinates
    Rect bestRescaled() {
      ret rescaleRect(best!, ii.getWidth(), ii.getHeight(),
        baseImage.getWidth(), baseImage.getHeight());
    }
    
    Scored<Rect> scoredBestRescaled() {
      ret scored(bestRescaled(), best.score);
    }
  }
  
  *() {}
  *(File prototypeImage, File imgFile) {
    this.prototypeImage = loadBWImage(prototypeImage);
    this.baseImage = loadBWIntegralImage(imgFile);
  }

  Scored<Rect> go() {
    assertNotNull(+baseImage);
    assertNotNull(+prototypeImage);
    
    if (tabs != null)
      addTab(tabs, "Best", northAndCenterWithMargins(
        bestLabel = jcenteredlabel(), 
        jFullCenterScroll(bestImageSurface = jImageSurface(bwIntegralImageToBWImage(baseImage)))));
        
    makeChains();

    time "Process" {
      print("Steps: " + stepAll_roundRobin(map(chains, c -> c.makeSteppable())));
    }
  
    showBest();
    ret bestResult();
  }
  
  void showBest {
    for (Chain c : chains)
      for (OneLevel l : c.levels)
        l.showBest();
    setText(bestLabel, bestResult());
    setImageSurfaceSelection(bestImageSurface, bestResult()!);
  }
  
  void makeChains {
    for (double ah : assumedPrototypeHeightPercentages)
      chains.add(new Chain(ah));
  }
      
  Scored<Rect> bestResult() {
    ret bestScored(map(methodLambda0 bestResult, chains));
  }
}

download  show line numbers  debug dex  old transpilations   

Travelled to 7 computer(s): bhatertpkbcr, mqqgnosmbjvj, pyentgdyhuwx, pzhvpgtvlbxg, tvejysmllsmz, vouqrxazstgt, xrpafgyirdlv

No comments. add comment

Snippet ID: #1027225
Snippet name: MultiLevelRecognizer1 - finds a single prototype image
Eternal ID of this version: #1027225/32
Text MD5: 2d327724a16b29fd1513a986e012be05
Transpilation MD5: 3b267b00ce652cb4b0c5826b3fd604cc
Author: stefan
Category: javax / image recognition
Type: JavaX fragment (include)
Public (visible to everyone): Yes
Archived (hidden from active list): No
Created/modified: 2020-02-26 15:16:33
Source code size: 5053 bytes / 155 lines
Pitched / IR pitched: No / No
Views / Downloads: 259 / 700
Version history: 31 change(s)
Referenced in: [show references]