라이트 텍스트와 배경 이미지 사이의 완벽한 대비를 못함
가벼운 배경 이미지에 겹쳐진 웹 사이트에서 가벼운 텍스트를 접한 적이 있습니까? 당신이 그것을 발견했다면, 당신은 그것이 읽기가 얼마나 어려운지 알게 될 것입니다. 이를 피하는 일반적인 방법 중 하나는 투명한 오버레이를 사용하는 것입니다. 그러나 이것은 중요한 질문을 제기합니다. 오버레이의 투명성은 얼마나 높아야합니까? 우리는 항상 같은 글꼴 크기, 두께 및 색상을 다루지는 않으며 물론 다른 그림도 다른 대비를 생성합니다.
고블린 게임을하는 것처럼 배경 이미지에서 텍스트 대비가 열악한 문제를 제거하십시오. 추측보다는 HTML을 사용하십시오<canvas></canvas>
이 문제를 해결하기위한 몇 가지 수학적 방법.
이와 같이:
우리는 "문제가 해결되었습니다!"라고 말할 수 있습니다. 그런 다음이 기사를 끝내십시오. 그러나 이것의 재미는 무엇입니까? 내가 보여주고 싶은 것은이 도구가 어떻게 작동하는지이 일반적인 문제를 처리 할 수있는 새로운 방법을 마스터 할 수 있습니다.
계획
먼저 목표를 명확히하겠습니다. 우리는 배경 이미지에 읽을 수있는 텍스트를 표시하고 싶다고 말했지만 "읽기 쉬운"은 정확히 무엇을 의미합니까? 우리의 목적을 위해, 우리는 AA 수준의 가독성에 대한 WCAG의 정의를 사용할 것입니다. 이는 텍스트와 배경 색상 사이에 충분한 대비가 필요하여 한 색상이 다른 색보다 4.5 배 더 밝습니다.
시작점으로 텍스트 색상, 배경 이미지 및 오버레이 색상을 선택합시다. 이러한 입력을 감안할 때 이미지를 너무 많이 숨기지 않고 텍스트를 읽을 수 있도록 오버레이 불투명도 레벨을 찾고 싶습니다. 물건을 조금 복잡하게하기 위해 어둡고 밝은 색상의 그림을 사용하고 오버레이가이를 고려해야합니다.
우리의 최종 결과는 오버레이의 CSS 불투명도 속성에 적용 할 수있는 값이 될 것이며, 이는 텍스트를 배경보다 4.5 배 더 밝게 만듭니다.
최고의 오버레이 불투명도를 찾으려면 4 단계를 수행합니다.
- 우리는 이미지를 HTML에 넣었습니다
<canvas></canvas>
이를 통해 그림에서 각 픽셀의 색상을 읽을 수 있습니다. - 우리는 텍스트와 가장 대비되는 그림에서 픽셀을 찾을 것입니다.
- 다음으로, 우리는 해당 픽셀의 색상에 대한 다른 불투명도 수준의 영향을 테스트하는 데 사용할 수있는 색상 믹싱 공식을 준비합니다.
- 마지막으로 텍스트 대비가 가독성 목표에 도달 할 때까지 오버레이의 불투명도를 조정합니다. 이것은 무작위 추측이 아닙니다. 이진 검색 기술을 사용 하여이 프로세스 속도를 높일 것입니다.
시작합시다!
1 단계 : 캔버스에서 이미지 색상을 읽으십시오
캔버스를 사용하면 이미지에 포함 된 색상을 "읽을"할 수 있습니다. 이를 위해서는 이미지를<canvas></canvas>
요소에서 캔버스 컨텍스트 (CTX)의 getImageData()
메소드를 사용하여 이미지 색상 목록을 생성하십시오.
함수 getImagePixelColorsUsUsingCanvas (이미지, 캔버스) { // 캔버스의 컨텍스트 (일반적으로 CTX로 약칭)는 캔버스를 제어하기위한 많은 기능을 포함하는 객체입니다. const ctx = canvas.getContext ( '2d'); // 너비는 값이 될 수 있으므로 세부 사항을 캡처하기에 충분히 크지 만 계산을 더 빨리 만들기에 충분히 작기 때문에 500을 선택했습니다. Canvas.width = 500; // 캔버스가 이미지 캔버스의 스케일과 일치하는지 확인하십시오 .Height = (image.height / image.width) * canvas.width; // 이미지 및 캔버스의 측정 값을 얻을 수 있도록 다음 단계에서 사용할 수 있도록 sourceimagecoordinates = [0, 0, image.width, image.height]; Const DestinationCanvasCoordinates = [0, 0, Canvas.Width, Canvas.Height]; // CANVAS 'DrawImage ()는 이미지의 측정 값을 ctx.DrawImage에 그려려는 캔버스에 캔버스에 매핑하여 작동합니다. 영상, ... SourceImageCoordinates, ... DestinationCanvasCoordinates ); // getImagedata는 동일한 소스 또는 크로스-오리핀이 활성화 된 이미지에서만 작동한다는 것을 기억하십시오. // https://developer.mozilla.org/en-us/docs/web/html/cors_enabled_image const imagepixelcolors = ctx.getImageData (... DestinationCanvasCoordinates); ImagePixelColors 리턴; }
getImageData()
메소드는 각 픽셀의 색상을 나타내는 숫자 목록을 제공합니다. 각 픽셀은 빨간색, 녹색, 파란색 및 불투명도 ( "알파"라고도합니다. 이것을 알면, 우리는 픽셀 목록을 통해 반복하고 필요한 정보를 찾을 수 있습니다. 이것은 다음 단계에서 매우 유용합니다.
2 단계 : 대비가 가장 적은 픽셀을 찾으십시오
그 전에는 대비를 계산하는 방법을 알아야합니다. getContrast()
라는 함수를 작성하여 두 가지 색상을 사용하여 두 가지 색상 사이의 대비 수준을 나타내는 숫자를 출력합니다. 숫자가 높을수록 대비가 높아지고 가독성이 좋습니다.
이 프로젝트의 색상을 연구하기 시작했을 때 간단한 공식을 찾을 것으로 예상되었습니다. 여러 단계가 있었다는 것이 밝혀졌습니다.
두 가지 색상의 대비를 계산하려면 밝기 수준을 알아야합니다. 이는 본질적으로 밝기입니다 (Stacie Arellano는 밝기를 심도있게 보며 볼 가치가 있습니다).
W3C 덕분에 밝기를 사용하여 대비를 계산하기위한 공식을 알고 있습니다.
const contrast = (lightercolorluminance 0.05) / (Darkercolorluminance 0.05);
색상의 밝기를 얻는 것은 네트워크에서 사용되는 일반 8 비트 RGB 값 (각 색상이 0-255 인 경우)에서 선형 RGB라고하는 색상을 변환해야한다는 것을 의미합니다. 색상 변화에 따라 밝기가 고르게 증가하지 않기 때문에이 작업을 수행해야합니다. 색상을 색상을 색상으로 고르게 변하는 형식으로 변환해야합니다. 이를 통해 밝기를 올바르게 계산할 수 있습니다. 마찬가지로 W3C는 여기에서 도움을 제공합니다.
const luminance = (0.2126 * getLeinearrgb (r) 0.7152 * getlinearrgb (g) 0.0722 * getLeinearrgb (b));
그러나 잠깐, 더 많은 것이 있습니다! 8 비트 RGB (0 ~ 255)를 선형 RGB로 변환하려면 0 ~ 1의 비율을 갖는 표준 RGB (SRGB라고도 함)라고하는 것을 살펴 봐야합니다.
따라서 프로세스는 다음과 같습니다.
<code>8位RGB → 标准RGB → 线性RGB → 亮度</code>
비교하려는 두 가지 색상의 밝기가 있으면 밝기 값을 공식으로 대체하여 해당 색상 사이의 대비를 얻을 수 있습니다.
// getContrast는 직접 상호 작용 해야하는 유일한 기능입니다. // 나머지 함수는 중간 보조 단계입니다. 함수 getContrast (color1, color2) { const color1_luminance = getLuminance (color1); const color2_luminance = getLuminance (color2); const lightercolorluminance = math.max (color1_luminance, color2_luminance); const darkercolorluminance = math.min (color1_luminance, color2_luminance); const contrast = (lightercolorluminance 0.05) / (Darkercolorluminance 0.05); 반환 대비; } 함수 getLuminance ({r, g, b}) { return (0.2126 * getlinearrgb (r) 0.7152 * getlinearrgb (g) 0.0722 * getlinearrgb (b)); } 함수 getLineArrgb (PrimaryColor_8bit) { // 첫 번째 8 비트 RGB (0-255)에서 표준 RGB (0-1)로 변환 const primarycolor_srgb = convert_8bit_rgb_to_standard_rgb (primarycolor_8bit); // 그런 다음 SRGB에서 Linear RGB로 변환하여 밝기를 계산하여 Const PrimaryColor_RGB_LINEAR = CONVERT_STANDERD_RGB_TO_LINEAR_RGB (PrimaryColor_SRGB); PrimaryColor_RGB_LINEAR을 반환합니다. } 함수 convert_8bit_rgb_to_standard_rgb (PrimaryColor_8bit) { PrimaryColor_8bit / 255를 반환합니다. } 함수 convert_standard_rgb_to_linear_rgb (primarycolor_srgb) { const primarycolor_linear = primarycolor_srgb <p> 이제 대비를 계산할 수 있으므로 이전 단계에서 이미지를보고 각 픽셀을 반복하여 해당 픽셀의 색상과 전경 텍스트의 색상 간의 대비를 비교해야합니다. 이미지의 픽셀을 가로 질러 지금까지 최악의 (가장 낮은) 대비를 추적 할 것이며, 루프의 끝에 도달하면 이미지에서 최악의 대비가있는 색상을 알게 될 것입니다.</p><pre class="brush:php;toolbar:false"> 함수 getworstContrastColorinimage (TextColor, ImagePixelColors) { 최악의 상쇄 콜로 라니 지주를하자; 최악의 계약 = 무한대; // 이것은 너무 낮은 값으로 시작하지 않도록합니다 (i = 0; i <imagepixelcolors.data.length i="4)" const r="ImagePixelColors.Data" g="ImagePixelColors.Data" b="ImagePixelColors.Data" imagepixelcolor="{r," contrast="getContrast" if><p></p> <h3 id="단계-오버레이-불투명도-레벨을-테스트하기-위해-색상-혼합-공식-준비"> 3 단계 : 오버레이 불투명도 레벨을 테스트하기 위해 색상 혼합 공식 준비</h3> <p></p> <p> 이제 우리는 이미지에서 최악의 대비를 가진 색상을 알았으므로 다음 단계는 오버레이의 투명성이 얼마나 높아야하는지 결정하고 이것이 텍스트와의 대비가 어떻게 바뀌는 지 확인하는 것입니다.</p> <p></p> <p> 내가 이것을 처음 구현했을 때 나는 별도의 캔버스를 사용하여 색상을 혼합하고 결과를 읽었습니다. 그러나 투명성에 관한 Ana Tudor의 기사 덕분에 기본 색상을 투명한 오버레이와 혼합 한 후 결과 색상을 계산하는 편리한 공식이 있다는 것을 알고 있습니다.</p> <p></p> <p> 각 컬러 채널 (빨간색, 녹색 및 파란색) 마다이 공식을 적용하여 혼합 색상을 얻습니다.</p> <p> 혼합 색상 = 기본 색상 (중첩 색상 - 기본 색상) * 겹치는 불투명도</p> <p></p> <p> 따라서 코드에서는 다음과 같습니다.</p> <pre class="brush:php;toolbar:false"> 함수 mixcolors (basecolor, 오버레이 컬러, 오버레이 옵션) { const mixedColor = { R : BaseColor.r (오버레이 컬러 -r- basecolor.r) * 오버레이 옵션, G : BaseColor.g (오버레이 컬러 .g- basecolor.g) * 오버레이 옵션, B : BaseColor.B (오버레이 콜러 .B- BaseColor.B) * 오버레이 옵션, } MixedColor를 반환하십시오. }
이제 색상을 혼합 할 수 있으므로 오버레이 불투명도 값을 적용 할 때 대비를 테스트 할 수 있습니다.
함수 getTextContrastWithImagePlusOverLay ({TextColor, OrdayColor, ImagePixelColor, OrdayOpacity}) { const colorfimagepixelplusoverlay = mixcolors (ImagePixelColor, OverlayColor, OverlayOpacity); const contrast = getContrast (TextColor, ColorOfImagePixElplusOverLay); 반환 대비; }
이것으로 우리는 최고의 오버레이 불투명도를 찾는 데 필요한 모든 도구를 가지고 있습니다!
4 단계 : 대비 대상에 도달하는 오버레이 불투명도 찾기
오버레이의 불투명도를 테스트하고 이것이 텍스트와 이미지의 대비에 어떤 영향을 미치는지 확인할 수 있습니다. 텍스트가 배경보다 4.5 배 더 밝은 대상 대비에 도달하는 값을 찾을 때까지 다양한 불투명도 레벨을 시도합니다. 이것은 미치게 들릴지 모르지만 걱정하지 마십시오. 우리는 무작위로 추측하지 않을 것입니다. 우리는 정확한 결과를 얻을 때까지 가능한 답변 세트를 빠르게 좁힐 수있는 프로세스 인 Binary Search를 사용합니다.
이진 검색의 작동 방식은 다음과 같습니다.
<code>- 在中间猜测。 - 如果猜测过高,我们将消除答案的上半部分。太低了吗?我们将改为消除下半部分。 - 在新的范围中间猜测。 - 重复此过程,直到我们得到一个值。我碰巧有一个工具可以展示它是如何工作的:在这种情况下,我们试图猜测一个介于0和1之间的不透明度值。因此,我们将从中间猜测,测试结果对比度是太高还是太低,消除一半的选项,然后再次猜测。如果我们将二分查找限制为八次猜测,我们将立即得到一个精确的答案。在我们开始搜索之前,我们需要一种方法来检查是否根本需要叠加层。我们根本不需要优化我们不需要的叠加层! ```javascript function isOverlayNecessary(textColor, worstContrastColorInImage, desiredContrast) { const contrastWithoutOverlay = getContrast(textColor, worstContrastColorInImage); return contrastWithoutOverlay </code>
이제 이진 검색을 사용하여 가장 좋은 오버레이 불투명도를 찾을 수 있습니다.
함수 findOpTimalOverLayOpacity (TextColor, OverlayColor, 최악의 CollastColorinimage, 원하는 구성) { // 대비가 충분하면 오버레이 할 필요가 없습니다. // 우리는 나머지를 건너 뛸 수 있습니다. const isoverlaynecessary = isoverlaynecessary (TextColor, 최악의 상쇄 콜로린 -, 원하는 대조); if (! isoverlaynecessary) { 반환 0; } const exacitygeessrange = { Lowerbound : 0, 중간 점 : 0.5, 어퍼 바운드 : 1, }; numberofguesses = 0을하자; Const MaxGuesses = 8; // 해결책이 없으면 불투명도 추측은 1에 가깝습니다. // 솔루션없이 상황을 점검하기 위해 상한으로 사용할 수 있습니다. const opcacityLimit = 0.99; //이 루프는 결과를 얻을 때까지 추측을 반복적으로 좁 힙니다. 수정; const currentguess = irsacitygeessrange.midpoint; const contrast = getTextContrastWithImagePlusOverLay ({TextColor, OverlayColor, ImagePixelColor : 최악의 구성 콜로 리니지, 오버레이 옵션 : currentGuess}); const isguesstoolow = contrast <destiredcontrast const isguesstoohigh="contrast"> desired contrast; if (isguesstoolow) { 불투명 GuessRange.lowerBound = CurrentGuess; } else if (isguesstoohigh) { 불투명 GuessRange.upperbound = currentguess; } const newmidpoint = ((epacityGuessRange.upperBound -OpacityGuessRange.LowerBound) / 2) 불편성 GuessRange.LowerBound; 불투명 GuessRange.midpoint = NewMidPoint; } const OptimalOpacity = irsacityGuessRange.midpoint; const hasnosolution = OptimalOpacity> 불투명어; if (hasnosolution) { Console.log ( '솔루션 없음'); // 해결할 수없는 상황을 필요에 따라 처리 할 수없는 상황을 반환합니다. } 최적의 반환; }</destiredcontrast>
실험이 완료되면 이제 너무 많은 배경 이미지를 숨기지 않고 오버레이가 텍스트를 읽을 수 있도록하는 데 얼마나 투명 해야하는지 정확히 알 수 있습니다.
우리는 그것을했다!
개선 및 제한
우리가 소개하는 방법은 텍스트 색상과 오버레이 색상 자체가 충분히 대비되는 경우에만 효과적입니다. 예를 들어, 오버레이와 동일한 텍스트 색상을 선택하면 이미지에 오버레이가 필요하지 않으면 최적의 솔루션이 없습니다.
또한 대비가 수학적으로 허용되지만 항상 멋지게 보이는 것은 아닙니다. 이것은 가벼운 오버레이와 바쁜 배경 이미지가있는 어두운 텍스트에 특히 그렇습니다. 이미지의 일부는 텍스트에서 방해가 될 수 있으며 대비가 수치 적으로 좋더라도 읽기가 어려울 수 있습니다. 그렇기 때문에 인기있는 조언은 어두운 배경에서 가벼운 텍스트를 사용하는 것입니다.
우리는 또한 픽셀 위치 또는 컬러 당 픽셀 수를 고려하지 않았습니다. 이것의 단점 중 하나는 모서리의 픽셀이 결과에 과도한 영향을 줄 수 있다는 것입니다. 그러나 이점은 이미지의 색상이 어떻게 배포되는지 또는 텍스트의 위치에 대해 걱정할 필요가 없다는 것입니다. 대비가 가장 적은 곳을 다루는 한 다른 곳에서 안전 할 수 있기 때문입니다.
나는 길을 따라 무언가를 배웠다
이 실험 후, 나는 무언가를 얻었고 당신과 공유하고 싶습니다.
<code>- **明确目标非常有帮助!**我们从一个模糊的目标开始,即想要在图像上显示可读的文本,最终得到了一个我们可以努力达到的特定对比度级别。 - **明确术语非常重要。**例如,标准RGB并非我所期望的。我了解到,我认为的“常规”RGB(0到255)正式称为8位RGB。此外,我认为我研究的方程式中的“L”表示“亮度”,但它实际上表示“亮度”,这不能与“光度”混淆。澄清术语有助于我们编写代码以及讨论最终结果。 - **复杂并不意味着无法解决。**听起来很困难的问题可以分解成更小、更容易管理的部分。 - **当你走过这条路时,你会发现捷径。**对于白色文本在黑色透明叠加层上的常见情况,您永远不需要超过0.54的不透明度即可达到WCAG AA级可读性。 ### 总结…您现在有了一种方法可以在背景图像上使文本可读,而不会牺牲过多的图像。如果您已经读到这里,我希望我已经能够让您大致了解其工作原理。我最初开始这个项目是因为我看到(并制作了)太多网站横幅,其中文本在背景图像上难以阅读,或者背景图像被叠加层过度遮挡。我想做些什么,我想给其他人提供一种同样的方法。我写这篇文章是为了希望你们能够更好地理解网络上的可读性。我希望你们也学习了一些很酷的canvas技巧。如果您在可读性或canvas方面做了一些有趣的事情,我很乐意在评论中听到您的想法!</code>
위 내용은 라이트 텍스트와 배경 이미지 사이의 완벽한 대비를 못함의 상세 내용입니다. 자세한 내용은 PHP 중국어 웹사이트의 기타 관련 기사를 참조하세요!

핫 AI 도구

Undresser.AI Undress
사실적인 누드 사진을 만들기 위한 AI 기반 앱

AI Clothes Remover
사진에서 옷을 제거하는 온라인 AI 도구입니다.

Undress AI Tool
무료로 이미지를 벗다

Clothoff.io
AI 옷 제거제

Video Face Swap
완전히 무료인 AI 얼굴 교환 도구를 사용하여 모든 비디오의 얼굴을 쉽게 바꾸세요!

인기 기사

뜨거운 도구

메모장++7.3.1
사용하기 쉬운 무료 코드 편집기

SublimeText3 중국어 버전
중국어 버전, 사용하기 매우 쉽습니다.

스튜디오 13.0.1 보내기
강력한 PHP 통합 개발 환경

드림위버 CS6
시각적 웹 개발 도구

SublimeText3 Mac 버전
신 수준의 코드 편집 소프트웨어(SublimeText3)

새로운 프로젝트가 시작될 때, Sass 컴파일은 눈을 깜박이게합니다. 특히 BrowserSync와 짝을 이루는 경우 기분이 좋습니다.

이번 주에 플랫폼 뉴스 라운드 업 RONDUP, Chrome은로드에 대한 새로운 속성, 웹 개발자를위한 접근성 사양 및 BBC Move를 소개합니다.

이것은 처음으로 HTML 요소를보고 있습니다. 나는 그것을 잠시 동안 알고 있었지만 아직 스핀을 위해 그것을 가져 갔다. 그것은 꽤 시원하고 있습니다

구매 또는 빌드는 기술 분야의 고전적인 논쟁입니다. 신용 카드 청구서에 라인 항목이 없기 때문에 물건을 구축하는 것이 저렴할 수 있지만

한동안 iTunes는 팟 캐스팅에서 큰 개 였으므로 "Podcast 구독"을 링크 한 경우 다음과 같습니다.

사이트에서 방문자 및 사용 데이터를 추적하는 데 도움이되는 분석 플랫폼이 많이 있습니다. 아마도 널리 사용되는 Google 웹 로그 분석

이번 주에 타이포그래피를 검사하기위한 편리한 북마크 인 Roundup, JavaScript 모듈과 Facebook의 Facebook 등을 어떻게 가져 오는지 땜질하기 위해 대기하는 편리한 북마크 인 Roundup과 Facebook의
