Switching theme of my website - less

I wish to allow users to switch the entire color-scheme of my site with a buttonpress.
I have 2 separate .less files with the same global variables, but different colors. The problem seems quite simple.. "swap 1 .less file for the other". But how do I actually accomplish this?
Of course, I could alter the entire site element-by-element in the .js based on the state of a singleton, but that seems like a duct-tape-solution.

One possible solution by example: say you have a div element that you wish to color its background differently in each theme. Load both .less files and edit them like this (add the theme class to the body element that wraps the whole document):
theme-1.less
body.theme-1 {
div.address {
background-color: yellow;
}
}
theme-2.less
body.theme-2 {
div.address {
background-color: fuchsia;
}
}
Then provide a mechanism for the user to change the theme (e.g. drop-down menu). When the user selects from the menu - say for example changing from theme-1 to theme-2 - issue this JS:
document.getElementsByTagName("body")[0].classList.replace("theme-1", "theme-2");
Generically you can do it in more than one way:
document.getElementsByTagName("body")[0].classList.replace(<currently-selected-theme>, <newly-selected-theme);
or
document.getElementsByTagName("body")[0].classList.remove(<currently-selected-theme>).add(<newly-selected-theme>);

Related

Best way to dynamically change theme of my Vue.js SPA?

So I think the title is enough explaination: I would like to dynamically theme my whole application. Maybe this means to change color of all divs when I press a specific button, or change the whole webapp's colors when a specific user logs in.
Just to give some insights on what I am currently working on I will say that I have built a Vue.js app that uses many libraries, including one called Element-ui which already has a theming option built onto it. The problem is that it's written in scss and I would like to change all the variable colors during the navigation. My project looks something like this:
<template>
... some HTML and components...
</template>
<script>
... some javascript ...
</script>
<style scoped>
... some style that is scoped to the current component only ...
</style>
I have many files like this one so making a "global function" for all of them doesn't seem practical to me. Also I import the main scss file just once in my main.js.
Is there anything I can do to create a dinamic theming for my webapp? Is using saas a good idea? Javascript maybe?
EDIT
I feel like I didn't explain it good enough so I want to add a simple example. If you visit the Element page you can see in the top right corner there is a color selector that, when a color changes, it changes also the whole website's accent colors like the buttons colors, the links colors etc.
Hope this can help understanding a bit better
EDIT
Right now I have settled on a very poor and, I think, badly optimized solution. The idea is that when the user changes theme, I just create a new css file and append it to the current document.
let sheet = document.createElement('style')
sheet.innerHTML = `*[class*="--primary"]{
background-color: ${colors[0]};
}
...`;
document.body.appendChild(sheet);
I truly think this is a very bad solution but right now I can't come up with nothing else that could work dinamically when the user changes a parameter. I would really want the process to be flawless: the user picks a color and the whole application just changes to that specific color, no prebuilt theme.css.
FINAL EDIT
I've finally found a solution, refer to the answer!
Finally, after a few long days I came up with a solution that I think is both easy to implement and very very lightweight.
CSS VARIABLES
Before searching up a lot, I didn't even know the existance of these kind of variables and they don't seem so used. Anyway, I hope this can help someone out there seeking my same answer:
<template
<app-main></app-main>
<app-sidebar></app-sidebar>
...
</template>
<style>
:root{
--primary-color: #C5C5C5!important;
--secondary-color: #6C7478!important;
--tertiary-color: #FFFFFF!important;
--success-color: #80b855!important;
--warning-color: #eaca44!important;
--error-color: #ef4d4d!important;
}
/* Theming */
header{
background-color: var(--primary-color);
}
div{
color: var(--tetriary-colory);
}
...
/* END */
</style>
<script>
import axios from 'axios' /* all your imports etc. */
export default{
data(){
},
methods: {
axios.post(`http://localhost:8080/foo`).then(function (response){
let bodyStyles = document.body.style;
bodyStyles.setProperty('--primary-color', response.colors[0]);
bodyStyles.setProperty('--tertiary-color', response.colors[1]);
...
}
}
}
</script>
As you can see, I just initialize a few useful CSS variables and when I need them (for example in that api post call) I just modify them using a simple bodyStyles.setProperty('propertyName') function.
I really enjoy this type of setup since I use it in my login page so when a user successfully logs-in I load from the database his own colors and set them up just like that.
Hoping this can help someone! Cheers!

Hide title in header of my Dokuwiki

Because I'm using a logo in my header, I don't need the title-text. But I would like to have a browser-title.
So I need to set a title and have to hide it in the header - but how?
Possible also to hide the title text with a proper CSS display: none setting. It can be put into the conf/userstyle.css file, so it wont be overwritten by updates. The text resides still in the page but becomes invisible. It may improve the search-engine hits also, maybe.
Possible CSS code:
div.headings h1 span { display: none !important; }
I assume that your wiki looks like dokuwiki.org (meaning that you are using one of recent versions and default template). If not the approach still should be the same, search for $conf['title'] in your template.
There is a block in lib/tpl/dokuwiki/tpl_header.php:
// display logo and wiki title in a link to the home page
tpl_link(
wl(),
'<img src="'.$logo.'" '.$logoSize[3].' alt="" /> <span>'.$conf['title'].'</span>',
'accesskey="h" title="[H]"'
);
Remove <span>'.$conf['title'].'</span> from it.
Each update of Dokuwiki engine will overwrite this change. You'll need to repeat it manually after each update or copy paste doku template into a new one and update this new template manually.
Possible also to hide the title text with a proper CSS display: none setting. It can be put into the conf/userstyle.css file, so it wont be overwritten by updates. The text resides still in the page but becomes invisible. It may improve the search-engine hits also, maybe.
Possible CSS code:
div.headings h1 span { display: none !important; }
This is the good answer. It works for me.

How to change less parameters and compile css dynamically in the browser?

I am trying to implement a basic theme roller functionality using LESS CSS.
Suppose I have the following Less Code, which compiles to a .css file included in the page:
#main-background-color: #809BB8;
body
{
background-color: #main-background-color;
}
I would like to change the #main-background-color dynamically with javascript based on an user action (Color Picker) and compile the LESS code dynamically and refresh the styles of the page so that the user changes are reflected immediately in the browser.
Is this possible at all?
Please advise!
Thanks
you could try using less.js functions like:
less.refreshStyles()
or
less.modifyVars()
you can maybe read some more on this here: Dynamically changing less variables
Something along this lines with JavaScript and modifyVars might work:
var $picked-color = "#809BB8";
less.modifyVars({
'#main-background-color': $picked-color
});

Change the paginator links with the angular-ui bootstrap carousel?

I'm using angular-ui bootstrap carousel and would like to change the right and left navigation links with images. It seems that within the tpl they are hardcoded with ‹ and ›
Does anyone have any recommendations on changing these to images without changing the actual angular-ui bootstrap files? I want to keep this in a library and don't want to change it after each version release.
The only solution I had was a hack to make the control of these angle brackets super small in CSS so they couldn't be seen and placed the images.
.carousel-control {
font-size: 1px
}
.carousel-control.left, carousel-control.right {
background: url(/path/to/[image-here].png) no-repeat !important;
}
Is there a better solution?
The goal for the http://angular-ui.github.io/bootstrap/ project is to have customizable templates so if you don't like the default markup you can swap it for your own. If you want to change carousel's look and feel I would recommend overriding the default template (https://github.com/angular-ui/bootstrap/tree/master/template/carousel).
You can easily override individual templates without messing without touching project's deliverables as described here: https://stackoverflow.com/a/17677437/1418796

Sencha touch Theming a specific Container in scss

I wanted to know how to theme a specific Container and not every Container in the whole app.
#ext-element-18 x-scroll-container
if I wanted to change a background color of this would it be?
app.scss
#ext-element-18 x-scroll-container{
background-color: #000;
}
this is not working
It's bad pratice to base your CSS on auto-generated id's like ext-element-18. It can change anytime. So what I suggest is you use the cls config
Give a cls attribute to your contrainer :
cls:'my-css-class'
Then use this class in your CSS or SCSS file to customize the component.
If you ever need to reach children of your component you can now do something like
.my-css-class .x-scroll-container{
// custom style
}
This works too;
Ext.get(Ext.fly('ext-groepen_detail-1').query('.x-scroll-container')).elements[0].style.backgroundImage = 'url("http://somedomain/path/to/test logo 2.jpg")';