Сообщение onClick вызывает нежелательное обновление страницы - PullRequest
2 голосов
/ 30 марта 2020

Я пытаюсь создать сайт в Elm, и он включает в себя пару ссылок для изменения языка:

div [ class "language" ][ a [ class englishClass, onClick (ChangeLanguage English) ] [ text "EN" ]
                        , a [ class germanClass, onClick (ChangeLanguage German) ] [ text "DE" ]
                        , a [ class italianClass, onClick (ChangeLanguage Italian) ] [ text "IT" ]
                        ]

Мое обновление выглядит так:

update : Msg -> Model -> ( Model, Cmd Msg )
update msg model =
    case msg of
        ...  -- Stuff for URLs

        ChangeLanguage language ->
            ( { model | language = language }
            , Cmd.none
            )

type Msg
    = LinkClicked Browser.UrlRequest
    | UrlChanged Url.Url
    | ChangeLanguage Language

Это моя модель:

type alias Model =
    { key : Nav.Key
    , url : Url.Url
    , language : Language
    }

И это моя функция инициализации, которая (по крайней мере, на мой взгляд) по умолчанию использует английский язык sh:

init : flags -> Url.Url -> Nav.Key -> ( Model, Cmd Msg )
init _ url key = ( Model key url English, Cmd.none )

проблема:

Всякий раз, когда я нажимаю на ссылки, которые меняют язык, они делают , кажется, работают: я вижу, как меняется язык абзацев на странице, но затем появляются некоторые нежелательные вещи бывает:

  1. Страница обновляется. Поскольку я уже видел изменение языка по всей странице, ясно, что в этом нет необходимости, поэтому я бы хотел этого избежать.
  2. Как следствие 1, область просмотра переносится полностью в верхнюю часть страница снова.
  3. Язык снова меняется на английский по умолчанию sh снова!

Как я могу избежать 1 (и, следовательно, 2), чтобы это произошло?
И что я отсутствует, чтобы сделать так, чтобы изменение сохранялось по всему сайту (по крайней мере, при обновлении страницы, поскольку я еще не пробовал работать с сеансами или файлами cookie)?

1 Ответ

3 голосов
/ 31 марта 2020

Я считаю это поведение ошибкой в ​​Elm, и подал проблему для него, как и другие с связанными PR . Но в течение полутора лет с тех пор никто из тех, кто действительно может что-то с этим сделать, не получал никакого внимания, что, к сожалению, является нормой для Элма.

Проблема в том, что Элм "захватывает" onClick on a элементов для создания событий навигации, чтобы якоря могли обрабатываться в Elm. При использовании Browser.application при нажатии на элемент a вызов Elm будет onUrlReuqest со значением Browser.UrlRequest, который будет классифицировать URL-адрес как Internal или External и потребовать от вас принятия решения о том, что

Проблема в root этого состоит в том, что пропуск href сгенерирует External UrlRequest с URL, являющимся пустой строкой. По умолчанию и при обычной обработке External браузер загружает URL-адрес как обычно, обновляя страницу. Но это также предполагает, что возможный обходной путь - это специальный случай External "":

update msg model =
    case msg of
        UrlRequested (Browser.Internal _) ->
            ( model, Cmd.none )

        UrlRequested (Browser.External "") ->
            ( model, Cmd.none )

        UrlRequested (Browser.External url) ->
            ( model, Browser.Navigation.load url )

        UrlChanged _ ->
            ( model, Cmd.none )

Другой обходной путь - добавить href="#" к элементам a, что будет правильно классифицировать их как Internal

...