React CSS Style is getting overridden - html

I have a react application which uses 3rd party libraries to create components.
The problem I am facing is one library css is getting loaded from CDN and other through node_modules. The css coming from CDN is overriding the css from other libraries.
CSS from CDN is written as -
.solar-theme button {
// css properties
}
CSS from other library is as -
.some-button {
// css properties
}
And button component in this library uses solar-theme as classname.
How to isolate the CSS coming from CDN to a single react component so that it doesn't overrides the other library css?
I am new to UI/UX. Please help.

Since you can't edit the CSS files from the libraries, you should write a new stylesheet to override certain properties as you come across them.
You might also have to use important! to enforce your properties.
For example:
/* Your custom stylesheet */
.some-button {
background-color: red !important;
}
If this does not work (it probably won't), you need to be more specific with your declarations.
Generally, the more specific you can be, the higher the chance of your style getting applied (when there are conflicting stylesheets).
So you can upgrade the declaration above by doing something like this instead:
/* Your custom stylesheet */
footer .container .some-button {
background-color: red !important;
}
It's called specificity. You can read more about it here:
https://developer.mozilla.org/en-US/docs/Web/CSS/Specificity

Related

How can I override A-Frame CSS in an app built using create-react-app? [duplicate]

This question already has answers here:
How are the points in CSS specificity calculated
(7 answers)
Closed 12 months ago.
I'm building a mobile app with 2D & 3D elements.
2D elements use React, and I'm using create-react-app for the build/bundling etc.
3D elements use A-Frame.
For iOS, I need to obtain device orientation permissions, and I'm doing this using the standard A-Frame component: https://aframe.io/docs/1.3.0/components/device-orientation-permission-ui.html
However I want to change the appearance of the modal, by specifying my own CSS (as suggested on that page).
I have a problem that appears only in my production build.
I've written the CSS overrides that I want in my App.css. I build my production JS and CSS files.
They are included in index.html like this (inside the <head>)
<script defer="defer" src="/static/js/main.6b739253.js"></script>
<link href="/static/css/main.8198a130.css" rel="stylesheet">
However, on initialization, A-Frame adds its own CSS files to the end of the HTML header:
<style type="text/css" data-href="src/style/aframe.css">
...CSS here...
</style>
Because the A-Frame CSS appears at the end of the HTML header, it takes priority over my custom CSS, and I end up with the A-Frame styling for the modal, rather than my custom styling.
I've come up with a solution for this, but I think there's got to be a better one...
My solution: the following code at the top of my top-level React component, which explicitly removes the aframe.css styles from the HTML (I've also added the A-Frame styles that I don't want to override directly in my App.css, where I can have full control over what I do & don't include).
useEffect(() => {
var head = document.getElementsByTagName('HEAD')[0];
for (var ii = 0; ii < head.children.length; ii++) {
const child = head.children[ii];
if (child.attributes['data-href'] &&
child.attributes['data-href'].nodeValue === "src/style/aframe.css") {
head.removeChild(child);
}
}
}, [])
I'm looking for a better solution, where I don't have to duplicate large chunks of aframe.css in my own CSS file, and I can simply have the two CSS files loaded, but prioritized in a different order.
Ideally that solution would not require me to eject from create-react-app, which I have managed to avoid needing to do so far.
There is in fact a simple solution here.
A CSS specifier that specifies an element selector + a class selector is more specific than a specifier that specifies a class selector only.
https://www.w3schools.com/css/css_specificity.asp
So the following CSS...
button.a-dialog-allow-button {
background-color: red;
}
will be more specific (and hence take precedence over) the A-Frame defaults which look like this:
.a-dialog-allow-button {
background-color: #00ceff;
}
Similarly you can override .a-modal with div.a-modal, .a-dialog with div.a-dialog etc.
One thing to watch out for (this threw me when testing this)... Not all A-Frame modals use the a-modal and a-dialog classes.
There are various other classes, used for specific modals - e.g. a-enter-vr-modal and a-orientation-modal (used for portrait / landscape orientation, rather than for device orientation permisions).
So just if you see an A-Frame modal, and your changes don't seem to have worked, it may be because it is using a different set of modal classes from the ones you changed. Check the class names carefully!

_reboot.scss is overwriting my custom CSS

Hello for some reason my custom CSS is being overwritten, I have correctly placed my custom CSS below the CDN bootstrap reference but that does not seem to solve the issue. For example if I am trying to change the font color for a header with an h1 inside. When using classes or id's the font color will not change. Though if I target the header by writing whats below in my CSS file it does work
header h1 {
color: white;
}
I do have an some understanding about specificy but I would assume declaring it with a class or id should be specific enough and go over the _reboot.scss file but it does not seem to. I am using BootStrap 5.
In your example cdn or node_modules css always on top. After that put your custom css files.
Order of prioritization when using multiple contradictory css files

Angular: Override CSS of other component

I am fairly new to Angular and HTML.
I have two different components, let's say componentAand componentB, both with their repsective .html, .css and .ts files.
In componentA.css, I define some styles, e.g.:
.compA-style {
font-size: 20px;
}
Now in componentB.hmtl, I am using componentA's directive:
<compA></compA>
How can I now change the styles of componentA inside the css file of componentB, without changing the style inside componentA?
Note: I cannot change the style of componentA because I want to use the unmodifed style inside other components, I only want to change for the componentB.
Note: I already tried !important inside componentB.css, i.e. I tried this one:
.compA-style {
font-size: 30px !important;
}
And then in componentB.html:
<compA class=".compA-style"></compA>
But that didn't work.
Angular encapsulates CSS at component level.
This means that even if you have multiple CSS classes with the same name across multiple components, each of those components will use its own class, regardless of the DOM structure.
There are times when you might want to modify a child component styling, though.
You can do this in multiple ways. Let's assume compB contains compA.
::ng-deep
:host {
// ... Other styles
::ng-deep compA {
// ... Custom compA styles
}
}
Explanation: ::ng-deep selector provides cross-component visibility of CSS given its boundaries (wrapper selectors). Whatever you write within ::ng-deep compA will be shared with everything in compA.
WARNING: If you use ::ng-deep at base level in a component styling sheet (without a wrapper), the styles it contains will be spread both up and down across the application (NOT only within current component) and they load whenever the component loads. That is why it's usually wrapped into a :host selector.
Global style sheets
You can write custom styles in application base level styles.css file or create new css files to include at application load (outside Angular environment, for example with a <link> tag in index.html).
They are useful when you have a bunch of styles to overwrite that are the same across the application and don't want to mess with specific component stylesheets too much. Might not always be a good practice.
Add new component stylesheets in styleUrls array in the #Component decorator.
This might not necessarily apply to your case, but it's worth mentioning.
#Component({
selector: 'app-main',
templateUrl: './main.component.html',
styleUrls: ['./main.component.css', '../styles/background.css', '../styles/input.css', '../styles/container.css' /* ... other stylesheets here */]
})
This is a good approach that helps keeping common styles in a single place while not making them global. You can add whatever styles you need to the specific component and split them as needed.
How can I now change the styles of componentA inside the css file of componentB, without changing the style inside componentA?
There is only way to add styles without edit component-A directly.
on componentB.css
:host ::ng-deep compA-style {
font-size: 30px !important;
}
on componentA.html
<compA class="compA-style"></compA>
NOTE: This functionality is deprecated.
Checkout docs ng-deep.
https://angular.io/guide/component-styles#deprecated-deep--and-ng-deep

Can we edit bootstrap css style without download the packaging?

I used a lot of bootstrap template that I didn't download, when I open the 'inspect' to change the color etc it show a ..bootstrap.min.scss (something like that) link that I can't even open. Is it posibble to modified the template without having the css file in our computer?
you can always override the styles applied by a framework or external style sheet by creating rules that are more specific. Let's say the bootstrap code styles your links, you will have to create a more specific rule that overrules the previous in your own style sheet on your local machine.
Let's say bootstrap styles the a tag, you can give your body a class like:
<body id="cherry">
my link
</body>
in your css file:
#cherry a {
color: magenta;
}
For further reading I recommend: https://developer.mozilla.org/en-US/docs/Web/CSS/Specificity

Override CSS remove property

I'm using a lib and i want to remove a property on a class. What is proper way to do it ?
Example :
Lib.css
div {
width: 100%;
}
and custom.css
div {
width: none; //something like that
}
Every rule in CSS has a different default value. Many might have none or auto as default. Check MDN for Reference. Search for 'Initial value'
Example
https://developer.mozilla.org/en-US/docs/Web/CSS/width
Initial value: auto
Edit
You can also use the special value initial, if you don't need to support MSIE browsers.
I encourage you to read about CSS specificity here in the docs:
CSS Specificity: Mozilla Developers and check my answer down below.
There are several ways to overwrite CSS properties from external libraries.
Case 1: if you're using Bootstrap or Zurb Foundation via npm package,
you need to change a variable value that is responsible for given property and place it after importing all library files to ovewrite correctyly eg.
import 'files from library.sass';
// my settings
$default-width: 80%;
Case 2: if you're using CDN to deliver your library you can use a more specific CSS selector to overwrite given property eg:
to overwrite div selector
div {} ----> div.my-class {}
The second technique, but for sure not recommended is to use !important declaration. But remember, using !important declaration often causes many problems during the development process. It is always better to find a more specific selector than use !important.