Skip to main content

CSS & HTML on Python Easily

Project description

Chope

CSS & HTML on Python Easily.

PyPI Pepy Total Downlods GitHub GitHub Workflow Status (with branch) PyPI - Python Version

Chope is a library that aims to provide a HTML and CSS domain-specific language (DSL) for Python. It draws inspiration from Clojure's Hiccup and JavaScript's Emotion.

Install

Chope can be installed through pip.

pip install chope

Syntax

Here is a basic example of Chope syntax:

from chope import *
from chope.css import *

page = html[
    head[
        style[
            Css[
                'body': dict(
                    background_color='linen',
                    font_size=pt/12
                ),
                '.inner-div': dict(
                    color='maroon',
                    margin_left=px/40
                )
            ]
        ]
    ],
    body[
        h1['Title'],
        div(class_='outer-div')[
            div(class_='inner-div')[
                'Some content.'
            ]
        ]
    ]
]

HTML

Declaring an element is as simple as this:

# <div>content</div>

div['content']

Element attributes can be specified like so:

# <div id="my-id" class="my-class your-class">content</div>

div(id='my-id', class_='my-class your-class')['content']

Notice the _ suffix in the class_ attribute. This suffix is necessary for any attribute names that clashes with any Python keyword.

You can also define id and class using CSS selector syntax:

# <div id="my-id" class="my-class your-class" title="Title">content</div>

div('#my-id.my-class.your-class', title='Title')['content']

Iterables can be used to generate a sequence of elements in the body of an element.

# <ul><li>0</li><li>1</li><li>2</li></ul>

ul[
    (li[str(i)] for i in range(3))
]

Creating custom elements

If you want to create a custom element with a custom tag, simply inherit from the Element class.

from chope import Element


class custom(Element):  ## class name will be used as tag name during rendering
    pass


custom['some content.']  ## <custom>some content.</custom>

Normally, you don't need to override any method of Element, but if you want to change how your element is rendered, you can override the render() method.

CSS

The CSS syntax in Chope is simply a mapping between CSS selector strings and declarations dictionaries.

Here's how a simple CSS stylesheet looks like in Chope:

'''
h1 {
    color: blue;
}

.my-class {
    background-color: linen;
    text-align: center;
}
'''

Css[
    'h1': dict(
        color='blue'
    ),
    '.my-class': dict(
        background_color='linen',
        text_align='center'
    )
]

# OR

Css[
    'h1': {
        'color': 'blue'
    },
    '.my-class': {
        'background-color': 'linen',
        'text-align': 'center'
    }
]

When you do declarations using the dict constructor, any _ will be converted to - automatically.

If your attribute name actually contains an _, declare using dictionary literal instead.

Units

Declaring size properties is very simple:

'''
.my-class {
    font-size: 14px;
    margin: 20%;
}
'''

Css[
    '.my-class': dict(
        font_size=px/14,
        margin=percent/20
    )
]

Chope supports standard HTML units. (e.g.em, rem, pt, etc.)

To set properties with multiple values, simply pass an iterable or a string.

'''
.my-class {
    padding: 58px 0 0;
}
'''

Css[
    '.my-class': dict(
        padding=(px/58, 0, 0)
    )
]

# OR

Css[
    '.my-class': dict(
        padding='58px 0 0'
    )
]

Render

Once you are done defining your CSS and HTML, you can render them into string using the render() method.

>>> page = html[
    head[
        style[
            Css[
                '.item': dict(font_size=px/14)
            ]
        ]
    ],
    body[
        div('#my-item.item')['My content.']
    ]
]
>>> print(page.render())
'<html>
  <head>
    <style>
      .item {
        font-size: 14px;
      }
    </style>
  </head>
  <body>
    <div id="my-item" class="item">
      My content.
    </div>
  </body>
</html>'

By default, render() will add indentations with 2 spaces. You can modify this using the indent keyword argument.

>>> print(page.render(indent=4))
'<html>
    <head>
        <style>
            .item {
                font-size: 14px;
            }
        </style>
    </head>
    <body>
        <div id="my-item" class="item">
            My content.
        </div>
    </body>
</html>'
>>> print(page.render(indent=0))  ## render flat string
'<html><head><style>.item {font-size: 14px;}</style></head><body><div id="my-item" class="item">My content.</div></body></html>'

CSS objects can also be rendered the same way.

>>> css = Css[
    'h1': dict(font_size=px/14),
    '.my-class': dict(
        color='blue',
        padding=(0,0,px/20)
    )
]
>>> print(css.render())
'h1 {
    font-size: 14px;
}

.my-class {
    color: blue;
    padding: 0 0 20px;
}'

Variable

If you'd like to build a HTML template, you can do so using the Var object.

from chope import *
from chope.variable import Var

template = html[
    div[Var('my-content')]
]

final_html = template.set_vars({'my-content': 'This is my content.'})

print(final_html.render(indent=0))  ## <html><div>This is my content.</div></html>

A variable can have a default value.

>>> print(div[Var('content', 'This is default content.')].render(indent=0))
<div>This is default content.</div>

Variable value can be set to an element.

>>> content = div[Var('inner')]
>>> new_content = content.set_vars({'inner': div['This is inner content.']})
>>> print(new_content.render())
<div>
  <div>
    This is inner content.
  </div>
</div>

Var works in an element attribute as well.

>>> content = div(name=Var('name'))['My content.']
>>> new_content = content.set_vars({'name': 'my-content'})
>>> print(new_content.render())
<div name="my-content">
  My content.
</div>

You can use Var in CSS too.

>>> css = Css[
    # CSS rule as a variable
    'h1': dict(font_size=Var('h1.font-size')),

    # CSS declaration as a variable
    '.my-class': Var('my-class')
]
>>> new_css = css.set_vars({'h1.font-size': px/1, 'my-class': {'color': 'blue'}})
>>> print(new_css.render())
h1 {
  font-size: 1px;
}

.my-class {
  color: blue;
}

The set of all variable names in an element/CSS can be retrieved using the get_vars() method.

>>> template = html[
    style[
        Css[
            'h1': dict(font_size=Var('css.h1.font-size'))
        ]
    ],
    div[
        Var('main-content'),
        div[
            Var('inner-content')
        ]
    ]
]
>>> print(template.get_vars())
{'main-content', 'inner-content', 'css.h1.font-size'}

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

chope-0.3.1.tar.gz (14.4 kB view details)

Uploaded Source

Built Distribution

chope-0.3.1-py3-none-any.whl (11.0 kB view details)

Uploaded Python 3

File details

Details for the file chope-0.3.1.tar.gz.

File metadata

  • Download URL: chope-0.3.1.tar.gz
  • Upload date:
  • Size: 14.4 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/4.0.2 CPython/3.9.16

File hashes

Hashes for chope-0.3.1.tar.gz
Algorithm Hash digest
SHA256 bb3cc84d1a1b9012bf407580e5b7f655837867910e84f29a20184699dbf9bf67
MD5 77b1f9215fc18c31344d7f0a9ecc6695
BLAKE2b-256 8acbe894a7728312c14b8e31448b23c96eeaab68232e6f4757e4a50ae1ea4739

See more details on using hashes here.

File details

Details for the file chope-0.3.1-py3-none-any.whl.

File metadata

  • Download URL: chope-0.3.1-py3-none-any.whl
  • Upload date:
  • Size: 11.0 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/4.0.2 CPython/3.9.16

File hashes

Hashes for chope-0.3.1-py3-none-any.whl
Algorithm Hash digest
SHA256 eedd65cdbff400f592c2e347f6d37cc8e0201426f4a4cae46443b44197b296ee
MD5 4d202840c41d7490104c393f3d57a4fa
BLAKE2b-256 a157e72a18b69d0b916ff1cea717a541c0520cf4d13ed6773dac0c5ca5ca89cf

See more details on using hashes here.

Supported by

AWS AWS Cloud computing and Security Sponsor Datadog Datadog Monitoring Fastly Fastly CDN Google Google Download Analytics Microsoft Microsoft PSF Sponsor Pingdom Pingdom Monitoring Sentry Sentry Error logging StatusPage StatusPage Status page