To output our own goals,
I'll add a new component in the components folder and to keep it manageable,
I'll actually create a new subfolder for every component,
this is not a must do but I personally like doing this because then I can quickly find all my components.
Of course you now need to adjust your import here in app.js,
my IDE did it automatically, in case that did not happen,
make sure you adjust your goal list import to reflect that new folder
I added and then I will add a new goals component here in the components folder as well, in there
add a new goal.js file and a new goal.css
file
if we want to apply some styling. Now in the NewGoal.js file, we first of all need to import React
from React,
you always need to do that
otherwise you can't use jsx in that file because keep in mind, jsx is translated to React create
element and then here, I have my new goal component here.
We could accept props but as long as we don't need them,
we don't have to
and then I export new goal. Now in app.js,
I want to render new goal, so I will import new goal,
again the name here is up to you but it should start with a capital starting character and I import
this from components, new goal, new goal and then here we can render this above our goal list let's say
like that.
Now this wouldn't work because new goal is not yet a valid React component because it's a function right
now but it's not a function that works as a React component because it's not doing one crucial thing,
it's not returning jsx, so let's return some jsx here and there to keep things simple, I'll add a form
and in that form, I'll add an input field, type text, self closing element. In regular HTML,
this doesn't have to be self closing, in jsx this does have to be self closing and then a button which
is of type
submit where I say add goal. A very simple form and if we now save that, you should see it here.
Now let's add some styling to make this look a bit prettier,
for that I'll add a class to the form, new-goal and I'll import the NewGoal.css file into the
NewGoal.js file
and then here on the new goal class which is added on the form, I'll add a margin of 2rem in all directions
and text align
center so that this looks a bit nicer
and now we could also style the input and the button but I don't want to spend too much time on that,
so I will leave it the way it is. Now right now when you click the button by the way,
this page will reload because right now the default browser functionality will kick in, which is that
when a button of type submit is clicked in a form, a request is sent to the server that served this
page.
Now that's not the behavior we want here though because here, I don't want to send a request to any server
because we're not doing anything on the server side,
instead I want a handle that click with Javascript and that is the first thing I'll do here.
Let's see how we can handle events because thus far, we haven't done that.
I want to handle the submit event of this form here and React makes that simple,
we can add event listeners to any element, not just to the form but to any element, by adding on, lowercase
on and then the name of the event.
Now not every event is supported on every element but here you've got the default HTML elements
available,
so for example on a form element, you have the submit event, on submit. On a button, you also have on click
but since it's a button in a form, it's better to handle this on the form itself. Now what do you pass
as a value to on submit though? As a value,
you have to pass a function that should be triggered when this event happens,
so a pointer to a function.
You could do this here with curly braces and then an anonymous inline function
but I don't like that too much,
instead I will create a new function here and in Javascript, you can create functions in functions.
So inside of the new goal function which it still is in the end, I can create a new function,
I will create my add goal handler.
Now the naming is up to you
but I like this naming of having handler at the end of my function name
if it is a function that is triggered upon some event.
So this is a function,
in this case I'll again use an arrow function which is not a must do but I will use only arrow functions
here and on submit
now can point at add goal handler.
Don't execute it here, so don't add parentheses,
instead you just want to point at the function so that the browser and React in a common effort can
execute this function for you when this submit event occurs.
Now this function will get an event object, an event parameter passed in automatically by React and
there for example we can call prevent default, which prevents the browser default of sending a request
to some backend, which it shouldn't do here because we're not handling this on the server side here.
Our server only serves that single index.html file, it does not have any logic to handle any submissions.
Instead I want to handle it here in Javascript on the frontend, in my React application and for the
moment, I'll ignore what the user entered here and I will simply instead create a dummy goal and I want
to pass that dummy goal to app.js and add it to my course goals here so that it then is rendered here.
Now step-by-step, we can create a new dummy goal of course in that add goal handler by adding a new goal
constant here which is a Javascript object,
the ID here could be a random number with math random,
this of course is not really a unique ID but it's good enough and I'll convert it to a string,
it's good enough for our demo application here I mean and then the text here later will be the text
the user entered here, for now just some dummy text,
my new goal.
So now we have the new goal here and of course we can console log that to see that everything up to
this point works.
So if we save that, we see our form here
and if I click on add goal, the page will not reload but instead we see this dummy goal here and I can
create of course multiple goals but at the moment, they're not added to this list. To add them to the
list,
we now need to get that goal out of the new goal component to the app component.
Now before, we learned we can pass data around the props but that was from app to goal list,
so to a lower level component, a component which is included in app,
now it's the other direction, we want to pass data from new goal to the parent component, so to the component
which includes the new goal component.
How does this work?