ข้อความโปร่งใสถูกตัดออกจากพื้นหลัง


92

มีวิธีใดบ้างในการตัดข้อความโปร่งใสออกจากเอฟเฟกต์พื้นหลังเช่นเดียวกับในภาพต่อไปนี้ด้วย CSS
คงเป็นเรื่องน่าเศร้าที่ต้องสูญเสีย SEO อันมีค่าทั้งหมดไปเพราะรูปภาพแทนที่ข้อความ

ข้อความโปร่งใสถูกตัดออกจากพื้นหลัง

ตอนแรกฉันนึกถึงเงา แต่คิดอะไรไม่ออก ...

รูปภาพเป็นพื้นหลังของไซต์ซึ่งเป็น<img>แท็กที่อยู่ในตำแหน่งที่แน่นอน


"สูญเสีย SEO อันมีค่าทั้งหมดเพราะรูปภาพแทนที่ข้อความ" นอกจากนี้ยังมีเทคนิคการเปลี่ยนภาพที่มีอยู่ซึ่งยังคงเป็นมิตรกับสิ่งแวดล้อม BTW: จริงๆแล้วพื้นหลังด้านหลังตัวอักษรยังต้องโปร่งใสซึ่งเป็นปัญหาที่นี่…
feeela

ใช่นี่จะเป็นการฝึกฝนที่ยอดเยี่ยมถ้าเป็นไปได้ด้วย css ...
Jessica Lingmn

ผมไม่เห็นเหตุผลว่าทำไม<h1><img alt="Some Text" /></h1>เป็นน้อย ๆ SEO <h1>Some Text</h1>เป็นมิตรกว่า ตามเนื้อผ้าปัญหาเกี่ยวกับรูปภาพคือเพิ่งถูกทิ้งบนหน้าโดยไม่มีมาร์กอัปรองรับ
cimmanon

@cimmanon ใช่คุณพูดถูก ฉันอาจจะใช้รูปภาพโดยไม่เสียคะแนน SEO แต่คุณยังเลือกข้อความไม่ได้การค้นหาในหน้าการเชื่อมโยงจะซับซ้อนกว่านี้และจะต้องทำงานมากขึ้นในการอัปเดตข้อความ ... : /
Love Dager

2
ขอแจ้งให้ทราบว่า Google เจ๋งสุด ๆ กับเทคนิคการเปลี่ยนรูปภาพด้วย CSS: mezzoblue.com/archives/2008/05/05/image_replac
cimmanon

คำตอบ:


47

เป็นไปได้ด้วย css3 แต่ไม่รองรับในทุกเบราว์เซอร์

มี background-clip: text; คุณสามารถใช้พื้นหลังสำหรับข้อความได้ แต่คุณจะต้องจัดแนวให้ตรงกับพื้นหลังของหน้า

body {
    background: url(http://www.color-hex.com/palettes/26323.png) repeat;
    margin:10px;
}
h1 { 
    background-color:#fff;
    overflow:hidden;
    display:inline-block; 
    padding:10px; 
    font-weight:bold;
    font-family:arial;
    color:transparent;
    font-size:200px;
}
span { 
    background: url(http://www.color-hex.com/palettes/26323.png) -20px -20px repeat;
    -webkit-text-fill-color: transparent;
    -webkit-background-clip: text;
    display:block;
}
<h1><span>ABCDEFGHIKJ</span></h1>

http://jsfiddle.net/JGPuZ/1337/


การจัดตำแหน่งอัตโนมัติ

ด้วยจาวาสคริปต์เล็กน้อยคุณสามารถจัดแนวพื้นหลังโดยอัตโนมัติ:

$(document).ready(function(){
  //Position of the header in the webpage
  var position = $("h1").position();
  var padding = 10; //Padding set to the header
  var left = position.left + padding;
  var top = position.top + padding;
  $("h1").find("span").css("background-position","-"+left+"px -"+top+"px"); 
});
body {
    background: url(http://www.color-hex.com/palettes/26323.png) repeat;
    margin:10px;
}
h1 { 
    background-color:#fff;
    overflow:hidden;
    display:inline-block; 
    padding:10px; 
    font-weight:bold;
    font-family:arial;
    color:transparent;
    font-size:200px;
}
span { 
    background: url(http://www.color-hex.com/palettes/26323.png) -20px -20px repeat;
    -webkit-text-fill-color: transparent;
    -webkit-background-clip: text;
    display:block;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<h1><span>ABCDEFGHIKJ</span></h1>

http://jsfiddle.net/JGPuZ/1336/


คุณเป็นคนเร็วเกินไป: D
Gijs

โอ้เยี่ยม! ฉันจะทดสอบการจัดตำแหน่งอัตโนมัติให้เร็วที่สุดเท่าที่ฉันจะถึงบ้าน! ขอบคุณ! : D
Love Dager

คุณ maby ต้องเปลี่ยนรหัสเล็กน้อยขึ้นอยู่กับสถานการณ์ตอนนี้มันอาจขัดแย้งกับองค์ประกอบอื่น ๆ และอันนี้เขียนเร็วมากหากคุณมีคำถามใด ๆ ฉันจะได้ยินพวกเขา
Gijs

3
อย่าเพิกเฉยต่อคำตอบซึ่งเป็นทางออกที่ดีมาก แต่background-clip:textเป็นตัวเลือกที่ไม่ได้มาตรฐานสำหรับ Webkit เท่านั้น CSS3 ไม่อนุญาตให้ใช้textค่าสำหรับแอตทริบิวต์นี้ ( ดู )
tanius

1
เทคนิคนี้ช่วยให้คุณเห็นพื้นหลังขององค์ประกอบที่โดยปกติข้อความจะเป็น ฉันกำลังมองหาวิธีดูว่ามีอะไรอยู่ภายใต้องค์ประกอบที่มีข้อความผ่านตำแหน่งที่ข้อความปกติ
Vince

49

แม้ว่านี่จะเป็นไปได้ด้วย CSS เป็นวิธีการที่ดีกว่าจะใช้SVG อินไลน์กับSVG กำบัง วิธีนี้มีข้อดีกว่า CSS:

CodePen Demo: มาสก์ข้อความ SVG

พื้นหลังการตัดข้อความโปร่งใส

body,html{height:100%;margin:0;padding:0;}
body{
  background:url('https://farm9.staticflickr.com/8760/17195790401_94fcf60556_c.jpg');
  background-size:cover;
  background-attachment:fixed;
}
svg{width:100%;}
<svg viewbox="0 0 100 60">
  <defs>
    <mask id="mask" x="0" y="0" width="100" height="50">
      <rect x="0" y="0" width="100" height="40" fill="#fff"/>
      <text text-anchor="middle" x="50" y="18" dy="1">SVG</text>
      <text text-anchor="middle" x="50" y="30" dy="1">Text mask</text>
    </mask>
  </defs>
  <rect x="5" y="5" width="90" height="30" mask="url(#mask)" fill-opacity="0.5"/>    
</svg>

หากคุณตั้งเป้าหมายที่จะทำให้ข้อความสามารถเลือกและค้นหาได้คุณจะต้องรวมข้อความนั้นไว้นอก<defs>แท็ก ตัวอย่างต่อไปนี้แสดงวิธีการที่จะทำให้ข้อความโปร่งใสกับ<use>แท็ก:

body,html{height:100%;margin:0;padding:0;}
body{
  background:url('https://farm9.staticflickr.com/8760/17195790401_94fcf60556_c.jpg');
  background-size:cover;
  background-attachment:fixed;
}
svg{width:100%;}
<svg viewbox="0 0 100 60">
  <defs>
    <g id="text">
      <text text-anchor="middle" x="50" y="18" dy="1">SVG</text>
      <text text-anchor="middle" x="50" y="30" dy="1">Text mask</text>
    </g>
    <mask id="mask" x="0" y="0" width="100" height="50">
      <rect x="0" y="0" width="100" height="40" fill="#fff"/>
      <use xlink:href="#text" />
    </mask>
  </defs>
  <rect x="5" y="5" width="90" height="30" mask="url(#mask)" fill-opacity="0.5"/>
  <use xlink:href="#text" mask="url(#mask)" />
</svg>


2
ดูเหมือนจะเป็นทางออกเดียวที่ใช้งานข้ามเบราว์เซอร์ได้ในปัจจุบัน: IE11, FF, Chrome, Safari และไม่จำเป็นต้องใช้รูปภาพเป็นพื้นหลังเหมือนกับวิธีแก้ปัญหาอื่น ๆ อีกมากมายที่มีให้ในเว็บ
Timo Kähkönen

1
แรงบันดาลใจจากคำตอบนี้ฉันสร้างภาพเคลื่อนไหวคีย์เฟรมโดยที่ข้อความ SVG โปร่งใสบนสี่เหลี่ยมผืนผ้าโค้งมนสีขาวจะหมุน พื้นหลังมีข้อความและรูปภาพ ไปดู: jsbin.com/nipuqu/3 (การแข่งขันชิงแชมป์โลกกำลังจะมาถึง :))
Timo Kähkönen

2
วิธีแก้ปัญหาที่ดี แต่เนื่องจาก "เลือกข้อความและค้นหาในหน้า" ดูเหมือนจะอยู่ในข้อกำหนดของ OP คุณอาจต้องการรวมส่วน<text>นอก<defs>ไว้ด้วย (btw ฉันไม่แน่ใจว่าโปรแกรมรวบรวมข้อมูล SE จัดการกับเนื้อหา SVG ใน defs อย่างไร) นี่คือวิธีรักษาสิ่งที่ OP ต้องการด้วยการหาประโยชน์จากข้อผิดพลาด FF ที่น่ากลัว: jsfiddle.net/tfneqxxb
Kaiido

จะเกิดอะไรขึ้นถ้าข้อความเป็นแบบไดนามิก มันไม่ได้ปรับขนาดความกว้างอัตโนมัติ
Imran Bughio

1
@ImranBughio ไม่มันไม่ได้ ข้อความ SVG ไม่ทำหน้าที่เหมือนข้อความ HTML ธรรมดา คุณต้องวางตำแหน่ง สำหรับข้อมูลเพิ่มเติมโปรดดูที่นี่
web-tiki

16

วิธีหนึ่งที่ใช้ได้กับเบราว์เซอร์รุ่นใหม่ส่วนใหญ่ (ยกเว้นเช่น edge) แม้ว่าจะใช้เฉพาะพื้นหลังสีดำเท่านั้น

background: black;
color: white;
mix-blend-mode: multiply;

ในองค์ประกอบข้อความของคุณแล้วใส่พื้นหลังที่คุณต้องการไว้ด้านหลัง โดยทั่วไปแล้วจะจับคู่รหัสสี 0-255 เป็น 0-1 แล้วคูณด้วยสิ่งที่อยู่เบื้องหลังดังนั้นสีดำจึงยังคงเป็นสีดำและสีขาวคูณด้วย 1 และจะกลายเป็นโปร่งใสอย่างมีประสิทธิภาพ http://codepen.io/nic_klaassen/full/adKqWX/


3
สำหรับพื้นหลังสีขาวที่มีการใช้สีดำcolor-dodge, lightenหรือscreenบนmix-blend-mode
Imran Bughio

3

มันเป็นไปได้ แต่จนถึงขณะนี้เฉพาะกับเบราว์เซอร์ Webkit based (Chrome, Safari, Rockmelt อะไรอยู่บนพื้นฐานของโครงการโครเมี่ยม.)

เคล็ดลับคือการมีองค์ประกอบภายในองค์ประกอบสีขาวที่มีพื้นหลังเหมือนกับร่างกายจากนั้นใช้-webkit- background-clip: text;กับองค์ประกอบด้านในซึ่งโดยพื้นฐานแล้วหมายถึง "อย่าขยายพื้นหลังเกินข้อความ" และใช้ข้อความโปร่งใส

section
{
    background: url(http://norcaleasygreen.com/wp-content/uploads/2012/11/turf-grass1.jpg);
    width: 100%;
    height: 300px;
}

div
{
    background: rgba(255, 255, 255, 1);
    color: rgba(255, 255, 255, 0);

    width: 60%;
    heighT: 80%;
    margin: 0 auto;
    font-size: 60px;
    text-align: center;
}

p
{
    background: url(http://norcaleasygreen.com/wp-content/uploads/2012/11/turf-grass1.jpg);
    -webkit-background-clip: text;
}
​

http://jsfiddle.net/BWRsA/


เคล็ดลับเด็ด! แต่ตอนนี้การจัดวางทุกอย่างให้ถูกต้องจะเป็นเรื่องเลวร้าย .. -.-
Love Dager

ใช่นั่นเป็นอีกปัญหาหนึ่งของมัน มันยังอยู่ในระหว่างการพัฒนาและฉันหวังเป็นอย่างยิ่งว่าเราจะได้เห็นอะไรแบบนี้เร็ว ๆ นี้! :)
Kyle

นอกจากนี้คุณสามารถเลเยอร์ทับข้อความโปร่งใสบนรูปภาพเพื่อให้ยังคงเลือกได้ แต่ฉันแน่ใจว่ามันเป็นการปฏิบัติที่ไม่ดีสำหรับ SEO .. ข้อความ / คำหลักที่ซ่อนอยู่และอื่น ๆ
Kyle

ฉันแน่ใจว่ามันดูดีมากในเบราว์เซอร์ Webkit แต่สำหรับคนอื่น ๆ มันเป็นกล่องสีขาวกึ่งโปร่งใสที่ด้านบนของหญ้า
cimmanon

1
อามาเลย ... ใช่ฉันวางแผนที่จะใช้มันในการผลิต แต่แน่นอนว่าไม่มีทางเลือก! @cimmanon
Love Dager

2

ฉันเดาว่าคุณสามารถทำได้โดยใช้background-clipสิ่งนั้นแต่ฉันยังไม่ได้ทดสอบ

ดูตัวอย่างนี้:
http://www.css3.info/wp-content/uploads/2008/03/webkit-backgroundcliptext_color.html
(เฉพาะ Webkit ฉันยังไม่รู้วิธีเปลี่ยนพื้นหลังสีดำเป็นสีขาว)


ใช่มันอาจได้ผล! ขอบคุณตอนนี้เพื่อจัดตำแหน่งทุกอย่างให้ถูกต้อง .. ไอ้ .. -.-
Love Dager

2

ฉันเพิ่งค้นพบวิธีใหม่ในการทำสิ่งนี้ในขณะที่ยุ่งเหยิงฉันไม่แน่ใจว่ามันทำงานอย่างไร (หากมีคนอื่นต้องการอธิบายโปรดทำ)

ดูเหมือนว่าจะทำงานได้ดีและไม่ต้องใช้พื้นหลังสองเท่าหรือ JavaScript

นี่คือรหัส: JSFIDDLE

body {
  padding: 0;
  margin: 0;
}

div {
  background: url(http://www.color-hex.com/palettes/26323.png) repeat;
  width: 100vw;
  height: 100vh;
}

body::before {
  content: '$ALPHABET';
  left: 0;
  top: 0;
  position: absolute;
  color: #222;
  background-color: #fff;
  padding: 1rem;
  font-family: Arial;
  z-index: 1;
  mix-blend-mode: screen;
  font-weight: 800;
  font-size: 3rem;
  letter-spacing: 1rem;
}
<div></div>


1

คุณสามารถใช้แบบอักษรกลับหัว / ลบ / ย้อนกลับและใช้กับfont-face="…"กฎ CSS คุณอาจต้องเล่นกับระยะห่างของตัวอักษรเพื่อหลีกเลี่ยงช่องว่างสีขาวเล็ก ๆ ระหว่างตัวอักษร

หากคุณไม่ต้องการแบบอักษรเฉพาะก็ทำได้ง่ายๆ ดาวน์โหลดตัวอย่างเช่นจากคอลเล็กชันแบบอักษรกลับหัวนี้

หากคุณต้องการแบบอักษรเฉพาะ (พูดว่า "Open Sans") เป็นเรื่องยาก คุณต้องแปลงแบบอักษรที่มีอยู่เป็นเวอร์ชันกลับหัว สิ่งนี้เป็นไปได้ด้วยตนเองด้วย Font Creator, FontForge เป็นต้น แต่แน่นอนว่าเราต้องการโซลูชันอัตโนมัติ ฉันไม่พบคำแนะนำสำหรับสิ่งนั้น แต่มีคำแนะนำบางประการ:


1

คุณสามารถใช้ปลั๊กอินPatternizer jQuery ของ myadzelเพื่อให้ได้เอฟเฟกต์นี้ในเบราว์เซอร์ ในขณะนี้ยังไม่มีวิธีข้ามเบราว์เซอร์ที่ทำได้โดยใช้ CSS เพียงอย่างเดียว

คุณใช้ Patternizer โดยเพิ่มclass="background-clip"ในองค์ประกอบ HTML ที่คุณต้องการให้ข้อความถูกวาดเป็นรูปแบบรูปภาพและระบุรูปภาพในdata-pattern="…"แอตทริบิวต์เพิ่มเติม ดูแหล่งที่มาของการสาธิต Patternizer จะสร้างภาพ SVG ที่มีข้อความที่เต็มไปด้วยลวดลายและวางไว้ใต้องค์ประกอบ HTML ที่แสดงผลแบบโปร่งใส

หากในรูปตัวอย่างของคำถามรูปแบบการเติมข้อความควรเป็นส่วนหนึ่งของภาพพื้นหลังที่ขยายออกไปเกินองค์ประกอบที่เป็น "ลวดลาย" ฉันเห็นสองตัวเลือก (ยังไม่ทดสอบซึ่งเป็นรายการโปรดของฉันก่อน):

  • ใช้การมาสก์แทนภาพพื้นหลังใน SVG เช่นเดียวกับคำตอบของ web-tikiซึ่งการใช้ Patternizer จะยังคงเพิ่มการสร้าง SVG โดยอัตโนมัติและองค์ประกอบ HTML ที่มองไม่เห็นอยู่ด้านบนซึ่งช่วยให้สามารถเลือกและคัดลอกข้อความได้
  • หรือใช้การจัดตำแหน่งภาพรูปแบบโดยอัตโนมัติ สามารถทำได้ด้วยโค้ด JavaScript คล้ายกับหนึ่งในคำตอบของ Gijs

1

แค่ใส่ css นั้น

    .banner-sale-1 .title-box .title-overlay {
      font-weight: 900;
      overflow: hidden;
      margin: 0;
      padding-right: 10%;
      padding-left: 10%;
      text-transform: uppercase;
      color: #080404;
      background-color: rgba(255, 255, 255, .85);

      /* that css is the main think (mix-blend-mode: lighten;)*/
      mix-blend-mode: lighten;

    }

1

ภาพหน้าจอการสาธิต

ฉันต้องการสร้างข้อความที่ดูเหมือนในโพสต์ต้นฉบับ แต่ฉันไม่สามารถปลอมแปลงได้โดยการจัดเรียงพื้นหลังเพราะมีภาพเคลื่อนไหวอยู่เบื้องหลังองค์ประกอบ ดูเหมือนจะยังไม่มีใครแนะนำสิ่งนี้ดังนั้นนี่คือสิ่งที่ฉันทำ: (พยายามทำให้อ่านง่ายที่สุดเท่าที่จะทำได้)

var el = document.body; //Parent Element. Text is centered inside.
var mainText = "THIS IS THE FIRST LINE"; //Header Text.
var subText = "THIS TEXT HAS A KNOCKOUT EFFECT"; //Knockout Text.
var fontF = "Roboto, Arial"; //Font to use.
var mSize = 42; //Text size.

//Centered text display:
var tBox = centeredDiv(el), txtMain = mkDiv(tBox, mainText), txtSub = mkDiv(tBox),
ts = tBox.style, stLen = textWidth(subText, fontF, mSize)+5; ts.color = "#fff";
ts.font = mSize+"pt "+fontF; ts.fontWeight = 100; txtSub.style.fontWeight = 400;

//Generate subtext SVG for knockout effect:
txtSub.innerHTML =
"<svg xmlns='http://www.w3.org/2000/svg' width='"+stLen+"px' height='"+(mSize+11)+"px' viewBox='0 0 "+stLen+" "+(mSize+11)+"'>"+
    "<rect x='0' y='0' width='100%' height='100%' fill='#fff' rx='4px' ry='4px' mask='url(#txtSubMask)'></rect>"+
    "<mask id='txtSubMask'>"+
        "<rect x='0' y='0' width='100%' height='100%' fill='#fff'></rect>"+
        "<text x='"+(stLen/2)+"' y='"+(mSize+6)+"' font='"+mSize+"pt "+fontF+"' text-anchor='middle' fill='#000'>"+subText+"</text>"+
    "</mask>"+
"</svg>";

//Relevant Helper Functions:
function centeredDiv(parent) {
    //Container:
    var d = document.createElement('div'), s = d.style;
    s.display = "table"; s.position = "relative"; s.zIndex = 999;
    s.top = s.left = 0; s.width = s.height = "100%";
    //Content Box:
    var k = document.createElement('div'), j = k.style;
    j.display = "table-cell"; j.verticalAlign = "middle";
    j.textAlign = "center"; d.appendChild(k);
    parent.appendChild(d); return k;
}
function mkDiv(parent, tCont) {
    var d = document.createElement('div');
    if(tCont) d.textContent = tCont;
    parent.appendChild(d); return d;
}
function textWidth(text, font, size) {
    var canvas = window.textWidthCanvas || (window.textWidthCanvas = document.createElement("canvas")),
    context = canvas.getContext("2d"); context.font = size+(typeof size=="string"?" ":"pt ")+font;
    return context.measureText(text).width;
}

เพียงแค่โยนสิ่งนั้นลงในหน้าต่างของคุณโหลดตั้งค่าพื้นหลังของร่างกายเป็นรูปภาพของคุณและดูความมหัศจรรย์ที่เกิดขึ้น!


0

ไม่สามารถทำได้ด้วย CSS ตอนนี้ฉันกลัว

ทางออกที่ดีที่สุดของคุณคือใช้รูปภาพ (อาจเป็น PNG) และวางข้อความแสดงแทน / ชื่อเรื่องที่ดี

หรือคุณสามารถใช้ SPAN หรือ DIV และมีภาพเป็นพื้นหลังพร้อมกับข้อความของคุณที่คุณต้องการสำหรับวัตถุประสงค์ SEO ภายใน แต่จะเยื้องข้อความออกจากหน้าจอ


ถูกของคุณ. ฉันอาจจะใช้รูปภาพโดยไม่เสียคะแนน SEO แต่คุณยังเลือกข้อความไม่ได้การค้นหาในหน้าการเชื่อมโยงจะซับซ้อนกว่านี้และจะต้องทำงานมากขึ้นในการอัปเดตข้อความ ... : /
Love Dager

0

mix-blend-mode ยังเป็นไปได้สำหรับเอฟเฟกต์แบบนั้น

mix-blend-modeชุดคุณสมบัติ CSS ว่าเนื้อหาเป็นองค์ประกอบควรผสมผสานกับเนื้อหาของผู้ปกครองขององค์ประกอบและพื้นหลังขององค์ประกอบที่

h1 {
background:white;
mix-blend-mode:screen;

/* demo purpose from here */
padding:0.25em;
mix-blend-mode:screen;
}


html {
background:url(https://i.picsum.photos/id/1069/367/267.jpg?hmac=w5sk7UQ6HGlaOVQ494mSfIe902cxlel1BfGUBpEYoRw)center / cover ;
min-height:100vh;
display:flex;
}
body {margin:auto;}
h1:hover {border:dashed 10px white;background-clip:content-box;box-shadow:inset 0 0 0 2px #fff, 0 0 0 2px #fff}
<h1>ABCDEFGHIJKLMNOPQRSTUVWXYZ</h1>

โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.