Come aggiungere un'icona a forma di spinner al pulsante quando si trova nello stato Caricamento?


191

I pulsanti di Twitter Bootstrap hanno un bel Loading...stato disponibile.

Il fatto è che mostra solo un messaggio come Loading...passato attraverso l' data-loading-textattributo in questo modo:

<button type="button" class="btn btn-primary start" id="btnStartUploads"
        data-loading-text="@Localization.Uploading">
    <i class="icon-upload icon-large"></i>
    <span>@Localization.StartUpload</span>
</button>

Guardando Font Awesome, vedi che ora c'è un'icona a forma di spinner animato .

Ho provato a integrare l'icona di quel filatore quando sparavo Uploadun'operazione come questa:

$("#btnStartUploads").button('loading');
$("#btnStartUploads i").removeAttr('class');
$("#btnStartUploads i").addClass('icon-spinner icon-spin icon-large');

ma questo non ha avuto alcun effetto, cioè vedo solo il Uploading...testo sul pulsante.

È possibile aggiungere un'icona quando il pulsante è nello stato Caricamento? Sembra che Bootstrap rimuova in qualche modo l'icona <i class="icon-upload icon-large"></i>all'interno del pulsante mentre si trova nello stato Caricamento.


Ecco una semplice demo che mostra il comportamento che descrivo sopra. Come vedi quando entra nello stato Caricamento, l'icona scompare. Riappare subito dopo l'intervallo di tempo.


1
È possibile controllare la mia soluzione per animare aspetto filatore: stackoverflow.com/questions/15982233/...
Andrew Dryga

Vi consiglio di utilizzare questo approccio stackoverflow.com/a/15988830/437690
limitium

Risposte:


101

Se guardi l'origine bootstrap-button.js , vedrai che il plug-in bootstrap sostituisce i pulsanti html interni con qualsiasi cosa sia nel testo di caricamento dei dati durante la chiamata $(myElem).button('loading').

Per il tuo caso, penso che dovresti essere in grado di farlo:

<button type="button"
        class="btn btn-primary start"
        id="btnStartUploads"
        data-loading-text="<i class='icon-spinner icon-spin icon-large'></i> @Localization.Uploading">
    <i class="icon-upload icon-large"></i>
    <span>@Localization.StartUpload</span>
</button>

1
Funziona alla grande gurch101! Ho dimenticato che si può mescolare HTMLcon il testo in una proprietà tag. :-)
Leniel Maccaferri,

11
Fiddle non funziona per Safari 6.0.5 (7536.30.1), Chrome 31.0.1604.0 canary su Mac OS X.
Burak Erdem

16
Risolto: jsfiddle.net/6U5q2/270 Nota che è per v2.3.2. Non so se funziona per 3.x
Eric Freese

13
data-loading-textè obsoleto dalla v3.3.5 e verrà rimosso nella v4.
Jonathan,

2
@Jonathan Se è deprecato in v3.3.5, qual è la sostituzione in entrambi dopo v3.3.5 e v4?
PaladiN,

324

Soluzione semplice per Bootstrap 3 utilizzando animazioni CSS3.

Inserisci quanto segue nel tuo CSS:

.glyphicon.spinning {
    animation: spin 1s infinite linear;
    -webkit-animation: spin2 1s infinite linear;
}

@keyframes spin {
    from { transform: scale(1) rotate(0deg); }
    to { transform: scale(1) rotate(360deg); }
}

@-webkit-keyframes spin2 {
    from { -webkit-transform: rotate(0deg); }
    to { -webkit-transform: rotate(360deg); }
}

Quindi aggiungi la spinninglezione a un glyphiconpo 'durante il caricamento per ottenere l'icona che gira:

<button class="btn btn-lg btn-warning">
    <span class="glyphicon glyphicon-refresh spinning"></span> Loading...    
</button>

Basato su http://www.bootply.com/128062#

  • Nota: IE9 e versioni precedenti non supportano le animazioni CSS3.

4
Non dovrebbe essere animatione non -animation?
Andrey Mikhaylov - lolmaus,

3
Soluzione eccellente Sto riscontrando problemi con questa animazione in Safari sul desktop e sull'iPad. Mostra l'icona ma non la anima. Hai mai provato qualcosa del genere?
JayhawksFan93,

@ JayhawksFan93 sì, recentemente ho notato lo stesso in IE. Presto lo
esaminerò

2
la risposta è stata aggiornata animationinvece di -animation. Con quel cambiamento bene in FF e IE per me. L'animazione di Firefox non sembra molto liscia.
Flion,

1
+1.
Ne ho


13

Per rendere la soluzione di @flion davvero fantastica, puoi regolare il punto centrale per quell'icona in modo che non oscilli su e giù. Questo mi sembra giusto per una piccola dimensione del carattere:

.glyphicon-refresh.spinning {
  transform-origin: 48% 50%;
}

1
.glyphicon-refresh.spinning { transform-origin: 50% 58%; }ha funzionato per me
oluckyman il

ronza, { transform-origin: 50% 49%; }risolvi nel mio caso dove sto usando coginvece.
Vitor Canova,

Noto anche l'oscillazione, ma qual è la logica per cambiare questi numeri? Come devo sintonizzarli?
Elachell,

2

Ecco la mia soluzione per Bootstrap 4:

<button id="search" class="btn btn-primary" 
data-loading-text="<i class='fa fa-spinner fa-spin fa-fw' aria-hidden='true'></i>Searching">
  Search
</button>

var setLoading = function () {
  var search = $('#search');
  if (!search.data('normal-text')) {
    search.data('normal-text', search.html());
  }
  search.html(search.data('loading-text'));
};

var clearLoading = function () {
  var search = $('#search');
  search.html(search.data('normal-text'));
};

setInterval(() => {
  setLoading();
  setTimeout(() => {
    clearLoading();
  }, 1000);
}, 2000);

Dai un'occhiata su JSFiddle


2

Questi sono miei, basati su animazioni SVG e CSS pure. Non prestare attenzione al codice JS nel seguente snippet, è solo a scopo dimostrativo. Sentiti libero di personalizzare i tuoi in base al mio, è semplicissimo.

var svg = d3.select("svg"),
    columnsCount = 3;

['basic', 'basic2', 'basic3', 'basic4', 'loading', 'loading2', 'spin', 'chrome', 'chrome2', 'flower', 'flower2', 'backstreet_boys'].forEach(function(animation, i){
  var x = (i%columnsCount+1) * 200-100,
      y = 20 + (Math.floor(i/columnsCount) * 200);
  
  
  svg.append("text")
    .attr('text-anchor', 'middle')
    .attr("x", x)
    .attr("y", y)
    .text((i+1)+". "+animation);
  
  svg.append("circle")
    .attr("class", animation)
    .attr("cx",  x)
    .attr("cy",  y+40)
    .attr("r",  16)
});
circle {
  fill: none;
  stroke: #bbb;
  stroke-width: 4
}

.basic {
  animation: basic 0.5s linear infinite;
  stroke-dasharray: 20 80;
}

@keyframes basic {
  0%    {stroke-dashoffset: 100;}
  100%  {stroke-dashoffset: 0;}
}

.basic2 {
  animation: basic2 0.5s linear infinite;
  stroke-dasharray: 80 20;
}

@keyframes basic2 {
  0%    {stroke-dashoffset: 100;}
  100%  {stroke-dashoffset: 0;}
}

.basic3 {
  animation: basic3 0.5s linear infinite;
  stroke-dasharray: 20 30;
}

@keyframes basic3 {
  0%    {stroke-dashoffset: 100;}
  100%  {stroke-dashoffset: 0;}
}

.basic4 {
  animation: basic4 0.5s linear infinite;
  stroke-dasharray: 10 23.3;
}

@keyframes basic4 {
  0%    {stroke-dashoffset: 100;}
  100%  {stroke-dashoffset: 0;}
}

.loading {
  animation: loading 1s linear infinite;
  stroke-dashoffset: 25;
}

@keyframes loading {
  0%    {stroke-dashoffset: 0;    stroke-dasharray: 50 0; }
  50%   {stroke-dashoffset: -100; stroke-dasharray: 0 50;}
  100%  { stroke-dashoffset: -200;stroke-dasharray: 50 0;}
}

.loading2 {
  animation: loading2 1s linear infinite;
}

@keyframes loading2 {
  0% {stroke-dasharray: 5 28.3;   stroke-dashoffset: 75;}
  50% {stroke-dasharray: 45 5;    stroke-dashoffset: -50;}
  100% {stroke-dasharray: 5 28.3; stroke-dashoffset: -125; }
}

.spin {
  animation: spin 1s linear infinite;
  stroke-dashoffset: 25;
}

@keyframes spin {
  0%    {stroke-dashoffset: 0;    stroke-dasharray: 33.3 0; }
  50%   {stroke-dashoffset: -100; stroke-dasharray: 0 33.3;}
  100%  { stroke-dashoffset: -200;stroke-dasharray: 33.3 0;}
}

.chrome {
  animation: chrome 2s linear infinite;
}

@keyframes chrome {
  0%    {stroke-dasharray: 0 100; stroke-dashoffset: 25;}
  25%   {stroke-dasharray: 75 25; stroke-dashoffset: 0;}
  50%   {stroke-dasharray: 0 100;  stroke-dashoffset: -125;}
  75%    {stroke-dasharray: 75 25; stroke-dashoffset: -150;}
  100%   {stroke-dasharray: 0 100; stroke-dashoffset: -275;}
}

.chrome2 {
  animation: chrome2 1s linear infinite;
}

@keyframes chrome2 {
  0%    {stroke-dasharray: 0 100; stroke-dashoffset: 25;}
  25%   {stroke-dasharray: 50 50; stroke-dashoffset: 0;}
  50%   {stroke-dasharray: 0 100;  stroke-dashoffset: -50;}
  75%   {stroke-dasharray: 50 50;  stroke-dashoffset: -125;}
  100%  {stroke-dasharray: 0 100;  stroke-dashoffset: -175;}
}

.flower {
  animation: flower 1s linear infinite;
}

@keyframes flower {
  0%    {stroke-dasharray: 0  20; stroke-dashoffset: 25;}
  50%   {stroke-dasharray: 20 0;  stroke-dashoffset: -50;}
  100%  {stroke-dasharray: 0 20;  stroke-dashoffset: -125;}
}

.flower2 {
  animation: flower2 1s linear infinite;
}

@keyframes flower2 {
  0%    {stroke-dasharray: 5 20;  stroke-dashoffset: 25;}
  50%   {stroke-dasharray: 20 5;  stroke-dashoffset: -50;}
  100%  {stroke-dasharray: 5 20;  stroke-dashoffset: -125;}
}

.backstreet_boys {
  animation: backstreet_boys 3s linear infinite;
}

@keyframes backstreet_boys {
  0%    {stroke-dasharray: 5 28.3;  stroke-dashoffset: -225;}
  15%    {stroke-dasharray: 5 28.3;  stroke-dashoffset: -300;}
  30%   {stroke-dasharray: 5 20;  stroke-dashoffset: -300;}
  45%    {stroke-dasharray: 5 20;  stroke-dashoffset: -375;}
  60%   {stroke-dasharray: 5 15;  stroke-dashoffset: -375;}
  75%    {stroke-dasharray: 5 15;  stroke-dashoffset: -450;}
  90%   {stroke-dasharray: 5 15;  stroke-dashoffset: -525;}
  100%   {stroke-dasharray: 5 28.3;  stroke-dashoffset: -925;}
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/d3/4.13.0/d3.min.js"></script>
<svg width="600px" height="700px"></svg>

Disponibile anche su CodePen: https://codepen.io/anon/pen/PeRazr


1

Ecco una soluzione css a tutti gli effetti ispirata a Bulma. Basta aggiungere

    .button {
      display: inline-flex;
      align-items: center;
      justify-content: center;
      position: relative;
      min-width: 200px;
      max-width: 100%;
      min-height: 40px;
      text-align: center;
      cursor: pointer;
    }

    @-webkit-keyframes spinAround {
      from {
        -webkit-transform: rotate(0deg);
        transform: rotate(0deg);
      }
      to {
        -webkit-transform: rotate(359deg);
        transform: rotate(359deg);
      }
    }
    @keyframes spinAround {
      from {
        -webkit-transform: rotate(0deg);
        transform: rotate(0deg);
      }
      to {
        -webkit-transform: rotate(359deg);
        transform: rotate(359deg);
      }
    }

    .button.is-loading {
      text-indent: -9999px;
      box-shadow: none;
      font-size: 1rem;
      height: 2.25em;
      line-height: 1.5;
      vertical-align: top;
      padding-bottom: calc(0.375em - 1px);
      padding-left: 0.75em;
      padding-right: 0.75em;
      padding-top: calc(0.375em - 1px);
      white-space: nowrap;
    }

    .button.is-loading::after  {
      -webkit-animation: spinAround 500ms infinite linear;
      animation: spinAround 500ms infinite linear;
      border: 2px solid #dbdbdb;
      border-radius: 290486px;
      border-right-color: transparent;
      border-top-color: transparent;
      content: "";
      display: block;
      height: 1em;
      position: relative;
      width: 1em;
    }
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.