diff --git a/Notebook.md b/Notebook.md index 51147c7..1841f12 100644 --- a/Notebook.md +++ b/Notebook.md @@ -115,7 +115,7 @@ We should use classes to make things easier later.

Projects

- +

Contact

@@ -408,6 +408,7 @@ For the projects section I want to highlight two personal projects, maybe includ To accomplish stacking the different projet sections I am going to introduce some grid organization into the projects section. Withe simple CSS we can achieve a nice staked layout within our projects section. **CSS** + ``` .grid-container { display: grid; @@ -427,13 +428,15 @@ To accomplish stacking the different projet sections I am going to introduce som align-items: center; } ``` + **HTML** + ```

Personal Projects

- +
@@ -448,7 +451,7 @@ To accomplish stacking the different projet sections I am going to introduce som

LunaLight - Teaser

- +
@@ -476,7 +479,7 @@ Now let's get into the interactive project components The first project highlight will be for my personal retro game project and include an imbedded you tube video as the interactive component. To help with this I'll be referencing som eof the infomation here: [HTML YouTube Videos](https://www.w3schools.com/html/html_youtube.asp). -So we'll be using a component called `iframe` which allows us to embed video and set many useful attributes. +So we'll be using a component called `iframe` which allows us to embed video and set many useful attributes. As it turns out, if you click share on a YouTube video there is on option for "embed"! You can simply copy and paste it into your HTML! @@ -524,8 +527,7 @@ In this section I want to showcase a really cool program I built that generates To showcase this I would like to create a user form that allows the user to input the parameters and the hit a button that says "generate". As the program runs it will give some indication as to what it is doing and play each waveform. It will then prompt the user if they woudl like to save the generated wav file. -*This is actually going to be quite difficult I think... To be continued...* - +_This is actually going to be quite difficult I think... To be continued..._ --- @@ -533,7 +535,7 @@ To showcase this I would like to create a user form that allows the user to inpu **12/07/2024** -For this section I am going to keep things relatively simple. I also think ths will be a good case for the use of cards. There will be three cards that give a brief overview of my experiences at a few of my favorite past work experiences. In addition each card wil act as a button to open a link to the relevant linked-in page for each of the work experiences. +For this section I am going to keep things relatively simple. I also think ths will be a good case for the use of cards. There will be three cards that give a brief overview of my experiences at a few of my favorite past work experiences. In addition each card wil act as a button to open a link to the relevant linked-in page for each of the work experiences. ```
@@ -563,7 +565,7 @@ For this section I am going to keep things relatively simple. I also think ths w
``` -To make each card a link I can add an `` tag element, +To make each card a link I can add an `` tag element, ``` @@ -576,7 +578,6 @@ To make each card a link I can add an `` tag element, and add the following CSS to create a nice effect when hovering above each card. - ``` .work-card-link { text-decoration: none; @@ -596,15 +597,15 @@ and add the following CSS to create a nice effect when hovering above each card. **12/07/2024** -Here the user should be prompted to enter their email and a message if they would like to collaborate or work. +Here the user should be prompted to enter their email and a message if they would like to collaborate or work. We will use a simple form that allows input for an email and a message. The form will have a submit button and reset button a well a validation. Submitting the message should validate user input and send an email to my preferred email with their contact info and message. Resetting should clear the form. -So how do we send an email from the form? We also need to think about deployment to github pages. Here is a good stack about email options when deploying to GH pages. +So how do we send an email from the form? We also need to think about deployment to github pages. Here is a good stack about email options when deploying to GH pages. - [Stack Overflow - Email from GitHub Pages](https://stackoverflow.com/questions/24348223/send-email-from-static-page-hosted-on-github-pages) -In this various people discuss options and honestly I thinkthe best option would be to use a third party service. +In this various people discuss options and honestly I thinkthe best option would be to use a third party service. Here are some options: @@ -628,10 +629,10 @@ We can now build our `html` form section and include our email server configurat
- + - +
@@ -646,7 +647,7 @@ This works really well just as html however there are some things that I think n - Successful submission redirects to a formspree confirmation screen. - When returning to our site, the form is not cleared -Formspree includes an option to disable the redirect if you upgade to a paid account.. we don't want to do that. Instead we can fix these issues by taking control of what happens on submit action via JavaScript. We can submit the form using the fetch API and catch the response. We will want to handle potential errors as well as communciate to the user success or fail. We will use a simple alert message for both. On success, we will reset the form. +Formspree includes an option to disable the redirect if you upgade to a paid account.. we don't want to do that. Instead we can fix these issues by taking control of what happens on submit action via JavaScript. We can submit the form using the fetch API and catch the response. We will want to handle potential errors as well as communciate to the user success or fail. We will use a simple alert message for both. On success, we will reset the form. ``` // On contact submit @@ -674,7 +675,7 @@ document.getElementById("contact-form").addEventListener("submit", async functio } } catch (error) { // Log any errors - console.error("Error:", error); + console.error("Error:", error); alert("There was a problem submitting your form. Please try again later."); } }); @@ -700,8 +701,12 @@ Although this would be really cool I've decided it is outside the scope of this **12/08/2024** -Another fun idea I had that is defintely within the scope is to create a parallaxing background. I think this will give a really cool user experience and highlight my love of game development. +Another fun idea I had that is defintely within the scope is to create a parallax background. I think this will give a really cool user experience and highlight my love of art and game development. -As the user scrolls to the bottom of the page there will be layered background elements that move at different speeds giving the effect that the view is descending into a pixel at view of the background. The parallaxing will give a depth and movement effect that will be fun for the user experience. +As the user scrolls to the bottom of the page there will be layered background elements that move at different speeds giving the effect that the view is descending into a pixel art view of the background. The parallaxing will give a depth and movement effect that will be fun for the user experience. -We have already done some of the work for this with our dynamic scrolling. \ No newline at end of file +We have already done some of the work for this with our dynamic scrolling. + +**The plan** + +We are going to create additional _background_ layers that will be layered on top of the actual background. We will update our JavaScript scroll event listener to control the scroll speed of each of these layers. Finally we will use CSS to ensure the layers are styled correctly to get our parallax effect. diff --git a/images/Bridge.png b/images/Bridge.png new file mode 100644 index 0000000..f4bbda4 Binary files /dev/null and b/images/Bridge.png differ diff --git a/images/Castle.png b/images/Castle.png new file mode 100644 index 0000000..b61bdf5 Binary files /dev/null and b/images/Castle.png differ diff --git a/images/Clouds.png b/images/Clouds.png index b5cb813..581c355 100644 Binary files a/images/Clouds.png and b/images/Clouds.png differ diff --git a/images/Moon.png b/images/Moon.png new file mode 100644 index 0000000..0ccf882 Binary files /dev/null and b/images/Moon.png differ diff --git a/images/Trees.png b/images/Trees.png new file mode 100644 index 0000000..27a7b50 Binary files /dev/null and b/images/Trees.png differ diff --git a/site.html b/site.html index c5d373e..b037c01 100644 --- a/site.html +++ b/site.html @@ -24,6 +24,7 @@ Projects Work Contact + Credits
@@ -113,7 +114,7 @@ >
- +
@@ -234,6 +235,13 @@
+
+
+
+

I made this website! Copyright Jesse M. Ellis 2024 😊

+
+
+
diff --git a/site.js b/site.js index 7c6db02..02a620e 100644 --- a/site.js +++ b/site.js @@ -14,22 +14,51 @@ document.addEventListener("DOMContentLoaded", () => { const navBar = document.querySelector(".navbar"); const titleBox = document.querySelector(".title-box"); const aboutSection = document.querySelector("#about"); + const contactSection = document.querySelector("#contact"); const scrollY = window.scrollY; - const aboutTop = aboutSection.getBoundingClientRect().top + window.scrollY; + const aboutTop = aboutSection.getBoundingClientRect().top + scrollY; + const contactTop = contactSection.getBoundingClientRect().top + scrollY; const slowScrollRate = 0.5; - // move title-box if it's above the viewport and not yet touching about-section + // Get viewport height for parallax background offsets + const viewportHeight = window.innerHeight; + + // Move title-box if it's above the viewport and not yet touching about-section if (scrollY < aboutTop) { - const opacity = scrollY / aboutTop; - // adjust opacity of navbar - navBar.style.opacity = Math.min(0.7 + opacity, 1); - // Adjust position and opacity of title box + const opacity1 = scrollY / aboutTop; titleBox.style.transform = `translateY(${scrollY * slowScrollRate}px)`; - titleBox.style.opacity = Math.max(1 - opacity, 0); + titleBox.style.opacity = Math.max(1 - opacity1, 0); } else { titleBox.style.transform = "translateY(0)"; titleBox.style.opacity = 0; } + + // Adjust navbar opacity when below the contact section + const contactBottom = contactTop + contactSection.offsetHeight; + if (scrollY > contactBottom) { + // Calculate opacity based on how far below the contact section we are + const fadeDistance = 100; + const distanceBelow = scrollY - contactBottom; + const opacity2 = Math.max(1 - distanceBelow / fadeDistance, 0); + navBar.style.opacity = opacity2; + } else { + navBar.style.opacity = 1; + } + + // Parallax background scroll rates + const body = document.body; + const bridgeScrollRate = 0.4; + const treesScrollRate = 0.5; + const castleScrollRate = 0.7; + const cloudsScrollRate = 0.9; + + body.style.backgroundPosition = ` + left ${scrollY * bridgeScrollRate + viewportHeight * 3.05}px, + left ${scrollY * treesScrollRate + viewportHeight * 2.55}px, + left ${scrollY * castleScrollRate + viewportHeight * 1.5}px, + left ${scrollY * cloudsScrollRate + viewportHeight * 0.4}px, + left 0px + `; }); // Function to load text from a file into an html component diff --git a/style.css b/style.css index ddcf60e..c90d65b 100644 --- a/style.css +++ b/style.css @@ -1,10 +1,13 @@ body { margin: 0; font-family: Arial, sans-serif; - background-image: url("../images/Clouds.png"); - background-size: cover; - background-position: left; - background-attachment: fixed; + background-image: url("../images/Bridge.png"), url("../images/Trees.png"), + url("../images/Castle.png"), url("../images/Clouds.png"), + url("../images/Moon.png"); + background-size: auto, auto, auto, auto, cover; + background-repeat: no-repeat, no-repeat, no-repeat, no-repeat, no-repeat; + background-attachment: scroll, scroll, scroll, scroll, fixed; + background-position: left 300vh, left 300vh, left 300vh, left 350vh, left top; min-width: 768px; } @@ -66,8 +69,7 @@ body { margin-top: 2rem; } -.title-section, -.page-bottom-section { +.title-section { position: relative; height: 70vh; display: flex; @@ -77,6 +79,26 @@ body { align-items: center; } +.page-bottom-section { + height: 90vh; + margin-top: 3rem; +} + +.credits-section { + display: flex; + justify-content: center; + align-items: center; +} + +.credits-box { + display: flex; + background: rgba(0, 0, 0, 1); + border-radius: 100px; + width: 400px; + padding: 10px; + margin-bottom: 2rem; +} + .title-box { display: flex; align-items: center; @@ -149,7 +171,7 @@ body { display: flex; margin-top: 10rem; gap: 2rem; - background: rgba(0, 0, 0, 0.9); + background: rgba(0, 0, 0, 0.8); border-radius: 20px; padding: 2rem; width: 95%; @@ -194,7 +216,7 @@ body { display: none; height: 400px; width: 95%; - margin: 10PX; + margin: 10px; justify-content: center; align-items: center; } @@ -248,13 +270,11 @@ button:hover { /* Projects Box */ - - .project-box { display: flex; margin-top: 10rem; gap: 2rem; - background: rgba(0, 0, 0, 0.9); + background: rgba(0, 0, 0, 0.8); border-radius: 20px; padding: 2rem; width: 95%; @@ -421,11 +441,12 @@ button:hover { font-weight: bold; } -.contact-form input, .contact-form textarea { +.contact-form input, +.contact-form textarea { padding: 10px; border: 1px solid #ccc; border-radius: 5px; - font-family: 'Courier New', Courier, monospace; + font-family: "Courier New", Courier, monospace; } .form-buttons { @@ -451,7 +472,6 @@ button[type="reset"] { color: white; } - /* Media Queries */ @media (min-width: 1440px) {