In this post, I covered from minute 2:54:50 until 3:12:56 of this video.
Editing the profile image
The way we're getting the image and store it in a folder is the same as we
done for the post controller when user uploaded an image to a post, with a
minor change to the stored location. We will store the profile image in
profile
folder instead of posts
. Another thing is, when we want to pass the
data, instead of passing it as a normal array, we will use a php function
called array_merge
. This function takes any number of array and appends
them together. At line 41 and 42 of the code below, the $data
array does have
a key of image but the second array ['image' => $imagePath]
overrides
that image.
22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 |
public function update(User $user)
{
$this->authorize('update', $user->profile);
$data = request()->validate([
'title' => '',
'description' => '',
'url' => 'url',
'image' => ''
]);
if (request('image')) {
$imagePath = request('image')->store('profile', 'public');
$image = Image::make(public_path("storage/{$imagePath}"))->fit(1000, 1000);
$image->save();
}
auth()->user()->profile->update(array_merge(
$data,
['image' => $imagePath]
));
return redirect("/profile/{$user->id}");
}
|
app > Http > Controllers > ProfilesController.php
To see what the
array_merge
do clearly, let's try die and dump it.
dd($data)
array_merge
This should be ready to go. However, if we look at profiles table, we don't
really have anything for image so we're going to add it. If not, we definitely
will run into error that says the image table doesn't exist.
16 17 18 19 20 21 22 23 24 25 26 |
Schema::create('profiles', function (Blueprint $table) {
$table->id();
$table->foreignId('user_id');
$table->string('title')->nullable();
$table->text('description')->nullable();
$table->string('url')->nullable();
$table->string('image')->nullable();
$table->timestamps();
$table->index('user_id');
});
|
database > migrations >
2021_12_28_130508_create_profiles_table.php
Now that we have changed the Schema, we need to remake our database. Always
remember to remake database every time you can change anything for migrations!
Let's run
php artisan migrate:fresh
. This will erase everything so we're
going to start from scratch again.
Create A Profile Using Model Events
Let's go ahead an register. After registered, when you try to open your
profile, you will get an error. This error is because when we creating a user,
we are not creating a profile for them. There is no record of user in the
profiles table. So as part of our registration, we really need to create
kind of a blank profile for user so they can start using it and edit it.
There are several ways to overcome this. What we're going to do is hooking up
an event in the user model. Something that says, "Hey, I am creating a
new user, is there anything else that I should do?".
There is this method called
boot
. This boot method is what gets called when we
are booting up the model. In the method, we hook a created event. Please refer
to
Events
in the documentation. There are creating
, created
, updating
, updated
and
many others. The different between '-ing' and '-ed' is, '-ing' gets called before it
actually creates the record and database, '-ed' is after it's done. In our case,
we're using created
, meaning that, after the record for user has been created,
we then create the profile for that user. We can just create an empty profile
for that user with $user->profile()->create()
but let's say if we want
to add a default value for some of the table, we can write it like line 51 -
53. The lines mean that we set the default value for user's title the same as
their username.
41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 |
protected $casts = [
'email_verified_at' => 'datetime',
];
protected static function boot()
{
parent::boot();
static::created(function ($user) {
$user->profile()->create([
'title' => $user->username
]);
});
}
|
app > models > User.php
Let's try registering a new user again! It should be working and look like
this:
Displaying the profile image
Right now, our profile image is still hardcoded. We need to pull the image and
display it properly.
6 7 8 |
<div class="col-4 d-flex align-items-center justify-content-center"> <img src="/storage/{{ $user->profile->image }}" class="rounded-circle w-100" style="border: 1px solid #e4e3e1"> </div> |
resources > views > profiles > index.blade.php
By default, the profile image is empty so you will get a broken image until
you upload a new image in edit profile page. We will fix this later.
Adjusting the view for individual post page
Now for the individual post page, again, we need to pull the image from our
table, and style the page to make it look as closely as possible to Instagram.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 | @extends('layouts.app')
@section('content')
<div class="container">
<div class="row">
<div class="col-8">
<img src="/storage/{{ $post->image }}" class="w-100">
</div>
<div class="col-4">
<div class="d-flex align-items-center">
<img src="/storage/{{ $post->user->profile->image }}" class="rounded-circle mr-3" style="width:40px;border: 1px solid #e4e3e1">
<a href="/profile/{{ $post->user->id }}" class="font-weight-bold text-dark">{{ $post->user->username }}</a>
<a href="#" class="font-weight-bold pl-3">Follow</a>
</div>
<hr>
<p>
<a href="/profile/{{ $post->user->id }}" class="font-weight-bold text-dark">{{ $post->user->username }}</a>
<span>{{ $post->caption }}</span>
</p>
</div>
</div>
</div>
@endsection
|
resources > views > profiles > show.blade.php
It's finally looking more like Instagram post now.
That's all for now. In the next part, we will learn on how to add a default profile image and make it possible that a user doesn't need to upload profile image every single time they want to edit something in their profile.
No comments:
Post a Comment