How to reference the element id in VUE :class - css

I have several divs, which I'm not going to put in v-for, but still need to unique reference them. For #click id attribute works well.
<div v-bind:class="setAreaStyle('CAR')" #click="setFocus($event)" id="CAR">
But is there a way I can use element id, without click event, as reference in called function, so setAreaStyle would received 'CAR' as argument?
<div v-bind:class="setAreaStyle(id)" id="CAR">

Use $event.target.id
<div :class="setAreaStyle($event.target.id)"
#click="setFocus($event)"
id="CAR"
>

I guess the id you'll use will come from the v-for item, no ? You can then use it in both places:
<div
v-for="item in items"
:key="item.id"
:class="setAreaStyle(item.id)"
:id="item.id"
#click="setFocus($event)"
>
Side note: the name setAreaStyle is strange (seems it will do some side effects), you should only get something here, and it is the class name => getClass would make more sense.
Or :style="getStyle(item.id)" if you want to add inline CSS

Related

Hide all elements with duplicate class names besides the first with CSS

I have a loop displaying some markup that has dynamic class names. Is it possible to hide all elements with duplicate class name besides the first instance? For example below I would only want the first .SomethingDynamic1 and the first .SomethingDynamic2 to be visible.
I think I might be able to use the div[class^="group"] "starts with" attribute selector to achieve this but am I able to match dynamic text after that and filter out the duplicates? I would prefer a CSS only solution if possible.
<div class="group-SomethingDynamic1">
<div class="group-SomethingDynamic1">
<div class="group-SomethingDynamic1">
<div class="group-SomethingDynamic1">
<div class="group-SomethingDynamic2">
<div class="group-SomethingDynamic2">
<div class="group-SomethingDynamic2">
<div class="group-SomethingDynamic2">
Update (credit #Temani Afif)
If you want a CSS only solution, you will need to know the classes to filter beforehand.
Given that, you can simply use a siblings selector like the following:
.group-SomethingDynamic1 ~ .group-SomethingDynamic1 {
display: none;
}
Here is a stackblitz example

How to apply conditional css?

I have a component item that represents a card with the data about the item. Since all the cards have the same structure (price/color/size/photo categories are shown on each card, nothing more and nothing less), I would like to apply a conditional CSS, but I don't know how, since the cards' style differ (slightly) based on:
price (for example, the card is bigger if the price is lower)
if the user has marked it as favorite
whether they are a part of this or that component (the URL can be the same). For example, in a single view there is the first component with a X card's style and the second component with a Y card's style - but the cards have the same data.
I'd really appriciate any suggestion!
<div [className]="'example-class'"></div>
This allows us to add classes based on a condition:
<div [className]="condition ? 'example-class' : 'other-class'"></div>
Or we could build the class name at runtime:
<div [className]="'class' + someValue"></div>
we can easily toggle CSS classes like so:
<div [class.example-class]="condition"></div>
we can assign a variable class name :
<div [ngClass]="seleted-class"></div>
NgClass can also assign multiple static class names all at once:
We can also use ngClass to assign multiple CSS classes based on multiple conditions.
<div
[ngClass]="{
'example-class': condition,
'other-class': !condition
}"
></div>
<div [ngClass]="['example-class', 'other-class']"></div>
source : https://malcoded.com/posts/angular-ngclass/
You can use NgClass to add conditional classes. For more info, refer the documentation - https://angular.io/api/common/NgClass

How can I select an element by an attribute set on its parent using CSS 2.0 selectors?

I have a HTML like this in my QWebView
<div class='a' id='root'>
<div id='x'>...</div>
<p> ...
<p>
...
<div id='x2'>...</div>
<div>
<a href='go/xxxx'>go</a>
</div>
</div>
How do I select the a? I tried this selectores:
div[id='root'].a
div[id='root'] + a
but it didn't worked. Code:
QWebFrame* frame = webView->page()->mainFrame();
QWebElement button = frame->documentElement().findFirst("div[id='root'].a");
assert(!button.isNull()); // gets executed
Your selector is selecting the div with id='root' and class='a'. If you want to select the a tag inside of that div, you need to make your selector:
div[id='root'].a a
The additional 'a' at the end of the selector tells jquery to select the a inside of the div.
You can switch to using XPath 2.0 in Qt to have more expressive freedom, but then you need to process your HTML as XML.
To resolve, add a descendant selector1 for a. I.e., change this div[id='root'].a into this:
div[id=root].a a
As an alternative, if there's a bug in Qt, try:
div[id=root][class=a] a
Or (which is potentially a bit wider):
div[id~=root][class~=a] a
These last two are just alternatives in case for some reason the original fix to your code (adding the a descendant selector) didn't work.
The code snippets above doesn't use quoted strings, this is optional.
1 adding a was seen in stevenc4's answer), after my original (wrong) solution. Kudos to him :)

Get rid of unneeded DIVs in my if binding knockout

I have an observable array with the following structure (where type can be only text or img):
ko.observableArray([{
type: 'text',
info: 'Hello'
},{
type: 'img',
info: 'http://cdn.zendesk.com/images/documentation/apps/logo-small.png'
}]);
Depending on the type I want to output either image or a bunch of text. So I am using the if binding. The result looks the way I expected, but the problem is in the underlying html:
<div data-bind="foreach: elements">
<div data-bind="if: type == 'text'"><div data-bind="text: info">Hello</div> </div>
<div data-bind="if: type == 'img'"></div> // Do not want it to be here
<div data-bind="if: type == 'text'"></div> // Do not want it to be here
<div data-bind="if: type == 'img'"><img data-bind="attr: { 'src': info}" src="http://cdn.zendesk.com/images/documentation/apps/logo-small.png">
</div>
</div>
It keeps inserting empty <divs> if the if statement returns false.
When I tried to achieve what I wanted with putting if and text binding in the same element I got the following error:
Multiple bindings (if and text) are trying to control descendant
bindings of the same
How can I get rid of unneeded DIVs in my output html with the if binding?
If this is impossible to achieve with if-binding, is there a way to do this somehow else? Because if I will have not only type = 'text' or 'img' but also 'video' and a dozen of other things I will have all them empty sitting there just as an artifact.
If you don't need the extra divs you can use the containerless control flow syntax of the if binding, which is based on comment tags:
<div data-bind="foreach: elements">
<!-- ko if: type == 'text' -->
<div data-bind="text: info"></div>
<!-- /ko -->
<!-- ko if: type == 'img' -->
<img data-bind="attr: { 'src': info}" />
<!-- /ko -->
</div>
Demo JSFiddle.
And the generated DOM will look like:
no extra divs only a few extra comments.
To get rid of these comments you can use templates.
You cannot get rid of the extra divs. I use the if binding do what you're doing on a regular basis.
The error you're getting simply indicates that you have competing bindings, which is expected with if and visible bindings. Your if and visible bindings should always be one div higher, so to speak.
Below is a screenshot of my DOM using Google's dev tools. The web application is actually running, and I use the if binding to reveal the view the user has chosen.
The extra divs are simply an artifact of the if binding.
If you think about it, if the if binding were to disappear altogether, what would be left in the DOM to reconstitute it when the condition is satisfied and that portion of the view should be shown?
UPDATE
Upon reconsidering the template approach, you could push the logic into the viewmodel (vm), bind the name of the template to an observable on the vm, and then dynamically set the template based on that logic. But, the templates themselves are going to hang around in the DOM. So I don't think there's a net gain here.

CSS div style - should I use class or id?

I have a repeater of div's that look a little bit like this:
<div class="header_div">
<!-- Content -->
</div>
I want to have the background color of the divs change based on a dynamic property of the content of the div (lets call it the category), but I still want the "header_div" style to be assgined in cases where I dont have a css class for that category. Whats the best way of doing this?
The best way I can think of is to render the category as the "id" of the div and apply styles based on the id, but that strikes me as really messy - standards dictate that the id should uniquenly identify the element on the page and there will definitely be repeats of each category.
The simple answer would be to use multiple classes for the <div> so that
<div class="header_div header_red">
<!-- Content -->
</div>
<div class="header_div header_green">
<!-- Content -->
</div>
You're correct about the need for IDs to be unique.
There's nothing stopping you from specifying more than one value per class attribute - just separate them with a space.
<div class="header_div category">
<!-- Content -->
</div>
Just be careful to check what happens when both classes specify different values for the same style - I can't say whether the first or the second would take precedence.
You could supply multiple styles for the div class:
<div class="header_div mystyle">
<!-- Content -->
</div>
I believe styles declared later in the declaration override earlier ones. As long as you ensure your custom styles "shadow" those of the header-div, you can always include the header-div element, and it will only have an effect when any secondary style is absent (or empty).
If it's going to be used repeatedly on the page, it should be a class.
If it's unique on the page, use an id.
Without knowing more about your content, can you not use one of the header tags (<h1> etc)?
You are correct, IDs should be unique and if you want to use the same style more than once then use a class.
You can't have duplicate IDs so if you had multiple divs of the same category you would have an issue. Classes should be used when the style needs to be applied for 1 or more items on a single page.
Why not assign the class on databinding of the div based on the category? As your repeater is getting bound, find your div for the item you are binding and assign it.
You could also substitute the div for an asp:Panel and use it's onDataBinding method. It should look exactly like your div.

Resources