Rendering Chart JS via a Slot in Lightning Web Components - salesforce

I am trying to render a Chart JS canvas via a slot;
chartWrapper.html
<template>
<div class="chart-wrapper">
<slot name="chart"></slot>
</div>
</template>
chartWrapperContainer.html
<c-chart-wrapper>
<canvas slot="chart" class="donut" lwc:dom="manual"></canvas>
</c-chart-wrapper>
The chart does not render and the canvas in the rendered Markup shows 0 width and height. Rendering without the slot works well; I need to wrap it into a slot for structural reasons.
What could be wrong with this?

This was sorted out by wrapping the canvas in a div; made some logical sense to me not to push a plain 'photo' into a slot whose internals it's unaware of.
<!-- chartWrapper.html -->
<template>
<div class="chart-wrapper">
<slot name="chart"></slot>
</div>
</template>
<!-- chartWrapperContainer.html -->
<c-chart-wrapper>
<div slot="chart">
<canvas class="donut" lwc:dom="manual"></canvas>
</div>
</c-chart-wrapper>

Alternately, you could set a CSS property that defines the Custom Element as a block, or inline-block through the :host pseudo-class. (By default a custom element has its display value set to inline.)
Then you can set its height and width or let the default ones:
<!-- chartWrapper.html -->
<template>
<style>
:host {
display: inline-block ;
width: 50% ;
height: 200px ;
}
</style>
<slot></slot>
</template>

Related

ng-class content changes but it doesn't apply css changes

I have a page with two tabs and in one of them I have a clickable component that is supposed to change a scope attribute that represents a class. The class content changes is working fine but it is not applying the effect of the class, just when I switch from this tab to another one and come back. Then, when I switch back it applies the CSS class changes.
<!-- Element 1 -->
<div ng-class="{ '{{scopeAttibute}}': true }">
content
</div>
<!-- Element 2 -->
<div ng-click="scopeAttibute=localAttrubute">
content
</div>
I solved it replacing the ng-class for id and the classes for IDs in my CSS style. Like this:
<div id="{{scopeAttibute}}">
content
</div>
<!-- Element 2 -->
<div ng-click="scopeAttibute=localAttrubute">
content
</div>
First you have to set scopeAttribute = true
<!-- Element 1 -->
<div ng-class="{'scopeAttibute': scopeAttibute == true}">
content
</div>

How to define composable components in AngularJS

In AngularJS (1.x), how can we create a reusable widget (component) that has insertion points (slots) for other widgets (components)?
Imagine we have a component/directive called "verticalsplitter". It's purpose is to divide the screen area into a "top" and "bottom" area (perhaps allowing user resizing, collapsing, etc).
Now imagine we have a bunch of other rich components e.g. a richtextview, a treeview, a videoplayer and a gridview.
One page/view 1 I want a verticalsplitter with a richtextview on top and treeview on bottom. On page/view 2 I want a verticalsplitter with a videoplayer on top and a gridview on bottom.
Page 1
<html>
<body>
<verticalsplitter>
<top ng-initialSize="30%">
<richtextview />
</top>
<bottom ng-initialSize="70%">
<treeview />
</bottom>
</verticalsplitter>
</body>
</html>
Page 2
<html>
<body>
<verticalsplitter ng-locked="true">
<top>
<videoplayer />
</top>
<bottom>
<gridview />
</bottom>
</verticalsplitter>
</body>
</html>
How can I achieve this? If it's not possible with components (and I need to use directives for transclude) then that's OK.
Components can transclude. It is clearly stated so in the AngularJS Developers Guide for Components:
app.component("verticlesplitter", {
transclude: {
'topPart': 'top',
'bottomPart': 'bottom'
},
template: `
<div style="border: 1px solid black;">
<div class="top" ng-transclude="topPart"></div>
<div>Something in the middle</div>
<div class="bottom" ng-transclude="bottomPart"></div>
</div>
`
});
For more information, see
AngularJS Developers Guide for Components
AngularJS ng-transclude Directive API Reference (Multi-slot Transclusion)

Angular - Bootstrap

I have a page designed in angular bootstrap. I am trying to use a popover as follws ..
<div class="col-md-4">
<div class="row">
<ul>
AM TEST AM
</ul>
</div>
</div>
The template I am using pops over fine, but I could not increase the size of the popover whatsoever.
How can I increase the size of the popover?
You can simply do this using CSS
<style>
.popover{ /* Will change ALL popovers. Add element id to target specific popver */
max-width: 100%
}
</style>

Can't change drawerWidth on paper-drawer-panel Polymer 1.0

It's pretty basic but i don't know if it's a bug or i'm wrong with something.
I cant change the width of the drawer in the paper-drawer-panel. In the documentation page specify to add the property drawerWith.
Here is some code:
<dom-module id="my-app">
<template>
<style>
:host {
display: block;
}
</style>
<paper-drawer-panel drawerWidth="300px">
<!-- Nav Bar -->
<section drawer>
<!-- Logo -->
<div id="logoContainer">
<img id="logo" src="../img/logo.png">
</div>
</section>
<!-- Content -->
<paper-header-panel main>
<paper-toolbar>
<paper-icon-button icon="menu" paper-drawer-toggle></paper-icon-button>
<div class="flex">My App</div>
</paper-toolbar>
</paper-header-panel>
</paper-drawer-panel>
</template>
<script>
// element registration
Polymer({
is: "my-app",
});
</script>
</dom-module>
This should work:
<paper-drawer-panel drawer-width="300px">
Here you can find the documentation that talks about it.
Attribute names with dashes are converted to camelCase property names by capitalizing the character following each dash, then removing the dashes. For example, the attribute first-name maps to firstName.
So, in documentation says drawerWidth when you use it in your elements must be: drawer-width

How to override Foundation's display:inherit property for visibility classes?

I'm using Foundation in a mobile first project where many elements are hidden based on the browser size, and I'm running into some trouble using Foundation's visibility classes like .show-for-small-only as Foundation applies
display: inherit !important;
to any element which uses these visibility classes. (For example, see line 5808)...
.show-for-small-only {
display:inherit !important;
}
This is causing me issues. Say have an element that I want to .show-for-small-only:
<div class="someElem show-for-small-only">
<!-- Content -->
</div>
Yet I want this element, when shown, to be formatted as a display:inline-block element. Due to Foundation's use of !important, the div is forced to assume it's default display state of block.
Is there any workaround to this, short of declaring my styling as !important too? (I don't want to have to do that though)...
I agree, using !important always feels gross.
Precedence in CSS is given to the element furthest down the tree so to override the Foundation !important property, just target an element further down the tree, like so:
<div class="show-for-small-only">
<div class="someElm">
<!-- your content here -->
</div>
</div>
With the following CSS
.someElm {
display: inline-block;
}
Here's a Plunker for kicks (just remember the items wont show up unless the screen is small).
I hope this helps.
To overwrite inportant just declare it again after the first declaration
.show-for-small-only {
display:inherit !important;
}
.show-for-small-only {
display: inline-block!important;
}
<div class="someElem show-for-small-only">
Content
</div>

Resources