Правило цвета тела Google Chrome не изменяется сразу - PullRequest
0 голосов
/ 01 мая 2020

Я пытаюсь создать плавный переход для всех CSS правил, связанных с цветами (background-color, border-color, color ...), когда пользователь меняет тему моего сайта, добавляя transition Править для всех элементов одновременно с помощью селектора *, который я удаляю после завершения перехода, поэтому другие правила transition остаются такими же, какими они должны быть после завершения перехода темы.

Отлично работает на Firefox, но в Google Chrome (v81) кажется, что правило color, примененное к телу, немного задерживается (вы также можете увидеть это на событии transitionend):

(Примечание: когда я ссылаюсь на переход color, речь идет о правиле CSS color, которое применяется к тексту, я не ссылаюсь на цвет тела или другие)

document.querySelector('button').addEventListener('click', () => {
  if (document.documentElement.classList.contains('dark-theme')) {
    document.documentElement.classList.remove('dark-theme');
  }
  else {
    document.documentElement.classList.add('dark-theme');
  }
});

document.addEventListener('transitionstart', (event) => {
  if (event.propertyName === 'color') {
    if (event.target.tagName === 'H1') {
      document.querySelector('.h1-transition').textContent = 'start';
    }
    else if (event.target.tagName === 'BODY') {
      document.querySelector('.body-transition').textContent = 'start';
    }
  }
});

document.addEventListener('transitionend', (event) => {
  if (event.propertyName === 'color') {
    if (event.target.tagName === 'H1') {
      document.querySelector('.h1-transition').textContent = 'end';
    }
    else if (event.target.tagName === 'BODY') {
      document.querySelector('.body-transition').textContent = 'end';
    }
  }
});
body {
  padding: 0;
  margin: 0;
  background-color: #fff;
  color: #000;
  font-family: sans-serif;
  text-align: center;
}

:root.dark-theme body {
  background-color: #333;
  color: #fff;
}

:root * {
  transition: all 5s ease-in-out;
}
<h1>Some text</h1>
<button>Change theme</button>
<p>
  Body's color transition :
  <span class="body-transition">none</span>
</p>
<p>
  H1's color transition :
  <span class="h1-transition">none</span>
</p>

Вот мой окончательный код, в который я добавляю правило перехода, только когда нажимаю кнопку, а затем удаляю его, когда тело завершило свою работу. переход:

function themeTransitionEnd(event) {
  if (event.target === document.body) {
    document.documentElement.removeEventListener('transitionend', themeTransitionEnd);
    document.documentElement.classList.remove('theme-transition');
  }
}

function invertTheme() {
  document.documentElement.addEventListener('transitionend', themeTransitionEnd);
  document.documentElement.classList.add('theme-transition');

  if (document.documentElement.classList.contains('dark-theme')) {
    document.documentElement.classList.remove('dark-theme');
  }
  else {
    document.documentElement.classList.add('dark-theme');
  }
}

document.querySelector('button').addEventListener('click', invertTheme);

/* TRACK TRANSITIONS FOR DEBUG PURPOSE */
document.addEventListener('transitionstart', (event) => {
  if (event.propertyName === 'color') {
    if (event.target.tagName === 'BODY') {
      document.querySelector('.body-transition').textContent = 'start';
    }
    else if (event.target.tagName === 'H1') {
      document.querySelector('.h1-transition').textContent = 'start';
    }
    else if (event.target.tagName === 'H2') {
      document.querySelector('.h2-transition').textContent = 'start';
    }
  }
});
document.addEventListener('transitionend', (event) => {
  if (event.propertyName === 'color') {
    if (event.target.tagName === 'BODY') {
      document.querySelector('.body-transition').textContent = 'end';
    }
    else if (event.target.tagName === 'H1') {
      document.querySelector('.h1-transition').textContent = 'end';
    }
    else if (event.target.tagName === 'H2') {
      document.querySelector('.h2-transition').textContent = 'end';
    }
  }
});
/* LIGHT THEME */
body {
  padding: 0;
  margin: 0;
  background-color: #fff;
  color: #000;
  font-family: sans-serif;
  transition: none;
  text-align: center;
}
h2 {
  color: purple;
}


/* DARK THEME */
:root.dark-theme body {
  background-color: #444;
  color: #fff;
}
:root.dark-theme h2 {
  color: red;
}

/* TRANSITIONS */
:root.theme-transition * {
  transition: all 5s linear !important;
}
<h1>Some text using body's color rule</h1>

<h2>Some text using its own color rule</h2>

<button>Invert theme</button>

<p>
  Body's color transition :
  <span class="body-transition">none</span>
</p>
<p>
  H1's color transition :
  <span class="h1-transition">none</span>
</p>
<p>
  H2's color transition :
  <span class="h2-transition">none</span>
</p>

Переход 5s предназначен для лучшего понимания проблемы, и, как вы можете видеть, цвет Н2 медленно меняется с фиолетового на красный и наоборот , но из-за задержки на цвете тела цвет H1 внезапно меняется, и transitionend никогда не срабатывает.

Меня не волнует, что transitionend событие не сработает, это только для того, чтобы отладка, но я не использую его, но задержка цветового перехода тела довольно некрасива.

Это ошибка в Google Chrome, или она предназначена? И как я могу это исправить?

...