styled components styled overriden by thrid party (antd) style - antd

I've got a simple styled-components that is being applied to an antd component:
import { Card } from 'antd';
export const UsageCard = styled(Card)`
box-shadow: 1px 1px;
padding: 2px;
`
This creates a div with a class attribute that looks like : "ant-card edit-style__UsageCard-jsklqS hBLsXc ant-card-bordered"
Where .hBLsXc is my styled-component. Unfortunately the padding which is 2px in my styled-componentn gets overriden by the ant-card (0px).
Any idea why this is happening? The styled-components is supposed to come first since it's implemented over the thrid-party component. Is this a problem with the forwarding of className from third-party component I've read on multiple occasion? In any case, I don't really gets how this is supposed to work.
Thanks for your help!

The className has to be put in the Card Component, otherwise this will not work. You should check with antd to see if they did so. It has to look something like this:
const Card = ({ className }) => (
<div className={className}>
...
</div>
)
Here is the documentation for it:
https://www.styled-components.com/docs/basics#styling-any-components
edit:
I checked with antd and it looks like you can pass the className to it. There is a section in https://github.com/ant-design/ant-design/blob/master/components/card/index.tsx:
const classString = classNames(prefixCls, className, {
[`${prefixCls}-loading`]: loading,
[`${prefixCls}-bordered`]: bordered,
[`${prefixCls}-hoverable`]: this.getCompatibleHoverable(),
[`${prefixCls}-wider-padding`]: this.state.widerPadding,
[`${prefixCls}-padding-transition`]: this.updateWiderPaddingCalled,
[`${prefixCls}-contain-grid`]: this.isContainGrid(),
[`${prefixCls}-contain-tabs`]: tabList && tabList.length,
[`${prefixCls}-type-${type}`]: !!type,
});
You can pass the className via props. So this should actually work, but the passed className goes first, so I guess the antd styles will always override the styled-components ones, if they are the same. Maybe a fork might help?

Related

Web components with vaadin and rollup with svelte: Primary button ignores theme attribute

Maybe someone tried this before and is able to give me a hint.
I have used normal svelte setup (mentioned in the main page) which scaffolds the app;
npx degit sveltejs/template my-svelte-project
I wanted to use vaadin web components in Svelte. I've installed it;
npm install #vaadin/vaadin
the code of main.ts:
<script lang="ts">
import '#vaadin/button/theme/material'
</script>
<main>
<vaadin-button theme="primary">Primary</vaadin-button>
<vaadin-button theme="secondary">Sec</vaadin-button>
</main>
<style>
main {
text-align: center;
padding: 1em;
max-width: 240px;
margin: 0 auto;
}
#media (min-width: 640px) {
main {
max-width: none;
}
}
</style>
And the thing is that it almost works :) The buttons are styled, I can click on them but... the theme is ignored;
The primary should have a background color like stated in docs;
https://vaadin.com/docs/latest/ds/components/button/#styles
any idea???
This is happening because of how Svelte sets data on custom elements. If a property exists on the element with the same name as the attribute you set, Svelte will set the property instead of the attribute. Otherwise, it will fall back to the attribute. So, the following...
<vaadin-button theme="primary">Primary</vaadin-button>
...gets compiled to something like:
button.theme = "primary";
Normally this works great, especially when setting array and object properties. However, the vaadin-button styles expect the theme attribute to be set, not the property. Because Svelte sets the property instead, the styles don't apply.
:host([theme~="primary"]) {
background-color: var(--_lumo-button-primary-background-color, var(--lumo-primary-color));
color: var(--_lumo-button-primary-color, var(--lumo-primary-contrast-color));
font-weight: 600;
min-width: calc(var(--lumo-button-size) * 2.5);
}
I would argue that this is a Vaadin bug - if you expose an attribute and a property for the same data, it shouldn't matter which one the consumer sets. Setting the property should have the same effect as setting the attribute. A quick way to fix this would be for vaadin-button to reflect the theme property, so that setting theme also sets the attribute. Here's how to do that in Lit.
However, that change requires the component library authors to implement it. As a consumer of the library, you can also work around this in Svelte by using an action to force Svelte to set the attribute instead.
<script>
import "#vaadin/button";
function setAttributes(node, attributes) {
for (const [attr, value] of Object.entries(attributes))
node.setAttribute(attr, value);
}
</script>
<main>
<vaadin-button use:setAttributes={{ theme: "primary" }}>Primary</vaadin-button>
<vaadin-button>Normal</vaadin-button>
</main>
I wrote an article about this behavior and other workarounds at CSS-Tricks, if you want a more in-depth explanation.
You seem to be importing the Material theme version of the Button component. The "primary" theme variant is only available if you use the default Lumo theme. To import that, use import '#vaadin/button';
For the Material theme, you can use the "outlined" and "contained" theme variants instead: https://cdn.vaadin.com/vaadin-material-styles/1.3.2/demo/buttons.html

How to print a Component in Vaadin?

I have been struggling for sometime now, trying to find ways to print out/generate document using vaadin.
i have tried using the below code but this prints all the components. I wanted to print only a particular form or layout.
UI.getCurrent().getElement().executeJs("print();")
Can some one guide me?
You'll need some CSS (similar to the approach mentioned here) that will hide everything when printing is invoked, except for the Layout or Component that needs to be printed.
For example, assuming you have the following two DIVs in your view:
Div printable = new Div(new Span("printable"));
Div nonPrintable = new Div(new Span("nonPrintable"));
You can give one of those a classname:
printable.addClassName("printable");
Then, you would add the following CSS to the global scope:
#media print {
body, body * {
visibility: hidden;
}
.printable, .printable * {
visibility: visible;
}
.printable {
position: absolute;
left: 0;
top: 0;
}
}
Note, in a Vaadin 14 project, the previous CSS is most easily incorporated using the #CssImport annotation. For example, the following annotations can be added to one of your Java classes:
#CssImport("./shared-styles.css")
Then under the directory {projecr-root-directory}/frontend, you'd need to create shared-styles.css and place the aforementioned styling there.

Angular: Mat-card keyboard navigation

I am trying to make a mat-card navigable from the keyboard. Right now, when pressing tab the element is focused however the redirect event (should be the same as the click event) isn't triggered when pressing enter.
I've tried keydown.enter and onKeyDown (from a11y package) but no success so far.
HTML
<mat-card role="group" (click)="addQueryParam(group.name)" (keydown.enter)="addQueryParam(group.name)" class="mat-elevation-z0"
[ngClass]="'background-'+index" (mouseout)="mouseOver=false"
(mouseover)="mouseOver=true" style="padding: none; margin: 5px">
Typescript
addQueryParam(groupName) {
this.router.navigate(['/data'], { queryParams: { ['groups.title']: groupName }, queryParamsHandling: 'merge' });
}
Any idea how to solve this issue?
TIA,
Isabela
I suggest you two things:
try using (keyup.enter)=.... I used it a couple of times and it worked well
If that doesn't work try using (keyup) or (keydown) and in your function check if the key code is 13 (enter key code), something like this:
HTML
<mat-card role="group" (click)="addQueryParam(group.name)" (keydown)="addQueryParam($event, group.name)" class="mat-elevation-z0"
[ngClass]="'background-'+index" (mouseout)="mouseOver=false"
(mouseover)="mouseOver=true" style="padding: none; margin: 5px">
Typescript:
addQueryParam($event, groupName) {
if($event.keyCode === 13){
this.router.navigate(['/data'], { queryParams: ...);
}
}
If i remember correctly you can check the type of the event in a field like event.type, or something like that.
Additionally check this discussion out, because theese functions are not well documented, and here you can find som infos :
What are the options for (keyup) in Angular2?
EDIT
I also found this very useful article: https://medium.com/claritydesignsystem/angular-pseudo-events-d4e7f89247ee

Reveal.js: Add fragments inside code

I've got a presentation running with reveal.js and everything is working. I am writing some sample code and highlight.js is working well within my presentation. But, I want to incrementally display code. E.g., imagine that I'm explaining a function to you, and I show you the first step, and then want to show the subsequent steps. Normally, I would use fragments to incrementally display items, but it's not working in a code block.
So I have something like this:
<pre><code>
def python_function()
<span class="fragment">display this first</span>
<span class="fragment">now display this</span>
</code></pre>
But the <span> elements are getting syntax-highlighted instead of read as HTML fragments. It looks something like this: http://imgur.com/nK3yNIS
FYI without the <span> elements highlight.js reads this correctly as python, but with the <span>, the language it detects is coffeescript.
Any ideas on how to have fragments inside a code block (or another way to simulate this) would be greatly appreciated.
To make fragments work in code snippets, you can now use the attribute data-noescape with the <code> tag
Source: Reveal.js docs
I got this to work. I had to change the init for the highlight.js dependency:
{ src: 'plugin/highlight/highlight.js', async: true, callback: function() {
[].forEach.call( document.querySelectorAll( '.highlight' ), function( v, i) {
hljs.highlightBlock(v);
});
} },
Then I authored the section this way:
<section>
<h2>Demo</h2>
<pre class="stretch highlight cpp">
#pragma once
void step_one_setup(ofApp* app)
{
auto orbit_points = app-><span class="fragment zoom-in highlight-current-green">orbitPointsFromTimeInPeriod</span>(
app-><span class="fragment zoom-in highlight-current-green">timeInPeriodFromMilliseconds</span>(
app->updates.
<span class="fragment zoom-in highlight-current-green" data->milliseconds</span>()));
}
</pre>
</section>
Results:
I would try to use multiple <pre class="fragment">and change manually .reveal pre to margin: 0 auto; and box-shadow: none; so they will look like one block of code.
OR
Have you tried <code class="fragment">? If you use negative vertical margin to remove space between individual fragments and add the same background to <pre> as <code> has then you get what you want.
Result:

Is there a template creation Event in Darts Web_ui?

Is there anything like a notification mechanism for the instantiation of a template?
Assume the following simple template:
<template iterate="name in names">
<div>{{name}}</div>
</template>
When a name is very long, it might be possible that the container of the name div is overflown. So what I would like to do is to get an event when the name div is added to the DOM so that I can take a look at the resulting width. I would then shorten the name until it fits nicely.
Note: I assume you can't achieve what you want with CSS. So here's a code solution.
I am not aware of any event or a way to hook into the creation process.
However, I have done something like this with success:
import 'dart:async';
inserted() {
Timer.run(() {
// Do your calculations here...
});
}
If you set your name variable later, then you could alternatively make it observable and set the timer after the value changes:
observe(() => name), (_) {
Timer.run(() {
// Recalculate...
});
});
And remember to mark it #observable and set the listener in created().
You should really handle something like this in CSS:
.name {
width: 50px;
overflow: hidden;
white-space: nowrap;
text-overflow: ellipsis;
}
And give your div a class of name.
This will automatically shrink the text down to the container width and add an ellipsis to indicate that the text has been truncated.

Resources