| 1 | |
|---|
| 2 | |
|---|
| 3 | <!-- data picker infrastructure --> |
|---|
| 4 | <link rel="stylesheet" type="text/css" media="all" href="/jscalendar/calendar-win2k-cold-1.css" title="win2k-cold-1" /> |
|---|
| 5 | <script type="text/javascript" src="/jscalendar/calendar.js"></script> |
|---|
| 6 | <script type="text/javascript" src="/jscalendar/lang/calendar-en.js"></script> |
|---|
| 7 | <script type="text/javascript" src="/jscalendar/calendar-setup.js"></script> |
|---|
| 8 | |
|---|
| 9 | |
|---|
| 10 | <?cs include "header.cs" ?> |
|---|
| 11 | <?cs include "macros.cs" ?> |
|---|
| 12 | |
|---|
| 13 | <div id="ctxtnav" class="nav"> |
|---|
| 14 | <h2>Ticket Navigation</h2><?cs |
|---|
| 15 | with:links = chrome.links ?><?cs |
|---|
| 16 | if:len(links.prev) || len(links.up) || len(links.next) ?><ul><?cs |
|---|
| 17 | if:len(links.prev) ?> |
|---|
| 18 | <li class="first<?cs if:!len(links.up) && !len(links.next) ?> last<?cs /if ?>"> |
|---|
| 19 | ← <a href="<?cs var:links.prev.0.href ?>" title="<?cs |
|---|
| 20 | var:links.prev.0.title ?>">Previous Ticket</a> |
|---|
| 21 | </li><?cs |
|---|
| 22 | /if ?><?cs |
|---|
| 23 | if:len(links.up) ?> |
|---|
| 24 | <li class="<?cs if:!len(links.prev) ?>first<?cs /if ?><?cs |
|---|
| 25 | if:!len(links.next) ?> last<?cs /if ?>"> |
|---|
| 26 | <a href="<?cs var:links.up.0.href ?>" title="<?cs |
|---|
| 27 | var:links.up.0.title ?>">Back to Query</a> |
|---|
| 28 | </li><?cs |
|---|
| 29 | /if ?><?cs |
|---|
| 30 | if:len(links.next) ?> |
|---|
| 31 | <li class="<?cs if:!len(links.prev) && !len(links.up) ?>first <?cs /if ?>last"> |
|---|
| 32 | <a href="<?cs var:links.next.0.href ?>" title="<?cs |
|---|
| 33 | var:links.next.0.title ?>">Next Ticket</a> → |
|---|
| 34 | </li><?cs |
|---|
| 35 | /if ?></ul><?cs |
|---|
| 36 | /if ?><?cs |
|---|
| 37 | /with ?> |
|---|
| 38 | </div> |
|---|
| 39 | |
|---|
| 40 | <div id="content" class="ticket"> |
|---|
| 41 | |
|---|
| 42 | <h1>Ticket #<?cs var:ticket.id ?> <?cs |
|---|
| 43 | if:ticket.type ?>(<?cs var:ticket.type ?>)<?cs /if ?></h1> |
|---|
| 44 | |
|---|
| 45 | <div id="searchable"> |
|---|
| 46 | <div id="ticket"> |
|---|
| 47 | <div class="date"> |
|---|
| 48 | <p title="<?cs var:ticket.opened ?>">Opened <?cs var:ticket.opened_delta ?> ago</p><?cs |
|---|
| 49 | if:ticket.lastmod ?> |
|---|
| 50 | <p title="<?cs var:ticket.lastmod ?>">Last modified <?cs var:ticket.lastmod_delta ?> ago</p> |
|---|
| 51 | <?cs /if ?> |
|---|
| 52 | </div> |
|---|
| 53 | <h2 class="summary"><?cs var:ticket.summary ?></h2> |
|---|
| 54 | <h3 class="status">Status: <strong><?cs var:ticket.status ?><?cs |
|---|
| 55 | if:ticket.resolution ?> (<?cs var:ticket.resolution ?>)<?cs |
|---|
| 56 | /if ?></strong></h3> |
|---|
| 57 | <table class="properties"> |
|---|
| 58 | <tr> |
|---|
| 59 | <th id="h_reporter">Reported by:</th> |
|---|
| 60 | <td headers="h_reporter"><?cs var:ticket.reporter ?></td> |
|---|
| 61 | <th id="h_owner">Assigned to:</th> |
|---|
| 62 | <td headers="h_owner"><?cs var:ticket.owner ?><?cs |
|---|
| 63 | if:ticket.status == 'assigned' ?> (accepted)<?cs /if ?></td> |
|---|
| 64 | </tr><tr><?cs |
|---|
| 65 | each:field = ticket.fields ?><?cs |
|---|
| 66 | if:!field.skip ?><?cs |
|---|
| 67 | set:num_fields = num_fields + 1 ?><?cs |
|---|
| 68 | /if ?><?cs |
|---|
| 69 | /each ?><?cs |
|---|
| 70 | set:idx = 0 ?><?cs |
|---|
| 71 | each:field = ticket.fields ?><?cs |
|---|
| 72 | if:!field.skip ?><?cs set:fullrow = field.type == 'textarea' ?><?cs |
|---|
| 73 | if:fullrow && idx % 2 ?><th></th><td></td></tr><tr><?cs /if ?> |
|---|
| 74 | <th id="h_<?cs var:name(field) ?>"><?cs var:field.label ?>:</th> |
|---|
| 75 | <td<?cs if:fullrow ?> colspan="3"<?cs /if ?> headers="h_<?cs |
|---|
| 76 | var:name(field) ?>"><?cs var:ticket[name(field)] ?></td><?cs |
|---|
| 77 | if:idx % 2 || fullrow ?></tr><tr><?cs |
|---|
| 78 | elif:idx == num_fields - 1 ?><th></th><td></td><?cs |
|---|
| 79 | /if ?><?cs set:idx = idx + #fullrow + 1 ?><?cs |
|---|
| 80 | /if ?><?cs |
|---|
| 81 | /each ?></tr> |
|---|
| 82 | </table> |
|---|
| 83 | <?cs if:ticket.description ?><div class="description"> |
|---|
| 84 | <?cs var:ticket.description.formatted ?> |
|---|
| 85 | </div><?cs /if ?> |
|---|
| 86 | </div> |
|---|
| 87 | |
|---|
| 88 | <?cs if:ticket.attach_href || len(ticket.attachments) ?> |
|---|
| 89 | <h2>Attachments</h2><?cs |
|---|
| 90 | if:len(ticket.attachments) ?><div id="attachments"> |
|---|
| 91 | <dl class="attachments"><?cs each:attachment = ticket.attachments ?> |
|---|
| 92 | <dt><a href="<?cs var:attachment.href ?>" title="View attachment"><?cs |
|---|
| 93 | var:attachment.filename ?></a> (<?cs var:attachment.size ?>) - added by <em><?cs |
|---|
| 94 | var:attachment.author ?></em> on <?cs |
|---|
| 95 | var:attachment.time ?>.</dt><?cs |
|---|
| 96 | if:attachment.description ?> |
|---|
| 97 | <dd><?cs var:attachment.description ?></dd><?cs |
|---|
| 98 | /if ?><?cs |
|---|
| 99 | /each ?></dl><?cs |
|---|
| 100 | /if ?><?cs |
|---|
| 101 | if:ticket.attach_href ?> |
|---|
| 102 | <form method="get" action="<?cs var:ticket.attach_href ?>"><div> |
|---|
| 103 | <input type="hidden" name="action" value="new" /> |
|---|
| 104 | <input type="submit" value="Attach File" /> |
|---|
| 105 | </div></form><?cs |
|---|
| 106 | /if ?><?cs if:len(ticket.attachments) ?></div><?cs /if ?> |
|---|
| 107 | <?cs /if ?> |
|---|
| 108 | |
|---|
| 109 | <?cs if:len(ticket.changes) ?><h2>Change History</h2> |
|---|
| 110 | <div id="changelog"><?cs |
|---|
| 111 | each:change = ticket.changes ?> |
|---|
| 112 | <h3 id="change_<?cs var:name(change) ?>" class="change"><?cs |
|---|
| 113 | var:change.date ?>: Modified by <?cs var:change.author ?></h3><?cs |
|---|
| 114 | if:len(change.fields) ?> |
|---|
| 115 | <ul class="changes"><?cs |
|---|
| 116 | each:field = change.fields ?> |
|---|
| 117 | <li><strong><?cs var:name(field) ?></strong> <?cs |
|---|
| 118 | if:name(field) == 'attachment' ?><em><?cs var:field.new ?></em> added<?cs |
|---|
| 119 | elif:field.old && field.new ?>changed from <em><?cs |
|---|
| 120 | var:field.old ?></em> to <em><?cs var:field.new ?></em><?cs |
|---|
| 121 | elif:!field.old && field.new ?>set to <em><?cs var:field.new ?></em><?cs |
|---|
| 122 | elif:field.old && !field.new ?>deleted<?cs |
|---|
| 123 | else ?>changed<?cs |
|---|
| 124 | /if ?>.</li> |
|---|
| 125 | <?cs |
|---|
| 126 | /each ?> |
|---|
| 127 | </ul><?cs |
|---|
| 128 | /if ?> |
|---|
| 129 | <div class="comment"><?cs var:change.comment ?></div><?cs |
|---|
| 130 | /each ?></div><?cs |
|---|
| 131 | /if ?> |
|---|
| 132 | |
|---|
| 133 | <?cs if:trac.acl.TICKET_CHGPROP || trac.acl.TICKET_APPEND ?> |
|---|
| 134 | <form action="<?cs var:ticket.href ?>#preview" method="post"> |
|---|
| 135 | <hr /> |
|---|
| 136 | <h3><a name="edit" onfocus="document.getElementById('comment').focus()">Add/Change #<?cs |
|---|
| 137 | var:ticket.id ?> (<?cs var:ticket.summary ?>)</a></h3> |
|---|
| 138 | <div class="field"> |
|---|
| 139 | <label for="author">Your email or username:</label><br /> |
|---|
| 140 | <input type="text" id="author" name="author" size="40" |
|---|
| 141 | value="<?cs var:ticket.reporter_id ?>" /><br /> |
|---|
| 142 | </div> |
|---|
| 143 | <div class="field"> |
|---|
| 144 | <fieldset class="iefix"> |
|---|
| 145 | <label for="comment">Comment (you may use <a tabindex="42" href="<?cs |
|---|
| 146 | var:trac.href.wiki ?>/WikiFormatting">WikiFormatting</a> here):</label><br /> |
|---|
| 147 | <p><textarea id="comment" name="comment" class="wikitext" rows="10" cols="78"><?cs |
|---|
| 148 | var:ticket.comment ?></textarea></p> |
|---|
| 149 | </fieldset><?cs |
|---|
| 150 | if ticket.comment_preview ?> |
|---|
| 151 | <fieldset id="preview"> |
|---|
| 152 | <legend>Comment Preview</legend> |
|---|
| 153 | <?cs var:ticket.comment_preview ?> |
|---|
| 154 | </fieldset><?cs |
|---|
| 155 | /if ?> |
|---|
| 156 | </div> |
|---|
| 157 | |
|---|
| 158 | <?cs if:trac.acl.TICKET_CHGPROP ?><fieldset id="properties"> |
|---|
| 159 | <legend>Change Properties</legend> |
|---|
| 160 | <table><tr> |
|---|
| 161 | <th><label for="summary">Summary:</label></th> |
|---|
| 162 | <td class="fullrow" colspan="3"><input type="text" id="summary" name="summary" value="<?cs |
|---|
| 163 | var:ticket.summary ?>" size="70" /></td> |
|---|
| 164 | </tr><?cs |
|---|
| 165 | if:len(ticket.fields.type.options) ?> |
|---|
| 166 | <tr> |
|---|
| 167 | <th><label for="type">Type:</label></th> |
|---|
| 168 | <td><?cs |
|---|
| 169 | call:hdf_select(ticket.fields.type.options, 'type', ticket.type, 0) ?> |
|---|
| 170 | </td> |
|---|
| 171 | </tr><?cs |
|---|
| 172 | /if ?><?cs |
|---|
| 173 | if:trac.acl.TICKET_ADMIN ?><tr> |
|---|
| 174 | <th><label for="description">Description:</label></th> |
|---|
| 175 | <td class="fullrow" colspan="3"> |
|---|
| 176 | <textarea id="description" name="description" class="wikitext" rows="10" cols="68"><?cs |
|---|
| 177 | var:ticket.description ?></textarea> |
|---|
| 178 | </td> |
|---|
| 179 | </tr><tr> |
|---|
| 180 | <th><label for="reporter">Reporter:</label></th> |
|---|
| 181 | <td class="fullrow" colspan="3"><input type="text" value="<?cs |
|---|
| 182 | var:ticket.reporter ?>" id="reporter" name="reporter" size="70" /></td> |
|---|
| 183 | </tr><?cs |
|---|
| 184 | /if ?> |
|---|
| 185 | <tr><?cs set:num_fields = 0 ?><?cs |
|---|
| 186 | each:field = ticket.fields ?><?cs |
|---|
| 187 | if:!field.skip ?><?cs |
|---|
| 188 | set:num_fields = num_fields + 1 ?><?cs |
|---|
| 189 | /if ?><?cs |
|---|
| 190 | /each ?><?cs set:idx = 0 ?><?cs |
|---|
| 191 | each:field = ticket.fields ?><?cs |
|---|
| 192 | if:!field.skip ?><?cs set:fullrow = field.type == 'textarea' ?><?cs |
|---|
| 193 | if:fullrow && idx % 2 ?><?cs set:idx = idx + 1 ?><th class="col2"></th><td></td></tr><tr><?cs /if ?> |
|---|
| 194 | <th class="col<?cs var:idx % 2 + 1 ?>"><?cs |
|---|
| 195 | if:field.type != 'radio' ?><label for="<?cs var:name(field) ?>"><?cs |
|---|
| 196 | /if ?><?cs alt:field.label ?><?cs var:field.name ?><?cs /alt ?>:<?cs |
|---|
| 197 | if:field.type != 'radio' ?></label><?cs /if ?></th> |
|---|
| 198 | <td<?cs if:fullrow ?> colspan="3"<?cs /if ?>><?cs |
|---|
| 199 | if:field.type == 'text' ?><input type="text" id="<?cs |
|---|
| 200 | var:name(field) ?>" name="<?cs |
|---|
| 201 | var:name(field) ?>" value="<?cs var:ticket[name(field)] ?>" /><?cs if:name(field) == 'completeby' ?> |
|---|
| 202 | <img src="/jscalendar/deskcalendar.png" align="top" id="completeby_button" style="cursor: pointer; border: none;" title="Date selector" /> |
|---|
| 203 | <script type="text/javascript"> |
|---|
| 204 | Calendar.setup({ |
|---|
| 205 | inputField : "completeby", // id of the input field |
|---|
| 206 | ifFormat : "%Y-%m-%d", // format of the input field |
|---|
| 207 | showsTime : false, // will display a time selector |
|---|
| 208 | button : "completeby_button", // trigger for the calendar (button ID) |
|---|
| 209 | singleClick : true, // double-click mode |
|---|
| 210 | step : 1 // show all years in drop-down boxes (instead of every other year as default) |
|---|
| 211 | }); |
|---|
| 212 | </script> |
|---|
| 213 | <?cs elif:name(field) == 'nextactiondue' ?> |
|---|
| 214 | <img src="/jscalendar/deskcalendar.png" align="top" id="nextactiondue_button" style="cursor: pointer; border: none;" title="Date selector" /> |
|---|
| 215 | <script type="text/javascript"> |
|---|
| 216 | Calendar.setup({ |
|---|
| 217 | inputField : "nextactiondue", // id of the input field |
|---|
| 218 | ifFormat : "%Y-%m-%d", // format of the input field |
|---|
| 219 | showsTime : false, // will display a time selector |
|---|
| 220 | button : "nextactiondue_button", // trigger for the calendar (button ID) |
|---|
| 221 | singleClick : true, // double-click mode |
|---|
| 222 | step : 1 // show all years in drop-down boxes (instead of every other year as default) |
|---|
| 223 | }); |
|---|
| 224 | </script> |
|---|
| 225 | <?cs /if ?><?cs |
|---|
| 226 | elif:field.type == 'select' ?><select id="<?cs |
|---|
| 227 | var:name(field) ?>" name="<?cs |
|---|
| 228 | var:name(field) ?>"><?cs |
|---|
| 229 | if:field.optional ?><option></option><?cs /if ?><?cs |
|---|
| 230 | each:option = field.options ?><option<?cs |
|---|
| 231 | if:option == ticket[name(field)] ?> selected="selected"<?cs /if ?>><?cs |
|---|
| 232 | var:option ?></option><?cs |
|---|
| 233 | /each ?></select><?cs |
|---|
| 234 | elif:field.type == 'checkbox' ?><input type="hidden" name="checkbox_<?cs |
|---|
| 235 | var:name(field) ?>" /><input type="checkbox" id="<?cs |
|---|
| 236 | var:name(field) ?>" name="<?cs |
|---|
| 237 | var:name(field) ?>" value="1"<?cs |
|---|
| 238 | if:ticket[name(field)] ?> checked="checked"<?cs /if ?> /><?cs |
|---|
| 239 | elif:field.type == 'textarea' ?><textarea id="<?cs |
|---|
| 240 | var:name(field) ?>" name="<?cs |
|---|
| 241 | var:name(field) ?>"<?cs |
|---|
| 242 | if:field.height ?> rows="<?cs var:field.height ?>"<?cs /if ?><?cs |
|---|
| 243 | if:field.width ?> cols="<?cs var:field.width ?>"<?cs /if ?>><?cs |
|---|
| 244 | var:ticket[name(field)] ?></textarea><?cs |
|---|
| 245 | elif:field.type == 'radio' ?><?cs set:optidx = 0 ?><?cs |
|---|
| 246 | each:option = field.options ?><label><input type="radio" id="<?cs |
|---|
| 247 | var:name(field) ?>" name="<?cs |
|---|
| 248 | var:name(field) ?>" value="<?cs var:option ?>"<?cs |
|---|
| 249 | if:ticket[name(field)] == option ?> checked="checked"<?cs /if ?> /> <?cs |
|---|
| 250 | var:option ?></label> <?cs set:optidx = optidx + 1 ?><?cs |
|---|
| 251 | /each ?><?cs |
|---|
| 252 | /if ?></td><?cs |
|---|
| 253 | if:idx % 2 || fullrow ?><?cs |
|---|
| 254 | if:idx < num_fields - 1 ?></tr><tr><?cs |
|---|
| 255 | /if ?><?cs |
|---|
| 256 | elif:idx == num_fields - 1 ?><th class="col2"></th><td></td><?cs |
|---|
| 257 | /if ?><?cs set:idx = idx + #fullrow + 1 ?><?cs |
|---|
| 258 | /if ?><?cs |
|---|
| 259 | /each ?></tr> |
|---|
| 260 | </table> |
|---|
| 261 | </fieldset><?cs /if ?> |
|---|
| 262 | |
|---|
| 263 | <?cs if:ticket.actions.accept || ticket.actions.reopen || |
|---|
| 264 | ticket.actions.resolve || ticket.actions.reassign ?> |
|---|
| 265 | <fieldset id="action"> |
|---|
| 266 | <legend>Action</legend><?cs |
|---|
| 267 | if:!ticket.action ?><?cs set:ticket.action = 'leave' ?><?cs |
|---|
| 268 | /if ?><?cs |
|---|
| 269 | def:action_radio(id) ?> |
|---|
| 270 | <input type="radio" id="<?cs var:id ?>" name="action" value="<?cs |
|---|
| 271 | var:id ?>"<?cs if:ticket.action == id ?> checked="checked"<?cs |
|---|
| 272 | /if ?> /><?cs |
|---|
| 273 | /def ?> |
|---|
| 274 | <?cs call:action_radio('leave') ?> |
|---|
| 275 | <label for="leave">leave as <?cs var:ticket.status ?></label><br /><?cs |
|---|
| 276 | if:ticket.actions.accept ?><?cs |
|---|
| 277 | call:action_radio('accept') ?> |
|---|
| 278 | <label for="accept">accept ticket</label><br /><?cs |
|---|
| 279 | /if ?><?cs |
|---|
| 280 | if:ticket.actions.reopen ?><?cs |
|---|
| 281 | call:action_radio('reopen') ?> |
|---|
| 282 | <label for="reopen">reopen ticket</label><br /><?cs |
|---|
| 283 | /if ?><?cs |
|---|
| 284 | if:ticket.actions.resolve ?><?cs |
|---|
| 285 | call:action_radio('resolve') ?> |
|---|
| 286 | <label for="resolve">resolve</label><?cs |
|---|
| 287 | if:len(ticket.fields.resolution.options) ?> |
|---|
| 288 | <label for="resolve_resolution">as:</label> |
|---|
| 289 | <?cs call:hdf_select(ticket.fields.resolution.options, "resolve_resolution", |
|---|
| 290 | ticket.resolve_resolution, 0) ?><br /><?cs |
|---|
| 291 | /if ?><?cs |
|---|
| 292 | /if ?><?cs |
|---|
| 293 | if:ticket.actions.reassign ?><?cs |
|---|
| 294 | call:action_radio('reassign') ?> |
|---|
| 295 | <label for="reassign">reassign</label> |
|---|
| 296 | <label>to:<?cs |
|---|
| 297 | if:len(ticket.fields.owner.options) ?><?cs |
|---|
| 298 | call:hdf_select(ticket.fields.owner.options, "reassign_owner", |
|---|
| 299 | ticket.reassign_owner, 1) ?><?cs |
|---|
| 300 | else ?> |
|---|
| 301 | <input type="text" id="reassign_owner" name="reassign_owner" size="40" value="<?cs |
|---|
| 302 | var:ticket.reassign_owner ?>" /><?cs |
|---|
| 303 | /if ?></label><?cs |
|---|
| 304 | /if ?><?cs |
|---|
| 305 | if ticket.actions.resolve || ticket.actions.reassign ?> |
|---|
| 306 | <script type="text/javascript"><?cs |
|---|
| 307 | each:action = ticket.actions ?> |
|---|
| 308 | var <?cs var:name(action) ?> = document.getElementById("<?cs var:name(action) ?>");<?cs |
|---|
| 309 | /each ?> |
|---|
| 310 | var updateActionFields = function() { |
|---|
| 311 | <?cs if:ticket.actions.resolve ?> enableControl('resolve_resolution', resolve.checked);<?cs /if ?> |
|---|
| 312 | <?cs if:ticket.actions.reassign ?> enableControl('reassign_owner', reassign.checked);<?cs /if ?> |
|---|
| 313 | }; |
|---|
| 314 | addEvent(window, 'load', updateActionFields);<?cs |
|---|
| 315 | each:action = ticket.actions ?> |
|---|
| 316 | addEvent(<?cs var:name(action) ?>, 'click', updateActionFields);<?cs |
|---|
| 317 | /each ?> |
|---|
| 318 | </script><?cs |
|---|
| 319 | /if ?> |
|---|
| 320 | </fieldset><?cs |
|---|
| 321 | else ?> |
|---|
| 322 | <input type="hidden" name="action" value="leave" /><?cs |
|---|
| 323 | /if ?> |
|---|
| 324 | |
|---|
| 325 | <script type="text/javascript" src="<?cs |
|---|
| 326 | var:chrome.href ?>/common/js/wikitoolbar.js"></script> |
|---|
| 327 | |
|---|
| 328 | <div class="buttons"> |
|---|
| 329 | <input type="hidden" name="ts" value="<?cs var:ticket.ts ?>" /> |
|---|
| 330 | <input type="submit" name="preview" value="Preview" accesskey="r" /> |
|---|
| 331 | <input type="submit" value="Submit changes" /> |
|---|
| 332 | </div> |
|---|
| 333 | </form> |
|---|
| 334 | <?cs /if ?> |
|---|
| 335 | |
|---|
| 336 | </div> |
|---|
| 337 | </div> |
|---|
| 338 | <?cs include "footer.cs"?> |
|---|