touchable-templates 2026.2.1a0__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- touchable_templates-2026.2.1a0/.gitignore +10 -0
- touchable_templates-2026.2.1a0/LICENSE +21 -0
- touchable_templates-2026.2.1a0/PKG-INFO +125 -0
- touchable_templates-2026.2.1a0/README.md +114 -0
- touchable_templates-2026.2.1a0/pyproject.toml +31 -0
- touchable_templates-2026.2.1a0/src/touchable_templates/static/js/touchable_templates.js +66 -0
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2026 bradywhitby
|
|
4
|
+
|
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
6
|
+
of this software and associated documentation files (the "Software"), to deal
|
|
7
|
+
in the Software without restriction, including without limitation the rights
|
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
|
10
|
+
furnished to do so, subject to the following conditions:
|
|
11
|
+
|
|
12
|
+
The above copyright notice and this permission notice shall be included in all
|
|
13
|
+
copies or substantial portions of the Software.
|
|
14
|
+
|
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
21
|
+
SOFTWARE.
|
|
@@ -0,0 +1,125 @@
|
|
|
1
|
+
Metadata-Version: 2.4
|
|
2
|
+
Name: touchable-templates
|
|
3
|
+
Version: 2026.2.1a0
|
|
4
|
+
Summary: A dev tool that magically opens templates and partials in your IDE
|
|
5
|
+
Author: Brady Whitby
|
|
6
|
+
License-Expression: MIT
|
|
7
|
+
License-File: LICENSE
|
|
8
|
+
Requires-Python: >=3.10
|
|
9
|
+
Requires-Dist: beautifulsoup4>=4.9.2
|
|
10
|
+
Description-Content-Type: text/markdown
|
|
11
|
+
|
|
12
|
+
|
|
13
|
+
# touchable-templates
|
|
14
|
+
|
|
15
|
+
touchable-templates is a small developer helper that wraps rendered templates in a lightweight
|
|
16
|
+
HTML marker and ships a tiny client-side script so you can, for example, click
|
|
17
|
+
on a rendered component in the browser to automatically open the source template in your IDE.
|
|
18
|
+
|
|
19
|
+
This package is purposely minimal and designed to be installed into Django projects.
|
|
20
|
+
Note: Future versions may support Jinja2, Flask, and other frameworks. This package is not intended to be used in production.
|
|
21
|
+
|
|
22
|
+
## Key features
|
|
23
|
+
|
|
24
|
+
- Server-side wrapper for Django template responses (middleware)
|
|
25
|
+
- Small client-side script included as package static files
|
|
26
|
+
|
|
27
|
+
## Installation
|
|
28
|
+
|
|
29
|
+
### pip install
|
|
30
|
+
|
|
31
|
+
```bash
|
|
32
|
+
pip install touchable-templates
|
|
33
|
+
```
|
|
34
|
+
|
|
35
|
+
### uv install
|
|
36
|
+
|
|
37
|
+
```bash
|
|
38
|
+
uv add touchable-templates
|
|
39
|
+
```
|
|
40
|
+
|
|
41
|
+
## Django integration (quick start)
|
|
42
|
+
|
|
43
|
+
1. Add the app to your `INSTALLED_APPS` in `settings.py`:
|
|
44
|
+
|
|
45
|
+
```py
|
|
46
|
+
INSTALLED_APPS = [
|
|
47
|
+
# ...
|
|
48
|
+
"touchable_templates",
|
|
49
|
+
]
|
|
50
|
+
```
|
|
51
|
+
|
|
52
|
+
2. Add the middleware so HTML responses are post-processed to convert wrapper containers
|
|
53
|
+
into elements with the `touchable-templates` class (the client script uses that):
|
|
54
|
+
|
|
55
|
+
```py
|
|
56
|
+
MIDDLEWARE = [
|
|
57
|
+
# ...
|
|
58
|
+
"touchable_templates.django.middleware.TouchableTemplatesMiddleware",
|
|
59
|
+
# ...
|
|
60
|
+
]
|
|
61
|
+
```
|
|
62
|
+
|
|
63
|
+
3. Configure enablement and IDE mapping. You can set these via environment variables or
|
|
64
|
+
in `settings.py`. Example (development):
|
|
65
|
+
|
|
66
|
+
```py
|
|
67
|
+
# TOUCHABLE_TEMPLATES settings (example)
|
|
68
|
+
TOUCHABLE_TEMPLATES_ENABLE = True
|
|
69
|
+
TOUCHABLE_TEMPLATES_IDE = "vscode"
|
|
70
|
+
# Optional settings: Use if your project is dockerized or paths need adjustment
|
|
71
|
+
TOUCHABLE_TEMPLATES_ROOT = "/full/path/to/your/project/root/on/local/machine"
|
|
72
|
+
TOUCHABLE_TEMPLATES_REMOVE_PREFIX = "project/root/in/docker/container"
|
|
73
|
+
```
|
|
74
|
+
|
|
75
|
+
## Supported IDEs
|
|
76
|
+
|
|
77
|
+
- `atom`
|
|
78
|
+
- `codelite`
|
|
79
|
+
- `cursor`
|
|
80
|
+
- `emacs`
|
|
81
|
+
- `espresso`
|
|
82
|
+
- `idea`
|
|
83
|
+
- `macvim`
|
|
84
|
+
- `netbeans`
|
|
85
|
+
- `nova`
|
|
86
|
+
- `pycharm`
|
|
87
|
+
- `sublime`
|
|
88
|
+
- `textmate`
|
|
89
|
+
- `vscode`
|
|
90
|
+
- `vscode-insiders`
|
|
91
|
+
- `vscode-insiders-remote`
|
|
92
|
+
- `vscode-remote`
|
|
93
|
+
- `vscodium`
|
|
94
|
+
- `xdebug`
|
|
95
|
+
|
|
96
|
+
4. Include the client JavaScript in your base template (requires `django.contrib.staticfiles`):
|
|
97
|
+
Add Script tag at the end of the body, or in the head.
|
|
98
|
+
|
|
99
|
+
```django
|
|
100
|
+
{% load static %}
|
|
101
|
+
<script src="{% static 'js/touchable_templates.js' %}"></script>
|
|
102
|
+
```
|
|
103
|
+
|
|
104
|
+
## Use
|
|
105
|
+
|
|
106
|
+
Press the `alt` or `opt` key to toggle the functionality on and off.
|
|
107
|
+
Moving your mouse around the page you will see a floating element indicating the template path/name
|
|
108
|
+
Click on any element on the page to open the corresponding template in your configured IDE.
|
|
109
|
+
|
|
110
|
+
## Notes
|
|
111
|
+
|
|
112
|
+
- The middleware only processes responses with `Content-Type: text/html` to ensure we are not processing json requests.
|
|
113
|
+
- Make sure `TOUCHABLE_TEMPLATES_ENABLE` is `True` in development and `False` in production.
|
|
114
|
+
- Use `TOUCHABLE_TEMPLATES_REMOVE_PREFIX` to strip any leading path segments that are
|
|
115
|
+
not part of the local filesystem path (e.g. if your project runs in a Docker container
|
|
116
|
+
with a different root path).
|
|
117
|
+
|
|
118
|
+
## Troubleshooting
|
|
119
|
+
|
|
120
|
+
- No overlay appears: verify `TOUCHABLE_TEMPLATES_ENABLE` is True and the JS is loaded correctly (check browser devtools network tab).
|
|
121
|
+
- Alt-click does nothing: ensure the HTML elements have `touchable-templates` class (middleware unwraps container into children).
|
|
122
|
+
|
|
123
|
+
## License
|
|
124
|
+
|
|
125
|
+
MIT License (MIT)
|
|
@@ -0,0 +1,114 @@
|
|
|
1
|
+
|
|
2
|
+
# touchable-templates
|
|
3
|
+
|
|
4
|
+
touchable-templates is a small developer helper that wraps rendered templates in a lightweight
|
|
5
|
+
HTML marker and ships a tiny client-side script so you can, for example, click
|
|
6
|
+
on a rendered component in the browser to automatically open the source template in your IDE.
|
|
7
|
+
|
|
8
|
+
This package is purposely minimal and designed to be installed into Django projects.
|
|
9
|
+
Note: Future versions may support Jinja2, Flask, and other frameworks. This package is not intended to be used in production.
|
|
10
|
+
|
|
11
|
+
## Key features
|
|
12
|
+
|
|
13
|
+
- Server-side wrapper for Django template responses (middleware)
|
|
14
|
+
- Small client-side script included as package static files
|
|
15
|
+
|
|
16
|
+
## Installation
|
|
17
|
+
|
|
18
|
+
### pip install
|
|
19
|
+
|
|
20
|
+
```bash
|
|
21
|
+
pip install touchable-templates
|
|
22
|
+
```
|
|
23
|
+
|
|
24
|
+
### uv install
|
|
25
|
+
|
|
26
|
+
```bash
|
|
27
|
+
uv add touchable-templates
|
|
28
|
+
```
|
|
29
|
+
|
|
30
|
+
## Django integration (quick start)
|
|
31
|
+
|
|
32
|
+
1. Add the app to your `INSTALLED_APPS` in `settings.py`:
|
|
33
|
+
|
|
34
|
+
```py
|
|
35
|
+
INSTALLED_APPS = [
|
|
36
|
+
# ...
|
|
37
|
+
"touchable_templates",
|
|
38
|
+
]
|
|
39
|
+
```
|
|
40
|
+
|
|
41
|
+
2. Add the middleware so HTML responses are post-processed to convert wrapper containers
|
|
42
|
+
into elements with the `touchable-templates` class (the client script uses that):
|
|
43
|
+
|
|
44
|
+
```py
|
|
45
|
+
MIDDLEWARE = [
|
|
46
|
+
# ...
|
|
47
|
+
"touchable_templates.django.middleware.TouchableTemplatesMiddleware",
|
|
48
|
+
# ...
|
|
49
|
+
]
|
|
50
|
+
```
|
|
51
|
+
|
|
52
|
+
3. Configure enablement and IDE mapping. You can set these via environment variables or
|
|
53
|
+
in `settings.py`. Example (development):
|
|
54
|
+
|
|
55
|
+
```py
|
|
56
|
+
# TOUCHABLE_TEMPLATES settings (example)
|
|
57
|
+
TOUCHABLE_TEMPLATES_ENABLE = True
|
|
58
|
+
TOUCHABLE_TEMPLATES_IDE = "vscode"
|
|
59
|
+
# Optional settings: Use if your project is dockerized or paths need adjustment
|
|
60
|
+
TOUCHABLE_TEMPLATES_ROOT = "/full/path/to/your/project/root/on/local/machine"
|
|
61
|
+
TOUCHABLE_TEMPLATES_REMOVE_PREFIX = "project/root/in/docker/container"
|
|
62
|
+
```
|
|
63
|
+
|
|
64
|
+
## Supported IDEs
|
|
65
|
+
|
|
66
|
+
- `atom`
|
|
67
|
+
- `codelite`
|
|
68
|
+
- `cursor`
|
|
69
|
+
- `emacs`
|
|
70
|
+
- `espresso`
|
|
71
|
+
- `idea`
|
|
72
|
+
- `macvim`
|
|
73
|
+
- `netbeans`
|
|
74
|
+
- `nova`
|
|
75
|
+
- `pycharm`
|
|
76
|
+
- `sublime`
|
|
77
|
+
- `textmate`
|
|
78
|
+
- `vscode`
|
|
79
|
+
- `vscode-insiders`
|
|
80
|
+
- `vscode-insiders-remote`
|
|
81
|
+
- `vscode-remote`
|
|
82
|
+
- `vscodium`
|
|
83
|
+
- `xdebug`
|
|
84
|
+
|
|
85
|
+
4. Include the client JavaScript in your base template (requires `django.contrib.staticfiles`):
|
|
86
|
+
Add Script tag at the end of the body, or in the head.
|
|
87
|
+
|
|
88
|
+
```django
|
|
89
|
+
{% load static %}
|
|
90
|
+
<script src="{% static 'js/touchable_templates.js' %}"></script>
|
|
91
|
+
```
|
|
92
|
+
|
|
93
|
+
## Use
|
|
94
|
+
|
|
95
|
+
Press the `alt` or `opt` key to toggle the functionality on and off.
|
|
96
|
+
Moving your mouse around the page you will see a floating element indicating the template path/name
|
|
97
|
+
Click on any element on the page to open the corresponding template in your configured IDE.
|
|
98
|
+
|
|
99
|
+
## Notes
|
|
100
|
+
|
|
101
|
+
- The middleware only processes responses with `Content-Type: text/html` to ensure we are not processing json requests.
|
|
102
|
+
- Make sure `TOUCHABLE_TEMPLATES_ENABLE` is `True` in development and `False` in production.
|
|
103
|
+
- Use `TOUCHABLE_TEMPLATES_REMOVE_PREFIX` to strip any leading path segments that are
|
|
104
|
+
not part of the local filesystem path (e.g. if your project runs in a Docker container
|
|
105
|
+
with a different root path).
|
|
106
|
+
|
|
107
|
+
## Troubleshooting
|
|
108
|
+
|
|
109
|
+
- No overlay appears: verify `TOUCHABLE_TEMPLATES_ENABLE` is True and the JS is loaded correctly (check browser devtools network tab).
|
|
110
|
+
- Alt-click does nothing: ensure the HTML elements have `touchable-templates` class (middleware unwraps container into children).
|
|
111
|
+
|
|
112
|
+
## License
|
|
113
|
+
|
|
114
|
+
MIT License (MIT)
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
[project]
|
|
2
|
+
name = "touchable-templates"
|
|
3
|
+
version = "2026.02.1a"
|
|
4
|
+
description = "A dev tool that magically opens templates and partials in your IDE"
|
|
5
|
+
readme = "README.md"
|
|
6
|
+
license = "MIT"
|
|
7
|
+
authors = [
|
|
8
|
+
{ name = "Brady Whitby" }
|
|
9
|
+
]
|
|
10
|
+
requires-python = ">=3.10"
|
|
11
|
+
dependencies = [
|
|
12
|
+
"beautifulsoup4>=4.9.2",
|
|
13
|
+
]
|
|
14
|
+
|
|
15
|
+
[build-system]
|
|
16
|
+
requires = ["hatchling"]
|
|
17
|
+
build-backend = "hatchling.build"
|
|
18
|
+
|
|
19
|
+
[[tool.uv.index]]
|
|
20
|
+
name = "testpypi"
|
|
21
|
+
url = "https://test.pypi.org/simple/"
|
|
22
|
+
publish-url = "https://test.pypi.org/legacy/"
|
|
23
|
+
explicit = true
|
|
24
|
+
|
|
25
|
+
[tool.hatch.build]
|
|
26
|
+
include = [
|
|
27
|
+
"src/touchable_templates/static/**",
|
|
28
|
+
]
|
|
29
|
+
[tool.hatch.build.targets.wheel]
|
|
30
|
+
packages = ["src/touchable_templates"]
|
|
31
|
+
|
|
@@ -0,0 +1,66 @@
|
|
|
1
|
+
let altToggled = false;
|
|
2
|
+
|
|
3
|
+
// Append the element to the DOM, for example, to the body
|
|
4
|
+
var elemDiv = document.createElement('div');
|
|
5
|
+
elemDiv.id = 'floating-template-name';
|
|
6
|
+
elemDiv.style.cssText = "display: none; position: absolute; background: white; border: 1px solid black; padding: 5px; z-index: 9999;"
|
|
7
|
+
document.body.appendChild(elemDiv);
|
|
8
|
+
const floatingElement = document.getElementById("floating-template-name");
|
|
9
|
+
|
|
10
|
+
document.addEventListener("DOMContentLoaded", function(event) {
|
|
11
|
+
|
|
12
|
+
document.addEventListener('keydown', function(event) {
|
|
13
|
+
if (event.key === 'Alt') {
|
|
14
|
+
altToggled = !altToggled;
|
|
15
|
+
if (!altToggled) {
|
|
16
|
+
floatingElement.style.display = 'none';
|
|
17
|
+
}
|
|
18
|
+
}
|
|
19
|
+
});
|
|
20
|
+
|
|
21
|
+
document.addEventListener('click', function(event) {
|
|
22
|
+
if (altToggled) {
|
|
23
|
+
let closestElement = event.target.closest('.touchable-templates');
|
|
24
|
+
if (closestElement) {
|
|
25
|
+
let templatePath = closestElement.getAttribute('data-template-path');
|
|
26
|
+
if (templatePath) {
|
|
27
|
+
window.open(templatePath, '_blank');
|
|
28
|
+
event.stopPropagation();
|
|
29
|
+
}
|
|
30
|
+
}
|
|
31
|
+
}
|
|
32
|
+
}, true);
|
|
33
|
+
|
|
34
|
+
document.addEventListener('mousemove', (e) => {
|
|
35
|
+
if (!altToggled) return;
|
|
36
|
+
const el = e.target.closest('.touchable-templates');
|
|
37
|
+
if (!el) return floatingElement.style.display = 'none';
|
|
38
|
+
|
|
39
|
+
const name = el.getAttribute('data-template-name');
|
|
40
|
+
if (!name) return;
|
|
41
|
+
|
|
42
|
+
floatingElement.textContent = name;
|
|
43
|
+
floatingElement.style.display = 'block';
|
|
44
|
+
const { pageX: x, pageY: y } = e;
|
|
45
|
+
const { offsetWidth: w, offsetHeight: h } = floatingElement;
|
|
46
|
+
const { innerWidth: vw, innerHeight: vh } = window;
|
|
47
|
+
floatingElement.style.left = `${x + w + 20 > vw ? x - w - 5 : x + 10}px`;
|
|
48
|
+
floatingElement.style.top = `${y + h + 20 > vh ? y - h - 5 : y + 10}px`;
|
|
49
|
+
});
|
|
50
|
+
|
|
51
|
+
document.addEventListener('mouseleave', () => {
|
|
52
|
+
floatingElement.style.display = 'none';
|
|
53
|
+
});
|
|
54
|
+
|
|
55
|
+
document.addEventListener('mouseenter', (e) => {
|
|
56
|
+
if (altToggled) {
|
|
57
|
+
const el = e.target.closest('.touchable-templates');
|
|
58
|
+
if (el) {
|
|
59
|
+
const name = el.getAttribute('data-template-name');
|
|
60
|
+
floatingElement.textContent = name;
|
|
61
|
+
floatingElement.style.display = 'block';
|
|
62
|
+
}
|
|
63
|
+
}
|
|
64
|
+
});
|
|
65
|
+
|
|
66
|
+
});
|