Pour certaines raisons de compatibilité mobile, l'un de nos projets nécessite que le front-end convertisse le PDF en une interface pouvant être visualisée directement sur la page mobile. Afin de faciliter la solution, nous utilisons le plug-in pdf.js, qui peut convertir le pdf en canevas et le dessiner sur la page. Cependant, au cours du processus de test, il a été découvert que sur le navigateur mobile, le contenu affiché était très flou (comme indiqué ci-dessous). Après analyse, il a été constaté que cela était dû à l'écran haute définition du terminal mobile. Après avoir résolu le problème, notez les raisons et les conclusions par écrit.
Avant d'expliquer le problème, vous devez d'abord comprendre quelques connaissances de base sur l'affichage mobile et les cavans pour faciliter une exploration plus approfondie. Si vous souhaitez voir les résultats directement, vous pouvez faire défiler jusqu'à la fin.
Quelques connaissances de base sur les écrans Pixels physiques (DP)Les pixels physiques sont également appelés pixels de l'appareil. Nous entendons souvent dire que la résolution des téléphones mobiles est constituée de pixels physiques. Par exemple, la résolution physique de l'iPhone 7 est de 750 * 1334. L'écran est composé de pixels, ce qui signifie que l'écran a 750 pixels dans le sens horizontal et 1334 pixels dans le sens vertical.
Pixel indépendant de l'appareil (DIP)Également appelés pixels logiques, par exemple, les tailles de l'Iphone4 et de l'Iphone3GS sont toutes deux de 3,5 pouces. La résolution physique de l'iPhone4 est de 640 * 980, tandis que celle du 3gs n'est que de 320 * 480. Si nous dessinons une image d'une largeur de 320 pixels selon le. disposition réelle, sur l'iPhone 4. Seule la moitié de l'écran a du contenu et la moitié restante est vide. Afin d'éviter ce problème, nous avons introduit des pixels logiques et défini les pixels logiques des deux téléphones mobiles sur 320 pixels pour faciliter le dessin.
Rapport de pixels de l'appareil (DPR)Les pixels indépendants du périphérique ci-dessus sont finalement destinés à faciliter le calcul. Nous avons unifié les pixels logiques du périphérique, mais les pixels physiques représentés par chaque pixel logique ne sont pas certains. Afin de déterminer la relation entre les pixels physiques et les pixels logiques sans mise à l'échelle, , nous avons introduit le concept de ratio de pixels de l'appareil (DPR)
Rapport de pixels de l'appareil = pixels de l'appareil / pixels logiques DPR = DP / DIP
Il existe de nombreuses théories mentionnées ci-dessus. Voici une image pour expliquer.
Comme le montre la figure ci-dessus, avec la même taille de pixels logiques, un écran haute définition possède plus de pixels physiques. Sous un écran normal, 1 pixel logique correspond à 1 pixel physique, tandis que sous un écran haute définition avec dpr = 2, 1 pixel logique est composé de 4 pixels physiques. C'est aussi la raison pour laquelle les écrans haute définition sont plus délicats.
Quelques connaissances de base sur la toile Canvas dessine des bitmapsC'est un point de connaissance que tous ceux qui connaissent Canvas devraient connaître, et c'est aussi le cœur du problème que nous analyserons ensuite.
Nous laisserons l'explication des bitmaps plus tard. Il ne nous reste plus qu'à savoir que l'image dessinée par Canvas est un bitmap.
Les propriétés de largeur et de hauteur de la toileLes attributs de largeur et de hauteur de la toile sont très faciles à commettre pour les débutants. Ces deux propriétés sont souvent confondues avec les propriétés width et height en CSS.
Par exemple, nous avons le code suivant (1) :
<largeur du canevas=600 hauteur=300 style=largeur : 300px hauteur : 150px></canvas>
Si vous n’arrivez toujours pas à le comprendre, vous pouvez l’imaginer comme le code suivant (2) :
<!-- Les pixels de logo.png sont 600 * 300 --><img style=width: 300px height: 150px src=logo.png />
La largeur et la hauteur par défaut du canevas sont de 300 * 150. Après avoir défini le CSS dessus, le canevas sera mis à l'échelle (notez qu'il n'est pas recadré) en fonction de la largeur et de la hauteur CSS définies . C'est la même chose que la balise img.
Le code ci-dessus (1) peut en fait être expliqué d'une manière plus populaire, c'est-à-dire qu'un pixel logique est en fait rempli par deux pixels de canevas.
Une discussion préliminaire sur les causes de l’ambiguïtéCe qui précède est une introduction à certaines connaissances de base requises, et l'exploration formelle commencera ci-dessous.
Tout d'abord, nous avons mentionné que l'utilisation de Canvas pour dessiner des images est du bitmap, et que les fichiers jpg et png que nous utilisons habituellement sont également des bitmaps. Alors, qu’est-ce qu’un bitmap ?
Bitmap, également appelé carte de pixels ou carte raster, stocke et affiche les images en enregistrant la couleur, la profondeur, la transparence et d'autres informations de chaque point de l'image. Pour le dire plus concrètement, vous pouvez considérer un bitmap comme un énorme puzzle. Ce puzzle comporte d'innombrables pièces, et chaque pièce représente un pixel de couleur unie. Théoriquement, un pixel bitmap correspond à un pixel physique . Mais que se passe-t-il si vous utilisez un écran haute définition, tel que l'écran Retina d'Apple, pour visualiser une image ?
Supposons que nous ayons le code suivant, qui sera affiché sur l'écran Retina de l'iPhone 4 :
<largeur du canevas=320 hauteur=150 style=largeur : 320px hauteur : 150px></canvas>
Les pixels physiques de l'iPhone 4 lui-même sont de 640 * 980, tandis que les pixels indépendants de l'appareil sont de 320 * 480, ce qui signifie qu'un pixel CSS est en fait composé de 4 pixels physiques. Les pixels du canevas sont de 320 * 150 et ses pixels CSS sont. 320 * 150. Cela signifie que 1 pixel css sera composé de 1 élément canvas, donc la conversion est effectuée, Sur un écran Retina, un pixel de toile (ou un pixel bitmap) remplira 4 pixels physiques. Puisqu'un seul pixel bitmap ne peut pas être divisé davantage, il ne peut prendre que la couleur la plus proche, ce qui rend l'image floue.
Si vous êtes toujours confus, l'image suivante peut illustrer comment le bitmap est rempli sur l'écran Retina :
Le côté gauche de l'image ci-dessus montre les règles d'affichage sur un écran normal. On peut voir qu'il y a 4 pixels bitmap, tandis que l'écran haute définition de droite a 16 pixels. Comme les pixels ne peuvent pas être coupés, la couleur change.
Mais une chose qui n’a pas été expliquée clairement est la raison pour laquelle l’image prend la couleur la plus proche au lieu de prendre directement la valeur d’origine. C’est également la cause du flou.
L'homme dans les coulisses --- lisser la technologieVoici ce qu'un de mes camarades de classe m'a aidé à expliquer. Nous venons de dire que chaque élément bitmap est en fait un pixel de couleur unie. Supposons maintenant que nous devions dessiner un chiffre 0 sur un écran normal avec une taille CSS de 4px * 4px et un dpr de 1. Ensuite, ce que nous dessinons devrait ressembler à l'image suivante, où 1 représente les pixels noirs et 0 représente les pixels blancs.
On peut voir que lorsque le dpr est relativement petit, notre motif 0 est encore relativement évident. Maintenant, si notre taille CSS reste inchangée, mais que l'image est dessinée sur l'écran Retina, quel sera l'effet ?
Nous savons que sous l'écran rétine, un pixel CSS représente 4 pixels physiques. Si nous n'effectuons aucun traitement, organisons directement selon la matrice ci-dessus et développons la matrice, nous constaterons que sous l'écran rétine, notre motif a un. sentiment irrégulier très évident. L'image manque clairement d'un soupçon de teinte.
Si nous modifions légèrement l'image, remplacez-la par l'image suivante
L'image semble instantanément plus douce, mais l'endroit qui aurait dû être rempli de 4 0 est devenu 3 1 plus 1 0. Il s'agit en fait du processus de lissage de l'image. Afin de résoudre la sensation d'irrégularité, la couleur d'origine est modifiée sur les images remplies de plus de couleurs, afin d'être plus naturelles, les joints des images deviennent également des couleurs approximatives. explique pourquoi Lors du remplissage de la couleur ci-dessus, ce n'est pas la couleur d'origine mais la couleur approximative qui est utilisée.
Résumé des raisonsAprès l'explication ci-dessus, résumons maintenant les conclusions suivantes. Maintenant que les terminaux mobiles sont populaires et que les écrans haute définition sont devenus populaires, un pixel CSS de 1 px représente en réalité 4 pixels physiques ou plus. Cependant, en raison de notre problème de code, notre pixel CSS de 1 px et notre pixel de canevas sont égaux, ce qui signifie que 1 pixel de canevas doit en fait être rempli avec 4 pixels physiques ou plus afin d'assurer un traitement d'image fluide, le remplissage physique restant. les pixels utilisent une approximation de la couleur d’origine, ce qui donne une image floue.
Idées de solutionsUne fois que vous avez compris la cause du problème, il est facile de résoudre le problème. La chose la plus importante pour résoudre le problème est d'égaliser un pixel de toile et un pixel physique.
Il y a un attribut devicePixelRatio suspendu sous l'objet window des navigateurs de version supérieure, qui est le dpr mentionné ci-dessus.
Lorsque la largeur et la hauteur CSS de l'élément canevas sont déterminées, nous pouvons le faire
let canvas = document.getElementById('canvas');let ctx = canvas.getContext('2d');let dpr = window.devicePixelRatio; // Supposons que dpr soit 2// Obtenez la largeur et la hauteur du CSS let { width: cssWidth, hauteur : cssHeight } = canvas.getBoundingClientRect();// Selon dpr, agrandissez les pixels du canevas de sorte qu'un pixel du canevas soit égal à un pixel physique canvas.width = dpr * cssWidth; canvas.height = dpr * cssHeight; Le canevas s'agrandit également. Si le contenu du dessin est basé sur le système de coordonnées d'origine, le contenu sera réduit // donc l'échelle du dessin doit être agrandie ctx.scale(dpr,dpr);Résumé de l'expérience
Souvent, lorsque nous trouvons un problème, nous ne pouvons pas nous concentrer sur sa résolution. Au lieu de cela, nous devons comprendre profondément la cause du problème afin de pouvoir mieux avancer.
Ce qui précède représente l’intégralité du contenu de cet article. J’espère qu’il sera utile à l’étude de chacun. J’espère également que tout le monde soutiendra le réseau VeVb Wulin.