Styles in react-pdf showing abnormal behaviour - css

I'm trying to use italic styling in react-pdf.
Everything works well until I use font-style: italic;.
Is there another way style text as Italic in react-pdf ?
const Italic = styled.Text`
font-size: 12px;
lineheight: 20px;
text-align: left;
font-family: "Roboto Condensed";
letter-spacing: 0.5px;
font-style: italic;//problem is with this line
font-weight:400;
`;
It is giving me the error:
Uncaught (in promise) Error: Could not resolve font for undefined, fontWeight 400

When you register your fonts, you need to make sure to include a variant for each fontStyle you wish to use. For example:
Font.register({
family: 'Roboto',
fonts: [
{ src: '<path-to-normal-font-variant>' },
{ src: '<path-to-italic-font-variant>', fontStyle: 'italic' },
...
]
});

const Italic = styled.Text`
font-size: "12px";
lineheight: "20px";
text-align: left;
font-family: "Roboto Condensed";
letter-spacing: "0.5px";
font-style: "italic";//problem is with this line
font-weight:400;
`;
where ever you are suffixing px needs to be in either single or double quotes and font-style: value(italic) need to be in double quotes as well.

Related

Inlining fonts and images inside CSS files with Webpack5?

I need to import into my project some CSS files with Webpack 5 and I need to inline all these resources (it's a requirement sadly). Inside the CSS there are some fonts and images with relative URI, like this:
#font-face { font-family: "MyFont"; src: url(./fonts/Roboto-Regular.ttf) format("truetype"); font-weight: normal;}
#font-face { font-family: "MyFont"; src: url(./fonts/Roboto-Bold.ttf) format("truetype"); font-weight: bold;}
#font-face { font-family: "MyFont"; src: url(./fonts/Roboto-Italic.ttf) format("truetype"); font-weight: normal; font-style: italic;}
#font-face { font-family: "MyFont"; src: url(./fonts/Roboto-BoldItalic.ttf) format("truetype"); font-weight: bold; font-style: italic;}
#font-face { font-family: 'Material Icons'; font-style: normal; font-weight: 400; src: url(./fonts/material-icons.woff2) format('woff2'); }
#font-face { font-family: 'Material Icons Outlined'; font-style: normal; font-weight: 400; src: url(./fonts/material-icons-outlined.woff2) format('woff2'); }
* { font-family: "MyFont", "Roboto-Light", "Noto Sans CJK SC", "DejaVu Sans"; }
.UICheckbox { width:80px; height:89px; background-image:url("img/checkboxOFF.png"); background-repeat:no-repeat; }
.UICheckbox.checked { background-image:url("img/checkboxON.png"); }
Since I need to import as base64 the CSS files I cannot actually process automatically the resources found inside of them (contrary to how it is done with PostCSS or similiars).
My current webpack configuration is the following but it just ignores the url() statements:
{
test: /\.(png|jpg|gif)$/i,
type: "asset/inline",
},
{
test: /\.(woff|woff2|eot|ttf|otf)$/i,
type: "asset/inline",
},
{
test: /\.css$/i,
type: "asset/inline",
},
Is there a better way to handle this?
I found a solution that is not really generic or solid but does the job, at least in my case scenario.
The imports are relatives to a fixed source path so the idea is to read the resources found inside the url() rules and process it as DataURI in base64 encoding.
I found quite useful the use of datauri which provides a way to include data in-line as if they were external resources and manages the mimetypes automatically.
npm install datauri --save
Then I had to modify the generator handler inside webpack.config.js to process the resources manually exploiting the datauri package.
const path = require("path");
const Datauri = require("datauri/sync");
const EXTERNAL_ROOT_PATH = "./src/external/dev/";
module.exports = {
...
module: {
rules: [
{
test: /\.css$/i,
type: "asset/inline",
generator: {
dataUrl: (content) => {
content = content.toString();
// Get the resource paths inside the CSS url() rules
let asset_urls = [];
let match,
regex = /url\((.*?)\)/gi;
while ((match = regex.exec(content))) {
asset_urls.push(match[1]);
}
// console.log(asset_urls);
// Convert the resource to a DataURI and replace it inside url()
asset_urls.forEach((file_path) => {
// Sanitize the file path first
sanitized_file_path = file_path.replace(/[\"\']/g, "").replace(/^(?:\.\.\/)+/, "");
const data_uri = Datauri(path.join(EXTERNAL_ROOT_PATH, sanitized_file_path));
// console.log(data_uri.content); //=> "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAA..."
// console.log(data_uri.mimetype); //=> "image/png"
// console.log(data_uri.base64); //=> "iVBORw0KGgoAAAANSUhEUgAA..."
// console.log(data_uri.buffer); //=> file buffer
content = content.replace(file_path, data_uri.content);
});
return "data:text/css;base64," + Buffer.from(content).toString("base64");
},
},
},
],
},
};

Nextjs css variable not defined

I have a Next.js project that uses styled-components, variables.less imported in global.less and theme object that is available globally for all components.
theme.ts fonts vars
font: {
weight: { regular: 350 },
family: {
bold: 'var(--bold-font)',
medium: 'var(--medium-font)',
light: 'var(--light-font)',
book: 'var(--book-font)',
roboto: 'Roboto, sans-serif',
},
},
variables.less
#bold-font: 'GothamRounded, Bold', Arial, sans-serif;
#medium-font: 'GothamRounded, Medium', Arial, sans-serif;
#light-font: 'GothamRounded, Light', Arial, sans-serif;
#book-font: 'GothamRounded, Book', Arial, sans-serif;
styled component
font-family: ${({ theme }) => theme.font.family.book};
the problem is that some variables work some dont, and I cannot figure out the pattern to solve the problem. The variable can be undefined randomly, #white: #fff works but #asd: #fff does not. Am I doing something wrong?

Stylus: a hash key for multiple values isn't compiling

In Stylus, how can we assign a hash key to a list of values? None of the following ways are working for me, it won't compile:
main-content-font = {
family: "Noto Sans", sans-serif,
size: 1em
}
main-content-font = {
family: ("Noto Sans", sans-serif),
size: 1em
}
main-content-font = {
family: ("Noto Sans" sans-serif),
size: 1em
}
main-content-font = {
family: "Noto Sans" sans-serif,
size: 1em
}
main-content-font = {
family: "Noto Sans" sans-serif
size: 1em
}
You didn't note how you were calling it, but here are 2 alternatives:
Encasing the whole thing in single quotes and calling it with unquote should get you there:
main-content-font = {
family: '"Noto Sans", sans-serif',
size: 1em
}
.selector {
font-family unquote(main-content-font[family]);
.subselector {
font-size main-content-font[size];
}
}
Confirm in the stylus REPL.
As would creating a variable with the font family there, referencing it in the hash, and then calling the hash member without an additional function:
sansserif = "Noto Sans", sans-serif
main-content-font = {
family: sansserif,
size: 1em
}
Also viewable in the REPL.

Custom fonts with L.divIcon Leaflet not showing

Using the icomoon internet service to create custom icon-fonts, having trouble to make them visible on Leaflet map. Somehow I can not fetch the icons, what have I missed!? I have the data on the map as I can open up the popup, the problem is there is no icons visible....
I have the fonts folder in the correct place and stylesheet is loaded
This is part of the CSS from icomoon I have in a custom-style.css
#font-face {
font-family: 'icomoon';
src: url('myplace/customer/fonts/icomoon.eot?bf4cat');
src: url('myplace/customer/fonts/icomoon.eot?bf4cat#iefix') format('embedded-opentype'),
url('myplace/customer/fonts/icomoon.ttf?bf4cat') format('truetype'),
url('myplace/customer/fonts/icomoon.woff?bf4cat') format('woff'),
url('myplace/customer/fonts/icomoon.svg?bf4cat#icomoon') format('svg');
font-weight: normal;
font-style: normal;
font-display: block;
}
[class^="icon-"], [class*=" icon-"] {
/* use !important to prevent issues with browser extensions that change fonts */
font-family: 'icomoon' !important;
speak: never;
font-style: normal;
font-weight: normal;
font-variant: normal;
text-transform: none;
line-height: 1;
/* Better Font Rendering =========== */
-webkit-font-smoothing: antialiased;
-moz-osx-font-smoothing: grayscale;
}
.icon-bb .path1:before {
content: "\e900";
color: rgb(35, 31, 32);
}
.icon-bb .path2:before {
content: "\e901";
margin-left: -1em;
color: rgb(0, 0, 0);
}
.icon-bb .path3:before {
content: "\e902";
margin-left: -1em;
color: rgb(0, 0, 0);
} etc....
Then I created a function to look for customer name and give them a className
function getCustomer(x){
x === 'customerBB' ? 'icon- icon-bb' :
x === 'customerCA' ? 'icon- icon-ca' :
x === 'customerCE' ? 'icon- icon-ce' :
'leaflet-div-icon'; //default blue icon if no match
Then a function to return className depending on the results found in feature.properties.customer_name
var setDivIcon = function(feature){
return {
className: getCustomer(feature.properties.customer_name)
};
}
var customerIcon = L.divIcon(setDivIcon);
Later on I use the pointToLayer to add the GeoJSON to the map
customerLayer = L.geoJson(json, {
pointToLayer: function(feature, latlng) {
var time = feature.properties.timeMean_numb;
var point
if (time < 0.167){
point = L.marker(latlng, {icon: L.divIcon(setDivIcon(feature)) }).addTo(time_1);
}
else if (time >= 0.167 && time <= 0.334){
point = L.marker(latlng, {icon: L.divIcon(setDivIcon(feature)) }).addTo(time_2);
}
In your fontface rule you are missing some src:? This could explain them not being fetched

How to declare multiple font-face and assign each of them to a variable and access them in styled-components

I am using font-face in index.css and accessing these font-family in other places of my application.
My requirement is to assign each of these font-face to different variables. And use these variables in my applications. I want to name these variables generically as 'regular', 'medium' because if I change it from OpenSans to other font-family I need not change font-family as OpenSans to other in other parts of my application.
I am using styled-components for stylings .
#font-face{
font-family: 'OpenSans';
font-style: normal;
font-weight: 400;
src: url(./assets/Fonts/OpenSans-Regular.ttf)
}
#font-face{
font-family:'OpenSans-SemiBold';
font-style: normal;
font-weight: 400;
src:url(./assets/Fonts/OpenSans-SemiBold.ttf)
}
#font-face{
font-family:'OpenSans-SemiBoldItalic';
font-style: normal;
font-weight: 400;
src:url(./assets/Fonts/OpenSans-SemiBoldItalic.ttf)
}
#font-face{
font-family: 'Proxima Nova';
font-style: normal;
font-weight: 400;
src: url(./assets/Fonts/ProximaNova-Regular.ttf);
}
#font-face{
font-family: 'Proxima Nova Medium';
font-style: normal;
font-weight: 400;
src: url(./assets/Fonts/proxima-nova-medium.ttf);
}
Also, once these font-faces are assigned to different variables how can I access in styled-components of other components
eg:
const p = styled.p`
font-family: ??? --> is it using ${variable_name} ?
`
my requirement in index.css :
var Medium-font = {
#font-face{
font-family: 'Proxima Nova Medium';
font-style: normal;
font-weight: 400;
src: url(./assets/Fonts/proxima-nova-medium.ttf);
}
};
var Regulat-font = {
#font-face{
font-family: 'Proxima Nova';
font-style: normal;
font-weight: 400;
src: url(./assets/Fonts/ProximaNova-Regular.ttf);
}
};
and so on..
You don't need to assign the whole font-face to a variable. Fonts are NOT something that you change often. But even if you do for some reason... the font-face will still need to be changed like url and the name of the font itself in the index.css but the only change in actual css will be the font-family property.
You can just assign the font-family to a variable in styled-components and then use it everywhere. This way you'll only need to change it in one place in your theme.
You can use ThemeProvider to achieve this.
// Some component
const Para = styled.p`
font-family: ${props => props.theme.fontFamily1};
`;
const Para2 = styled.p`
font-family: ${props => props.theme.fontFamily2};
`;
// Define what props.theme will look like
const theme = {
fontFamily1: "OpenSans",
fontFamily2: " Proxima Nova"
};
//render method of App.jsx or root app file
render(
<div>
<ThemeProvider theme={theme}>
<Para>Lorem ipsum dolor sit amet, consectetur adipiscing elit.</Para>
<Para2>Lorem ipsum dolor sit amet, consectetur adipiscing elit.</Para2>
</ThemeProvider>
</div>
);
<Para> compoent will now have the font OpenSans and <Para2> Proxima Nova.
If you decide to change the font, just change the fontFamily1/fontFamily2 prop in theme accordingly and it'll reflect in all the components using the theme.
Refer this for more info: https://styled-components.com/docs/advanced#theming
Hope this helps !

Resources