// Called when camera take a frame
  @Override
  public void onPreviewFrame(byte[] data, Camera camera) {

    PlanarYUVLuminanceSource source =
        mCameraManager.buildLuminanceSource(data, mPreviewWidth, mPreviewHeight);

    HybridBinarizer hybBin = new HybridBinarizer(source);
    BinaryBitmap bitmap = new BinaryBitmap(hybBin);

    try {
      Result result = mQRCodeReader.decode(bitmap);

      // Notify We're found a QRCode
      if (mOnQRCodeReadListener != null) {
        // Transform resultPoints to View coordinates
        PointF[] transformedPoints = transformToViewCoordinates(result.getResultPoints());
        mOnQRCodeReadListener.onQRCodeRead(result.getText(), transformedPoints);
      }

    } catch (ChecksumException e) {
      Log.d(TAG, "ChecksumException");
      e.printStackTrace();
    } catch (NotFoundException e) {
      // Notify QR not found
      if (mOnQRCodeReadListener != null) {
        mOnQRCodeReadListener.QRCodeNotFoundOnCamImage();
      }
    } catch (FormatException e) {
      Log.d(TAG, "FormatException");
      e.printStackTrace();
    } finally {
      mQRCodeReader.reset();
    }
  }
  private Result decode(BinaryBitmap bitmap) {
    QRCodeReader qrCodeReader = new QRCodeReader();

    int[] decodeHintAllowedLength = new int[] {qrCodeW, qrCodeH}; // ???
    qrHints.put(DecodeHintType.ALLOWED_LENGTHS, decodeHintAllowedLength);
    qrHints.put(DecodeHintType.TRY_HARDER, Boolean.TRUE);
    // qrHints.put(DecodeHintType.CHARACTER_SET, );

    Result result;
    try {
      result = qrCodeReader.decode(bitmap, qrHints);
    } catch (ReaderException ex) {
      throw new RuntimeException("Failed to decode", ex);
    }
    return result;
  }
        private void decode(final byte[] data) {
          final PlanarYUVLuminanceSource source = cameraManager.buildLuminanceSource(data);
          final BinaryBitmap bitmap = new BinaryBitmap(new HybridBinarizer(source));

          try {
            hints.put(
                DecodeHintType.NEED_RESULT_POINT_CALLBACK,
                new ResultPointCallback() {
                  @Override
                  public void foundPossibleResultPoint(final ResultPoint dot) {
                    runOnUiThread(
                        new Runnable() {
                          @Override
                          public void run() {
                            scannerView.addDot(dot);
                          }
                        });
                  }
                });
            final Result scanResult = reader.decode(bitmap, hints);

            final int thumbnailWidth = source.getThumbnailWidth();
            final int thumbnailHeight = source.getThumbnailHeight();
            final float thumbnailScaleFactor = (float) thumbnailWidth / source.getWidth();

            final Bitmap thumbnailImage =
                Bitmap.createBitmap(thumbnailWidth, thumbnailHeight, Bitmap.Config.ARGB_8888);
            thumbnailImage.setPixels(
                source.renderThumbnail(), 0, thumbnailWidth, 0, 0, thumbnailWidth, thumbnailHeight);

            runOnUiThread(
                new Runnable() {
                  @Override
                  public void run() {
                    handleResult(scanResult, thumbnailImage, thumbnailScaleFactor);
                  }
                });
          } catch (final ReaderException x) {
            // retry
            cameraHandler.post(fetchAndDecodeRunnable);
          } finally {
            reader.reset();
          }
        }
Esempio n. 4
0
  private QrDecodingResult decodeQR(BufferedImage image, int filenumber) {
    // Create qr image from original for decoding

    BufferedImage qrcorner = extractTopRightCornerForQR(image);
    BufferedImage blackWhite =
        new BufferedImage(
            qrcorner.getWidth() / 2, qrcorner.getHeight() / 2, BufferedImage.TYPE_INT_RGB);
    Graphics2D g2d = blackWhite.createGraphics();
    g2d.drawImage(qrcorner, 0, 0, qrcorner.getWidth() / 2, qrcorner.getHeight() / 2, null);
    g2d.dispose();
    qrcorner = blackWhite;

    QrDecodingResult decodingresult = new QrDecodingResult();

    try {

      // Decode QR
      Result result = null;
      Exception decodeException = null;

      // Try to decode at least three times
      int maxattempts = 3;
      int attempt = 1;
      while (attempt <= maxattempts) {
        logger.debug("Attempt " + attempt);
        try {
          BinaryBitmap bitmap = getBitmapFromBufferedImage(qrcorner);
          result = reader.decode(bitmap);
          decodeException = null;
          logger.debug("Success!");
          break;
        } catch (Exception e) {
          decodeException = e;
          if (debugcorners) {
            try {
              ImageIO.write(
                  (RenderedImage) qrcorner,
                  "jpg",
                  new File(
                      tempdir.getAbsolutePath() + "/corner" + filenumber + "_" + attempt + ".jpg"));
            } catch (IOException ex) {
              ex.printStackTrace();
            }
          }
        }
        attempt++;
        com.jhlabs.image.MedianFilter filter = new MedianFilter();
        BufferedImage newqrcorner =
            new BufferedImage(
                qrcorner.getWidth(), qrcorner.getHeight(), BufferedImage.TYPE_BYTE_GRAY);
        filter.filter(qrcorner, newqrcorner);
        qrcorner = newqrcorner;
      }

      if (decodeException != null) throw decodeException;

      // Clean the output from the QR
      decodingresult.setOutput(result.getText().replace(" ", "").trim());

      // The image filename will be the output
      decodingresult.setFilename(decodingresult.getOutput());

      // Consistency checking
      if (decodingresult.getFilename().length() == 0) {
        decodingresult.setFilename("ERROR-EMPTYQR-" + (filenumber + 1));
      } else {
        String[] parts = decodingresult.getFilename().split("-");

        // Now check if the QR string has five parts (which indicates it is an answer sheet)
        if (parts.length == 5 && parts[4].trim().contains("BB")) {
          decodingresult.setAttemptId(Integer.parseInt(parts[3]));
          decodingresult.setAnswersheet(true);
        }

        // Now check if the QR string has a fourth component (image is rotated)
        if (parts.length == 4 && parts[3].trim().contains("R")) {
          decodingresult.setRotated(true);
        }

        // If everything looks well, parse the numbers from the decoded QR info
        if (parts.length >= 3) {

          // Parse the parts (any exception will be caught as an error)
          decodingresult.setUserid(Integer.parseInt(parts[0]));
          decodingresult.setCourseid(Integer.parseInt(parts[1]));
          decodingresult.setExampage(Integer.parseInt(parts[2]));

          // Set filename with the corresponding IDs
          decodingresult.setFilename(
              decodingresult.getUserid()
                  + "-"
                  + decodingresult.getCourseid()
                  + "-"
                  + decodingresult.getExampage());

          // Processing was a success
          decodingresult.setSuccess(true);
        } else {
          logger.error("QR contains invalid information");
          decodingresult.setFilename("ERROR-INVALIDPARTSQR-" + (filenumber + 1));
        }
      }
    } catch (NotFoundException e) {
      decodingresult.setFilename("ERROR-NOTFOUND-" + (filenumber + 1));
    } catch (ChecksumException e) {
      decodingresult.setFilename("ERROR-CHECKSUM-" + (filenumber + 1));
    } catch (FormatException e) {
      decodingresult.setFilename("ERROR-CHECKSUM-" + (filenumber + 1));
    } catch (Exception e) {
      decodingresult.setFilename("ERROR-NULL-" + (filenumber + 1));
    }

    // Regardless of the result, the back-file name is the sames as the file with a b
    decodingresult.setBackfilename(decodingresult.getFilename() + "b");

    return decodingresult;
  }