#
UDTextFit Powershell Universal Component Module 📝
#
The Project 🏗️
So this component was built to please those who like me sometimes wish that text could be formatted a little better, like keeping a title to one line. Sometimes this is not possible, and like I have done on a good few of these blog pages, you end up with a title that spans just over one line, but the next title size down looks a bit to blantant that you have made that title smaller. Would it not be awesome if the text just magically sized itself to fit? Well folks now you can see why I decided that this particular component would be a good component to add.
#
Using New Site To Find Components 📰
Yep so even though I am providing the link to the official react component above which is pointing to npmjs.com it seems for some reason when I am searching on npmjs.com I get limited to 20 results no matter what. Like I used to get back thousands of results, and scroll through pages and pages of components till I found the one I was looking for. I even signed up to npmjs thinking maybe you now need to be a member to get back all the results, but I was still only getting 20 results back.
Thankfully the internet has more than just one webpage to find react components, and I then landed on:-
Which was bringing back the number of results I used to get on npmjs and it even gave me the link to the npmjs package page.
So I know this is not the most super-fancy react component but as mentioned I could really see this being useful if your title spills one or two characters long to fit nicely on the line you are typing. As this is a pretty basic react component with a few parameters I have included all of these in the JSX file which was used to build the final Powershell module.
#
Component JSX File 🗃️
So there are a fair few good files you need to edit in some shape or form to build a component, I think it would be a good idea for me to document this process to show how simple it really is. Before I could edit this JSX file within the components folder I needed to make sure I had installed the npm pacakge for this react component as I saw this needed more than one dependency I used the following website to detect all the dependencies to save me clicking
I then copied this list into notepad then ran this one line to install all these dependencies
gc C:\Builds\dependencies.txt | % {npm i $_ --legacy-peer-deps}
So once these were installed, and I had renamed the .PSD1 and .PSM1 file to the module name I wanted. I then edited the .PSD1 file to include the RootModule as the newly named .PSM1 file, I edited the component.build.ps1 file to copy the newly named modules
Copy-Item $PSScriptRoot\UDTextFit.psd1 $OutputPath
Copy-Item $PSScriptRoot\UDTextFit.psm1 $OutputPath
also edited line 20 in the webpack.config.js file to be
library: 'udtextfit'
Within the components folder there is an index.js file my edited file looked like
import UDTextFit from './component';
UniversalDashboard.register("udtextfit", UDTextFit);
Please keep case-sensitive lower-case for the webpack.config.js file which then reflects what is typed as first arguement within the parenthesis as shown above. Once you have made all these edits to the existing template files, and installed the npm package and all dependencies (in this case I only had two packages to install as only one dependency) it is time to construct the actual component that will be displayed on the dashboard. This is done by editing the component.jsx file witin the components folder within the github template you downloaded. This is my final edited component.jsx file:-
import React from 'react';
import { withComponentFeatures } from 'universal-dashboard'
import { Textfit } from 'react-textfit';
const UDTextFit = props => {
return (
<Textfit
key={props.id}
mode={props.mode}
forceSingleModeWidth={props.singleWidth}>
{props.text}
</Textfit>
);;
}
export default withComponentFeatures(UDTextFit)
So VSCode was not complaining about any of the code above, so now I needed to edit the .PSM1 and .PSD1 file to finish this component off before running invoke-build so this is my final PSD1 file below
#
# Module manifest for module 'UDTextFit'
#
# Generated by: adam bacon
#
# Generated on: 12/09/2020
#
@{
# Script module or binary module file associated with this manifest.
RootModule = 'UDTextFit.psm1'
# Version number of this module.
ModuleVersion = '0.0.1'
# Supported PSEditions
# CompatiblePSEditions = @()
# ID used to uniquely identify this module
GUID = '76de2c49-86a9-4b58-9247-edbe35fed09a'
# Author of this module
Author = 'psdevuk'
# Company or vendor of this module
CompanyName = 'Home'
# Copyright statement for this module
Copyright = '(c) adamr. All rights reserved.'
# Description of the functionality provided by this module
# Description = ''
# Minimum version of the PowerShell engine required by this module
# PowerShellVersion = ''
# Name of the PowerShell host required by this module
# PowerShellHostName = ''
# Minimum version of the PowerShell host required by this module
# PowerShellHostVersion = ''
# Minimum version of Microsoft .NET Framework required by this module. This prerequisite is valid for the PowerShell Desktop edition only.
# DotNetFrameworkVersion = ''
# Minimum version of the common language runtime (CLR) required by this module. This prerequisite is valid for the PowerShell Desktop edition only.
# ClrVersion = ''
# Processor architecture (None, X86, Amd64) required by this module
# ProcessorArchitecture = ''
# Modules that must be imported into the global environment prior to importing this module
# RequiredModules = @()
# Assemblies that must be loaded prior to importing this module
# RequiredAssemblies = @()
# Script files (.ps1) that are run in the caller's environment prior to importing this module.
# ScriptsToProcess = @()
# Type files (.ps1xml) to be loaded when importing this module
# TypesToProcess = @()
# Format files (.ps1xml) to be loaded when importing this module
# FormatsToProcess = @()
# Modules to import as nested modules of the module specified in RootModule/ModuleToProcess
# NestedModules = @()
# Functions to export from this module, for best performance, do not use wildcards and do not delete the entry, use an empty array if there are no functions to export.
FunctionsToExport = '*'
# Cmdlets to export from this module, for best performance, do not use wildcards and do not delete the entry, use an empty array if there are no cmdlets to export.
CmdletsToExport = '*'
# Variables to export from this module
VariablesToExport = '*'
# Aliases to export from this module, for best performance, do not use wildcards and do not delete the entry, use an empty array if there are no aliases to export.
AliasesToExport = '*'
# DSC resources to export from this module
# DscResourcesToExport = @()
# List of all modules packaged with this module
# ModuleList = @()
# List of all files packaged with this module
# FileList = @()
# Private data to pass to the module specified in RootModule/ModuleToProcess. This may also contain a PSData hashtable with additional module metadata used by PowerShell.
PrivateData = @{
PSData = @{
# Tags applied to this module. These help with module discovery in online galleries.
# Tags = @()
# A URL to the license for this module.
# LicenseUri = ''
# A URL to the main website for this project.
# ProjectUri = ''
# A URL to an icon representing this module.
# IconUri = ''
# ReleaseNotes of this module
# ReleaseNotes = ''
# Prerelease string of this module
# Prerelease = ''
# Flag to indicate whether the module requires explicit user acceptance for install/update/save
# RequireLicenseAcceptance = $false
# External dependent modules of this module
# ExternalModuleDependencies = @()
} # End of PSData hashtable
} # End of PrivateData hashtable
# HelpInfo URI of this module
# HelpInfoURI = ''
# Default prefix for commands exported from this module. Override the default prefix using Import-Module -Prefix.
# DefaultCommandPrefix = ''
}
Please note I still need to edit this before I can publish it to the gallery as no description
To make the actual cmdlet behind this component you need to edit the pre-defined function in the .PSM1 file so this is my finished .PSM1 before running the invoke-build
$IndexJs = Get-ChildItem "$PSScriptRoot\index.*.bundle.js"
$AssetId = [UniversalDashboard.Services.AssetService]::Instance.RegisterAsset($IndexJs.FullName)
function New-UDTextFit {
<#
.SYNOPSIS
Creates a new component
.DESCRIPTION
Creates a new component
.PARAMETER Id
The ID of this editor
.PARAMETER Mode
single or multi Algorithm to fit the text. Use single for headlines and multi for paragraphs. Default is single
.PARAMETER SingleModeWidth
When mode is single and forceSingleModeWidth is true, the element's height will be ignored. Default is false
.PARAMETER Text
Text for the component
.EXAMPLE
New-UDTextFit -Text "This is too big for one line" -Mode single
#>
param(
[Parameter()]
[string]$Id = (New-Guid).ToString(),
[Parameter()]
[ValidateSet("single","multi")]
[string]$Mode = "single",
[Parameter()]
[bool]$SingleModeWidth = $false,
[Patermeter()]
[string]$Text
)
End {
@{
assetId = $AssetId
isPlugin = $true
type = "udtextfit"
id = $Id
mode = $Mode
singleWidth = $SingleModeWidth
text = $text
}
}
}
#
Ready, Steady, Go! 🚦
So once you have followed the above, you are now ready to run:-
invoke-build
As long as you read the official documentation on building a custom component you would have already downloaded all the prerequisite modules and software required to build custom components. I did find I needed to also install the psake module as well. This process literally took 10 seconds or less. As long as you do not get any errors, and the process completes then within the output directory you will have you brand-new custom component you built.
I restarted the PowershellUniversal service then logged into the main portal. Verified the module was being picked up by the software, by searching the available modules within the program. Once I verified my new module was included, I then did a test on the dashboard.
I now had a fully working react custom component loaded into the Powershell Universal dashboard I had created. I then verified all the parameters worked, which they did then it was time to publish this module to the Powershell Gallery. Please note to include ud-component within the module tags to enable your custom component to be found on the market place exclusive to this product.