Question

Je souhaite imprimer un bitmap sur une imprimante Bluetooth mobile (Bixolon SPP-R200) ​​- le SDK n'offre pas de méthodes directes pour imprimer une image en mémoire.J'ai donc pensé à convertir un Bitmap comme ceci :

Bitmap bitmap = Bitmap.createBitmap(width, height, Bitmap.Config.ARGB_8888);

Vers un bitmap monochrome.Je dessine du texte noir sur le Bitmap ci-dessus à l'aide d'un canevas, qui fonctionne bien.Cependant, lorsque je convertis le Bitmap ci-dessus en ByteArray, l'imprimante semble incapable de gérer ces octets.Je soupçonne que j'ai besoin d'un tableau avec un bit par pixel (un pixel serait soit blanc = 1, soit noir = 0).

Comme il ne semble pas y avoir de moyen pratique et original de le faire, une idée que j'ai eue était d'utiliser :

bitmap.getPixels(pixels, offset, stride, x, y, width, height)

pour obtenir les pixels.Je suppose que je devrais l'utiliser comme suit :

int width = bitmap.getWidth();
int height = bitmap.getHeight();

int [] pixels = new int [width * height];
bitmap.getPixels(pixels, 0, width, 0, 0, width, height);

Cependant, je ne suis pas sûr de certaines choses :

  • Dans getPixels, est-il logique de simplement transmettre la largeur comme argument « Stride » ?
  • Je suppose que je devrais évaluer les informations de couleur de chaque pixel et les passer en noir ou en blanc (et j'écrirais cette valeur dans un nouveau tableau d'octets cible que je transmettrais finalement à l'imprimante) ?
  • Comment évaluer au mieux les informations de couleur de chaque pixel afin de décider s'il doit être noir ou blanc ?(Le Bitmap rendu est une douleur noire sur fond blanc)

Cette approche a-t-elle du sens ?Existe-t-il un moyen plus simple ?Il ne suffit pas de rendre le bitmap en noir et blanc, le principal problème est de réduire les informations de couleur de chaque pixel en un seul bit.

MISE À JOUR

Comme suggéré par Reuben, je vais d'abord convertir le Bitmap en Bitmap monochrome.puis je vais parcourir chaque pixel :

    int width = bitmap.getWidth();
    int height = bitmap.getHeight();

    int[] pixels = new int[width * height];
    bitmap.getPixels(pixels, 0, width, 0, 0, width, height);

    // Iterate over height
    for (int y = 0; y < height; y++) {
        int offset = y * height;
        // Iterate over width
        for (int x = 0; x < width; x++) {
            int pixel = bitmap.getPixel(x, y);
        }
    }

Maintenant, Reuben a suggéré de "lire l'octet le plus bas de chaque pixel de 32 bits" - cela serait lié à ma question sur la façon d'évaluer la couleur du pixel.Ma dernière question à ce sujet :Puis-je obtenir l'octet le plus bas en faisant simplement ceci :

// Using the pixel from bitmap.getPixel(x,y)
int lowestByte = pixel & 0xff;
Était-ce utile?

La solution

Vous pouvez convertir l'image en monochrome 32 bpp à l'aide d'un ColorMatrix.

Bitmap bmpMonochrome = Bitmap.createBitmap(width, height, Bitmap.Config.ARGB_8888);
Canvas canvas = new Canvas(bmpMonochrome);
ColorMatrix ma = new ColorMatrix();
ma.setSaturation(0);
Paint paint = new Paint();
paint.setColorFilter(new ColorMatrixColorFilter(ma));
canvas.drawBitmap(bmpSrc, 0, 0, paint);

Cela simplifie la conversion couleur->monochrome.Maintenant, vous pouvez simplement faire un getPixels() et lire l'octet le plus bas de chaque pixel de 32 bits.Si c'est <128 c'est un 0, sinon c'est un 1.

Autres conseils

Eh bien, je pense qu'il est assez tard maintenant pour répondre à ce fil, mais je travaillais aussi parfois sur ce sujet et j'ai décidé de créer ma propre bibliothèque qui convertira n'importe quelle image jpg ou png en 1bpp .bmp.La plupart des imprimantes qui nécessitent des images 1bpp prendront en charge cette image (testée sur l'une d'entre elles :)).Vous trouverez ici une bibliothèque ainsi qu'un projet de test qui l'utilise pour créer une image monochrome monocanal.N'hésitez pas à le changer.. :)

https://github.com/acdevs/1bpp-monochrome-android

Apprécier..!!:)

Conversion en monochrome avec exactement la même taille que le bitmap d'origine pas assez imprimer.

Les imprimantes ne peuvent imprimer chaque "pixel" (point) qu'en monochrome car chaque tache d'encre n'a qu'une seule couleur, elles doivent donc utiliser beaucoup plus de points que nécessaire et ajuster leur taille, leur densité...pour imiter la sensation de niveaux de gris.Cette technique est appelée demi-teintes.Vous pouvez voir que les imprimantes ont souvent une résolution d'au moins 600 dpi, normalement de 1 200 à 4 800 dpi, tandis que l'écran d'affichage atteint souvent 200 à 300 ppi.

Halftone

Votre bitmap monochrome devrait donc être au moins 3 fois la résolution originale de chaque côté.

Vous devez convertir chaque pixel en espace HSV et utiliser la valeur pour déterminer si le pixel de l'image cible doit être noir ou blanc :

  Bitmap bwBitmap = Bitmap.createBitmap( bitmap.getWidth(), bitmap.getHeight(), Bitmap.Config.RGB_565 );
  float[] hsv = new float[ 3 ];
  for( int col = 0; col < bitmap.getWidth(); col++ ) {
    for( int row = 0; row < bitmap.getHeight(); row++ ) {
      Color.colorToHSV( bitmap.getPixel( col, row ), hsv );
      if( hsv[ 2 ] > 0.5f ) {
        bwBitmap.setPixel( col, row, 0xffffffff );
      } else {
        bwBitmap.setPixel( col, row, 0xff000000 );
      }
    }
  }
  return bwBitmap;
Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top