Lucius mixins cause "unexpected end of input", Can't find end of block

106 Views Asked by At

I'm trying to use mixins in Yesod's Lucius, but have run into a problem. Currently my 'center' mixin is the only one that seems to work, which also happens to be the only mixin without variable interpolation, although I'm not sure that is related to the problem the problem.

Lucius:

@keyframes blink {
    0%   {opacity: 0}
    40%  {opacity: 0.8}
    80%  {opacity: 0}
    100% {opacity: 0}
}

@-webkit-keyframes blink {
    0%   {opacity: 0}
    40%  {opacity: 0.8}
    80%  {opacity: 0}
    100% {opacity: 0}
}


html, body {
    height: 100%;
    margin: 0;
}

*, *:after, *:before {
    text-rendering: optimizeLegibility;
    -webkit-font-smoothing: antialiased;
    -moz-osx-font-smoothing: grayscale;
    ^{box-sizing "inherit"}
}

header {
    min-height: 100%;
    z-index: 0;
    background-image: url(@{StaticR images_landing__jpg});
    background-position: center center;
    background-size: cover;

    .greeting {
        min-width: 30%;
        padding: 3%;
        background-image: url(@{StaticR images_neg_lines_png});
        background-repeat: repeat;
        text-align: center;
        ^{center "both"}
        color: whitesmoke;

        h2, h4 {
            font-family: "Lato";
            font-weight: 300;
        }
        h4 {
            font-family: "Lato";
            ^{font-size 20}
        }
        h1 {
            font-family: "Tangerine";
            font-weight: bold;
            color: #ffffff;
            ^{font-size 96}
        }
    }

    .scroll-link {
        ^{center "x"}
        bottom: 5%;
        .scroll-arrow {
            display: inline;
            path {
                stroke: white;
                fill: transparent;
                stroke-width: 1px;
                animation: blink 2s infinite;
                -webkit-animation: blink 2s infinite;
            }
            path.a1 {
                animation-delay: -1s;
                -webkit-animation-delay: -1s;
            }
            path.a2 {
                animation-delay: -0.5s;
                -webkit-animation-delay: -0.5s;
            }
            path.a3 {
                animation-delay: 0s;
                -webkit-animation-delay: 0s;
            }
        }
    }
}

.main-container {
    background: whitesmoke;
}

Mixins:

{-# LANGUAGE QuasiQuotes #-}
module Mixins
    ( center
    , box_sizing
    , font_size
    , unlink
    ) where

import Text.Lucius
import ClassyPrelude.Yesod

center :: String -> Mixin
center axis
  | axis == "x" =
    [luciusMixin|
        left: 50%;
        -webkit-transform: translate(-50%, 0);
        -ms-transform: translate(-50%, 0);
        transform: translate(-50%, 0);
    |]
  | axis == "y" =
    [luciusMixin|
        top: 50%;
        -webkit-transform: translate(0, -50%);
        -ms-transform: translate(0, -50%);
        transform: translate(0, -50%);
    |]
  | otherwise =
    [luciusMixin|
        top: 50%;
        left: 50%;
        -webkit-transform: translate(-50%, -50%);
        -ms-transform: translate(-50%, -50%);
        transform: translate(-50%, -50%);
    |]

box_sizing :: String -> Mixin
box_sizing box_model =
  [luciusMixin|
        -webkit-box-sizing: #{box_model};
        -moz-box-sizing: #{box_model};
        box-sizing: #{box_model};
  |]

font_size :: Double -> Mixin
font_size size =
  [luciusMixin|
        font-size: #(pxsize}px;
        font-size: #(remsize)rem;
  |]
  where
    pxsize = show size
    remsize = show $ size * 0.125

unlink :: String -> Mixin
unlink color =
  [luciusMixin|
        color: #{color};
        text-decoration: none;
  |]

Error:

[...]/Foundation.hs:132:15:
    Exception when trying to run compile-time code:
      "
[...]
" (line 94, column 1)
unexpected end of input
expecting "/*", "}", "#", "@" or "{"
checkIfBlock
    Code: widgetFile "default-layout"
    In the splice: $(widgetFile "default-layout")

Things I've troubleshot:

  • Add trailing semicolons -> No effect
  • Remove all mixins but 'center' -> Compiles
  • Remove all mixins but 'box_sizing' and make static (no interpolation) -> No effect

It's quite possible I'm missing something obvious, and I'd hate to be that guy, however there's not much in the way of documentation for these types of things. Perhaps this can help someone else in a similar position.

Anyways, any and all help is appreciated.

EDIT:

As it turns out, after merging some separate lucius files, the 'unlink' mixin also compiles without error. Due to the fact that it is, structurally speaking, essentially identical to other mixins such as 'box_sizing' I now know that interpolation is not the culprit, nor the formatting of the function (Guards vs. Equation).

I'm becoming more and more suspicious of the formatting in the Lucius file as it seems the Haskell code is insignificant. I'm starting to feel the problem might just be basic css syntax error that i'm blind to for whatever reason.

EDIT 2:

I have merged the Lucius code for my navbar, which revealed that a mixin that could not previously compile, under certain (albeit unknown) circumstances, can succeed.

The relevant code:
(note the 'font_size' mixin succesfully compiles in this code)

/* Navbar */
@navheight: 6rem;

nav {
    z-index: 10000;
    position: absolute;
    background-color: transparent;
    color: rgba(255, 255, 255, 1);
    height: #{navheight};
    line-height: #{navheight};
    ^{font-size 16};
    .left {
        padding-left: 2rem;
        padding-right: 2rem;
        height: #{navheight};

        .brand {
            display: inline;
            font-family: "Lato";
            font-weight: bold;
            ^{unlink "inherit"};
        }
        .more {
            display: inline;
            font-family: "Lato";
        }
    }

    .right {
        height: #{navheight};
        ul li {
            display: inline-block;
            padding-left: 2rem;
            padding-right: 2rem;
            a {
                font-family: "RaleWay";
                display: block;
                text-align: center;
                ^{unlink "inherit"};
            }
        }
    }
}
2

There are 2 best solutions below

0
On BEST ANSWER

Well, the error was caused by a few typos (font-size -> font_size; box-sizing -> box_sizing), sadly I had glazed over the idea of a naming error due to the fact that I was not getting a 'font-size' is not in scope error. The parser was seeing the - as subtraction due to the fact that they are not allowed in haskell function names. On the plus side, I now know the insides of Yesod and shakespeare very well, and can hopefully help people with actual problems.

1
On

I suspect, there it is

font_size :: Double -> Mixin
font_size size =
  [luciusMixin|
        font-size: #(pxsize}px;
        font-size: #(remsize)rem;
  |]

Note #(pxsize}px.