CSS values using HTML5 data attribute [duplicate] - css

This question already has answers here:
CSS3's attr() doesn't work in major browsers
(5 answers)
Closed 5 years ago.
width: attr(data-width);
I want to know if there's any way it's possible to set a css value using HTML5's data- attribute the same way that you can set css content. Currently it doesn't work.
HTML
<div data-width="600px"></div>
CSS
div { width: attr(data-width) }

There is, indeed, prevision for such feature, look http://www.w3.org/TR/css3-values/#attr-notation
This fiddle should work like what you need, but will not for now.
Unfortunately, it's still a draft, and isn't fully implemented on major browsers.
It does work for content on pseudo-elements, though.

You can create with javascript some css-rules, which you can later use in your styles: http://jsfiddle.net/ARTsinn/vKbda/
var addRule = (function (sheet) {
if(!sheet) return;
return function (selector, styles) {
if (sheet.insertRule) return sheet.insertRule(selector + " {" + styles + "}", sheet.cssRules.length);
if (sheet.addRule) return sheet.addRule(selector, styles);
}
}(document.styleSheets[document.styleSheets.length - 1]));
var i = 101;
while (i--) {
addRule("[data-width='" + i + "%']", "width:" + i + "%");
}
This creates 100 pseudo-selectors like this:
[data-width='1%'] { width: 1%; }
[data-width='2%'] { width: 2%; }
[data-width='3%'] { width: 3%; }
...
[data-width='100%'] { width: 100%; }
Note: This is a bit offtopic, and not really what you (or someone) wants, but maybe helpful.

As of today, you can read some values from HTML5 data attributes in CSS3 declarations. In CaioToOn's fiddle the CSS code can use the data properties for setting the content.
Unfortunately it is not working for the width and height (tested in Google Chrome 35, Mozilla Firefox 30 & Internet Explorer 11).
But there is a CSS3 attr() Polyfill from Fabrice Weinberg which provides support for data-width and data-height. You can find the GitHub repo to it here: cssattr.js.

Related

How to declare SCSS <length> type attribute selector by REACT property

Basically I want to create a reusable component which can be slightly modified from the outside in react:
SomewhereElse.tsx
...
<FooComponent width={200}>
...
FooComponent.tsx
interface IFooProps {
//default width of 150px
width?: 150;
//default margin of 5px
margin?: 5;
}
interface IFooState{
checked: boolean;
}
class FooComponent extends Component<IFooProps, IFooState> {
constructor(props: IFooProps) {
super(props);
...
}
...
render(): ReactElement {
return (
<div className="foo-component"
data-width={this.props.width + 'px'}
>
...
FooComponent.scss
.foo-component {
...
width: attr(data-width length);
...
But it always gives me the following error when running the application (chrome):
... Please consider that I need a "number" as property because I am doing some calculations based on that number for some of the inner components so everything fits together.
EDIT:
Using "style" is not working for me because I have some ::before ::after features in my scss which are broken when using style because they occasionally modify "right:" based on the width.
For better understanding, this is my base:
https://www.sitepoint.com/react-toggle-switch-reusable-component/
To answer your question
Please find a solution with attribute selector or tell me that it is not possible because of X reasons (link to docs in best-case).
No, although it would be super useful, according to my research it's currently not possible:
MDN about CSS attr():
Note: The attr() function can be used with any CSS property, but support for properties other than content is experimental, and support for the type-or-unit parameter is sparse.
According to caniuse.com about css3-attr, the ability to use attr() on any CSS property (besides content, and to use it for non-string values (e.g. numbers, colors) via <type_or_unit> as defined per "CSS Values and Units Level 3" is currently unsupported by all browsers.
See also the statement on the current draft for "CSS Values and Units Module Level 4":
The following features are at-risk, and may be dropped during the CR period: toggle(), attr() [...]
(Source: https://drafts.csswg.org/css-values/#status)
In the Chromium issue, I found a link to an interesting resource I wasn't aware of: web-platform-tests dashboard for css-values. Take a look at the (failing) tests prefixed with attr-, especially attr-length-valid.html and attr-px-valid.html.
But there is hope: the Chromium team recently (05/15/2020) posted an Intent to Implement and Ship: CSS advanced attr() function
Implement the augmentation to attr() specified in CSS Level 4, namely, allowing various types (besides ) and usage in all CSS properties (besides pseudo-element 'content').
Note: CSS Level 4 has made substantial revisions to attr() compared to Level 3 to ease the implementation. We'll follow CSS4. [...]
Motivation: This is a highly requested feature, with 77 stars at crbug.com/246571. [...]
Chromium tracking Issue 246571: Implement CSS3 attribute / attr references
)
Firefox also show recent activity, see Firefox tracking Bug 435426 [meta] Implement CSS Values 3 extensions to attr(), there they at least are referring to Chromiums current efforts.
(WebKit Bug 26609 - Support CSS3 attr() function shows no activity, which could be a deal-breaker)
As suggested from G-Cyrillus I have found a possible solution using CSS custom properties. Unfortunetly I did not find a solution using attribute selector so I could stick to one solution type.
Add your custom properties in the scss file "parent" class like:
.foo-component {
--customwidth: 150px;
--custommargin: 5px;
width: var(--customwidth, 150px);
...
&-inner {
margin-left: var(--custommargin, 5px);
}
...
}
After you declared the customproperty it's possible to use it with var(<propertyname>, <initialvalue>).
In React you slightly can modify the render() like:
render(): ReactElement {
//set the custom properties for width, margin and slider position
let cssProperties = {};
cssProperties['--customwidth'] = this.props.width == null ? '150px' : this.props.width + 'px';
cssProperties['--custommargin'] = this.props.margin == null ? '150px' : this.props.margin + 'px';
cssProperties['--switchposition'] = (this.props.width == null ? 115 : this.props.width - 35) + 'px';
return (
<div className="foo-component" style={cssProperties}>
...
}
Which will work for every component seperatly.
An easier way would be using inline style:
return (
<div className="foo-component"
style=`width:${this.props.width};`
>
With attr you need to specify the attribute by providing the selector in your scss styles
.foo-component[data-width] {
...
width: attr(data-width length);
...
If you have multiple such attribute you can write them like
.foo-component[data-width][data-margin] {
...
width: attr(data-width length);
margin: attr(data-margin number);
...
Please check the MDN docs for more details

Set CKEditor height in Vue.js [duplicate]

This question already has answers here:
How to set the height of CKEditor 5 (Classic Editor)
(28 answers)
Closed 4 years ago.
I was trying out ckeditor5 in Vue.js, and I came across a problem of not being able to set it's height manually, below is my code please let me know if I am doing anything wrong.
<ckeditor :editor="editor" v-model="editorData" :config="editorConfig"></ckeditor>
data() {
return {
editor: Editor,
editorData: '',
editorConfig: {
height: '500px'
}
}
Classic editor (CKEditor 5) no longer encapsulates the editing area in an , which means that the height (and similar options) of the editing area can be easily controlled with CSS. For example the height setting can be achieved with :
<style>
.ck-editor__editable {
min-height: 500px;
}
</style>
or
.ck-content { height:500px; }.
2020 Note: when working with single page Vue components, do not scope the CSS you want to add to ckeditor, as it's elements are rendered separately from Vue and no data attributes are added to them. In other words, don't do this, as it will not work:
<style scoped> /* don't add "scoped"; note that this will also globalize the CSS for all editors in your project */
.ck-editor__editable {
min-height: 5000px;
}
</style>

What's the bs-css child selector equivalent of sass child selector?

I currently have some SASS I'm trying to convert to use bs-css (7.3).
The sass looks like
.checkbox {
svg {
height: 28px;
width: 28px;
}
}
I've tried using
open Css;
let checkbox =
style([
backgroundColor(Basics.Colors.white),
border(`px(1), `solid, Basics.Colors.gray850),
selector(
"svg",
[height(Basics.Icon.epsilon), width(Basics.Icon.epsilon)],
),
]);
But I get back the css property svg set to [Object Object]
bs-css is basically bindings to glamor, so you can use any selector described in its docs.
For child selectors it recommends using "& svg", and although the & can be omitted, I'd really recommend including it for readability. Whitespace tends to be easy to miss.

Creating CSS Rules Using Class Prefixes [duplicate]

This question already has answers here:
Is there a CSS selector by class prefix?
(4 answers)
Closed 8 years ago.
Twitter Bootstrap's different column selectors have different CSS properties. Col-md-1 has a smaller width than col-md-2. However, they all have some properties in common.
How can one rule be created that applies to multiple classes who all share the same prefix?
I imagine something like this:
.col*{
margin:0,2%;
}
.col-md-1{
width:4.3333333333%;
}
.col-md-2{
width:6.33333333%;
}
In the example above, both of .col-md-1 and .col-md-2 would have a margin of 0,2%. What is the correct way (if any) of doing this?
You can use :
[class^=col] {margin:0.2%;}
div {
height: 50px;
margin: 10px;
}
[class^=col] {
background: red;
}
<div class="col-md-1"></div>
<div></div>
<div class="col-md-2"></div>
This ^= means "begins with". You could also use the [class*=col] or [class*=md] for more info, see the specs on substring matching attribute selectors.
(Note that you should be using a dot instead of a comma or a white space in the margin value declaration)
You can either use a ^= operator (starts with), or a |= operator (is on a dash-separated list):
[class^=col] {
/* this will work just for prefixes */
}
[class|=col] {
/* this will work for any dash-separated segment... */
}
[class|=md] {
/* ...such as "md" in your case */
}
A word of warning, though - these aren't the best selectors in terms of performance. Try not to use them extensively.

CSS first-letter Selector in a link

I'm currently getting headaches from this darn pseudo-element called :first-letter. It seems to be so helpful, but ultimately does not work the way I expected.
Here's an example on jsfiddle, how I tried and how it should look like:
FIDDLE is here
As you can see, :first-letter does nothing. I expected it to overwrite the normal link settings and also the :hover selector.
What could've possibly gone wrong? Any other idea how to achieve this only with CSS?
Instead of putting your "»" in the HTML you could put it in the CSS
http://jsfiddle.net/4DnKu/4/
a.one:before {
content: "»";
color:#0F0;
padding:0 5px 0 0;
}
IMHO it shouldn't be in the HTML either way, as it actually is only decoration.
Pseudo elements are supported by all major browsers, only one you'll have problems with is IE<8. There you could use CSS expressions as a workaround (handle with care!):
a.one {
*zoom: expression( (new Function('elem', '\
if(elem.before)\
return;\
elem.innerHTML = "<span class=ie7-before>»</span>" + elem.innerHTML;\
elem.before = true;\
elem.style.zoom = "1";\
'))(this) );
}
a.one > .ie7-before,
a.one:before {
content: "»";
color:#0F0;
padding:0 5px 0 0;
}
This uses quite a few hacks, so I would not recommend using it unless you understand what is going on there.

Resources