' +
+- '';
++ if (diffContent != "" || binary) {
++ finalContent += '
' +
++ '';
++ }
+
+- if (!binary) {
++ if (!binary && (diffContent != "")) {
+ finalContent += '
' +
+ '
' + line1 + "
" +
+ '
' + line2 + "
" +
+@@ -86,7 +88,8 @@ var highlightDiff = function(diff, element, callbacks) {
+ }
+ }
+
+- finalContent += '
';
++ if (diffContent != "" || binary)
++ finalContent += '
';
+
+ line1 = "";
+ line2 = "";
+@@ -117,6 +120,29 @@ var highlightDiff = function(diff, element, callbacks) {
+ }
+
+ if (header) {
++ if (firstChar == "n") {
++ if (l.match(/^new file mode .*$/))
++ startname = "/dev/null";
++
++ if (match = l.match(/^new mode (.*)$/)) {
++ mode_change = true;
++ new_mode = match[1];
++ }
++ continue;
++ }
++ if (firstChar == "o") {
++ if (match = l.match(/^old mode (.*)$/)) {
++ mode_change = true;
++ old_mode = match[1];
++ }
++ continue;
++ }
++
++ if (firstChar == "d") {
++ if (l.match(/^deleted file mode .*$/))
++ endname = "/dev/null";
++ continue;
++ }
+ if (firstChar == "-") {
+ if (match = l.match(/^--- (a\/)?(.*)$/))
+ startname = match[2];
+@@ -153,17 +179,6 @@ var highlightDiff = function(diff, element, callbacks) {
+ }
+ }
+
+- if (match = l.match(/^old mode (.*)$/)) {
+- mode_change = true;
+- old_mode = match[1];
+- }
+-
+- if (match = l.match(/^new mode (.*)$/)) {
+- mode_change = true;
+- new_mode = match[1];
+- }
+-
+-
+ // Finish the header
+ if (firstChar == "@")
+ header = false;
+@@ -188,7 +203,7 @@ var highlightDiff = function(diff, element, callbacks) {
+ header = false;
+ }
+
+- if (m = l.match(/@@ \-([0-9]+),\d+ \+(\d+),\d+ @@/))
++ if (m = l.match(/@@ \-([0-9]+),?\d* \+(\d+),?\d* @@/))
+ {
+ hunk_start_line_1 = parseInt(m[1]) - 1;
+ hunk_start_line_2 = parseInt(m[2]) - 1;
+@@ -199,14 +214,14 @@ var highlightDiff = function(diff, element, callbacks) {
+ } else if (firstChar == " ") {
+ line1 += ++hunk_start_line_1 + "\n";
+ line2 += ++hunk_start_line_2 + "\n";
+- diffContent += l + "\n";
++ diffContent += "
" + l + "
";
+ }
+ }
+
+ finishContent();
+
+ // This takes about 7ms
+- element.innerHTML = finalContent;
++ // element.innerHTML = finalContent;
+
+ // TODO: Replace this with a performance pref call
+ if (false)
+diff --git a/html/test.html b/html/test.html
+index 795c686..8919193 100644
+--- a/html/test.html
++++ b/html/test.html
+@@ -13,10 +13,13 @@
+ }
+
+ var doeHet = function() {
++ var start = Date.now();
+ highlightDiff($("orig_diff").value,
+ $("diff"),
+ { "newfile" : newFile }
+ );
++ var end = Date.now();
++ console.debug("Parsing took: " + (end - start) + " ms");
+ }
+
+
+diff --git a/html/views/commit/commit.css b/html/views/commit/commit.css
+index 18d6a2e..268109d 100644
+--- a/html/views/commit/commit.css
++++ b/html/views/commit/commit.css
+@@ -61,7 +61,6 @@ table.diff {
+ }
+
+ .diff a.stagebutton {
+- display: block;
+ width: 40px;
+ padding: 0 2px 0 2px;
+ margin-bottom: 4px;
+@@ -77,7 +76,6 @@ table.diff {
+ text-align: center;
+
+ -webkit-border-radius: 2px;
+- float: left;
+ }
+
+ #multiselect {
+@@ -94,4 +92,4 @@ table.diff {
+ border: 5px solid #EEE;
+ margin: -5px;
+ padding-left: 20px;
+-}
+\ No newline at end of file
++}
+diff --git a/html/views/history/history.css b/html/views/history/history.css
+index 7c1aaf8..ff505aa 100644
+--- a/html/views/history/history.css
++++ b/html/views/history/history.css
+@@ -48,7 +48,7 @@ a.servicebutton{
+ }
+
+ .property_name {
+- width: 50px;
++ width: 6em;
+ color:#7F7F7F;
+ text-align: right;
+ font-weight: bold;
+diff --git a/html/views/history/history.js b/html/views/history/history.js
+index 258310c..ee94436 100644
+--- a/html/views/history/history.js
++++ b/html/views/history/history.js
+@@ -40,11 +40,34 @@ var Commit = function(obj) {
+ }
+
+ this.reloadRefs = function() {
+- this.refs = this.object.refs;
++ this.refs = this.object.refs();
+ }
+
+ };
+
++
++var confirm_gist = function(confirmation_message) {
++ if (!Controller.isFeatureEnabled_("confirmGist")) {
++ gistie();
++ return;
++ }
++
++ // Set optional confirmation_message
++ confirmation_message = confirmation_message || "Yes. Paste this commit.";
++ var deleteMessage = Controller.getConfig_("github.token") ? " " : "You might not be able to delete it after posting.
";
++ var publicMessage = Controller.isFeatureEnabled_("publicGist") ? "
public" : "private";
++ // Insert the verification links into div#notification_message
++ var notification_text = 'This will create a ' + publicMessage + ' paste of your commit to
http://gist.github.com/' +
++ deleteMessage +
++ 'Are you sure you want to continue?
' +
++ '
No. Cancel. | ' +
++ '
' + confirmation_message + '';
++
++ notify(notification_text, 0);
++ // Hide img#spinner, since it?s visible by default
++ $("spinner").style.display = "none";
++}
++
+ var gistie = function() {
+ notify("Uploading code to Gistie..", 0);
+
+@@ -60,9 +83,9 @@ var gistie = function() {
+ if (token && login) {
+ parameters.login = login;
+ parameters.token = token;
+- } else {
+- parameters.private = true;
+ }
++ if (!Controller.isFeatureEnabled_("publicGist"))
++ parameters.private = true;
+
+ var params = [];
+ for (var name in parameters)
+@@ -223,8 +246,22 @@ var enableFeatures = function()
+
+ var loadExtendedCommit = function(commit)
+ {
+- if (commit.author_email)
+- $("authorID").innerHTML = commit.author_name + " <
" + commit.author_email + ">";
++ var formatEmail = function(name, email) {
++ return email ? name + " <
" + email + ">" : name;
++ }
++
++ $("authorID").innerHTML = formatEmail(commit.author_name, commit.author_email);
++
++ if (commit.committer_name != commit.author_name) {
++ $("committerID").parentNode.style.display = "";
++ $("committerID").innerHTML = formatEmail(commit.committer_name, commit.committer_email);
++
++ $("committerDate").parentNode.style.display = "";
++ $("committerDate").innerHTML = commit.committer_date;
++ } else {
++ $("committerID").parentNode.style.display = "none";
++ $("committerDate").parentNode.style.display = "none";
++ }
+
+ $("date").innerHTML = commit.author_date;
+ $("message").innerHTML = commit.message.replace(/\n/g,"
");
+diff --git a/html/views/history/index.html b/html/views/history/index.html
+index c120e01..65117c3 100644
+--- a/html/views/history/index.html
++++ b/html/views/history/index.html
+@@ -14,7 +14,7 @@
+
+
+
+@@ -33,6 +33,14 @@
+
Date: |
+
Pieter de Bie |
+
++
++ | Committer: |
++ Pieter de Bie |
++
++
++ | Commit Date: |
++ Pieter de Bie |
++
+
+ | Subject: |
+ Pieter de Bie |
+@@ -48,7 +56,7 @@
+
+
+
+
+diff --git a/speedtest.m b/speedtest.m
+index 2d96213..18173bb 100644
+--- a/speedtest.m
++++ b/speedtest.m
+@@ -6,18 +6,36 @@
+ // Copyright 2008 Pieter de Bie. All rights reserved.
+ //
+
+-#import "speedtest.h"
+ #import "PBGitRepository.h"
+-#import "PBGitRevList.h"
++#import "PBGitRevSpecifier.h"
++#import "PBGitCommit.h"
++#import "PBGitRevPool.h"
+
+ int main()
+ {
+- PBGitRepository *repo = [[PBGitRepository alloc] initWithURL:[NSURL URLWithString:@"file:///Users/pieter/projects/git"]];
+- PBGitRevList *revList = [[PBGitRevList alloc] initWithRepository:repo];
+- PBGitRevSpecifier *revSpecifier = [[PBGitRevSpecifier alloc] initWithParameters:[NSArray arrayWithObject:@"master"]];
++ PBGitRepository *repo = [[PBGitRepository alloc] initWithURL:[NSURL URLWithString:@"file:///Users/pieter/projects/External/git"]];
++ //PBGitRevList *revList = [[PBGitRevList alloc] initWithRepository:repo];
++ PBGitRevSpecifier *revSpecifier = [[PBGitRevSpecifier alloc] initWithParameters:[NSArray arrayWithObject:@"HEAD"]];
++ PBGitRevPool *revPool = [[PBGitRevPool alloc] initWithRepository:repo];
+
+ //[repo reloadRefs];
+- [revList walkRevisionListWithSpecifier:revSpecifier];
+-
++ [revPool loadRevisions:revSpecifier];
++// [revPool listCommits];
++
++ NSDate *start = [NSDate date];
++ PBGitCommit *commit = [revPool commitWithSha:@"6270bae2fe7b13a0809061760ddb2b03ce2ca33a"];
++ NSMutableArray *array = [NSMutableArray array];
++ while (commit)
++ {
++ [array addObject:[commit realSha]];
++ if (commit.nParents)
++ commit = [revPool commitWithOid:commit.parentShas[0]];
++ else
++ commit = NULL;
++ }
++ NSTimeInterval duration = [[NSDate date] timeIntervalSinceDate:start];
++
++ NSLog(@"Walked all refs in %f seconds", duration);
++ NSLog(@"%@", [array componentsJoinedByString:@"\n"]);
+ return 0;
+ }
+\ No newline at end of file
+