epub.js icon indicating copy to clipboard operation
epub.js copied to clipboard

The theme does not render correctly

Open godlanbo opened this issue 4 years ago • 8 comments

When I use rendition.themes.register to register multiple themes, I can only switch my themes once, and then switch the themes that have just been selected will not take effect.

// themeList
[
    {
      name: 'Default',
      style: {
        body: {
          'color': '#4c5059',
          'background': '#cecece',
        }
      }
    },
    ...
]
// register
this.themeList.forEach(theme => {
   this.rendition.themes.register(theme.name, theme.style)
})

This problem occurs when I use the 0.3.87 version. When I use the 0.3.71 version, this problem does not occur, but when using the 0.3.71 version, many css will appear after switching the theme multiple times in the rendered iframe. image

godlanbo avatar Jul 07 '20 15:07 godlanbo

Hi @godlanbo, I'm having the same issue as you and was able to circumvent it by calling the override method instead, like this:

      const backgroundColors = {
        dark: {
          background: 'black',
          color: 'white'
        },
      }
      rendition.themes.override('color', backgroundColors.dark.color, true)
      rendition.themes.override(
        'background',
        backgroundColors.dark.background,
        true
      )

hope this helps you while a proper fix is issued

gsinovsky avatar Jul 13 '20 20:07 gsinovsky

Hi @godlanbo, I'm having the same issue as you and was able to circumvent it by calling the override method instead, like this:

      const backgroundColors = {
        dark: {
          background: 'black',
          color: 'white'
        },
      }
      rendition.themes.override('color', backgroundColors.dark.color, true)
      rendition.themes.override(
        'background',
        backgroundColors.dark.background,
        true
      )

hope this helps you while a proper fix is issued

Thank you for your answer, but I have some questions: After I registered the theme, I hope to switch the theme through rendition.themes.select(name). How do you change the whole theme style in this way of writing? In your writing, it seems that I need to traverse the entire theme into the e-book when it is used.

godlanbo avatar Jul 14 '20 07:07 godlanbo

@godlanbo I'm not registering any themes whatsoever, so I'm not using select. I keep my own themes saved in the store of my app and I switch between them using the override method, in mi case I'm only changing the background color and the font color of the book, so I only need to call the method twice every time to apply the "theme".

gsinovsky avatar Jul 14 '20 13:07 gsinovsky

@godlanbo I'm not registering any themes whatsoever, so I'm not using select. I keep my own themes saved in the store of my app and I switch between them using the override method, in mi case I'm only changing the background color and the font color of the book, so I only need to call the method twice every time to apply the "theme".

Thank you for your reply, I know what you mean, but my theme style will be effective in my entire project, not only the background color and font color, so use override one by one to change the attribute value one by one in this case. The following seems unrealistic. Because each of my theme style file tables is more than 100 lines, using override to reset the style is a disaster for me.

godlanbo avatar Jul 14 '20 13:07 godlanbo

Same questions here. The themes can only be switched once. I can switch theme A to theme B , but I fail to swicth theme B back to theme A. I guess the data has been updated correctly but the epubjs can't rerender it as fast as possible.

Chorer avatar Aug 09 '20 07:08 Chorer

@godlanbo Since traversing the entire theme may be inefficient,in this project it could be the only choice.I am developing this project too and I know when switching the theme, we need to reset the reader style and the global style.For the reader style ,we could consider using for...in loop and override method to add attributes one by one: Supposed here is one of the theme:

const  _themeList = [
    {
      name: 'Default',
      style: {
        body: {
          'color': '#4c5059',
          'background': '#cecece',
        }
      }
    }
  ]

And here is the changeTheme method:

  methods:{
    changeTheme(index){
      const name = this._themeList[index].name
      // this.currentBook.rendition.themes.select(name)
      const bodyObject = this._themeList[index].style.body
      for(let key in bodyObject){
        this.currentBook.rendition.themes.override(key,bodyObject[key],true)
      }
    }
  }

According to what @gsinovsky has said,we use override instead of select.I know it may cause performance loss,but for this project,we could use it since the total lines of each theme's style haven't more than 10. You said each of your theme style file tables is more than 100 lines,but I guess what you mean is the global style,not the reader style.And for the the global style,we can include it by other ways.

Chorer avatar Aug 09 '20 08:08 Chorer

@godlanbo Since traversing the entire theme may be inefficient,in this project it could be the only choice.I am developing this project too and I know when switching the theme, we need to reset the reader style and the global style.For the reader style ,we could consider using for...in loop and override method to add attributes one by one: Supposed here is one of the theme:

const  _themeList = [
    {
      name: 'Default',
      style: {
        body: {
          'color': '#4c5059',
          'background': '#cecece',
        }
      }
    }
  ]

And here is the changeTheme method:

  methods:{
    changeTheme(index){
      const name = this._themeList[index].name
      // this.currentBook.rendition.themes.select(name)
      const bodyObject = this._themeList[index].style.body
      for(let key in bodyObject){
        this.currentBook.rendition.themes.override(key,bodyObject[key],true)
      }
    }
  }

According to what @gsinovsky has said,we use override instead of select.I know it may cause performance loss,but for this project,we could use it since the total lines of each theme's style haven't more than 10. You said each of your theme style file tables is more than 100 lines,but I guess what you mean is the global style,not the reader style.And for the the global style,we can include it by other ways.

Thank you for your reply. Your last paragraph woke me up. It is true that only the reader style needs to be registered before switching. This can be replaced by override, and then the global style can be considered to use the global style tag when switching Dynamic loading.

godlanbo avatar Aug 09 '20 09:08 godlanbo

@godlanbo Since traversing the entire theme may be inefficient,in this project it could be the only choice.I am developing this project too and I know when switching the theme, we need to reset the reader style and the global style.For the reader style ,we could consider using for...in loop and override method to add attributes one by one: Supposed here is one of the theme:

const  _themeList = [
    {
      name: 'Default',
      style: {
        body: {
          'color': '#4c5059',
          'background': '#cecece',
        }
      }
    }
  ]

And here is the changeTheme method:

  methods:{
    changeTheme(index){
      const name = this._themeList[index].name
      // this.currentBook.rendition.themes.select(name)
      const bodyObject = this._themeList[index].style.body
      for(let key in bodyObject){
        this.currentBook.rendition.themes.override(key,bodyObject[key],true)
      }
    }
  }

According to what @gsinovsky has said,we use override instead of select.I know it may cause performance loss,but for this project,we could use it since the total lines of each theme's style haven't more than 10. You said each of your theme style file tables is more than 100 lines,but I guess what you mean is the global style,not the reader style.And for the the global style,we can include it by other ways.

@Chorer thank you . your answer help me to solved the problem. but can you help me. how can i add this style dynamically like
font size.


body: {
        p: {
        line-height: 1.5rem
        }
   }

robiulhassanshakil avatar Oct 27 '22 06:10 robiulhassanshakil