dotswan / filament-map-picker

Map Picker is a Filament custom field designed to simplify the process of choosing a location on a map and obtaining its geo-coordinates.
MIT License
32 stars 10 forks source link

Error after map load #2

Closed threecolors-lab closed 3 months ago

threecolors-lab commented 3 months ago

I get error: App\Filament\Resources\MyResource::App\Filament\Resources{closure}(): Argument #3 ($old) must be of type ?string, array given, called in D:\www\vendor\filament\support\src\Concerns\EvaluatesClosures.php on line 35.

I use this code: Map::make('location') ->label('Location') ->columnSpanFull() ->afterStateUpdated(function (Get $get, Set $set, ?string $old, ?array $state): void { $set('latitude', $state['lat']); $set('longitude', $state['lng']); }) ->afterStateHydrated(function ($state, $record, Set $set): void { $set('location', ['lat' => $record->latitude, 'lng' => $record->longitude]); }) ->liveLocation() ->showMarker() ->markerColor("#22c55eff") ->showFullscreenControl() ->showZoomControl() ->draggable() ->tilesUrl("http://tile.openstreetmap.de/{z}/{x}/{y}.png") ->zoom(15) ->detectRetina() ->extraTileControl([]) ->extraControl([ 'zoomDelta' => 1, 'zoomSnap' => 2, ])

image

How to fix that error?

mohaphez commented 3 months ago

Hi ,

You can remove $old argument from afterStateUpdated or change type from ?string to ?array

If your problem is not solved or you have other questions Please do not hesitate to inform us.

threecolors-lab commented 3 months ago

Thanks for your fast response. The problem can be resolved. But there is a new problem after I save the coordinates of a location into the database, then I open the edit option, the map displayed is not the location that is saved in the database. What could be the problem?

mohaphez commented 3 months ago

Do you have latitude and longitude column in your database table ?

also, make sure you can get correct value from $record?->latitude and $record?->longitude in

->afterStateHydrated(function ($state, $record, Set $set): void {
                    $set('location', ['lat' => $record?->latitude, 'lng' => $record?->longitude]);
                })
threecolors-lab commented 3 months ago

I have created three fields but the problem still persists:

$table->double('latitude')->nullable(); $table->double('longitude')->nullable(); $table->json('location')->nullable();

Is it correct?

mohaphez commented 3 months ago

I don't think that after saving the form, something will be inside latitude & longitude , right?

In this case, you do not need the location column Just add these two fields to your form.

TextInput::make('latitude')
                ->hiddenLabel()
                ->hidden(),

 TextInput::make('longitude')
                ->hiddenLabel()
                ->hidden()

If you want the values ​​not to be displayed numerically, hide them like code . otherwise , you can remove hidden() and set readOnly().

If you want it to be a location field, in that case you don't need the latitude and longitude columns and you have to write something like Attribute, the filament codes will be different in that case.


class YourModel extends Model
{
    protected function location(): Attribute
    {
        return Attribute::make(
        get: fn (mixed $value, array $attributes) => [ 'latitude' => $attributes['latitude'], 'longitude' =>  $attributes['longitude']],
        set: fn (array $value) => [
            'latitude' => $value->['latitude'],
            'longitude' => $value[longitude],
        ],
    );
    }
}

My preference is the first solution.

threecolors-lab commented 3 months ago

Thats right. I have implemented this:

TextInput::make('latitude') ->hiddenLabel() ->hidden(),

TextInput::make('longitude') ->hiddenLabel() ->hidden()

but I did not implement this:

class YourModel extends Model { protected function location(): Attribute { return Attribute::make( get: fn (mixed $value, array $attributes) => [ 'latitude' => $attributes['latitude'], 'longitude' => $attributes['longitude']], set: fn (array $value) => [ 'latitude' => $value->['latitude'], 'longitude' => $value[longitude], ], ); } }

and everything works perfectly for me! Thank you for your help. I really like this plugin.