diff --git a/02CSS/Day06/notes/notes.md b/02CSS/Day06/notes/notes.md
new file mode 100644
index 0000000..67c15c1
--- /dev/null
+++ b/02CSS/Day06/notes/notes.md
@@ -0,0 +1,440 @@
+# Lecture 06: Media query , Shadows and Overflow
+
+- [Lecture 06: Media query , Shadows and Overflow](#lecture-06-media-query--shadows-and-overflow)
+ - [Media Query](#media-query)
+ - [The First Principle: One Size Does Not Fit All](#the-first-principle-one-size-does-not-fit-all)
+ - [The Core Problem](#the-core-problem)
+ - [The Logical Solution: The Media Query](#the-logical-solution-the-media-query)
+ - [The Key Media Features: min-width and max-width](#the-key-media-features-min-width-and-max-width)
+ - [max-width (The "Desktop First" or "Shrinking" Logic)](#max-width-the-desktop-first-or-shrinking-logic)
+ - [min-width (The "Mobile First" or "Growing" Logic)](#min-width-the-mobile-first-or-growing-logic)
+ - [The Combined Form: Targeting a Specific Range](#the-combined-form-targeting-a-specific-range)
+ - [Box Shadows in CSS](#box-shadows-in-css)
+ - [The First Principle: Light Creates Shadow, Shadow Creates Depth](#the-first-principle-light-creates-shadow-shadow-creates-depth)
+ - [The Core Problem](#the-core-problem-1)
+ - [The Logical Solution: The box-shadow Property](#the-logical-solution-the-box-shadow-property)
+ - [Step 1: offsetX and offsetY (The Position of the Light Source)](#step-1-offsetx-and-offsety-the-position-of-the-light-source)
+ - [Step 2: blurRadius (The Key to Realism)](#step-2-blurradius-the-key-to-realism)
+ - [Step 3: color with rgba() (The Secret to Subtlety)](#step-3-color-with-rgba-the-secret-to-subtlety)
+ - [Step 4: spreadRadius (Controlling the Size)](#step-4-spreadradius-controlling-the-size)
+ - [Step 5: inset (Flipping the Shadow)](#step-5-inset-flipping-the-shadow)
+ - [Multiple Shadows](#multiple-shadows)
+ - [Overflow in CSS](#overflow-in-css)
+ - [The First Principle: A Box Has a Fixed Size, But Content is Fluid](#the-first-principle-a-box-has-a-fixed-size-but-content-is-fluid)
+ - [The Core Problem: The Inevitable Conflict](#the-core-problem-the-inevitable-conflict)
+ - [The Logical Solution: The overflow Property](#the-logical-solution-the-overflow-property)
+ - [The Four overflow Values](#the-four-overflow-values)
+ - [1. overflow: visible; (The Default)](#1-overflow-visible-the-default)
+ - [2. overflow: hidden;](#2-overflow-hidden)
+ - [3. overflow: scroll;](#3-overflow-scroll)
+ - [4. overflow: auto; (The Smart and Common Choice)](#4-overflow-auto-the-smart-and-common-choice)
+ - [Controlling Axes Independently: overflow-x and overflow-y](#controlling-axes-independently-overflow-x-and-overflow-y)
+
+
+
+
+## Media Query
+
+### The First Principle: One Size Does Not Fit All
+
+The most fundamental truth of modern web design is that your website will be viewed on an incredible variety of screens. A design that is optimized for a 27-inch desktop monitor is fundamentally unusable on a 6-inch phone screen held vertically.
+
+This is not a failure of design; it is a physical reality. The context in which the user is viewing your content has changed dramatically.
+
+### The Core Problem
+
+How do we create a single website that can **adapt its layout** to provide an optimal experience for all these different contexts?
+
+- A simple, single-column layout is perfect for a narrow phone screen.
+- A two-column layout might be ideal for a tablet.
+- A three-column layout might make the best use of space on a wide desktop monitor.
+
+We need a mechanism within CSS to apply different styling rules based on the properties of the device rendering the page, most importantly, the **width of the browser's viewport**. We need an "if-then" statement for our styles.
+
+### The Logical Solution: The Media Query
+
+The @media rule is CSS's native "if-then" statement. It creates a conditional block. The CSS rules inside this block will **only be applied if the condition is met**.
+
+The syntax logically breaks down into three parts:
+
+@media media-type and (media-feature)
+
+1. **@media**: The "if." It tells the browser a conditional block is starting.
+2. **media-type**: "If the device is a..." screen, print, speech. We almost always use screen.
+3. **(media-feature)**: "and if it has this characteristic..." This is the actual condition.
+
+---
+
+### The Key Media Features: min-width and max-width
+
+The most critical "characteristic" we need to check is the viewport width.
+
+### max-width (The "Desktop First" or "Shrinking" Logic)
+
+- **The Question it Asks:** "Is the browser window **this width or smaller**?"
+- **The Logic:** You can think of it as setting an **upper bound**. The styles will apply from 0px up to the max-width you specify.
+- **Analogy:** "You must be **at most** 5 feet tall to ride this ride." Anyone 5'0" or shorter can ride.
+- **Use Case:** This is traditionally used in a "desktop-first" approach. You write your desktop styles first, and then use max-width media queries to "fix" the layout as the screen gets smaller. code CSS
+
+
+ ```css
+ /* --- Default styles (for desktop) --- */
+ .container {
+ grid-template-columns: 1fr 1fr 1fr; /* 3 columns */
+ }
+
+ /* --- Tablet styles --- */
+ @media screen and (max-width: 1024px) {
+ .container {
+ grid-template-columns: 1fr 1fr; /* Change to 2 columns */
+ }
+ }
+
+ /* --- Mobile styles --- */
+ @media screen and (max-width: 767px) {
+ .container {
+ grid-template-columns: 1fr; /* Change to 1 column */
+ }
+ }
+ ```
+
+
+### min-width (The "Mobile First" or "Growing" Logic)
+
+- **The Question it Asks:** "Is the browser window **this width or wider**?"
+- **The Logic:** You can think of it as setting a **lower bound**. The styles will apply from the min-width you specify up to infinity.
+- **Analogy:** "You must be **at least** 5 feet tall to ride this ride." Anyone 5'0" or taller can ride.
+- **Use Case:** This is the cornerstone of the modern "mobile-first" approach. You write simple, single-column mobile styles first, and then use min-width to add complexity as the screen gets larger. code CSS
+
+
+ ```css
+ /* --- Default styles (for mobile) --- */
+ .container {
+ grid-template-columns: 1fr; /* 1 column by default */
+ }
+
+ /* --- Tablet styles AND UP --- */
+ @media screen and (min-width: 768px) {
+ .container {
+ grid-template-columns: 1fr 1fr; /* Become 2 columns */
+ }
+ }
+
+ /* --- Desktop styles AND UP --- */
+ @media screen and (min-width: 1024px) {
+ .container {
+ grid-template-columns: 1fr 1fr 1fr; /* Become 3 columns */
+ }
+ }
+ ```
+
+
+This approach is generally cleaner and more efficient.
+
+---
+
+### The Combined Form: Targeting a Specific Range
+
+- **The Core Problem:** The rules above apply from a certain point "and up" or "and down". What if we want to apply styles **only to a specific range**, like a tablet in portrait mode? We need a way to combine a min-width and a max-width.
+- **The Logical Solution:** Use the and keyword to chain multiple conditions together. The styles will only apply if **ALL conditions are true**.
+- **The Syntax:**
+
+ @media screen and (min-width: [smaller-value]) and (max-width: [larger-value])
+
+- **The Question it Asks:** "Is the browser window **wider than the min value AND narrower than the max value**?"
+- **Analogy:** "To get this discount, you must be **at least 18 years old AND at most 25 years old**." You must satisfy both conditions.
+- **Example: Targeting a "Tablet" Viewport Range** code CSS
+
+ Let's say we want a special layout *only* for screens between 768px and 1023px wide.
+
+ ```css
+ /* Default (Mobile) styles */
+ .sidebar {
+ display: none; /* Hide the sidebar on mobile */
+ }
+
+ /* Tablet-only styles */
+ @media screen and (min-width: 768px) and (max-width: 1023px) {
+ body {
+ background-color: lightgoldenrodyellow; /* Give a visual cue */
+ }
+ .container {
+ grid-template-columns: 1fr 1fr; /* A two-column layout */
+ }
+ .sidebar {
+ display: block; /* Show the sidebar */
+ }
+ }
+
+ /* Desktop and up styles */
+ @media screen and (min-width: 1024px) {
+ body {
+ background-color: white; /* Back to white */
+ }
+ .container {
+ grid-template-columns: 1fr 3fr; /* A different two-column layout */
+ }
+ .sidebar {
+ display: block; /* The sidebar is also visible here */
+ }
+ }
+ ```
+
+
+In this example, the yellow background will **only** appear when the screen width is between 768px and 1023px. This allows you to create highly specific styles for different "breakpoints" in your design, giving you complete control over the responsive experience.
+
+## Box Shadows in CSS
+
+### The First Principle: Light Creates Shadow, Shadow Creates Depth
+
+The most fundamental truth is that on a 2D screen, we don't have true depth. We can only **simulate** it. In the real world, our brains perceive depth based on how light interacts with objects. When an object is closer to you (or "floating" above a surface), it casts a shadow onto the surface behind it.
+
+The characteristics of this shadow (its position, softness, and darkness) give us powerful visual cues about the object's position in 3D space.
+
+### The Core Problem
+
+How do we, as developers, create a realistic, simulated shadow for our rectangular element "boxes"? A simple, hard-edged border doesn't create depth; it just creates an outline.
+
+We need a CSS property that can generate a shadow and give us precise control over its:
+
+1. **Position:** Where is the light source coming from?
+2. **Softness (Blur):** Is it a sharp, hard shadow from a direct light source, or a soft, diffuse shadow from an ambient light source?
+3. **Size (Spread):** How big is the shadow relative to the object?
+4. **Color & Transparency:** How dark and solid is the shadow?
+
+### The Logical Solution: The box-shadow Property
+
+The box-shadow property is the CSS solution. It's a highly versatile property that allows you to "paint" a shadow based on the shape of an element's box.
+
+Let's build a realistic shadow step-by-step, understanding the logic of each value in its syntax.
+
+**The Full Syntax:** box-shadow: [inset] offsetX offsetY blurRadius spreadRadius color;
+
+---
+
+### Step 1: offsetX and offsetY (The Position of the Light Source)
+
+- **The Problem:** We need to tell the browser where to place the shadow relative to the element.
+- **The Logic:** We define the shadow's position with two values: a horizontal offset (offsetX) and a vertical offset (offsetY).
+ - offsetX: A positive value pushes the shadow to the **right**. A negative value pushes it to the **left**.
+ - offsetY: A positive value pushes the shadow **down**. A negative value pushes it **up**.
+- **The "Hard Shadow" (Our Starting Point):** Let's start with a simple, hard-edged shadow. We'll omit the blur and spread for now. code CSS
+
+
+ ```css
+ .box {
+ box-shadow: 10px 5px black;
+ }
+ ```
+
+ - **Result:** This creates a solid black copy of the box, shifted 10px to the right and 5px down. It looks very fake and unnatural, like a bad 90s graphic effect. This tells us that position alone is not enough.
+
+---
+
+### Step 2: blurRadius (The Key to Realism)
+
+- **The Problem:** The hard shadow looks fake because real-world shadows have soft, blurry edges.
+- **The Logic:** We need a value to control the "softness" or "diffusion" of the shadow. This is the blurRadius.
+ - A value of 0 (the default if omitted) means a perfectly sharp edge.
+ - A larger value (e.g., 15px) tells the browser to apply a Gaussian blur algorithm over a 15px radius, making the shadow's edges soft and faded.
+- **Improving Our Shadow:** code CSS
+
+
+ ```css
+ .box {
+ box-shadow: 10px 5px 15px black;
+ }
+ ```
+
+ - **Result:** This is a huge improvement. The shadow now has soft, fuzzy edges and looks much more like it's being cast by a real object.
+
+---
+
+### Step 3: color with rgba() (The Secret to Subtlety)
+
+- **The Problem:** Our blurred shadow is still pure black, which is very harsh. Real shadows are not completely opaque; they are semi-transparent, allowing the color of the surface behind them to show through.
+- **The Logic:** We need to define the shadow's color using a format that supports transparency. This is the perfect use case for rgba().
+- **Creating a Modern, Subtle Shadow:** code CSS
+
+
+ ```css
+ .box {
+ /* A small offset, a nice blur, and a light, transparent black */
+ box-shadow: 0px 4px 15px rgba(0, 0, 0, 0.1);
+ }
+ ```
+
+ - **Result:** This is the style of shadow you see on most modern websites (like Google's Material Design). It's subtle, soft, and feels natural. The 0px horizontal offset often makes it look like the light is coming directly from above. The rgba(0, 0, 0, 0.1) creates a black shadow that is only 10% opaque.
+
+---
+
+### Step 4: spreadRadius (Controlling the Size)
+
+- **The Problem:** What if we want the shadow to be bigger or smaller than the element itself *before* the blur is applied?
+- **The Logic:** We add an optional spreadRadius value.
+ - A positive value (e.g., 5px) will expand the shadow, making it 5px bigger on all sides *before* the blur. This creates a larger, more prominent shadow.
+ - A negative value (e.g., -5px) will contract the shadow, making it smaller than the element. This can create a subtle "inner glow" effect.
+- **Example:** code CSS
+
+
+ ```css
+ .box {
+ /* A large, diffuse "glow" effect */
+ box-shadow: 0 0 20px 5px rgba(0, 150, 255, 0.5);
+ }
+ ```
+
+
+---
+
+### Step 5: inset (Flipping the Shadow)
+
+- **The Problem:** All our shadows so far are "drop shadows," appearing *behind* the element. How do we make an element look like it's pressed *into* the page?
+- **The Logic:** Create a keyword that flips the shadow to be drawn on the **inside** of the element's border instead of the outside. This is the inset keyword.
+- **Example:** code CSS
+
+
+ ```css
+ .input-field:focus {
+ /* Creates a subtle inner shadow to show the field is active */
+ box-shadow: inset 0px 2px 4px rgba(0, 0, 0, 0.1);
+ }
+ ```
+
+
+### Multiple Shadows
+
+Finally, the box-shadow property is extra powerful because you can apply **multiple shadows** to the same element by separating them with a comma. This is how designers create incredibly realistic and nuanced depth effects.
+
+code CSS
+
+```css
+.card {
+ /* A short, subtle shadow right underneath */
+ box-shadow: 0 1px 3px rgba(0,0,0,0.12),
+ /* A longer, softer shadow for ambient depth */
+ 0 1px 2px rgba(0,0,0,0.24);
+}
+```
+
+By understanding these five components and how they build on each other, your students can move from creating fake, hard-edged shadows to crafting the subtle, realistic depth that defines modern web design.
+
+## Overflow in CSS
+
+### The First Principle: A Box Has a Fixed Size, But Content is Fluid
+
+The most fundamental truth is that when you define a box in CSS (like a
), you often give it a specific width and height. You are creating a container with finite boundaries.
+
+However, the content you put inside that box (text, images, etc.) is fluid. You might have a short paragraph or a very long one. You can't always know in advance how much content a box will need to hold.
+
+### The Core Problem: The Inevitable Conflict
+
+This leads to an inevitable conflict: **What happens when the content is bigger than the box it's supposed to fit in?**
+
+You have a box that is 200px tall, but you place a paragraph inside it that needs 400px of vertical space to be displayed. The content is "overflowing" its container.
+
+The browser cannot just delete the extra content—its primary job is to display everything. And it cannot magically resize the box if you've explicitly told it to be 200px tall. So, what should it do?
+
+### The Logical Solution: The overflow Property
+
+To solve this, CSS provides a property that lets you, the developer, take control and decide exactly how the browser should handle this "overflowing" content. This is the **overflow** property.
+
+Let's explore the four main choices you can make, using a clear analogy.
+
+**The Analogy:** An Overfilled Cup of Water
+
+- **The Box:** A glass cup with a fixed size.
+- **The Content:** The water you are pouring into it.
+- **Overflow:** When you pour in more water than the cup can hold.
+
+---
+
+### The Four overflow Values
+
+### 1. overflow: visible; (The Default)
+
+- **What it does:** The content simply **spills out** of the box's boundaries. It will render on top of any other elements that come after it, often breaking the layout of your page.
+- **Analogy:** The water overflows the cup and spills all over the table, making a mess and getting on top of other things on the table.
+- **Why is this the default?** The browser's #1 priority is to **show the user all the content**. It would rather make the layout look messy than hide information from the user by default. This is a safe, if sometimes ugly, starting point.
+
+**Example:**
+
+```css
+.box {
+ height: 100px;
+ overflow: visible; /* Default behavior */
+}
+```
+
+**Result:** The text will start inside the box and then continue flowing down the page, potentially covering up the content that comes after it.
+
+---
+
+### 2. overflow: hidden;
+
+- **What it does:** The content is **clipped** at the boundaries of the box. Anything that overflows is simply cut off and becomes invisible and inaccessible.
+- **Analogy:** You put a flat lid on the overflowing cup. The extra water is still in there, but it's completely hidden, and you can't get to it.
+- **When to use it:**
+ - To strictly enforce a design where nothing should ever break out of its container.
+ - To hide parts of an image for a "masking" effect.
+ - A very common use case: to contain child elements that have been positioned with position: absolute that might otherwise poke out of their parent container.
+
+**Example:**
+
+```css
+.box {
+ height: 100px;
+ overflow: hidden;
+}
+```
+
+**Result:** The user will only see the first few lines of text that fit within the 100px height. The rest of the paragraph will be gone.
+
+---
+
+### 3. overflow: scroll;
+
+- **What it does:** The content is clipped, but the browser adds **scrollbars (both horizontal and vertical)** to the box, allowing the user to scroll and see the rest of the content.
+- **The "Gotcha":** This value adds the scrollbars **whether they are needed or not**. Even if the content fits perfectly, you will still see disabled scrollbar tracks, which can sometimes look clunky.
+- **Analogy:** The overflowing cup is placed in a special holder with scroll wheels on both the side and the bottom, allowing you to move the water's surface up/down and left/right. The wheels are always there.
+
+**Example:**
+
+```css
+.box {
+ height: 100px;
+ overflow: scroll;
+}
+```
+
+**Result:** A 100px tall box with a vertical scrollbar that allows the user to read the entire paragraph. A horizontal scrollbar will also be present, although it will be disabled if the text doesn't overflow horizontally.
+
+---
+
+### 4. overflow: auto; (The Smart and Common Choice)
+
+- **What it does:** This is the "smart" version of scroll. The browser will **only add scrollbars if and when they are actually needed**. If the content fits, no scrollbars appear. If it overflows vertically, only a vertical scrollbar appears.
+- **Analogy:** A "smart" holder that only makes the scroll wheels appear when the cup is actually overflowing. It's clean and efficient.
+- **When to use it:** This is the value you will use **95% of the time** when you want to create a scrollable area. It's perfect for chat windows, sidebars with long lists, code display blocks, or any container with dynamic content.
+
+**Example:**
+
+code CSS
+
+```css
+.box {
+ height: 100px;
+ overflow: auto;
+}
+```
+
+**Result:** If the text is short, it will look like a normal box. If the text is long, a vertical scrollbar will appear automatically. This is the most user-friendly and aesthetically pleasing option.
+
+### Controlling Axes Independently: overflow-x and overflow-y
+
+You can also control the overflow behavior for the horizontal (x) and vertical (y) axes separately.
+
+- overflow-x: scroll; will add a horizontal scrollbar.
+- overflow-y: hidden; will clip any vertical overflow.
+
+This is useful for specific cases, like creating a horizontally scrolling gallery of images.
\ No newline at end of file
diff --git a/02CSS/Day07/notes/notes.md b/02CSS/Day07/notes/notes.md
new file mode 100644
index 0000000..c4fd2c6
--- /dev/null
+++ b/02CSS/Day07/notes/notes.md
@@ -0,0 +1,220 @@
+# Lecture 07: Animation in CSS
+
+- [Lecture 07: Animation in CSS](#lecture-07-animation-in-css)
+ - [Part 1: What is an Animation? (The First Principle)](#part-1-what-is-an-animation-the-first-principle)
+ - [Part 2: Creating the Storyboard with @keyframes](#part-2-creating-the-storyboard-with-keyframes)
+ - [Part 3: Applying the Animation with the animation Property](#part-3-applying-the-animation-with-the-animation-property)
+ - [Part 4: Controlling the Animation's Repetition](#part-4-controlling-the-animations-repetition)
+ - [Part 5: Animating Size - A Practical "Progress Bar" Project](#part-5-animating-size---a-practical-progress-bar-project)
+
+
+
+
+
+
+### Part 1: What is an Animation? (The First Principle)
+
+- **The Fundamental Truth:** An animation is a **change in style over a period of time**.
+- **The Analogy: A Sunset**
+ - "Think about a sunset. At 6 PM, the sky is bright blue. This is the **start state**.
+ - By 7 PM, the sky is a deep orange. This is the **end state**.
+ - The sunset itself is the **animation**—the gradual, smooth change from blue to orange over the course of one hour (the **duration**)."
+- **The Core Problem:** A normal CSS rule, like .sky { background-color: blue; }, only defines a single moment in time. How do we describe the entire sunset from start to finish?
+- **The Logical Solution: A Two-Part System**
+
+ "CSS solves this by giving us a two-part system:"
+
+ 1. **The Storyboard (@keyframes):** "First, we describe the key moments of our story. We define what the sky looks like at the beginning and at the end. This 'storyboard' is called a **@keyframes** rule."
+ 2. **The Director (animation property):** "Second, we tell an element (our 'sky') to perform this story. We use the **animation** property to give it directions, like how long the sunset should take."
+
+---
+
+### Part 2: Creating the Storyboard with @keyframes
+
+- **The First Principle:** An animation is defined by its key states. The simplest animation has a beginning and an end.
+- **The Syntax:** code CSS
+
+ ```css
+ @keyframes animation-name {
+ from { /* Start styles */ }
+ to { /* End styles */ }
+ }
+ ```
+
+ - **@keyframes**: The special command to start defining an animation.
+ - **animation-name**: A name you invent for your storyboard.
+- **Practical Example: The "Sunset" Animation** code CSS
+
+ Let's create the storyboard for our sunset. We will animate the background-color.
+
+ ```css
+ @keyframes sunset-effect {
+ from {
+ background-color: #87CEEB; /* A bright Sky Blue */
+ }
+ to {
+ background-color: #FF4500; /* A deep OrangeRed */
+ }
+ }
+ ```
+
+ - **Explain:** "This storyboard is named sunset-effect. It tells a simple story: start as sky blue, end as orange-red. The browser will automatically figure out all the in-between colors to make the change smooth."
+
+---
+
+### Part 3: Applying the Animation with the animation Property
+
+- **The First Principle:** A storyboard needs an element to apply it to.
+- **The Core Problem:** How do we tell our
to use the sunset-effect storyboard, and how long should it take?
+- **The Solution:** The animation property (and its individual parts).
+- **Building it up Step-by-Step:** code Html code CSS
+
+
+ ```css
+
+ ```
+
+ ```css
+ /* Don't forget to include the @keyframes rule from above! */
+
+ .sky {
+ height: 200px;
+ width: 200px;
+ background-color: #87CEEB; /* The starting color */
+
+ /* --- Let's give our director the instructions --- */
+
+ /* 1. Which storyboard to use? (Required) */
+ animation-name: sunset-effect;
+
+ /* 2. How long should the animation take? (Required) */
+ animation-duration: 5s; /* 5 seconds */
+ }
+ ```
+
+ - **Result (Live Demo):** When the page loads, the box will start as sky blue and smoothly change to orange-red over 5 seconds. But then it stops.
+
+---
+
+### Part 4: Controlling the Animation's Repetition
+
+- **The Problem:** The animation only plays once. How do we make it loop or go back and forth?
+- **The Solution:** Introduce two new "director's instructions."
+ 1. **animation-iteration-count (How Many Times?):**
+ - Controls how many times the animation repeats.
+ - **infinite**: The keyword for a loop that never ends.
+
+ ```css
+ .sky {
+ /* ... other animation properties ... */
+ animation-iteration-count: infinite;
+ }
+ ```
+
+ - **Result:** The box will animate from blue to orange, then instantly **snap back** to blue and start over, forever. This snap is jarring.
+ 2. **animation-direction (How to Loop Smoothly?):**
+ - **The Problem:** The "snap back" at the end of the loop doesn't look like a real sunset and sunrise. We need it to animate backwards smoothly.
+ - **The Solution:** The alternate value.
+ - **alternate**: This tells the animation to play forwards (from -> to) on the first run, then backwards (to -> from) on the second run, and so on.
+ - **Example:** code CSS
+
+ ```css
+ .sky {
+ /* ... other animation properties ... */
+ animation-iteration-count: infinite;
+ animation-direction: alternate;
+ }
+ ```
+
+ - **Result:** A perfect day/night cycle. The box will smoothly animate from blue to orange (the sunset), and then smoothly back from orange to blue (the sunrise), forever.
+
+---
+
+### Part 5: Animating Size - A Practical "Progress Bar" Project
+
+*This project introduces animating a different property, width, and the concept of what happens after an animation ends.*
+
+- **The Goal:** Create a bar that fills up from left to right, once.
+- **HTML:** A container
and a fill
. code Html
+
+
+ ```css
+
+ ```
+
+- **The CSS Storyboard:** code CSS
+
+
+ ```css
+ @keyframes fill-the-bar {
+ from {
+ width: 0%;
+ }
+ to {
+ width: 100%;
+ }
+ }
+ ```
+
+- **The CSS Director's Instructions:** code CSS
+
+
+ ```css
+ .progress-fill {
+ height: 30px;
+ background-color: #4CAF50; /* Green */
+ width: 0; /* Important: It starts at 0 width */
+
+ animation-name: fill-the-bar;
+ animation-duration: 4s;
+
+ /* What happens when it's done? */
+ animation-fill-mode: forwards;
+ }
+ ```
+
+- **Introducing animation-fill-mode:**
+ - **The Problem:** By default, once our 4-second animation is over, the .progress-fill element will snap back to its original style (width: 0;). The bar would fill up and then instantly become empty again.
+ - **The Solution:** animation-fill-mode: forwards;. This is a crucial instruction that tells the browser: "After the animation is finished, **keep the styles from the final (to) keyframe**."
+ - **Result:** The progress bar animates from 0% to 100% width and then **stays full**.
+
+
+
+
+ | fill-mode |
+ Behavior During delay |
+ Behavior After Animation Ends |
+ Use Case |
+
+
+
+
+ | none (Default) |
+ Shows element's resting style. |
+ Reverts to element's resting style. |
+ Simple looping animations where the start/end states match. |
+
+
+ | forwards |
+ Shows element's resting style. |
+ Retains the last keyframe's style. |
+ Animations that need to "stick" in their final state (e.g., a fade-out). |
+
+
+ | backwards |
+ Applies the first keyframe's style. |
+ Reverts to element's resting style. |
+ Animations with a delay that need a specific starting state (e.g., a fade-in). |
+
+
+ | both |
+ Applies the first keyframe's style. |
+ Retains the last keyframe's style. |
+ The "all-in-one" solution for delayed, one-shot animation |
+
+
+
+
+
\ No newline at end of file
diff --git a/02CSS/Day08/notes/notes.md b/02CSS/Day08/notes/notes.md
new file mode 100644
index 0000000..9a8151e
--- /dev/null
+++ b/02CSS/Day08/notes/notes.md
@@ -0,0 +1,140 @@
+# Lecture 08: CSS Transition and transformation
+
+- [Lecture 08: CSS Transition and transformation](#lecture-08-css-transition-and-transformation)
+ - [Part 1 - The transform Property - The Change](#part-1---thetransformproperty---the-change)
+ - [Part 2 - The transition Property - The Smoothness](#part-2---thetransitionproperty---the-smoothness)
+ - [Part 3 - Practical Example - The Interactive "Lifting Card"](#part-3---practical-example---the-interactive-lifting-card)
+
+### Part 1 - The transform Property - The Change
+
+- **First Principle:** We need a way to visually alter an element (move, resize, rotate) **without** disrupting the layout of the elements around it.
+- **Analogy:** Using margin to move an element is like shoving someone in a crowded line—everyone else has to shift. Using transform is like that person levitating up and moving—no one else in the line is affected. It's much smoother and more efficient for the browser.
+
+The transform property applies a function to an element *after* the page layout is calculated.
+
+**The 4 Core Transform Functions:**
+
+**1. translate() - To Move**
+
+Moves an element along the X (horizontal) and/or Y (vertical) axis.
+
+- **transform: translateX(50px);** // Moves 50px to the right.
+- **transform: translateY(-20px);** // Moves 20px up.
+- **transform: translate(50px, -20px);** // Moves 50px right AND 20px up.
+
+**2. scale() - To Resize**
+
+Makes an element larger or smaller from its center point.
+
+- **transform: scale(1.2);** // Makes the element 20% larger.
+- **transform: scale(0.9);** // Makes the element 10% smaller.
+
+**3. rotate() - To Turn**
+
+Rotates an element around its center point.
+
+- **transform: rotate(45deg);** // Rotates 45 degrees clockwise.
+- **transform: rotate(-10deg);** // Rotates 10 degrees counter-clockwise.
+
+**4. skew() - To Distort**
+
+Slants an element along an axis.
+
+- **transform: skewX(15deg);** // Slants horizontally.
+
+**Combining Transforms:** You can apply multiple functions in one line. The order matters!
+
+transform: translateX(50px) rotate(10deg) scale(1.2);
+
+---
+
+### Part 2 - The transition Property - The Smoothness
+
+- **First Principle:** Changes on a webpage should feel natural, not instant. A door swings open; it doesn't teleport. A transition is what makes a change in style happen smoothly over time.
+- **The Core Problem:** When you use a pseudo-class like :hover to change a style, the change is instant and jarring.
+
+ ```css
+ .button:hover { background-color: red; } /* Instantly snaps to red */
+ ```
+
+- **The Solution:** The transition property. You apply it to the **base element** (not the :hover state). It tells the browser to "watch" for changes and animate them smoothly.
+
+**The Anatomy of a transition:**
+
+The transition property is a shorthand for four sub-properties. The syntax is:
+
+transition: property duration timing-function delay;
+
+**1. transition-property (What to Animate)**
+
+The CSS property you want to animate.
+
+- **background-color**: Animates only the background color.
+- **transform**: Animates only the transform.
+- **all**: (Most common) Animates any property that changes.
+
+**2. transition-duration (How Long)**
+
+The time the animation should take.
+
+- **0.3s** (0.3 seconds) or **300ms** (300 milliseconds). Values between 0.2s and 0.5s feel the most natural for UI interactions.
+
+**3. transition-timing-function (The Pacing)**
+
+The "speed curve" of the animation.
+
+- **ease**: (Default) Starts slow, speeds up, ends slow. Feels natural.
+- **linear**: A constant, robotic speed.
+- **ease-in-out**: A slightly more pronounced version of ease. A very popular choice.
+
+**4. transition-delay (When to Start)**
+
+An optional delay before the transition begins (e.g., 1s).
+
+---
+
+### Part 3 - Practical Example - The Interactive "Lifting Card"
+
+This project combines everything we've learned to create a professional UI effect.
+
+- **The Goal:** Create a card that smoothly "lifts" and grows when the user hovers over it.
+
+```html
+
+
Hover Over Me
+
See the smooth transition and transform effect.
+
+```
+
+-
+
+ ```css
+ .card {
+ width: 250px;
+ padding: 20px;
+ background-color: white;
+ border-radius: 8px;
+ box-shadow: 0 4px 8px rgba(0,0,0,0.1);
+
+ /*
+ * STEP 1: Add the transition instruction to the BASE state.
+ * We're telling it to watch the 'transform' and 'box-shadow' properties
+ * and animate any changes over 0.3 seconds.
+ */
+ transition: transform 0.3s ease-in-out, box-shadow 0.3s ease-in-out;
+ }
+
+ /*
+ * STEP 2: Define the 'hover' state.
+ * This is what we want the card to look like when the user's mouse is over it.
+ */
+ .card:hover {
+ /* Lifts the card up by 10 pixels */
+ transform: translateY(-10px);
+
+ /* Make the shadow larger and softer to enhance the "lifted" effect */
+ box-shadow: 0 10px 20px rgba(0,0,0,0.2);
+ }
+ ```
+
+- **How it Works:** When you hover, the browser sees the new transform and box-shadow styles in the :hover rule. Because the base .card rule has a transition property watching them, the browser doesn't snap to the new styles. Instead, it creates a smooth, 0.3-second animation to the new state. When you move the mouse away, it does the same thing in reverse.
\ No newline at end of file
diff --git a/03JS/Day09/index.js b/03JS/Day09/index.js
index 68f8519..e170bb5 100644
--- a/03JS/Day09/index.js
+++ b/03JS/Day09/index.js
@@ -130,8 +130,8 @@
// function meet(callback){
// console.log("I am going to meet someone");
-// // dance(); hardcode (Reusable)
-// // code hota jisko marta
+ // dance(); hardcode (Reusable)
+ // code hota jisko marta
// callback();
// console.log("I have finished meeting");
// }
diff --git a/03JS/notes/1-intro-to-js.md b/03JS/notes/1-intro-to-js.md
new file mode 100644
index 0000000..81e15c9
--- /dev/null
+++ b/03JS/notes/1-intro-to-js.md
@@ -0,0 +1,107 @@
+# Introduction to Javascript
+
+Developer know html and CSS, why do we need javascript
+
+1: We can’t put C++ in the browser , it’s too heavy, unsafe, and inaccessible. Our users are not kernel developers; they’re web authors who just learned `
` and ``. We need something lightweight, interpreted, forgiving, and safe.
+
+```cpp
+#include
+using namespace std;
+int main() {
+ cout << "Hello World";
+}
+
+```
+
+```jsx
+console.log("Hello World")
+```
+
+2: **Massive Security Nightmare:**
+
+- **Unrestricted Access:** C++ gives you low-level control over memory and system calls. If a browser ran arbitrary C++ code from a website, that code could easily:
+ - Read/write any file on your computer.
+ - Install malware.
+ - Access your webcam or microphone without permission.
+ - Crash your entire operating system.
+
+ ### 1. **File system access**
+
+ ```cpp
+ #include
+ std::ofstream file("C:\\Users\\rohit\\secrets.txt");
+ file << "stolen data";
+
+ ```
+
+ - Without sandboxing, this code could read/write/delete any file on your machine.
+ - In a sandboxed environment, you’d have to **intercept all file I/O** calls and either block them or restrict them to a safe “virtual” file system.
+
+ ---
+
+ ### 2. **System calls (executing programs)**
+
+ ```cpp
+ #include
+ system("rm -rf /"); // Linux
+ system("format C:"); // Windows 95 nightmare
+
+ ```
+
+ - Raw C++ can call `system()` to run OS commands.
+ - Sandboxing would mean completely **disabling or trapping** such calls, otherwise a website could literally wipe your drive.
+
+ ---
+
+ ### 3. **Direct memory access (pointers)**
+
+ ```cpp
+ int* p = (int*)0xB8000; // Access video memory
+ *p = 42;
+
+ ```
+
+ - C++ allows arbitrary pointer arithmetic → could overwrite OS/kernel memory or peek into sensitive regions.
+ - In a sandbox, you’d have to **rewrite the runtime** so pointers never escape into raw machine addresses.
+
+ ---
+
+ ### 4. **Networking**
+
+ ```cpp
+ #include
+ connect(...); // Open a raw socket to exfiltrate data
+
+ ```
+
+ - C++ can open arbitrary sockets, bypassing the browser’s control.
+ - Sandboxing would require blocking direct socket creation and only allowing **browser-controlled HTTP requests**.
+
+
+3: System Configurate was very less like 4-8mb ram, 200-400mb hard disk.
+
+### Typical Home PC Specs in 1995
+
+- **RAM:**
+ - Average consumer PCs had **4 MB to 8 MB** of RAM.
+ - Higher-end machines (for developers/enthusiasts) sometimes had **16 MB**.
+ - Anything beyond that was rare and expensive.
+- **Hard Disk:**
+ - Common sizes: **200 MB – 500 MB**.
+ - Higher-end PCs: **1 GB** drives were just starting to appear.
+ - Compare that to today’s **1 TB SSDs** 😅.
+- **CPU:**
+ - Intel **Pentium 75–133 MHz** was mainstream.
+ - 486 processors were still common in cheaper systems.
+
+---
+
+### 🔹 Why this mattered for C++ vs JS in browsers
+
+- Running a **sandboxed C++ runtime** would’ve eaten up tons of RAM and CPU → impossible when you only had 8 MB of RAM total, shared with Windows 95 and the browser itself.
+- Hard disks were small and slow → no space for large runtime environments or heavy libraries.
+- Browsers had to stay **lightweight** or else people simply wouldn’t use them.
+
+4: **Automatic Memory Management (Garbage Collection):**
+
+- Developers don't have to manually allocate and free memory. The JavaScript engine handles it, reducing complexity and preventing common bugs like memory leaks that plague manual memory management in C++.
\ No newline at end of file
diff --git a/03JS/notes/10-JS-Execution.md b/03JS/notes/10-JS-Execution.md
new file mode 100644
index 0000000..52ffeef
--- /dev/null
+++ b/03JS/notes/10-JS-Execution.md
@@ -0,0 +1,244 @@
+# Lecture 10: JS Code Execution
+
+## **The Fundamental Problem: Computers are Not Smart**
+
+The most important thing to remember is that a computer's processor (CPU) doesn't understand JavaScript. It only understands one thing: **Machine Code** (sequences of 1s and 0s).
+
+Our goal is to translate the human-friendly JavaScript we write into machine-friendly instructions. This translation job is done by the **JavaScript Engine**.
+
+**The JavaScript Engine:** A program that reads, translates, and executes JavaScript code. The most famous one is Google's **V8**, which powers Chrome and Node.js.
+
+### **The Engine's Two Core Components**
+
+To manage our code, the engine sets up two primary areas in memory:
+
+1. **The Memory Heap:** A large, unstructured pool of memory. Think of it as a giant warehouse where all the "things" (objects, arrays, and most importantly, functions) from your code are stored.
+2. **The Call Stack:** A highly organized, temporary workspace. Think of it as a to-do list where you can only add tasks to the top and can only work on the topmost task. It's responsible for managing which function is currently running.
+
+### **The Two-Phase Process: The Secret to "Hoisting"**
+
+The engine does not just read your code from top to bottom and run it. For any piece of code (the global script, a function), it performs a two-phase process.
+
+1. **Creation Phase (Memory Setup):** The engine takes a quick first pass through the code. It doesn't execute anything. Its only job is to find all the variable and function declarations and set aside memory for them.
+2. **Execution Phase (Doing the Work):** After the setup is complete, the engine takes a second pass to actually execute the code: assigning values to variables, calling functions, and running the logic.
+
+This two-phase process is what creates the effect we call **hoisting**.
+
+---
+
+### **A Detailed Walkthrough: From Code to Console**
+
+Let's trace the following code step-by-step to see every part of the process.
+
+**Our Code Example:**
+
+```jsx
+// script.js
+var score = 50;
+const playerName = "Alex";
+
+function calculateBonus(currentScore) {
+ var bonus = currentScore / 10;
+ return bonus;
+}
+
+var finalScore = score + calculateBonus(score);
+console.log(finalScore);
+
+```
+
+### **Step 0: The "Before You Run" Phase (Compilation)**
+
+Before anything else, the V8 engine takes our `script.js` file and compiles it.
+
+1. **Parsing:** The code is read and turned into a data structure called an **Abstract Syntax Tree (AST)**.
+2. **Compilation:** The AST is then compiled into **Bytecode**. This is a low-level set of instructions that the engine can execute very quickly. This bytecode is loaded into a special, executable area of memory called the **Code Space**.
+
+The engine will not be reading our text file during execution; it will be running this highly optimized bytecode.
+
+### **Step 1: Global Execution - The Creation Phase**
+
+The engine is now ready to run the global part of our script. It starts with the creation phase.
+
+1. A **Global Execution Context (GEC)** is created. This is the main environment for our script. It is pushed onto the **Call Stack**.
+2. The engine scans the global code for declarations:
+ - `var score;`: Finds this. In the GEC's memory, it creates a property `score` and initializes it with `undefined`.
+ - `const playerName;`: Finds this. It creates a `playerName` binding but leaves it in an **uninitialized** state. This is the start of its **Temporal Dead Zone (TDZ)**.
+ - `function calculateBonus(...)`: Finds this. This is special.
+ - A complete **Function Object** is created on the **Memory Heap**. This object contains the function's metadata and, crucially, a pointer to its executable bytecode in the Code Space.
+ - In the GEC's memory, a property `calculateBonus` is created and is immediately initialized with a pointer to that object on the Heap.
+ - `var finalScore;`: Finds this. Creates a `finalScore` property and initializes it with `undefined`.
+
+**Memory State After Global Creation:**
+
+- **Call Stack:** `[ GEC ]`
+- **Global Memory:** `score: undefined`, `playerName: `, `calculateBonus: `, `finalScore: undefined`
+- **Heap:** Contains the `calculateBonus` Function Object.
+
+### **Step 2: Global Execution - The Execution Phase**
+
+The engine now executes the global bytecode instructions.
+
+- `var score = 50;`
+ - The value `50` is assigned to `score` in global memory.
+- `const playerName = "Alex";`
+ - The value `"Alex"` is assigned to `playerName`. Its TDZ is now over.
+- `function calculateBonus(...)`
+ - This is a declaration. It was fully handled in the creation phase, so the engine skips it.
+- `var finalScore = score + calculateBonus(score);`
+ - This is the most important line. The engine needs to resolve this expression from right to left.
+ - It first needs to execute `calculateBonus(score)`.
+ - It looks up `score` in global memory and gets its value, `50`.
+ - It prepares to call `calculateBonus` with the argument `50`. **The execution of the global code is now paused.**
+
+### **Step 3: The Function Call - `calculateBonus(50)`**
+
+This is where the Call Stack comes into play.
+
+1. **A new Function Execution Context (FEC)** is created for this specific call.
+2. Before jumping to the function's code, the engine creates a **"bookmark"**. It takes the memory address of the **next bytecode instruction** needed to complete the `var finalScore = ...` line and stores this **Return Address** inside the new FEC.
+3. The FEC is **pushed onto the top of the Call Stack**.
+4. **FEC Creation Phase:**
+ - The engine creates a local environment for this function.
+ - The parameter `currentScore` is created as a local variable and initialized with the passed value, `50`.
+ - The engine scans the function's code for declarations: it finds `var bonus;`. A local variable `bonus` is created and initialized with `undefined`.
+5. **FEC Execution Phase:** The engine now executes the function's bytecode.
+ - `var bonus = currentScore / 10;`: It looks up `currentScore` (finds `50` locally), calculates `50 / 10 = 5`, and assigns `5` to the local variable `bonus`.
+ - `return bonus;`: The function needs to return. It looks up the value of `bonus` (which is `5`).
+
+**Visualizing the Call Stack at its Deepest Point:**
+
+```
+ TOP
++------------------------------+
+| calculateBonus() Exec. Context | <-- We are executing here
+| - Return Address: |
+| - Local Memory: |
+| - currentScore: 50 |
+| - bonus: 5 |
++------------------------------+
+| Global Execution Context | <-- This is paused
+| - Global Memory: |
+| - score: 50 |
+| - ... |
++------------------------------+
+
+```
+
+### **Step 4: The Return**
+
+1. The `calculateBonus` function is finished. It packages up the return value, `5`.
+2. The engine looks at the current FEC, finds the **Return Address** ("the bookmark"), and prepares to jump back.
+3. The **FEC is popped from the Call Stack**. All of its local variables (`currentScore`, `bonus`) are instantly destroyed. The memory is cleaned up.
+4. The engine's Program Counter is set to the retrieved Return Address.
+
+### **Step 5: Resuming Global Execution**
+
+- Execution is now back on the line `var finalScore = ...`.
+- The expression has been resolved to `50 + 5`.
+- The engine calculates `55` and assigns this value to `finalScore` in global memory.
+- `console.log(finalScore);`
+ - This is another function call. A new FEC for `console.log` is pushed to the stack.
+ - It looks up `finalScore` (gets `55`), performs its job of printing to the console.
+ - The `console.log` FEC is popped from the stack.
+
+The script is now finished. The GEC is popped from the Call Stack, and the program ends.
+
+---
+
+### **Key Takeaways**
+
+1. **Code is Compiled First:** Your JavaScript text is transformed into optimized Bytecode before it runs.
+2. **Creation Before Execution:** Memory is set aside for variables and functions *before* the code is executed. This is why function declarations can be called before they appear in the code.
+3. **The Call Stack Manages Flow:** The Call Stack keeps track of which function is currently running. Every function call creates a new, temporary, isolated environment (an Execution Context).
+4. **The Stack is for "Who" and "Where":** It holds the execution contexts and the "return addresses" (bookmarks) to manage the flow of the program.
+5. **The Heap is for "What":** It holds the actual objects and functions, which can live on long after the function that created them has finished.
+
+## Hoisting
+
+### The Misleading Idea (The Lie)
+
+The common explanation is: "Hoisting is when JavaScript moves your variable and function declarations to the top of their scope before execution."
+
+This is a lie. Nothing is physically moved. Forgetting this lie is the first step to truly understanding.
+
+### The Real Mechanism (The Truth)
+
+The truth is that JavaScript code runs in two phases (or passes):
+
+1. **Creation Phase (Memory Setup):** Before executing any code, the JavaScript engine reads through your code and sets aside memory for all the variables and functions it finds. This is like a chef doing *mise en place*—getting all the ingredients ready before starting to cook.
+2. **Execution Phase (Doing the Work):** After setting up memory, the engine goes back through the code line by line and actually executes it (assigns values, calls functions, etc.).
+
+**Hoisting is simply the visible effect of this two-phase process.** Because the engine already knows about your variables and functions from the first pass, it feels like they were "hoisted" to the top.
+
+---
+
+### The Unforgettable Analogy: The Teacher and the Roster
+
+Imagine a teacher (the JavaScript Engine) walking into a classroom (your code's scope).
+
+The teacher does two things:
+
+1. **Takes Attendance (Creation Phase):** Before starting the lesson, the teacher takes out the class roster and reads all the students' names. They now *know which students are supposed to be in the class*.
+2. **Teaches the Lesson (Execution Phase):** The teacher starts teaching from the first page of the textbook to the last.
+
+Now, let's see how `var`, `let`, `const`, and `function` behave like different types of students during the **"Attendance" phase**.
+
+### 1. Function Declarations: The Eager Student
+
+```jsx
+// You ask the teacher about the student before the lesson starts
+console.log(sayHello()); // "Hello!"
+
+function sayHello() {
+ return "Hello!";
+}
+
+```
+
+- **Attendance (Creation Phase):** The teacher sees `function sayHello` on the roster. This student is so eager, they are **already in their seat and have their homework done**. The teacher marks them as "Present and Ready."
+- **Result:** You can ask about this student (`call the function`) even before the lesson gets to their page, because the teacher already knows everything about them.
+
+---
+
+### 2. `var` Declarations: The Absent Student with a Reserved Desk
+
+```jsx
+// You ask about the student's homework
+console.log(studentName); // undefined
+
+var studentName = "Alice";
+
+console.log(studentName); // "Alice"
+
+```
+
+- **Attendance (Creation Phase):** The teacher sees `var studentName` on the roster. The teacher knows this student exists, so they reserve a desk for them, but the student isn't actually here yet. The teacher marks their status as "Absent" (which in JavaScript is `undefined`).
+- **Result:** If you ask about `studentName` before the lesson reaches their line, the teacher will tell you their status: "Absent" (`undefined`). They won't say "I don't know who that is" (`ReferenceError`). They know the student exists, but they have no value yet.
+
+---
+
+### 3. `let` and `const` Declarations: The Late Student (Strict Rule)
+
+```jsx
+// You ask about the student
+console.log(score); // Uncaught ReferenceError: Cannot access 'score' before initialization
+
+let score = 100;
+
+```
+
+- **Attendance (Creation Phase):** The teacher sees `let score` on the roster. The teacher knows this student is supposed to be in the class, but has a very strict rule: **"No one is allowed to talk about this student or ask for their homework until they physically walk through the classroom door."** This period of time before they arrive is the **Temporal Dead Zone (TDZ)**.
+- **Result:** If you ask about `score` before the lesson reaches its line, the teacher (JS Engine) doesn't just say they're absent. They stop the entire class and give you a `ReferenceError`. You broke the strict rule.
+
+---
+
+### The Final, Memorable Definition
+
+Forget the "moving code" idea. Remember this instead:
+
+> Hoisting is JavaScript's behavior of knowing about a variable or function's existence before executing the code. How it treats that knowledge depends on the keyword (function, var, let, or const).
+>
+- **`function`:** Hoisted completely (name and body).
+- **`var`:** Hoisted and initialized with `undefined`.
+- **`let`/`const`:** Hoisted, but not initialized. They are put in a Temporal Dead Zone.
\ No newline at end of file
diff --git a/03JS/notes/11-closure.md b/03JS/notes/11-closure.md
new file mode 100644
index 0000000..5ab37c7
--- /dev/null
+++ b/03JS/notes/11-closure.md
@@ -0,0 +1,361 @@
+# Lecture 11: Scope and Closures:
+
+## Part 1: SCOPE - What Can See What?
+
+### What is Scope?
+
+**Scope** = The **visibility** and **accessibility** of variables. It answers: "From where can I access this variable?"
+
+Think of scope like **rooms in a house**:
+
+- Variables declared in a room are accessible in that room
+- You can look OUT from inner rooms to outer rooms
+- You CANNOT look IN from outer rooms to inner rooms
+
+---
+
+### The Three Types of Scope
+
+### 1. Global Scope (The House Itself)
+
+Variables declared outside any function or block are **global**.
+
+```jsx
+const globalVar = "I'm global";
+
+function someFunction() {
+ console.log(globalVar); // ✅ Can access
+}
+
+someFunction(); // "I'm global"
+console.log(globalVar); // ✅ Can access from anywhere
+
+```
+
+**Real-world analogy:** Like the air outside - everyone can access it.
+
+---
+
+### 2. Function Scope (A Room)
+
+Variables declared inside a function are **only accessible inside that function**.
+
+```jsx
+function myFunction() {
+ const functionVar = "I'm in the function";
+ console.log(functionVar); // ✅ Works
+}
+
+myFunction(); // "I'm in the function"
+console.log(functionVar); // ❌ ReferenceError: functionVar is not defined
+
+```
+
+**Key point:** `var`, `let`, and `const` are all function-scoped (but `let`/`const` are also block-scoped).
+
+---
+
+### 3. Block Scope (A Closet in a Room)
+
+Variables declared with `let` or `const` inside `{}` are **block-scoped**.
+
+```jsx
+if (true) {
+ let blockVar = "I'm in a block";
+ const alsoBlockVar = "Me too";
+ var notBlockScoped = "I'm different!";
+
+ console.log(blockVar); // ✅ Works
+}
+
+console.log(blockVar); // ❌ ReferenceError
+console.log(alsoBlockVar); // ❌ ReferenceError
+console.log(notBlockScoped); // ✅ Works! (var ignores block scope)
+
+```
+
+**Important:** `var` is NOT block-scoped, only function-scoped!
+
+```jsx
+function testVar() {
+ if (true) {
+ var x = 10;
+ }
+ console.log(x); // ✅ 10 - var leaks out of block!
+}
+
+function testLet() {
+ if (true) {
+ let y = 10;
+ }
+ console.log(y); // ❌ ReferenceError - let respects block scope
+}
+
+```
+
+---
+
+### Lexical Scope (The Key Concept!)
+
+**Lexical scope** = Scope is determined by **where you write the code**, not where you call it.
+
+```jsx
+const name = "Global";
+
+function outer() {
+ const name = "Outer";
+
+ function inner() {
+ const name = "Inner";
+ console.log(name); // Which "name" will this print?
+ }
+
+ inner();
+}
+
+outer(); // "Inner"
+
+```
+
+**Why "Inner"?** JavaScript looks for variables in this order:
+
+1. **Current scope** (inner function) → Found `name = "Inner"` ✓
+2. If not found, check **outer scope** (outer function)
+3. If not found, check **global scope**
+4. If still not found → ReferenceError
+
+This is called the **Scope Chain**.
+
+---
+
+### The Scope Chain in Action
+
+```jsx
+const level1 = "Global";
+
+function outer() {
+ const level2 = "Outer";
+
+ function middle() {
+ const level3 = "Middle";
+
+ function inner() {
+ const level4 = "Inner";
+
+ // Can access ALL outer scopes!
+ console.log(level4); // "Inner"
+ console.log(level3); // "Middle"
+ console.log(level2); // "Outer"
+ console.log(level1); // "Global"
+ }
+
+ inner();
+ }
+
+ middle();
+}
+
+outer();
+
+```
+
+**Visual representation of scope chain:**
+
+```
+inner() scope
+ ↓ (can look up)
+middle() scope
+ ↓ (can look up)
+outer() scope
+ ↓ (can look up)
+Global scope
+
+```
+
+**But you CANNOT look down:**
+
+```jsx
+function outer() {
+ function inner() {
+ const secret = "Hidden";
+ }
+
+ inner();
+ console.log(secret); // ❌ ReferenceError - can't look INTO inner function
+}
+
+```
+
+---
+
+## Part 2: CLOSURES - Functions Remember Their Birthplace
+
+### What is a Closure?
+
+**Closure** = A function that **remembers** variables from its **outer scope** even after the outer function has finished executing.
+
+This is THE most important concept for understanding JavaScript!
+
+---
+
+### The Basic Closure Example
+
+```jsx
+function outer() {
+ const message = "Hello";
+
+ function inner() {
+ console.log(message); // Accesses outer's variable
+ }
+
+ return inner; // Return the function
+}
+
+const myFunction = outer(); // outer() finishes executing
+myFunction(); // "Hello" - but how does it still remember "message"?
+
+```
+
+**What just happened?**
+
+1. `outer()` runs and creates `message`
+2. `inner()` is defined INSIDE `outer()` - it "closes over" `message`
+3. `outer()` returns `inner` and finishes
+4. Normally, `message` would be garbage collected... **BUT**
+5. `inner` still has a reference to `message` - this is a **closure**!
+6. When we call `myFunction()` (which is `inner`), it still remembers `message`
+
+---
+
+### Why Closures Exist
+
+**Without closures:** Functions would only access their own variables and globals.
+
+**With closures:** Functions can "carry" their environment with them!
+
+```jsx
+function createCounter() {
+ let count = 0; // Private variable
+
+ return function() {
+ count++; // Accesses outer variable
+ return count;
+ };
+}
+
+const counter = createCounter();
+
+console.log(counter()); // 1
+console.log(counter()); // 2
+console.log(counter()); // 3
+
+// "count" is NEVER directly accessible!
+console.log(count); // ❌ ReferenceError
+
+```
+
+**Key insight:** `count` lives on even though `createCounter()` finished! The returned function "closes over" it.
+
+---
+
+### Real-World Example 1: Private Variables
+
+Closures let you create **truly private** variables!
+
+```jsx
+function createBankAccount(initialBalance) {
+ let balance = initialBalance; // PRIVATE - can't be accessed directly
+
+ return {
+ deposit: function(amount) {
+ balance += amount;
+ return balance;
+ },
+
+ withdraw: function(amount) {
+ if (amount > balance) {
+ return "Insufficient funds";
+ }
+ balance -= amount;
+ return balance;
+ },
+
+ getBalance: function() {
+ return balance;
+ }
+ };
+}
+
+const myAccount = createBankAccount(100);
+
+console.log(myAccount.getBalance()); // 100
+myAccount.deposit(50); // 150
+myAccount.withdraw(30); // 120
+
+// Can't directly access or modify balance!
+console.log(myAccount.balance); // undefined
+myAccount.balance = 9999999; // Doesn't work!
+console.log(myAccount.getBalance()); // 120 - still protected
+
+```
+
+**Why this works:** All three methods (`deposit`, `withdraw`, `getBalance`) are closures that remember the `balance` variable!
+
+# Higher-Order Functions in JavaScript
+
+## The Simplest Definition
+
+**A higher-order function is a function that either:**
+
+1. **Takes a function as an argument**, OR
+2. **Returns a function as a result**
+
+That's it!
+
+## Why "Higher-Order"?
+
+Think of it like hierarchy:
+
+- **Regular values**: numbers, strings, booleans
+- **First-order functions**: functions that work with regular values
+- **Higher-order functions**: functions that work with other functions
+
+In JavaScript, functions are **first-class citizens** - they can be treated like any other value (passed around, returned, stored in variables).
+
+---
+
+## Type 1: Functions That Take Functions as Arguments
+
+### Example 1: Array Methods
+
+javascript
+
+```rust
+const numbers = [1, 2, 3, 4, 5];
+
+*// map is a higher-order function// It takes a function as an argument*
+const doubled = numbers.map(function(num) {
+ return num * 2;
+});
+
+console.log(doubled); *// [2, 4, 6, 8, 10]*
+```
+
+**Why is `map` higher-order?** Because it accepts a function (`function(num) { return num * 2 }`) as a parameter.
+
+### Example 2: Custom Higher-Order Function
+```js
+// repeat is a higher-order function
+function repeat(n, action) {
+ for (let i = 0; i < n; i++) {
+ action(i);
+ }
+}
+
+// Using it:
+repeat(3, function(i) {
+ console.log("Iteration " + i);
+});
+
+// Output:// Iteration 0// Iteration 1// Iteration 2
+```
\ No newline at end of file
diff --git a/03JS/notes/12-map,filter,reduce.md b/03JS/notes/12-map,filter,reduce.md
new file mode 100644
index 0000000..8f738de
--- /dev/null
+++ b/03JS/notes/12-map,filter,reduce.md
@@ -0,0 +1,460 @@
+# Lecture 12: filter, set , reducer, map and set
+
+### **In-Depth Guide: Modern JavaScript Array Methods**
+
+The methods we are about to cover are called **Higher-Order Functions**. This is a fancy term that simply means they are functions that take *another function* as an argument (this is the "callback" function you provide).
+
+**The Core Idea:** Instead of manually writing a `for` loop every time, you tell the array *what* you want to do, and the array method handles the looping for you.
+
+Let's use this sample array for our examples:
+
+```jsx
+const products = [
+ { id: 1, name: "Laptop", category: "Electronics", price: 1200, inStock: true },
+ { id: 2, name: "Book", category: "Books", price: 30, inStock: true },
+ { id: 3, name: "Coffee Maker", category: "Appliances", price: 150, inStock: false },
+ { id: 4, name: "Headphones", category: "Electronics", price: 200, inStock: true }
+];
+
+```
+
+---
+
+## **1. `.forEach()` - The Simple Looper**
+
+- **First Thought:** "I want to walk along the conveyor belt and do something with each item, but I'm not creating a new line of items."
+- **Core Purpose:** To execute a function once for each element in the array. It's a modern alternative to a `for` loop.
+- **Key Characteristics:**
+ - It does **not** return anything (it returns `undefined`).
+ - It does **not** create a new array.
+ - You **cannot** `break` out of it or `continue` to the next iteration.
+- **Syntax:**`array.forEach((element, index) => { /* ... your code ... */ });`
+ - `element`: The current item being processed in the array.
+ - `index` (Optional): The index of the current item.
+- **Detailed Example:** Just logging the name of each product.
+
+ ```jsx
+ console.log("--- Our Products ---");
+ products.forEach(product => {
+ console.log(`- ${product.name}`);
+ });
+
+ ```
+
+ **Output:**
+
+ ```
+ --- Our Products ---
+ - Laptop
+ - Book
+ - Coffee Maker
+ - Headphones
+
+ ```
+
+- **When to Use:** When you need to "do something" for each item but you don't need to create a new array from the results. Examples: logging, updating a UI, saving each item to a database.
+
+---
+
+## **2. `.map()` - The Transformer**
+
+- **First Thought:** "I have a list of raw materials. I want to put each one through a machine to create a **new list** of finished products."
+- **Core Purpose:** To create a **new array** by transforming every element from an original array.
+- **Key Characteristics:**
+ - It **always** returns a **new array**.
+ - The new array will **always** have the **same length** as the original array.
+ - It is **non-mutating**; it does not change the original array.
+- **Syntax:**`const newArray = array.map((element, index) => { return /* new value */; });`
+The `return` value from your callback function becomes the element in the new array at that same position.
+- **Detailed Example:** Let's create a new array containing just the names of the products for display.
+
+ ```jsx
+ const productNames = products.map(product => {
+ return product.name;
+ });
+
+ console.log(productNames); // ["Laptop", "Book", "Coffee Maker", "Headphones"]
+ console.log(products); // The original `products` array is unchanged!
+
+ ```
+
+- **When to Use:** When you need a new array that is a modified version of the original. This is one of the most-used array methods.
+
+---
+
+## **3. `.filter()` - The Sieve / The Bouncer**
+
+- **First Thought:** "I have a big list of items. I want to run each one through a test and create a **new, shorter list** containing only the items that pass the test."
+- **Core Purpose:** To create a **new array** containing only the elements from the original array that meet a specific condition.
+- **Key Characteristics:**
+ - It **always** returns a **new array**.
+ - The new array can have the **same length or be shorter** than the original. It will never be longer.
+ - It is **non-mutating**.
+- **Syntax:**`const newArray = array.filter((element, index) => { return /* true or false */; });`
+If your callback function returns `true`, the element is kept. If it returns `false`, the element is discarded.
+- **Detailed Example:** Let's create a new array of only the products that are in stock and are in the "Electronics" category.
+
+ ```jsx
+ const availableElectronics = products.filter(product => {
+ // The condition must evaluate to true or false.
+ // We combine two conditions here.
+ return product.inStock === true && product.category === "Electronics";
+ });
+
+ console.log(availableElectronics);
+ // [
+ // { id: 1, name: "Laptop", ... },
+ // { id: 4, name: "Headphones", ... }
+ // ]
+
+ ```
+
+- **When to Use:** Whenever you need to select a subset of data from an array based on one or more conditions.
+
+---
+
+## **4. `.reduce()` - The Accumulator / The Snowball**
+
+- **First Thought:** "I want to roll up this entire list into a **single final value**." (e.g., Summing a list of numbers, counting items, etc.)
+- **Core Purpose:** To execute a "reducer" function on each element of the array, resulting in a single output value.
+- **Key Characteristics:**
+ - It is the most powerful and flexible of the iteration methods.
+ - It can return **any type of value**: a number, a string, an object, another array.
+ - It is **non-mutating**.
+- **Syntax:**`const finalValue = array.reduce((accumulator, currentValue, index) => { /* ... */ return newAccumulator; }, initialValue);`
+ - `accumulator`: The value that is "accumulated" or carried over from the previous iteration. It's the snowball.
+ - `currentValue`: The current element being processed.
+ - `initialValue`: The **starting value** for the accumulator (the small snowball you start with). This is a crucial argument.
+- **Detailed Example:** Let's calculate the total value of all the items that are currently in stock.
+
+ ```jsx
+ const totalStockValue = products.reduce((total, product) => {
+ console.log(`Current Total: ${total}, Current Product: ${product.name}, Price: ${product.price}`);
+
+ if (product.inStock) {
+ // The return value of this step becomes the 'total' for the NEXT step.
+ return total + product.price;
+ }
+ // If not in stock, just return the current total without adding anything.
+ return total;
+ }, 0); // Our initial value for the total is 0.
+
+ console.log(`\\nFinal Total Stock Value: $${totalStockValue}`);
+
+ ```
+
+ **Trace of the Output:**
+
+ ```
+ Current Total: 0, Current Product: Laptop, Price: 1200
+ Current Total: 1200, Current Product: Book, Price: 30
+ Current Total: 1230, Current Product: Coffee Maker, Price: 150
+ Current Total: 1230, Current Product: Headphones, Price: 200
+
+ Final Total Stock Value: $1430
+
+ ```
+
+- **When to Use:** When you need to derive a single summary value from an array. Examples: sum, average, finding the most expensive item, grouping items into an object.
+
+---
+
+## **5. Other Essential Methods for Finding & Testing**
+
+- **`.find()`:** Like `.filter()`, but it **stops** and returns the **very first element** that matches the condition. If nothing matches, it returns `undefined`.
+
+ ```jsx
+ const coffeeMaker = products.find(product => product.name === "Coffee Maker");
+ console.log(coffeeMaker); // The coffee maker object
+
+ ```
+
+- **`.some()`:** Checks if **at least one** element in the array passes the test. Returns `true` or `false`. It stops as soon as it finds one.
+
+ ```jsx
+ const hasOutOfStockItems = products.some(product => product.inStock === false);
+ console.log(hasOutOfStockItems); // true
+
+ ```
+
+- **`.every()`:** Checks if **all** elements in the array pass the test. Returns `true` or `false`. It stops as soon as it finds one that *doesn't* pass.
+
+ ```jsx
+ const areAllItemsInStock = products.every(product => product.inStock === true);
+ console.log(areAllItemsInStock); // false
+
+ ```
+
+
+## Set and Map
+
+### **Part 1: The `Set` Object**
+
+### **First Thought: A `Set` is a list that enforces uniqueness. It's a collection of items where duplicates are impossible.**
+
+Think of it like a members-only club. You can add a person to the member list, but you can't add the same person twice. The `Set` automatically handles this for you.
+
+---
+
+### **A. The Basics of `Set`**
+
+**1. Creating a Set**
+You create a `Set` with `new Set()`. You can optionally pass in an iterable (like an array) to pre-populate it. Duplicates are automatically removed.
+
+```jsx
+// Create an empty Set
+const mySet = new Set();
+
+// Create a Set from an array (duplicates are ignored)
+const numbersArray = [1, 2, 3, 3, 4, 2, 5];
+const numbersSet = new Set(numbersArray);
+
+console.log(numbersSet); // Set(5) { 1, 2, 3, 4, 5 }
+
+```
+
+**2. Core Methods (CRUD)**
+
+- **`.add(value)`:** Adds a new element. If the element already exists, it does nothing. It returns the `Set` object, so you can chain `.add()` calls.
+- **`.has(value)`:** Checks if an element exists. Returns `true` or `false`.
+- **`.delete(value)`:** Removes a specific element.
+- **`.clear()`:** Removes all elements from the `Set`.
+
+```jsx
+const userRoles = new Set();
+
+// Add elements (chaining)
+userRoles.add("editor").add("viewer");
+console.log(userRoles); // Set(2) { "editor", "viewer" }
+
+// Add a duplicate - nothing happens
+userRoles.add("editor");
+console.log(userRoles); // Still Set(2) { "editor", "viewer" }
+
+// Check for an element
+console.log(userRoles.has("admin")); // false
+console.log(userRoles.has("editor")); // true
+
+// Delete an element
+userRoles.delete("viewer");
+console.log(userRoles.has("viewer")); // false
+
+// Clear the entire Set
+userRoles.clear();
+console.log(userRoles); // Set(0) {}
+
+```
+
+**3. The `.size` Property**
+Unlike arrays which have `.length`, a `Set` has a `.size` property to tell you how many items it contains.
+
+```jsx
+console.log(numbersSet.size); // 5
+
+```
+
+---
+
+### **B. Iterating Over a `Set`**
+
+Sets are iterable. The best way to loop over a `Set` is with a `for...of` loop. The items are iterated in **insertion order**.
+
+```jsx
+const permissions = new Set(["read", "write", "execute"]);
+
+for (const permission of permissions) {
+ console.log(permission);
+}
+// Outputs:
+// read
+// write
+// execute
+
+```
+
+You can also use `.forEach()`.
+
+---
+
+### **C. Real-World Use Cases (Why use a `Set`?)**
+
+1. **Removing Duplicates from an Array (The #1 Use Case):** This is a powerful and concise one-liner.
+
+ ```jsx
+ const duplicateEmails = ["a@a.com", "b@b.com", "a@a.com"];
+
+ // Convert to a Set to remove duplicates, then spread it back into a new array.
+ const uniqueEmails = [...new Set(duplicateEmails)];
+
+ console.log(uniqueEmails); // ["a@a.com", "b@b.com"]
+
+ ```
+
+2. **Checking for Uniqueness / Existence:** `Set.has()` is much faster than `Array.includes()` for very large datasets. If you just need to track if you've "seen" an item before, a `Set` is far more performant.
+
+ ```jsx
+ // Imagine tracking unique visitors to a page
+ const visitedUsers = new Set();
+
+ function userVisits(userId) {
+ if (!visitedUsers.has(userId)) {
+ console.log(`Welcome, new visitor #${userId}!`);
+ visitedUsers.add(userId);
+ } else {
+ console.log(`Welcome back, visitor #${userId}!`);
+ }
+ }
+
+ userVisits(101); // Welcome, new visitor #101!
+ userVisits(102); // Welcome, new visitor #102!
+ userVisits(101); // Welcome back, visitor #101!
+
+ ```
+
+
+| Use... | When you need... |
+| --- | --- |
+| **`Array`** | An ordered list where **duplicates are allowed** and you need index-based access (`arr[0]`). |
+| **`Set`** | A collection of **unique values** where the main task is adding, deleting, and checking for existence. |
+
+---
+
+### **Part 2: The `Map` Object**
+
+### **First Thought: A `Map` is like an object, but its keys can be *anything* (not just strings).**
+
+This is the most critical difference. In a standard object `{}`, keys are automatically converted to strings. A `Map` preserves the key's type, allowing you to use objects, functions, or any other data type as a key.
+
+---
+
+### **A. The Basics of `Map`**
+
+**1. The Problem with Plain Objects**
+
+```jsx
+let myObject = {};
+let keyObject1 = { id: 1 };
+let keyObject2 = { id: 2 };
+
+// Both keyObject1 and keyObject2 get converted to the SAME string: "[object Object]"
+myObject[keyObject1] = "Value for key 1";
+myObject[keyObject2] = "Value for key 2";
+
+// The second assignment overwrote the first!
+console.log(myObject); // { "[object Object]": "Value for key 2" }
+
+```
+
+**2. Creating a Map**
+You create a `Map` with `new Map()`. You can pre-populate it with an array of `[key, value]` pairs.
+
+```jsx
+// Create an empty Map
+const myMap = new Map();
+
+// Create a Map with initial values
+const userMap = new Map([
+ ["name", "Alice"],
+ [true, "is verified"],
+ [100, "points"]
+]);
+
+```
+
+**3. Core Methods (CRUD)**
+
+- **`.set(key, value)`:** Adds or updates a key-value pair. Returns the `Map`, so you can chain it.
+- **`.get(key)`:** Retrieves the value for a given key. Returns `undefined` if the key doesn't exist.
+- **`.has(key)`:** Checks if a key exists. Returns `true` or `false`.
+- **`.delete(key)`:** Removes a key-value pair.
+- **`.clear()`:** Removes all key-value pairs.
+
+```jsx
+const metadata = new Map();
+let user1 = { name: "Alice" };
+let user2 = { name: "Bob" };
+
+// Set values using objects as keys
+metadata.set(user1, { lastLogin: "2023-10-27" });
+metadata.set(user2, { lastLogin: "2023-10-26" });
+
+// Get a value using the exact same object reference
+console.log(metadata.get(user1)); // { lastLogin: "2023-10-27" }
+
+console.log(metadata.has(user2)); // true
+
+```
+
+**4. The `.size` Property**
+Like `Set`, a `Map` has a `.size` property.
+
+```jsx
+console.log(metadata.size); // 2
+
+```
+
+---
+
+### **B. Iterating Over a `Map`**
+
+A `Map` is also iterable. The best way to loop is with `for...of` and **destructuring**. The items are iterated in **insertion order**.
+
+```jsx
+const userMap = new Map([
+ ["name", "Alice"],
+ ["age", 30]
+]);
+
+// Use destructuring to unpack the [key, value] pair
+for (const [key, value] of userMap) {
+ console.log(`${key} -> ${value}`);
+}
+// Outputs:
+// name -> Alice
+// age -> 30
+
+```
+
+You can also use `.keys()`, `.values()`, and `.entries()` to get iterators, or `.forEach()`.
+
+---
+
+### **C. Real-World Use Cases (Why use a `Map`?)**
+
+1. **Storing Metadata for Objects:** This is the killer use case. You can "attach" data to an object without actually modifying the object itself. This is great for keeping DOM elements clean.
+
+ ```jsx
+ const elementData = new Map();
+ const button1 = document.querySelector("#btn1");
+
+ // Associate some metadata with this specific button element
+ elementData.set(button1, { clicks: 0, lastClickTime: null });
+
+ // Now you can store and retrieve data about `button1` without
+ // ever doing `button1.mydata = ...`, which pollutes the DOM object.
+
+ ```
+
+2. **High-Performance Caching:** If you have a function that performs a complex calculation, you can use a `Map` to cache the results. The arguments to the function can be the key, and the result can be the value.
+3. **When You Need a "Dictionary" with Non-String Keys:** Any time your keys are not simple strings, a `Map` is the correct and only choice.
+
+| Use... | When you need... |
+| --- | --- |
+| **`Object`** | A simple, fixed set of **string-based keys**. Great for storing the structure of a single entity (like a `user`). |
+| **`Map`** | A collection of key-value pairs where **keys can be of any type**, you need to iterate in insertion order, or you need to get the size quickly. |
+
+---
+
+### **Part 3: Advanced - `WeakSet` and `WeakMap`**
+
+**First Thought: A "weak" version is a Map or Set that doesn't prevent its items from being garbage collected.**
+
+- A normal `Map` or `Set` holds a **strong reference** to its items. As long as an object is in a `Map`, it will **never be garbage collected**.
+- A `WeakMap` or `WeakSet` holds a **weak reference**. If an object is the key in a `WeakMap` and it's the *only* reference left in your entire program, the garbage collector is free to destroy it, and it will be automatically removed from the `WeakMap`.
+
+**Use Case:** Caching. In the DOM element example above, if you remove `button1` from the page, you want its metadata in the `elementData` map to be automatically deleted to prevent a **memory leak**. If you used a `Map`, the data would stay there forever. If you use a `WeakMap`, it cleans itself up.
+
+**Limitations:**
+
+- You can only store **objects** in a `WeakSet` or as keys in a `WeakMap` (not primitives).
+- You **cannot iterate** over them (because the items could disappear at any moment during the loop). They only have `.has()`, `.get()`, `.set()`, and `.delete()`.
\ No newline at end of file
diff --git a/03JS/notes/13-dom-manipulation.md b/03JS/notes/13-dom-manipulation.md
new file mode 100644
index 0000000..d0e91fa
--- /dev/null
+++ b/03JS/notes/13-dom-manipulation.md
@@ -0,0 +1,553 @@
+# Lecture 13: Introduction to DOM
+
+### **Start with a Question:**
+
+*"You have HTML and JavaScript. How do they talk to each other?"*
+
+### **The Setup:**
+
+```html
+
+
+
+
+ My Page
+
+
+ Hello World
+ This is a paragraph.
+
+
+
+```
+
+```jsx
+// script.js
+// How do I change "Hello World" to "Goodbye World"?
+// How do I make the paragraph red?
+// How do I add a new button?
+
+```
+
+### **The Core Problem:**
+
+- HTML is just **text with tags** (markup language)
+- JavaScript is a **programming language** (works with objects, functions, variables)
+- They speak different "languages"!
+
+### **Real-world Analogy:**
+
+- **HTML** = Blueprint of a house (static document)
+- **JavaScript** = Construction crew (wants to modify the house)
+- **DOM** = The actual built house that the crew can walk through and modify
+
+**Key Point:** *"The DOM is the bridge that lets JavaScript understand and manipulate HTML."*
+
+---
+
+## **PART 2: What is the DOM?**
+
+### **Definition (Simple):**
+
+*"The DOM (Document Object Model) is a tree-like representation of your HTML document that JavaScript can understand and manipulate.*
+
+### **Visual Explanation:**
+
+### **Your HTML:**
+
+```html
+
+
+ My Site
+
+
+ Welcome
+ Hello there!
+
+
+
+```
+
+### **Browser Creates This Tree:**
+
+```
+document
+└── html
+ ├── head
+ │ └── title
+ │ └── "My Site"
+ └── body
+ ├── h1
+ │ └── "Welcome"
+ └── p
+ └── "Hello there!"
+
+```
+
+### **Key Concepts (Explain with Diagrams):**
+
+### **1. Everything is a Node**
+
+```
+Types of Nodes:
+- Element Nodes: ,
,
+- Text Nodes: The actual text content
+- Document Node: The root (document)
+
+```
+
+### **2. HTML Elements Become Objects**
+
+```html
+Hello
+
+```
+
+Becomes:
+
+```jsx
+{
+ tagName: "H1",
+ id: "title",
+ textContent: "Hello",
+ style: { color: "", fontSize: "" },
+ parentElement: body,
+ children: [],
+ // ... many more properties and methods
+}
+
+```
+
+**Tell students:** *"Every HTML tag becomes a JavaScript object with properties and methods!"*
+
+### **3. The `window` and `document` Objects**
+
+Draw this hierarchy:
+
+```
+Window (global object - the browser API)
+ └── document (your HTML page as objects)
+ └── documentElement (the tag)
+ ├── head
+ └── body
+ └── (all your elements)
+
+```
+
+**Key Points:**
+
+- `window` = The browser environment (has alert, setTimeout, localStorage, etc.)
+- `document` = Your HTML page (the DOM tree)
+
+---
+
+## Different way to select the Element
+
+### Sample HTML to Work With
+
+```html
+
+
+
+ DOM Selection
+
+
+
+
+
Main Title
+
This is the first paragraph.
+
This is the second paragraph with a class.
+
+
+ - Item 1
+ - Item 2
+ - Item 3
+
+
+
+
+
+
+
+
+
+
+```
+
+---
+
+### 1. The Classic, Specific Methods (The Old Guard)
+
+These were the original ways to select elements. They are very fast for their specific purpose but are less flexible than the modern methods.
+
+### **A. `document.getElementById('id')`**
+
+- **What it does:** Selects the **single** element that has the specified `id`.
+- **Returns:** A **single element object**, or `null` if no element with that ID is found.
+- **First Thought:** "Get me the one, unique thing with this exact ID."
+
+```jsx
+const mainContainer = document.getElementById('main-container');
+mainContainer.style.border = '2px solid red'; // Puts a red border around the main div
+
+const itemList = document.getElementById('item-list');
+console.log(itemList);
+
+```
+
+**Why it's great:** It's extremely fast and direct because IDs are meant to be unique in a document. This is the best method to use when you have a unique ID.
+
+### **B. `document.getElementsByTagName('tagName')`**
+
+- **What it does:** Selects **all** elements that have the specified tag name (like `p`, `li`, `div`).
+- **Returns:** A **live `HTMLCollection`** (an array-like object) of all matching elements.
+- **First Thought:** "Get me all the paragraphs" or "Get me all the list items."
+
+```jsx
+const allParagraphs = document.getElementsByTagName('p');
+console.log(allParagraphs.length); // 3
+
+// You can loop through the collection
+for (let i = 0; i < allParagraphs.length; i++) {
+ allParagraphs[i].style.fontStyle = 'italic';
+}
+
+```
+
+**What "live" means:** If you add a new `
` to the page *after* you've selected them, the `allParagraphs` collection will **automatically update** to include it.
+
+### **C. `document.getElementsByClassName('className')`**
+
+- **What it does:** Selects **all** elements that have the specified class name.
+- **Returns:** A **live `HTMLCollection`** of all matching elements.
+- **First Thought:** "Get me everything with the class 'item'."
+
+```jsx
+const allItems = document.getElementsByClassName('item');
+console.log(allItems.length); // 3
+
+// You can also get elements with multiple classes
+const footerContainer = document.getElementsByClassName('container footer');
+console.log(footerContainer[0]);
+
+```
+
+---
+
+### 2. The Modern, Powerful Methods (The "Query" Selectors)
+
+These methods were a game-changer. They allow you to select elements using the same powerful **CSS selector syntax** that you use in your stylesheets. **These are the methods you should use most of the time.**
+
+### **A. `document.querySelector('cssSelector')`**
+
+- **What it does:** Selects the **first element** in the document that matches the specified CSS selector.
+- **Returns:** A **single element object**, or `null` if no match is found.
+- **First Thought:** "Find me the *very first* thing that matches this CSS rule."
+
+```jsx
+// Get the element with the ID 'main-container'
+const main = document.querySelector('#main-container');
+
+// Get the FIRST element with the class 'container'
+const firstContainer = document.querySelector('.container');
+console.log(firstContainer); // This will be the main div, not the footer
+
+// Get the FIRST paragraph
+const firstP = document.querySelector('p');
+console.log(firstP);
+
+// Get the list item that has BOTH 'item' and 'special' classes
+const specialItem = document.querySelector('.item.special');
+specialItem.style.color = 'orange';
+
+// Get the input with the name 'username'
+const usernameInput = document.querySelector('input[name="username"]');
+
+```
+
+### **B. `document.querySelectorAll('cssSelector')`**
+
+- **What it does:** Selects **all** elements in the document that match the specified CSS selector.
+- **Returns:** A **static `NodeList`** (an array-like object) of all matching elements.
+- **First Thought:** "Find me *every single thing* that matches this CSS rule."
+
+```jsx
+// Get ALL elements with the class 'container'
+const allContainers = document.querySelectorAll('.container');
+console.log(allContainers.length); // 2
+
+// Get ALL list items inside the element with the ID 'item-list'
+const listItems = document.querySelectorAll('#item-list li');
+
+// A NodeList has a .forEach method, which is very convenient!
+listItems.forEach(item => {
+ item.style.fontWeight = 'bold';
+});
+
+```
+
+**What "static" means:** Unlike an `HTMLCollection`, a `NodeList` returned by `querySelectorAll` is **not live**. If you add a new matching element to the page later, the `listItems` collection will **not** automatically update. This is usually the behavior you want, as it's more predictable.
+
+---
+
+### 3. Other, More Niche Selections
+
+- **`document.getElementsByName('name')`:** Selects elements based on their `name` attribute (most commonly used for form elements).
+
+ ```jsx
+ const loginForm = document.getElementsByName('login-form');
+ const usernameInputByName = document.getElementsByName('username');
+
+ ```
+
+- **Traversing the DOM:** Once you have one element, you can navigate to its relatives.
+
+ ```jsx
+ const itemList = document.getElementById('item-list');
+
+ const parentContainer = itemList.parentElement; // The #main-container div
+ const listChildren = itemList.children; // An HTMLCollection of the 3
elements
+ const firstLi = itemList.firstElementChild; // The first
+ const lastLi = itemList.lastElementChild; // The last
+
+ const specialLi = document.querySelector('.special');
+ const nextItem = specialLi.nextElementSibling; // The 3rd
+ const prevItem = specialLi.previousElementSibling; // The 1st
+
+ ```
+
+
+### Summary: Which Method Should I Use?
+
+| Goal | Best Method | Why? |
+| --- | --- | --- |
+| Get a **single, unique** element | **`getElementById()`** | Fastest and most direct. |
+| Get the **first** element that matches a complex rule | **`querySelector()`** | Extremely flexible, uses familiar CSS syntax. **Your default choice for single elements.** |
+| Get **all** elements that match a complex rule | **`querySelectorAll()`** | Extremely flexible, and the returned `NodeList` has a convenient `.forEach()` method. **Your default choice for multiple elements.** |
+| Get all elements by tag or class (and you need a "live" collection) | `getElementsByTagName()` or `getElementsByClassName()` | Use these only if you specifically need the "live" auto-updating behavior. Otherwise, `querySelectorAll` is better. |
+| | | |
+
+### Once you've selected an element, the next step is to interact with it. You do this by reading and writing to its properties. These properties are the bridge that lets your JavaScript code control the content, appearance, and attributes of the HTML elements.
+
+Let's do a deep dive into the most important properties, using this HTML snippet as our reference:
+
+```html
+
+
+ Smart Headphones
+
+ SALE
+
+
+ These headphones have noise-cancelling features.
+
+
+
+```
+
+---
+
+### **1. Properties for Manipulating Content**
+
+These three properties are used to read or change the content *inside* an element, but they have critical differences.
+
+### **A. `.textContent` (The Safe and Recommended Choice)**
+
+- **First Thought:** "Give me **just the text**, exactly as it is, with no HTML."
+- **What it does:** It gets or sets the raw text content of an element and all its descendants. It completely ignores all HTML tags and gives you just the text.
+- **When Reading:**
+
+ ```jsx
+ const desc = document.getElementById('description');
+ console.log(desc.textContent);
+ // Output: "These headphones have noise-cancelling features."
+ // Notice the tags are gone.
+
+ const productName = document.getElementById('product-name');
+ console.log(productName.textContent);
+ // Output: "Smart Headphones SALE"
+ // It includes text from hidden elements but ignores comments.
+
+ ```
+
+- **When Writing (Safe):** When you set `.textContent`, the browser treats your input as pure text. It will **not** parse any HTML tags. This is a crucial security feature that prevents Cross-Site Scripting (XSS) attacks.
+
+ ```jsx
+ const desc = document.getElementById('description');
+
+ // Let's try to inject some HTML
+ desc.textContent = "Click here to win!";
+
+ // The browser will display the literal text, not a clickable link:
+ // "Click here to win!"
+
+ ```
+
+- **Performance:** It's very fast because the browser doesn't need to parse HTML.
+- **Best For:** Reading or writing plain text content. **This should be your default choice.**
+
+### **B. `.innerHTML` (The Powerful but Dangerous Choice)**
+
+- **First Thought:** "Give me **everything inside**, including all the HTML markup."
+- **What it does:** It gets or sets the full HTML content of an element.
+- **When Reading:**
+
+ ```jsx
+ const desc = document.getElementById('description');
+ console.log(desc.innerHTML);
+ // Output: "These headphones have noise-cancelling features."
+ // It includes the HTML tags as a string.
+
+ ```
+
+- **When Writing (Dangerous):** When you set `.innerHTML`, the browser will **parse your string and create actual HTML elements** from it. This is powerful, but it's a major security risk if the string comes from a user.
+
+ ```jsx
+ const desc = document.getElementById('description');
+
+ // This is powerful and useful for creating new elements.
+ desc.innerHTML = "Updated features: Active Noise Cancelling and Bluetooth 5.0.";
+ // The browser will correctly render the bold and italic text.
+
+ // SECURITY RISK: What if the string comes from a malicious user?
+ let userInput = `
`;
+ // desc.innerHTML = userInput; // This would execute the malicious script!
+
+ ```
+
+- **Performance:** It's slower than `.textContent` because the browser has to parse the string into DOM nodes.
+- **Best For:** Only use it when you **explicitly need to create HTML elements** from a string that you, the developer, have created and trust completely. **Never use it with user-provided input.**
+
+### **C. `.innerText` (The "Smart" but Tricky Choice)**
+
+- **First Thought:** "Give me the text **as it appears on the screen**."
+- **What it does:** This is a non-standard but widely supported property. It tries to get the text content as it is rendered to the user, taking CSS into account.
+- **When Reading:**
+
+ ```jsx
+ const productName = document.getElementById('product-name');
+ console.log(productName.innerText);
+ // Output: "SMART HEADPHONES" (if CSS `text-transform: uppercase` was applied)
+ // It will NOT include the text from the hidden ("SALE").
+
+ ```
+
+ `.innerText` is "style-aware." It won't return text from hidden elements, and it might reflect CSS transformations.
+
+- **When Writing:** It behaves similarly to `.textContent`, setting the raw text.
+- **Performance:** It's the **slowest** of the three because the browser may need to trigger a layout calculation (a "reflow") to figure out what is actually visible on the screen.
+- **Best For:** Rarely needed. Use it only if you have a specific need to get the text exactly as a user would see it, excluding hidden content. Prefer `.textContent` in almost all cases.
+
+**Summary of Content Properties:**
+
+| Property | HTML Content | CSS Aware | Speed | Security (on write) |
+| --- | --- | --- | --- | --- |
+| `.textContent` | No | No | Fastest | **Safe** |
+| `.innerHTML` | Yes | No | Slower | **Dangerous** |
+| `.innerText` | No | Yes | Slowest | Safe |
+
+---
+
+### **2. Properties for Manipulating Attributes**
+
+These properties give you direct access to the HTML attributes of an element.
+
+### **A. `.id` and `.className` (Direct Properties)**
+
+For the most common attributes like `id` and `class`, JavaScript provides direct properties.
+
+- **`.id`:** Gets or sets the `id` attribute.
+
+ ```jsx
+ const card = document.getElementById('product-card');
+ console.log(card.id); // "product-card"
+ card.id = 'new-card-id'; // Changes the element's ID
+
+ ```
+
+- **`.className`:** Gets or sets the entire `class` attribute as a **single string**.
+Because it overwrites everything, `.className` is clumsy. The `.classList` property is much better.
+
+ ```jsx
+ console.log(card.className); // "card featured"
+
+ // This will OVERWRITE all existing classes.
+ card.className = "card-dark-mode";
+ // The element now only has the class "card-dark-mode". "featured" is gone.
+
+ ```
+
+
+### **B. `.classList` (The Modern Way to Handle Classes)**
+
+- **First Thought:** "Give me a smart toolbox for adding, removing, and checking for classes without messing up the other ones."
+- **What it is:** An object with helpful methods to manage an element's classes.
+ - `.add('className')`: Adds a new class.
+ - `.remove('className')`: Removes a class.
+ - `.toggle('className')`: Adds the class if it's missing, removes it if it's present.
+ - `.contains('className')`: Returns `true` or `false` if the element has the class.
+
+ ```jsx
+ const card = document.getElementById('product-card');
+
+ card.classList.add('in-cart'); // Adds 'in-cart'
+ card.classList.remove('featured'); // Removes 'featured'
+
+ // Toggle a 'selected' class every time a function is called
+ card.classList.toggle('selected');
+
+ if (card.classList.contains('in-cart')) {
+ console.log("This item is in the cart.");
+ }
+
+ ```
+
+- **Best For:** **This is the correct and modern way to manipulate CSS classes.**
+
+### **C. `.getAttribute()` and `.setAttribute()` (For Any Attribute)**
+
+These are generic methods that can work with *any* HTML attribute, including custom ones.
+
+```jsx
+const card = document.getElementById('product-card');
+
+// Add a custom data attribute
+card.setAttribute('data-product-id', 'xyz-123');
+
+// Get the value of an attribute
+const productId = card.getAttribute('data-product-id');
+console.log(productId); // "xyz-123"
+
+// Remove an attribute
+card.removeAttribute('class');
+
+```
+
+---
+
+### **3. The `.style` Property**
+
+- **First Thought:** "Give me direct control over the element's **inline styles**."
+- **What it does:** An object that represents the `style="..."` attribute of an element. You can change CSS properties through it.
+- **The "Gotcha": Property Names are camelCased.** CSS properties with hyphens (like `background-color`) must be written in `camelCase` in JavaScript.
+ - `background-color` -> `backgroundColor`
+ - `font-size` -> `fontSize`
+ - `z-index` -> `zIndex`
+
+```jsx
+const title = document.querySelector('.title');
+
+title.style.color = 'blue';
+title.style.backgroundColor = '#f0f0f0'; // Note the camelCase
+title.style.fontSize = '24px'; // The value must be a string
+title.style.padding = '10px';
+
+```
+
+**Important:** The `.style` property **only knows about inline styles**. It cannot read styles that are set in an external CSS file. To do that, you need to use the global function `window.getComputedStyle(element)`.
+
+**Best Practice:** It's generally better to use `.classList` to add or remove CSS classes that are defined in your stylesheet, rather than manipulating inline styles directly with JavaScript. This keeps your styling rules separate from your logic.
\ No newline at end of file
diff --git a/03JS/notes/14-CRUD.md b/03JS/notes/14-CRUD.md
new file mode 100644
index 0000000..d10f3ad
--- /dev/null
+++ b/03JS/notes/14-CRUD.md
@@ -0,0 +1,505 @@
+# Lecture 14: DOM Manipulation
+
+### **In-Depth Guide to DOM Manipulation**
+
+Once you have selected an element and stored it in a variable, you have a powerful object that gives you full control over that part of your webpage. Let's cover the three main categories of manipulation:
+
+1. **Editing What's Inside (Content & HTML)**
+2. **Editing the Tag Itself (Attributes, Classes, and Styles)**
+3. **Editing the Page Structure (Creating, Adding, and Removing Elements)**
+
+---
+
+### **Part 1: Editing the Content Inside an Element**
+
+This is about what the user sees *inside* an element's opening and closing tags.
+
+**HTML Snippet for this section:**
+
+```html
+
+ Please log in to see your messages.
+
+
+```
+
+```jsx
+// We've selected our target element
+const welcomeBox = document.getElementById('welcome-box');
+
+```
+
+### **A. `.textContent` (For Plain Text - The Safe Default)**
+
+- **What it does:** Gets or sets the **pure text** content of an element. It ignores and strips out all HTML tags.
+- **Use Case:** This should be your **default choice** for changing text on the page.
+
+```jsx
+// Reading the text content
+console.log(welcomeBox.textContent); // "Please log in to see your messages."
+
+// Writing new text content
+welcomeBox.textContent = "Welcome back, Alice!";
+
+```
+
+**The Security Benefit:** When you set `.textContent`, the browser treats your string as plain text. This is **safe** because it prevents malicious code from being executed.
+
+```jsx
+// Even if this string came from a hacker...
+const maliciousInput = "";
+
+welcomeBox.textContent = maliciousInput;
+// The browser will LITERALLY display the text: ""
+// It will NOT run the script.
+
+```
+
+### **B. `.innerHTML` (For HTML - Powerful but Dangerous)**
+
+- **What it does:** Gets or sets the **full HTML markup** inside an element.
+- **Use Case:** Use this **only when you need to generate HTML** and the content is from a **trusted source** (i.e., you, the developer).
+
+```jsx
+// Let's create a more complex message
+const welcomeMessage = `
+ Welcome back, Alice!
+ You have 5 new messages.
+`;
+
+// Writing new HTML content
+welcomeBox.innerHTML = welcomeMessage;
+
+```
+
+**The Security Risk (XSS - Cross-Site Scripting):** Never use `.innerHTML` with content provided by a user (like a comment or a username). If a user enters malicious `