From 73db2ae15e9ba10e5225c6d29b1c19de74c9cc6a Mon Sep 17 00:00:00 2001 From: Eric Date: Mon, 20 Jun 2022 19:08:35 -0500 Subject: [PATCH] Website: add component (#6244) * Website: add component * Lint fixes --- .../call-to-action-banner-background.svg | 19 +++ .../js/components/call-to-action.component.js | 115 ++++++++++++++++++ .../components/call-to-action.component.less | 88 ++++++++++++++ website/assets/styles/importer.less | 1 + website/scripts/build-static-content.js | 1 + 5 files changed, 224 insertions(+) create mode 100644 website/assets/images/call-to-action-banner-background.svg create mode 100644 website/assets/js/components/call-to-action.component.js create mode 100644 website/assets/styles/components/call-to-action.component.less diff --git a/website/assets/images/call-to-action-banner-background.svg b/website/assets/images/call-to-action-banner-background.svg new file mode 100644 index 000000000000..ba95ad4f6e5e --- /dev/null +++ b/website/assets/images/call-to-action-banner-background.svg @@ -0,0 +1,19 @@ + + + + + + + + + + + + + + + + + + + diff --git a/website/assets/js/components/call-to-action.component.js b/website/assets/js/components/call-to-action.component.js new file mode 100644 index 000000000000..b2817f7ce990 --- /dev/null +++ b/website/assets/js/components/call-to-action.component.js @@ -0,0 +1,115 @@ +/** + * + * ----------------------------------------------------------------------------- + * A customizeable call to action. + * + * @type {Component} + * + * ----------------------------------------------------------------------------- + */ + +parasails.registerComponent('callToAction', { + // ╔═╗╦═╗╔═╗╔═╗╔═╗ + // ╠═╝╠╦╝║ ║╠═╝╚═╗ + // ╩ ╩╚═╚═╝╩ ╚═╝ + props: [ + 'title', // Required: The title of this call-to-action + 'text', // Required: The text of the call to action + 'primaryButtonText', // Required: The text of the call to action's button + 'primaryButtonHref', // Required: the url that the call to action button leads + 'secondaryButtonText', // Optional: if provided with a `secondaryButtonHref`, a second button will be added to the call to action with this value as the button text + 'secondaryButtonHref', // Optional: if provided with a `secondaryButtonText`, a second button will be added to the call to action with this value as the href + ], + + // ╦╔╗╔╦╔╦╗╦╔═╗╦ ╔═╗╔╦╗╔═╗╔╦╗╔═╗ + // ║║║║║ ║ ║╠═╣║ ╚═╗ ║ ╠═╣ ║ ║╣ + // ╩╝╚╝╩ ╩ ╩╩ ╩╩═╝ ╚═╝ ╩ ╩ ╩ ╩ ╚═╝ + data: function (){ + let callToActionTitle = ''; + let callToActionText = ''; + let calltoActionPrimaryBtnText = ''; + let calltoActionPrimaryBtnHref = ''; + let calltoActionSecondaryBtnText = ''; + let calltoActionSecondaryBtnHref = ''; + + return { + callToActionTitle, + callToActionText, + calltoActionPrimaryBtnText, + calltoActionPrimaryBtnHref, + calltoActionSecondaryBtnText, + calltoActionSecondaryBtnHref + }; + }, + + // ╦ ╦╔╦╗╔╦╗╦ + // ╠═╣ ║ ║║║║ + // ╩ ╩ ╩ ╩ ╩╩═╝ + template: ` +
+
+
{{callToActionTitle}}
+
{{callToActionText}}
+
+ +
+ `, + + // ╦ ╦╔═╗╔═╗╔═╗╦ ╦╔═╗╦ ╔═╗ + // ║ ║╠╣ ║╣ ║ ╚╦╝║ ║ ║╣ + // ╩═╝╩╚ ╚═╝╚═╝ ╩ ╚═╝╩═╝╚═╝ + beforeMount: function() { + + }, + mounted: async function() { + if (this.title) { + this.callToActionTitle = this.title; + } else { + throw new Error('Incomplete usage of : Please provide a `title` example: title="Secure laptops & servers"'); + } + if (this.text) { + this.callToActionText = this.text; + } else { + throw new Error('Incomplete usage of : Please provide a `text` example: text="Get up and running with a test environment of Fleet within minutes"'); + } + if (this.primaryButtonText) { + this.calltoActionPrimaryBtnText = this.primaryButtonText; + } else { + throw new Error('Incomplete usage of : Please provide a `primaryButtonText`. example: primary-button-text="Get started"'); + } + if (this.primaryButtonHref) { + this.calltoActionPrimaryBtnHref = this.primaryButtonHref; + } else { + throw new Error('Incomplete usage of : Please provide a `primaryButtonHref` example: primary-button-href="/get-started?try-it-now"'); + } + if (this.secondaryButtonText) { + this.calltoActionSecondaryBtnText = this.secondaryButtonText; + } + if (this.secondaryButtonHref) { + this.calltoActionSecondaryBtnHref = this.secondaryButtonHref; + } + }, + watch: { + title: function(unused) { throw new Error('Changes to `title` are not currently supported in !'); }, + text: function(unused) { throw new Error('Changes to `text` are not currently supported in !'); }, + primaryButtonText: function(unused) { throw new Error('Changes to `primaryButtonText` are not currently supported in !'); }, + primaryButtonHref: function(unused) { throw new Error('Changes to `primaryButtonHref` are not currently supported in !'); }, + secondaryButtonText: function(unused) { throw new Error('Changes to `secondaryButtonText` are not currently supported in !'); }, + secondaryButtonHref: function(unused) { throw new Error('Changes to `secondaryButtonHref` are not currently supported in !'); }, + }, + beforeDestroy: function() { + //… + }, + + // ╦╔╗╔╔╦╗╔═╗╦═╗╔═╗╔═╗╔╦╗╦╔═╗╔╗╔╔═╗ + // ║║║║ ║ ║╣ ╠╦╝╠═╣║ ║ ║║ ║║║║╚═╗ + // ╩╝╚╝ ╩ ╚═╝╩╚═╩ ╩╚═╝ ╩ ╩╚═╝╝╚╝╚═╝ + methods: { + //… + } +}); diff --git a/website/assets/styles/components/call-to-action.component.less b/website/assets/styles/components/call-to-action.component.less new file mode 100644 index 000000000000..b72b73f4f431 --- /dev/null +++ b/website/assets/styles/components/call-to-action.component.less @@ -0,0 +1,88 @@ + +/** + * + * + * App-wide styles for our component. + */ +[parasails-component='call-to-action'] { + background-image: url('/images/call-to-action-banner-background.svg'); + background-position-x: center; + background-size: cover; + background-color: #192147; + padding: 60px 90px; + border-radius: 16px; + margin-top: 40px; + margin-bottom: 40px; + + [purpose='cta-content'] { + color: #FFF; + margin-bottom: 24px; + [purpose='cta-title'] { + font-weight: 900; + font-size: 28px; + line-height: 40px; + margin-bottom: 4px; + } + [purpose='cta-text'] { + font-size: 18px; + line-height: 28px; + margin-bottom: 0px; + } + } + + [purpose='cta-buttons'] { + [purpose='primary-button'] { + padding: 16px 63px; + } + [purpose='secondary-button'] { + .btn-animated-arrow-red(); + } + } + + @media(max-width: 991px) { + padding: 60px 45px; + [purpose='cta-content'] { + [purpose='cta-title'] { + font-weight: 900; + font-size: 24px; + line-height: 32px; + margin-bottom: 4px; + } + [purpose='cta-text'] { + font-size: 16px; + line-height: 24px; + margin-bottom: 0px; + } + } + [purpose='cta-buttons'] { + [purpose='primary-button'] { + padding: 16px 63px; + } + } + } + + @media(max-width: 576px) { + padding: 60px 24px; + margin-left: -16px; + margin-right: -16px; + [purpose='cta-buttons'] { + [purpose='primary-button'] { + padding: 16px 63px; + } + } + [purpose='cta-content'] { + + [purpose='cta-title'] { + font-weight: 900; + font-size: 24px; + line-height: 32px; + margin-bottom: 4px; + } + [purpose='cta-text'] { + font-size: 16px; + line-height: 24px; + margin-bottom: 0px; + } + } + } +} diff --git a/website/assets/styles/importer.less b/website/assets/styles/importer.less index 96b86709e9d7..824de2dad3a6 100644 --- a/website/assets/styles/importer.less +++ b/website/assets/styles/importer.less @@ -23,6 +23,7 @@ @import 'components/modal.component.less'; @import 'components/cloud-error.component.less'; @import 'components/bar-chart.component.less'; +@import 'components/call-to-action.component.less'; // Per-page styles @import 'pages/homepage.less'; diff --git a/website/scripts/build-static-content.js b/website/scripts/build-static-content.js index e3c4b5f5d3bb..736351bd70ce 100644 --- a/website/scripts/build-static-content.js +++ b/website/scripts/build-static-content.js @@ -200,6 +200,7 @@ module.exports = { // > • What about images referenced in markdown files? :: They need to be referenced using an absolute URL src-- e.g. ![](https://fleetdm.com/images/foo.png) See also https://github.com/fleetdm/fleet/issues/706#issuecomment-884641081 for reasoning. // > • What about GitHub-style emojis like `:white_check_mark:`? :: Use actual unicode emojis instead. Need to revisit this? Visit https://github.com/fleetdm/fleet/pull/1380/commits/19a6e5ffc70bf41569293db44100e976f3e2bda7 for more info. let mdString = await sails.helpers.fs.read(pageSourcePath); + mdString = mdString.replace(/(\n+])\n+(>)/g, '$1$2'); // « Removes any newlines that might exist before the closing `>` when the compontent is added to markdown files. mdString = mdString.replace(/(```)([a-zA-Z0-9\-]*)(\s*\n)/g, '$1\n' + '' + '$3'); // « Based on the github-flavored markdown's language annotation, (e.g. ```js```) add a temporary marker to code blocks that can be parsed post-md-compilation when this is HTML. Note: This is an HTML comment because it is easy to over-match and "accidentally" add it underneath each code block as well (being an HTML comment ensures it doesn't show up or break anything). For more information, see https://github.com/uncletammy/doc-templater/blob/2969726b598b39aa78648c5379e4d9503b65685e/lib/compile-markdown-tree-from-remote-git-repo.js#L198-L202 let htmlString = await sails.helpers.strings.toHtml(mdString); htmlString = (// « Add the appropriate class to the `` based on the temporary "LANG" markers that were just added above