javascript w3schools - É possível aplicar CSS a metade de um caractere?



array objetos (16)

Pode ser irrelevante, talvez não, mas há algum tempo criei uma função jQuery que faz a mesma coisa, mas horizontalmente.

Eu chamei de "Strippex" Para 'stripe' + 'text', demo: http://cdpn.io/FcIBg

Eu não estou dizendo que esta é a solução de qualquer problema, mas eu já tentei aplicar css a metade de um personagem, mas horizontalmente, então a ideia é a mesma, a realização pode ser horrível, mas funciona.

Ah, e o mais importante, me diverti criando!

O que estou procurando:

Uma maneira de estilizar um MEIO de um personagem. (Neste caso, metade da letra é transparente)

O que eu tenho procurado atualmente e tentei (sem sorte):

  • Métodos para estilizar metade de um caractere / letra
  • Estilizando parte de um personagem com CSS ou JavaScript
  • Aplicar CSS a 50% de um caractere

Abaixo está um exemplo do que estou tentando obter.

Existe uma solução CSS ou JavaScript para isso, ou terei que recorrer a imagens? Eu preferiria não seguir a rota da imagem, pois esse texto acabará sendo gerado dinamicamente.

ATUALIZAR:

Já que muitos perguntaram por que eu gostaria de escolher metade de um personagem, é por isso. Minha cidade gastou recentemente US $ 250.000 para definir uma nova "marca" para si mesma. Este logo é o que eles inventaram. Muitas pessoas reclamaram da simplicidade e da falta de criatividade e continuam a fazê-lo. Meu objetivo era criar este website como uma brincadeira. Digite 'Halifax' e você verá o que quero dizer. :)


Que tal algo assim para texto mais curto?

Poderia até funcionar com texto mais longo se você fizesse algo com um loop, repetindo os caracteres com JavaScript. De qualquer forma, o resultado é algo assim:

p.char {
  position: relative;
  display: inline-block;
  font-size: 60px;
  color: red;
}

p.char:before {
  position: absolute;
  content: attr(char);
  width: 50%;
  overflow: hidden;
  color: black;
}
<p class="char" char="S">S</p>
<p class="char" char="t">t</p>
<p class="char" char="a">a</p>
<p class="char" char="c">c</p>
<p class="char" char="k">k</p>
<p class="char" char="o">o</p>
<p class="char" char="v">v</p>
<p class="char" char="e">e</p>
<p class="char" char="r">r</p>
<p class="char" char="f">f</p>
<p class="char" char="l">l</p>
<p class="char" char="o">o</p>
<p class="char" char="w">w</p>


Você também pode fazer isso usando SVG, se desejar:

var title = document.querySelector('h1'),
    text = title.innerHTML,
    svgTemplate = document.querySelector('svg'),
    charStyle = svgTemplate.querySelector('#text');

svgTemplate.style.display = 'block';

var space = 0;

for (var i = 0; i < text.length; i++) {
  var x = charStyle.cloneNode();
  x.textContent = text[i];
  svgTemplate.appendChild(x);
  x.setAttribute('x', space);
  space += x.clientWidth || 15;
}

title.innerHTML = '';
title.appendChild(svgTemplate);
<svg style="display: none; height: 100px; width: 100%" xmlns="http://www.w3.org/2000/svg" xmlns:svg="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" version="1.1">
    <defs id="FooDefs">
        <linearGradient id="MyGradient" x1="0%" y1="0%" x2="100%" y2="0%">
            <stop offset="50%" stop-color="blue" />
            <stop offset="50%" stop-color="red" />
        </linearGradient>
    </defs>
    <text y="50%" id="text" style="font-size: 72px; fill: url(#MyGradient)"></text>
</svg>

<h1>This is not a solution X</h1>

http://codepen.io/nicbell/pen/jGcbq


JSFiddle DEMO

Vamos fazer isso usando apenas pseudo seletores CSS!

Essa técnica funcionará com conteúdo gerado dinamicamente e tamanhos e larguras de fonte diferentes.

HTML:

<div class='split-color'>Two is better than one.</div>

CSS:

.split-color > span {
    white-space: pre-line;
    position: relative;
    color: #409FBF;
}

.split-color > span:before {
    content: attr(data-content);
    pointer-events: none;  /* Prevents events from targeting pseudo-element */
    position: absolute;
    overflow: hidden;
    color: #264A73;
    width: 50%;
    z-index: 1;
}

Para envolver a string gerada dinamicamente, você poderia usar uma função como esta:

// Wrap each letter in a span tag and return an HTML string
// that can be used to replace the original text
function wrapString(str) {
  var output = [];
  str.split('').forEach(function(letter) {
    var wrapper = document.createElement('span');
    wrapper.dataset.content = wrapper.innerHTML = letter;

    output.push(wrapper.outerHTML);
  });

  return output.join('');
}

// Replace the original text with the split-color text
window.onload = function() {
    var el  = document.querySelector('.split-color'),
        txt = el.innerHTML;

    el.innerHTML = wrapString(txt);
}

Isso pode ser feito apenas com o :beforeseletor CSS e content property value.

.halfed, .halfed1 {
  float: left;
}

.halfed, .halfed1 {
  font-family: arial;
  font-size: 300px;
  font-weight: bolder;
  width: 200px;
  height: 300px;
  position: relative; /* To help hold the content value within */
  overflow: hidden;
  color: #000;
}




.halfed:before, .halfed1:before   {
  width: 50%; /* How much we'd like to show */
  overflow: hidden; /* Hide what goes beyond our dimension */  
  content: 'X'; /* Halfed character */
  height: 100%;
  position: absolute;
  color: #28507D;

}



/* For Horizontal cut off */ 

.halfed1:before   {
  width: 100%;
  height: 55%;
  
}
<div class="halfed"> X </div>

<div class="halfed1"> X </div>

>> Veja no jsFiddle


Outra solução somente CSS (embora o atributo data seja necessário se você não quiser escrever CSS específico para letra). Este funciona mais em toda a linha (Tested IE 9/10, Chrome latest & FF latest)

span {
  position: relative;
  color: rgba(50,50,200,0.5);
}

span:before {
  content: attr(data-char);
  position: absolute;
  width: 50%;
  overflow: hidden;
  color: rgb(50,50,200);
}
<span data-char="X">X</span>


Se você está interessado nisso, então Glitch de Lucas Bebber é um efeito muito parecido e super legal:

Criado usando um simples SASS Mixin como

.example-one {
  font-size: 100px;
  @include textGlitch("example-one", 17, white, black, red, blue, 450, 115);
}

Mais detalhes em CSS Tricks de Chris Coyer e na página de Codepen de Lucas Bebber


CSS e jQuery Solution limitados

Não tenho certeza de como essa solução é elegante, mas corta tudo exatamente pela metade: http://jsfiddle.net/9wxfY/11/

Caso contrário, eu criei uma boa solução para você ... Tudo que você precisa fazer é ter isso para o seu HTML:

Dê uma olhada nesta edição mais recente e precisa de 6/13/2016: http://jsfiddle.net/9wxfY/43/

Quanto ao CSS, é muito limitado ... Você só precisa aplicá-lo para :nth-child(even)

$(function(){
  var $hc = $('.half-color');
  var str = $hc.text();
  $hc.html("");

  var i = 0;
  var chars;
  var dupText;

  while(i < str.length){
    chars = str[i];
    if(chars == " ") chars = "&nbsp;";
    dupText = "<span>" + chars + "</span>";

    var firstHalf = $(dupText);
    var secondHalf = $(dupText);

    $hc.append(firstHalf)
    $hc.append(secondHalf)

    var width = firstHalf.width()/2;

    firstHalf.width(width);
    secondHalf.css('text-indent', -width);

    i++;
  }
});
.half-color span{
  font-size: 2em;
  display: inline-block;
  overflow: hidden;
}
.half-color span:nth-child(even){
  color: red;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div class="half-color">This is a sentence</div>


Edit (out 2017): background-image options background-clip ou rather background-image options são agora suportadas por todos os principais navegadores: CanIUse

Sim, você pode fazer isso com apenas um caractere e apenas CSS.

Webkit (e Chrome) apenas, embora:

http://jsbin.com/rexoyice/1/

h1 {
  display: inline-block;
  margin: 0; /* for demo snippet */
  line-height: 1em; /* for demo snippet */
  font-family: helvetica, arial, sans-serif;
  font-weight: bold;
  font-size: 300px;
  background: linear-gradient(to right, #7db9e8 50%,#1e5799 50%);
  -webkit-background-clip: text;
  -webkit-text-fill-color: transparent;
}
<h1>X</h1>

Visualmente, todos os exemplos que usam dois caracteres (seja via JS, pseudo-elementos CSS ou apenas HTML) parecem bem, mas note que isso adiciona conteúdo ao DOM que pode causar acessibilidade - assim como seleção de texto / corte / cole problemas.


O mais próximo que eu posso conseguir:

$(function(){
  $('span').width($('span').width()/2);
  $('span:nth-child(2)').css('text-indent', -$('span').width());
});
body{
  font-family: arial;
}
span{
  display: inline-block;
  overflow: hidden;
}
span:nth-child(2){
  color: red;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<span>X</span><span>X</span>

Demonstração: http://jsfiddle.net/9wxfY/2/

Heres uma versão que usa apenas um span: http://jsfiddle.net/9wxfY/4/





Acabei de terminar de desenvolver o plugin e ele está disponível para todos! Espero que você goste.

Veja o projeto no GitHub - Visualize o Website projeto. (assim você pode ver todos os estilos de divisão)

Uso

Primeiro de tudo, verifique se a biblioteca jQuery está incluída. A melhor maneira de obter a versão mais recente do jQuery é atualizar sua tag head com:

<script src="http://code.jquery.com/jquery-latest.min.js"></script>

Depois de baixar os arquivos, inclua-os no seu projeto:

<link rel="stylesheet" type="text/css" href="css/splitchar.css">
<script type="text/javascript" src="js/splitchar.js"></script>

Marcação

Tudo o que você precisa fazer é atribuir a classe splitchar , seguida pelo estilo desejado, ao elemento que envolve seu texto. por exemplo

<h1 class="splitchar horizontal">Splitchar</h1>

Depois de tudo isso ser feito, certifique-se de chamar a função jQuery no arquivo pronto para o documento da seguinte forma:

$(".splitchar").splitchar();

Customizing

Para fazer com que o texto fique exatamente como você deseja, tudo o que você precisa fazer é aplicar seu design da seguinte forma:

.horizontal { /* Base CSS - e.g font-size */ }
.horizontal:before { /* CSS for the left half */ }
.horizontal:after { /* CSS for the right half */ }


É isso aí! Agora você tem o plugin Splitchar todo definido. Mais informações sobre isso em Website .


.halfStyle {
    position:relative;
    display:inline-block;
    font-size:68px; /* or any font size will work */
    color: rgba(0,0,0,0.8); /* or transparent, any color */
    overflow:hidden;
    white-space: pre; /* to preserve the spaces from collapsing */
    transform:rotate(4deg);
    -webkit-transform:rotate(4deg);
    text-shadow:2px 1px 3px rgba(0,0,0,0.3);
}
.halfStyle:before {
    display:block;
    z-index:1;
    position:absolute;
    top:-0.5px;
    left:-3px;
    width: 100%;
    content: attr(data-content); /* dynamic content for the pseudo element */
    overflow:hidden;
    color: white;
    transform:rotate(-4deg);
    -webkit-transform:rotate(-4deg);
    text-shadow:0 0 1px black;

}

samtremaine.co.uk

Você pode colocar este código em todos os tipos de coisas interessantes - esta é apenas uma implementação que eu e meu colega criamos na noite passada.


Acabei de jogar com a solução da @ Arbel:

var textToHalfStyle = $('.textToHalfStyle').text();
var textToHalfStyleChars = textToHalfStyle.split('');
$('.textToHalfStyle').html('');
$.each(textToHalfStyleChars, function(i,v){
    $('.textToHalfStyle').append('<span class="halfStyle" data-content="' + v + '">' + v + '</span>');
});
body{
    background-color: black;
}
.textToHalfStyle{
    display:block;
    margin: 200px 0 0 0;
    text-align:center;
}
.halfStyle {
    font-family: 'Libre Baskerville', serif;
    position:relative;
    display:inline-block;
    width:1;
    font-size:70px;
    color: black;
    overflow:hidden;
    white-space: pre;
    text-shadow: 1px 2px 0 white;
}
.halfStyle:before {
    display:block;
    z-index:1;
    position:absolute;
    top:0;
    width: 50%;
    content: attr(data-content); /* dynamic content for the pseudo element */
    overflow:hidden;
    color: white;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.0/jquery.min.js"></script>
<span class="textToHalfStyle">Dr. Jekyll and M. Hide</span>


Você pode usar o código abaixo. Aqui neste exemplo eu usei h1tag e adicionei um atributo data-title-text="Display Text"que aparecerá com texto de cor diferente no h1elemento de texto de tag, que dá efeito de texto com meia cor, como mostrado no exemplo abaixo

body {
  text-align: center;
  margin: 0;
}

h1 {
  color: #111;
  font-family: arial;
  position: relative;
  font-family: 'Oswald', sans-serif;
  display: inline-block;
  font-size: 2.5em;
}

h1::after {
  content: attr(data-title-text);
  color: #e5554e;
  position: absolute;
  left: 0;
  top: 0;
  clip: rect(0, 1000px, 30px, 0);
}
<h1 data-title-text="Display Text">Display Text</h1>


Uma ótima solução somente para o WebKit que aproveita o background-clip: textsuporte: http://jsfiddle.net/sandro_paganotti/wLkVt/

span{
   font-size: 100px;
   background: linear-gradient(to right, black, black 50%, grey 50%, grey);
   -webkit-background-clip: text;
   -webkit-text-fill-color: transparent;
}

Eu respondi sua pergunta em profundidade aqui: explanation

O artigo também explica como escapar de qualquer caractere em CSS (e JavaScript), e eu também fiz uma ferramenta útil para isso. Daquela página:

Se você tivesse que dar a um elemento um valor de ID de [email protected]$%^&*()_+-=,./';:"?><[]{}|`# , O seletor ficaria assim:

CSS:

<style>
  #\~\!\@\$\%\^\&\*\(\)\_\+-\=\,\.\/\'\;\:\"\?\>\<\[\]\\\{\}\|\`\#
  {
    background: hotpink;
  }
</style>

JavaScript:

<script>
  // document.getElementById or similar
  document.getElementById('[email protected]$%^&*()_+-=,./\';:"?><[]\\{}|`#');
  // document.querySelector or similar
  $('#\\~\\!\\@\\$\\%\\^\\&\\*\\(\\)\\_\\+-\\=\\,\\.\\/\\\'\\;\\:\\"\\?\\>\\<\\[\\]\\\\\\{\\}\\|\\`\\#');
</script>




javascript html css styling