diff --git a/SUGGESTIONS.md b/SUGGESTIONS.md new file mode 100644 index 00000000..35bcc9b1 --- /dev/null +++ b/SUGGESTIONS.md @@ -0,0 +1,33 @@ +# Suggestions for Improving the Website + +## Easy Changes + +### Improve SEO and Performance +1. Optimize images by compressing them and using modern formats like WebP. +2. Implement lazy loading for images to improve page load times. +3. Add meta tags for better SEO. +4. Use a Content Delivery Network (CDN) to serve static assets faster. + +### Add More Interactive Elements +1. Add subtle CSS animations to existing components like buttons, images, and text. +2. Implement scroll animations to make elements appear as the user scrolls down the page. + +## Medium Changes + +### Add Dynamic Content with React State +1. Create a new interactive FAQ accordion component that expands and collapses answers when clicked. +2. Add a carousel component to showcase testimonials or case studies. + +### Add Interactive Forms and Modals +1. Enhance the existing contact form by adding form validation and interactive feedback messages. +2. Create a modal component that displays additional information or images when clicked. + +## Hard Changes + +### Advanced SEO and Performance Improvements +1. Implement server-side rendering (SSR) for better SEO and faster initial page loads. +2. Use code splitting to load only the necessary JavaScript for each page. + +### Advanced Interactive Elements +1. Add complex animations and transitions using libraries like Framer Motion. +2. Implement real-time features like live chat or notifications using WebSockets. diff --git a/gatsby-config.js b/gatsby-config.js index bc530ea7..5b73dc48 100644 --- a/gatsby-config.js +++ b/gatsby-config.js @@ -117,6 +117,37 @@ module.exports = { }, }, // must be after other CSS plugins 'gatsby-plugin-netlify', // make sure to keep it last in the array + { + resolve: 'gatsby-plugin-sharp', + options: { + defaults: { + formats: ['auto', 'webp', 'avif'], + placeholder: 'dominantColor', + quality: 50, + breakpoints: [750, 1080, 1366, 1920], + backgroundColor: 'transparent', + tracedSVGOptions: {}, + blurredOptions: {}, + jpgOptions: {}, + pngOptions: {}, + webpOptions: {}, + avifOptions: {}, + }, + }, + }, + { + resolve: 'gatsby-transformer-sharp', + options: { + // The option defaults to true + checkSupportedExtensions: true, + }, + }, + { + resolve: 'gatsby-image', + options: { + // Add any options here + }, + }, ], // for avoiding CORS while developing Netlify Functions locally // read more: https://www.gatsbyjs.org/docs/api-proxy/#advanced-proxying diff --git a/src/components/Carousel.js b/src/components/Carousel.js new file mode 100644 index 00000000..5d577215 --- /dev/null +++ b/src/components/Carousel.js @@ -0,0 +1,39 @@ +import React from 'react'; +import Slider from 'react-slick'; +import PropTypes from 'prop-types'; +import "slick-carousel/slick/slick.css"; +import "slick-carousel/slick/slick-theme.css"; + +const Carousel = ({ items }) => { + const settings = { + dots: true, + infinite: true, + speed: 500, + slidesToShow: 1, + slidesToScroll: 1, + autoplay: true, + autoplaySpeed: 3000, + }; + + return ( + + {items.map((item, index) => ( +
+

{item.title}

+

{item.content}

+
+ ))} +
+ ); +}; + +Carousel.propTypes = { + items: PropTypes.arrayOf( + PropTypes.shape({ + title: PropTypes.string.isRequired, + content: PropTypes.string.isRequired, + }) + ).isRequired, +}; + +export default Carousel; diff --git a/src/components/ContactUs.js b/src/components/ContactUs.js index 90ff3448..00723711 100644 --- a/src/components/ContactUs.js +++ b/src/components/ContactUs.js @@ -12,12 +12,50 @@ export default class ContactUs extends React.Component { super(props); this.submitForm = this.submitForm.bind(this); this.state = { - status: Status.Initial + status: Status.Initial, + name: '', + email: '', + message: '', + errors: { + name: '', + email: '', + message: '' + } }; } + validateForm() { + const { name, email, message } = this.state; + let errors = { name: '', email: '', message: '' }; + let formIsValid = true; + + if (!name) { + formIsValid = false; + errors.name = 'Name is required'; + } + + if (!email) { + formIsValid = false; + errors.email = 'Email is required'; + } else if (!/\S+@\S+\.\S+/.test(email)) { + formIsValid = false; + errors.email = 'Email is invalid'; + } + + if (!message) { + formIsValid = false; + errors.message = 'Message is required'; + } + + this.setState({ errors }); + return formIsValid; + } + submitForm(ev) { ev.preventDefault(); + if (!this.validateForm()) { + return; + } const form = ev.target; const data = new FormData(form); const xhr = new XMLHttpRequest(); @@ -36,7 +74,13 @@ export default class ContactUs extends React.Component { this.setState({status: Status.Processing}); } + handleChange = (event) => { + const { name, value } = event.target; + this.setState({ [name]: value }); + } + render() { + const { errors } = this.state; return

Contact Us

We respond to 100% of messages. Ask us anything.

@@ -47,20 +91,23 @@ export default class ContactUs extends React.Component {
-