Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Extending the media modal? #249

Open
haleyngonadi opened this issue Dec 10, 2023 · 7 comments
Open

Extending the media modal? #249

haleyngonadi opened this issue Dec 10, 2023 · 7 comments
Labels
bug Something isn't working

Comments

@haleyngonadi
Copy link

Filament Version

v3.0.97

Plugin Version

v3.2.6

PHP Version

PHP 8.2

Problem description

Following up on this discussion: I'm trying to extend the existing MediaAction to allow for an "align" attribute.

Here's my custom MediaAction (which doesn't work)

<?php
[...]
class MediaAction extends Action
{
    public static function getDefaultName(): ?string
    {
        return 'filament_tiptap_media';
    }

    protected function setUp(): void
    {
        parent::setUp();

        $this
            ->arguments([
                'src' => '',
                'alt' => '',
                'title' => '',
                'align' => '',
                'width' => '',
                'height' => '',
            ])
            ->modalWidth('md')
            ->mountUsing(function (TiptapEditor $component, ComponentContainer $form, array $arguments) {
                $source = $arguments['src'] !== ''
                    ? $component->getDirectory() . Str::of($arguments['src'])
                    ->after($component->getDirectory())
                    : null;

                $form->fill([
                    'src' => $source,
                    'alt' => $arguments['alt'] ?? '',
                    'title' => $arguments['title'] ?? '',
                    'align' => $arguments['align'] ?? '',
                    'width' => $arguments['width'] ?? '',
                    'height' => $arguments['height'] ?? '',
                ]);
            })->modalHeading(function (TiptapEditor $component, array $arguments) {
                $context = blank($arguments['src'] ?? null) ? 'insert' : 'update';

                return __('filament-tiptap-editor::media-modal.heading.' . $context);
            })->form(function (TiptapEditor $component) {
                return [
                    FileUpload::make('src')
                        ->label(__('filament-tiptap-editor::media-modal.labels.file'))
                        ->disk($component->getDisk())
                        ->directory($component->getDirectory())
                        ->visibility(config('filament-tiptap-editor.visibility'))
                        ->preserveFilenames(config('filament-tiptap-editor.preserve_file_names'))
                        ->acceptedFileTypes($component->getAcceptedFileTypes())
                        ->maxFiles(1)
                        ->maxSize($component->getMaxFileSize())
                        ->imageResizeMode(config('filament-tiptap-editor.image_resize_mode'))
                        ->imageCropAspectRatio(config('filament-tiptap-editor.image_crop_aspect_ratio'))
                        ->imageResizeTargetWidth(config('filament-tiptap-editor.image_resize_target_width'))
                        ->imageResizeTargetHeight(config('filament-tiptap-editor.image_resize_target_height'))
                        ->required()
                        ->live()
                        ->afterStateUpdated(function (TemporaryUploadedFile $state, callable $set) {
                            if (Str::contains($state->getMimeType(), 'image')) {
                                $set('type', 'image');
                            } else {
                                $set('type', 'document');
                            }
                        })
                        ->saveUploadedFileUsing(function (BaseFileUpload $component, TemporaryUploadedFile $file, callable $set) {
                            $filename = $component->shouldPreserveFilenames() ? pathinfo($file->getClientOriginalName(), PATHINFO_FILENAME) : Str::uuid();

                            $storeMethod = $component->getVisibility() === 'public' ? 'storePubliclyAs' : 'storeAs';

                            if (Storage::disk($component->getDiskName())->exists(ltrim($component->getDirectory() . '/' . $filename . '.' . $file->getClientOriginalExtension(), '/'))) {
                                $filename = $filename . '-' . time();
                            }

                            if (Str::contains($file->getMimeType(), 'image')) {
                                if (config('filesystems.disks.s3.driver') === 's3') {
                                    $image = Image::make($file->readStream());
                                } else {
                                    $image = Image::make($file->getRealPath());
                                }

                                $set('width', $image->getWidth());
                                $set('height', $image->getHeight());
                            }

                            $upload = $file->{$storeMethod}($component->getDirectory(), $filename . '.' . $file->getClientOriginalExtension(), $component->getDiskName());

                            return Storage::disk($component->getDiskName())->url($upload);
                        }),
                    TextInput::make('link_text')
                        ->label(__('filament-tiptap-editor::media-modal.labels.link_text'))
                        ->required()
                        ->visible(fn (callable $get) => $get('type') == 'document'),
                    TextInput::make('alt')
                        ->label(__('filament-tiptap-editor::media-modal.labels.alt'))
                        ->hidden(fn (callable $get) => $get('type') == 'document')
                        ->hintAction(
                            Action::make('alt_hint_action')
                                ->label('?')
                                ->color('primary')
                                ->url('https://www.w3.org/WAI/tutorials/images/decision-tree', true)
                        ),
                    TextInput::make('title')
                        ->label(__('filament-tiptap-editor::media-modal.labels.title')),
                    Select::make('align')
                        ->label('Alignment')
                        ->options([
                            'left' => 'Left',
                            'center' => 'Center',
                            'right' => 'Right',
                        ]),
                    Hidden::make('width'),
                    Hidden::make('height'),
                    Hidden::make('type')
                        ->default('document'),
                ];
            })->action(function (TiptapEditor $component, $data) {
                if (config('filament-tiptap-editor.use_relative_paths')) {
                    $source = Str::replace(config('app.url'), '', $data['src']);
                } else {
                    $source = str_starts_with($data['src'], 'http')
                        ? $data['src']
                        : Storage::disk(config('filament-tiptap-editor.disk'))->url($data['src']);
                }

                $component->getLivewire()->dispatch(
                    'insert-content',
                    type: 'media',
                    statePath: $component->getStatePath(),
                    media: [
                        'src' => $source,
                        'alt' => $data['alt'] ?? null,
                        'title' => $data['title'],
                        'class' => $data['align'] ? 'align-' . $data['align'] : null,
                        'width' => $data['width'],
                        'height' => $data['height'],
                        'align' => $data['align'],
                        'link_text' => $data['link_text'] ?? null,
                    ],
                );
            });
    }
}

Expected behavior

When you insert an image, the "align" attribute should be added to the img tag, like so tag.

Steps to reproduce

N/A

Reproduction repository

No response

Relevant log output

No response

@haleyngonadi haleyngonadi added the bug Something isn't working label Dec 10, 2023
@awcodes
Copy link
Owner

awcodes commented Dec 16, 2023

According to MDN the 'align' attribute has been deprecated for images. https://developer.mozilla.org/en-US/docs/Web/HTML/Element/img#align

I recommend inserting the image then using the alignment tools from the toolbar.

@awcodes awcodes closed this as completed Dec 16, 2023
@haleyngonadi
Copy link
Author

Hi @awcodes, I wasn't trying to use the align attribute per se; I just wanted to be able to add a custom class to the image. Is that something that can be done?

@awcodes
Copy link
Owner

awcodes commented Dec 16, 2023

Ah. ok. i'll reopen then.

@awcodes awcodes reopened this Dec 16, 2023
@rubenlopezgea-at-coodex

Many time after this, I'm back.
I don't want to open a new issue, as it's the same subject.

It'd be great to be able to add more params.
For example, srcset or sizes (as I'm trying to do)
I can make the PHP part for it, but as soon as it gets to plugins.js, it removes all attributes not in this list:

filament-tiptap-editor/resources/js/plugin.js:465

.setImage({
    src: src,
    alt: media?.alt,
    title: media?.title,
    width: media?.width,
    height: media?.height,
    lazy: media?.lazy,
})

Here there's a list of all possible attributes:
https://developer.mozilla.org/en-US/docs/Web/HTML/Element/img#attributes

  • alt
  • crossorigin
  • decoding
  • elementimg
  • fetchpriority
  • height
  • ismap
  • loading
  • referrerpolicy
  • sizes
  • src
  • srcset
  • width
  • usemap

and of course, some global attributes as:

  • title
  • class
  • style
  • draggable
  • id

and some event handlers:

  • onload
  • onclick
  • onmouseenter
  • onmouseleave

Adding all those to plugin.js would help us to make any plugin with ease.

@awcodes
Copy link
Owner

awcodes commented Oct 23, 2024

I'm open to PRs. Haven't forgotten about the original issue. Just haven't had the time. Sorry.

@rubenlopezgea-at-coodex

The plugin is awesome. Let me first of all thank you for it.

I've already made a PR with those properties needed for responsive images coming from spatie/laravel-medialibrary

@awcodes
Copy link
Owner

awcodes commented Oct 23, 2024

I'll look at the PR when I get a chance. Thank you.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug Something isn't working
Projects
None yet
Development

No branches or pull requests

3 participants