PluginProbe
Hash Form – Drag & Drop Form Builder / trunk
Hash Form – Drag & Drop Form Builder vtrunk
1.4.4 1.4.3 1.4.2 1.4.1 1.1.1 1.1.2 1.1.3 1.1.4 1.1.5 1.1.6 1.1.7 1.1.8 1.1.9 1.2.0 1.2.1 1.2.2 1.2.3 1.2.4 1.2.5 1.2.6 1.2.6.1 1.2.7 1.2.8 1.2.9 1.3.0 All 47 releases
hash-form / admin / forms / preview / shell.php

shell.php in Hash Form – Drag & Drop Form Builder trunk, at admin/forms/preview/shell.php

226 lines 8.0 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2 defined('ABSPATH') || die();
3 /*
4 * A template, included from inside a class method - never loaded on its own.
5 * The variables below are locals of the method that includes it, not globals,
6 * which is what the prefix sniff assumes about a file-scope assignment.
7 */
8 // phpcs:disable WordPress.NamingConventions.PrefixAllGlobals.NonPrefixedVariableFound -- included from within a method, so these are function locals.
9
10 /*
11 * The preview shell: a toolbar and an iframe holding the form.
12 *
13 * Deliberately self-contained — no wp_head(), no wp_footer(). The theme and
14 * every front-end asset belong to the document inside the frame, which is
15 * the thing being previewed; loading them out here as well would style the
16 * toolbar with whatever the site happens to use and double the page weight.
17 */
18
19 $hf_widths = HashFormPreview::preview_widths();
20 $hf_can_edit = HashFormCapabilities::user_can('hashform_edit_forms');
21 ?>
22 <!DOCTYPE html>
23 <html <?php language_attributes(); ?>>
24
25 <head>
26 <title><?php echo esc_html($form->name); ?> <?php esc_html_e('Preview', 'hash-form'); ?></title>
27 <meta charset="<?php bloginfo('charset'); ?>" />
28 <meta name="viewport" content="width=device-width, initial-scale=1.0" />
29 <?php // The endpoint answers to logged-out visitors, so keep it out of the index. ?>
30 <meta name="robots" content="noindex, nofollow" />
31 <style>
32 :root {
33 --hfp-bar: #1e2327;
34 --hfp-bar-text: #e6e8ea;
35 --hfp-muted: #9aa0a6;
36 --hfp-line: rgba(255, 255, 255, .14);
37 --hfp-active: rgba(255, 255, 255, .14);
38 --hfp-stage: #eceef1;
39 }
40
41 * { box-sizing: border-box; }
42
43 html, body {
44 height: 100%;
45 margin: 0;
46 }
47
48 body {
49 background: var(--hfp-stage);
50 display: flex;
51 flex-direction: column;
52 font: 13px/1.5 -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, Helvetica, Arial, sans-serif;
53 }
54
55 .hfp-bar {
56 align-items: center;
57 background: var(--hfp-bar);
58 color: var(--hfp-bar-text);
59 display: flex;
60 flex: 0 0 auto;
61 gap: 16px;
62 justify-content: space-between;
63 padding: 0 16px;
64 min-height: 48px;
65 }
66
67 .hfp-id {
68 align-items: center;
69 display: flex;
70 gap: 8px;
71 min-width: 0;
72 }
73
74 .hfp-tag {
75 background: var(--hfp-active);
76 border-radius: 999px;
77 color: var(--hfp-bar-text);
78 font-size: 11px;
79 font-weight: 600;
80 letter-spacing: .04em;
81 padding: 3px 8px;
82 text-transform: uppercase;
83 white-space: nowrap;
84 }
85
86 .hfp-name {
87 font-weight: 600;
88 overflow: hidden;
89 text-overflow: ellipsis;
90 white-space: nowrap;
91 }
92
93 .hfp-sizes {
94 display: flex;
95 gap: 2px;
96 }
97
98 .hfp-size {
99 background: none;
100 border: 0;
101 border-radius: 6px;
102 color: var(--hfp-muted);
103 cursor: pointer;
104 font: inherit;
105 padding: 6px 12px;
106 transition: background-color .15s ease, color .15s ease;
107 }
108
109 .hfp-size:hover { color: var(--hfp-bar-text); }
110
111 .hfp-size[aria-pressed="true"] {
112 background: var(--hfp-active);
113 color: #fff;
114 }
115
116 .hfp-size:focus-visible {
117 outline: 2px solid #fff;
118 outline-offset: 1px;
119 }
120
121 .hfp-actions {
122 align-items: center;
123 display: flex;
124 gap: 14px;
125 }
126
127 .hfp-note { color: var(--hfp-muted); }
128
129 .hfp-edit {
130 border: 1px solid var(--hfp-line);
131 border-radius: 6px;
132 color: var(--hfp-bar-text);
133 padding: 6px 12px;
134 text-decoration: none;
135 transition: background-color .15s ease;
136 white-space: nowrap;
137 }
138
139 .hfp-edit:hover { background: var(--hfp-active); }
140
141 .hfp-stage {
142 display: flex;
143 flex: 1 1 auto;
144 justify-content: center;
145 min-height: 0;
146 overflow: auto;
147 padding: 0;
148 }
149
150 /* Padding only once the frame is narrowed, so a desktop preview is
151 edge to edge exactly as the page would be. */
152 .hfp-stage.is-constrained { padding: 24px; }
153
154 .hfp-frame {
155 background: #fff;
156 border: 0;
157 flex: 0 0 auto;
158 height: 100%;
159 width: 100%;
160 }
161
162 .hfp-stage.is-constrained .hfp-frame {
163 border-radius: 8px;
164 box-shadow: 0 10px 30px -10px rgba(16, 24, 40, .25);
165 height: 100%;
166 }
167
168 @media (max-width: 782px) {
169 .hfp-bar { flex-wrap: wrap; padding: 8px 12px; }
170 .hfp-note { display: none; }
171 }
172 </style>
173 </head>
174
175 <body>
176 <div class="hfp-bar">
177 <div class="hfp-id">
178 <span class="hfp-tag"><?php esc_html_e('Preview', 'hash-form'); ?></span>
179 <span class="hfp-name"><?php echo esc_html($form->name); ?></span>
180 </div>
181
182 <div class="hfp-sizes" role="group" aria-label="<?php esc_attr_e('Preview width', 'hash-form'); ?>">
183 <?php foreach ($hf_widths as $hf_key => $hf_size) { ?>
184 <button type="button" class="hfp-size" data-width="<?php echo absint($hf_size['width']); ?>" aria-pressed="<?php echo ('desktop' === $hf_key) ? 'true' : 'false'; ?>">
185 <?php echo esc_html($hf_size['label']); ?>
186 </button>
187 <?php } ?>
188 </div>
189
190 <div class="hfp-actions">
191 <?php // The submit button is disabled in preview; say so rather than leaving people to discover it. ?>
192 <span class="hfp-note"><?php esc_html_e('Submitting is off in preview', 'hash-form'); ?></span>
193 <?php if ($hf_can_edit) { ?>
194 <a class="hfp-edit" href="<?php echo esc_url(admin_url('admin.php?page=hashform&hashform_action=edit&id=' . absint($form->id))); ?>"><?php esc_html_e('Edit form', 'hash-form'); ?></a>
195 <?php } ?>
196 </div>
197 </div>
198
199 <div class="hfp-stage" id="hfp-stage">
200 <iframe class="hfp-frame" id="hfp-frame" title="<?php echo esc_attr(sprintf(/* translators: %s: form name. */ __('%s preview', 'hash-form'), $form->name)); ?>" src="<?php echo esc_url(HashFormPreview::frame_url($form->id)); ?>"></iframe>
201 </div>
202
203 <script>
204 (function () {
205 var stage = document.getElementById('hfp-stage');
206 var frame = document.getElementById('hfp-frame');
207 var buttons = document.querySelectorAll('.hfp-size');
208
209 Array.prototype.forEach.call(buttons, function (button) {
210 button.addEventListener('click', function () {
211 var width = parseInt(button.getAttribute('data-width'), 10) || 0;
212
213 Array.prototype.forEach.call(buttons, function (other) {
214 other.setAttribute('aria-pressed', String(other === button));
215 });
216
217 stage.classList.toggle('is-constrained', width > 0);
218 frame.style.width = width ? width + 'px' : '100%';
219 });
220 });
221 }());
222 </script>
223 </body>
224
225 </html>
226