web-dev-qa-db-fra.com

CSS Inset Borders

J'ai une petite question sur les frontières CSS.

J'ai besoin de créer une bordure de couleur unie. C'est le peu de CSS que j'utilise:

border: 10px inset rgba(51,153,0,0.65);

Malheureusement, cela crée une bordure striée 3D (ignorez les carrés et la zone de description sombre):

http://dl.dropbox.com/u/12147973/border-current.jpg

C'est l'objectif:

http://dl.dropbox.com/u/12147973/border-boal.jpg

Des idées?

58
JacobTheDev

Vous pouvez utiliser box-shadow, éventuellement:

#something {
    background: transparent url(https://i.stack.imgur.com/RL5UH.png) 50% 50% no-repeat;
    min-width: 300px;
    min-height: 300px;
    box-shadow: inset 0 0 10px #0f0;
}

#something {
  background: transparent url(https://i.stack.imgur.com/RL5UH.png) 50% 50% no-repeat;
  min-width: 300px;
  min-height: 300px;
  box-shadow: inset 0 0 10px #0f0;
}
<div id="something"></div>

Cela présente l’avantage de recouvrir l’image d’arrière-plan de la variable div, mais elle est bien entendu floue (comme on peut s’y attendre de la propriété box-shadow). Pour construire la density de l'ombre, vous pouvez bien sûr ajouter d'autres ombres:

#something {
    background: transparent url(https://i.stack.imgur.com/RL5UH.png) 50% 50% no-repeat;
    min-width: 300px;
    min-height: 300px;
    box-shadow: inset 0 0 20px #0f0, inset 0 0 20px #0f0, inset 0 0 20px #0f0;
}

#something {
  background: transparent url(https://i.stack.imgur.com/RL5UH.png) 50% 50% no-repeat;
  min-width: 300px;
  min-height: 300px;
  box-shadow: inset 0 0 20px #0f0, inset 0 0 20px #0f0, inset 0 0 20px #0f0;
}
<div id="something"></div>


Edited parce que je me suis rendu compte que je suis un idiot et que j'ai oublié de proposer la solution la plus simple (première} _, qui utilise un élément enfant autrement vide pour appliquer les bordures sur l'arrière-plan:

#something {
  background: transparent url(https://i.stack.imgur.com/RL5UH.png) 50% 50% no-repeat;
  min-width: 300px;
  min-height: 300px;
  padding: 0;
  position: relative;
}
#something div {
  position: absolute;
  top: 0;
  left: 0;
  right: 0;
  bottom: 0;
  border: 10px solid rgba(0, 255, 0, 0.6);
}
<div id="something">
  <div></div>
</div>


Edited after @ Commentaire de CoryDanielson, ci-dessous :

jsfiddle.net/dPcDu/2 vous pouvez ajouter un 4ème paramètre px pour le box-shadow qui diffuse et reflétera plus facilement ses images.

#something {
  background: transparent url(https://i.stack.imgur.com/RL5UH.png) 50% 50% no-repeat;
  min-width: 300px;
  min-height: 300px;
  box-shadow: inset 0 0 0 10px rgba(0, 255, 0, 0.5);
}
<div id="something"></div>

124
David Thomas

Je recommanderais d'utiliser box-sizing.

*{
  -webkit-box-sizing:border-box;
  -moz-box-sizing:border-box;
  -ms-box-sizing:border-box;
  box-sizing:border-box;
}

#bar{
  border: 10px solid green;
  }
34

Pour produire un encadré dans un élément, la seule solution que j'ai trouvée (et j'ai essayé toutes les suggestions de ce fil en vain) est d'utiliser un pseudo-élément tel que: before

Par exemple.

.has-inset-border:before {
  content: "foo"; /* you need something or it will be invisible at least on Chrome */
  color: transparent;
  position: absolute;
  left: 10px;
  right: 10px;
  top: 10px;
  width: 10px;
  border: 4px dashed red;
}

La propriété de taille de boîte ne fonctionnera pas, car la bordure se termine toujours en dehors de tout.

L'option box-shadow présente le double inconvénient de ne pas fonctionner correctement et de ne pas être supportée aussi largement (et de rendre plus de temps de calcul pour le rendu du processeur, si vous y tenez).

11
podperson

C'est un vieux truc, mais je trouve toujours que le moyen le plus simple de le faire est d'utiliser un contour décalé avec une valeur négative (l'exemple ci-dessous utilise -6px). Voici un violon de celui-ci - j'ai rendu la bordure extérieure rouge et le contour blanc pour différencier les deux:

.outline-offset {
width:300px;
height:200px;
background:#333c4b;
border:2px solid red;
outline:2px #fff solid;
outline-offset:-6px;
}

<div class="outline-offset"></div>
7
Vanessa King

Je ne sais pas à quoi vous comparez.

Mais un moyen très simple d'avoir un aspect de bordure inséré par rapport à d'autres éléments non délimités par une bordure consiste à ajouter un border: ?px solid transparent; à tous les éléments qui non ont une bordure. 

L'objet à bordure aura l'air inséré.

http://jsfiddle.net/cmunns/cgrtd/

2
Adam Munns

Si vous voulez vous assurer que la bordure se trouve à l'intérieur de votre élément, vous pouvez utiliser

box-sizing:border-box;

cela placera la bordure suivante à l'intérieur de l'élément:

border: 10px solid black;

(résultat similaire, vous obtiendrez le paramètre additonal inset sur box-shadow, mais celui-ci est destiné à la bordure réelle et vous pouvez toujours utiliser votre shadow pour autre chose.)

Note pour une autre réponse ci-dessus: dès que vous utilisez une variable quelconque inset sur box-shadow d'un élément donné, vous êtes limité à un maximum de 2 ombres de boîte sur cet élément et nécessiteriez un div wrapper pour une ombre supplémentaire.

Les deux solutions doivent également vous débarrasser des effets 3D indésirables ..__ Notez également que les deux solutions sont empilables (voir l'exemple que j'ai ajouté en 2018).

.example-border {
  width:100px;
  height:100px;
  border:40px solid blue;
  box-sizing:border-box;
  float:left;
}

.example-shadow {
  width:100px;
  height:100px;
  float:left;
  margin-left:20px;
  box-shadow:0 0 0 40px green inset;
}

.example-combined {
  width:100px;
  height:100px;
  float:left;
  margin-left:20px;
  border:20px solid orange;
  box-sizing:border-box;
  box-shadow:0 0 0 20px red inset;
}
<div class="example-border"></div>
<div class="example-shadow"></div>
<div class="example-combined"></div>

2
Chris S.

Tu peux le faire:

.thing {
  border: 2px solid transparent;
}
.thing:hover {
  border: 2px solid green;
}
0
Gustavo Lopez

J'essayais donc de faire passer une bordure en survol, mais la barre du bas du menu principal était déplacée, ce qui ne semblait pas très beau.

#top-menu .menu-item a:hover {
    border-bottom:4px solid #ec1c24;
    padding-bottom:14px !important;
}
#top-menu .menu-item a {
    padding-bottom:18px !important;
}

J'espère que cela aidera quelqu'un là-bas.

0
Derrik de Moei

Solution SCSS simple avec pseudo-éléments

Démo en direct: https://codepen.io/vlasterx/pen/xaMgag

// Change border size here
$border-width: 5px;

.element-with-border {
	display: flex;
	height: 100px;
	width: 100%;
	position: relative;
	background-color: #f2f2f2;
	box-sizing: border-box;
	
	// Use pseudo-element to create inset border
	&:before {
		position: absolute;
		content: ' ';
		display: flex;
		border: $border-width solid black;
		left: 0;
		right: 0;
		top: 0;
		bottom: 0;
		border: $border-width solid black;
		// Important: We must deduct border size from width and height
		width: calc(100% - $border-width); 
		height: calc(100% - $border-width);
	}
}
<div class="element-with-border">
  Lorem ipsum dolor sit amet
</div>

0
Vladimir Jovanović

Vous pouvez utiliser background-clip: border-box;

Exemple:

.example {
padding: 2em;
border: 10px solid rgba(51,153,0,0.65);
background-clip: border-box;
background-color: yellow;
}

<div class="example">Example with background-clip: border-box;</div>
0
Jaha Ganiev

Si box-sizing n'est pas une option, une autre façon de faire est simplement d'en faire un enfant de l'élément size.

Démo

CSS

.box {
  width: 100px;
  height: 100px;
  display: inline-block;
  margin-right: 5px;
}
.border {
  border: 1px solid;
  display: block;
}
.medium { border-width: 10px; }
.large  { border-width: 25px; }


HTML

<div class="box">
  <div class="border small">A</div>
</div>
<div class="box">
  <div class="border medium">B</div>
</div>
<div class="box">
  <div class="border large">C</div>
</div>
0
Adam Grant