Элементы Svelte Dynami c html не применяются css - PullRequest
1 голос
/ 09 января 2020

У меня есть компонент svelte, который использует библиотеку для отображения дерева JSON, но эта библиотека нуждается в хуке html для загрузки. После этого он генерирует свою собственную структуру html со своими собственными классами и идентификаторами. Пока все хорошо, но если я добавлю в свой компонент некоторые стили для селекторов, которые будут сгенерированы в будущем, стиль не будет применен.

Это проблема? Есть ли какое-то решение?

Вот мой пример кода:

<script>
  import { onMount } from "svelte";
  import { Content } from "@smui/card";
  import { copyToClipboard } from "../../public/js/utils";

  export let data;
  let contentBody;

  onMount(() => {

    const editor = new JSONEditor(
      contentBody,
      { mode: "view", navigationBar: false },
      data
    );

    const editorMenu = document.getElementsByClassName("jsoneditor-menu")[0];
    const copy = document.createElement("img");
    copy.src = "../../public/img/copy.png";
    copy.setAttribute("class", "custom-button");
    editorMenu.append(copy);

    copy.onclick = () => copyToClipboard(editor.getText()));
  });
</script>

<style>
  .jsoneditor-menu {
    background-color: #525b69;
    border: 1px solid #e8e8e8;
  }

  .jsoneditor {
    border: 1px solid #e8e8e8;
  }

  .json {
    height: 555px;
  }

 .custom-button {
    width: 20px;
    height: 20px;
    margin: 2px;
    padding: 2px;
    border-radius: 2px;
    border: 1px solid transparent;
    color: #fff;
    opacity: 0.8;
    font-family: arial, sans-serif;
    font-size: 10pt;
    float: left;
  }

</style>

<Content>
  <div class="json" bind:this={contentBody} />
</Content>

Примечание. Стиль применяется только для root element json class

1 Ответ

2 голосов
/ 09 января 2020

Да, вы правильно определили проблему. Решение состоит в том, чтобы сделать ваш стиль глобальным с помощью псевдо-селектора :global magi c ( docs ).

<style>
  /* this will not be removed, and not scoped to the component */
  :global(.foo) { ... }

  /* this will not be removed, but still scoped to divs inside _this_ component */
  div :global(.bar) { ... }
</style>

CSS определение объема в Svelte реализовано путем добавления уникального Класс для CSS селекторов, как вы их создали. Например, если вы напишите .foo, компилятор превратит его в .svelte-a3bmb2.foo.

Чтобы это работало, компилятору также необходимо добавить этот класс ко всем элементам, соответствующим селектору .foo. Он может сделать это для элементов, которые он видит в разметке. Но он не может сделать это для элементов, которые динамически создаются во время выполнения.

Вот почему (я полагаю) Svelte удаляет CSS правил, которые ничего не соответствуют в разметке компонента. Когда это происходит, компилятор обычно выдает предупреждения, например «неиспользуемый CSS селектор».

Если вы сделаете стили глобальными, компилятору больше не нужно их расширять, поэтому проблема решена.

...