Archive for the 'PrimeNG' Category

January 5th, 2021
6:15 pm
Installing/running multiple Node/Angular/primeng + showcase versions under windows

Posted under Angular & PrimeNG & Web
Tags ,

I needed to upgrade node/angular/PrimeNG/primeNG Showcase to the latest versions (Node 15.5, Angular 11, PrimeNG 11) , but I also wanted to be able to maintain projects on older versions using Angular 6.

This post details how to do this with nvm under Linux, but an alternive nvm implementation is needed for windows. This is detailed here, and the git repo for this version with full instructions is here . I uninstalled the existing angular cli/PrimeNG via npm uninstall, and then removed my node installation via control panel.

Next I installed nvm per the above post for the windows implementation. Per the above post for the Linux version, I used nvm install to install node versions 10.4.0 and 15.5. I then selected each in turn via nvm use, and for each version, I installed the desired angular/cli for that version globally in the standard way, using for example npm install -g @angular/cli@6.2.2 for the legacy version. Note that using -g in this case installs globally for the currently selected node version only, so when you switch/select the current node version with npm use, you also automatically select the angular/cli version that you previously installed with it.

Having done this, and as per the above posts, you must remember to select the desired node version with nvm use in each command window or batch file that you use. The version is not selected for a project directory, but is per command window/process.

I was then able to use both the latest angular/primeNG and the legacy ones, and could build and run with both on the same machine.

One issue I hit with primeNG when performing npm install on the latest version was a bug in the latest version of node: “Cannot destructure property ‘name’ of ‘node’ as it is null.” This bug is detailed here. Per the post comment by Mika Bertels, I reverted to npm 6 using npm i -g npm@6. In my case, npm gave a file already exists error, so as hinted by node I used the –force flag to force the reversion of version. This worked fine, and my npm install of primeng worked successfully

Per the instructions here, the primeng 11 can just be installed and then run with ng serve, and I did not hit any issues with theme building etc. which I did with earlier versions, presumably due to all the themeing changes. Note also that this setup guide for primeng explains how to install primeng and primeicons when using with your own project – I did not need to do this initially as I was just running the showcase.

 

Comments Off on Installing/running multiple Node/Angular/primeng + showcase versions under windows

February 20th, 2020
4:34 pm
Loading/Busy Indicator

Posted under Angular & PrimeNG & Web
Tags

I needed an indicator such as some kind of spinner whilst microapps were loading.

PrimeNG has a progress spinner here. However, the implementation uses scalable vector graphics, which I was not able to use.

My base line for browser support included IE11, and unfortunately this only has a partial implementation which broke when using the PrimeNG spinner.

I therefore used loading.io to design my own animated gif. The site has a number of free as well as paid for spinner/busy patterns, and each one has a form allowing a number of variables to be tweaked, allowing customisation of your spinner design. You can then download the result in a choice of formats including animated GIF as well as SVG. I stuck with an animated GIF as this worked across all the browsers. I designed different versions (e.g. colour), making them themeable as part of the application theme. For each base theme I implemented a choice of 2 spinners – A rolling spinner, and a spinning circles spinner. Both gave excellent results and were free.

 

Comments Off on Loading/Busy Indicator

January 22nd, 2020
4:11 pm
PrimeNG theming no longer open source

Posted under Angular & PrimeNG & Web

The PrimeNG changelog states that as of 8.0.0-rc1, the old theming architecture based on Themeroller is being removed completely in favour of the new theme architecture and designer, as per change #7762.

The new theme architecture looks much more fully functional, and the designer looks a good and powerful tool.

A number of themes are paid for and not open source, as before which is fine and not a problem.

The designer itself is also paid for, which is perhaps slightly sad but not a real problem if you can roll your own themes directly in SCSS, e.g. by adapting a free theme as I have done in the past.

 

However, the big frustration is that the full SCSS theming API definition itself is proprietary and not open sourced/publicly documented, as per this prime post here. This means that the only official way to create a new SCSS based theme is with the designer, which is paid for.

This is a real frustration as due to the version matrix, if you stick with an older PrimeNG you cannot upgrade to the latest Angular, e.g. to Angular 8/Ivy.

One way around it is detailed in this helpful blog post here, which involves a certain amount of reverse engineering of the free themes. This is in itself not a big issue as normally in the past I have created themes by modifying an existing themeroller theme (or, for Primefaces, even by rolling one via the ThemeRoller web site tool).

However as the post points out, the fact that the global common SCSS is not now released, we may be subject to breaking changes in the future.

Prime states on the PrimeNG page that the components are all open source, but with parts of the theming architecture now being proprietary and not released, this is does not now appear to be the case any more.

I will continue to monitor this and see what others are doing, but it may be that for my own projects, for the first time ever I will need to move to another component set (e.g. use Material Design when using Angular) and no longer use Prime.

Comments Off on PrimeNG theming no longer open source

January 21st, 2020
3:50 pm
Using flex for PrimeNG message layout vs float/display:table-cell

Posted under Angular & PrimeNG & Web

I’m currently using PrimeNg 6.1.3 with the older themeroller architecture

This has a glitch on message display as follows:

I wanted the text to be indented past the LHS icon rather than on a new line.

My old school version in my theme used a left float on the icon, and a display:table-cell on the <ul> text container.

This worked fine as follows:-

I didn’t like using display:table-cell but had to in this case as I had no control over the markup generated by the message component, only the theme SCSS.

My second version, which is simpler, just removed the float and the display:table-cell, and made the containing div a flex container via display:flex.

This worked in exactly the same way, and was all I needed to do. The flex defaults just worked with no strange tweaking required.

The W3 Schools page on flex, including numerous try out examples that you can play with, is here.

PrimeNG Generated Markup

<div class=”ui-messages ui-widget ui-corner-all ng-tns-c2-0 ng-trigger ng-trigger-messageAnimation ng-star-inserted ui-messages-warn” style=”display: block; transform: translateY(0px); opacity: 1;” ng-reflect-ng-class=”[object Object]”>
   <a class=”ui-messages-close ng-tns-c2-0 ng-star-inserted” href=”#” style=””>
      <i class=”pi pi-times”></i>
   </a>
   <span class=”ui-messages-icon pi pi-exclamation-triangle” ng-reflect-klass=”ui-messages-icon pi” ng-reflect-ng-class=”pi-exclamation-triangle”></span>
   <ul class=”ng-tns-c2-0″>
      <li class=”ng-tns-c2-0 ng-star-inserted” style=””>
         <span class=”ui-messages-summary ng-tns-c2-0 ng-star-inserted”>Age Invalid:</span>
         <span class=”ui-messages-detail ng-tns-c2-0 ng-star-inserted”>Your age is  outside the required age range of 18 to 50</span>
      </li>
   </ul>
</div>

Original Style Fragment (SCSS)

.ui-messages.ui-widget {
padding: .5em;
border: 0 none;
color: $contentTextColor;

.ui-messages-icon {
      float: left;
margin-right: .1em;
}
&, .ui-messages-close {
color: $headerIconTextColor;
~ ul {
padding-right: 1.4em;
}
.pi, .ui-messages-icon.pi {
font-size: 1.6em;
}
}
    ul {
display:table-cell;
}

.ui-messages-summary {
margin-left: 0;
}
&.ui-messages-success {
background-color: #b7d8b7;
}
/*…other message severities… */
}

Flex Style Fragment (SCSS)

.ui-messages.ui-widget {
  /* We have to use !important here as the markup (which we cannot control)
uses an inline style for display:block 🙁 */
display: flex !important;
    padding: .5em;
border: 0 none;
color: $contentTextColor;

.ui-messages-icon {
margin-right: .1em;
}
&, .ui-messages-close {
color: $headerIconTextColor;
~ ul {
padding-right: 1.4em;
}
.pi, .ui-messages-icon.pi {
font-size: 1.6em;
}
}
.ui-messages-summary {
margin-left: 0;
}
&.ui-messages-success {
background-color: #b7d8b7;
}
/*…other message severities… */
}

Comments Off on Using flex for PrimeNG message layout vs float/display:table-cell

March 17th, 2019
8:13 pm
@angular-devkit/build-angular version causes initialisation failure with angular elements Microapp POC

Posted under Angular & PrimeNG
Tags , , ,

I did an npm-update of  my microapp-fabric-prototype and my microapp-dataview app.

This resulted in the upgrade of

"@angular-devkit/build-angular": "~0.8.2"

to:

"@angular-devkit/build-angular": "^0.13.4",

in package.json. This caused my microapp POC to fail.

When the host Microapp Fabric application receives a menu action from a menu item click, it dynamically creates an angular element in its microapp container; the element contains the target microapp.

This should result in the initialisation of the angular runtime environment for the custom angular element, including initialisation of the IOC/DI environment for the target angular element app. This includes creation of all the required components/services and calling of their various constructors.

Unfortunately, with the later version above, instead of initialising the app-config-service in the angular element, it tried to re-initialise the app-config-service for the host app a second time which caused the whole app to fail.

The precise reason for the issue is not known. Both apps have some services (such as app-config-service) which have the same name, and sometimes when debugging it can cause confusion when trying to navigate the source maps in the debugger.

However, as all the services and components for each app (the main app and any angular-elements) are correctly encapsulated, there is never a confusion between them, even though the script environment is common and not shadowed. (In this demo, we are using a shadow dom for the W3C custom elements/angular elements, but the javascript is not shadowed. This is correct, and allows angular to have a runtime environment which persists across the main app and all the angular elements, and manages them all correctly).

As I have found before, care needs to be taken when upgrading versions – this is quite often not straightforward and needs care to check out dependencies that cause failures. Care will be needed I suspect when upgrading from Angular 6.1.7 to Angular 7!

No Comments »

March 2nd, 2019
11:22 pm
Compiling a custom PrimeNG theme deployed as a static asset

Posted under Angular & PrimeNG
Tags ,

I am  using multiple themes and theme selection, using custom themes

For interest I am loading the theme css as a static asset, in index.html:-

<head>
<meta charset=”utf-8″>
<title>Microapp Fabric Prototype</title>
<base href=”/”>
<meta name=”viewport” content=”width=device-width, initial-scale=1″>
<link id=”theme-css” rel=”stylesheet” type=”text/css” href=”assets/resources/themes/salient/theme.css”>
</head>

Then I am dynamically changing the href to switch themes:-

export class ThemeSwitcher {
/*
* Select the target theme
* this may be an external theme or an internal packaged one
* If the path contains a ‘/’ the theme is assumed to be an external theme source
*/
changeTheme(theme: string) {
const themeLink: HTMLLinkElement = <HTMLLinkElement>document.getElementById(‘theme-css’);
themeLink.href = theme.indexOf(‘/’) >= 0 ? theme : ‘assets/resources/themes/’ + theme + ‘/theme.css’;
}
}

A theme SCSS under the assets folder will be automatically compiled and included inline in the package only when a specific theme is referred to in the “style” section of angular.json. When dynamically switching multiple themes as above, the themes are kept as static assets and are not inlined in the package and so are removed from the “style” section. When this is done, the theme scss files for all the themes are not compiled to css automatically when an ng build or ng serve is done. This post here details how to manually install and build the scss using node-sass. It goes into other details which I haven’t needed as I am using static assets, so only node-sass is needed. If in the actual theme directory, the following commands will install  node-sass and compile the scss for the theme and also create the source map:-

npm install node-sass

node-sass theme.scss theme.css ––source-map .

This can also be added to the scripts section of package.json to make an npm command:

“scripts”: {
“ng”: “ng”,
“start”: “ng serve”,
“build”: “ng build”,
“test”: “ng test”,
“lint”: “ng lint”,
“e2e”: “ng e2e”,
“scss”: “cd src/assets/resources/themes/legacy-blue && node-sass theme.scss theme.css ––source-map .”
},

This can be run by simply using npm run scss

Note as above that npm supports the cd command in the scripts section, both for linux and windows (as detailed here). The default directory is the root of the project, and this is consistent even if you run the npm command e.g. from a subdirectory. I did not manage to find a way to automate this via an ng build or ng serve command, so these would have to be run in conjunction with npm run scss (with the latter running first).

No Comments »

May 29th, 2018
4:56 pm
Problems upgrading angular 5 project to angular 6, and upgrading angular on a PC

Posted under Angular & PrimeNG
Tags

I had serious issues trying to upgrade an existing project, and it was not clear online what I should do.

The main persistent error was:-

./node_modules/raw-loader!./node_modules/postcss-loader/lib??embedded!./node_modules/sass-loader/lib/loader.js??ref–8-3!./src/styles.scss
Module build failed: Error: Node Sass does not yet support your current environment: Windows 64-bit with Unsupported runtime (64)
For more information on which environments are supported please see:
https://github.com/sass/node-sass/releases/tag/v4.8.3

The online information on this was not clear.

Initially I used a liberal combination of npm-update and npm-update –g on various things but still had the above error.

I reached a point of installing primeng successfully under angular 6 as detailed here.

I then tried hand editing the package.json file for the upgrade project, stealing the versions from the package.json for the primeng application. However this did not appear to help -I still had the above issues.

In the end a combination of the following resolved this:-

ng update @angular/cli

ng update @angular/cli

npm install –g node-sass@latest

npm install node-sass@latest

I think the key issue here was installing the latest node-sass. I also had some code errors to resolve in the application but I did mange to run it successfully.

No Comments »

May 23rd, 2018
7:51 pm
Installing and running the PrimeNG showcase locally under windows

Posted under Angular & PrimeNG
Tags , , ,

Update 23/5/2018

I retried this using Angular 6 and the latest primeng.

Step 2/ below was not needed, and I did not install/reinstall gulp per step 3/ (not used this time – need to check/confirm re this)

The wiki steps referred to below, here, referred to using sass to build the css, but this command did not work for me even when I installed the node.js sass per here -  the –update command came back with an error.

I then gave up using sass to compile the sass files.

Because of this issue I still had to fix the theming, so tried to copy the css files as below rather than compile the sass. This time the themes folder was under src\assets\components.

I therefore created another skeleton app, installed primeng using “npm install primeng”, and then copied the themes folder from under node_modules\primeng\resources  to src\assets\components, overwriting the themes already there.

This added the css files that were missing.

I could then run the showcase with theming fully working, either using “npm start” or “ng serve” – either worked.

I did notice that the theming borders on the treetable component did not appear to work, but apart from that all the theming including theme switching worked fine.

Original Post

It is useful to have this running locally in order to can try out occasional code hacks on the example code to try out ideas or check how things work if the docs are not clear on a point, knowing that you have started from a working example.

The steps for this basically follow the wiki steps here. Note the following additions/amendments to the steps:-

1/ I cloned the repository from here. Having cloned I then listed and disconnected from the remote repositories, as the clones were just for local use:-

git remote –v

git remote rm origin

git remote –v

2/ Dependencies as follows were added to package.json as per instructions:-

  "dependencies": {
      "@angular/common": "4.0.0",
      "@angular/compiler": "4.0.0",
      "@angular/core": "4.0.0",
      "@angular/forms": "4.0.0",
      "@angular/http": "4.0.0",
      "@angular/platform-browser": "4.0.0",
      "@angular/platform-browser-dynamic": "4.0.0",
      "@angular/router": "4.0.0",
      "@angular/animations": "4.0.0",
      "core-js": "^2.4.1",
      "rxjs": "^5.2.0",
      "zone.js": "^0.8.4"
  },

Following this npm install was run to download all the dependencies

3/ In order to build using gulp as instructed (gulp build), I installed gulp first as per the instructions here:-

npm install --global gulp-cli
npm install --save-dev gulp

4/ I then ran npm start to run the showcase, which defaults to http://localhost:8080/

The showcase ran ok locally but there were some issues with the theming – the theme had a transluscent background on the menus and dropdowns for example which did not correctly occlude the text underneath. The live showcase on the PrimeNG site did not have this problem.

On investigation it appears that the theme files are under the main resources/themes directory, but are not being sass compiled from scss during the build so there are no .css files there. The gulp file for the project, gulpfile.js, does not have any entries that do sass compilation so this may be an omission/bug in the version I had downloaded.

The showcase does not use the primeng under node_modules – it defines its own primeng package such that if you try to enter npm install primeng to install the themes in the normal way as part of the npm installed package, you get an error from npm about the duplicate primeng.

My workaround was straightforward – I just copied the theme folder and all subfolders from under the node_modules\primeng\resources directory in another application folder to the projects top level resources directory (in fact I used the primeng-quickstart-webpack which I had already set up) – any other project where you have installed primeng will do. This solved the problem by providing all the css files for the themes, and the themes and theme switching then worked.

As I have no requirement to do a full working build for the showcase this is no problem.

I checked for other posts about theming issues and found a couple of StackOverflow posts about theme issues with Webpack here and here. These may prove relevant for future development.

No Comments »

May 26th, 2017
12:55 pm
Dynamically updating css classes on child components from a parent property

Posted under Angular & CSS & PrimeNG
Tags , , ,

I was using a button component to encapsulate the primeNG one, to allow it to responsively change to an icon only button at smaller screen widths. Whilst in theory I could have dynamically modified the internal primeNG button CSS, this was complex and I did not want  to become tightly coupled to it. My button component therefore simply selected one of 2 buttons via a media query, setting the unwanted one to display:none.

I wanted any classes added to the top level ss-button to be set on the underlying primeNG buttons. One use of these buttons was in a home brewed tab component, and  I was dynamically changing the button colour via ui-button-primary, ui-button-secondary so that the active tab had a ‘primary’ coloured button and the inactive ones were ‘secondary’ which caused them to become uncoloured ghost buttons – ideal for my requirement.

During refactoring to replace the ‘full size only’ primeNG buttons with the resizing ss-buttons I introduced a bug and the colour change failed to work. The initial (incorrect) refactored code was as follows:-

ss-tab-toolbar.component.html

<ng-container *ngFor="let tab of tabs">
<app-ss-button [label]="tab.label" [icon]="tab.icon" (click)="setActiveTab(tab)"
[ngClass]="{'ui-button-primary': isActiveTab(tab), 'ui-button-secondary': ! isActiveTab(tab)}"></app-ss-button>
</ng-container>

ss-button.component.html

<button pButton type="button" [title]="label" [label]="label" [icon]="icon" class="ss-button icon-text"
[ngClass]="class" ></button>
<button pButton type="button" [title]="label" [icon]="icon" class="ss-button icon-only"
[ngClass]="class" ></button>

ss-button.component.ts

@Component({
selector: 'app-ss-button',
templateUrl: './ss-button.component.html',
styleUrls: ['./ss-button.component.scss']
})
export class SSTabButtonComponent {

@Input() label: string;
@Input() icon: string;
@Input() class: string;

constructor() { }
}

The issue was that I was using [ngClass] dynamically to update the classes on the <app-ss-button> in ss-tab-toolbar.component. html. This used to work for the PrimeNG buttons, but now would have no effect as the classes need to be changed on the child buttons not the encapsulating parent. A simple change of [ngClass] to [class] fixed the problem, as the parent style change then updated the property on the parent component which was then picked up by the children correctly.

modified ss-tab-toolbar.component.html

<ng-container *ngFor="let tab of tabs">
<app-ss-button [label]="tab.label" [icon]="tab.icon" (click)="setActiveTab(tab)"
[class]="{'ui-button-primary': isActiveTab(tab), 'ui-button-secondary': ! isActiveTab(tab)}"></app-ss-button>
</ng-container>

Happily the dynamic nature of angular meant that this worked perfectly for tab changes – the change on the parent class was propagated correctly to the child and the button colours changed correctly.

I was wondering initially whether I would need to involve observables to make this work but this was not the case – this kind of dynamic propagation pattern is worth remembering in future.

No Comments »

May 18th, 2017
6:30 pm
Tricks with the PrimeNG Grid CSS Component

Posted under Angular & CSS & HTML & PrimeNG
Tags ,

Update 19/5/2017

I noticed that my original attempt below, whilst causing the text div to flow under the image div at smaller screen sizes, did not cause the text div to be full width when it was sitting underneath. To do this properly I needed to use a combination of 2 specific non-default (i.e. not ui-g-*) responsive style classes on the text div, in this case ui-md-9 and ui-sm-12. This causes the following:-

  1. At the u-md-* screen size boundary, and higher, the ui-md-9 kicks in and the image and text are on the same line.
  2. Below the ui-md-9 boundary, the ui-sm-12 kicks in and allows the text div to be full width. Without this, it would sit underneath but the default ui-g-9 would still be in effect so it would not switch to full width.

The modified code fragment for the item-text div is as follows:-

<div class="ui-g-9 ui-sm-12 ui-md-9 item-text">

Original Post

I did this quite by accident, due to adding an unwanted “>” on the end of a ui-g-3 class for the div around the left image in a data list – it caused the class to be ignored.

The code (with the offending character and the ui-g-3 class removed) is as follows:-

<ng-template let-place pTemplate="item">
<div class="ui-g list-item item-image">
<div class="item-image">
<img src={{place.thumbUrl}}>
</div>
<div class="ui-g-9 item-text">
<h4>{{place.shortLocation}}</h4>
<h3>{{place.name}}</h3>
<p>{{place.strapline}}</p>
</div>
</div>
</ng-template>

The scss for the component is here (note this is from the component scss file so is encapsulated by Angular from bleeding out):-

h3 {
font-size:1.1em;
font-weight: normal;
margin:.2em 0;
}
h4 {
font-size:1em;
font-weight: normal;
margin: 0;
}
p {
font-size:1em;
margin:.2em 0;
}
.list-item {
padding:.5em;
border-bottom:1px solid #D5D5D5;
display:flex;
align-items: center;
}
.list-item .item-image {
padding-right:1em;
}
.list-item .item-text {
padding-left:0;
}

The happy effect of this was that the image div did not have a ui-g-* class to size it, so had a fixed size determined by the thumbnail, and was not a floating div. When I used a ui-g-3 class for it by removing the offending “>”, then the gap between the image and the text increased as the width changed, which is not something I wanted – the fixed padding there due to the bug was fine for all screen widths.

The ui-g-9 class happily floated next to it and flowed underneath as required. Different ui-g-* classes such as ui-g-6 and ui-g-8 just caused the flow to happen at a different width point.

I could probably have achieved a similar effect by using a ui-g-3 class for the image as I had intended, and then explicitly fixing the width for that div (or e.g. setting a min-width and a max-width).

I may need to do this or re-jig it if I have to cater for different thumbnail sizes, but my preferences is to scale all thumbnails to the same size as it gives a much better layout.

Whether this trick technically breaks or violates the ui-g-* grid css rules I am not sure, the documentation on them is not hugely comprehensive, but I will ponder this one in due course.

For now it works fine!

No Comments »