Compare commits

...

47 Commits

Author SHA1 Message Date
00e9de72c8 git-gui 0.13
Signed-off-by: Pat Thoyts <patthoyts@users.sourceforge.net>
2010-09-14 22:42:37 +01:00
2473543caa git-gui: avoid mis-encoding the copyright message on Windows.
On Windows the tcl script file will use the system encoding and attempting
to convert the copyright mis-encodes the string. Instead, keep the message
as ASCII and substitute in the correct unicode character when running.

Signed-off-by: Pat Thoyts <patthoyts@users.sourceforge.net>
2010-09-13 20:41:42 +01:00
421a31e22d git-gui: Update Swedish translation (521t).
Signed-off-by: Peter Krefting <peter@softwolves.pp.se>
Signed-off-by: Pat Thoyts <patthoyts@users.sourceforge.net>
2010-09-13 19:25:55 +01:00
aef0b48ef0 git-gui: ensure correct application termination in git-gui--askpass
With Tk 8.5 the askpass utility can hang waiting for the wish shell
implicit event loop to exit. This patch uses an explicit event loop
to ensure correct application termination.

Reported-by: Anders Kaseorg <andersk@mit.edu>
Tested-by: Jonathan Nieder <jrnieder@gmail.com>
Signed-off-by: Pat Thoyts <patthoyts@users.sourceforge.net>
2010-08-18 23:19:24 +01:00
d5257fb3c1 git-gui: handle textconv filter on Windows and in development
When developing/testing we run git-gui.sh directly and the makefile
configured variables are not properly set. Configure the new shellpath
accessor to handle this case.

On Windows we may not find the shell so in this case revert to simply
executing the filter command without the shell intermediate.

Signed-off-by: Pat Thoyts <patthoyts@users.sourceforge.net>
2010-08-12 21:37:32 +01:00
62f9a632c8 git-gui: use shell to launch textconv filter in "blame"
The textconv filters may include multiple arguments and may make use
of unix shell features. To maintain compatibility with 'git blame'
ensure these commands are passed through bash.

Reported-by: Kirill Smelkov <kirr@landau.phys.spbu.ru>
Signed-off-by: Matthieu Moy <Matthieu.Moy@imag.fr>
Signed-off-by: Pat Thoyts <patthoyts@users.sourceforge.net>
2010-08-12 21:35:09 +01:00
780777720a git-gui: display error launching blame as a message box.
This does not appear to Windows users and can follow the form of the fatal
error messages near the top of the script file.

Signed-off-by: Pat Thoyts <patthoyts@users.sourceforge.net>
2010-08-08 00:07:43 +01:00
ea47503d4d git-gui: Make usage statement visible on Windows.
On Windows stdout and stderr are not connected to anything so the usage
statement is never shown to the user when an error is made with a command
line like 'git gui browser'. Use a messagebox on windows.

Signed-off-by: Pat Thoyts <patthoyts@users.sourceforge.net>
2010-08-08 00:07:01 +01:00
2810a58dba git-gui: fix size and position of window panes on startup
The themed panedwindow needs to have the sash position set after the
widget has been mapped therefore apply this setting in the Map event
binding. To avoid visible redraws as the application is constructed
the main window should be withdrawn until all the widgets have been added

Signed-off-by: Pat Thoyts <patthoyts@users.sourceforge.net>
2010-08-02 13:42:45 +01:00
9cb268c426 git-gui: mc cannot be used before msgcat has been loaded
If someone attempts to use an older version that Tk 8.4 the error was
masked by the lack of a mc command.

Signed-off-by: Pat Thoyts <patthoyts@users.sourceforge.net>
2010-08-02 12:13:05 +01:00
1fbaccad4d git-gui: use textconv filter for diff and blame
Create a checkbox "Use Textconv For Diffs and Blame" in git-gui options.
If checked and if the driver for the concerned file exists, git-gui calls diff
and blame with --textconv option

Signed-off-by: Clément Poulain <clement.poulain@ensimag.imag.fr>
Signed-off-by: Diane Gasselin <diane.gasselin@ensimag.imag.fr>
Signed-off-by: Axel Bonnet <axel.bonnet@ensimag.imag.fr>
Signed-off-by: Matthieu Moy <Matthieu.Moy@imag.fr>
Signed-off-by: Pat Thoyts <patthoyts@users.sourceforge.net>
2010-07-30 10:05:27 +01:00
85123549f0 git-gui: Avoid using the <<Copy>> binding as a menu accelerator on win32
On Windows the Control-C binding is used to copy and is mapped to the Tk
virtual event <<Copy>>. In the initial git-gui dialog this is also bound
as an accelerator for the Clone menu item. The effect is that both bindings
run, copying the text but resetting the clone page or switching to the clone
page when the user tries to copy text from one of the entry fields.
This patch avoids this by using Control-L instead for Windows only.

Signed-off-by: Pat Thoyts <patthoyts@users.sourceforge.net>
2010-07-30 10:05:27 +01:00
fc17e5e5bd git-gui: fix shortcut creation on cygwin
When the user tried to create a desktop icon with git gui on cygwin
wscript was complaining about an unknown option and displaying the
non-native path as such.

Signed-off-by: Heiko Voigt <hvoigt@hvoigt.net>
Signed-off-by: Johannes Schindelin <johannes.schindelin@gmx.de>
Signed-off-by: Pat Thoyts <patthoyts@users.sourceforge.net>
2010-07-30 10:05:26 +01:00
4c79adc5c0 git-gui: fix PATH environment for mingw development environment
When creating a desktop shortcut from the gui the shortcut directly
starts wish with the git-gui script. In the msysgit development
environment some dll's reside in the mingw/bin directory which causes
that git can not start because libiconv2.dll is not found.

When using such a link the error is even more cryptic stating:
"child killed: unknown signal"

Signed-off-by: Heiko Voigt <hvoigt@hvoigt.net>
Signed-off-by: Johannes Schindelin <johannes.schindelin@gmx.de>
Signed-off-by: Pat Thoyts <patthoyts@users.sourceforge.net>
2010-07-30 09:57:26 +01:00
a197b1e89a git-gui: fix usage of _gitworktree when creating shortcut for windows
This fixes msysGit issue 425.

Signed-off-by: Heiko Voigt <heiko.voigt@mahr.de>
Signed-off-by: Johannes Schindelin <johannes.schindelin@gmx.de>
Signed-off-by: Pat Thoyts <patthoyts@users.sourceforge.net>
2010-07-30 09:57:26 +01:00
2e0cda658e git-gui: fix "Explore Working Copy" for Windows again
It has already been fixed in commit 454efb47 (git-gui (Win): make
"Explore Working Copy" more robust, 2009-04-01), but has been broken in
commit 21985a11 (git-gui: handle non-standard worktree locations,
2010-01-23) by accidentally replacing too much with a new variable.

The problem can be reproduced when starting git-gui from within a
subdirectory. The solution is to convert the path name, explorer.exe is
invoked with, to a platform native name.

Signed-off-by: Markus Heidelberg <markus.heidelberg@web.de>
Signed-off-by: Pat Thoyts <patthoyts@users.sourceforge.net>
2010-07-30 09:57:26 +01:00
b963d11827 git-gui: fix usage of themed widgets variable
There was one forgotten global so NS was not visible to the method
which resulted in an error.

Signed-off-by: Heiko Voigt <hvoigt@hvoigt.net>
2010-07-10 23:41:54 +01:00
13a3d637b2 git-gui: Handle failure of core.worktree to identify the working directory.
Commit 21985a11 'git-gui: handle non-standard worktree locations' attempts
to use either GIT_WORK_TREE or core.worktree to set the _gitworktree
variable but these may not be set which leads to a failure to launch
gitk to review history. Use _gitdir to set the location for a standard
git layout where the parent of the .git directory is the working tree.

Signed-off-by: Pat Thoyts <patthoyts@users.sourceforge.net>
2010-07-10 23:40:59 +01:00
2a9edd0305 Merge branch 'maint'
* maint:
  git-gui: check whether systems nice command works or disable it
2010-02-08 07:57:37 -08:00
9c898a18ea git-gui: check whether systems nice command works or disable it
This fixes issue 394 from msysgit. It seems that the Gnuwin32 project
provides a nice command but it returns a "not implemented" error. To
help users we now try to execute once and disable it in case it fails.

Signed-off-by: Heiko Voigt <hvoigt@hvoigt.net>
Signed-off-by: Shawn O. Pearce <spearce@spearce.org>
2010-02-08 07:56:55 -08:00
89d61592bd git-gui: update french translation
Signed-off-by: Emmanuel Trillaud <etrillaud@gmail.com>
Signed-off-by: Shawn O. Pearce <spearce@spearce.org>
2010-02-02 07:34:04 -08:00
5bf46841c0 git-gui: update Japanese translation
Update ja.po to match 2010-01-26 version of pot file.

Signed-off-by: しらいし ななこ <nanako3@lavabit.com>
Signed-off-by: Shawn O. Pearce <spearce@spearce.org>
2010-02-02 06:59:06 -08:00
e1a3f28b14 Merge branch 'maint'
* maint:
  git-gui: fix shortcut for menu "Commit/Revert Changes"
2010-01-29 07:58:56 -08:00
d6db1bbe11 git-gui: fix shortcut for menu "Commit/Revert Changes"
The shortcut was not properly recognized previously.

Signed-off-by: Heiko Voigt <heiko.voigt@mahr.de>
Signed-off-by: Shawn O. Pearce <spearce@spearce.org>
2010-01-29 07:58:52 -08:00
831cc7ebb4 git-gui: Quote git path when starting another gui in a submodule
In do_git_gui the path of the git executable has to be put into a
list, otherwise calling it will fail when when spaces are present
in its path.

Reported-by: Heiko Voigt <hvoigt@hvoigt.net>
Signed-off-by: Jens Lehmann <Jens.Lehmann@web.de>
Signed-off-by: Shawn O. Pearce <spearce@spearce.org>
2010-01-28 15:44:41 -08:00
cbdaf567c9 git-gui: update Italian translation
Signed-off-by: Michele Ballabio <barra_cuda@katamail.com>
Signed-off-by: Shawn O. Pearce <spearce@spearce.org>
2010-01-28 07:18:29 -08:00
fe9c06b7c9 git-gui: Update Swedish translation (520t0f0u)
Signed-off-by: Peter Krefting <peter@softwolves.pp.se>
Signed-off-by: Shawn O. Pearce <spearce@spearce.org>
2010-01-28 07:17:47 -08:00
c80d7be5e1 git-gui: use themed tk widgets with Tk 8.5
This patch enables the use of themed Tk widgets with Tk 8.5 and above.
These make a significant difference on Windows in making the
application appear native. On Windows and MacOSX ttk defaults to the
native look as much as possible. On X11 the user may select a theme
using the TkTheme XRDB resource class by adding an line to the
.Xresources file. The set of installed theme names is available using
the Tk command 'ttk::themes'. The default on X11 is similar to the current
un-themed style - a kind of thin bordered motif look.

A new git config variable 'gui.usettk' may be set to disable this if
the user prefers the classic Tk look. Using Tk 8.4 will also avoid the
use of themed widgets as these are only available since 8.5.

Some support is included for Tk 8.6 features (themed spinbox and native
font chooser for MacOSX and Windows).

Signed-off-by: Pat Thoyts <patthoyts@users.sourceforge.net>
Signed-off-by: Shawn O. Pearce <spearce@spearce.org>
2010-01-27 17:13:52 -08:00
ab2d3b0d7d git-gui: Update German translation (12 new or changed strings).
Signed-off-by: Shawn O. Pearce <spearce@spearce.org>
2010-01-27 17:13:47 -08:00
60eb4f1bd0 git-gui: Update translation template
Signed-off-by: Shawn O. Pearce <spearce@spearce.org>
2010-01-26 15:47:45 -08:00
73b3446b82 git-gui: Remove unused icon file_parttick
This icon hasn't been used in git gui.  I think it dates back to
the original set of icons I took from Paul Mackerras' prototype
that I turned into git gui.

Signed-off-by: Shawn O. Pearce <spearce@spearce.org>
2010-01-25 07:33:41 -08:00
0602de48f7 git-gui: use different icon for new and modified files in the index
This allows to quickly differentiate between new and modified files
in the index without selecting the file and looking at the diff.

Signed-off-by: Peter Oberndorfer <kumbayo84@arcor.de>
Signed-off-by: Shawn O. Pearce <spearce@spearce.org>
2010-01-25 07:31:38 -08:00
a9fa11fe5b git-gui: set GIT_DIR and GIT_WORK_TREE after setup
Rather than juggling with the env var GIT_DIR around the invocation of
gitk, set it and GIT_WORK_TREE after finishing setup, ensuring that any
external tool works with the setup we're running with.

This also allows us to remove a couple of conditionals when running gitk
or git gui in a submodule, as we know that the variables are present and
have to be unset and reset before and after the invocation.

Signed-off-by: Giuseppe Bilotta <giuseppe.bilotta@gmail.com>
Signed-off-by: Shawn O. Pearce <spearce@spearce.org>
2010-01-23 16:02:16 -08:00
3748b03d92 git-gui: update shortcut tools to use _gitworktree
Signed-off-by: Giuseppe Bilotta <giuseppe.bilotta@gmail.com>
Signed-off-by: Shawn O. Pearce <spearce@spearce.org>
2010-01-23 15:15:55 -08:00
29e5573d1e git-gui: handle bare repos correctly
Refactor checking for a bare repository into its own proc, that relies
on git rev-parse --is-bare-repository if possible. For older versions of
git we fall back to a logic such that the repository is considered bare
if:
 * either the core.bare setting is true
 * or the worktree is not set and the directory name ends with .git
The error message for the case of an unhandled bare repository is also
updated to reflect the fact that the problem is not the funny name but
the bareness.

The new refactored proc is also used to disable the menu entry to
explore the working copy, and to skip changing to the worktree before
the gitk invocation.

Signed-off-by: Giuseppe Bilotta <giuseppe.bilotta@gmail.com>
Signed-off-by: Shawn O. Pearce <spearce@spearce.org>
2010-01-23 15:14:21 -08:00
21985a1136 git-gui: handle non-standard worktree locations
Don't rely on the git worktree being the updir of the gitdir, since it
might not be. Instead, define (and use) a new _gitworktree global
variable, setting it to $GIT_WORK_TREE if present, falling back to
core.worktree if defined, and finally to whatever we guess the correct
worktree is. Getting core.worktree requires the config from the alleged
git dir _gitdir to be loaded early.

Supporting non-standard worktree locations also breaks the git-gui
assumption (made when calling gitk) that the worktree was the dirname of
$_gitdir and that, by consequence, the git dir could be set to the tail
of $_gitdir once we changed to the worktree root directory. Therefore,
we need to export a GIT_DIR environment variable set to the full,
normalized path of $_gitdir instead. We also skip changing to the worktree
directory if it's empty (i.e. if we're working on a bare repository).

Signed-off-by: Giuseppe Bilotta <giuseppe.bilotta@gmail.com>
Signed-off-by: Shawn O. Pearce <spearce@spearce.org>
2010-01-23 15:14:21 -08:00
ff07c3b621 git-gui: Support applying a range of changes at once
Multiple lines can be selected in the diff viewer and applied all
at once, rather than selecting "Stage Line For Commit" on each
individual line.

Signed-off-by: Jeff Epler <jepler@unpythonic.net>
Signed-off-by: Shawn O. Pearce <spearce@spearce.org>
2010-01-23 15:14:15 -08:00
25476c63e7 git-gui: Add a special diff popup menu for submodules
To make it easier for users to deal with submodules, a special diff
popup menu has been added for submodules. The "Show Less Context"
and "Show More Context" entries have been removed, as they don't make
any sense for a submodule summary. Four new entries are added to the
top of the popup menu to gain access to more detailed information
about the changes in a submodule than the plain summary does offer.

These are:
- "Visualize These Changes In The Submodule"
  starts gitk showing the selected commit range

- "Visualize These Changes In The Submodule"
  starts gitk showing the whole submodule history of the current branch

- "Visualize All Branch History In The Submodule"
  starts gitk --all in the submodule

- "Start git gui In The Submodule"
  guess what :-)

Signed-off-by: Jens Lehmann <Jens.Lehmann@web.de>
Signed-off-by: Shawn O. Pearce <spearce@spearce.org>
2010-01-23 15:14:15 -08:00
a9ae14a1c5 git-gui: Use git diff --submodule when available
Doing so is much faster and gives the same output.
Here are some numbers:

  $ time git submodule summary
  real	0m0.219s
  user	0m0.050s
  sys	0m0.111s

  $ time git diff --submodule
  real	0m0.012s
  user	0m0.003s
  sys	0m0.009s

Signed-off-by: Jens Lehmann <Jens.Lehmann@web.de>
Signed-off-by: Shawn O. Pearce <spearce@spearce.org>
2010-01-23 15:14:15 -08:00
87cd09f43e git-gui: work from the .git dir
When git-gui is run from a .git dir, _gitdir would be set to "." by
rev-parse, something that confuses the worktree detection.

Fix by expanding the value of _gitdir to pwd in this special case.

Signed-off-by: Giuseppe Bilotta <giuseppe.bilotta@gmail.com>
Signed-off-by: Shawn O. Pearce <spearce@spearce.org>
2010-01-23 15:14:04 -08:00
390425bdef git-gui: Fix applying a line when all following lines are deletions
If a diff looked like:

 @@
  context
 -del1
 -del2

and you wanted to stage the deletion 'del1', the generated patch
wouldn't apply because it was missing the line 'del2' converted to
context, but this line was counted in the @@-line

Signed-off-by: Jeff Epler <jepler@unpythonic.net>
Signed-off-by: Shawn O. Pearce <spearce@spearce.org>
2010-01-23 15:00:09 -08:00
7ec2b69f1a git-gui: Correct file_states when unstaging partly staged entry
When unstaging a partly staged file or submodule, the file_states
list was not updated properly (unless unstaged linewise). Its
index_info part did not contain the former head_info as it should
have but kept its old value.

This seems not to have had any bad effects but diminishes the value
of the file_states list for future enhancements.

Signed-off-by: Jens Lehmann <Jens.Lehmann@web.de>
Signed-off-by: Shawn O. Pearce <spearce@spearce.org>
2010-01-23 14:46:13 -08:00
e27d106ec4 git-gui: Fix gitk for branch whose name matches local file
When trying to run gitk on a branch name whose name matches a local
file, it will toss an error saying that the name is ambiguous. Adding
a pair of dashes will make gitk parse the options to the left of
it as branch names. Since wish eats the first pair of dashes we
throw at it, we need to add a second one to ensure they get through.

Signed-off-by: Peter Krefting <peter@softwolves.pp.se>
Signed-off-by: Shawn O. Pearce <spearce@spearce.org>
2010-01-23 14:46:12 -08:00
3c6a287027 git-gui: Keep repo_config(gui.recentrepos) and .gitconfig in sync
When the number of recent repo's gets to ten there can be a
situation where an item is removed from the .gitconfig file via
a call to git config --unset, but the internal representation of
that file (repo_config(gui.recentrepo)) is not updated.  Then a
subsequent attempt to remove an item from the list fails because
git-gui attempts to call --unset on a value that has already
been removed.  This leads to duplicates in the .gitconfig file,
which then also cause errors if the git-gui tries to --unset them
(rather than using --unset-all. --unset-all is not used because it
is not expected that duplicates should ever be allowed to exist.)

When loading the list of recent repositories (proc _get_recentrepos)
if a repo in the list is not considered a valid git reposoitory
then we should go ahead and remove it so it doesn't take up a slot
in the list (since we limit to 10 items). This will prevent a bunch
of invalid entries in the list (which are not shown) from making
valid entries dissapear off the list even when there are less than
ten valid entries.

See: http://code.google.com/p/msysgit/issues/detail?id=362
Signed-off-by: Shawn O. Pearce <spearce@spearce.org>
2010-01-23 14:46:12 -08:00
ea888f84bd git-gui: handle really long error messages in updateindex.
As reported to msysGit (bug #340) it is possible to get some very
long error messages when updating the index. The use of a label to
display this prevents scrolling the output. This patch replaces the
label with a scrollable text widget configured to look like a label.

Signed-off-by: Pat Thoyts <patthoyts@users.sourceforge.net>
Signed-off-by: Shawn O. Pearce <spearce@spearce.org>
2010-01-23 14:22:28 -08:00
b677c66e29 git-gui: Add hotkeys for "Unstage from commit" and "Revert changes"
Signed-off-by: Vitaly _Vi Shukela <public_vi@tut.by>
Signed-off-by: Shawn O. Pearce <spearce@spearce.org>
2010-01-06 18:21:11 -08:00
54350a2bb4 git-gui: Makefile: consolidate .FORCE-* targets
Providing multiple targets to force a rebuild is unnecessary
complication.

Avoid using a name that could conflict with future special
targets in GNU make (a leading period followed by uppercase
letters).

Cc: Junio C Hamano <gitster@pobox.com>
Signed-off-by: Jonathan Nieder <jrnieder@gmail.com>
Signed-off-by: Shawn O. Pearce <spearce@spearce.org>
2010-01-06 18:20:01 -08:00
39 changed files with 3713 additions and 2954 deletions

View File

@ -1,7 +1,7 @@
#!/bin/sh #!/bin/sh
GVF=GIT-VERSION-FILE GVF=GIT-VERSION-FILE
DEF_VER=0.12.GITGUI DEF_VER=0.13.GITGUI
LF=' LF='
' '

View File

@ -7,7 +7,7 @@ all::
# TCL_PATH must be vaild for this to work. # TCL_PATH must be vaild for this to work.
# #
GIT-VERSION-FILE: .FORCE-GIT-VERSION-FILE GIT-VERSION-FILE: FORCE
@$(SHELL_PATH) ./GIT-VERSION-GEN @$(SHELL_PATH) ./GIT-VERSION-GEN
-include GIT-VERSION-FILE -include GIT-VERSION-FILE
@ -215,6 +215,7 @@ endif
$(GITGUI_MAIN): git-gui.sh GIT-VERSION-FILE GIT-GUI-VARS $(GITGUI_MAIN): git-gui.sh GIT-VERSION-FILE GIT-GUI-VARS
$(QUIET_GEN)rm -f $@ $@+ && \ $(QUIET_GEN)rm -f $@ $@+ && \
sed -e '1s|#!.*/sh|#!$(SHELL_PATH_SQ)|' \ sed -e '1s|#!.*/sh|#!$(SHELL_PATH_SQ)|' \
-e 's|@@SHELL_PATH@@|$(SHELL_PATH_SQ)|' \
-e '1,30s|^ argv0=$$0| argv0=$(GITGUI_SCRIPT)|' \ -e '1,30s|^ argv0=$$0| argv0=$(GITGUI_SCRIPT)|' \
-e '1,30s|^ exec wish | exec '\''$(TCLTK_PATH_SED)'\'' |' \ -e '1,30s|^ exec wish | exec '\''$(TCLTK_PATH_SED)'\'' |' \
-e 's/@@GITGUI_VERSION@@/$(GITGUI_VERSION)/g' \ -e 's/@@GITGUI_VERSION@@/$(GITGUI_VERSION)/g' \
@ -270,7 +271,7 @@ TRACK_VARS = \
GITGUI_MACOSXAPP=$(GITGUI_MACOSXAPP) \ GITGUI_MACOSXAPP=$(GITGUI_MACOSXAPP) \
#end TRACK_VARS #end TRACK_VARS
GIT-GUI-VARS: .FORCE-GIT-GUI-VARS GIT-GUI-VARS: FORCE
@VARS='$(TRACK_VARS)'; \ @VARS='$(TRACK_VARS)'; \
if test x"$$VARS" != x"`cat $@ 2>/dev/null`" ; then \ if test x"$$VARS" != x"`cat $@ 2>/dev/null`" ; then \
echo 1>&2 " * new locations or Tcl/Tk interpreter"; \ echo 1>&2 " * new locations or Tcl/Tk interpreter"; \
@ -340,5 +341,4 @@ ifdef GITGUI_WINDOWS_WRAPPER
endif endif
.PHONY: all install uninstall dist-version clean .PHONY: all install uninstall dist-version clean
.PHONY: .FORCE-GIT-VERSION-FILE .PHONY: FORCE
.PHONY: .FORCE-GIT-GUI-VARS

View File

@ -5,6 +5,8 @@ exec wish "$0" -- "$@"
# This is a trivial implementation of an SSH_ASKPASS handler. # This is a trivial implementation of an SSH_ASKPASS handler.
# Git-gui uses this script if none are already configured. # Git-gui uses this script if none are already configured.
package require Tk
set answer {} set answer {}
set yesno 0 set yesno 0
set rc 255 set rc 255
@ -30,16 +32,20 @@ if {!$yesno} {
frame .b frame .b
button .b.ok -text OK -command finish button .b.ok -text OK -command finish
button .b.cancel -text Cancel -command {destroy .} button .b.cancel -text Cancel -command cancel
pack .b.ok -side left -expand 1 pack .b.ok -side left -expand 1
pack .b.cancel -side right -expand 1 pack .b.cancel -side right -expand 1
pack .b -side bottom -fill x -padx 10 -pady 10 pack .b -side bottom -fill x -padx 10 -pady 10
bind . <Visibility> {focus -force .e} bind . <Visibility> {focus -force .e}
bind . <Key-Return> finish bind . <Key-Return> [list .b.ok invoke]
bind . <Key-Escape> {destroy .} bind . <Key-Escape> [list .b.cancel invoke]
bind . <Destroy> {exit $rc} bind . <Destroy> {set rc $rc}
proc cancel {} {
set ::rc 255
}
proc finish {} { proc finish {} {
if {$::yesno} { if {$::yesno} {
@ -50,10 +56,11 @@ proc finish {} {
} }
} }
set ::rc 0
puts $::answer puts $::answer
destroy . set ::rc 0
} }
wm title . "OpenSSH" wm title . "OpenSSH"
tk::PlaceWindow . tk::PlaceWindow .
vwait rc
exit $rc

View File

@ -10,8 +10,8 @@
exec wish "$argv0" -- "$@" exec wish "$argv0" -- "$@"
set appvers {@@GITGUI_VERSION@@} set appvers {@@GITGUI_VERSION@@}
set copyright [encoding convertfrom utf-8 { set copyright [string map [list (c) \u00a9] {
Copyright © 2006, 2007 Shawn Pearce, et. al. Copyright (c) 2006-2010 Shawn Pearce, et. al.
This program is free software; you can redistribute it and/or modify This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by it under the terms of the GNU General Public License as published by
@ -38,7 +38,7 @@ if {[catch {package require Tcl 8.4} err]
tk_messageBox \ tk_messageBox \
-icon error \ -icon error \
-type ok \ -type ok \
-title [mc "git-gui: fatal error"] \ -title "git-gui: fatal error" \
-message $err -message $err
exit 1 exit 1
} }
@ -121,11 +121,14 @@ unset oguimsg
set _appname {Git Gui} set _appname {Git Gui}
set _gitdir {} set _gitdir {}
set _gitworktree {}
set _isbare {}
set _gitexec {} set _gitexec {}
set _githtmldir {} set _githtmldir {}
set _reponame {} set _reponame {}
set _iscygwin {} set _iscygwin {}
set _search_path {} set _search_path {}
set _shellpath {@@SHELL_PATH@@}
set _trace [lsearch -exact $argv --trace] set _trace [lsearch -exact $argv --trace]
if {$_trace >= 0} { if {$_trace >= 0} {
@ -135,6 +138,18 @@ if {$_trace >= 0} {
set _trace 0 set _trace 0
} }
proc shellpath {} {
global _shellpath env
if {[string match @@* $_shellpath]} {
if {[info exists env(SHELL)]} {
return $env(SHELL)
} else {
return /bin/sh
}
}
return $_shellpath
}
proc appname {} { proc appname {} {
global _appname global _appname
return $_appname return $_appname
@ -267,6 +282,17 @@ proc is_config_true {name} {
} }
} }
proc is_config_false {name} {
global repo_config
if {[catch {set v $repo_config($name)}]} {
return 0
} elseif {$v eq {false} || $v eq {0} || $v eq {no}} {
return 1
} else {
return 0
}
}
proc get_config {name} { proc get_config {name} {
global repo_config global repo_config
if {[catch {set v $repo_config($name)}]} { if {[catch {set v $repo_config($name)}]} {
@ -276,6 +302,32 @@ proc get_config {name} {
} }
} }
proc is_bare {} {
global _isbare
global _gitdir
global _gitworktree
if {$_isbare eq {}} {
if {[catch {
set _bare [git rev-parse --is-bare-repository]
switch -- $_bare {
true { set _isbare 1 }
false { set _isbare 0}
default { throw }
}
}]} {
if {[is_config_true core.bare]
|| ($_gitworktree eq {}
&& [lindex [file split $_gitdir] end] ne {.git})} {
set _isbare 1
} else {
set _isbare 0
}
}
}
return $_isbare
}
###################################################################### ######################################################################
## ##
## handy utils ## handy utils
@ -295,6 +347,8 @@ proc _trace_exec {cmd} {
puts stderr $d puts stderr $d
} }
#'" fix poor old emacs font-lock mode
proc _git_cmd {name} { proc _git_cmd {name} {
global _git_cmd_path global _git_cmd_path
@ -388,6 +442,9 @@ proc _lappend_nice {cmd_var} {
if {![info exists _nice]} { if {![info exists _nice]} {
set _nice [_which nice] set _nice [_which nice]
if {[catch {exec $_nice git version}]} {
set _nice {}
}
} }
if {$_nice ne {}} { if {$_nice ne {}} {
lappend cmd $_nice lappend cmd $_nice
@ -606,6 +663,7 @@ proc rmsel_tag {text} {
return $text return $text
} }
wm withdraw .
set root_exists 0 set root_exists 0
bind . <Visibility> { bind . <Visibility> {
bind . <Visibility> {} bind . <Visibility> {}
@ -649,13 +707,18 @@ if {[is_Windows]} {
## config defaults ## config defaults
set cursor_ptr arrow set cursor_ptr arrow
font create font_diff -family Courier -size 10
font create font_ui font create font_ui
if {[lsearch -exact [font names] TkDefaultFont] != -1} {
eval [linsert [font actual TkDefaultFont] 0 font configure font_ui]
eval [linsert [font actual TkFixedFont] 0 font create font_diff]
} else {
font create font_diff -family Courier -size 10
catch { catch {
label .dummy label .dummy
eval font configure font_ui [font actual [.dummy cget -font]] eval font configure font_ui [font actual [.dummy cget -font]]
destroy .dummy destroy .dummy
} }
}
font create font_uiitalic font create font_uiitalic
font create font_uibold font create font_uibold
@ -669,6 +732,9 @@ foreach class {Button Checkbutton Entry Label
} }
if {![is_MacOSX]} { if {![is_MacOSX]} {
option add *Menu.font font_ui option add *Menu.font font_ui
option add *Entry.borderWidth 1 startupFile
option add *Entry.relief sunken startupFile
option add *RadioButton.anchor w startupFile
} }
unset class unset class
@ -721,6 +787,18 @@ proc apply_config {} {
font configure ${font}bold -weight bold font configure ${font}bold -weight bold
font configure ${font}italic -slant italic font configure ${font}italic -slant italic
} }
global use_ttk NS
set use_ttk 0
set NS {}
if {$repo_config(gui.usettk)} {
set use_ttk [package vsatisfies [package provide Tk] 8.5]
if {$use_ttk} {
set NS ttk
bind [winfo class .] <<ThemeChanged>> [list InitTheme]
pave_toplevel .
}
}
} }
set default_config(branch.autosetupmerge) true set default_config(branch.autosetupmerge) true
@ -734,6 +812,7 @@ set default_config(user.email) {}
set default_config(gui.encoding) [encoding system] set default_config(gui.encoding) [encoding system]
set default_config(gui.matchtrackingbranch) false set default_config(gui.matchtrackingbranch) false
set default_config(gui.textconv) true
set default_config(gui.pruneduringfetch) false set default_config(gui.pruneduringfetch) false
set default_config(gui.trustmtime) false set default_config(gui.trustmtime) false
set default_config(gui.fastcopyblame) false set default_config(gui.fastcopyblame) false
@ -747,6 +826,7 @@ set default_config(gui.fontui) [font configure font_ui]
set default_config(gui.fontdiff) [font configure font_diff] set default_config(gui.fontdiff) [font configure font_diff]
# TODO: this option should be added to the git-config documentation # TODO: this option should be added to the git-config documentation
set default_config(gui.maxfilesdisplayed) 5000 set default_config(gui.maxfilesdisplayed) 5000
set default_config(gui.usettk) 1
set font_descs { set font_descs {
{fontui font_ui {mc "Main Font"}} {fontui font_ui {mc "Main Font"}}
{fontdiff font_diff {mc "Diff/Console Font"}} {fontdiff font_diff {mc "Diff/Console Font"}}
@ -1074,6 +1154,8 @@ if {[catch {
set _prefix {} set _prefix {}
}] }]
&& [catch { && [catch {
# beware that from the .git dir this sets _gitdir to .
# and _prefix to the empty string
set _gitdir [git rev-parse --git-dir] set _gitdir [git rev-parse --git-dir]
set _prefix [git rev-parse --show-prefix] set _prefix [git rev-parse --show-prefix]
} err]} { } err]} {
@ -1082,6 +1164,14 @@ if {[catch {
choose_repository::pick choose_repository::pick
set picked 1 set picked 1
} }
# we expand the _gitdir when it's just a single dot (i.e. when we're being
# run from the .git dir itself) lest the routines to find the worktree
# get confused
if {$_gitdir eq "."} {
set _gitdir [pwd]
}
if {![file isdirectory $_gitdir] && [is_Cygwin]} { if {![file isdirectory $_gitdir] && [is_Cygwin]} {
catch {set _gitdir [exec cygpath --windows $_gitdir]} catch {set _gitdir [exec cygpath --windows $_gitdir]}
} }
@ -1090,25 +1180,44 @@ if {![file isdirectory $_gitdir]} {
error_popup [strcat [mc "Git directory not found:"] "\n\n$_gitdir"] error_popup [strcat [mc "Git directory not found:"] "\n\n$_gitdir"]
exit 1 exit 1
} }
# _gitdir exists, so try loading the config
load_config 0
apply_config
# try to set work tree from environment, falling back to core.worktree
if {[catch { set _gitworktree $env(GIT_WORK_TREE) }]} {
set _gitworktree [get_config core.worktree]
if {$_gitworktree eq ""} {
set _gitworktree [file dirname [file normalize $_gitdir]]
}
}
if {$_prefix ne {}} { if {$_prefix ne {}} {
if {$_gitworktree eq {}} {
regsub -all {[^/]+/} $_prefix ../ cdup regsub -all {[^/]+/} $_prefix ../ cdup
} else {
set cdup $_gitworktree
}
if {[catch {cd $cdup} err]} { if {[catch {cd $cdup} err]} {
catch {wm withdraw .} catch {wm withdraw .}
error_popup [strcat [mc "Cannot move to top of working directory:"] "\n\n$err"] error_popup [strcat [mc "Cannot move to top of working directory:"] "\n\n$err"]
exit 1 exit 1
} }
set _gitworktree [pwd]
unset cdup unset cdup
} elseif {![is_enabled bare]} { } elseif {![is_enabled bare]} {
if {[lindex [file split $_gitdir] end] ne {.git}} { if {[is_bare]} {
catch {wm withdraw .} catch {wm withdraw .}
error_popup [strcat [mc "Cannot use funny .git directory:"] "\n\n$_gitdir"] error_popup [strcat [mc "Cannot use bare repository:"] "\n\n$_gitdir"]
exit 1 exit 1
} }
if {[catch {cd [file dirname $_gitdir]} err]} { if {$_gitworktree eq {}} {
set _gitworktree [file dirname $_gitdir]
}
if {[catch {cd $_gitworktree} err]} {
catch {wm withdraw .} catch {wm withdraw .}
error_popup [strcat [mc "No working directory"] " [file dirname $_gitdir]:\n\n$err"] error_popup [strcat [mc "No working directory"] " $_gitworktree:\n\n$err"]
exit 1 exit 1
} }
set _gitworktree [pwd]
} }
set _reponame [file split [file normalize $_gitdir]] set _reponame [file split [file normalize $_gitdir]]
if {[lindex $_reponame end] eq {.git}} { if {[lindex $_reponame end] eq {.git}} {
@ -1117,6 +1226,9 @@ if {[lindex $_reponame end] eq {.git}} {
set _reponame [lindex $_reponame end] set _reponame [lindex $_reponame end]
} }
set env(GIT_DIR) $_gitdir
set env(GIT_WORK_TREE) $_gitworktree
###################################################################### ######################################################################
## ##
## global init ## global init
@ -1613,6 +1725,9 @@ proc merge_state {path new_state {head_info {}} {index_info {}}} {
} elseif {$s0 ne {_} && [string index $state 0] eq {_} } elseif {$s0 ne {_} && [string index $state 0] eq {_}
&& $head_info eq {}} { && $head_info eq {}} {
set head_info $index_info set head_info $index_info
} elseif {$s0 eq {_} && [string index $state 0] ne {_}} {
set index_info $head_info
set head_info {}
} }
set file_states($path) [list $s0$s1 $icon \ set file_states($path) [list $s0$s1 $icon \
@ -1795,15 +1910,6 @@ static unsigned char file_fulltick_bits[] = {
0x62, 0x10, 0x02, 0x10, 0xfe, 0x1f}; 0x62, 0x10, 0x02, 0x10, 0xfe, 0x1f};
} -maskdata $filemask } -maskdata $filemask
image create bitmap file_parttick -background white -foreground "#005050" -data {
#define parttick_width 14
#define parttick_height 15
static unsigned char parttick_bits[] = {
0xfe, 0x01, 0x02, 0x03, 0x7a, 0x05, 0x02, 0x09, 0x7a, 0x1f, 0x02, 0x10,
0x7a, 0x14, 0x02, 0x16, 0x02, 0x13, 0x8a, 0x11, 0xda, 0x10, 0x72, 0x10,
0x22, 0x10, 0x02, 0x10, 0xfe, 0x1f};
} -maskdata $filemask
image create bitmap file_question -background white -foreground black -data { image create bitmap file_question -background white -foreground black -data {
#define file_question_width 14 #define file_question_width 14
#define file_question_height 15 #define file_question_height 15
@ -1844,7 +1950,7 @@ set ui_index .vpane.files.index.list
set ui_workdir .vpane.files.workdir.list set ui_workdir .vpane.files.workdir.list
set all_icons(_$ui_index) file_plain set all_icons(_$ui_index) file_plain
set all_icons(A$ui_index) file_fulltick set all_icons(A$ui_index) file_plain
set all_icons(M$ui_index) file_fulltick set all_icons(M$ui_index) file_fulltick
set all_icons(D$ui_index) file_removed set all_icons(D$ui_index) file_removed
set all_icons(U$ui_index) file_merge set all_icons(U$ui_index) file_merge
@ -1920,7 +2026,10 @@ proc incr_font_size {font {amt 1}} {
set starting_gitk_msg [mc "Starting gitk... please wait..."] set starting_gitk_msg [mc "Starting gitk... please wait..."]
proc do_gitk {revs} { proc do_gitk {revs {is_submodule false}} {
global current_diff_path file_states current_diff_side ui_index
global _gitdir _gitworktree
# -- Always start gitk through whatever we were loaded with. This # -- Always start gitk through whatever we were loaded with. This
# lets us bypass using shell process on Windows systems. # lets us bypass using shell process on Windows systems.
# #
@ -1931,23 +2040,78 @@ proc do_gitk {revs} {
} else { } else {
global env global env
if {[info exists env(GIT_DIR)]} { set pwd [pwd]
set old_GIT_DIR $env(GIT_DIR)
} else { if {!$is_submodule} {
set old_GIT_DIR {} if {![is_bare]} {
cd $_gitworktree
} }
} else {
cd $current_diff_path
if {$revs eq {--}} {
set s $file_states($current_diff_path)
set old_sha1 {}
set new_sha1 {}
switch -glob -- [lindex $s 0] {
M_ { set old_sha1 [lindex [lindex $s 2] 1] }
_M { set old_sha1 [lindex [lindex $s 3] 1] }
MM {
if {$current_diff_side eq $ui_index} {
set old_sha1 [lindex [lindex $s 2] 1]
set new_sha1 [lindex [lindex $s 3] 1]
} else {
set old_sha1 [lindex [lindex $s 3] 1]
}
}
}
set revs $old_sha1...$new_sha1
}
# GIT_DIR and GIT_WORK_TREE for the submodule are not the ones
# we've been using for the main repository, so unset them.
# TODO we could make life easier (start up faster?) for gitk
# by setting these to the appropriate values to allow gitk
# to skip the heuristics to find their proper value
unset env(GIT_DIR)
unset env(GIT_WORK_TREE)
}
eval exec $cmd $revs "--" "--" &
set env(GIT_DIR) $_gitdir
set env(GIT_WORK_TREE) $_gitworktree
cd $pwd
ui_status $::starting_gitk_msg
after 10000 {
ui_ready $starting_gitk_msg
}
}
}
proc do_git_gui {} {
global current_diff_path
# -- Always start git gui through whatever we were loaded with. This
# lets us bypass using shell process on Windows systems.
#
set exe [list [_which git]]
if {$exe eq {}} {
error_popup [mc "Couldn't find git gui in PATH"]
} else {
global env
global _gitdir _gitworktree
# see note in do_gitk about unsetting these vars when
# running tools in a submodule
unset env(GIT_DIR)
unset env(GIT_WORK_TREE)
set pwd [pwd] set pwd [pwd]
cd [file dirname [gitdir]] cd $current_diff_path
set env(GIT_DIR) [file tail [gitdir]]
eval exec $cmd $revs & eval exec $exe gui &
if {$old_GIT_DIR eq {}} { set env(GIT_DIR) $_gitdir
unset env(GIT_DIR) set env(GIT_WORK_TREE) $_gitworktree
} else {
set env(GIT_DIR) $old_GIT_DIR
}
cd $pwd cd $pwd
ui_status $::starting_gitk_msg ui_status $::starting_gitk_msg
@ -1958,6 +2122,7 @@ proc do_gitk {revs} {
} }
proc do_explore {} { proc do_explore {} {
global _gitworktree
set explorer {} set explorer {}
if {[is_Cygwin] || [is_Windows]} { if {[is_Cygwin] || [is_Windows]} {
set explorer "explorer.exe" set explorer "explorer.exe"
@ -1967,7 +2132,7 @@ proc do_explore {} {
# freedesktop.org-conforming system is our best shot # freedesktop.org-conforming system is our best shot
set explorer "xdg-open" set explorer "xdg-open"
} }
eval exec $explorer [list [file nativename [file dirname [gitdir]]]] & eval exec $explorer [list [file nativename $_gitworktree]] &
} }
set is_quitting 0 set is_quitting 0
@ -1983,7 +2148,7 @@ proc do_quit {{rc {1}}} {
global ui_comm is_quitting repo_config commit_type global ui_comm is_quitting repo_config commit_type
global GITGUI_BCK_exists GITGUI_BCK_i global GITGUI_BCK_exists GITGUI_BCK_i
global ui_comm_spell global ui_comm_spell
global ret_code global ret_code use_ttk
if {$is_quitting} return if {$is_quitting} return
set is_quitting 1 set is_quitting 1
@ -2041,8 +2206,13 @@ proc do_quit {{rc {1}}} {
} }
set cfg_geometry [list] set cfg_geometry [list]
lappend cfg_geometry [wm geometry .] lappend cfg_geometry [wm geometry .]
if {$use_ttk} {
lappend cfg_geometry [.vpane sashpos 0]
lappend cfg_geometry [.vpane.files sashpos 0]
} else {
lappend cfg_geometry [lindex [.vpane sash coord 0] 0] lappend cfg_geometry [lindex [.vpane sash coord 0] 0]
lappend cfg_geometry [lindex [.vpane.files sash coord 0] 1] lappend cfg_geometry [lindex [.vpane.files sash coord 0] 1]
}
if {[catch {set rc_geometry $repo_config(gui.geometry)}]} { if {[catch {set rc_geometry $repo_config(gui.geometry)}]} {
set rc_geometry {} set rc_geometry {}
} }
@ -2331,8 +2501,6 @@ proc show_less_context {} {
## ##
## ui construction ## ui construction
load_config 0
apply_config
set ui_comm {} set ui_comm {}
# -- Menu Bar # -- Menu Bar
@ -2364,10 +2532,12 @@ if {[is_enabled multicommit] || [is_enabled singlecommit]} {
# #
menu .mbar.repository menu .mbar.repository
if {![is_bare]} {
.mbar.repository add command \ .mbar.repository add command \
-label [mc "Explore Working Copy"] \ -label [mc "Explore Working Copy"] \
-command {do_explore} -command {do_explore}
.mbar.repository add separator .mbar.repository add separator
}
.mbar.repository add command \ .mbar.repository add command \
-label [mc "Browse Current Branch's Files"] \ -label [mc "Browse Current Branch's Files"] \
@ -2543,12 +2713,14 @@ if {[is_enabled multicommit] || [is_enabled singlecommit]} {
[list .mbar.commit entryconf [.mbar.commit index last] -state] [list .mbar.commit entryconf [.mbar.commit index last] -state]
.mbar.commit add command -label [mc "Unstage From Commit"] \ .mbar.commit add command -label [mc "Unstage From Commit"] \
-command do_unstage_selection -command do_unstage_selection \
-accelerator $M1T-U
lappend disable_on_lock \ lappend disable_on_lock \
[list .mbar.commit entryconf [.mbar.commit index last] -state] [list .mbar.commit entryconf [.mbar.commit index last] -state]
.mbar.commit add command -label [mc "Revert Changes"] \ .mbar.commit add command -label [mc "Revert Changes"] \
-command do_revert_selection -command do_revert_selection \
-accelerator $M1T-J
lappend disable_on_lock \ lappend disable_on_lock \
[list .mbar.commit entryconf [.mbar.commit index last] -state] [list .mbar.commit entryconf [.mbar.commit index last] -state]
@ -2686,7 +2858,13 @@ bind all <$M1B-Key-W> {destroy [winfo toplevel %W]}
set subcommand_args {} set subcommand_args {}
proc usage {} { proc usage {} {
puts stderr "usage: $::argv0 $::subcommand $::subcommand_args" set s "usage: $::argv0 $::subcommand $::subcommand_args"
if {[tk windowingsystem] eq "win32"} {
wm withdraw .
tk_messageBox -icon info -title "Usage" -message $s
} else {
puts stderr $s
}
exit 1 exit 1
} }
@ -2763,6 +2941,7 @@ blame {
set current_branch $head set current_branch $head
} }
wm deiconify .
switch -- $subcommand { switch -- $subcommand {
browser { browser {
if {$jump_spec ne {}} usage if {$jump_spec ne {}} usage
@ -2778,7 +2957,12 @@ blame {
} }
blame { blame {
if {$head eq {} && ![file exists $path]} { if {$head eq {} && ![file exists $path]} {
puts stderr [mc "fatal: cannot stat path %s: No such file or directory" $path] catch {wm withdraw .}
tk_messageBox \
-icon error \
-type ok \
-title [mc "git-gui: fatal error"] \
-message [mc "fatal: cannot stat path %s: No such file or directory" $path]
exit 1 exit 1
} }
blame::new $head $path $jump_spec blame::new $head $path $jump_spec
@ -2807,14 +2991,13 @@ default {
# -- Branch Control # -- Branch Control
# #
frame .branch \ ${NS}::frame .branch
-borderwidth 1 \ if {!$use_ttk} {.branch configure -borderwidth 1 -relief sunken}
-relief sunken ${NS}::label .branch.l1 \
label .branch.l1 \
-text [mc "Current Branch:"] \ -text [mc "Current Branch:"] \
-anchor w \ -anchor w \
-justify left -justify left
label .branch.cb \ ${NS}::label .branch.cb \
-textvariable current_branch \ -textvariable current_branch \
-anchor w \ -anchor w \
-justify left -justify left
@ -2824,15 +3007,20 @@ pack .branch -side top -fill x
# -- Main Window Layout # -- Main Window Layout
# #
panedwindow .vpane -orient horizontal ${NS}::panedwindow .vpane -orient horizontal
panedwindow .vpane.files -orient vertical ${NS}::panedwindow .vpane.files -orient vertical
if {$use_ttk} {
.vpane add .vpane.files
} else {
.vpane add .vpane.files -sticky nsew -height 100 -width 200 .vpane add .vpane.files -sticky nsew -height 100 -width 200
}
pack .vpane -anchor n -side top -fill both -expand 1 pack .vpane -anchor n -side top -fill both -expand 1
# -- Index File List # -- Index File List
# #
frame .vpane.files.index -height 100 -width 200 ${NS}::frame .vpane.files.index -height 100 -width 200
label .vpane.files.index.title -text [mc "Staged Changes (Will Commit)"] \ tlabel .vpane.files.index.title \
-text [mc "Staged Changes (Will Commit)"] \
-background lightgreen -foreground black -background lightgreen -foreground black
text $ui_index -background white -foreground black \ text $ui_index -background white -foreground black \
-borderwidth 0 \ -borderwidth 0 \
@ -2842,8 +3030,8 @@ text $ui_index -background white -foreground black \
-xscrollcommand {.vpane.files.index.sx set} \ -xscrollcommand {.vpane.files.index.sx set} \
-yscrollcommand {.vpane.files.index.sy set} \ -yscrollcommand {.vpane.files.index.sy set} \
-state disabled -state disabled
scrollbar .vpane.files.index.sx -orient h -command [list $ui_index xview] ${NS}::scrollbar .vpane.files.index.sx -orient h -command [list $ui_index xview]
scrollbar .vpane.files.index.sy -orient v -command [list $ui_index yview] ${NS}::scrollbar .vpane.files.index.sy -orient v -command [list $ui_index yview]
pack .vpane.files.index.title -side top -fill x pack .vpane.files.index.title -side top -fill x
pack .vpane.files.index.sx -side bottom -fill x pack .vpane.files.index.sx -side bottom -fill x
pack .vpane.files.index.sy -side right -fill y pack .vpane.files.index.sy -side right -fill y
@ -2851,8 +3039,8 @@ pack $ui_index -side left -fill both -expand 1
# -- Working Directory File List # -- Working Directory File List
# #
frame .vpane.files.workdir -height 100 -width 200 ${NS}::frame .vpane.files.workdir -height 100 -width 200
label .vpane.files.workdir.title -text [mc "Unstaged Changes"] \ tlabel .vpane.files.workdir.title -text [mc "Unstaged Changes"] \
-background lightsalmon -foreground black -background lightsalmon -foreground black
text $ui_workdir -background white -foreground black \ text $ui_workdir -background white -foreground black \
-borderwidth 0 \ -borderwidth 0 \
@ -2862,15 +3050,19 @@ text $ui_workdir -background white -foreground black \
-xscrollcommand {.vpane.files.workdir.sx set} \ -xscrollcommand {.vpane.files.workdir.sx set} \
-yscrollcommand {.vpane.files.workdir.sy set} \ -yscrollcommand {.vpane.files.workdir.sy set} \
-state disabled -state disabled
scrollbar .vpane.files.workdir.sx -orient h -command [list $ui_workdir xview] ${NS}::scrollbar .vpane.files.workdir.sx -orient h -command [list $ui_workdir xview]
scrollbar .vpane.files.workdir.sy -orient v -command [list $ui_workdir yview] ${NS}::scrollbar .vpane.files.workdir.sy -orient v -command [list $ui_workdir yview]
pack .vpane.files.workdir.title -side top -fill x pack .vpane.files.workdir.title -side top -fill x
pack .vpane.files.workdir.sx -side bottom -fill x pack .vpane.files.workdir.sx -side bottom -fill x
pack .vpane.files.workdir.sy -side right -fill y pack .vpane.files.workdir.sy -side right -fill y
pack $ui_workdir -side left -fill both -expand 1 pack $ui_workdir -side left -fill both -expand 1
.vpane.files add .vpane.files.workdir -sticky nsew .vpane.files add .vpane.files.workdir
.vpane.files add .vpane.files.index -sticky nsew .vpane.files add .vpane.files.index
if {!$use_ttk} {
.vpane.files paneconfigure .vpane.files.workdir -sticky news
.vpane.files paneconfigure .vpane.files.index -sticky news
}
foreach i [list $ui_index $ui_workdir] { foreach i [list $ui_index $ui_workdir] {
rmsel_tag $i rmsel_tag $i
@ -2880,68 +3072,69 @@ unset i
# -- Diff and Commit Area # -- Diff and Commit Area
# #
frame .vpane.lower -height 300 -width 400 ${NS}::frame .vpane.lower -height 300 -width 400
frame .vpane.lower.commarea ${NS}::frame .vpane.lower.commarea
frame .vpane.lower.diff -relief sunken -borderwidth 1 ${NS}::frame .vpane.lower.diff -relief sunken -borderwidth 1
pack .vpane.lower.diff -fill both -expand 1 pack .vpane.lower.diff -fill both -expand 1
pack .vpane.lower.commarea -side bottom -fill x pack .vpane.lower.commarea -side bottom -fill x
.vpane add .vpane.lower -sticky nsew .vpane add .vpane.lower
if {!$use_ttk} {.vpane paneconfigure .vpane.lower -sticky nsew}
# -- Commit Area Buttons # -- Commit Area Buttons
# #
frame .vpane.lower.commarea.buttons ${NS}::frame .vpane.lower.commarea.buttons
label .vpane.lower.commarea.buttons.l -text {} \ ${NS}::label .vpane.lower.commarea.buttons.l -text {} \
-anchor w \ -anchor w \
-justify left -justify left
pack .vpane.lower.commarea.buttons.l -side top -fill x pack .vpane.lower.commarea.buttons.l -side top -fill x
pack .vpane.lower.commarea.buttons -side left -fill y pack .vpane.lower.commarea.buttons -side left -fill y
button .vpane.lower.commarea.buttons.rescan -text [mc Rescan] \ ${NS}::button .vpane.lower.commarea.buttons.rescan -text [mc Rescan] \
-command ui_do_rescan -command ui_do_rescan
pack .vpane.lower.commarea.buttons.rescan -side top -fill x pack .vpane.lower.commarea.buttons.rescan -side top -fill x
lappend disable_on_lock \ lappend disable_on_lock \
{.vpane.lower.commarea.buttons.rescan conf -state} {.vpane.lower.commarea.buttons.rescan conf -state}
button .vpane.lower.commarea.buttons.incall -text [mc "Stage Changed"] \ ${NS}::button .vpane.lower.commarea.buttons.incall -text [mc "Stage Changed"] \
-command do_add_all -command do_add_all
pack .vpane.lower.commarea.buttons.incall -side top -fill x pack .vpane.lower.commarea.buttons.incall -side top -fill x
lappend disable_on_lock \ lappend disable_on_lock \
{.vpane.lower.commarea.buttons.incall conf -state} {.vpane.lower.commarea.buttons.incall conf -state}
if {![is_enabled nocommitmsg]} { if {![is_enabled nocommitmsg]} {
button .vpane.lower.commarea.buttons.signoff -text [mc "Sign Off"] \ ${NS}::button .vpane.lower.commarea.buttons.signoff -text [mc "Sign Off"] \
-command do_signoff -command do_signoff
pack .vpane.lower.commarea.buttons.signoff -side top -fill x pack .vpane.lower.commarea.buttons.signoff -side top -fill x
} }
button .vpane.lower.commarea.buttons.commit -text [commit_btn_caption] \ ${NS}::button .vpane.lower.commarea.buttons.commit -text [commit_btn_caption] \
-command do_commit -command do_commit
pack .vpane.lower.commarea.buttons.commit -side top -fill x pack .vpane.lower.commarea.buttons.commit -side top -fill x
lappend disable_on_lock \ lappend disable_on_lock \
{.vpane.lower.commarea.buttons.commit conf -state} {.vpane.lower.commarea.buttons.commit conf -state}
if {![is_enabled nocommit]} { if {![is_enabled nocommit]} {
button .vpane.lower.commarea.buttons.push -text [mc Push] \ ${NS}::button .vpane.lower.commarea.buttons.push -text [mc Push] \
-command do_push_anywhere -command do_push_anywhere
pack .vpane.lower.commarea.buttons.push -side top -fill x pack .vpane.lower.commarea.buttons.push -side top -fill x
} }
# -- Commit Message Buffer # -- Commit Message Buffer
# #
frame .vpane.lower.commarea.buffer ${NS}::frame .vpane.lower.commarea.buffer
frame .vpane.lower.commarea.buffer.header ${NS}::frame .vpane.lower.commarea.buffer.header
set ui_comm .vpane.lower.commarea.buffer.t set ui_comm .vpane.lower.commarea.buffer.t
set ui_coml .vpane.lower.commarea.buffer.header.l set ui_coml .vpane.lower.commarea.buffer.header.l
if {![is_enabled nocommit]} { if {![is_enabled nocommit]} {
radiobutton .vpane.lower.commarea.buffer.header.new \ ${NS}::radiobutton .vpane.lower.commarea.buffer.header.new \
-text [mc "New Commit"] \ -text [mc "New Commit"] \
-command do_select_commit_type \ -command do_select_commit_type \
-variable selected_commit_type \ -variable selected_commit_type \
-value new -value new
lappend disable_on_lock \ lappend disable_on_lock \
[list .vpane.lower.commarea.buffer.header.new conf -state] [list .vpane.lower.commarea.buffer.header.new conf -state]
radiobutton .vpane.lower.commarea.buffer.header.amend \ ${NS}::radiobutton .vpane.lower.commarea.buffer.header.amend \
-text [mc "Amend Last Commit"] \ -text [mc "Amend Last Commit"] \
-command do_select_commit_type \ -command do_select_commit_type \
-variable selected_commit_type \ -variable selected_commit_type \
@ -2950,7 +3143,7 @@ if {![is_enabled nocommit]} {
[list .vpane.lower.commarea.buffer.header.amend conf -state] [list .vpane.lower.commarea.buffer.header.amend conf -state]
} }
label $ui_coml \ ${NS}::label $ui_coml \
-anchor w \ -anchor w \
-justify left -justify left
proc trace_commit_type {varname args} { proc trace_commit_type {varname args} {
@ -2982,7 +3175,7 @@ text $ui_comm -background white -foreground black \
-width $repo_config(gui.commitmsgwidth) -height 9 -wrap none \ -width $repo_config(gui.commitmsgwidth) -height 9 -wrap none \
-font font_diff \ -font font_diff \
-yscrollcommand {.vpane.lower.commarea.buffer.sby set} -yscrollcommand {.vpane.lower.commarea.buffer.sby set}
scrollbar .vpane.lower.commarea.buffer.sby \ ${NS}::scrollbar .vpane.lower.commarea.buffer.sby \
-command [list $ui_comm yview] -command [list $ui_comm yview]
pack .vpane.lower.commarea.buffer.header -side top -fill x pack .vpane.lower.commarea.buffer.header -side top -fill x
pack .vpane.lower.commarea.buffer.sby -side right -fill y pack .vpane.lower.commarea.buffer.sby -side right -fill y
@ -3048,19 +3241,19 @@ proc trace_current_diff_path {varname args} {
} }
trace add variable current_diff_path write trace_current_diff_path trace add variable current_diff_path write trace_current_diff_path
frame .vpane.lower.diff.header -background gold gold_frame .vpane.lower.diff.header
label .vpane.lower.diff.header.status \ tlabel .vpane.lower.diff.header.status \
-background gold \ -background gold \
-foreground black \ -foreground black \
-width $max_status_desc \ -width $max_status_desc \
-anchor w \ -anchor w \
-justify left -justify left
label .vpane.lower.diff.header.file \ tlabel .vpane.lower.diff.header.file \
-background gold \ -background gold \
-foreground black \ -foreground black \
-anchor w \ -anchor w \
-justify left -justify left
label .vpane.lower.diff.header.path \ tlabel .vpane.lower.diff.header.path \
-background gold \ -background gold \
-foreground black \ -foreground black \
-anchor w \ -anchor w \
@ -3084,7 +3277,7 @@ bind_button3 .vpane.lower.diff.header.path "tk_popup $ctxm %X %Y"
# -- Diff Body # -- Diff Body
# #
frame .vpane.lower.diff.body ${NS}::frame .vpane.lower.diff.body
set ui_diff .vpane.lower.diff.body.t set ui_diff .vpane.lower.diff.body.t
text $ui_diff -background white -foreground black \ text $ui_diff -background white -foreground black \
-borderwidth 0 \ -borderwidth 0 \
@ -3093,9 +3286,9 @@ text $ui_diff -background white -foreground black \
-xscrollcommand {.vpane.lower.diff.body.sbx set} \ -xscrollcommand {.vpane.lower.diff.body.sbx set} \
-yscrollcommand {.vpane.lower.diff.body.sby set} \ -yscrollcommand {.vpane.lower.diff.body.sby set} \
-state disabled -state disabled
scrollbar .vpane.lower.diff.body.sbx -orient horizontal \ ${NS}::scrollbar .vpane.lower.diff.body.sbx -orient horizontal \
-command [list $ui_diff xview] -command [list $ui_diff xview]
scrollbar .vpane.lower.diff.body.sby -orient vertical \ ${NS}::scrollbar .vpane.lower.diff.body.sby -orient vertical \
-command [list $ui_diff yview] -command [list $ui_diff yview]
pack .vpane.lower.diff.body.sbx -side bottom -fill x pack .vpane.lower.diff.body.sbx -side bottom -fill x
pack .vpane.lower.diff.body.sby -side right -fill y pack .vpane.lower.diff.body.sby -side right -fill y
@ -3139,15 +3332,6 @@ $ui_diff tag raise sel
# #
proc create_common_diff_popup {ctxm} { proc create_common_diff_popup {ctxm} {
$ctxm add command \
-label [mc "Show Less Context"] \
-command show_less_context
lappend diff_actions [list $ctxm entryconf [$ctxm index last] -state]
$ctxm add command \
-label [mc "Show More Context"] \
-command show_more_context
lappend diff_actions [list $ctxm entryconf [$ctxm index last] -state]
$ctxm add separator
$ctxm add command \ $ctxm add command \
-label [mc Refresh] \ -label [mc Refresh] \
-command reshow_diff -command reshow_diff
@ -3199,10 +3383,19 @@ set ui_diff_applyhunk [$ctxm index last]
lappend diff_actions [list $ctxm entryconf $ui_diff_applyhunk -state] lappend diff_actions [list $ctxm entryconf $ui_diff_applyhunk -state]
$ctxm add command \ $ctxm add command \
-label [mc "Apply/Reverse Line"] \ -label [mc "Apply/Reverse Line"] \
-command {apply_line $cursorX $cursorY; do_rescan} -command {apply_range_or_line $cursorX $cursorY; do_rescan}
set ui_diff_applyline [$ctxm index last] set ui_diff_applyline [$ctxm index last]
lappend diff_actions [list $ctxm entryconf $ui_diff_applyline -state] lappend diff_actions [list $ctxm entryconf $ui_diff_applyline -state]
$ctxm add separator $ctxm add separator
$ctxm add command \
-label [mc "Show Less Context"] \
-command show_less_context
lappend diff_actions [list $ctxm entryconf [$ctxm index last] -state]
$ctxm add command \
-label [mc "Show More Context"] \
-command show_more_context
lappend diff_actions [list $ctxm entryconf [$ctxm index last] -state]
$ctxm add separator
create_common_diff_popup $ctxm create_common_diff_popup $ctxm
set ctxmmg .vpane.lower.diff.body.ctxmmg set ctxmmg .vpane.lower.diff.body.ctxmmg
@ -3225,9 +3418,53 @@ $ctxmmg add command \
-command {merge_resolve_one 1} -command {merge_resolve_one 1}
lappend diff_actions [list $ctxmmg entryconf [$ctxmmg index last] -state] lappend diff_actions [list $ctxmmg entryconf [$ctxmmg index last] -state]
$ctxmmg add separator $ctxmmg add separator
$ctxmmg add command \
-label [mc "Show Less Context"] \
-command show_less_context
lappend diff_actions [list $ctxmmg entryconf [$ctxmmg index last] -state]
$ctxmmg add command \
-label [mc "Show More Context"] \
-command show_more_context
lappend diff_actions [list $ctxmmg entryconf [$ctxmmg index last] -state]
$ctxmmg add separator
create_common_diff_popup $ctxmmg create_common_diff_popup $ctxmmg
proc popup_diff_menu {ctxm ctxmmg x y X Y} { set ctxmsm .vpane.lower.diff.body.ctxmsm
menu $ctxmsm -tearoff 0
$ctxmsm add command \
-label [mc "Visualize These Changes In The Submodule"] \
-command {do_gitk -- true}
lappend diff_actions [list $ctxmsm entryconf [$ctxmsm index last] -state]
$ctxmsm add command \
-label [mc "Visualize Current Branch History In The Submodule"] \
-command {do_gitk {} true}
lappend diff_actions [list $ctxmsm entryconf [$ctxmsm index last] -state]
$ctxmsm add command \
-label [mc "Visualize All Branch History In The Submodule"] \
-command {do_gitk --all true}
lappend diff_actions [list $ctxmsm entryconf [$ctxmsm index last] -state]
$ctxmsm add separator
$ctxmsm add command \
-label [mc "Start git gui In The Submodule"] \
-command {do_git_gui}
lappend diff_actions [list $ctxmsm entryconf [$ctxmsm index last] -state]
$ctxmsm add separator
create_common_diff_popup $ctxmsm
proc has_textconv {path} {
if {[is_config_false gui.textconv]} {
return 0
}
set filter [gitattr $path diff set]
set textconv [get_config [join [list diff $filter textconv] .]]
if {$filter ne {set} && $textconv ne {}} {
return 1
} else {
return 0
}
}
proc popup_diff_menu {ctxm ctxmmg ctxmsm x y X Y} {
global current_diff_path file_states global current_diff_path file_states
set ::cursorX $x set ::cursorX $x
set ::cursorY $y set ::cursorY $y
@ -3238,20 +3475,32 @@ proc popup_diff_menu {ctxm ctxmmg x y X Y} {
} }
if {[string first {U} $state] >= 0} { if {[string first {U} $state] >= 0} {
tk_popup $ctxmmg $X $Y tk_popup $ctxmmg $X $Y
} elseif {$::is_submodule_diff} {
tk_popup $ctxmsm $X $Y
} else { } else {
set has_range [expr {[$::ui_diff tag nextrange sel 0.0] != {}}]
if {$::ui_index eq $::current_diff_side} { if {$::ui_index eq $::current_diff_side} {
set l [mc "Unstage Hunk From Commit"] set l [mc "Unstage Hunk From Commit"]
if {$has_range} {
set t [mc "Unstage Lines From Commit"]
} else {
set t [mc "Unstage Line From Commit"] set t [mc "Unstage Line From Commit"]
}
} else { } else {
set l [mc "Stage Hunk For Commit"] set l [mc "Stage Hunk For Commit"]
if {$has_range} {
set t [mc "Stage Lines For Commit"]
} else {
set t [mc "Stage Line For Commit"] set t [mc "Stage Line For Commit"]
} }
if {$::is_3way_diff || $::is_submodule_diff }
if {$::is_3way_diff
|| $current_diff_path eq {} || $current_diff_path eq {}
|| {__} eq $state || {__} eq $state
|| {_O} eq $state || {_O} eq $state
|| {_T} eq $state || {_T} eq $state
|| {T_} eq $state} { || {T_} eq $state
|| [has_textconv $current_diff_path]} {
set s disabled set s disabled
} else { } else {
set s normal set s normal
@ -3261,7 +3510,7 @@ proc popup_diff_menu {ctxm ctxmmg x y X Y} {
tk_popup $ctxm $X $Y tk_popup $ctxm $X $Y
} }
} }
bind_button3 $ui_diff [list popup_diff_menu $ctxm $ctxmmg %x %y %X %Y] bind_button3 $ui_diff [list popup_diff_menu $ctxm $ctxmmg $ctxmsm %x %y %X %Y]
# -- Status Bar # -- Status Bar
# #
@ -3271,24 +3520,44 @@ $main_status show [mc "Initializing..."]
# -- Load geometry # -- Load geometry
# #
catch { proc on_ttk_pane_mapped {w pane pos} {
bind $w <Map> {}
after 0 [list after idle [list $w sashpos $pane $pos]]
}
proc on_tk_pane_mapped {w pane x y} {
bind $w <Map> {}
after 0 [list after idle [list $w sash place $pane $x $y]]
}
proc on_application_mapped {} {
global repo_config use_ttk
bind . <Map> {}
set gm $repo_config(gui.geometry) set gm $repo_config(gui.geometry)
wm geometry . [lindex $gm 0] if {$use_ttk} {
.vpane sash place 0 \ bind .vpane <Map> \
[list on_ttk_pane_mapped %W 0 [lindex $gm 1]]
bind .vpane.files <Map> \
[list on_ttk_pane_mapped %W 0 [lindex $gm 2]]
} else {
bind .vpane <Map> \
[list on_tk_pane_mapped %W 0 \
[lindex $gm 1] \ [lindex $gm 1] \
[lindex [.vpane sash coord 0] 1] [lindex [.vpane sash coord 0] 1]]
.vpane.files sash place 0 \ bind .vpane.files <Map> \
[list on_tk_pane_mapped %W 0 \
[lindex [.vpane.files sash coord 0] 0] \ [lindex [.vpane.files sash coord 0] 0] \
[lindex $gm 2] [lindex $gm 2]]
unset gm }
wm geometry . [lindex $gm 0]
}
if {[info exists repo_config(gui.geometry)]} {
bind . <Map> [list on_application_mapped]
wm geometry . [lindex $repo_config(gui.geometry) 0]
} }
# -- Load window state # -- Load window state
# #
catch { if {[info exists repo_config(gui.wmstate)]} {
set gws $repo_config(gui.wmstate) catch {wm state . $repo_config(gui.wmstate)}
wm state . $gws
unset gws
} }
# -- Key Bindings # -- Key Bindings
@ -3296,6 +3565,10 @@ unset gws
bind $ui_comm <$M1B-Key-Return> {do_commit;break} bind $ui_comm <$M1B-Key-Return> {do_commit;break}
bind $ui_comm <$M1B-Key-t> {do_add_selection;break} bind $ui_comm <$M1B-Key-t> {do_add_selection;break}
bind $ui_comm <$M1B-Key-T> {do_add_selection;break} bind $ui_comm <$M1B-Key-T> {do_add_selection;break}
bind $ui_comm <$M1B-Key-u> {do_unstage_selection;break}
bind $ui_comm <$M1B-Key-U> {do_unstage_selection;break}
bind $ui_comm <$M1B-Key-j> {do_revert_selection;break}
bind $ui_comm <$M1B-Key-J> {do_revert_selection;break}
bind $ui_comm <$M1B-Key-i> {do_add_all;break} bind $ui_comm <$M1B-Key-i> {do_add_all;break}
bind $ui_comm <$M1B-Key-I> {do_add_all;break} bind $ui_comm <$M1B-Key-I> {do_add_all;break}
bind $ui_comm <$M1B-Key-x> {tk_textCut %W;break} bind $ui_comm <$M1B-Key-x> {tk_textCut %W;break}
@ -3352,6 +3625,8 @@ bind . <$M1B-Key-s> do_signoff
bind . <$M1B-Key-S> do_signoff bind . <$M1B-Key-S> do_signoff
bind . <$M1B-Key-t> do_add_selection bind . <$M1B-Key-t> do_add_selection
bind . <$M1B-Key-T> do_add_selection bind . <$M1B-Key-T> do_add_selection
bind . <$M1B-Key-j> do_revert_selection
bind . <$M1B-Key-J> do_revert_selection
bind . <$M1B-Key-i> do_add_all bind . <$M1B-Key-i> do_add_all
bind . <$M1B-Key-I> do_add_all bind . <$M1B-Key-I> do_add_all
bind . <$M1B-Key-minus> {show_less_context;break} bind . <$M1B-Key-minus> {show_less_context;break}
@ -3370,7 +3645,7 @@ unset i
set file_lists($ui_index) [list] set file_lists($ui_index) [list]
set file_lists($ui_workdir) [list] set file_lists($ui_workdir) [list]
wm title . "[appname] ([reponame]) [file normalize [file dirname [gitdir]]]" wm title . "[appname] ([reponame]) [file normalize $_gitworktree]"
focus -force $ui_comm focus -force $ui_comm
# -- Warn the user about environmental problems. Cygwin's Tcl # -- Warn the user about environmental problems. Cygwin's Tcl
@ -3543,3 +3818,9 @@ if {[is_enabled retcode]} {
if {$picked && [is_config_true gui.autoexplore]} { if {$picked && [is_config_true gui.autoexplore]} {
do_explore do_explore
} }
# Local variables:
# mode: tcl
# indent-tabs-mode: t
# tab-width: 4
# End:

View File

@ -4,31 +4,26 @@
proc do_about {} { proc do_about {} {
global appvers copyright oguilib global appvers copyright oguilib
global tcl_patchLevel tk_patchLevel global tcl_patchLevel tk_patchLevel
global ui_comm_spell global ui_comm_spell NS use_ttk
set w .about_dialog set w .about_dialog
toplevel $w Dialog $w
wm geometry $w "+[winfo rootx .]+[winfo rooty .]" wm geometry $w "+[winfo rootx .]+[winfo rooty .]"
pack [git_logo $w.git_logo] -side left -fill y -padx 10 -pady 10 pack [git_logo $w.git_logo] -side left -fill y -padx 10 -pady 10
label $w.header -text [mc "About %s" [appname]] \ ${NS}::label $w.header -text [mc "About %s" [appname]] \
-font font_uibold -font font_uibold -anchor center
pack $w.header -side top -fill x pack $w.header -side top -fill x
frame $w.buttons ${NS}::frame $w.buttons
button $w.buttons.close -text {Close} \ ${NS}::button $w.buttons.close -text {Close} \
-default active \ -default active \
-command [list destroy $w] -command [list destroy $w]
pack $w.buttons.close -side right pack $w.buttons.close -side right
pack $w.buttons -side bottom -fill x -pady 10 -padx 10 pack $w.buttons -side bottom -fill x -pady 10 -padx 10
label $w.desc \ paddedlabel $w.desc \
-text "[mc "git-gui - a graphical user interface for Git."]\n$copyright" \ -text "[mc "git-gui - a graphical user interface for Git."]\n$copyright"
-padx 5 -pady 5 \
-justify left \
-anchor w \
-borderwidth 1 \
-relief solid
pack $w.desc -side top -fill x -padx 5 -pady 5 pack $w.desc -side top -fill x -padx 5 -pady 5
set v {} set v {}
@ -52,22 +47,10 @@ proc do_about {} {
append d "git exec dir: [gitexec]\n" append d "git exec dir: [gitexec]\n"
append d "git-gui lib: $oguilib" append d "git-gui lib: $oguilib"
label $w.vers \ paddedlabel $w.vers -text $v
-text $v \
-padx 5 -pady 5 \
-justify left \
-anchor w \
-borderwidth 1 \
-relief solid
pack $w.vers -side top -fill x -padx 5 -pady 5 pack $w.vers -side top -fill x -padx 5 -pady 5
label $w.dirs \ paddedlabel $w.dirs -text $d
-text $d \
-padx 5 -pady 5 \
-justify left \
-anchor w \
-borderwidth 1 \
-relief solid
pack $w.dirs -side top -fill x -padx 5 -pady 5 pack $w.dirs -side top -fill x -padx 5 -pady 5
menu $w.ctxm -tearoff 0 menu $w.ctxm -tearoff 0

View File

@ -61,7 +61,7 @@ field tooltip_timer {} ; # Current timer event for our tooltip
field tooltip_commit {} ; # Commit(s) in tooltip field tooltip_commit {} ; # Commit(s) in tooltip
constructor new {i_commit i_path i_jump} { constructor new {i_commit i_path i_jump} {
global cursor_ptr M1B M1T have_tk85 global cursor_ptr M1B M1T have_tk85 use_ttk NS
variable active_color variable active_color
variable group_colors variable group_colors
@ -73,15 +73,15 @@ constructor new {i_commit i_path i_jump} {
set font_w [font measure font_diff "0"] set font_w [font measure font_diff "0"]
frame $w.header -background gold gold_frame $w.header
label $w.header.commit_l \ tlabel $w.header.commit_l \
-text [mc "Commit:"] \ -text [mc "Commit:"] \
-background gold \ -background gold \
-foreground black \ -foreground black \
-anchor w \ -anchor w \
-justify left -justify left
set w_back $w.header.commit_b set w_back $w.header.commit_b
label $w_back \ tlabel $w_back \
-image ::blame::img_back_arrow \ -image ::blame::img_back_arrow \
-borderwidth 0 \ -borderwidth 0 \
-relief flat \ -relief flat \
@ -94,20 +94,20 @@ constructor new {i_commit i_path i_jump} {
[cb _history_menu] [cb _history_menu]
} }
" "
label $w.header.commit \ tlabel $w.header.commit \
-textvariable @commit \ -textvariable @commit \
-background gold \ -background gold \
-foreground black \ -foreground black \
-anchor w \ -anchor w \
-justify left -justify left
label $w.header.path_l \ tlabel $w.header.path_l \
-text [mc "File:"] \ -text [mc "File:"] \
-background gold \ -background gold \
-foreground black \ -foreground black \
-anchor w \ -anchor w \
-justify left -justify left
set w_path $w.header.path set w_path $w.header.path
label $w_path \ tlabel $w_path \
-background gold \ -background gold \
-foreground black \ -foreground black \
-anchor w \ -anchor w \
@ -209,10 +209,10 @@ constructor new {i_commit i_path i_jump} {
set w_columns [list $w_amov $w_asim $w_line $w_file] set w_columns [list $w_amov $w_asim $w_line $w_file]
scrollbar $w.file_pane.out.sbx \ ${NS}::scrollbar $w.file_pane.out.sbx \
-orient h \ -orient h \
-command [list $w_file xview] -command [list $w_file xview]
scrollbar $w.file_pane.out.sby \ ${NS}::scrollbar $w.file_pane.out.sby \
-orient v \ -orient v \
-command [list scrollbar2many $w_columns yview] -command [list scrollbar2many $w_columns yview]
eval grid $w_columns $w.file_pane.out.sby -sticky nsew eval grid $w_columns $w.file_pane.out.sby -sticky nsew
@ -254,10 +254,10 @@ constructor new {i_commit i_path i_jump} {
-background $active_color \ -background $active_color \
-font font_ui -font font_ui
$w_cviewer tag raise sel $w_cviewer tag raise sel
scrollbar $w.file_pane.cm.sbx \ ${NS}::scrollbar $w.file_pane.cm.sbx \
-orient h \ -orient h \
-command [list $w_cviewer xview] -command [list $w_cviewer xview]
scrollbar $w.file_pane.cm.sby \ ${NS}::scrollbar $w.file_pane.cm.sby \
-orient v \ -orient v \
-command [list $w_cviewer yview] -command [list $w_cviewer yview]
pack $w.file_pane.cm.sby -side right -fill y pack $w.file_pane.cm.sby -side right -fill y
@ -449,12 +449,36 @@ method _load {jump} {
$status show [mc "Reading %s..." "$commit:[escape_path $path]"] $status show [mc "Reading %s..." "$commit:[escape_path $path]"]
$w_path conf -text [escape_path $path] $w_path conf -text [escape_path $path]
set do_textconv 0
if {![is_config_false gui.textconv] && [git-version >= 1.7.2]} {
set filter [gitattr $path diff set]
set textconv [get_config [join [list diff $filter textconv] .]]
if {$filter ne {set} && $textconv ne {}} {
set do_textconv 1
}
}
if {$commit eq {}} { if {$commit eq {}} {
if {$do_textconv ne 0} {
# Run textconv with sh -c "..." to allow it to
# contain command + arguments. On windows, just
# call the filter command.
if {![file executable [shellpath]]} {
set fd [open |[linsert $textconv end $path] r]
} else {
set fd [open |[list [shellpath] -c "$textconv \"\$0\"" $path] r]
}
} else {
set fd [open $path r] set fd [open $path r]
}
fconfigure $fd -eofchar {} fconfigure $fd -eofchar {}
} else {
if {$do_textconv ne 0} {
set fd [git_read cat-file --textconv "$commit:$path"]
} else { } else {
set fd [git_read cat-file blob "$commit:$path"] set fd [git_read cat-file blob "$commit:$path"]
} }
}
fconfigure $fd \ fconfigure $fd \
-blocking 0 \ -blocking 0 \
-translation lf \ -translation lf \

View File

@ -10,21 +10,24 @@ field opt_fetch 1; # refetch tracking branch if used?
field opt_detach 0; # force a detached head case? field opt_detach 0; # force a detached head case?
constructor dialog {} { constructor dialog {} {
make_toplevel top w global use_ttk NS
make_dialog top w
wm withdraw $w
wm title $top [append "[appname] ([reponame]): " [mc "Checkout Branch"]] wm title $top [append "[appname] ([reponame]): " [mc "Checkout Branch"]]
if {$top ne {.}} { if {$top ne {.}} {
wm geometry $top "+[winfo rootx .]+[winfo rooty .]" wm geometry $top "+[winfo rootx .]+[winfo rooty .]"
} }
label $w.header -text [mc "Checkout Branch"] -font font_uibold ${NS}::label $w.header -text [mc "Checkout Branch"] \
-font font_uibold -anchor center
pack $w.header -side top -fill x pack $w.header -side top -fill x
frame $w.buttons ${NS}::frame $w.buttons
button $w.buttons.create -text [mc Checkout] \ ${NS}::button $w.buttons.create -text [mc Checkout] \
-default active \ -default active \
-command [cb _checkout] -command [cb _checkout]
pack $w.buttons.create -side right pack $w.buttons.create -side right
button $w.buttons.cancel -text [mc Cancel] \ ${NS}::button $w.buttons.cancel -text [mc Cancel] \
-command [list destroy $w] -command [list destroy $w]
pack $w.buttons.cancel -side right -padx 5 pack $w.buttons.cancel -side right -padx 5
pack $w.buttons -side bottom -fill x -pady 10 -padx 10 pack $w.buttons -side bottom -fill x -pady 10 -padx 10
@ -33,14 +36,14 @@ constructor dialog {} {
$w_rev bind_listbox <Double-Button-1> [cb _checkout] $w_rev bind_listbox <Double-Button-1> [cb _checkout]
pack $w.rev -anchor nw -fill both -expand 1 -pady 5 -padx 5 pack $w.rev -anchor nw -fill both -expand 1 -pady 5 -padx 5
labelframe $w.options -text [mc Options] ${NS}::labelframe $w.options -text [mc Options]
checkbutton $w.options.fetch \ ${NS}::checkbutton $w.options.fetch \
-text [mc "Fetch Tracking Branch"] \ -text [mc "Fetch Tracking Branch"] \
-variable @opt_fetch -variable @opt_fetch
pack $w.options.fetch -anchor nw pack $w.options.fetch -anchor nw
checkbutton $w.options.detach \ ${NS}::checkbutton $w.options.detach \
-text [mc "Detach From Local Branch"] \ -text [mc "Detach From Local Branch"] \
-variable @opt_detach -variable @opt_detach
pack $w.options.detach -anchor nw pack $w.options.detach -anchor nw
@ -50,6 +53,7 @@ constructor dialog {} {
bind $w <Visibility> [cb _visible] bind $w <Visibility> [cb _visible]
bind $w <Key-Escape> [list destroy $w] bind $w <Key-Escape> [list destroy $w]
bind $w <Key-Return> [cb _checkout]\;break bind $w <Key-Return> [cb _checkout]\;break
wm deiconify $w
tkwait window $w tkwait window $w
} }

View File

@ -16,48 +16,48 @@ field opt_fetch 1; # refetch tracking branch if used?
field reset_ok 0; # did the user agree to reset? field reset_ok 0; # did the user agree to reset?
constructor dialog {} { constructor dialog {} {
global repo_config global repo_config use_ttk NS
make_toplevel top w make_dialog top w
wm withdraw $w
wm title $top [append "[appname] ([reponame]): " [mc "Create Branch"]] wm title $top [append "[appname] ([reponame]): " [mc "Create Branch"]]
if {$top ne {.}} { if {$top ne {.}} {
wm geometry $top "+[winfo rootx .]+[winfo rooty .]" wm geometry $top "+[winfo rootx .]+[winfo rooty .]"
} }
label $w.header -text [mc "Create New Branch"] -font font_uibold ${NS}::label $w.header -text [mc "Create New Branch"] \
-font font_uibold -anchor center
pack $w.header -side top -fill x pack $w.header -side top -fill x
frame $w.buttons ${NS}::frame $w.buttons
button $w.buttons.create -text [mc Create] \ ${NS}::button $w.buttons.create -text [mc Create] \
-default active \ -default active \
-command [cb _create] -command [cb _create]
pack $w.buttons.create -side right pack $w.buttons.create -side right
button $w.buttons.cancel -text [mc Cancel] \ ${NS}::button $w.buttons.cancel -text [mc Cancel] \
-command [list destroy $w] -command [list destroy $w]
pack $w.buttons.cancel -side right -padx 5 pack $w.buttons.cancel -side right -padx 5
pack $w.buttons -side bottom -fill x -pady 10 -padx 10 pack $w.buttons -side bottom -fill x -pady 10 -padx 10
labelframe $w.desc -text [mc "Branch Name"] ${NS}::labelframe $w.desc -text [mc "Branch Name"]
radiobutton $w.desc.name_r \ ${NS}::radiobutton $w.desc.name_r \
-anchor w \
-text [mc "Name:"] \ -text [mc "Name:"] \
-value user \ -value user \
-variable @name_type -variable @name_type
if {!$use_ttk} {$w.desc.name_r configure -anchor w}
set w_name $w.desc.name_t set w_name $w.desc.name_t
entry $w_name \ ${NS}::entry $w_name \
-borderwidth 1 \
-relief sunken \
-width 40 \ -width 40 \
-textvariable @name \ -textvariable @name \
-validate key \ -validate key \
-validatecommand [cb _validate %d %S] -validatecommand [cb _validate %d %S]
grid $w.desc.name_r $w_name -sticky we -padx {0 5} grid $w.desc.name_r $w_name -sticky we -padx {0 5}
radiobutton $w.desc.match_r \ ${NS}::radiobutton $w.desc.match_r \
-anchor w \
-text [mc "Match Tracking Branch Name"] \ -text [mc "Match Tracking Branch Name"] \
-value match \ -value match \
-variable @name_type -variable @name_type
if {!$use_ttk} {$w.desc.match_r configure -anchor w}
grid $w.desc.match_r -sticky we -padx {0 5} -columnspan 2 grid $w.desc.match_r -sticky we -padx {0 5} -columnspan 2
grid columnconfigure $w.desc 1 -weight 1 grid columnconfigure $w.desc 1 -weight 1
@ -66,34 +66,34 @@ constructor dialog {} {
set w_rev [::choose_rev::new $w.rev [mc "Starting Revision"]] set w_rev [::choose_rev::new $w.rev [mc "Starting Revision"]]
pack $w.rev -anchor nw -fill both -expand 1 -pady 5 -padx 5 pack $w.rev -anchor nw -fill both -expand 1 -pady 5 -padx 5
labelframe $w.options -text [mc Options] ${NS}::labelframe $w.options -text [mc Options]
frame $w.options.merge ${NS}::frame $w.options.merge
label $w.options.merge.l -text [mc "Update Existing Branch:"] ${NS}::label $w.options.merge.l -text [mc "Update Existing Branch:"]
pack $w.options.merge.l -side left pack $w.options.merge.l -side left
radiobutton $w.options.merge.no \ ${NS}::radiobutton $w.options.merge.no \
-text [mc No] \ -text [mc No] \
-value none \ -value none \
-variable @opt_merge -variable @opt_merge
pack $w.options.merge.no -side left pack $w.options.merge.no -side left
radiobutton $w.options.merge.ff \ ${NS}::radiobutton $w.options.merge.ff \
-text [mc "Fast Forward Only"] \ -text [mc "Fast Forward Only"] \
-value ff \ -value ff \
-variable @opt_merge -variable @opt_merge
pack $w.options.merge.ff -side left pack $w.options.merge.ff -side left
radiobutton $w.options.merge.reset \ ${NS}::radiobutton $w.options.merge.reset \
-text [mc Reset] \ -text [mc Reset] \
-value reset \ -value reset \
-variable @opt_merge -variable @opt_merge
pack $w.options.merge.reset -side left pack $w.options.merge.reset -side left
pack $w.options.merge -anchor nw pack $w.options.merge -anchor nw
checkbutton $w.options.fetch \ ${NS}::checkbutton $w.options.fetch \
-text [mc "Fetch Tracking Branch"] \ -text [mc "Fetch Tracking Branch"] \
-variable @opt_fetch -variable @opt_fetch
pack $w.options.fetch -anchor nw pack $w.options.fetch -anchor nw
checkbutton $w.options.checkout \ ${NS}::checkbutton $w.options.checkout \
-text [mc "Checkout After Creation"] \ -text [mc "Checkout After Creation"] \
-variable @opt_checkout -variable @opt_checkout
pack $w.options.checkout -anchor nw pack $w.options.checkout -anchor nw
@ -109,6 +109,7 @@ constructor dialog {} {
bind $w <Visibility> [cb _visible] bind $w <Visibility> [cb _visible]
bind $w <Key-Escape> [list destroy $w] bind $w <Key-Escape> [list destroy $w]
bind $w <Key-Return> [cb _create]\;break bind $w <Key-Return> [cb _create]\;break
wm deiconify $w
tkwait window $w tkwait window $w
} }

View File

@ -9,41 +9,40 @@ field w_check ; # revision picker for merge test
field w_delete ; # delete button field w_delete ; # delete button
constructor dialog {} { constructor dialog {} {
global current_branch global current_branch use_ttk NS
make_toplevel top w make_dialog top w
wm withdraw $w
wm title $top [append "[appname] ([reponame]): " [mc "Delete Branch"]] wm title $top [append "[appname] ([reponame]): " [mc "Delete Branch"]]
if {$top ne {.}} { if {$top ne {.}} {
wm geometry $top "+[winfo rootx .]+[winfo rooty .]" wm geometry $top "+[winfo rootx .]+[winfo rooty .]"
} }
label $w.header -text [mc "Delete Local Branch"] -font font_uibold ${NS}::label $w.header -text [mc "Delete Local Branch"] \
-font font_uibold -anchor center
pack $w.header -side top -fill x pack $w.header -side top -fill x
frame $w.buttons ${NS}::frame $w.buttons
set w_delete $w.buttons.delete set w_delete $w.buttons.delete
button $w_delete \ ${NS}::button $w_delete \
-text [mc Delete] \ -text [mc Delete] \
-default active \ -default active \
-state disabled \ -state disabled \
-command [cb _delete] -command [cb _delete]
pack $w_delete -side right pack $w_delete -side right
button $w.buttons.cancel \ ${NS}::button $w.buttons.cancel \
-text [mc Cancel] \ -text [mc Cancel] \
-command [list destroy $w] -command [list destroy $w]
pack $w.buttons.cancel -side right -padx 5 pack $w.buttons.cancel -side right -padx 5
pack $w.buttons -side bottom -fill x -pady 10 -padx 10 pack $w.buttons -side bottom -fill x -pady 10 -padx 10
labelframe $w.list -text [mc "Local Branches"] ${NS}::labelframe $w.list -text [mc "Local Branches"]
set w_heads $w.list.l set w_heads $w.list.l
listbox $w_heads \ slistbox $w_heads \
-height 10 \ -height 10 \
-width 70 \ -width 70 \
-selectmode extended \ -selectmode extended \
-exportselection false \ -exportselection false
-yscrollcommand [list $w.list.sby set]
scrollbar $w.list.sby -command [list $w.list.l yview]
pack $w.list.sby -side right -fill y
pack $w.list.l -side left -fill both -expand 1 pack $w.list.l -side left -fill both -expand 1
pack $w.list -fill both -expand 1 -pady 5 -padx 5 pack $w.list -fill both -expand 1 -pady 5 -padx 5
@ -67,6 +66,7 @@ constructor dialog {} {
" "
bind $w <Key-Escape> [list destroy $w] bind $w <Key-Escape> [list destroy $w]
bind $w <Key-Return> [cb _delete]\;break bind $w <Key-Return> [cb _delete]\;break
wm deiconify $w
tkwait window $w tkwait window $w
} }

View File

@ -8,9 +8,10 @@ field oldname
field newname field newname
constructor dialog {} { constructor dialog {} {
global current_branch global current_branch use_ttk NS
make_toplevel top w make_dialog top w
wm withdraw $w
wm title $top [append "[appname] ([reponame]): " [mc "Rename Branch"]] wm title $top [append "[appname] ([reponame]): " [mc "Rename Branch"]]
if {$top ne {.}} { if {$top ne {.}} {
wm geometry $top "+[winfo rootx .]+[winfo rooty .]" wm geometry $top "+[winfo rootx .]+[winfo rooty .]"
@ -19,27 +20,31 @@ constructor dialog {} {
set oldname $current_branch set oldname $current_branch
set newname [get_config gui.newbranchtemplate] set newname [get_config gui.newbranchtemplate]
label $w.header -text [mc "Rename Branch"] -font font_uibold ${NS}::label $w.header -text [mc "Rename Branch"]\
-font font_uibold -anchor center
pack $w.header -side top -fill x pack $w.header -side top -fill x
frame $w.buttons ${NS}::frame $w.buttons
button $w.buttons.rename -text [mc Rename] \ ${NS}::button $w.buttons.rename -text [mc Rename] \
-default active \ -default active \
-command [cb _rename] -command [cb _rename]
pack $w.buttons.rename -side right pack $w.buttons.rename -side right
button $w.buttons.cancel -text [mc Cancel] \ ${NS}::button $w.buttons.cancel -text [mc Cancel] \
-command [list destroy $w] -command [list destroy $w]
pack $w.buttons.cancel -side right -padx 5 pack $w.buttons.cancel -side right -padx 5
pack $w.buttons -side bottom -fill x -pady 10 -padx 10 pack $w.buttons -side bottom -fill x -pady 10 -padx 10
frame $w.rename ${NS}::frame $w.rename
label $w.rename.oldname_l -text [mc "Branch:"] ${NS}::label $w.rename.oldname_l -text [mc "Branch:"]
if {$use_ttk} {
ttk::combobox $w.rename.oldname_m -textvariable @oldname \
-values [load_all_heads] -state readonly
} else {
eval tk_optionMenu $w.rename.oldname_m @oldname [load_all_heads] eval tk_optionMenu $w.rename.oldname_m @oldname [load_all_heads]
}
label $w.rename.newname_l -text [mc "New Name:"] ${NS}::label $w.rename.newname_l -text [mc "New Name:"]
entry $w.rename.newname_t \ ${NS}::entry $w.rename.newname_t \
-borderwidth 1 \
-relief sunken \
-width 40 \ -width 40 \
-textvariable @newname \ -textvariable @newname \
-validate key \ -validate key \
@ -60,6 +65,7 @@ constructor dialog {} {
$w.rename.newname_t icursor end $w.rename.newname_t icursor end
focus $w.rename.newname_t focus $w.rename.newname_t
" "
wm deiconify $w
tkwait window $w tkwait window $w
} }

View File

@ -21,23 +21,23 @@ field browser_busy 1
field ls_buf {}; # Buffered record output from ls-tree field ls_buf {}; # Buffered record output from ls-tree
constructor new {commit {path {}}} { constructor new {commit {path {}}} {
global cursor_ptr M1B global cursor_ptr M1B use_ttk NS
make_toplevel top w make_dialog top w
wm withdraw $top
wm title $top [append "[appname] ([reponame]): " [mc "File Browser"]] wm title $top [append "[appname] ([reponame]): " [mc "File Browser"]]
set browser_commit $commit set browser_commit $commit
set browser_path $browser_commit:$path set browser_path $browser_commit:$path
label $w.path \ ${NS}::label $w.path \
-textvariable @browser_path \ -textvariable @browser_path \
-anchor w \ -anchor w \
-justify left \ -justify left \
-borderwidth 1 \
-relief sunken \
-font font_uibold -font font_uibold
if {!$use_ttk} { $w.path configure -borderwidth 1 -relief sunken}
pack $w.path -anchor w -side top -fill x pack $w.path -anchor w -side top -fill x
frame $w.list ${NS}::frame $w.list
set w_list $w.list.l set w_list $w.list.l
text $w_list -background white -foreground black \ text $w_list -background white -foreground black \
-borderwidth 0 \ -borderwidth 0 \
@ -49,19 +49,18 @@ constructor new {commit {path {}}} {
-xscrollcommand [list $w.list.sbx set] \ -xscrollcommand [list $w.list.sbx set] \
-yscrollcommand [list $w.list.sby set] -yscrollcommand [list $w.list.sby set]
rmsel_tag $w_list rmsel_tag $w_list
scrollbar $w.list.sbx -orient h -command [list $w_list xview] ${NS}::scrollbar $w.list.sbx -orient h -command [list $w_list xview]
scrollbar $w.list.sby -orient v -command [list $w_list yview] ${NS}::scrollbar $w.list.sby -orient v -command [list $w_list yview]
pack $w.list.sbx -side bottom -fill x pack $w.list.sbx -side bottom -fill x
pack $w.list.sby -side right -fill y pack $w.list.sby -side right -fill y
pack $w_list -side left -fill both -expand 1 pack $w_list -side left -fill both -expand 1
pack $w.list -side top -fill both -expand 1 pack $w.list -side top -fill both -expand 1
label $w.status \ ${NS}::label $w.status \
-textvariable @browser_status \ -textvariable @browser_status \
-anchor w \ -anchor w \
-justify left \ -justify left
-borderwidth 1 \ if {!$use_ttk} { $w.status configure -borderwidth 1 -relief sunken}
-relief sunken
pack $w.status -anchor w -side bottom -fill x pack $w.status -anchor w -side bottom -fill x
bind $w_list <Button-1> "[cb _click 0 @%x,%y];break" bind $w_list <Button-1> "[cb _click 0 @%x,%y];break"
@ -78,6 +77,7 @@ constructor new {commit {path {}}} {
bind $w_list <Right> break bind $w_list <Right> break
bind $w_list <Visibility> [list focus $w_list] bind $w_list <Visibility> [list focus $w_list]
wm deiconify $top
set w $w_list set w $w_list
if {$path ne {}} { if {$path ne {}} {
_ls $this $browser_commit:$path $path _ls $this $browser_commit:$path $path
@ -263,23 +263,27 @@ field w ; # widget path
field w_rev ; # mega-widget to pick the initial revision field w_rev ; # mega-widget to pick the initial revision
constructor dialog {} { constructor dialog {} {
make_toplevel top w global use_ttk NS
make_dialog top w
wm withdraw $top
wm title $top [append "[appname] ([reponame]): " [mc "Browse Branch Files"]] wm title $top [append "[appname] ([reponame]): " [mc "Browse Branch Files"]]
if {$top ne {.}} { if {$top ne {.}} {
wm geometry $top "+[winfo rootx .]+[winfo rooty .]" wm geometry $top "+[winfo rootx .]+[winfo rooty .]"
wm transient $top .
} }
label $w.header \ ${NS}::label $w.header \
-text [mc "Browse Branch Files"] \ -text [mc "Browse Branch Files"] \
-font font_uibold -font font_uibold \
-anchor center
pack $w.header -side top -fill x pack $w.header -side top -fill x
frame $w.buttons ${NS}::frame $w.buttons
button $w.buttons.browse -text [mc Browse] \ ${NS}::button $w.buttons.browse -text [mc Browse] \
-default active \ -default active \
-command [cb _open] -command [cb _open]
pack $w.buttons.browse -side right pack $w.buttons.browse -side right
button $w.buttons.cancel -text [mc Cancel] \ ${NS}::button $w.buttons.cancel -text [mc Cancel] \
-command [list destroy $w] -command [list destroy $w]
pack $w.buttons.cancel -side right -padx 5 pack $w.buttons.cancel -side right -padx 5
pack $w.buttons -side bottom -fill x -pady 10 -padx 10 pack $w.buttons -side bottom -fill x -pady 10 -padx 10
@ -291,6 +295,7 @@ constructor dialog {} {
bind $w <Visibility> [cb _visible] bind $w <Visibility> [cb _visible]
bind $w <Key-Escape> [list destroy $w] bind $w <Key-Escape> [list destroy $w]
bind $w <Key-Return> [cb _open]\;break bind $w <Key-Return> [cb _open]\;break
wm deiconify $top
tkwait window $w tkwait window $w
} }

View File

@ -17,6 +17,7 @@ variable all_families [list] ; # All fonts known to Tk
constructor pick {path title a_family a_size} { constructor pick {path title a_family a_size} {
variable all_families variable all_families
global use_ttk NS
set v_family $a_family set v_family $a_family
set v_size $a_size set v_size $a_size
@ -27,29 +28,30 @@ constructor pick {path title a_family a_size} {
set f_family $pv_family set f_family $pv_family
set f_size $pv_size set f_size $pv_size
make_toplevel top w make_dialog top w
wm withdraw $top
wm title $top "[appname] ([reponame]): $title" wm title $top "[appname] ([reponame]): $title"
wm geometry $top "+[winfo rootx $path]+[winfo rooty $path]" wm geometry $top "+[winfo rootx $path]+[winfo rooty $path]"
label $w.header -text $title -font font_uibold ${NS}::label $w.header -text $title -font font_uibold -anchor center
pack $w.header -side top -fill x pack $w.header -side top -fill x
frame $w.buttons ${NS}::frame $w.buttons
button $w.buttons.select \ ${NS}::button $w.buttons.select \
-text [mc Select] \ -text [mc Select] \
-default active \ -default active \
-command [cb _select] -command [cb _select]
button $w.buttons.cancel \ ${NS}::button $w.buttons.cancel \
-text [mc Cancel] \ -text [mc Cancel] \
-command [list destroy $w] -command [list destroy $w]
pack $w.buttons.select -side right pack $w.buttons.select -side right
pack $w.buttons.cancel -side right -padx 5 pack $w.buttons.cancel -side right -padx 5
pack $w.buttons -side bottom -fill x -pady 10 -padx 10 pack $w.buttons -side bottom -fill x -pady 10 -padx 10
frame $w.inner ${NS}::frame $w.inner
frame $w.inner.family ${NS}::frame $w.inner.family
label $w.inner.family.l \ ${NS}::label $w.inner.family.l \
-text [mc "Font Family"] \ -text [mc "Font Family"] \
-anchor w -anchor w
set w_family $w.inner.family.v set w_family $w.inner.family.v
@ -64,16 +66,16 @@ constructor pick {path title a_family a_size} {
-height 10 \ -height 10 \
-yscrollcommand [list $w.inner.family.sby set] -yscrollcommand [list $w.inner.family.sby set]
rmsel_tag $w_family rmsel_tag $w_family
scrollbar $w.inner.family.sby -command [list $w_family yview] ${NS}::scrollbar $w.inner.family.sby -command [list $w_family yview]
pack $w.inner.family.l -side top -fill x pack $w.inner.family.l -side top -fill x
pack $w.inner.family.sby -side right -fill y pack $w.inner.family.sby -side right -fill y
pack $w_family -fill both -expand 1 pack $w_family -fill both -expand 1
frame $w.inner.size ${NS}::frame $w.inner.size
label $w.inner.size.l \ ${NS}::label $w.inner.size.l \
-text [mc "Font Size"] \ -text [mc "Font Size"] \
-anchor w -anchor w
spinbox $w.inner.size.v \ tspinbox $w.inner.size.v \
-textvariable @f_size \ -textvariable @f_size \
-from 2 -to 80 -increment 1 \ -from 2 -to 80 -increment 1 \
-width 3 -width 3
@ -86,8 +88,8 @@ constructor pick {path title a_family a_size} {
grid columnconfigure $w.inner 0 -weight 1 grid columnconfigure $w.inner 0 -weight 1
pack $w.inner -fill both -expand 1 -padx 5 -pady 5 pack $w.inner -fill both -expand 1 -padx 5 -pady 5
frame $w.example ${NS}::frame $w.example
label $w.example.l \ ${NS}::label $w.example.l \
-text [mc "Font Example"] \ -text [mc "Font Example"] \
-anchor w -anchor w
set w_example $w.example.t set w_example $w.example.t
@ -129,6 +131,7 @@ constructor pick {path title a_family a_size} {
grab $w grab $w
focus $w focus $w
" "
wm deiconify $w
tkwait window $w tkwait window $w
} }

View File

@ -22,9 +22,9 @@ field readtree_err ; # Error output from read-tree (if any)
field sorted_recent ; # recent repositories (sorted) field sorted_recent ; # recent repositories (sorted)
constructor pick {} { constructor pick {} {
global M1T M1B global M1T M1B use_ttk NS
make_toplevel top w make_dialog top w
wm title $top [mc "Git Gui"] wm title $top [mc "Git Gui"]
if {$top eq {.}} { if {$top eq {.}} {
@ -71,11 +71,11 @@ constructor pick {} {
set w_body $w.body set w_body $w.body
set opts $w_body.options set opts $w_body.options
frame $w_body ${NS}::frame $w_body
text $opts \ text $opts \
-cursor $::cursor_ptr \ -cursor $::cursor_ptr \
-relief flat \ -relief flat \
-background [$w_body cget -background] \ -background [get_bg_color $w_body] \
-wrap none \ -wrap none \
-spacing1 5 \ -spacing1 5 \
-width 50 \ -width 50 \
@ -100,12 +100,17 @@ constructor pick {} {
$opts insert end [mc "Clone Existing Repository"] link_clone $opts insert end [mc "Clone Existing Repository"] link_clone
$opts insert end "\n" $opts insert end "\n"
if {$m_repo ne {}} { if {$m_repo ne {}} {
if {[tk windowingsystem] eq "win32"} {
set key L
} else {
set key C
}
$m_repo add command \ $m_repo add command \
-command [cb _next clone] \ -command [cb _next clone] \
-accelerator $M1T-C \ -accelerator $M1T-$key \
-label [mc "Clone..."] -label [mc "Clone..."]
bind $top <$M1B-c> [cb _next clone] bind $top <$M1B-[string tolower $key]> [cb _next clone]
bind $top <$M1B-C> [cb _next clone] bind $top <$M1B-[string toupper $key]> [cb _next clone]
} }
$opts tag conf link_open -foreground blue -underline 1 $opts tag conf link_open -foreground blue -underline 1
@ -132,15 +137,15 @@ constructor pick {} {
-label [mc "Recent Repositories"] -label [mc "Recent Repositories"]
} }
label $w_body.space ${NS}::label $w_body.space
label $w_body.recentlabel \ ${NS}::label $w_body.recentlabel \
-anchor w \ -anchor w \
-text [mc "Open Recent Repository:"] -text [mc "Open Recent Repository:"]
set w_recentlist $w_body.recentlist set w_recentlist $w_body.recentlist
text $w_recentlist \ text $w_recentlist \
-cursor $::cursor_ptr \ -cursor $::cursor_ptr \
-relief flat \ -relief flat \
-background [$w_body.recentlabel cget -background] \ -background [get_bg_color $w_body.recentlabel] \
-wrap none \ -wrap none \
-width 50 \ -width 50 \
-height 10 -height 10
@ -176,10 +181,10 @@ constructor pick {} {
} }
pack $w_body -fill x -padx 10 -pady 10 pack $w_body -fill x -padx 10 -pady 10
frame $w.buttons ${NS}::frame $w.buttons
set w_next $w.buttons.next set w_next $w.buttons.next
set w_quit $w.buttons.quit set w_quit $w.buttons.quit
button $w_quit \ ${NS}::button $w_quit \
-text [mc "Quit"] \ -text [mc "Quit"] \
-command exit -command exit
pack $w_quit -side right -padx 5 pack $w_quit -side right -padx 5
@ -203,6 +208,7 @@ constructor pick {} {
wm deiconify $top wm deiconify $top
tkwait variable @done tkwait variable @done
grab release $top
if {$top eq {.}} { if {$top eq {.}} {
eval destroy [winfo children $top] eval destroy [winfo children $top]
} }
@ -235,6 +241,8 @@ proc _get_recentrepos {} {
foreach p [get_config gui.recentrepo] { foreach p [get_config gui.recentrepo] {
if {[_is_git [file join $p .git]]} { if {[_is_git [file join $p .git]]} {
lappend recent $p lappend recent $p
} else {
_unset_recentrepo $p
} }
} }
return [lsort $recent] return [lsort $recent]
@ -243,6 +251,7 @@ proc _get_recentrepos {} {
proc _unset_recentrepo {p} { proc _unset_recentrepo {p} {
regsub -all -- {([()\[\]{}\.^$+*?\\])} $p {\\\1} p regsub -all -- {([()\[\]{}\.^$+*?\\])} $p {\\\1} p
git config --global --unset gui.recentrepo "^$p\$" git config --global --unset gui.recentrepo "^$p\$"
load_config 1
} }
proc _append_recentrepos {path} { proc _append_recentrepos {path} {
@ -261,6 +270,7 @@ proc _append_recentrepos {path} {
lappend recent $path lappend recent $path
git config --global --add gui.recentrepo $path git config --global --add gui.recentrepo $path
load_config 1
while {[llength $recent] > 10} { while {[llength $recent] > 10} {
_unset_recentrepo [lindex $recent 0] _unset_recentrepo [lindex $recent 0]
@ -280,9 +290,10 @@ method _open_recent_path {p} {
} }
method _next {action} { method _next {action} {
global NS
destroy $w_body destroy $w_body
if {![winfo exists $w_next]} { if {![winfo exists $w_next]} {
button $w_next -default active ${NS}::button $w_next -default active
pack $w_next -side right -padx 5 -before $w_quit pack $w_next -side right -padx 5 -before $w_quit
} }
_do_$action $this _do_$action $this
@ -371,26 +382,25 @@ proc _objdir {path} {
## Create New Repository ## Create New Repository
method _do_new {} { method _do_new {} {
global use_ttk NS
$w_next conf \ $w_next conf \
-state disabled \ -state disabled \
-command [cb _do_new2] \ -command [cb _do_new2] \
-text [mc "Create"] -text [mc "Create"]
frame $w_body ${NS}::frame $w_body
label $w_body.h \ ${NS}::label $w_body.h \
-font font_uibold \ -font font_uibold -anchor center \
-text [mc "Create New Repository"] -text [mc "Create New Repository"]
pack $w_body.h -side top -fill x -pady 10 pack $w_body.h -side top -fill x -pady 10
pack $w_body -fill x -padx 10 pack $w_body -fill x -padx 10
frame $w_body.where ${NS}::frame $w_body.where
label $w_body.where.l -text [mc "Directory:"] ${NS}::label $w_body.where.l -text [mc "Directory:"]
entry $w_body.where.t \ ${NS}::entry $w_body.where.t \
-textvariable @local_path \ -textvariable @local_path \
-borderwidth 1 \
-relief sunken \
-width 50 -width 50
button $w_body.where.b \ ${NS}::button $w_body.where.b \
-text [mc "Browse"] \ -text [mc "Browse"] \
-command [cb _new_local_path] -command [cb _new_local_path]
set w_localpath $w_body.where.t set w_localpath $w_body.where.t
@ -456,63 +466,57 @@ proc _new_ok {p} {
## Clone Existing Repository ## Clone Existing Repository
method _do_clone {} { method _do_clone {} {
global use_ttk NS
$w_next conf \ $w_next conf \
-state disabled \ -state disabled \
-command [cb _do_clone2] \ -command [cb _do_clone2] \
-text [mc "Clone"] -text [mc "Clone"]
frame $w_body ${NS}::frame $w_body
label $w_body.h \ ${NS}::label $w_body.h \
-font font_uibold \ -font font_uibold -anchor center \
-text [mc "Clone Existing Repository"] -text [mc "Clone Existing Repository"]
pack $w_body.h -side top -fill x -pady 10 pack $w_body.h -side top -fill x -pady 10
pack $w_body -fill x -padx 10 pack $w_body -fill x -padx 10
set args $w_body.args set args $w_body.args
frame $w_body.args ${NS}::frame $w_body.args
pack $args -fill both pack $args -fill both
label $args.origin_l -text [mc "Source Location:"] ${NS}::label $args.origin_l -text [mc "Source Location:"]
entry $args.origin_t \ ${NS}::entry $args.origin_t \
-textvariable @origin_url \ -textvariable @origin_url \
-borderwidth 1 \
-relief sunken \
-width 50 -width 50
button $args.origin_b \ ${NS}::button $args.origin_b \
-text [mc "Browse"] \ -text [mc "Browse"] \
-command [cb _open_origin] -command [cb _open_origin]
grid $args.origin_l $args.origin_t $args.origin_b -sticky ew grid $args.origin_l $args.origin_t $args.origin_b -sticky ew
label $args.where_l -text [mc "Target Directory:"] ${NS}::label $args.where_l -text [mc "Target Directory:"]
entry $args.where_t \ ${NS}::entry $args.where_t \
-textvariable @local_path \ -textvariable @local_path \
-borderwidth 1 \
-relief sunken \
-width 50 -width 50
button $args.where_b \ ${NS}::button $args.where_b \
-text [mc "Browse"] \ -text [mc "Browse"] \
-command [cb _new_local_path] -command [cb _new_local_path]
grid $args.where_l $args.where_t $args.where_b -sticky ew grid $args.where_l $args.where_t $args.where_b -sticky ew
set w_localpath $args.where_t set w_localpath $args.where_t
label $args.type_l -text [mc "Clone Type:"] ${NS}::label $args.type_l -text [mc "Clone Type:"]
frame $args.type_f ${NS}::frame $args.type_f
set w_types [list] set w_types [list]
lappend w_types [radiobutton $args.type_f.hardlink \ lappend w_types [${NS}::radiobutton $args.type_f.hardlink \
-state disabled \ -state disabled \
-anchor w \
-text [mc "Standard (Fast, Semi-Redundant, Hardlinks)"] \ -text [mc "Standard (Fast, Semi-Redundant, Hardlinks)"] \
-variable @clone_type \ -variable @clone_type \
-value hardlink] -value hardlink]
lappend w_types [radiobutton $args.type_f.full \ lappend w_types [${NS}::radiobutton $args.type_f.full \
-state disabled \ -state disabled \
-anchor w \
-text [mc "Full Copy (Slower, Redundant Backup)"] \ -text [mc "Full Copy (Slower, Redundant Backup)"] \
-variable @clone_type \ -variable @clone_type \
-value full] -value full]
lappend w_types [radiobutton $args.type_f.shared \ lappend w_types [${NS}::radiobutton $args.type_f.shared \
-state disabled \ -state disabled \
-anchor w \
-text [mc "Shared (Fastest, Not Recommended, No Backup)"] \ -text [mc "Shared (Fastest, Not Recommended, No Backup)"] \
-variable @clone_type \ -variable @clone_type \
-value shared] -value shared]
@ -1001,26 +1005,25 @@ method _postcheckout_wait {fd_ph} {
## Open Existing Repository ## Open Existing Repository
method _do_open {} { method _do_open {} {
global NS
$w_next conf \ $w_next conf \
-state disabled \ -state disabled \
-command [cb _do_open2] \ -command [cb _do_open2] \
-text [mc "Open"] -text [mc "Open"]
frame $w_body ${NS}::frame $w_body
label $w_body.h \ ${NS}::label $w_body.h \
-font font_uibold \ -font font_uibold -anchor center \
-text [mc "Open Existing Repository"] -text [mc "Open Existing Repository"]
pack $w_body.h -side top -fill x -pady 10 pack $w_body.h -side top -fill x -pady 10
pack $w_body -fill x -padx 10 pack $w_body -fill x -padx 10
frame $w_body.where ${NS}::frame $w_body.where
label $w_body.where.l -text [mc "Repository:"] ${NS}::label $w_body.where.l -text [mc "Repository:"]
entry $w_body.where.t \ ${NS}::entry $w_body.where.t \
-textvariable @local_path \ -textvariable @local_path \
-borderwidth 1 \
-relief sunken \
-width 50 -width 50
button $w_body.where.b \ ${NS}::button $w_body.where.b \
-text [mc "Browse"] \ -text [mc "Browse"] \
-command [cb _open_local_path] -command [cb _open_local_path]

View File

@ -10,7 +10,7 @@ field w_list ; # list of currently filtered specs
field w_filter ; # filter entry for $w_list field w_filter ; # filter entry for $w_list
field c_expr {}; # current revision expression field c_expr {}; # current revision expression
field filter ; # current filter string field filter ""; # current filter string
field revtype head; # type of revision chosen field revtype head; # type of revision chosen
field cur_specs [list]; # list of specs for $revtype field cur_specs [list]; # list of specs for $revtype
field spec_head ; # list of all head specs field spec_head ; # list of all head specs
@ -32,7 +32,7 @@ proc new_unmerged {path {title {}}} {
} }
constructor _new {path unmerged_only title} { constructor _new {path unmerged_only title} {
global current_branch is_detached global current_branch is_detached use_ttk NS
if {![info exists ::all_remotes]} { if {![info exists ::all_remotes]} {
load_all_remotes load_all_remotes
@ -41,65 +41,65 @@ constructor _new {path unmerged_only title} {
set w $path set w $path
if {$title ne {}} { if {$title ne {}} {
labelframe $w -text $title ${NS}::labelframe $w -text $title
} else { } else {
frame $w ${NS}::frame $w
} }
bind $w <Destroy> [cb _delete %W] bind $w <Destroy> [cb _delete %W]
if {$is_detached} { if {$is_detached} {
radiobutton $w.detachedhead_r \ ${NS}::radiobutton $w.detachedhead_r \
-anchor w \
-text [mc "This Detached Checkout"] \ -text [mc "This Detached Checkout"] \
-value HEAD \ -value HEAD \
-variable @revtype -variable @revtype
if {!$use_ttk} {$w.detachedhead_r configure -anchor w}
grid $w.detachedhead_r -sticky we -padx {0 5} -columnspan 2 grid $w.detachedhead_r -sticky we -padx {0 5} -columnspan 2
} }
radiobutton $w.expr_r \ ${NS}::radiobutton $w.expr_r \
-text [mc "Revision Expression:"] \ -text [mc "Revision Expression:"] \
-value expr \ -value expr \
-variable @revtype -variable @revtype
entry $w.expr_t \ ${NS}::entry $w.expr_t \
-borderwidth 1 \
-relief sunken \
-width 50 \ -width 50 \
-textvariable @c_expr \ -textvariable @c_expr \
-validate key \ -validate key \
-validatecommand [cb _validate %d %S] -validatecommand [cb _validate %d %S]
grid $w.expr_r $w.expr_t -sticky we -padx {0 5} grid $w.expr_r $w.expr_t -sticky we -padx {0 5}
frame $w.types ${NS}::frame $w.types
radiobutton $w.types.head_r \ ${NS}::radiobutton $w.types.head_r \
-text [mc "Local Branch"] \ -text [mc "Local Branch"] \
-value head \ -value head \
-variable @revtype -variable @revtype
pack $w.types.head_r -side left pack $w.types.head_r -side left
radiobutton $w.types.trck_r \ ${NS}::radiobutton $w.types.trck_r \
-text [mc "Tracking Branch"] \ -text [mc "Tracking Branch"] \
-value trck \ -value trck \
-variable @revtype -variable @revtype
pack $w.types.trck_r -side left pack $w.types.trck_r -side left
radiobutton $w.types.tag_r \ ${NS}::radiobutton $w.types.tag_r \
-text [mc "Tag"] \ -text [mc "Tag"] \
-value tag \ -value tag \
-variable @revtype -variable @revtype
pack $w.types.tag_r -side left pack $w.types.tag_r -side left
set w_filter $w.types.filter set w_filter $w.types.filter
entry $w_filter \ ${NS}::entry $w_filter \
-borderwidth 1 \
-relief sunken \
-width 12 \ -width 12 \
-textvariable @filter \ -textvariable @filter \
-validate key \ -validate key \
-validatecommand [cb _filter %P] -validatecommand [cb _filter %P]
pack $w_filter -side right pack $w_filter -side right
pack [label $w.types.filter_icon \ pack [${NS}::label $w.types.filter_icon \
-image ::choose_rev::img_find \ -image ::choose_rev::img_find \
] -side right ] -side right
grid $w.types -sticky we -padx {0 5} -columnspan 2 grid $w.types -sticky we -padx {0 5} -columnspan 2
if {$use_ttk} {
ttk::frame $w.list -style SListbox.TFrame -padding 2
} else {
frame $w.list frame $w.list
}
set w_list $w.list.l set w_list $w.list.l
listbox $w_list \ listbox $w_list \
-font font_diff \ -font font_diff \
@ -109,6 +109,9 @@ constructor _new {path unmerged_only title} {
-exportselection false \ -exportselection false \
-xscrollcommand [cb _sb_set $w.list.sbx h] \ -xscrollcommand [cb _sb_set $w.list.sbx h] \
-yscrollcommand [cb _sb_set $w.list.sby v] -yscrollcommand [cb _sb_set $w.list.sby v]
if {$use_ttk} {
$w_list configure -relief flat -highlightthickness 0 -borderwidth 0
}
pack $w_list -fill both -expand 1 pack $w_list -fill both -expand 1
grid $w.list -sticky nswe -padx {20 5} -columnspan 2 grid $w.list -sticky nswe -padx {20 5} -columnspan 2
bind $w_list <Any-Motion> [cb _show_tooltip @%x,%y] bind $w_list <Any-Motion> [cb _show_tooltip @%x,%y]
@ -235,11 +238,12 @@ constructor _new {path unmerged_only title} {
} }
method none {text} { method none {text} {
global NS use_ttk
if {![winfo exists $w.none_r]} { if {![winfo exists $w.none_r]} {
radiobutton $w.none_r \ ${NS}::radiobutton $w.none_r \
-anchor w \
-value none \ -value none \
-variable @revtype -variable @revtype
if {!$use_ttk} {$w.none_r configure -anchor w}
grid $w.none_r -sticky we -padx {0 5} -columnspan 2 grid $w.none_r -sticky we -padx {0 5} -columnspan 2
} }
$w.none_r configure -text $text $w.none_r configure -text $text
@ -425,6 +429,7 @@ method _delete {current} {
} }
method _sb_set {sb orient first last} { method _sb_set {sb orient first last} {
global NS
set old_focus [focus -lastfor $w] set old_focus [focus -lastfor $w]
if {$first == 0 && $last == 1} { if {$first == 0 && $last == 1} {
@ -440,10 +445,10 @@ method _sb_set {sb orient first last} {
if {![winfo exists $sb]} { if {![winfo exists $sb]} {
if {$orient eq {h}} { if {$orient eq {h}} {
scrollbar $sb -orient h -command [list $w_list xview] ${NS}::scrollbar $sb -orient h -command [list $w_list xview]
pack $sb -fill x -side bottom -before $w_list pack $sb -fill x -side bottom -before $w_list
} else { } else {
scrollbar $sb -orient v -command [list $w_list yview] ${NS}::scrollbar $sb -orient v -command [list $w_list yview]
pack $sb -fill y -side right -before $w_list pack $sb -fill y -side right -before $w_list
} }
if {$old_focus ne {}} { if {$old_focus ne {}} {

View File

@ -134,6 +134,13 @@ proc delete_this {{t {}}} {
if {[namespace exists $t]} {namespace delete $t} if {[namespace exists $t]} {namespace delete $t}
} }
proc make_dialog {t w args} {
upvar $t top $w pfx this this
global use_ttk
uplevel [linsert $args 0 make_toplevel $t $w]
pave_toplevel $pfx
}
proc make_toplevel {t w args} { proc make_toplevel {t w args} {
upvar $t top $w pfx this this upvar $t top $w pfx this this

View File

@ -27,20 +27,20 @@ constructor embed {path title} {
} }
method _init {} { method _init {} {
global M1B global M1B use_ttk NS
if {$is_toplevel} { if {$is_toplevel} {
make_toplevel top w -autodelete 0 make_dialog top w -autodelete 0
wm title $top "[appname] ([reponame]): $t_short" wm title $top "[appname] ([reponame]): $t_short"
} else { } else {
frame $w ${NS}::frame $w
} }
set console_cr 1.0 set console_cr 1.0
set w_t $w.m.t set w_t $w.m.t
frame $w.m ${NS}::frame $w.m
label $w.m.l1 \ ${NS}::label $w.m.l1 \
-textvariable @t_long \ -textvariable @t_long \
-anchor w \ -anchor w \
-justify left \ -justify left \
@ -78,7 +78,7 @@ method _init {} {
" "
if {$is_toplevel} { if {$is_toplevel} {
button $w.ok -text [mc "Close"] \ ${NS}::button $w.ok -text [mc "Close"] \
-state disabled \ -state disabled \
-command [list destroy $w] -command [list destroy $w]
pack $w.ok -side bottom -anchor e -pady 10 -padx 10 pack $w.ok -side bottom -anchor e -pady 10 -padx 10
@ -206,13 +206,14 @@ method done {ok} {
} }
method _sb_set {sb orient first last} { method _sb_set {sb orient first last} {
global NS
if {![winfo exists $sb]} { if {![winfo exists $sb]} {
if {$first == $last || ($first == 0 && $last == 1)} return if {$first == $last || ($first == 0 && $last == 1)} return
if {$orient eq {h}} { if {$orient eq {h}} {
scrollbar $sb -orient h -command [list $w_t xview] ${NS}::scrollbar $sb -orient h -command [list $w_t xview]
pack $sb -fill x -side bottom -before $w_t pack $sb -fill x -side bottom -before $w_t
} else { } else {
scrollbar $sb -orient v -command [list $w_t yview] ${NS}::scrollbar $sb -orient v -command [list $w_t yview]
pack $sb -fill y -side right -before $w_t pack $sb -fill y -side right -before $w_t
} }
} }

View File

@ -2,6 +2,7 @@
# Copyright (C) 2006, 2007 Shawn Pearce # Copyright (C) 2006, 2007 Shawn Pearce
proc do_stats {} { proc do_stats {} {
global use_ttk NS
set fd [git_read count-objects -v] set fd [git_read count-objects -v]
while {[gets $fd line] > 0} { while {[gets $fd line] > 0} {
if {[regexp {^([^:]+): (\d+)$} $line _ name value]} { if {[regexp {^([^:]+): (\d+)$} $line _ name value]} {
@ -21,24 +22,22 @@ proc do_stats {} {
} }
set w .stats_view set w .stats_view
toplevel $w Dialog $w
wm withdraw $w
wm geometry $w "+[winfo rootx .]+[winfo rooty .]" wm geometry $w "+[winfo rootx .]+[winfo rooty .]"
label $w.header -text [mc "Database Statistics"] ${NS}::frame $w.buttons
pack $w.header -side top -fill x ${NS}::button $w.buttons.close -text [mc Close] \
frame $w.buttons -border 1
button $w.buttons.close -text [mc Close] \
-default active \ -default active \
-command [list destroy $w] -command [list destroy $w]
button $w.buttons.gc -text [mc "Compress Database"] \ ${NS}::button $w.buttons.gc -text [mc "Compress Database"] \
-default normal \ -default normal \
-command "destroy $w;do_gc" -command "destroy $w;do_gc"
pack $w.buttons.close -side right pack $w.buttons.close -side right
pack $w.buttons.gc -side left pack $w.buttons.gc -side left
pack $w.buttons -side bottom -fill x -pady 10 -padx 10 pack $w.buttons -side bottom -fill x -pady 10 -padx 10
frame $w.stat -borderwidth 1 -relief solid ${NS}::labelframe $w.stat -text [mc "Database Statistics"]
foreach s { foreach s {
{count {mc "Number of loose objects"}} {count {mc "Number of loose objects"}}
{size {mc "Disk space used by loose objects"} { KiB}} {size {mc "Disk space used by loose objects"} { KiB}}
@ -55,8 +54,8 @@ proc do_stats {} {
set value "$value[lindex $s 2]" set value "$value[lindex $s 2]"
} }
label $w.stat.l_$name -text "$label:" -anchor w ${NS}::label $w.stat.l_$name -text "$label:" -anchor w
label $w.stat.v_$name -text $value -anchor w ${NS}::label $w.stat.v_$name -text $value -anchor w
grid $w.stat.l_$name $w.stat.v_$name -sticky we -padx {0 5} grid $w.stat.l_$name $w.stat.v_$name -sticky we -padx {0 5}
} }
pack $w.stat -pady 10 -padx 10 pack $w.stat -pady 10 -padx 10
@ -65,6 +64,7 @@ proc do_stats {} {
bind $w <Key-Escape> [list destroy $w] bind $w <Key-Escape> [list destroy $w]
bind $w <Key-Return> [list destroy $w] bind $w <Key-Return> [list destroy $w]
wm title $w [append "[appname] ([reponame]): " [mc "Database Statistics"]] wm title $w [append "[appname] ([reponame]): " [mc "Database Statistics"]]
wm deiconify $w
tkwait window $w tkwait window $w
} }

View File

@ -55,7 +55,7 @@ proc handle_empty_diff {} {
set path $current_diff_path set path $current_diff_path
set s $file_states($path) set s $file_states($path)
if {[lindex $s 0] ne {_M}} return if {[lindex $s 0] ne {_M} || [has_textconv $path]} return
# Prevent infinite rescan loops # Prevent infinite rescan loops
incr diff_empty_count incr diff_empty_count
@ -280,6 +280,18 @@ proc start_show_diff {cont_info {add_opts {}}} {
lappend cmd diff-files lappend cmd diff-files
} }
} }
if {![is_config_false gui.textconv] && [git-version >= 1.6.1]} {
lappend cmd --textconv
}
if {[string match {160000 *} [lindex $s 2]]
|| [string match {160000 *} [lindex $s 3]]} {
set is_submodule_diff 1
if {[git-version >= "1.6.6"]} {
lappend cmd --submodule
}
}
lappend cmd -p lappend cmd -p
lappend cmd --no-color lappend cmd --no-color
@ -296,9 +308,7 @@ proc start_show_diff {cont_info {add_opts {}}} {
lappend cmd $path lappend cmd $path
} }
if {[string match {160000 *} [lindex $s 2]] if {$is_submodule_diff && [git-version < "1.6.6"]} {
|| [string match {160000 *} [lindex $s 3]]} {
set is_submodule_diff 1
if {$w eq $ui_index} { if {$w eq $ui_index} {
set cmd [list submodule summary --cached -- $path] set cmd [list submodule summary --cached -- $path]
} else { } else {
@ -387,7 +397,9 @@ proc read_diff {fd cont_info} {
} }
} elseif {$is_submodule_diff} { } elseif {$is_submodule_diff} {
if {$line == ""} continue if {$line == ""} continue
if {[regexp {^\* } $line]} { if {[regexp {^Submodule } $line]} {
set tags d_@
} elseif {[regexp {^\* } $line]} {
set line [string replace $line 0 1 {Submodule }] set line [string replace $line 0 1 {Submodule }]
set tags d_@ set tags d_@
} else { } else {
@ -533,10 +545,23 @@ proc apply_hunk {x y} {
} }
} }
proc apply_line {x y} { proc apply_range_or_line {x y} {
global current_diff_path current_diff_header current_diff_side global current_diff_path current_diff_header current_diff_side
global ui_diff ui_index file_states global ui_diff ui_index file_states
set selected [$ui_diff tag nextrange sel 0.0]
if {$selected == {}} {
set first [$ui_diff index "@$x,$y"]
set last $first
} else {
set first [lindex $selected 0]
set last [lindex $selected 1]
}
set first_l [$ui_diff index "$first linestart"]
set last_l [$ui_diff index "$last lineend"]
if {$current_diff_path eq {} || $current_diff_header eq {}} return if {$current_diff_path eq {} || $current_diff_header eq {}} return
if {![lock_index apply_hunk]} return if {![lock_index apply_hunk]} return
@ -559,17 +584,15 @@ proc apply_line {x y} {
} }
} }
set the_l [$ui_diff index @$x,$y] set wholepatch {}
# operate only on change lines while {$first_l < $last_l} {
set c1 [$ui_diff get "$the_l linestart"] set i_l [$ui_diff search -backwards -regexp ^@@ $first_l 0.0]
if {$c1 ne {+} && $c1 ne {-}} { if {$i_l eq {}} {
unlock_index # If there's not a @@ above, then the selected range
return # must have come before the first_l @@
set i_l [$ui_diff search -regexp ^@@ $first_l $last_l]
} }
set sign $c1
set i_l [$ui_diff search -backwards -regexp ^@@ $the_l 0.0]
if {$i_l eq {}} { if {$i_l eq {}} {
unlock_index unlock_index
return return
@ -581,7 +604,8 @@ proc apply_line {x y} {
set hh [lindex [split $hh ,] 0] set hh [lindex [split $hh ,] 0]
set hln [lindex [split $hh -] 1] set hln [lindex [split $hh -] 1]
# There is a special situation to take care of. Consider this hunk: # There is a special situation to take care of. Consider this
# hunk:
# #
# @@ -10,4 +10,4 @@ # @@ -10,4 +10,4 @@
# context before # context before
@ -591,8 +615,8 @@ proc apply_line {x y} {
# +new 2 # +new 2
# context after # context after
# #
# We used to keep the context lines in the order they appear in the # We used to keep the context lines in the order they appear in
# hunk. But then it is not possible to correctly stage only # the hunk. But then it is not possible to correctly stage only
# "-old 1" and "+new 1" - it would result in this staged text: # "-old 1" and "+new 1" - it would result in this staged text:
# #
# context before # context before
@ -600,12 +624,14 @@ proc apply_line {x y} {
# new 1 # new 1
# context after # context after
# #
# (By symmetry it is not possible to *un*stage "old 2" and "new 2".) # (By symmetry it is not possible to *un*stage "old 2" and "new
# 2".)
# #
# We resolve the problem by introducing an asymmetry, namely, when # We resolve the problem by introducing an asymmetry, namely,
# a "+" line is *staged*, it is moved in front of the context lines # when a "+" line is *staged*, it is moved in front of the
# that are generated from the "-" lines that are immediately before # context lines that are generated from the "-" lines that are
# the "+" block. That is, we construct this patch: # immediately before the "+" block. That is, we construct this
# patch:
# #
# @@ -10,4 +10,5 @@ # @@ -10,4 +10,5 @@
# context before # context before
@ -614,43 +640,60 @@ proc apply_line {x y} {
# old 2 # old 2
# context after # context after
# #
# But we do *not* treat "-" lines that are *un*staged in a special # But we do *not* treat "-" lines that are *un*staged in a
# way. # special way.
# #
# With this asymmetry it is possible to stage the change # With this asymmetry it is possible to stage the change "old
# "old 1" -> "new 1" directly, and to stage the change # 1" -> "new 1" directly, and to stage the change "old 2" ->
# "old 2" -> "new 2" by first staging the entire hunk and # "new 2" by first staging the entire hunk and then unstaging
# then unstaging the change "old 1" -> "new 1". # the change "old 1" -> "new 1".
#
# Applying multiple lines adds complexity to the special
# situation. The pre_context must be moved after the entire
# first block of consecutive staged "+" lines, so that
# staging both additions gives the following patch:
#
# @@ -10,4 +10,6 @@
# context before
# +new 1
# +new 2
# old 1
# old 2
# context after
# This is non-empty if and only if we are _staging_ changes; # This is non-empty if and only if we are _staging_ changes;
# then it accumulates the consecutive "-" lines (after converting # then it accumulates the consecutive "-" lines (after
# them to context lines) in order to be moved after the "+" change # converting them to context lines) in order to be moved after
# line. # "+" change lines.
set pre_context {} set pre_context {}
set n 0 set n 0
set m 0
set i_l [$ui_diff index "$i_l + 1 lines"] set i_l [$ui_diff index "$i_l + 1 lines"]
set patch {} set patch {}
while {[$ui_diff compare $i_l < "end - 1 chars"] && while {[$ui_diff compare $i_l < "end - 1 chars"] &&
[$ui_diff get $i_l "$i_l + 2 chars"] ne {@@}} { [$ui_diff get $i_l "$i_l + 2 chars"] ne {@@}} {
set next_l [$ui_diff index "$i_l + 1 lines"] set next_l [$ui_diff index "$i_l + 1 lines"]
set c1 [$ui_diff get $i_l] set c1 [$ui_diff get $i_l]
if {[$ui_diff compare $i_l <= $the_l] && if {[$ui_diff compare $first_l <= $i_l] &&
[$ui_diff compare $the_l < $next_l]} { [$ui_diff compare $i_l < $last_l] &&
# the line to stage/unstage ($c1 eq {-} || $c1 eq {+})} {
# a line to stage/unstage
set ln [$ui_diff get $i_l $next_l] set ln [$ui_diff get $i_l $next_l]
if {$c1 eq {-}} { if {$c1 eq {-}} {
set n [expr $n+1] set n [expr $n+1]
set patch "$patch$pre_context$ln" set patch "$patch$pre_context$ln"
} else {
set patch "$patch$ln$pre_context"
}
set pre_context {} set pre_context {}
} else {
set m [expr $m+1]
set patch "$patch$ln"
}
} elseif {$c1 ne {-} && $c1 ne {+}} { } elseif {$c1 ne {-} && $c1 ne {+}} {
# context line # context line
set ln [$ui_diff get $i_l $next_l] set ln [$ui_diff get $i_l $next_l]
set patch "$patch$pre_context$ln" set patch "$patch$pre_context$ln"
set n [expr $n+1] set n [expr $n+1]
set m [expr $m+1]
set pre_context {} set pre_context {}
} elseif {$c1 eq $to_context} { } elseif {$c1 eq $to_context} {
# turn change line into context line # turn change line into context line
@ -661,17 +704,27 @@ proc apply_line {x y} {
set patch "$patch $ln" set patch "$patch $ln"
} }
set n [expr $n+1] set n [expr $n+1]
set m [expr $m+1]
} else {
# a change in the opposite direction of
# to_context which is outside the range of
# lines to apply.
set patch "$patch$pre_context"
set pre_context {}
} }
set i_l $next_l set i_l $next_l
} }
set patch "@@ -$hln,$n +$hln,[eval expr $n $sign 1] @@\n$patch" set patch "$patch$pre_context"
set wholepatch "$wholepatch@@ -$hln,$n +$hln,$m @@\n$patch"
set first_l [$ui_diff index "$next_l + 1 lines"]
}
if {[catch { if {[catch {
set enc [get_path_encoding $current_diff_path] set enc [get_path_encoding $current_diff_path]
set p [eval git_write $apply_cmd] set p [eval git_write $apply_cmd]
fconfigure $p -translation binary -encoding $enc fconfigure $p -translation binary -encoding $enc
puts -nonewline $p $current_diff_header puts -nonewline $p $current_diff_header
puts -nonewline $p $patch puts -nonewline $p $wholepatch
close $p} err]} { close $p} err]} {
error_popup [append $failed_msg "\n\n$err"] error_popup [append $failed_msg "\n\n$err"]
} }

View File

@ -71,11 +71,13 @@ proc ask_popup {msg} {
} }
proc hook_failed_popup {hook msg {is_fatal 1}} { proc hook_failed_popup {hook msg {is_fatal 1}} {
global use_ttk NS
set w .hookfail set w .hookfail
toplevel $w Dialog $w
wm withdraw $w
frame $w.m ${NS}::frame $w.m
label $w.m.l1 -text "$hook hook failed:" \ ${NS}::label $w.m.l1 -text "$hook hook failed:" \
-anchor w \ -anchor w \
-justify left \ -justify left \
-font font_uibold -font font_uibold
@ -87,10 +89,10 @@ proc hook_failed_popup {hook msg {is_fatal 1}} {
-width 80 -height 10 \ -width 80 -height 10 \
-font font_diff \ -font font_diff \
-yscrollcommand [list $w.m.sby set] -yscrollcommand [list $w.m.sby set]
scrollbar $w.m.sby -command [list $w.m.t yview] ${NS}::scrollbar $w.m.sby -command [list $w.m.t yview]
pack $w.m.l1 -side top -fill x pack $w.m.l1 -side top -fill x
if {$is_fatal} { if {$is_fatal} {
label $w.m.l2 \ ${NS}::label $w.m.l2 \
-text [mc "You must correct the above errors before committing."] \ -text [mc "You must correct the above errors before committing."] \
-anchor w \ -anchor w \
-justify left \ -justify left \
@ -104,7 +106,7 @@ proc hook_failed_popup {hook msg {is_fatal 1}} {
$w.m.t insert 1.0 $msg $w.m.t insert 1.0 $msg
$w.m.t conf -state disabled $w.m.t conf -state disabled
button $w.ok -text OK \ ${NS}::button $w.ok -text OK \
-width 15 \ -width 15 \
-command "destroy $w" -command "destroy $w"
pack $w.ok -side bottom -anchor e -pady 10 -padx 10 pack $w.ok -side bottom -anchor e -pady 10 -padx 10
@ -112,5 +114,6 @@ proc hook_failed_popup {hook msg {is_fatal 1}} {
bind $w <Visibility> "grab $w; focus $w" bind $w <Visibility> "grab $w; focus $w"
bind $w <Key-Return> "destroy $w" bind $w <Key-Return> "destroy $w"
wm title $w [strcat "[appname] ([reponame]): " [mc "error"]] wm title $w [strcat "[appname] ([reponame]): " [mc "error"]]
wm deiconify $w
tkwait window $w tkwait window $w
} }

View File

@ -8,36 +8,41 @@ proc _delete_indexlock {} {
} }
proc _close_updateindex {fd after} { proc _close_updateindex {fd after} {
global use_ttk NS
fconfigure $fd -blocking 1 fconfigure $fd -blocking 1
if {[catch {close $fd} err]} { if {[catch {close $fd} err]} {
set w .indexfried set w .indexfried
toplevel $w Dialog $w
wm withdraw $w
wm title $w [strcat "[appname] ([reponame]): " [mc "Index Error"]] wm title $w [strcat "[appname] ([reponame]): " [mc "Index Error"]]
wm geometry $w "+[winfo rootx .]+[winfo rooty .]" wm geometry $w "+[winfo rootx .]+[winfo rooty .]"
pack [label $w.msg \ set s [mc "Updating the Git index failed. A rescan will be automatically started to resynchronize git-gui."]
-justify left \ text $w.msg -yscrollcommand [list $w.vs set] \
-anchor w \ -width [string length $s] -relief flat \
-text [strcat \ -borderwidth 0 -highlightthickness 0 \
[mc "Updating the Git index failed. A rescan will be automatically started to resynchronize git-gui."] \ -background [get_bg_color $w]
"\n\n$err"] \ $w.msg tag configure bold -font font_uibold -justify center
] -anchor w ${NS}::scrollbar $w.vs -command [list $w.msg yview]
$w.msg insert end $s bold \n\n$err {}
$w.msg configure -state disabled
frame $w.buttons ${NS}::button $w.continue \
button $w.buttons.continue \
-text [mc "Continue"] \ -text [mc "Continue"] \
-command [list destroy $w] -command [list destroy $w]
pack $w.buttons.continue -side right -padx 5 ${NS}::button $w.unlock \
button $w.buttons.unlock \
-text [mc "Unlock Index"] \ -text [mc "Unlock Index"] \
-command "destroy $w; _delete_indexlock" -command "destroy $w; _delete_indexlock"
pack $w.buttons.unlock -side right grid $w.msg - $w.vs -sticky news
pack $w.buttons -side bottom -fill x -pady 10 -padx 10 grid $w.unlock $w.continue - -sticky se -padx 2 -pady 2
grid columnconfigure $w 0 -weight 1
grid rowconfigure $w 0 -weight 1
wm protocol $w WM_DELETE_WINDOW update wm protocol $w WM_DELETE_WINDOW update
bind $w.buttons.continue <Visibility> " bind $w.continue <Visibility> "
grab $w grab $w
focus $w.buttons.continue focus %W
" "
wm deiconify $w
tkwait window $w tkwait window $w
$::main_status stop $::main_status stop

View File

@ -139,14 +139,14 @@ method _finish {cons ok} {
constructor dialog {} { constructor dialog {} {
global current_branch global current_branch
global M1B global M1B use_ttk NS
if {![_can_merge $this]} { if {![_can_merge $this]} {
delete_this delete_this
return return
} }
make_toplevel top w make_dialog top w
wm title $top [append "[appname] ([reponame]): " [mc "Merge"]] wm title $top [append "[appname] ([reponame]): " [mc "Merge"]]
if {$top ne {.}} { if {$top ne {.}} {
wm geometry $top "+[winfo rootx .]+[winfo rooty .]" wm geometry $top "+[winfo rootx .]+[winfo rooty .]"
@ -154,21 +154,21 @@ constructor dialog {} {
set _start [cb _start] set _start [cb _start]
label $w.header \ ${NS}::label $w.header \
-text [mc "Merge Into %s" $current_branch] \ -text [mc "Merge Into %s" $current_branch] \
-font font_uibold -font font_uibold
pack $w.header -side top -fill x pack $w.header -side top -fill x
frame $w.buttons ${NS}::frame $w.buttons
button $w.buttons.visualize \ ${NS}::button $w.buttons.visualize \
-text [mc Visualize] \ -text [mc Visualize] \
-command [cb _visualize] -command [cb _visualize]
pack $w.buttons.visualize -side left pack $w.buttons.visualize -side left
button $w.buttons.merge \ ${NS}::button $w.buttons.merge \
-text [mc Merge] \ -text [mc Merge] \
-command $_start -command $_start
pack $w.buttons.merge -side right pack $w.buttons.merge -side right
button $w.buttons.cancel \ ${NS}::button $w.buttons.cancel \
-text [mc "Cancel"] \ -text [mc "Cancel"] \
-command [cb _cancel] -command [cb _cancel]
pack $w.buttons.cancel -side right -padx 5 pack $w.buttons.cancel -side right -padx 5

View File

@ -91,7 +91,7 @@ proc save_config {} {
proc do_options {} { proc do_options {} {
global repo_config global_config font_descs global repo_config global_config font_descs
global repo_config_new global_config_new global repo_config_new global_config_new
global ui_comm_spell global ui_comm_spell use_ttk NS
array unset repo_config_new array unset repo_config_new
array unset global_config_new array unset global_config_new
@ -110,26 +110,28 @@ proc do_options {} {
} }
set w .options_editor set w .options_editor
toplevel $w Dialog $w
wm withdraw $w
wm transient $w [winfo parent $w]
wm geometry $w "+[winfo rootx .]+[winfo rooty .]" wm geometry $w "+[winfo rootx .]+[winfo rooty .]"
frame $w.buttons ${NS}::frame $w.buttons
button $w.buttons.restore -text [mc "Restore Defaults"] \ ${NS}::button $w.buttons.restore -text [mc "Restore Defaults"] \
-default normal \ -default normal \
-command do_restore_defaults -command do_restore_defaults
pack $w.buttons.restore -side left pack $w.buttons.restore -side left
button $w.buttons.save -text [mc Save] \ ${NS}::button $w.buttons.save -text [mc Save] \
-default active \ -default active \
-command [list do_save_config $w] -command [list do_save_config $w]
pack $w.buttons.save -side right pack $w.buttons.save -side right
button $w.buttons.cancel -text [mc "Cancel"] \ ${NS}::button $w.buttons.cancel -text [mc "Cancel"] \
-default normal \ -default normal \
-command [list destroy $w] -command [list destroy $w]
pack $w.buttons.cancel -side right -padx 5 pack $w.buttons.cancel -side right -padx 5
pack $w.buttons -side bottom -fill x -pady 10 -padx 10 pack $w.buttons -side bottom -fill x -pady 10 -padx 10
labelframe $w.repo -text [mc "%s Repository" [reponame]] ${NS}::labelframe $w.repo -text [mc "%s Repository" [reponame]]
labelframe $w.global -text [mc "Global (All Repositories)"] ${NS}::labelframe $w.global -text [mc "Global (All Repositories)"]
pack $w.repo -side left -fill both -expand 1 -pady 5 -padx 5 pack $w.repo -side left -fill both -expand 1 -pady 5 -padx 5
pack $w.global -side right -fill both -expand 1 -pady 5 -padx 5 pack $w.global -side right -fill both -expand 1 -pady 5 -padx 5
@ -146,6 +148,7 @@ proc do_options {} {
{b gui.trustmtime {mc "Trust File Modification Timestamps"}} {b gui.trustmtime {mc "Trust File Modification Timestamps"}}
{b gui.pruneduringfetch {mc "Prune Tracking Branches During Fetch"}} {b gui.pruneduringfetch {mc "Prune Tracking Branches During Fetch"}}
{b gui.matchtrackingbranch {mc "Match Tracking Branches"}} {b gui.matchtrackingbranch {mc "Match Tracking Branches"}}
{b gui.textconv {mc "Use Textconv For Diffs and Blames"}}
{b gui.fastcopyblame {mc "Blame Copy Only On Changed Files"}} {b gui.fastcopyblame {mc "Blame Copy Only On Changed Files"}}
{i-20..200 gui.copyblamethreshold {mc "Minimum Letters To Blame Copy On"}} {i-20..200 gui.copyblamethreshold {mc "Minimum Letters To Blame Copy On"}}
{i-0..300 gui.blamehistoryctx {mc "Blame History Context Radius (days)"}} {i-0..300 gui.blamehistoryctx {mc "Blame History Context Radius (days)"}}
@ -161,7 +164,7 @@ proc do_options {} {
foreach f {repo global} { foreach f {repo global} {
switch -glob -- $type { switch -glob -- $type {
b { b {
checkbutton $w.$f.$optid -text $text \ ${NS}::checkbutton $w.$f.$optid -text $text \
-variable ${f}_config_new($name) \ -variable ${f}_config_new($name) \
-onvalue true \ -onvalue true \
-offvalue false -offvalue false
@ -169,10 +172,10 @@ proc do_options {} {
} }
i-* { i-* {
regexp -- {-(\d+)\.\.(\d+)$} $type _junk min max regexp -- {-(\d+)\.\.(\d+)$} $type _junk min max
frame $w.$f.$optid ${NS}::frame $w.$f.$optid
label $w.$f.$optid.l -text "$text:" ${NS}::label $w.$f.$optid.l -text "$text:"
pack $w.$f.$optid.l -side left -anchor w -fill x pack $w.$f.$optid.l -side left -anchor w -fill x
spinbox $w.$f.$optid.v \ tspinbox $w.$f.$optid.v \
-textvariable ${f}_config_new($name) \ -textvariable ${f}_config_new($name) \
-from $min \ -from $min \
-to $max \ -to $max \
@ -184,11 +187,9 @@ proc do_options {} {
} }
c - c -
t { t {
frame $w.$f.$optid ${NS}::frame $w.$f.$optid
label $w.$f.$optid.l -text "$text:" ${NS}::label $w.$f.$optid.l -text "$text:"
entry $w.$f.$optid.v \ ${NS}::entry $w.$f.$optid.v \
-borderwidth 1 \
-relief sunken \
-width 20 \ -width 20 \
-textvariable ${f}_config_new($name) -textvariable ${f}_config_new($name)
pack $w.$f.$optid.l -side left -anchor w pack $w.$f.$optid.l -side left -anchor w
@ -199,7 +200,7 @@ proc do_options {} {
menu $w.$f.$optid.m menu $w.$f.$optid.m
build_encoding_menu $w.$f.$optid.m \ build_encoding_menu $w.$f.$optid.m \
[list set ${f}_config_new($name)] 1 [list set ${f}_config_new($name)] 1
button $w.$f.$optid.b \ ${NS}::button $w.$f.$optid.b \
-text [mc "Change"] \ -text [mc "Change"] \
-command [list popup_btn_menu \ -command [list popup_btn_menu \
$w.$f.$optid.m $w.$f.$optid.b] $w.$f.$optid.m $w.$f.$optid.b]
@ -226,11 +227,17 @@ proc do_options {} {
set ${f}_config_new(gui.spellingdictionary) $value set ${f}_config_new(gui.spellingdictionary) $value
} }
frame $w.$f.$optid ${NS}::frame $w.$f.$optid
label $w.$f.$optid.l -text [mc "Spelling Dictionary:"] ${NS}::label $w.$f.$optid.l -text [mc "Spelling Dictionary:"]
if {$use_ttk} {
ttk::combobox $w.$f.$optid.v \
-textvariable ${f}_config_new(gui.spellingdictionary) \
-values $all_dicts -state readonly
} else {
eval tk_optionMenu $w.$f.$optid.v \ eval tk_optionMenu $w.$f.$optid.v \
${f}_config_new(gui.spellingdictionary) \ ${f}_config_new(gui.spellingdictionary) \
$all_dicts $all_dicts
}
pack $w.$f.$optid.l -side left -anchor w -fill x pack $w.$f.$optid.l -side left -anchor w -fill x
pack $w.$f.$optid.v -side right -anchor e -padx 5 pack $w.$f.$optid.v -side right -anchor e -padx 5
pack $w.$f.$optid -side top -anchor w -fill x pack $w.$f.$optid -side top -anchor w -fill x
@ -248,20 +255,20 @@ proc do_options {} {
set global_config_new(gui.$font^^size) \ set global_config_new(gui.$font^^size) \
[font configure $font -size] [font configure $font -size]
frame $w.global.$name ${NS}::frame $w.global.$name
label $w.global.$name.l -text "$text:" ${NS}::label $w.global.$name.l -text "$text:"
button $w.global.$name.b \ ${NS}::button $w.global.$name.b \
-text [mc "Change Font"] \ -text [mc "Change Font"] \
-command [list \ -command [list \
choose_font::pick \ tchoosefont \
$w \ $w \
[mc "Choose %s" $text] \ [mc "Choose %s" $text] \
global_config_new(gui.$font^^family) \ global_config_new(gui.$font^^family) \
global_config_new(gui.$font^^size) \ global_config_new(gui.$font^^size) \
] ]
label $w.global.$name.f -textvariable global_config_new(gui.$font^^family) ${NS}::label $w.global.$name.f -textvariable global_config_new(gui.$font^^family)
label $w.global.$name.s -textvariable global_config_new(gui.$font^^size) ${NS}::label $w.global.$name.s -textvariable global_config_new(gui.$font^^size)
label $w.global.$name.pt -text [mc "pt."] ${NS}::label $w.global.$name.pt -text [mc "pt."]
pack $w.global.$name.l -side left -anchor w pack $w.global.$name.l -side left -anchor w
pack $w.global.$name.b -side right -anchor e pack $w.global.$name.b -side right -anchor e
pack $w.global.$name.pt -side right -anchor w pack $w.global.$name.pt -side right -anchor w
@ -280,6 +287,7 @@ proc do_options {} {
set t [mc "Options"] set t [mc "Options"]
} }
wm title $w "[appname] ([reponame]): $t" wm title $w "[appname] ([reponame]): $t"
wm deiconify $w
tkwait window $w tkwait window $w
} }

View File

@ -13,45 +13,43 @@ field location {}; # location of the remote the user has chosen
field opt_action fetch; # action to do after registering the remote locally field opt_action fetch; # action to do after registering the remote locally
constructor dialog {} { constructor dialog {} {
global repo_config global repo_config use_ttk NS
make_toplevel top w make_dialog top w
wm withdraw $top
wm title $top [append "[appname] ([reponame]): " [mc "Add Remote"]] wm title $top [append "[appname] ([reponame]): " [mc "Add Remote"]]
if {$top ne {.}} { if {$top ne {.}} {
wm geometry $top "+[winfo rootx .]+[winfo rooty .]" wm geometry $top "+[winfo rootx .]+[winfo rooty .]"
} }
label $w.header -text [mc "Add New Remote"] -font font_uibold ${NS}::label $w.header -text [mc "Add New Remote"] \
-font font_uibold -anchor center
pack $w.header -side top -fill x pack $w.header -side top -fill x
frame $w.buttons ${NS}::frame $w.buttons
button $w.buttons.create -text [mc Add] \ ${NS}::button $w.buttons.create -text [mc Add] \
-default active \ -default active \
-command [cb _add] -command [cb _add]
pack $w.buttons.create -side right pack $w.buttons.create -side right
button $w.buttons.cancel -text [mc Cancel] \ ${NS}::button $w.buttons.cancel -text [mc Cancel] \
-command [list destroy $w] -command [list destroy $w]
pack $w.buttons.cancel -side right -padx 5 pack $w.buttons.cancel -side right -padx 5
pack $w.buttons -side bottom -fill x -pady 10 -padx 10 pack $w.buttons -side bottom -fill x -pady 10 -padx 10
labelframe $w.desc -text [mc "Remote Details"] ${NS}::labelframe $w.desc -text [mc "Remote Details"]
label $w.desc.name_l -text [mc "Name:"] ${NS}::label $w.desc.name_l -text [mc "Name:"]
set w_name $w.desc.name_t set w_name $w.desc.name_t
entry $w_name \ ${NS}::entry $w_name \
-borderwidth 1 \
-relief sunken \
-width 40 \ -width 40 \
-textvariable @name \ -textvariable @name \
-validate key \ -validate key \
-validatecommand [cb _validate_name %d %S] -validatecommand [cb _validate_name %d %S]
grid $w.desc.name_l $w_name -sticky we -padx {0 5} grid $w.desc.name_l $w_name -sticky we -padx {0 5}
label $w.desc.loc_l -text [mc "Location:"] ${NS}::label $w.desc.loc_l -text [mc "Location:"]
set w_loc $w.desc.loc_t set w_loc $w.desc.loc_t
entry $w_loc \ ${NS}::entry $w_loc \
-borderwidth 1 \
-relief sunken \
-width 40 \ -width 40 \
-textvariable @location -textvariable @location
grid $w.desc.loc_l $w_loc -sticky we -padx {0 5} grid $w.desc.loc_l $w_loc -sticky we -padx {0 5}
@ -59,21 +57,21 @@ constructor dialog {} {
grid columnconfigure $w.desc 1 -weight 1 grid columnconfigure $w.desc 1 -weight 1
pack $w.desc -anchor nw -fill x -pady 5 -padx 5 pack $w.desc -anchor nw -fill x -pady 5 -padx 5
labelframe $w.action -text [mc "Further Action"] ${NS}::labelframe $w.action -text [mc "Further Action"]
radiobutton $w.action.fetch \ ${NS}::radiobutton $w.action.fetch \
-text [mc "Fetch Immediately"] \ -text [mc "Fetch Immediately"] \
-value fetch \ -value fetch \
-variable @opt_action -variable @opt_action
pack $w.action.fetch -anchor nw pack $w.action.fetch -anchor nw
radiobutton $w.action.push \ ${NS}::radiobutton $w.action.push \
-text [mc "Initialize Remote Repository and Push"] \ -text [mc "Initialize Remote Repository and Push"] \
-value push \ -value push \
-variable @opt_action -variable @opt_action
pack $w.action.push -anchor nw pack $w.action.push -anchor nw
radiobutton $w.action.none \ ${NS}::radiobutton $w.action.none \
-text [mc "Do Nothing Else Now"] \ -text [mc "Do Nothing Else Now"] \
-value none \ -value none \
-variable @opt_action -variable @opt_action
@ -85,6 +83,7 @@ constructor dialog {} {
bind $w <Visibility> [cb _visible] bind $w <Visibility> [cb _visible]
bind $w <Key-Escape> [list destroy $w] bind $w <Key-Escape> [list destroy $w]
bind $w <Key-Return> [cb _add]\;break bind $w <Key-Return> [cb _add]\;break
wm deiconify $top
tkwait window $w tkwait window $w
} }

View File

@ -23,34 +23,40 @@ field full_cache
field cached field cached
constructor dialog {} { constructor dialog {} {
global all_remotes M1B global all_remotes M1B use_ttk NS
make_toplevel top w make_dialog top w
wm title $top [append "[appname] ([reponame]): " [mc "Delete Branch Remotely"]] wm title $top [append "[appname] ([reponame]): " [mc "Delete Branch Remotely"]]
if {$top ne {.}} { if {$top ne {.}} {
wm geometry $top "+[winfo rootx .]+[winfo rooty .]" wm geometry $top "+[winfo rootx .]+[winfo rooty .]"
} }
label $w.header -text [mc "Delete Branch Remotely"] -font font_uibold ${NS}::label $w.header -text [mc "Delete Branch Remotely"] \
-font font_uibold -anchor center
pack $w.header -side top -fill x pack $w.header -side top -fill x
frame $w.buttons ${NS}::frame $w.buttons
button $w.buttons.delete -text [mc Delete] \ ${NS}::button $w.buttons.delete -text [mc Delete] \
-default active \ -default active \
-command [cb _delete] -command [cb _delete]
pack $w.buttons.delete -side right pack $w.buttons.delete -side right
button $w.buttons.cancel -text [mc "Cancel"] \ ${NS}::button $w.buttons.cancel -text [mc "Cancel"] \
-command [list destroy $w] -command [list destroy $w]
pack $w.buttons.cancel -side right -padx 5 pack $w.buttons.cancel -side right -padx 5
pack $w.buttons -side bottom -fill x -pady 10 -padx 10 pack $w.buttons -side bottom -fill x -pady 10 -padx 10
labelframe $w.dest -text [mc "From Repository"] ${NS}::labelframe $w.dest -text [mc "From Repository"]
if {$all_remotes ne {}} { if {$all_remotes ne {}} {
radiobutton $w.dest.remote_r \ ${NS}::radiobutton $w.dest.remote_r \
-text [mc "Remote:"] \ -text [mc "Remote:"] \
-value remote \ -value remote \
-variable @urltype -variable @urltype
if {$use_ttk} {
ttk::combobox $w.dest.remote_m -textvariable @remote \
-values $all_remotes -state readonly
} else {
eval tk_optionMenu $w.dest.remote_m @remote $all_remotes eval tk_optionMenu $w.dest.remote_m @remote $all_remotes
}
grid $w.dest.remote_r $w.dest.remote_m -sticky w grid $w.dest.remote_r $w.dest.remote_m -sticky w
if {[lsearch -sorted -exact $all_remotes origin] != -1} { if {[lsearch -sorted -exact $all_remotes origin] != -1} {
set remote origin set remote origin
@ -62,13 +68,11 @@ constructor dialog {} {
} else { } else {
set urltype url set urltype url
} }
radiobutton $w.dest.url_r \ ${NS}::radiobutton $w.dest.url_r \
-text [mc "Arbitrary Location:"] \ -text [mc "Arbitrary Location:"] \
-value url \ -value url \
-variable @urltype -variable @urltype
entry $w.dest.url_t \ ${NS}::entry $w.dest.url_t \
-borderwidth 1 \
-relief sunken \
-width 50 \ -width 50 \
-textvariable @url \ -textvariable @url \
-validate key \ -validate key \
@ -81,33 +85,30 @@ constructor dialog {} {
grid columnconfigure $w.dest 1 -weight 1 grid columnconfigure $w.dest 1 -weight 1
pack $w.dest -anchor nw -fill x -pady 5 -padx 5 pack $w.dest -anchor nw -fill x -pady 5 -padx 5
labelframe $w.heads -text [mc "Branches"] ${NS}::labelframe $w.heads -text [mc "Branches"]
listbox $w.heads.l \ slistbox $w.heads.l \
-height 10 \ -height 10 \
-width 70 \ -width 70 \
-listvariable @head_list \ -listvariable @head_list \
-selectmode extended \ -selectmode extended
-yscrollcommand [list $w.heads.sby set]
scrollbar $w.heads.sby -command [list $w.heads.l yview]
frame $w.heads.footer ${NS}::frame $w.heads.footer
label $w.heads.footer.status \ ${NS}::label $w.heads.footer.status \
-textvariable @status \ -textvariable @status \
-anchor w \ -anchor w \
-justify left -justify left
button $w.heads.footer.rescan \ ${NS}::button $w.heads.footer.rescan \
-text [mc "Rescan"] \ -text [mc "Rescan"] \
-command [cb _rescan] -command [cb _rescan]
pack $w.heads.footer.status -side left -fill x pack $w.heads.footer.status -side left -fill x
pack $w.heads.footer.rescan -side right pack $w.heads.footer.rescan -side right
pack $w.heads.footer -side bottom -fill x pack $w.heads.footer -side bottom -fill x
pack $w.heads.sby -side right -fill y
pack $w.heads.l -side left -fill both -expand 1 pack $w.heads.l -side left -fill both -expand 1
pack $w.heads -fill both -expand 1 -pady 5 -padx 5 pack $w.heads -fill both -expand 1 -pady 5 -padx 5
labelframe $w.validate -text [mc "Delete Only If"] ${NS}::labelframe $w.validate -text [mc "Delete Only If"]
radiobutton $w.validate.head_r \ ${NS}::radiobutton $w.validate.head_r \
-text [mc "Merged Into:"] \ -text [mc "Merged Into:"] \
-value head \ -value head \
-variable @checktype -variable @checktype
@ -115,7 +116,7 @@ constructor dialog {} {
trace add variable @head_list write [cb _write_head_list] trace add variable @head_list write [cb _write_head_list]
trace add variable @check_head write [cb _write_check_head] trace add variable @check_head write [cb _write_check_head]
grid $w.validate.head_r $w.validate.head_m -sticky w grid $w.validate.head_r $w.validate.head_m -sticky w
radiobutton $w.validate.always_r \ ${NS}::radiobutton $w.validate.always_r \
-text [mc "Always (Do not perform merge checks)"] \ -text [mc "Always (Do not perform merge checks)"] \
-value always \ -value always \
-variable @checktype -variable @checktype

View File

@ -14,15 +14,16 @@ field smarktop
field smarkbot field smarkbot
constructor new {i_w i_text args} { constructor new {i_w i_text args} {
global use_ttk NS
set w $i_w set w $i_w
set ctext $i_text set ctext $i_text
frame $w ${NS}::frame $w
label $w.l -text [mc Find:] ${NS}::label $w.l -text [mc Find:]
entry $w.ent -textvariable ${__this}::searchstring -background lightgreen entry $w.ent -textvariable ${__this}::searchstring -background lightgreen
button $w.bn -text [mc Next] -command [cb find_next] ${NS}::button $w.bn -text [mc Next] -command [cb find_next]
button $w.bp -text [mc Prev] -command [cb find_prev] ${NS}::button $w.bp -text [mc Prev] -command [cb find_prev]
checkbutton $w.cs -text [mc Case-Sensitive] \ ${NS}::checkbutton $w.cs -text [mc Case-Sensitive] \
-variable ${__this}::casesensitive -command [cb _incrsearch] -variable ${__this}::casesensitive -command [cb _incrsearch]
pack $w.l -side left pack $w.l -side left
pack $w.cs -side right pack $w.cs -side right

View File

@ -2,6 +2,7 @@
# Copyright (C) 2006, 2007 Shawn Pearce # Copyright (C) 2006, 2007 Shawn Pearce
proc do_windows_shortcut {} { proc do_windows_shortcut {} {
global _gitworktree
set fn [tk_getSaveFile \ set fn [tk_getSaveFile \
-parent . \ -parent . \
-title [append "[appname] ([reponame]): " [mc "Create Desktop Icon"]] \ -title [append "[appname] ([reponame]): " [mc "Create Desktop Icon"]] \
@ -15,7 +16,7 @@ proc do_windows_shortcut {} {
[info nameofexecutable] \ [info nameofexecutable] \
[file normalize $::argv0] \ [file normalize $::argv0] \
] \ ] \
[file dirname [file normalize [gitdir]]] [file normalize $_gitworktree]
} err]} { } err]} {
error_popup [strcat [mc "Cannot write shortcut:"] "\n\n$err"] error_popup [strcat [mc "Cannot write shortcut:"] "\n\n$err"]
} }
@ -23,7 +24,7 @@ proc do_windows_shortcut {} {
} }
proc do_cygwin_shortcut {} { proc do_cygwin_shortcut {} {
global argv0 global argv0 _gitworktree
if {[catch { if {[catch {
set desktop [exec cygpath \ set desktop [exec cygpath \
@ -56,7 +57,7 @@ proc do_cygwin_shortcut {} {
$sh -c \ $sh -c \
"CHERE_INVOKING=1 source /etc/profile;[sq $me] &" \ "CHERE_INVOKING=1 source /etc/profile;[sq $me] &" \
] \ ] \
[file dirname [file normalize [gitdir]]] [file normalize $_gitworktree]
} err]} { } err]} {
error_popup [strcat [mc "Cannot write shortcut:"] "\n\n$err"] error_popup [strcat [mc "Cannot write shortcut:"] "\n\n$err"]
} }

View File

@ -15,7 +15,7 @@ proc find_ssh_key {} {
} }
proc do_ssh_key {} { proc do_ssh_key {} {
global sshkey_title have_tk85 sshkey_fd global sshkey_title have_tk85 sshkey_fd use_ttk NS
set w .sshkey_dialog set w .sshkey_dialog
if {[winfo exists $w]} { if {[winfo exists $w]} {
@ -23,7 +23,7 @@ proc do_ssh_key {} {
return return
} }
toplevel $w Dialog $w
wm transient $w . wm transient $w .
set finfo [find_ssh_key] set finfo [find_ssh_key]
@ -35,9 +35,9 @@ proc do_ssh_key {} {
set gen_state disabled set gen_state disabled
} }
frame $w.header -relief flat ${NS}::frame $w.header
label $w.header.lbl -textvariable sshkey_title -anchor w ${NS}::label $w.header.lbl -textvariable sshkey_title -anchor w
button $w.header.gen -text [mc "Generate Key"] \ ${NS}::button $w.header.gen -text [mc "Generate Key"] \
-command [list make_ssh_key $w] -state $gen_state -command [list make_ssh_key $w] -state $gen_state
pack $w.header.lbl -side left -expand 1 -fill x pack $w.header.lbl -side left -expand 1 -fill x
pack $w.header.gen -side right pack $w.header.gen -side right
@ -46,14 +46,16 @@ proc do_ssh_key {} {
text $w.contents -width 60 -height 10 -wrap char -relief sunken text $w.contents -width 60 -height 10 -wrap char -relief sunken
pack $w.contents -fill both -expand 1 pack $w.contents -fill both -expand 1
if {$have_tk85} { if {$have_tk85} {
$w.contents configure -inactiveselectbackground darkblue set clr darkblue
if {$use_ttk} { set clr [ttk::style lookup . -selectbackground] }
$w.contents configure -inactiveselectbackground $clr
} }
frame $w.buttons ${NS}::frame $w.buttons
button $w.buttons.close -text [mc Close] \ ${NS}::button $w.buttons.close -text [mc Close] \
-default active -command [list destroy $w] -default active -command [list destroy $w]
pack $w.buttons.close -side right pack $w.buttons.close -side right
button $w.buttons.copy -text [mc "Copy To Clipboard"] \ ${NS}::button $w.buttons.copy -text [mc "Copy To Clipboard"] \
-command [list tk_textCopy $w.contents] -command [list tk_textCopy $w.contents]
pack $w.buttons.copy -side left pack $w.buttons.copy -side left
pack $w.buttons -side bottom -fill x -pady 5 -padx 5 pack $w.buttons -side bottom -fill x -pady 5 -padx 5

View File

@ -13,14 +13,16 @@ field units {}; # unit of progress
field meter {}; # current core git progress meter (if active) field meter {}; # current core git progress meter (if active)
constructor new {path} { constructor new {path} {
global use_ttk NS
set w $path set w $path
set w_l $w.l set w_l $w.l
set w_c $w.c set w_c $w.c
frame $w \ ${NS}::frame $w
-borderwidth 1 \ if {!$use_ttk} {
-relief sunken $w configure -borderwidth 1 -relief sunken
label $w_l \ }
${NS}::label $w_l \
-textvariable @status \ -textvariable @status \
-anchor w \ -anchor w \
-justify left -justify left
@ -37,12 +39,13 @@ method _oneline_pack {} {
} }
constructor two_line {path} { constructor two_line {path} {
global NS
set w $path set w $path
set w_l $w.l set w_l $w.l
set w_c $w.c set w_c $w.c
frame $w ${NS}::frame $w
label $w_l \ ${NS}::label $w_l \
-textvariable @status \ -textvariable @status \
-anchor w \ -anchor w \
-justify left -justify left

174
lib/themed.tcl Normal file
View File

@ -0,0 +1,174 @@
# Functions for supporting the use of themed Tk widgets in git-gui.
# Copyright (C) 2009 Pat Thoyts <patthoyts@users.sourceforge.net>
proc InitTheme {} {
# Create a color label style (bg can be overridden by widget option)
ttk::style layout Color.TLabel {
Color.Label.border -sticky news -children {
Color.label.fill -sticky news -children {
Color.Label.padding -sticky news -children {
Color.Label.label -sticky news}}}}
eval [linsert [ttk::style configure TLabel] 0 \
ttk::style configure Color.TLabel]
ttk::style configure Color.TLabel \
-borderwidth 0 -relief flat -padding 2
ttk::style map Color.TLabel -background {{} gold}
# We also need a padded label.
ttk::style configure Padded.TLabel \
-padding {5 5} -borderwidth 1 -relief solid
# We need a gold frame.
ttk::style layout Gold.TFrame {
Gold.Frame.border -sticky nswe -children {
Gold.Frame.fill -sticky nswe}}
ttk::style configure Gold.TFrame -background gold -relief flat
# listboxes should have a theme border so embed in ttk::frame
ttk::style layout SListbox.TFrame {
SListbox.Frame.Entry.field -sticky news -border true -children {
SListbox.Frame.padding -sticky news
}
}
}
proc gold_frame {w args} {
global use_ttk
if {$use_ttk} {
eval [linsert $args 0 ttk::frame $w -style Gold.TFrame]
} else {
eval [linsert $args 0 frame $w -background gold]
}
}
proc tlabel {w args} {
global use_ttk
if {$use_ttk} {
set cmd [list ttk::label $w -style Color.TLabel]
foreach {k v} $args {
switch -glob -- $k {
-activebackground {}
default { lappend cmd $k $v }
}
}
eval $cmd
} else {
eval [linsert $args 0 label $w]
}
}
# The padded label gets used in the about class.
proc paddedlabel {w args} {
global use_ttk
if {$use_ttk} {
eval [linsert $args 0 ttk::label $w -style Padded.TLabel]
} else {
eval [linsert $args 0 label $w \
-padx 5 -pady 5 \
-justify left \
-anchor w \
-borderwidth 1 \
-relief solid]
}
}
# Create a toplevel for use as a dialog.
# If available, sets the EWMH dialog hint and if ttk is enabled
# place a themed frame over the surface.
proc Dialog {w args} {
eval [linsert $args 0 toplevel $w -class Dialog]
pave_toplevel $w
return $w
}
# Tk toplevels are not themed - so pave it over with a themed frame to get
# the base color correct per theme.
proc pave_toplevel {w} {
global use_ttk
if {$use_ttk && ![winfo exists $w.!paving]} {
set paving [ttk::frame $w.!paving]
place $paving -x 0 -y 0 -relwidth 1 -relheight 1
lower $paving
}
}
# Create a scrolled listbox with appropriate border for the current theme.
# On many themes the border for a scrolled listbox needs to go around the
# listbox and the scrollbar.
proc slistbox {w args} {
global use_ttk NS
if {$use_ttk} {
set f [ttk::frame $w -style SListbox.TFrame -padding 2]
} else {
set f [frame $w -relief flat]
}
if {[catch {
if {$use_ttk} {
eval [linsert $args 0 listbox $f.list -relief flat \
-highlightthickness 0 -borderwidth 0]
} else {
eval [linsert $args 0 listbox $f.list]
}
${NS}::scrollbar $f.vs -command [list $f.list yview]
$f.list configure -yscrollcommand [list $f.vs set]
grid $f.list $f.vs -sticky news
grid rowconfigure $f 0 -weight 1
grid columnconfigure $f 0 -weight 1
bind $f.list <<ListboxSelect>> \
[list event generate $w <<ListboxSelect>>]
interp hide {} $w
interp alias {} $w {} $f.list
} err]} {
destroy $f
return -code error $err
}
return $w
}
# fetch the background color from a widget.
proc get_bg_color {w} {
global use_ttk
if {$use_ttk} {
set bg [ttk::style lookup [winfo class $w] -background]
} else {
set bg [$w cget -background]
}
return $bg
}
# ttk::spinbox didn't get added until 8.6
proc tspinbox {w args} {
global use_ttk
if {$use_ttk && [llength [info commands ttk::spinbox]] > 0} {
eval [linsert $args 0 ttk::spinbox $w]
} else {
eval [linsert $args 0 spinbox $w]
}
}
# Tk 8.6 provides a standard font selection dialog. This uses the native
# dialogs on Windows and MacOSX or a standard Tk dialog on X11.
proc tchoosefont {w title familyvar sizevar} {
if {[package vsatisfies [package provide Tk] 8.6]} {
upvar #0 $familyvar family
upvar #0 $sizevar size
tk fontchooser configure -parent $w -title $title \
-font [list $family $size] \
-command [list on_choosefont $familyvar $sizevar]
tk fontchooser show
} else {
choose_font::pick $w $title $familyvar $sizevar
}
}
# Called when the Tk 8.6 fontchooser selects a font.
proc on_choosefont {familyvar sizevar font} {
upvar #0 $familyvar family
upvar #0 $sizevar size
set font [font actual $font]
set family [dict get $font -family]
set size [dict get $font -size]
}
# Local variables:
# mode: tcl
# indent-tabs-mode: t
# tab-width: 4
# End:

View File

@ -16,53 +16,50 @@ field ask_branch 0; # ask for a revision
field ask_args 0; # ask for additional args field ask_args 0; # ask for additional args
constructor dialog {} { constructor dialog {} {
global repo_config global repo_config use_ttk NS
make_toplevel top w make_dialog top w
wm title $top [append "[appname] ([reponame]): " [mc "Add Tool"]] wm title $top [append "[appname] ([reponame]): " [mc "Add Tool"]]
if {$top ne {.}} { if {$top ne {.}} {
wm geometry $top "+[winfo rootx .]+[winfo rooty .]" wm geometry $top "+[winfo rootx .]+[winfo rooty .]"
wm transient $top . wm transient $top .
} }
label $w.header -text [mc "Add New Tool Command"] -font font_uibold ${NS}::label $w.header -text [mc "Add New Tool Command"] \
-font font_uibold -anchor center
pack $w.header -side top -fill x pack $w.header -side top -fill x
frame $w.buttons ${NS}::frame $w.buttons
checkbutton $w.buttons.global \ ${NS}::checkbutton $w.buttons.global \
-text [mc "Add globally"] \ -text [mc "Add globally"] \
-variable @add_global -variable @add_global
pack $w.buttons.global -side left -padx 5 pack $w.buttons.global -side left -padx 5
button $w.buttons.create -text [mc Add] \ ${NS}::button $w.buttons.create -text [mc Add] \
-default active \ -default active \
-command [cb _add] -command [cb _add]
pack $w.buttons.create -side right pack $w.buttons.create -side right
button $w.buttons.cancel -text [mc Cancel] \ ${NS}::button $w.buttons.cancel -text [mc Cancel] \
-command [list destroy $w] -command [list destroy $w]
pack $w.buttons.cancel -side right -padx 5 pack $w.buttons.cancel -side right -padx 5
pack $w.buttons -side bottom -fill x -pady 10 -padx 10 pack $w.buttons -side bottom -fill x -pady 10 -padx 10
labelframe $w.desc -text [mc "Tool Details"] ${NS}::labelframe $w.desc -text [mc "Tool Details"]
label $w.desc.name_cmnt -anchor w\ ${NS}::label $w.desc.name_cmnt -anchor w\
-text [mc "Use '/' separators to create a submenu tree:"] -text [mc "Use '/' separators to create a submenu tree:"]
grid x $w.desc.name_cmnt -sticky we -padx {0 5} -pady {0 2} grid x $w.desc.name_cmnt -sticky we -padx {0 5} -pady {0 2}
label $w.desc.name_l -text [mc "Name:"] ${NS}::label $w.desc.name_l -text [mc "Name:"]
set w_name $w.desc.name_t set w_name $w.desc.name_t
entry $w_name \ ${NS}::entry $w_name \
-borderwidth 1 \
-relief sunken \
-width 40 \ -width 40 \
-textvariable @name \ -textvariable @name \
-validate key \ -validate key \
-validatecommand [cb _validate_name %d %S] -validatecommand [cb _validate_name %d %S]
grid $w.desc.name_l $w_name -sticky we -padx {0 5} grid $w.desc.name_l $w_name -sticky we -padx {0 5}
label $w.desc.cmd_l -text [mc "Command:"] ${NS}::label $w.desc.cmd_l -text [mc "Command:"]
set w_cmd $w.desc.cmd_t set w_cmd $w.desc.cmd_t
entry $w_cmd \ ${NS}::entry $w_cmd \
-borderwidth 1 \
-relief sunken \
-width 40 \ -width 40 \
-textvariable @command -textvariable @command
grid $w.desc.cmd_l $w_cmd -sticky we -padx {0 5} -pady {0 3} grid $w.desc.cmd_l $w_cmd -sticky we -padx {0 5} -pady {0 3}
@ -70,30 +67,30 @@ constructor dialog {} {
grid columnconfigure $w.desc 1 -weight 1 grid columnconfigure $w.desc 1 -weight 1
pack $w.desc -anchor nw -fill x -pady 5 -padx 5 pack $w.desc -anchor nw -fill x -pady 5 -padx 5
checkbutton $w.confirm \ ${NS}::checkbutton $w.confirm \
-text [mc "Show a dialog before running"] \ -text [mc "Show a dialog before running"] \
-variable @confirm -command [cb _check_enable_dlg] -variable @confirm -command [cb _check_enable_dlg]
labelframe $w.dlg -labelwidget $w.confirm ${NS}::labelframe $w.dlg -labelwidget $w.confirm
checkbutton $w.dlg.askbranch \ ${NS}::checkbutton $w.dlg.askbranch \
-text [mc "Ask the user to select a revision (sets \$REVISION)"] \ -text [mc "Ask the user to select a revision (sets \$REVISION)"] \
-variable @ask_branch -state disabled -variable @ask_branch -state disabled
pack $w.dlg.askbranch -anchor w -padx 15 pack $w.dlg.askbranch -anchor w -padx 15
checkbutton $w.dlg.askargs \ ${NS}::checkbutton $w.dlg.askargs \
-text [mc "Ask the user for additional arguments (sets \$ARGS)"] \ -text [mc "Ask the user for additional arguments (sets \$ARGS)"] \
-variable @ask_args -state disabled -variable @ask_args -state disabled
pack $w.dlg.askargs -anchor w -padx 15 pack $w.dlg.askargs -anchor w -padx 15
pack $w.dlg -anchor nw -fill x -pady {0 8} -padx 5 pack $w.dlg -anchor nw -fill x -pady {0 8} -padx 5
checkbutton $w.noconsole \ ${NS}::checkbutton $w.noconsole \
-text [mc "Don't show the command output window"] \ -text [mc "Don't show the command output window"] \
-variable @no_console -variable @no_console
pack $w.noconsole -anchor w -padx 5 pack $w.noconsole -anchor w -padx 5
checkbutton $w.needsfile \ ${NS}::checkbutton $w.needsfile \
-text [mc "Run only if a diff is selected (\$FILENAME not empty)"] \ -text [mc "Run only if a diff is selected (\$FILENAME not empty)"] \
-variable @needs_file -variable @needs_file
pack $w.needsfile -anchor w -padx 5 pack $w.needsfile -anchor w -padx 5
@ -182,40 +179,38 @@ field w ; # widget path
field w_names ; # name list field w_names ; # name list
constructor dialog {} { constructor dialog {} {
global repo_config global_config system_config global repo_config global_config system_config use_ttk NS
load_config 1 load_config 1
make_toplevel top w make_dialog top w
wm title $top [append "[appname] ([reponame]): " [mc "Remove Tool"]] wm title $top [append "[appname] ([reponame]): " [mc "Remove Tool"]]
if {$top ne {.}} { if {$top ne {.}} {
wm geometry $top "+[winfo rootx .]+[winfo rooty .]" wm geometry $top "+[winfo rootx .]+[winfo rooty .]"
wm transient $top . wm transient $top .
} }
label $w.header -text [mc "Remove Tool Commands"] -font font_uibold ${NS}::label $w.header -text [mc "Remove Tool Commands"] \
-font font_uibold -anchor center
pack $w.header -side top -fill x pack $w.header -side top -fill x
frame $w.buttons ${NS}::frame $w.buttons
button $w.buttons.create -text [mc Remove] \ ${NS}::button $w.buttons.create -text [mc Remove] \
-default active \ -default active \
-command [cb _remove] -command [cb _remove]
pack $w.buttons.create -side right pack $w.buttons.create -side right
button $w.buttons.cancel -text [mc Cancel] \ ${NS}::button $w.buttons.cancel -text [mc Cancel] \
-command [list destroy $w] -command [list destroy $w]
pack $w.buttons.cancel -side right -padx 5 pack $w.buttons.cancel -side right -padx 5
pack $w.buttons -side bottom -fill x -pady 10 -padx 10 pack $w.buttons -side bottom -fill x -pady 10 -padx 10
frame $w.list ${NS}::frame $w.list
set w_names $w.list.l set w_names $w.list.l
listbox $w_names \ slistbox $w_names \
-height 10 \ -height 10 \
-width 30 \ -width 30 \
-selectmode extended \ -selectmode extended \
-exportselection false \ -exportselection false
-yscrollcommand [list $w.list.sby set]
scrollbar $w.list.sby -command [list $w.list.l yview]
pack $w.list.sby -side right -fill y
pack $w.list.l -side left -fill both -expand 1 pack $w.list.l -side left -fill both -expand 1
pack $w.list -fill both -expand 1 -pady 5 -padx 5 pack $w.list -fill both -expand 1 -pady 5 -padx 5
@ -232,7 +227,7 @@ constructor dialog {} {
} }
if {$local_cnt > 0} { if {$local_cnt > 0} {
label $w.colorlbl -foreground blue \ ${NS}::label $w.colorlbl -foreground blue \
-text [mc "(Blue denotes repository-local tools)"] -text [mc "(Blue denotes repository-local tools)"]
pack $w.colorlbl -fill x -pady 5 -padx 5 pack $w.colorlbl -fill x -pady 5 -padx 5
} }
@ -277,14 +272,14 @@ field is_ok 0; # ok to start
field argstr {}; # arguments field argstr {}; # arguments
constructor dialog {fullname} { constructor dialog {fullname} {
global M1B global M1B use_ttk NS
set title [get_config "guitool.$fullname.title"] set title [get_config "guitool.$fullname.title"]
if {$title eq {}} { if {$title eq {}} {
regsub {/} $fullname { / } title regsub {/} $fullname { / } title
} }
make_toplevel top w -autodelete 0 make_dialog top w -autodelete 0
wm title $top [append "[appname] ([reponame]): " $title] wm title $top [append "[appname] ([reponame]): " $title]
if {$top ne {.}} { if {$top ne {.}} {
wm geometry $top "+[winfo rootx .]+[winfo rooty .]" wm geometry $top "+[winfo rootx .]+[winfo rooty .]"
@ -297,7 +292,7 @@ constructor dialog {fullname} {
set prompt [mc "Run Command: %s" $command] set prompt [mc "Run Command: %s" $command]
} }
label $w.header -text $prompt -font font_uibold ${NS}::label $w.header -text $prompt -font font_uibold -anchor center
pack $w.header -side top -fill x pack $w.header -side top -fill x
set argprompt [get_config "guitool.$fullname.argprompt"] set argprompt [get_config "guitool.$fullname.argprompt"]
@ -311,12 +306,10 @@ constructor dialog {fullname} {
set argprompt [mc "Arguments"] set argprompt [mc "Arguments"]
} }
labelframe $w.arg -text $argprompt ${NS}::labelframe $w.arg -text $argprompt
set w_args $w.arg.txt set w_args $w.arg.txt
entry $w_args \ ${NS}::entry $w_args \
-borderwidth 1 \
-relief sunken \
-width 40 \ -width 40 \
-textvariable @argstr -textvariable @argstr
pack $w_args -padx 5 -pady 5 -fill both pack $w_args -padx 5 -pady 5 -fill both
@ -337,18 +330,18 @@ constructor dialog {fullname} {
pack $w.rev -anchor nw -fill both -expand 1 -pady 5 -padx 5 pack $w.rev -anchor nw -fill both -expand 1 -pady 5 -padx 5
} }
frame $w.buttons ${NS}::frame $w.buttons
if {$is_ask_revs} { if {$is_ask_revs} {
button $w.buttons.visualize \ ${NS}::button $w.buttons.visualize \
-text [mc Visualize] \ -text [mc Visualize] \
-command [cb _visualize] -command [cb _visualize]
pack $w.buttons.visualize -side left pack $w.buttons.visualize -side left
} }
button $w.buttons.ok \ ${NS}::button $w.buttons.ok \
-text [mc OK] \ -text [mc OK] \
-command [cb _start] -command [cb _start]
pack $w.buttons.ok -side right pack $w.buttons.ok -side right
button $w.buttons.cancel \ ${NS}::button $w.buttons.cancel \
-text [mc "Cancel"] \ -text [mc "Cancel"] \
-command [cb _cancel] -command [cb _cancel]
pack $w.buttons.cancel -side right -padx 5 pack $w.buttons.cancel -side right -padx 5

View File

@ -91,50 +91,55 @@ trace add variable push_remote write \
proc do_push_anywhere {} { proc do_push_anywhere {} {
global all_remotes current_branch global all_remotes current_branch
global push_urltype push_remote push_url push_thin push_tags global push_urltype push_remote push_url push_thin push_tags
global push_force global push_force use_ttk NS
set w .push_setup set w .push_setup
toplevel $w toplevel $w
wm withdraw $w
wm geometry $w "+[winfo rootx .]+[winfo rooty .]" wm geometry $w "+[winfo rootx .]+[winfo rooty .]"
pave_toplevel $w
label $w.header -text [mc "Push Branches"] -font font_uibold ${NS}::label $w.header -text [mc "Push Branches"] \
-font font_uibold -anchor center
pack $w.header -side top -fill x pack $w.header -side top -fill x
frame $w.buttons ${NS}::frame $w.buttons
button $w.buttons.create -text [mc Push] \ ${NS}::button $w.buttons.create -text [mc Push] \
-default active \ -default active \
-command [list start_push_anywhere_action $w] -command [list start_push_anywhere_action $w]
pack $w.buttons.create -side right pack $w.buttons.create -side right
button $w.buttons.cancel -text [mc "Cancel"] \ ${NS}::button $w.buttons.cancel -text [mc "Cancel"] \
-default normal \ -default normal \
-command [list destroy $w] -command [list destroy $w]
pack $w.buttons.cancel -side right -padx 5 pack $w.buttons.cancel -side right -padx 5
pack $w.buttons -side bottom -fill x -pady 10 -padx 10 pack $w.buttons -side bottom -fill x -pady 10 -padx 10
labelframe $w.source -text [mc "Source Branches"] ${NS}::labelframe $w.source -text [mc "Source Branches"]
listbox $w.source.l \ slistbox $w.source.l \
-height 10 \ -height 10 \
-width 70 \ -width 70 \
-selectmode extended \ -selectmode extended
-yscrollcommand [list $w.source.sby set]
foreach h [load_all_heads] { foreach h [load_all_heads] {
$w.source.l insert end $h $w.source.l insert end $h
if {$h eq $current_branch} { if {$h eq $current_branch} {
$w.source.l select set end $w.source.l select set end
} }
} }
scrollbar $w.source.sby -command [list $w.source.l yview]
pack $w.source.sby -side right -fill y
pack $w.source.l -side left -fill both -expand 1 pack $w.source.l -side left -fill both -expand 1
pack $w.source -fill both -expand 1 -pady 5 -padx 5 pack $w.source -fill both -expand 1 -pady 5 -padx 5
labelframe $w.dest -text [mc "Destination Repository"] ${NS}::labelframe $w.dest -text [mc "Destination Repository"]
if {$all_remotes ne {}} { if {$all_remotes ne {}} {
radiobutton $w.dest.remote_r \ ${NS}::radiobutton $w.dest.remote_r \
-text [mc "Remote:"] \ -text [mc "Remote:"] \
-value remote \ -value remote \
-variable push_urltype -variable push_urltype
if {$use_ttk} {
ttk::combobox $w.dest.remote_m -textvariable push_remote \
-values $all_remotes
} else {
eval tk_optionMenu $w.dest.remote_m push_remote $all_remotes eval tk_optionMenu $w.dest.remote_m push_remote $all_remotes
}
grid $w.dest.remote_r $w.dest.remote_m -sticky w grid $w.dest.remote_r $w.dest.remote_m -sticky w
if {[lsearch -sorted -exact $all_remotes origin] != -1} { if {[lsearch -sorted -exact $all_remotes origin] != -1} {
set push_remote origin set push_remote origin
@ -145,13 +150,11 @@ proc do_push_anywhere {} {
} else { } else {
set push_urltype url set push_urltype url
} }
radiobutton $w.dest.url_r \ ${NS}::radiobutton $w.dest.url_r \
-text [mc "Arbitrary Location:"] \ -text [mc "Arbitrary Location:"] \
-value url \ -value url \
-variable push_urltype -variable push_urltype
entry $w.dest.url_t \ ${NS}::entry $w.dest.url_t \
-borderwidth 1 \
-relief sunken \
-width 50 \ -width 50 \
-textvariable push_url \ -textvariable push_url \
-validate key \ -validate key \
@ -166,16 +169,16 @@ proc do_push_anywhere {} {
grid columnconfigure $w.dest 1 -weight 1 grid columnconfigure $w.dest 1 -weight 1
pack $w.dest -anchor nw -fill x -pady 5 -padx 5 pack $w.dest -anchor nw -fill x -pady 5 -padx 5
labelframe $w.options -text [mc "Transfer Options"] ${NS}::labelframe $w.options -text [mc "Transfer Options"]
checkbutton $w.options.force \ ${NS}::checkbutton $w.options.force \
-text [mc "Force overwrite existing branch (may discard changes)"] \ -text [mc "Force overwrite existing branch (may discard changes)"] \
-variable push_force -variable push_force
grid $w.options.force -columnspan 2 -sticky w grid $w.options.force -columnspan 2 -sticky w
checkbutton $w.options.thin \ ${NS}::checkbutton $w.options.thin \
-text [mc "Use thin pack (for slow network connections)"] \ -text [mc "Use thin pack (for slow network connections)"] \
-variable push_thin -variable push_thin
grid $w.options.thin -columnspan 2 -sticky w grid $w.options.thin -columnspan 2 -sticky w
checkbutton $w.options.tags \ ${NS}::checkbutton $w.options.tags \
-text [mc "Include tags"] \ -text [mc "Include tags"] \
-variable push_tags -variable push_tags
grid $w.options.tags -columnspan 2 -sticky w grid $w.options.tags -columnspan 2 -sticky w
@ -191,5 +194,6 @@ proc do_push_anywhere {} {
bind $w <Key-Escape> "destroy $w" bind $w <Key-Escape> "destroy $w"
bind $w <Key-Return> [list start_push_anywhere_action $w] bind $w <Key-Return> [list start_push_anywhere_action $w]
wm title $w [append "[appname] ([reponame]): " [mc "Push"]] wm title $w [append "[appname] ([reponame]): " [mc "Push"]]
wm deiconify $w
tkwait window $w tkwait window $w
} }

View File

@ -18,9 +18,9 @@ proc win32_create_lnk {lnk_path lnk_exec lnk_dir} {
eval [list exec wscript.exe \ eval [list exec wscript.exe \
/E:jscript \ /E:jscript \
/nologo \ /nologo \
[file join $oguilib win32_shortcut.js] \ [file nativename [file join $oguilib win32_shortcut.js]] \
$lnk_path \ $lnk_path \
[file join $oguilib git-gui.ico] \ [file nativename [file join $oguilib git-gui.ico]] \
$lnk_dir \ $lnk_dir \
$lnk_exec] $lnk_args $lnk_exec] $lnk_args
} }

834
po/de.po

File diff suppressed because it is too large Load Diff

694
po/fr.po

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

630
po/it.po

File diff suppressed because it is too large Load Diff

661
po/ja.po

File diff suppressed because it is too large Load Diff

1352
po/sv.po

File diff suppressed because it is too large Load Diff

View File

@ -13,10 +13,11 @@ if { $argc >=2 && [lindex $argv 0] == "--working-dir" } {
incr argc -2 incr argc -2
} }
set bindir [file dirname \ set basedir [file dirname \
[file dirname \ [file dirname \
[file dirname [info script]]]] [file dirname [info script]]]]
set bindir [file join $bindir bin] set bindir [file join $basedir bin]
set bindir "$bindir;[file join $basedir mingw bin]"
regsub -all ";" $bindir "\\;" bindir regsub -all ";" $bindir "\\;" bindir
set env(PATH) "$bindir;$env(PATH)" set env(PATH) "$bindir;$env(PATH)"
unset bindir unset bindir