Implemented notes UI.
- Switched from a global reset in www/css/ts-screen.scss to a selected top-level elements reset to allow default formatting for user notes. - Restructured the #entry-list and entry displays. - Restructured notes div, now has a sub-div for text and a textarea element for input. - Added Showdown.js, a JavaScript Markdown library for formatting comments. - Moved EntryView blur events to the View events map. - Added images for expansion of notes. - Added the ability to edit notes. - Split EntryListView.addOne into renderOne and addOne so that renderOne can be called with a new entry (fixes duration glitch)
10
doc/todo.rst
@ -1,6 +1,5 @@
|
||||
Current
|
||||
=======
|
||||
- Add UI for note-taking
|
||||
|
||||
Upcoming
|
||||
========
|
||||
@ -16,6 +15,15 @@ Upcoming
|
||||
- Create a light, alternating background for entries
|
||||
- Add hover-enabled icons for editing entries/showing notes
|
||||
- Create tooltips.
|
||||
- Create a realtime tick-tock for the duration of the current item.
|
||||
- Mobile version of the app.
|
||||
- Refactor code, seperate out reusable bits for mobile version.
|
||||
- Automatic code-highlighting (Highlight.js)
|
||||
|
||||
Done
|
||||
====
|
||||
- Add UI for note-taking
|
||||
- Add Markdown converter for notes.
|
||||
- Fix the duration bug when adding new events. Need to set the nextModel for
|
||||
the previously 'current' timestamp and set the nextModel of the new timestamp
|
||||
to 'null'
|
||||
|
@ -4,30 +4,37 @@
|
||||
*/
|
||||
/* _rounded.scss */
|
||||
* {
|
||||
color: inherit;
|
||||
margin: 0;
|
||||
padding: 0; }
|
||||
color: inherit; }
|
||||
|
||||
body {
|
||||
color: #222222;
|
||||
width: 75%;
|
||||
margin: auto; }
|
||||
margin: auto;
|
||||
padding: 0; }
|
||||
|
||||
input {
|
||||
border: solid thin #555555;
|
||||
-webkit-box-shadow: inset 0px 2px 4px #CCC;
|
||||
box-shadow: inset 0px 2px 4px #CCC;
|
||||
margin: 0;
|
||||
margin-bottom: 0.5em;
|
||||
padding: 0;
|
||||
font-family: Cantarell; }
|
||||
|
||||
#top {
|
||||
background: #222222;
|
||||
color: #eeeeee;
|
||||
margin: 0;
|
||||
opacity: 1;
|
||||
padding: 0.5em 0;
|
||||
padding: 0.5rem 0;
|
||||
position: fixed;
|
||||
top: 0px;
|
||||
width: 75%; }
|
||||
width: 75%;
|
||||
z-index: 1; }
|
||||
#top * {
|
||||
margin: 0;
|
||||
padding: 0; }
|
||||
#top #fade-bar {
|
||||
background: url("img/fade.png") repeat-x;
|
||||
height: 32px;
|
||||
@ -73,6 +80,8 @@ input {
|
||||
#login {
|
||||
background: white;
|
||||
color: #eeeeee;
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
opacity: 1;
|
||||
position: fixed;
|
||||
top: 0px;
|
||||
@ -80,6 +89,9 @@ input {
|
||||
width: 100%;
|
||||
height: 100em;
|
||||
z-index: 10; }
|
||||
#login * {
|
||||
margin: 0;
|
||||
padding: 0; }
|
||||
#login div.container {
|
||||
background: #222222;
|
||||
border-radius: 10px;
|
||||
@ -138,28 +150,34 @@ input {
|
||||
width: 10em; }
|
||||
|
||||
#entry-list {
|
||||
margin-top: 6em;
|
||||
padding-bottom: 1em;
|
||||
margin-top: 6rem;
|
||||
padding-bottom: 1rem; }
|
||||
margin: 6em 0 0 0;
|
||||
margin: 6rem 0 0 0;
|
||||
padding-bottom: 1em 0 0 0;
|
||||
padding-bottom: 1rem 0 0 0; }
|
||||
#entry-list .day-seperator {
|
||||
background: #cccccc;
|
||||
color: #222222;
|
||||
font-family: Cantarell;
|
||||
font-weight: bold;
|
||||
margin-top: 1em;
|
||||
margin: 1em 0 0 0;
|
||||
margin: 1rem 0 0 0;
|
||||
padding: 0 2em;
|
||||
margin-top: 1rem;
|
||||
padding: 0 2rem; }
|
||||
#entry-list .day-seperator * {
|
||||
margin: 0;
|
||||
padding: 0; }
|
||||
#entry-list .day-seperator h4, #entry-list .day-seperator h5 {
|
||||
display: inline-block; }
|
||||
#entry-list .day-seperator h5 {
|
||||
color: #667; }
|
||||
#entry-list #new-entry {
|
||||
margin-top: 0.5em;
|
||||
margin: 0.5em 0 0 0;
|
||||
padding: 0 2em;
|
||||
margin-top: 0.5rem;
|
||||
margin: 0.5rem 0 0 0;
|
||||
padding: 0 2rem; }
|
||||
#entry-list #new-entry * {
|
||||
margin: 0;
|
||||
padding: 0; }
|
||||
#entry-list .timestamp, #entry-list .timestamp-input, #entry-list .duration {
|
||||
text-align: right;
|
||||
width: 14%; }
|
||||
@ -172,25 +190,33 @@ input {
|
||||
#entry-list .entry div {
|
||||
display: inline-block; }
|
||||
#entry-list .entry .mark {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
position: relative; }
|
||||
#entry-list .entry .mark img.delete-icon {
|
||||
#entry-list .entry .mark * {
|
||||
margin: 0;
|
||||
padding: 0; }
|
||||
#entry-list .entry .mark img.expand-entry, #entry-list .entry .mark img.collapse-entry {
|
||||
display: none;
|
||||
left: -20px;
|
||||
position: absolute;
|
||||
top: 6px; }
|
||||
#entry-list .entry .mark img.notes-icon {
|
||||
display: none;
|
||||
margin-top: 6px;
|
||||
float: right; }
|
||||
#entry-list .entry:hover .mark img {
|
||||
#entry-list .entry:hover .mark img.expand-entry, #entry-list .entry.show-notes img.collapse-entry {
|
||||
display: inline; }
|
||||
#entry-list .entry .mark-input, #entry-list .entry .timestamp-input {
|
||||
#entry-list .entry .mark-input, #entry-list .entry .timestamp-input, #entry-list .entry.show-notes:hover img.expand-entry {
|
||||
display: none; }
|
||||
#entry-list .entry .notes, #entry-list .entry .notes-input {
|
||||
#entry-list .entry .notes {
|
||||
display: none;
|
||||
font-family: Cantarell;
|
||||
font-size: small;
|
||||
padding-left: 1em; }
|
||||
margin: 0;
|
||||
padding: 0 0 0 1em; }
|
||||
#entry-list .entry .notes :first-child {
|
||||
margin-top: 0; }
|
||||
#entry-list .entry .notes .notes-input, #entry-list .entry .notes pre, #entry-list .entry .notes code {
|
||||
font-family: 'Anonymous Pro'; }
|
||||
#entry-list .entry .notes * {
|
||||
width: 100%; }
|
||||
#entry-list .entry.edit-mark .mark-input {
|
||||
display: inline-block; }
|
||||
#entry-list .entry.edit-mark .mark {
|
||||
@ -199,11 +225,20 @@ input {
|
||||
display: inline-block; }
|
||||
#entry-list .entry.edit-timestamp .timestamp {
|
||||
display: none; }
|
||||
#entry-list .entry .notes-input {
|
||||
display: none; }
|
||||
#entry-list .entry.edit-notes .notes-input {
|
||||
display: block; }
|
||||
#entry-list .entry.edit-notes .notes-text {
|
||||
display: none; }
|
||||
|
||||
.drop-menu {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
position: relative; }
|
||||
.drop-menu * {
|
||||
margin: 0;
|
||||
padding: 0; }
|
||||
.drop-menu .drop-menu-items {
|
||||
display: none;
|
||||
list-style: none;
|
||||
@ -223,10 +258,14 @@ input {
|
||||
background: #222222;
|
||||
color: #eeeeee;
|
||||
font-family: Bentham;
|
||||
margin: 0;
|
||||
padding: 1em 0;
|
||||
padding: 1rem 0;
|
||||
text-align: center;
|
||||
width: 100%; }
|
||||
.footer * {
|
||||
margin: 0;
|
||||
padding: 0; }
|
||||
.footer a {
|
||||
color: white;
|
||||
text-decoration: none; }
|
||||
|
@ -13,33 +13,41 @@ $medBg: #CCC;
|
||||
|
||||
* {
|
||||
color: inherit;
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
}
|
||||
|
||||
body {
|
||||
color: $darkTxt;
|
||||
width: 75%;
|
||||
margin: auto;
|
||||
|
||||
padding: 0;
|
||||
}
|
||||
|
||||
input {
|
||||
border: solid thin lighten($darkTxt, 20%);
|
||||
-webkit-box-shadow: inset 0px 2px 4px #CCC;
|
||||
box-shadow: inset 0px 2px 4px #CCC;
|
||||
margin: 0;
|
||||
margin-bottom: 0.5em; // IE fix
|
||||
padding: 0;
|
||||
font-family: Cantarell;
|
||||
}
|
||||
|
||||
#top {
|
||||
background: $darkBg;
|
||||
color: $lightTxt;
|
||||
margin: 0;
|
||||
opacity: 1;
|
||||
padding: 0.5em 0; // IE Fix
|
||||
padding: 0.5rem 0;
|
||||
position: fixed;
|
||||
top: 0px;
|
||||
width: 75%;
|
||||
z-index: 1;
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
}
|
||||
|
||||
#fade-bar {
|
||||
background: url('img/fade.png') repeat-x;
|
||||
@ -103,6 +111,8 @@ input {
|
||||
|
||||
background: white;
|
||||
color: $lightTxt;
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
opacity: 1;
|
||||
|
||||
position: fixed;
|
||||
@ -114,6 +124,11 @@ input {
|
||||
|
||||
z-index: 10;
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
}
|
||||
|
||||
div.container {
|
||||
|
||||
background: $darkBg;
|
||||
@ -197,10 +212,10 @@ input {
|
||||
|
||||
#entry-list {
|
||||
|
||||
margin-top: 6em;
|
||||
padding-bottom: 1em;
|
||||
margin-top: 6rem;
|
||||
padding-bottom: 1rem;
|
||||
margin: 6em 0 0 0;
|
||||
margin: 6rem 0 0 0;
|
||||
padding-bottom: 1em 0 0 0;
|
||||
padding-bottom: 1rem 0 0 0;
|
||||
|
||||
.day-seperator {
|
||||
|
||||
@ -208,22 +223,31 @@ input {
|
||||
color: $darkBg;
|
||||
font-family: Cantarell;
|
||||
font-weight: bold;
|
||||
margin-top: 1em;
|
||||
margin: 1em 0 0 0;
|
||||
margin: 1rem 0 0 0;
|
||||
padding: 0 2em;
|
||||
margin-top: 1rem;
|
||||
padding: 0 2rem;
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
}
|
||||
|
||||
h4, h5 { display: inline-block; }
|
||||
|
||||
h5 { color: #667; }
|
||||
}
|
||||
|
||||
#new-entry {
|
||||
margin-top: 0.5em;
|
||||
margin: 0.5em 0 0 0;
|
||||
padding: 0 2em;
|
||||
margin-top: 0.5rem;
|
||||
margin: 0.5rem 0 0 0;
|
||||
padding: 0 2rem;
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
}
|
||||
}
|
||||
|
||||
.timestamp, .timestamp-input, .duration {
|
||||
@ -242,33 +266,42 @@ input {
|
||||
div { display: inline-block; }
|
||||
|
||||
.mark {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
position: relative;
|
||||
|
||||
img.delete-icon {
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
}
|
||||
|
||||
img.expand-entry, img.collapse-entry {
|
||||
display: none;
|
||||
left: -20px;
|
||||
position: absolute;
|
||||
top: 6px;
|
||||
}
|
||||
|
||||
img.notes-icon {
|
||||
display: none;
|
||||
margin-top: 6px;
|
||||
float: right;
|
||||
}
|
||||
}
|
||||
|
||||
&:hover .mark img { display: inline; }
|
||||
&:hover .mark img.expand-entry, &.show-notes img.collapse-entry { display: inline; }
|
||||
|
||||
.mark-input, .timestamp-input { display: none; }
|
||||
.mark-input, .timestamp-input,
|
||||
&.show-notes:hover img.expand-entry { display: none; }
|
||||
|
||||
.notes, .notes-input {
|
||||
.notes {
|
||||
display: none;
|
||||
font-family: Cantarell;
|
||||
font-size: small;
|
||||
padding-left: 1em;
|
||||
margin: 0;
|
||||
padding: 0 0 0 1em;
|
||||
|
||||
:first-child { margin-top: 0; }
|
||||
|
||||
.notes-input, pre, code { font-family: 'Anonymous Pro'; }
|
||||
}
|
||||
|
||||
.notes * { width: 100%; }
|
||||
|
||||
&.edit-mark {
|
||||
.mark-input { display: inline-block; }
|
||||
.mark { display: none; }
|
||||
@ -279,15 +312,26 @@ input {
|
||||
.timestamp { display: none; }
|
||||
}
|
||||
|
||||
.notes-input { display: none; }
|
||||
|
||||
&.edit-notes .notes-input { display: block; }
|
||||
|
||||
&.edit-notes .notes-text { display: none; }
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
.drop-menu {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
position: relative;
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
}
|
||||
|
||||
.drop-menu-items {
|
||||
display: none;
|
||||
list-style: none;
|
||||
@ -316,11 +360,17 @@ input {
|
||||
background: $darkBg;
|
||||
color: $lightTxt;
|
||||
font-family: Bentham;
|
||||
margin: 0;
|
||||
padding: 1em 0;
|
||||
padding: 1rem 0;
|
||||
text-align: center;
|
||||
width: 100%;
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
}
|
||||
|
||||
a {
|
||||
color: lighten($lightTxt, 20%);
|
||||
text-decoration: none;
|
||||
|
BIN
www/img/br_down_icon_16.png
Normal file
After Width: | Height: | Size: 3.5 KiB |
BIN
www/img/br_down_icon_24.png
Normal file
After Width: | Height: | Size: 3.6 KiB |
BIN
www/img/br_down_icon_32.png
Normal file
After Width: | Height: | Size: 3.7 KiB |
BIN
www/img/br_down_icon_48.png
Normal file
After Width: | Height: | Size: 4.0 KiB |
BIN
www/img/br_up_icon_16.png
Normal file
After Width: | Height: | Size: 3.4 KiB |
BIN
www/img/br_up_icon_24.png
Normal file
After Width: | Height: | Size: 3.6 KiB |
BIN
www/img/br_up_icon_32.png
Normal file
After Width: | Height: | Size: 3.7 KiB |
BIN
www/img/br_up_icon_48.png
Normal file
After Width: | Height: | Size: 3.9 KiB |
BIN
www/img/gentleface-wireframe-icons.zip
Normal file
Before Width: | Height: | Size: 3.2 KiB After Width: | Height: | Size: 3.2 KiB |
Before Width: | Height: | Size: 3.3 KiB After Width: | Height: | Size: 3.3 KiB |
Before Width: | Height: | Size: 3.4 KiB After Width: | Height: | Size: 3.4 KiB |
Before Width: | Height: | Size: 3.7 KiB After Width: | Height: | Size: 3.7 KiB |
Before Width: | Height: | Size: 3.2 KiB After Width: | Height: | Size: 3.2 KiB |
Before Width: | Height: | Size: 3.4 KiB After Width: | Height: | Size: 3.4 KiB |
Before Width: | Height: | Size: 3.6 KiB After Width: | Height: | Size: 3.6 KiB |
Before Width: | Height: | Size: 3.2 KiB After Width: | Height: | Size: 3.2 KiB |
Before Width: | Height: | Size: 3.5 KiB After Width: | Height: | Size: 3.5 KiB |
Before Width: | Height: | Size: 3.6 KiB After Width: | Height: | Size: 3.6 KiB |
Before Width: | Height: | Size: 4.0 KiB After Width: | Height: | Size: 4.0 KiB |
@ -2,7 +2,7 @@
|
||||
<html>
|
||||
<head>
|
||||
<title>TimeStamper - Simple Time Tracking</title>
|
||||
<link href='http://fonts.googleapis.com/css?family=Arvo|Bentham|Cuprum|Cantarell|Geo|Josefin+Sans' rel='stylesheet' type='text/css'>
|
||||
<link href='http://fonts.googleapis.com/css?family=Anonymous+Pro|Arvo|Bentham|Cantarell|Josefin+Sans' rel='stylesheet' type='text/css'>
|
||||
<link rel="stylesheet" media="screen" href="/css/ts-screen.css" type="text/css"/>
|
||||
<!-- Needed for IE, but I'm not sure if I'm going to support IE with this tool. -->
|
||||
<!--<script type="text/javascript" src="/js/json2.js"></script>-->
|
||||
@ -14,6 +14,7 @@
|
||||
<!-- DEV -->
|
||||
<script type="text/javascript" src="/js/jquery-1.5.js"></script>
|
||||
|
||||
<script type="text/javascript" src="/js/showdown.js"></script>
|
||||
<script type="text/javascript" src="/js/underscore.js"></script>
|
||||
<script type="text/javascript" src="/js/ICanHaz.js"></script>
|
||||
<script type="text/javascript" src="/js/backbone.js"></script>
|
||||
@ -83,16 +84,18 @@ out(YArg) ->
|
||||
</script>
|
||||
<script type="text/html" id="entryTemplate">
|
||||
<div class="mark">
|
||||
<img class="delete-icon" src="/img/round_delete_icon&16.png"/>
|
||||
<img class="expand-entry" src="/img/br_down_icon_16.png"/>
|
||||
<img class="collapse-entry" src="/img/br_up_icon_16.png"/>
|
||||
<span>{{mark}}</span>
|
||||
<img class="notes-icon" src="/img/notepad_2_icon&16.png"/>
|
||||
</div>
|
||||
<input class="mark-input" type="text" value="{{mark}}"/>
|
||||
<div class="timestamp">{{start}}</div>
|
||||
<input class="timestamp-input" type="text" value="{{timestamp}}"/>
|
||||
<div class="duration">{{duration}}</div>
|
||||
<div class="notes">{{notes}}</div>
|
||||
<input class="notes-input" type="textarea" value="{{notes}}"/>
|
||||
<div class="notes">
|
||||
<div class="notes-text">{{notes}}</div>
|
||||
<textarea class="notes-input" rows="10">{{notes}}</textarea>
|
||||
</div>
|
||||
</script>
|
||||
<meta http-equiv="Content-Type" content="text/html;charset=utf-8" />
|
||||
</head>
|
||||
|
419
www/js/showdown-min.js
vendored
Normal file
@ -0,0 +1,419 @@
|
||||
/*
|
||||
A A L Source code at:
|
||||
T C A <http://www.attacklab.net/>
|
||||
T K B
|
||||
*/
|
||||
|
||||
var Showdown={};
|
||||
Showdown.converter=function(){
|
||||
var _1;
|
||||
var _2;
|
||||
var _3;
|
||||
var _4=0;
|
||||
this.makeHtml=function(_5){
|
||||
_1=new Array();
|
||||
_2=new Array();
|
||||
_3=new Array();
|
||||
_5=_5.replace(/~/g,"~T");
|
||||
_5=_5.replace(/\$/g,"~D");
|
||||
_5=_5.replace(/\r\n/g,"\n");
|
||||
_5=_5.replace(/\r/g,"\n");
|
||||
_5="\n\n"+_5+"\n\n";
|
||||
_5=_6(_5);
|
||||
_5=_5.replace(/^[ \t]+$/mg,"");
|
||||
_5=_7(_5);
|
||||
_5=_8(_5);
|
||||
_5=_9(_5);
|
||||
_5=_a(_5);
|
||||
_5=_5.replace(/~D/g,"$$");
|
||||
_5=_5.replace(/~T/g,"~");
|
||||
return _5;
|
||||
};
|
||||
var _8=function(_b){
|
||||
var _b=_b.replace(/^[ ]{0,3}\[(.+)\]:[ \t]*\n?[ \t]*<?(\S+?)>?[ \t]*\n?[ \t]*(?:(\n*)["(](.+?)[")][ \t]*)?(?:\n+|\Z)/gm,function(_c,m1,m2,m3,m4){
|
||||
m1=m1.toLowerCase();
|
||||
_1[m1]=_11(m2);
|
||||
if(m3){
|
||||
return m3+m4;
|
||||
}else{
|
||||
if(m4){
|
||||
_2[m1]=m4.replace(/"/g,""");
|
||||
}
|
||||
}
|
||||
return "";
|
||||
});
|
||||
return _b;
|
||||
};
|
||||
var _7=function(_12){
|
||||
_12=_12.replace(/\n/g,"\n\n");
|
||||
var _13="p|div|h[1-6]|blockquote|pre|table|dl|ol|ul|script|noscript|form|fieldset|iframe|math|ins|del";
|
||||
var _14="p|div|h[1-6]|blockquote|pre|table|dl|ol|ul|script|noscript|form|fieldset|iframe|math";
|
||||
_12=_12.replace(/^(<(p|div|h[1-6]|blockquote|pre|table|dl|ol|ul|script|noscript|form|fieldset|iframe|math|ins|del)\b[^\r]*?\n<\/\2>[ \t]*(?=\n+))/gm,_15);
|
||||
_12=_12.replace(/^(<(p|div|h[1-6]|blockquote|pre|table|dl|ol|ul|script|noscript|form|fieldset|iframe|math)\b[^\r]*?.*<\/\2>[ \t]*(?=\n+)\n)/gm,_15);
|
||||
_12=_12.replace(/(\n[ ]{0,3}(<(hr)\b([^<>])*?\/?>)[ \t]*(?=\n{2,}))/g,_15);
|
||||
_12=_12.replace(/(\n\n[ ]{0,3}<!(--[^\r]*?--\s*)+>[ \t]*(?=\n{2,}))/g,_15);
|
||||
_12=_12.replace(/(?:\n\n)([ ]{0,3}(?:<([?%])[^\r]*?\2>)[ \t]*(?=\n{2,}))/g,_15);
|
||||
_12=_12.replace(/\n\n/g,"\n");
|
||||
return _12;
|
||||
};
|
||||
var _15=function(_16,m1){
|
||||
var _18=m1;
|
||||
_18=_18.replace(/\n\n/g,"\n");
|
||||
_18=_18.replace(/^\n/,"");
|
||||
_18=_18.replace(/\n+$/g,"");
|
||||
_18="\n\n~K"+(_3.push(_18)-1)+"K\n\n";
|
||||
return _18;
|
||||
};
|
||||
var _9=function(_19){
|
||||
_19=_1a(_19);
|
||||
var key=_1c("<hr />");
|
||||
_19=_19.replace(/^[ ]{0,2}([ ]?\*[ ]?){3,}[ \t]*$/gm,key);
|
||||
_19=_19.replace(/^[ ]{0,2}([ ]?\-[ ]?){3,}[ \t]*$/gm,key);
|
||||
_19=_19.replace(/^[ ]{0,2}([ ]?\_[ ]?){3,}[ \t]*$/gm,key);
|
||||
_19=_1d(_19);
|
||||
_19=_1e(_19);
|
||||
_19=_1f(_19);
|
||||
_19=_7(_19);
|
||||
_19=_20(_19);
|
||||
return _19;
|
||||
};
|
||||
var _21=function(_22){
|
||||
_22=_23(_22);
|
||||
_22=_24(_22);
|
||||
_22=_25(_22);
|
||||
_22=_26(_22);
|
||||
_22=_27(_22);
|
||||
_22=_28(_22);
|
||||
_22=_11(_22);
|
||||
_22=_29(_22);
|
||||
_22=_22.replace(/ +\n/g," <br />\n");
|
||||
return _22;
|
||||
};
|
||||
var _24=function(_2a){
|
||||
var _2b=/(<[a-z\/!$]("[^"]*"|'[^']*'|[^'">])*>|<!(--.*?--\s*)+>)/gi;
|
||||
_2a=_2a.replace(_2b,function(_2c){
|
||||
var tag=_2c.replace(/(.)<\/?code>(?=.)/g,"$1`");
|
||||
tag=_2e(tag,"\\`*_");
|
||||
return tag;
|
||||
});
|
||||
return _2a;
|
||||
};
|
||||
var _27=function(_2f){
|
||||
_2f=_2f.replace(/(\[((?:\[[^\]]*\]|[^\[\]])*)\][ ]?(?:\n[ ]*)?\[(.*?)\])()()()()/g,_30);
|
||||
_2f=_2f.replace(/(\[((?:\[[^\]]*\]|[^\[\]])*)\]\([ \t]*()<?(.*?)>?[ \t]*((['"])(.*?)\6[ \t]*)?\))/g,_30);
|
||||
_2f=_2f.replace(/(\[([^\[\]]+)\])()()()()()/g,_30);
|
||||
return _2f;
|
||||
};
|
||||
var _30=function(_31,m1,m2,m3,m4,m5,m6,m7){
|
||||
if(m7==undefined){
|
||||
m7="";
|
||||
}
|
||||
var _39=m1;
|
||||
var _3a=m2;
|
||||
var _3b=m3.toLowerCase();
|
||||
var url=m4;
|
||||
var _3d=m7;
|
||||
if(url==""){
|
||||
if(_3b==""){
|
||||
_3b=_3a.toLowerCase().replace(/ ?\n/g," ");
|
||||
}
|
||||
url="#"+_3b;
|
||||
if(_1[_3b]!=undefined){
|
||||
url=_1[_3b];
|
||||
if(_2[_3b]!=undefined){
|
||||
_3d=_2[_3b];
|
||||
}
|
||||
}else{
|
||||
if(_39.search(/\(\s*\)$/m)>-1){
|
||||
url="";
|
||||
}else{
|
||||
return _39;
|
||||
}
|
||||
}
|
||||
}
|
||||
url=_2e(url,"*_");
|
||||
var _3e="<a href=\""+url+"\"";
|
||||
if(_3d!=""){
|
||||
_3d=_3d.replace(/"/g,""");
|
||||
_3d=_2e(_3d,"*_");
|
||||
_3e+=" title=\""+_3d+"\"";
|
||||
}
|
||||
_3e+=">"+_3a+"</a>";
|
||||
return _3e;
|
||||
};
|
||||
var _26=function(_3f){
|
||||
_3f=_3f.replace(/(!\[(.*?)\][ ]?(?:\n[ ]*)?\[(.*?)\])()()()()/g,_40);
|
||||
_3f=_3f.replace(/(!\[(.*?)\]\s?\([ \t]*()<?(\S+?)>?[ \t]*((['"])(.*?)\6[ \t]*)?\))/g,_40);
|
||||
return _3f;
|
||||
};
|
||||
var _40=function(_41,m1,m2,m3,m4,m5,m6,m7){
|
||||
var _49=m1;
|
||||
var _4a=m2;
|
||||
var _4b=m3.toLowerCase();
|
||||
var url=m4;
|
||||
var _4d=m7;
|
||||
if(!_4d){
|
||||
_4d="";
|
||||
}
|
||||
if(url==""){
|
||||
if(_4b==""){
|
||||
_4b=_4a.toLowerCase().replace(/ ?\n/g," ");
|
||||
}
|
||||
url="#"+_4b;
|
||||
if(_1[_4b]!=undefined){
|
||||
url=_1[_4b];
|
||||
if(_2[_4b]!=undefined){
|
||||
_4d=_2[_4b];
|
||||
}
|
||||
}else{
|
||||
return _49;
|
||||
}
|
||||
}
|
||||
_4a=_4a.replace(/"/g,""");
|
||||
url=_2e(url,"*_");
|
||||
var _4e="<img src=\""+url+"\" alt=\""+_4a+"\"";
|
||||
_4d=_4d.replace(/"/g,""");
|
||||
_4d=_2e(_4d,"*_");
|
||||
_4e+=" title=\""+_4d+"\"";
|
||||
_4e+=" />";
|
||||
return _4e;
|
||||
};
|
||||
var _1a=function(_4f){
|
||||
_4f=_4f.replace(/^(.+)[ \t]*\n=+[ \t]*\n+/gm,function(_50,m1){
|
||||
return _1c("<h1>"+_21(m1)+"</h1>");
|
||||
});
|
||||
_4f=_4f.replace(/^(.+)[ \t]*\n-+[ \t]*\n+/gm,function(_52,m1){
|
||||
return _1c("<h2>"+_21(m1)+"</h2>");
|
||||
});
|
||||
_4f=_4f.replace(/^(\#{1,6})[ \t]*(.+?)[ \t]*\#*\n+/gm,function(_54,m1,m2){
|
||||
var _57=m1.length;
|
||||
return _1c("<h"+_57+">"+_21(m2)+"</h"+_57+">");
|
||||
});
|
||||
return _4f;
|
||||
};
|
||||
var _58;
|
||||
var _1d=function(_59){
|
||||
_59+="~0";
|
||||
var _5a=/^(([ ]{0,3}([*+-]|\d+[.])[ \t]+)[^\r]+?(~0|\n{2,}(?=\S)(?![ \t]*(?:[*+-]|\d+[.])[ \t]+)))/gm;
|
||||
if(_4){
|
||||
_59=_59.replace(_5a,function(_5b,m1,m2){
|
||||
var _5e=m1;
|
||||
var _5f=(m2.search(/[*+-]/g)>-1)?"ul":"ol";
|
||||
_5e=_5e.replace(/\n{2,}/g,"\n\n\n");
|
||||
var _60=_58(_5e);
|
||||
_60=_60.replace(/\s+$/,"");
|
||||
_60="<"+_5f+">"+_60+"</"+_5f+">\n";
|
||||
return _60;
|
||||
});
|
||||
}else{
|
||||
_5a=/(\n\n|^\n?)(([ ]{0,3}([*+-]|\d+[.])[ \t]+)[^\r]+?(~0|\n{2,}(?=\S)(?![ \t]*(?:[*+-]|\d+[.])[ \t]+)))/g;
|
||||
_59=_59.replace(_5a,function(_61,m1,m2,m3){
|
||||
var _65=m1;
|
||||
var _66=m2;
|
||||
var _67=(m3.search(/[*+-]/g)>-1)?"ul":"ol";
|
||||
var _66=_66.replace(/\n{2,}/g,"\n\n\n");
|
||||
var _68=_58(_66);
|
||||
_68=_65+"<"+_67+">\n"+_68+"</"+_67+">\n";
|
||||
return _68;
|
||||
});
|
||||
}
|
||||
_59=_59.replace(/~0/,"");
|
||||
return _59;
|
||||
};
|
||||
_58=function(_69){
|
||||
_4++;
|
||||
_69=_69.replace(/\n{2,}$/,"\n");
|
||||
_69+="~0";
|
||||
_69=_69.replace(/(\n)?(^[ \t]*)([*+-]|\d+[.])[ \t]+([^\r]+?(\n{1,2}))(?=\n*(~0|\2([*+-]|\d+[.])[ \t]+))/gm,function(_6a,m1,m2,m3,m4){
|
||||
var _6f=m4;
|
||||
var _70=m1;
|
||||
var _71=m2;
|
||||
if(_70||(_6f.search(/\n{2,}/)>-1)){
|
||||
_6f=_9(_72(_6f));
|
||||
}else{
|
||||
_6f=_1d(_72(_6f));
|
||||
_6f=_6f.replace(/\n$/,"");
|
||||
_6f=_21(_6f);
|
||||
}
|
||||
return "<li>"+_6f+"</li>\n";
|
||||
});
|
||||
_69=_69.replace(/~0/g,"");
|
||||
_4--;
|
||||
return _69;
|
||||
};
|
||||
var _1e=function(_73){
|
||||
_73+="~0";
|
||||
_73=_73.replace(/(?:\n\n|^)((?:(?:[ ]{4}|\t).*\n+)+)(\n*[ ]{0,3}[^ \t\n]|(?=~0))/g,function(_74,m1,m2){
|
||||
var _77=m1;
|
||||
var _78=m2;
|
||||
_77=_79(_72(_77));
|
||||
_77=_6(_77);
|
||||
_77=_77.replace(/^\n+/g,"");
|
||||
_77=_77.replace(/\n+$/g,"");
|
||||
_77="<pre><code>"+_77+"\n</code></pre>";
|
||||
return _1c(_77)+_78;
|
||||
});
|
||||
_73=_73.replace(/~0/,"");
|
||||
return _73;
|
||||
};
|
||||
var _1c=function(_7a){
|
||||
_7a=_7a.replace(/(^\n+|\n+$)/g,"");
|
||||
return "\n\n~K"+(_3.push(_7a)-1)+"K\n\n";
|
||||
};
|
||||
var _23=function(_7b){
|
||||
_7b=_7b.replace(/(^|[^\\])(`+)([^\r]*?[^`])\2(?!`)/gm,function(_7c,m1,m2,m3,m4){
|
||||
var c=m3;
|
||||
c=c.replace(/^([ \t]*)/g,"");
|
||||
c=c.replace(/[ \t]*$/g,"");
|
||||
c=_79(c);
|
||||
return m1+"<code>"+c+"</code>";
|
||||
});
|
||||
return _7b;
|
||||
};
|
||||
var _79=function(_82){
|
||||
_82=_82.replace(/&/g,"&");
|
||||
_82=_82.replace(/</g,"<");
|
||||
_82=_82.replace(/>/g,">");
|
||||
_82=_2e(_82,"*_{}[]\\",false);
|
||||
return _82;
|
||||
};
|
||||
var _29=function(_83){
|
||||
_83=_83.replace(/(\*\*|__)(?=\S)([^\r]*?\S[*_]*)\1/g,"<strong>$2</strong>");
|
||||
_83=_83.replace(/(\*|_)(?=\S)([^\r]*?\S)\1/g,"<em>$2</em>");
|
||||
return _83;
|
||||
};
|
||||
var _1f=function(_84){
|
||||
_84=_84.replace(/((^[ \t]*>[ \t]?.+\n(.+\n)*\n*)+)/gm,function(_85,m1){
|
||||
var bq=m1;
|
||||
bq=bq.replace(/^[ \t]*>[ \t]?/gm,"~0");
|
||||
bq=bq.replace(/~0/g,"");
|
||||
bq=bq.replace(/^[ \t]+$/gm,"");
|
||||
bq=_9(bq);
|
||||
bq=bq.replace(/(^|\n)/g,"$1 ");
|
||||
bq=bq.replace(/(\s*<pre>[^\r]+?<\/pre>)/gm,function(_88,m1){
|
||||
var pre=m1;
|
||||
pre=pre.replace(/^ /mg,"~0");
|
||||
pre=pre.replace(/~0/g,"");
|
||||
return pre;
|
||||
});
|
||||
return _1c("<blockquote>\n"+bq+"\n</blockquote>");
|
||||
});
|
||||
return _84;
|
||||
};
|
||||
var _20=function(_8b){
|
||||
_8b=_8b.replace(/^\n+/g,"");
|
||||
_8b=_8b.replace(/\n+$/g,"");
|
||||
var _8c=_8b.split(/\n{2,}/g);
|
||||
var _8d=new Array();
|
||||
var end=_8c.length;
|
||||
for(var i=0;i<end;i++){
|
||||
var str=_8c[i];
|
||||
if(str.search(/~K(\d+)K/g)>=0){
|
||||
_8d.push(str);
|
||||
}else{
|
||||
if(str.search(/\S/)>=0){
|
||||
str=_21(str);
|
||||
str=str.replace(/^([ \t]*)/g,"<p>");
|
||||
str+="</p>";
|
||||
_8d.push(str);
|
||||
}
|
||||
}
|
||||
}
|
||||
end=_8d.length;
|
||||
for(var i=0;i<end;i++){
|
||||
while(_8d[i].search(/~K(\d+)K/)>=0){
|
||||
var _91=_3[RegExp.$1];
|
||||
_91=_91.replace(/\$/g,"$$$$");
|
||||
_8d[i]=_8d[i].replace(/~K\d+K/,_91);
|
||||
}
|
||||
}
|
||||
return _8d.join("\n\n");
|
||||
};
|
||||
var _11=function(_92){
|
||||
_92=_92.replace(/&(?!#?[xX]?(?:[0-9a-fA-F]+|\w+);)/g,"&");
|
||||
_92=_92.replace(/<(?![a-z\/?\$!])/gi,"<");
|
||||
return _92;
|
||||
};
|
||||
var _25=function(_93){
|
||||
_93=_93.replace(/\\(\\)/g,_94);
|
||||
_93=_93.replace(/\\([`*_{}\[\]()>#+-.!])/g,_94);
|
||||
return _93;
|
||||
};
|
||||
var _28=function(_95){
|
||||
_95=_95.replace(/<((https?|ftp|dict):[^'">\s]+)>/gi,"<a href=\"$1\">$1</a>");
|
||||
_95=_95.replace(/<(?:mailto:)?([-.\w]+\@[-a-z0-9]+(\.[-a-z0-9]+)*\.[a-z]+)>/gi,function(_96,m1){
|
||||
return _98(_a(m1));
|
||||
});
|
||||
return _95;
|
||||
};
|
||||
var _98=function(_99){
|
||||
function char2hex(ch){
|
||||
var _9b="0123456789ABCDEF";
|
||||
var dec=ch.charCodeAt(0);
|
||||
return (_9b.charAt(dec>>4)+_9b.charAt(dec&15));
|
||||
}
|
||||
var _9d=[function(ch){
|
||||
return "&#"+ch.charCodeAt(0)+";";
|
||||
},function(ch){
|
||||
return "&#x"+char2hex(ch)+";";
|
||||
},function(ch){
|
||||
return ch;
|
||||
}];
|
||||
_99="mailto:"+_99;
|
||||
_99=_99.replace(/./g,function(ch){
|
||||
if(ch=="@"){
|
||||
ch=_9d[Math.floor(Math.random()*2)](ch);
|
||||
}else{
|
||||
if(ch!=":"){
|
||||
var r=Math.random();
|
||||
ch=(r>0.9?_9d[2](ch):r>0.45?_9d[1](ch):_9d[0](ch));
|
||||
}
|
||||
}
|
||||
return ch;
|
||||
});
|
||||
_99="<a href=\""+_99+"\">"+_99+"</a>";
|
||||
_99=_99.replace(/">.+:/g,"\">");
|
||||
return _99;
|
||||
};
|
||||
var _a=function(_a3){
|
||||
_a3=_a3.replace(/~E(\d+)E/g,function(_a4,m1){
|
||||
var _a6=parseInt(m1);
|
||||
return String.fromCharCode(_a6);
|
||||
});
|
||||
return _a3;
|
||||
};
|
||||
var _72=function(_a7){
|
||||
_a7=_a7.replace(/^(\t|[ ]{1,4})/gm,"~0");
|
||||
_a7=_a7.replace(/~0/g,"");
|
||||
return _a7;
|
||||
};
|
||||
var _6=function(_a8){
|
||||
_a8=_a8.replace(/\t(?=\t)/g," ");
|
||||
_a8=_a8.replace(/\t/g,"~A~B");
|
||||
_a8=_a8.replace(/~B(.+?)~A/g,function(_a9,m1,m2){
|
||||
var _ac=m1;
|
||||
var _ad=4-_ac.length%4;
|
||||
for(var i=0;i<_ad;i++){
|
||||
_ac+=" ";
|
||||
}
|
||||
return _ac;
|
||||
});
|
||||
_a8=_a8.replace(/~A/g," ");
|
||||
_a8=_a8.replace(/~B/g,"");
|
||||
return _a8;
|
||||
};
|
||||
var _2e=function(_af,_b0,_b1){
|
||||
var _b2="(["+_b0.replace(/([\[\]\\])/g,"\\$1")+"])";
|
||||
if(_b1){
|
||||
_b2="\\\\"+_b2;
|
||||
}
|
||||
var _b3=new RegExp(_b2,"g");
|
||||
_af=_af.replace(_b3,_94);
|
||||
return _af;
|
||||
};
|
||||
var _94=function(_b4,m1){
|
||||
var _b6=m1.charCodeAt(0);
|
||||
return "~E"+_b6+"E";
|
||||
};
|
||||
};
|
||||
if(typeof exports!='undefined')exports.Showdown=Showdown;
|
@ -61,13 +61,6 @@
|
||||
//
|
||||
|
||||
|
||||
// **************************************************
|
||||
// GitHub Flavored Markdown modifications by Tekkub
|
||||
// http://github.github.com/github-flavored-markdown/
|
||||
//
|
||||
// Modifications are tagged with "GFM"
|
||||
// **************************************************
|
||||
|
||||
//
|
||||
// Showdown namespace
|
||||
//
|
||||
@ -154,66 +147,10 @@ this.makeHtml = function(text) {
|
||||
// attacklab: Restore tildes
|
||||
text = text.replace(/~T/g,"~");
|
||||
|
||||
// ** GFM ** Auto-link URLs and emails
|
||||
text = text.replace(/https?\:\/\/[^"\s\<\>]*[^.,;'">\:\s\<\>\)\]\!]/g, function(wholeMatch,matchIndex){
|
||||
var left = text.slice(0, matchIndex), right = text.slice(matchIndex)
|
||||
if (left.match(/<[^>]+$/) && right.match(/^[^>]*>/)) {return wholeMatch}
|
||||
return "<a href='" + wholeMatch + "'>" + wholeMatch + "</a>";
|
||||
});
|
||||
text = text.replace(/[a-z0-9_\-+=.]+@[a-z0-9\-]+(\.[a-z0-9-]+)+/ig, function(wholeMatch){return "<a href='mailto:" + wholeMatch + "'>" + wholeMatch + "</a>";});
|
||||
|
||||
// ** GFM ** Auto-link sha1 if GitHub.nameWithOwner is defined
|
||||
text = text.replace(/[a-f0-9]{40}/ig, function(wholeMatch,matchIndex){
|
||||
if (typeof(GitHub) == "undefined" || typeof(GitHub.nameWithOwner) == "undefined") {return wholeMatch;}
|
||||
var left = text.slice(0, matchIndex), right = text.slice(matchIndex)
|
||||
if (left.match(/@$/) || (left.match(/<[^>]+$/) && right.match(/^[^>]*>/))) {return wholeMatch;}
|
||||
return "<a href='http://github.com/" + GitHub.nameWithOwner + "/commit/" + wholeMatch + "'>" + wholeMatch.substring(0,7) + "</a>";
|
||||
});
|
||||
|
||||
// ** GFM ** Auto-link user@sha1 if GitHub.nameWithOwner is defined
|
||||
text = text.replace(/([a-z0-9_\-+=.]+)@([a-f0-9]{40})/ig, function(wholeMatch,username,sha,matchIndex){
|
||||
if (typeof(GitHub) == "undefined" || typeof(GitHub.nameWithOwner) == "undefined") {return wholeMatch;}
|
||||
GitHub.repoName = GitHub.repoName || _GetRepoName()
|
||||
var left = text.slice(0, matchIndex), right = text.slice(matchIndex)
|
||||
if (left.match(/\/$/) || (left.match(/<[^>]+$/) && right.match(/^[^>]*>/))) {return wholeMatch;}
|
||||
return "<a href='http://github.com/" + username + "/" + GitHub.repoName + "/commit/" + sha + "'>" + username + "@" + sha.substring(0,7) + "</a>";
|
||||
});
|
||||
|
||||
// ** GFM ** Auto-link user/repo@sha1
|
||||
text = text.replace(/([a-z0-9_\-+=.]+\/[a-z0-9_\-+=.]+)@([a-f0-9]{40})/ig, function(wholeMatch,repo,sha){
|
||||
return "<a href='http://github.com/" + repo + "/commit/" + sha + "'>" + repo + "@" + sha.substring(0,7) + "</a>";
|
||||
});
|
||||
|
||||
// ** GFM ** Auto-link #issue if GitHub.nameWithOwner is defined
|
||||
text = text.replace(/#([0-9]+)/ig, function(wholeMatch,issue,matchIndex){
|
||||
if (typeof(GitHub) == "undefined" || typeof(GitHub.nameWithOwner) == "undefined") {return wholeMatch;}
|
||||
var left = text.slice(0, matchIndex), right = text.slice(matchIndex)
|
||||
if (left == "" || left.match(/[a-z0-9_\-+=.]$/) || (left.match(/<[^>]+$/) && right.match(/^[^>]*>/))) {return wholeMatch;}
|
||||
return "<a href='http://github.com/" + GitHub.nameWithOwner + "/issues/#issue/" + issue + "'>" + wholeMatch + "</a>";
|
||||
});
|
||||
|
||||
// ** GFM ** Auto-link user#issue if GitHub.nameWithOwner is defined
|
||||
text = text.replace(/([a-z0-9_\-+=.]+)#([0-9]+)/ig, function(wholeMatch,username,issue,matchIndex){
|
||||
if (typeof(GitHub) == "undefined" || typeof(GitHub.nameWithOwner) == "undefined") {return wholeMatch;}
|
||||
GitHub.repoName = GitHub.repoName || _GetRepoName()
|
||||
var left = text.slice(0, matchIndex), right = text.slice(matchIndex)
|
||||
if (left.match(/\/$/) || (left.match(/<[^>]+$/) && right.match(/^[^>]*>/))) {return wholeMatch;}
|
||||
return "<a href='http://github.com/" + username + "/" + GitHub.repoName + "/issues/#issue/" + issue + "'>" + wholeMatch + "</a>";
|
||||
});
|
||||
|
||||
// ** GFM ** Auto-link user/repo#issue
|
||||
text = text.replace(/([a-z0-9_\-+=.]+\/[a-z0-9_\-+=.]+)#([0-9]+)/ig, function(wholeMatch,repo,issue){
|
||||
return "<a href='http://github.com/" + repo + "/issues/#issue/" + issue + "'>" + wholeMatch + "</a>";
|
||||
});
|
||||
|
||||
return text;
|
||||
}
|
||||
|
||||
|
||||
var _GetRepoName = function() {
|
||||
return GitHub.nameWithOwner.match(/^.+\/(.+)$/)[1]
|
||||
}
|
||||
|
||||
var _StripLinkDefinitions = function(text) {
|
||||
//
|
||||
// Strips link definitions from text, stores the URLs and titles in
|
||||
@ -724,10 +661,10 @@ var _DoHeaders = function(text) {
|
||||
// --------
|
||||
//
|
||||
text = text.replace(/^(.+)[ \t]*\n=+[ \t]*\n+/gm,
|
||||
function(wholeMatch,m1){return hashBlock("<h1>" + _RunSpanGamut(m1) + "</h1>");});
|
||||
function(wholeMatch,m1){return hashBlock('<h1 id="' + headerId(m1) + '">' + _RunSpanGamut(m1) + "</h1>");});
|
||||
|
||||
text = text.replace(/^(.+)[ \t]*\n-+[ \t]*\n+/gm,
|
||||
function(matchFound,m1){return hashBlock("<h2>" + _RunSpanGamut(m1) + "</h2>");});
|
||||
function(matchFound,m1){return hashBlock('<h2 id="' + headerId(m1) + '">' + _RunSpanGamut(m1) + "</h2>");});
|
||||
|
||||
// atx-style headers:
|
||||
// # Header 1
|
||||
@ -751,9 +688,12 @@ var _DoHeaders = function(text) {
|
||||
text = text.replace(/^(\#{1,6})[ \t]*(.+?)[ \t]*\#*\n+/gm,
|
||||
function(wholeMatch,m1,m2) {
|
||||
var h_level = m1.length;
|
||||
return hashBlock("<h" + h_level + ">" + _RunSpanGamut(m2) + "</h" + h_level + ">");
|
||||
return hashBlock("<h" + h_level + ' id="' + headerId(m2) + '">' + _RunSpanGamut(m2) + "</h" + h_level + ">");
|
||||
});
|
||||
|
||||
function headerId(m) {
|
||||
return m.replace(/[^\w]/g, '').toLowerCase();
|
||||
}
|
||||
return text;
|
||||
}
|
||||
|
||||
@ -1044,7 +984,6 @@ var _DoItalicsAndBold = function(text) {
|
||||
text = text.replace(/(\*\*|__)(?=\S)([^\r]*?\S[*_]*)\1/g,
|
||||
"<strong>$2</strong>");
|
||||
|
||||
text = text.replace(/(\w)_(\w)/g, "$1~E95E$2") // ** GFM ** "~E95E" == escaped "_"
|
||||
text = text.replace(/(\*|_)(?=\S)([^\r]*?\S)\1/g,
|
||||
"<em>$2</em>");
|
||||
|
||||
@ -1126,7 +1065,6 @@ var _FormParagraphs = function(text) {
|
||||
}
|
||||
else if (str.search(/\S/) >= 0) {
|
||||
str = _RunSpanGamut(str);
|
||||
str = str.replace(/\n/g,"<br />"); // ** GFM **
|
||||
str = str.replace(/^([ \t]*)/g,"<p>");
|
||||
str += "</p>"
|
||||
grafsOut.push(str);
|
||||
@ -1359,3 +1297,6 @@ var escapeCharacters_callback = function(wholeMatch,m1) {
|
||||
}
|
||||
|
||||
} // end of Showdown.converter
|
||||
|
||||
// export
|
||||
if (typeof exports != 'undefined') exports.Showdown = Showdown;
|
94
www/js/ts.js
@ -91,18 +91,30 @@ $(document).ready(function(){
|
||||
|
||||
className: 'entry',
|
||||
|
||||
notesCache: false,
|
||||
|
||||
events: {
|
||||
"click img.notes-icon" : "toggleNotes",
|
||||
"click img.expand-entry" : "showNotes",
|
||||
"click img.collapse-entry" : "hideNotes",
|
||||
"dblclick div.mark" : "editMark",
|
||||
"dblclick div.timestamp" : "editTimestamp",
|
||||
"dblclick div.notes" : "editNotes",
|
||||
"keypress .mark-input" : "updateOnEnter",
|
||||
"keypress .timestamp-input" : "updateOnEnter"
|
||||
"keypress .timestamp-input" : "updateOnEnter",
|
||||
"keypress .notes-input" : "updateOnCtrlEnter",
|
||||
"blur .mark-input" : "close",
|
||||
"blur .timestamp-input" : "close",
|
||||
"blur .notes-input" : "close"
|
||||
},
|
||||
|
||||
initialize: function(options) {
|
||||
_.bindAll(this, 'render', 'close', 'editTImestamp',
|
||||
'editMark', 'updateOnEnter', 'getViewModel', 'toggleNotes');
|
||||
this.model.bind('change', this.render);
|
||||
_.bindAll(this, 'render', 'close', 'editTImestamp', 'editMark',
|
||||
'update', 'updateOnEnter', 'updateOnCtrlEnter', 'getViewModel',
|
||||
'renderNotes', 'showNotes', 'hideNotes');
|
||||
|
||||
this.markdownConverter = options.markdownConverter;
|
||||
|
||||
this.model.bind('change', this.update);
|
||||
this.model.view = this;
|
||||
|
||||
this.nextModel = options.nextModel;
|
||||
@ -113,9 +125,12 @@ $(document).ready(function(){
|
||||
* HTML content. Add new `blur` listeners to the input fields.
|
||||
*/
|
||||
render: function() {
|
||||
// render the HTML
|
||||
$(this.el).html(ich.entryTemplate(this.getViewModel()));
|
||||
this.$(".mark-input").bind('blur', this.close);
|
||||
this.$(".timestamp-input").bind('blur', this.close);
|
||||
|
||||
// invalidate the notes display cache
|
||||
this.notesCache = false;
|
||||
|
||||
return this;
|
||||
},
|
||||
|
||||
@ -130,9 +145,19 @@ $(document).ready(function(){
|
||||
this.$('.timestamp').text(data.start);
|
||||
this.$('.timestamp-input').val(data.timestamp);
|
||||
this.$('.duration').text(data.duration);
|
||||
this.$('.notes-text').html(this.renderNotes(data.notes));
|
||||
this.$('.notes-input').val(data.notes);
|
||||
return this;
|
||||
},
|
||||
|
||||
renderNotes: function(source) {
|
||||
if (!this.notesCache) {
|
||||
this.notesCache = this.markdownConverter.makeHtml(source);
|
||||
}
|
||||
|
||||
return this.notesCache
|
||||
},
|
||||
|
||||
editMark: function() {
|
||||
$(this.el).addClass('edit-mark');
|
||||
this.$('.mark-input').focus();
|
||||
@ -145,6 +170,18 @@ $(document).ready(function(){
|
||||
return this;
|
||||
},
|
||||
|
||||
editNotes: function() {
|
||||
// invalidate notes HTML cache
|
||||
this.notesCache = false;
|
||||
|
||||
// show notes textarea, hide display
|
||||
$(this.el).addClass('edit-notes');
|
||||
|
||||
// focus input
|
||||
this.$('.notes-input').focus();
|
||||
return this;
|
||||
},
|
||||
|
||||
/**
|
||||
* Translate the model data into a form suitable to be displayed.
|
||||
* @return a map including display-able `start` and `duration` values.
|
||||
@ -156,20 +193,21 @@ $(document).ready(function(){
|
||||
var tsDate = new Date(data.timestamp);
|
||||
data.start = this.formatStart(tsDate);
|
||||
data.duration = this.formatDuration(this.model, this.nextModel);
|
||||
data.notes = data.notes ? data.notes : '*No notes for this entry.*';
|
||||
return data;
|
||||
},
|
||||
|
||||
/** Close editable fields. */
|
||||
close: function() {
|
||||
$(this.el).removeClass('edit-mark edit-timestamp');
|
||||
$(this.el).removeClass('edit-mark edit-timestamp edit-notes');
|
||||
},
|
||||
|
||||
/** Persist changes in input fields. */
|
||||
save: function() {
|
||||
this.model.save({
|
||||
mark: this.$('.mark-input').val(),
|
||||
timestamp: this.$('.timestamp-input').val()});
|
||||
this.update();
|
||||
timestamp: this.$('.timestamp-input').val(),
|
||||
notes: this.$('.notes-input').val()});
|
||||
},
|
||||
|
||||
/** Event handler for keypresses on entry input fields. */
|
||||
@ -177,6 +215,10 @@ $(document).ready(function(){
|
||||
if(e.keyCode == 13) { this.save(); this.close(); }
|
||||
},
|
||||
|
||||
updateOnCtrlEnter: function(e) {
|
||||
if (e.keyCode == 10) { this.save(); this.close(); }
|
||||
},
|
||||
|
||||
/**
|
||||
* Get the display-able start time from the entry timestamp.
|
||||
* @param startDate a Date object, the entry timestamp.
|
||||
@ -229,8 +271,19 @@ $(document).ready(function(){
|
||||
min + "m ";
|
||||
},
|
||||
|
||||
toggleNotes: function() {
|
||||
this.$('.notes').slideToggle();
|
||||
showNotes: function() {
|
||||
if (!this.notesCache) {
|
||||
this.$('.notes-text').html(
|
||||
this.renderNotes(this.model.get('notes')))
|
||||
}
|
||||
|
||||
this.$('.notes').slideDown();
|
||||
$(this.el).addClass('show-notes');
|
||||
},
|
||||
|
||||
hideNotes: function() {
|
||||
this.$('.notes').slideUp();
|
||||
$(this.el).removeClass('show-notes');
|
||||
}
|
||||
});
|
||||
|
||||
@ -243,15 +296,24 @@ $(document).ready(function(){
|
||||
},
|
||||
|
||||
initialize: function() {
|
||||
_.bindAll(this, 'addOne', 'createNewEntry', 'render');
|
||||
_.bindAll(this, 'addOne', 'createNewEntry', 'render', 'renderOne');
|
||||
this.collection.bind('add', this.addOne);
|
||||
this.collection.bind('refresh', this.render);
|
||||
this.collection.view = this;
|
||||
this.entryContainer = this.$("#entries")
|
||||
this.markdownConverter = new Showdown.converter();
|
||||
},
|
||||
|
||||
addOne: function(entry, nextEntry) {
|
||||
if (!entry.view) { new TS.EntryView({model: entry}); }
|
||||
addOne: function(entry) {
|
||||
var lastEntry = this.collection.at(this.collection.length - 2);
|
||||
lastEntry.view.nextModel = entry;
|
||||
lastEntry.view.update();
|
||||
this.renderOne(entry, null);
|
||||
},
|
||||
|
||||
renderOne: function(entry, nextEntry) {
|
||||
if (!entry.view) { new TS.EntryView(
|
||||
{model: entry, markdownConverter: this.markdownConverter}); }
|
||||
entry.view.nextModel = nextEntry
|
||||
this.entryContainer.prepend(entry.view.render().el);
|
||||
},
|
||||
@ -280,7 +342,7 @@ $(document).ready(function(){
|
||||
var entry = this.collection.at(i);
|
||||
var nextEntry = (i + 1 < len ? this.collection.at(i + 1) : null);
|
||||
|
||||
this.addOne(entry, nextEntry);
|
||||
this.renderOne(entry, nextEntry);
|
||||
}
|
||||
}
|
||||
});
|
||||
|