Compare commits

..

78 commits

Author SHA1 Message Date
Hylke Bons
86b8ca020a
Update Dockerfile 2023-08-14 13:25:45 +02:00
Hylke Bons
37ce57e12a
Update .travis.yml 2023-08-14 13:04:48 +02:00
Hylke Bons
e2618f793e
Update Dockerfile 2023-08-14 13:04:22 +02:00
Hylke Bons
63fe3710e5
Update SHA-256 for Bitbucket preset 2023-08-14 10:33:30 +02:00
Hylke Bons
6cfd602259
Update SHA-256 for GitHub preset 2023-08-14 10:29:10 +02:00
Hylke Bons
be9e12e0fe
Merge pull request #1959 from jimmac/master
update app icon
2023-01-24 15:01:00 +01:00
Hylke Bons
01c180d588
Merge pull request #1994 from uenz/fix/BuildMacOS
Fixed link errors and pack release
2023-01-24 14:59:39 +01:00
Hylke Bons
54eff3bee1
Merge pull request #1992 from uenz/fix/MacOSAddVentura
Update InstallationInfo.cs
2023-01-24 14:57:58 +01:00
uenz
1fb943b815 Fixed link errors and pack release 2022-11-05 13:05:22 +01:00
uenz
35951f0805 Update InstallationInfo.cs
Added Ventura
2022-11-02 16:46:16 +01:00
Hylke Bons
6ebda3a1d6
Merge pull request #1985 from uenz/fix/AboutController
Define security protocol
2021-11-01 22:22:26 +01:00
Hylke Bons
b65e0fed53
Merge pull request #1980 from uenz/fix/CryptoRepo
Fix for issue #1958
2021-11-01 22:20:23 +01:00
uenz
903382fd29 Undone changes in spaces 2021-11-01 20:37:32 +01:00
uenz
1cdbe02e3d Define security protocol 2021-11-01 20:33:42 +01:00
uenz
347ce97ea7
Update Git.Fetcher.cs
Added comment
2021-11-01 13:32:47 +01:00
Hylke Bons
7c118ee1b0
Merge pull request #1981 from uenz/fix/MacOSSystemVersion
Updated macOS version names
2021-10-31 17:33:35 +01:00
Andre Spahlinger
1c789aba1e Merge branch 'fix/MacOSSystemVersion' of https://github.com/uenz/SparkleShare into fix/MacOSSystemVersion 2021-10-28 12:03:23 +02:00
Andre Spahlinger
02ded513a7 Cleanup 2021-10-28 06:32:13 +02:00
uenz
3f1b02fe0c Create directory if parts of path not exists 2021-10-27 22:21:50 +02:00
uenz
ebc489bcc7 Updated macOS version names 2021-10-25 14:13:18 +02:00
Andre Spahlinger
85a65da878 Fix for issue #1958 2021-10-22 23:22:53 +02:00
Hylke Bons
85f3d449be
Merge pull request #1978 from kjyv/master
Poll for updates when waking up from sleep state (macOS)
2021-09-18 20:37:50 +02:00
Stefan Bethge
5ee0fe016f mac: poll for updates when waking up from sleep state 2021-09-12 18:47:36 +02:00
Hylke Bons
631f56386c
Merge pull request #1975 from uenz/fix/SetupDialogShowFiles
Fix crash when pressing show files
2021-08-03 13:47:56 +02:00
uenz
07f954cc72 Fix crash when pressing show files 2021-07-22 16:37:20 +02:00
Hylke Bons
af8a521aec
Merge pull request #1970 from markusstoll/bugfixes/mac-improve-fswatcher
Mac FileWatcher - reduce load
2021-02-15 19:55:56 +01:00
Markus Stoll
fbd3c79674 Drop changes in .git folder immediately, reduces load 2021-02-15 14:27:40 +01:00
Hylke Bons
cb08a35bf9
Merge pull request #1969 from markusstoll/bugfixes/mac-fix-encodingproblems
Bugfixes/mac fix encodingproblems
2021-02-15 14:10:00 +01:00
Hylke Bons
ba49f81af6
Merge branch 'master' into bugfixes/mac-fix-encodingproblems 2021-02-15 11:59:38 +01:00
Hylke Bons
dac6783a0e
Merge pull request #1967 from markusstoll/bugfixes/macos-increase-gitversion
macOS: increase git version to 29.2-2 and improve handling of download
2021-02-15 10:55:00 +01:00
Hylke Bons
c2fd750ad5
Merge branch 'master' into bugfixes/macos-increase-gitversion 2021-02-15 10:35:06 +01:00
Hylke Bons
948e14fe5e
Merge pull request #1965 from markusstoll/master
Fix problem on renaming HEAD file
2021-02-15 10:33:06 +01:00
Hylke Bons
954f1e6b1b
Merge pull request #1964 from markusstoll/bugfixes/osx_compile
Compile under OSX
2021-02-15 10:29:22 +01:00
Markus Stoll
07bb84318d Set UTF8 encoding for git commands, fixes 2021-02-14 20:16:34 +01:00
Markus Stoll
72603c5bef Improve git update handling 2021-02-14 20:03:21 +01:00
Markus Stoll
741ea0612a Remove conversion for utf8 encoded strings on macOS - with proper settings on git command things are already and would get worse if default encoding is ASCII (which seems to be the case for current VisualStudio 2019) 2021-02-14 19:27:22 +01:00
Markus Stoll
613625c5bf Set UTF8 encoding for git commands 2021-02-14 19:13:17 +01:00
Markus Stoll
37d49a990c Update git to version 2.29.2 2021-02-14 18:58:28 +01:00
Markus Stoll
6ca60c074c Fix to make SparkleShare compile under current OSX and current VisualStudio
Configuration ReleaseMac now works fine again for creating Standalone Release
2021-02-14 10:08:28 +01:00
Markus Stoll
ecd84c6b87 GIT Repostory, dealing with git modules - avoid File conflict on renaming HEAD file 2021-02-04 15:02:30 +01:00
Jakub Steiner
672442b8ab update app icon
- use a single size SVG
- use a commonly used nightly variant
2020-11-30 18:38:14 +01:00
Hylke Bons
23d7166012 Update release notes 2020-11-28 18:17:54 +01:00
Hylke Bons
1a31bc2a5a Update release notes 2020-11-28 18:10:54 +01:00
Hylke Bons
5f8c858658 Add micro bit of version number 2020-11-28 18:10:54 +01:00
Hylke Bons
b0c2c48dd3 ui: More helpful error message when missing AppIndicator 2020-11-28 18:10:54 +01:00
Hylke Bons
c93ec2447c Bump version to 3.38 2020-11-28 18:10:54 +01:00
Hylke Bons
38a7400536
Merge pull request #1955 from MalteKiefer/update-gravatar-cert-fingerprint
updated gravatar cert fingerprint
2020-11-28 18:09:42 +01:00
Hylke Bons
73b849da84
Merge branch 'master' into update-gravatar-cert-fingerprint 2020-11-28 17:37:21 +01:00
Hylke Bons
e9c9cf3f82
Merge pull request #1954 from MalteKiefer/feature-remove-planio
removed planio
2020-10-31 12:26:36 +01:00
Malte Kiefer
8e0b5e4b58 updated gravatar cert fingerprint 2020-10-23 06:04:52 +02:00
Malte Kiefer
c8e398bba2 removed planio 2020-10-23 05:31:34 +02:00
Hylke Bons
55c4e5e32e sparkles git: Replace hardcoded 'master' string 2020-06-23 17:18:11 +02:00
Hylke Bons
c1b62da1c5
Merge pull request #1928 from MalteKiefer/master
added LibRAavatar
2020-02-15 22:41:19 +01:00
Malte Kiefer
959a235799 added myself as Author 2020-02-15 10:14:02 +01:00
Malte Kiefer
a22152e1ab removed fingerprint check for libravatar 2020-02-15 04:31:44 +01:00
Malte Kiefer
9b3e95eff3 added support for libRAvatar 2020-02-14 21:17:56 +01:00
Malte Kiefer
3970c634a6 added libravatar 2020-02-14 20:37:45 +01:00
Malte Kiefer
13ed737818 update Gravatar Fingerprint 2020-02-14 20:04:44 +01:00
Hylke Bons
21c668491e build: Bump minimum macOS version to 10.9 2020-01-25 12:55:07 +01:00
Hylke Bons
a30b223180
Update README.md 2020-01-25 12:51:34 +01:00
Hylke Bons
f1df983b87 build: Bump minimum macOS version to 10.9 2020-01-25 12:42:32 +01:00
Hylke Bons
8d8fb10397
Create FUNDING.yml 2020-01-24 22:42:25 +01:00
Hylke Bons
cf446c00f1
travis: Force non-interactive environment 2019-05-25 11:18:00 +01:00
Hylke Bons
7ae9219fc7
build: Also bump Ubuntu in build script 2019-05-25 10:30:14 +01:00
Hylke Bons
2be2063a36
travis: Always use latest Ubuntu LTS to build 2019-05-25 10:17:36 +01:00
Hylke Bons
c50b1bad25
Merge pull request #1889 from jack1142/master
Update of license links in README.md
2019-01-17 11:53:10 +01:00
jack1142
d9a709ffff
Update AboutController.cs 2019-01-16 15:36:42 +01:00
jack1142
4619f9fbd8
Update README.md 2019-01-16 15:31:11 +01:00
Hylke Bons
c0ed43ff9b
Merge pull request #1884 from City-busz/patch-3
Add X-AppStream-Ignore property to autostart file
2018-12-26 15:22:56 +01:00
Balló György
31d47a7926
Add X-AppStream-Ignore property to autostart file
This makes appstream-generator to ignore this desktop entry.
2018-12-26 15:08:22 +01:00
Hylke Bons
9dac3a27c2
Merge pull request #1883 from City-busz/patch-2
Don't use legacy path for AppStream metainfo file
2018-12-26 12:45:11 +01:00
Hylke Bons
2207328611
Merge pull request #1882 from City-busz/patch-1
Fix AppStream metadata validation
2018-12-25 10:44:48 +01:00
Balló György
e6775a462a
Don't use legacy path for AppStream metainfo file
Metainfo files should be installed into /usr/share/metainfo.
2018-12-25 10:01:04 +01:00
Balló György
e0c4e972d0
Fix AppStream metadata validation 2018-12-25 09:53:41 +01:00
Hylke Bons
cf313dce4d
Merge pull request #1875 from Ppjet6/prevent-interactive-editor
Prevent blocking on interactive $EDITOR
2018-10-05 18:15:39 +01:00
Maxime “pep” Buquet
feb4e3d850
Prevent blocking on interactive $EDITOR
It happens that when merging, git calls out an interactive $EDITOR and
waits for user input. This causes SparkleShare to block as well.

Signed-off-by: Maxime “pep” Buquet <pep@collabora.com>
2018-10-05 17:41:20 +01:00
Hylke Bons
3b4fccd6a2
Update README.md 2018-09-29 20:53:16 +01:00
Hylke Bons
a82644e263 tests: Add simple unit tests 2018-09-01 11:06:54 +01:00
111 changed files with 2105 additions and 2825 deletions

1
.github/AUTHORS.md vendored
View file

@ -20,6 +20,7 @@ Code:
Luis Cordova <cordoval@gmail.com>
Łukasz Jernaś <deejay1@srem.org>
Markus Stoll <post@mstoll.de>
Malte Kiefer <malte.kiefer@mailgermania.de>
Michael Monreal <michael.monreal@gmail.com>
Nick Richards <nick@nickr.org>
Oleg Khlystov <pktfag@gmail.com>

1
.github/FUNDING.yml vendored Normal file
View file

@ -0,0 +1 @@
github: hbons

4
.gitignore vendored
View file

@ -18,8 +18,8 @@ obj/
git-*
Sparkles/InstallationInfo.Directory.cs
SparkleShare/Linux/sparkleshare
SparkleShare/Mac/git/*
SparkleShare/Mac/git*
SparkleShare/Mac/*.tar.gz
/sparkleshare-*
desktop.ini
_ReSharper.*
@ -29,6 +29,7 @@ _ReSharper.*
*.wxs
*.dotCover
SparkleShare/Windows/build/
.vs/
# NuGet Packages
*.nupkg
@ -36,3 +37,4 @@ SparkleShare/Windows/build/
**/packages/*
# except build/, which is used as an MSBuild target.
!**/packages/build/

View file

@ -9,7 +9,7 @@ matrix:
sudo: required
before_install:
- if [[ "$TRAVIS_OS_NAME" == "linux" ]]; then docker pull ubuntu:17.10 ; fi
- if [[ "$TRAVIS_OS_NAME" == "linux" ]]; then docker pull ubuntu:xenial ; fi
- if [[ "$TRAVIS_OS_NAME" == "osx" ]]; then wget https://dl.xamarin.com/XamarinforMac/Mac/xamarin.mac-3.0.0.393.pkg ; fi
- if [[ "$TRAVIS_OS_NAME" == "osx" ]]; then sudo installer -pkg xamarin.mac*.pkg -target / ; fi

View file

@ -1,9 +1,10 @@
# [SparkleShare](https://www.sparkleshare.org/)
[SparkleShare](https://www.sparkleshare.org/) is a file sharing and collaboration app. It works just like Dropbox, and you can run it on your own server. It's available for Linux distributions, macOS, and Windows. [Support the project on Patreon](https://www.patreon.com/SparkleShare).
[SparkleShare](https://www.sparkleshare.org/) is a file sharing and collaboration app. It works just like Dropbox, and you can run it on your own server. It's available for Linux distributions, macOS, and Windows.
![Banner](https://raw.githubusercontent.com/hbons/SparkleShare/master/SparkleShare/Common/Images/readme-banner.png)
You can support this project through [💕 GitHub Sponsors](https://github.com/sponsors/hbons).
## How does it work?
@ -20,6 +21,7 @@ flatpak install flathub org.sparkleshare.SparkleShare
Now you can run SparkleShare from the apps menu.
**Note:** by default SparkleShare uses an AppIndicator status icon on Linux. If you use GNOME on a distribution other than Ubuntu, please install the [AppIndicator extension](https://extensions.gnome.org/extension/615/appindicator-support/). If you don't use GNOME, you can start SparkleShare with `--status-icon=gtk`.
## Install on macOS
@ -33,12 +35,10 @@ Under the hood SparkleShare uses the version control system [Git](https://git-sc
## Build from source
`SparkleShare` is Free and Open Source software and licensed under the [GNU GPLv3 or later](legal/License_for_SparkleShare.txt). You are welcome to change and redistribute it under certain conditions. Its library `Sparkles` is licensed under the [GNU LGPLv3 or later](legal/License_for_Sparkles.txt).
`SparkleShare` is Free and Open Source software and licensed under the [GNU GPLv3 or later](LICENSE.md). You are welcome to change and redistribute it under certain conditions. Its library `Sparkles` is licensed under the [GNU LGPLv3 or later](LICENSE_Sparkles.md).
Here are instructions to build SparkleShare on [Linux distributions](SparkleShare/Linux/README.md), [macOS](SparkleShare/Mac/README.md), and [Windows](SparkleShare/Windows/README.md).
**Note:** by default SparkleShare uses an AppIndicator status icon on Linux. If you use GNOME on a distribution other than Ubuntu, please install the [AppIndicator extension](https://extensions.gnome.org/extension/615/appindicator-support/). If you don't use GNOME, you can start SparkleShare with `--status-icon=gtk`.
[![Build Status](https://travis-ci.org/hbons/SparkleShare.svg?branch=master)](https://travis-ci.org/hbons/SparkleShare)
[![Join the chat at https://gitter.im/hbons/SparkleShare](https://badges.gitter.im/hbons/SparkleShare.svg)](https://gitter.im/hbons/SparkleShare?utm_source=badge&utm_medium=badge&utm_campaign=pr-badge&utm_content=badge)

View file

@ -1,3 +1,12 @@
3.38.0 (Sun 29 Nov, 2020):
- Added support for LibRAavatar
- Updated Gravatar cert fingerprint
- Removed planio from supported presets
- Support default branches that are not named 'master'
- Added support for nightly Flatpak builds
3.28.0 (Sat 14 Jul, 2018):
Fixed a bunch of crashes and lots of under-the-hood improvements.

View file

@ -32,7 +32,7 @@ namespace SparkleShare {
public delegate void UpdateLabelEventDelegate (string text);
public readonly string WebsiteLinkAddress = "https://www.sparkleshare.org/";
public readonly string CreditsLinkAddress = "https://github.com/hbons/SparkleShare/blob/master/legal/Authors.txt";
public readonly string CreditsLinkAddress = "https://github.com/hbons/SparkleShare/blob/master/.github/AUTHORS.md";
public readonly string ReportProblemLinkAddress = "https://www.github.com/hbons/SparkleShare/issues";
public readonly string DebugLogLinkAddress = "file://" + SparkleShare.Controller.Config.LogFilePath;
@ -61,6 +61,8 @@ namespace SparkleShare {
UpdateLabelEvent ("Checking for updates…");
Thread.Sleep (500);
ServicePointManager.SecurityProtocol = SecurityProtocolType.Tls12;
var web_client = new WebClient ();
var uri = new Uri ("https://www.sparkleshare.org/version");

View file

@ -32,10 +32,11 @@ namespace SparkleShare
static List<string> skipped_avatars = new List<string> ();
public static string GetAvatar (string email, int size, string target_path)
public static string GetAvatar (string email, int size, string target_path, string provider)
{
#if __MonoCS__
ServicePointManager.ServerCertificateValidationCallback = GetAvatarValidationCallBack;
if (provider == "gravatar")
ServicePointManager.ServerCertificateValidationCallback = GetGravatarValidationCallBack;
#endif
email = email.ToLower ();
@ -68,7 +69,12 @@ namespace SparkleShare
}
var client = new WebClient ();
string url = "https://gravatar.com/avatar/" + email.MD5 () + ".png?s=" + size + "&d=404";
string url = "";
if (provider == "libravatar")
url = "https://seccdn.libravatar.org/avatar/" + email.MD5 () + ".png?s=" + size + "&d=404";
else
url = "https://secure.gravatar.com/avatar/" + email.MD5 () + ".png?s=" + size + "&d=404";
try {
byte [] buffer = client.DownloadData (url);
@ -107,7 +113,7 @@ namespace SparkleShare
}
private static bool GetAvatarValidationCallBack (Object sender,
private static bool GetGravatarValidationCallBack (Object sender,
X509Certificate certificate, X509Chain chain, SslPolicyErrors errors)
{
X509Certificate2 certificate2 = new X509Certificate2 (certificate.GetRawCertData ());
@ -115,9 +121,10 @@ namespace SparkleShare
// On some systems (mostly Linux) we can't assume the needed certificates are
// available, so we have to check the certificate's SHA-1 fingerprint manually.
//
// SHA1 fingerprinter obtained from https://www.gravatar.com/ on Oct 16 2015
// Set to expire on Oct 14 2018
string gravatar_cert_fingerprint = "1264B3F00814C6077D3853238771EE67FB6321C9";
// SHA1 fingerprinter obtained from https://www.gravatar.com/ on Oct 23 2020
// Set to expire on Nov 16 2022
string gravatar_cert_fingerprint = "846963703FD297724E91BDF47FFE4BC19E93EA15";
if (!certificate2.Thumbprint.Equals (gravatar_cert_fingerprint)) {
Logger.LogInfo ("Avatars", "Invalid certificate for https://www.gravatar.com/");

View file

@ -83,10 +83,10 @@ namespace SparkleShare {
public event Action ShowEventLogWindowEvent = delegate { };
public event FolderFetchedEventHandler FolderFetched = delegate { };
public delegate void FolderFetchedEventHandler (string remote_url);
public delegate void FolderFetchedEventHandler (string remote_url, string [] warnings);
public event FolderFetchErrorHandler FolderFetchError = delegate { };
public delegate void FolderFetchErrorHandler (string remote_url, string error, string error_details);
public delegate void FolderFetchErrorHandler (string remote_url, string [] errors);
public event FolderFetchingHandler FolderFetching = delegate { };
public delegate void FolderFetchingHandler (double percentage, double speed, string information);
@ -153,6 +153,16 @@ namespace SparkleShare {
}
}
public string AvatarsProvider {
get {
string avatars_provider_string = Config.GetConfigOption ("avatars_provider");
if (avatars_provider_string == null)
return "gravatar";
return avatars_provider_string;
}
}
// Path where the plugins are kept
public abstract string PresetsPath { get; }
@ -270,7 +280,7 @@ namespace SparkleShare {
}
if (FirstRun) {
ShowSetupWindow (PageType.User);
ShowSetupWindow (PageType.Setup);
} else {
new Thread (() => {
@ -286,7 +296,7 @@ namespace SparkleShare {
public void ShowSetupWindow (PageType page_type)
{
ShowSetupWindowEvent (PageType.User);
ShowSetupWindowEvent (page_type);
}
@ -451,8 +461,16 @@ namespace SparkleShare {
};
repo.NewChangeSet += delegate (ChangeSet change_set) {
if (AvatarsEnabled)
change_set.User.AvatarFilePath = Avatars.GetAvatar (change_set.User.Email, 48, Config.DirectoryPath);
if (AvatarsEnabled) {
string provider = "gravatar";
if (AvatarsProvider == "libravatar")
provider = AvatarsProvider;
change_set.User.AvatarFilePath = Avatars.GetAvatar (change_set.User.Email, 48, Config.DirectoryPath, provider);
}
NotificationRaised (change_set);
};
@ -554,13 +572,13 @@ namespace SparkleShare {
}
public void StartFetcher (FetcherInfo info)
public void StartFetcher (SparkleFetcherInfo info)
{
string canonical_name = Path.GetFileName (info.Address.AbsolutePath);
string backend = info.Backend;
string canonical_name = Path.GetFileName (info.RemotePath);
string backend = info.Backend;
if (string.IsNullOrEmpty (backend))
backend = BaseFetcher.GetBackend (info.Address.ToString ());
backend = BaseFetcher.GetBackend (info.Address);
info.TargetDirectory = Path.Combine (Config.TmpPath, canonical_name);
@ -576,8 +594,8 @@ namespace SparkleShare {
Logger.LogInfo ("Controller",
"Failed to load '" + backend + "' backend for '" + canonical_name + "' " + e.Message);
FolderFetchError (info.Address.ToString ().Replace (@"\", "/"),
"Could not find backend", "\"" + backend + "\" is missing.");
FolderFetchError (Path.Combine (info.Address, info.RemotePath).Replace (@"\", "/"),
new string [] {"Failed to load \"" + backend + "\" backend for \"" + canonical_name + "\""});
return;
}
@ -590,10 +608,10 @@ namespace SparkleShare {
}
void FetcherFinishedDelegate (StorageType storage_type)
void FetcherFinishedDelegate (StorageType storage_type, string [] warnings)
{
if (storage_type == StorageType.Unknown) {
ShowSetupWindow (PageType.Storage);
ShowSetupWindow (PageType.StorageSetup);
return;
}
@ -606,38 +624,10 @@ namespace SparkleShare {
}
void FetcherFailedDelegate (FetchResult result)
void FetcherFailedDelegate ()
{
string error = "Something went wrong";
string error_details = "Sorry, we're not quite sure what happened.";
if (result ==FetchResult.NoNetwork) {
error = "Could not connect to the internet";
error_details = "Please reconnect and try again.";
}
if (result == FetchResult.HostNotSupported) {
error = "Host not supported";
error_details = "The host wasn't set up right.";
}
if (result == FetchResult.HostChanged) {
error = "The host has changed its identity";
error_details = "Please contact its administrator.";
}
if (result == FetchResult.NotAuthenticated) {
error = "Could not authenticate";
error_details = "Please make sure the host knows your Public Key.";
}
if (result == FetchResult.UserInterrupted) {
error = "Cancelled.";
error_details = "";
}
FolderFetchError (this.fetcher.RemoteUrl.ToString (), error, error_details);
StopFetcher (); // TODO is this needed?
FolderFetchError (this.fetcher.RemoteUrl.ToString (), this.fetcher.Errors);
StopFetcher ();
}
@ -716,7 +706,7 @@ namespace SparkleShare {
RepositoriesLoaded = true;
FolderListChanged ();
FolderFetched (this.fetcher.RemoteUrl.ToString ()); // TODO warning handling
FolderFetched (this.fetcher.RemoteUrl.ToString (), this.fetcher.Warnings.ToArray ());
this.fetcher.Dispose ();
this.fetcher = null;

View file

@ -21,13 +21,20 @@ using Sparkles;
namespace SparkleShare {
public class BubblesController {
private bool fix_utf_encoding;
public event ShowBubbleEventHandler ShowBubbleEvent = delegate { };
public delegate void ShowBubbleEventHandler (string title, string subtext, string image_path);
public BubblesController ()
public BubblesController () : this(true)
{
}
public BubblesController (bool fix_utf_encoding)
{
this.fix_utf_encoding = fix_utf_encoding;
SparkleShare.Controller.AlertNotificationRaised += delegate (string title, string message) {
ShowBubble (title, message, null);
};
@ -40,10 +47,13 @@ namespace SparkleShare {
public void ShowBubble (string title, string subtext, string image_path)
{
byte [] title_bytes = Encoding.Default.GetBytes (title);
byte [] subtext_bytes = Encoding.Default.GetBytes (subtext);
title = Encoding.UTF8.GetString (title_bytes);
subtext = Encoding.UTF8.GetString (subtext_bytes);
if(fix_utf_encoding)
{
byte [] title_bytes = Encoding.Default.GetBytes (title);
byte [] subtext_bytes = Encoding.Default.GetBytes (subtext);
title = Encoding.UTF8.GetString (title_bytes);
subtext = Encoding.UTF8.GetString (subtext_bytes);
}
ShowBubbleEvent (title, subtext, image_path);
}

View file

@ -53,7 +53,7 @@ namespace SparkleShare {
private string selected_folder;
private RevisionInfo restore_revision_info;
private bool history_view_active;
private bool fix_utf_encoding;
public bool WindowIsOpen { get; private set; }
@ -73,8 +73,8 @@ namespace SparkleShare {
string html = HTML;
delay.Stop ();
if (!string.IsNullOrEmpty (html))
UpdateContentEvent (html);
if (!string.IsNullOrEmpty (html))
UpdateContentEvent (html);
UpdateSizeInfoEvent (Size, HistorySize);
@ -144,8 +144,14 @@ namespace SparkleShare {
}
public EventLogController ()
public EventLogController () : this (true)
{
}
public EventLogController (bool fix_utf_encoding)
{
this.fix_utf_encoding = fix_utf_encoding;
SparkleShare.Controller.ShowEventLogWindowEvent += delegate {
if (!WindowIsOpen) {
ContentLoadingEvent ();
@ -257,8 +263,11 @@ namespace SparkleShare {
string folder = href.Replace ("history://", "").Split ("/".ToCharArray ()) [0];
string file_path = href.Replace ("history://" + folder + "/", "");
byte [] file_path_bytes = Encoding.Default.GetBytes (file_path);
file_path = Encoding.UTF8.GetString (file_path_bytes);
if(fix_utf_encoding)
{
byte [] file_path_bytes = Encoding.Default.GetBytes (file_path);
file_path = Encoding.UTF8.GetString (file_path_bytes);
}
file_path = Uri.UnescapeDataString (file_path);
@ -536,10 +545,13 @@ namespace SparkleShare {
private string FormatBreadCrumbs (string path_root, string path)
{
byte [] path_root_bytes = Encoding.Default.GetBytes (path_root);
byte [] path_bytes = Encoding.Default.GetBytes (path);
path_root = Encoding.UTF8.GetString (path_root_bytes);
path = Encoding.UTF8.GetString (path_bytes);
if(fix_utf_encoding)
{
byte [] path_root_bytes = Encoding.Default.GetBytes (path_root);
byte [] path_bytes = Encoding.Default.GetBytes (path);
path_root = Encoding.UTF8.GetString (path_root_bytes);
path = Encoding.UTF8.GetString (path_bytes);
}
path_root = path_root.Replace ("/", Path.DirectorySeparatorChar.ToString ());
path = path.Replace ("/", Path.DirectorySeparatorChar.ToString ());
@ -598,7 +610,7 @@ namespace SparkleShare {
if (!SparkleShare.Controller.AvatarsEnabled)
return "<!-- $pixmaps-path -->/user-icon-default.png";
string fetched_avatar = Avatars.GetAvatar (user.Email, 48, SparkleShare.Controller.Config.DirectoryPath);
string fetched_avatar = Avatars.GetAvatar (user.Email, 48, SparkleShare.Controller.Config.DirectoryPath, SparkleShare.Controller.AvatarsProvider);
if (!string.IsNullOrEmpty (fetched_avatar))
return "file://" + fetched_avatar.Replace ("\\", "/");

View file

@ -1,182 +0,0 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!-- Created with Inkscape (http://www.inkscape.org/) -->
<svg
xmlns:dc="http://purl.org/dc/elements/1.1/"
xmlns:cc="http://creativecommons.org/ns#"
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:svg="http://www.w3.org/2000/svg"
xmlns="http://www.w3.org/2000/svg"
xmlns:xlink="http://www.w3.org/1999/xlink"
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
id="svg9662"
height="24"
width="24"
version="1.1"
inkscape:version="0.91+devel r14094"
sodipodi:docname="planio.svg"
viewBox="0 0 24 24"
inkscape:export-filename="/Users/hbons/Personal/Projects/SparkleShare/SparkleShare/Common/Presets/planio.png"
inkscape:export-xdpi="96"
inkscape:export-ydpi="96">
<sodipodi:namedview
pagecolor="#ffffff"
bordercolor="#666666"
borderopacity="1"
objecttolerance="10"
gridtolerance="10"
guidetolerance="10"
inkscape:pageopacity="0"
inkscape:pageshadow="2"
inkscape:window-width="1280"
inkscape:window-height="755"
id="namedview4365"
inkscape:document-units="px"
showgrid="false"
inkscape:zoom="16"
inkscape:cx="11.663307"
inkscape:cy="11.258003"
inkscape:window-x="0"
inkscape:window-y="0"
inkscape:window-maximized="0"
inkscape:current-layer="g4326"
inkscape:snap-global="true"
inkscape:snap-smooth-nodes="false"
inkscape:object-nodes="false"
inkscape:snap-bbox="true"
inkscape:snap-nodes="false"
inkscape:bbox-paths="false"
inkscape:bbox-nodes="true">
<inkscape:grid
type="xygrid"
id="grid4341" />
</sodipodi:namedview>
<defs
id="defs3">
<linearGradient
inkscape:collect="always"
id="linearGradient4455">
<stop
style="stop-color:#74caea;stop-opacity:1"
offset="0"
id="stop4457" />
<stop
style="stop-color:#34a1ca;stop-opacity:1"
offset="1"
id="stop4459" />
</linearGradient>
<linearGradient
inkscape:collect="always"
id="linearGradient4447">
<stop
style="stop-color:#ffffff;stop-opacity:1;"
offset="0"
id="stop4449" />
<stop
style="stop-color:#ffffff;stop-opacity:0;"
offset="1"
id="stop4451" />
</linearGradient>
<linearGradient
inkscape:collect="always"
id="linearGradient4428">
<stop
style="stop-color:#005474;stop-opacity:1"
offset="0"
id="stop4430" />
<stop
style="stop-color:#37a9d4;stop-opacity:1"
offset="1"
id="stop4432" />
</linearGradient>
<linearGradient
inkscape:collect="always"
id="linearGradient4304">
<stop
style="stop-color:#ce2509;stop-opacity:1"
offset="0"
id="stop4306" />
<stop
style="stop-color:#a9210a;stop-opacity:1"
offset="1"
id="stop4308" />
</linearGradient>
<linearGradient
inkscape:collect="always"
xlink:href="#linearGradient4304"
id="linearGradient4310"
x1="28.415369"
y1="9.2727699"
x2="31.521933"
y2="19.203804"
gradientUnits="userSpaceOnUse" />
<linearGradient
inkscape:collect="always"
xlink:href="#linearGradient4428"
id="linearGradient4434"
x1="39.367229"
y1="23.90914"
x2="34.828079"
y2="3.3593886"
gradientUnits="userSpaceOnUse"
gradientTransform="matrix(0.9885037,0,0,0.98994346,20.217703,1.7271878)" />
<radialGradient
inkscape:collect="always"
xlink:href="#linearGradient4447"
id="radialGradient4453"
cx="52.259827"
cy="9.6745958"
fx="52.259827"
fy="9.6745958"
r="9.5658912"
gradientTransform="matrix(2.1628252,0,0,2.9778165,-60.887608,-20.066985)"
gradientUnits="userSpaceOnUse" />
<linearGradient
inkscape:collect="always"
xlink:href="#linearGradient4455"
id="linearGradient4526"
x1="53.775932"
y1="11.068961"
x2="56.46653"
y2="23.231386"
gradientUnits="userSpaceOnUse" />
</defs>
<metadata
id="metadata4">
<rdf:RDF>
<cc:Work
rdf:about="">
<dc:format>image/svg+xml</dc:format>
<dc:type
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
<dc:title></dc:title>
</cc:Work>
</rdf:RDF>
</metadata>
<g
id="g4326"
transform="matrix(1.01163,0,0,1.0101587,-20.452835,-1.7447338)"
style="stroke-width:0.9892233">
<path
sodipodi:type="inkscape:offset"
inkscape:radius="0.46403605"
inkscape:original="M 54.814453 3.7070312 C 53.729581 3.7104612 52.652708 3.8923279 51.626953 4.2460938 L 52.835938 10.195312 L 48.294922 6.1738281 C 48.133924 6.3131014 47.977862 6.4580369 47.826172 6.6074219 C 46.443434 7.9940104 45.502551 9.7611672 45.123047 11.683594 L 50.873047 13.607422 L 45.123047 15.53125 C 45.502551 17.453676 46.443434 19.218881 47.826172 20.605469 C 47.977861 20.754855 48.133925 20.89979 48.294922 21.039062 L 52.833984 17.017578 L 51.626953 22.966797 C 52.652675 23.320563 53.729581 23.502434 54.814453 23.505859 C 55.899326 23.502359 56.976198 23.320563 58.001953 22.966797 L 56.794922 17.017578 L 61.335938 21.039062 C 61.496935 20.89979 61.652997 20.754855 61.804688 20.605469 C 63.187426 19.218881 64.128308 17.453676 64.507812 15.53125 L 58.757812 13.605469 L 64.507812 11.683594 C 64.128343 9.7611672 63.187425 7.9940104 61.804688 6.6074219 C 61.652998 6.4580369 61.496935 6.3131014 61.335938 6.1738281 L 56.796875 10.195312 L 58.001953 4.2460938 C 56.976198 3.892328 55.899326 3.7104568 54.814453 3.7070312 z "
xlink:href="#path4468"
style="opacity:1;fill:url(#linearGradient4526);fill-opacity:1;stroke:url(#linearGradient4434);stroke-width:0.9892233;stroke-linecap:round;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1"
id="path4443"
d="m 54.8125,3.2421875 c -1.135761,0.00359 -2.26189,0.1940319 -3.335938,0.5644531 a 0.46408245,0.46408245 0 0 0 -0.304687,0.53125 l 0.931641,4.5878906 -3.5,-3.0996093 a 0.46408245,0.46408245 0 0 0 -0.611328,-0.00391 C 47.822934,5.9686805 47.658148,6.1215986 47.5,6.2773438 a 0.46408245,0.46408245 0 0 0 -0.002,0.00195 C 46.05043,7.7309453 45.065232,9.581363 44.667969,11.59375 a 0.46408245,0.46408245 0 0 0 0.308593,0.529297 l 4.4375,1.484375 -4.4375,1.484375 a 0.46408245,0.46408245 0 0 0 -0.308593,0.529297 c 0.397274,2.012444 1.382614,3.861006 2.830078,5.3125 a 0.46408245,0.46408245 0 0 0 0.002,0.002 c 0.158151,0.155749 0.322936,0.308666 0.492188,0.455078 a 0.46408245,0.46408245 0 0 0 0.611328,-0.0039 l 3.5,-3.09961 -0.931641,4.587891 a 0.46408245,0.46408245 0 0 0 0.304687,0.53125 c 1.074021,0.370424 2.200175,0.560867 3.335938,0.564453 a 0.46408245,0.46408245 0 0 0 0.0039,0 c 1.135722,-0.0037 2.261872,-0.194026 3.335938,-0.564453 A 0.46408245,0.46408245 0 0 0 58.457031,22.875 l -0.93164,-4.589844 3.501953,3.101563 a 0.46408245,0.46408245 0 0 0 0.611328,0.0039 c 0.169252,-0.146414 0.334038,-0.299332 0.492187,-0.455078 a 0.46408245,0.46408245 0 0 0 0.002,-0.002 c 1.447464,-1.451494 2.432804,-3.300056 2.830079,-5.3125 a 0.46408245,0.46408245 0 0 0 -0.308594,-0.529297 l -4.4375,-1.486328 4.4375,-1.482422 A 0.46408245,0.46408245 0 0 0 64.962891,11.59375 C 64.565662,9.5813519 63.580426,7.7309425 62.132812,6.2792969 a 0.46408245,0.46408245 0 0 0 -0.002,-0.00195 C 61.97271,6.1215979 61.807923,5.9686793 61.638672,5.8222656 a 0.46408245,0.46408245 0 0 0 -0.611328,0.00391 l -3.5,3.1015625 0.929687,-4.5898438 a 0.46408245,0.46408245 0 0 0 -0.304687,-0.53125 C 57.078298,3.43622 55.95217,3.2457738 54.816406,3.2421875 a 0.46408245,0.46408245 0 0 0 -0.0039,0 z"
inkscape:href="#path4468"
transform="translate(-22.735586)" />
<path
inkscape:href="#path4468"
d="m 54.8125,4.1933594 c -0.888505,0.00318 -1.766397,0.1572767 -2.617188,0.4082031 L 53.3125,10.097656 a 0.4869683,0.4869683 0 0 1 -0.798828,0.462891 L 48.302734,6.8300781 c -0.04455,0.042299 -0.09086,0.081766 -0.134765,0.125 -1.211927,1.2167288 -2.016154,2.7596114 -2.423828,4.4238279 l 5.283203,1.767578 a 0.4869683,0.4869683 0 0 1 0,0.921875 l -5.283203,1.767579 c 0.407646,1.663899 1.211754,3.205001 2.423828,4.421874 0.0439,0.04323 0.09021,0.0827 0.134765,0.125 l 4.208985,-3.730468 a 0.4869683,0.4869683 0 0 1 0.798828,0.46289 l -1.115235,5.496094 c 0.852018,0.251293 1.731274,0.405394 2.621094,0.408203 0.888542,-0.0032 1.766407,-0.157292 2.617188,-0.408203 l -1.115235,-5.496094 a 0.4869683,0.4869683 0 0 1 0.798829,-0.46289 l 4.210937,3.730468 c 0.04322,-0.04103 0.08826,-0.07918 0.130859,-0.121093 1.21414,-1.217521 2.019652,-2.760098 2.427735,-4.425781 l -5.283203,-1.769532 a 0.4869683,0.4869683 0 0 1 0,-0.921875 l 5.283203,-1.765625 C 63.479068,9.7146987 62.674819,8.1718096 61.462891,6.9550781 l -0.0039,-0.00391 c -0.0426,-0.041909 -0.08764,-0.080065 -0.130859,-0.1210938 L 57.119141,10.560547 A 0.4869683,0.4869683 0 0 1 56.320312,10.099609 L 57.433594,4.6015625 C 56.582803,4.3506351 55.70491,4.1965336 54.816406,4.1933594 l -0.0039,0 z"
id="path4445"
style="opacity:0.3;fill:#34a1ca;fill-opacity:1;stroke:url(#radialGradient4453);stroke-width:0.9892233;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1"
xlink:href="#path4468"
inkscape:original="M 54.814453 3.7070312 C 53.729581 3.7104612 52.652708 3.8923279 51.626953 4.2460938 L 52.835938 10.195312 L 48.294922 6.1738281 C 48.133924 6.3131014 47.977862 6.4580369 47.826172 6.6074219 C 46.443434 7.9940104 45.502551 9.7611672 45.123047 11.683594 L 50.873047 13.607422 L 45.123047 15.53125 C 45.502551 17.453676 46.443434 19.218881 47.826172 20.605469 C 47.977861 20.754855 48.133925 20.89979 48.294922 21.039062 L 52.833984 17.017578 L 51.626953 22.966797 C 52.652675 23.320563 53.729581 23.502434 54.814453 23.505859 C 55.899326 23.502359 56.976198 23.320563 58.001953 22.966797 L 56.794922 17.017578 L 61.335938 21.039062 C 61.496935 20.89979 61.652997 20.754855 61.804688 20.605469 C 63.187426 19.218881 64.128308 17.453676 64.507812 15.53125 L 58.757812 13.605469 L 64.507812 11.683594 C 64.128343 9.7611672 63.187425 7.9940104 61.804688 6.6074219 C 61.652998 6.4580369 61.496935 6.3131014 61.335938 6.1738281 L 56.796875 10.195312 L 58.001953 4.2460938 C 56.976198 3.892328 55.899326 3.7104568 54.814453 3.7070312 z "
inkscape:radius="-0.48691961"
sodipodi:type="inkscape:offset"
transform="translate(-22.735586)" />
</g>
</svg>

Before

Width:  |  Height:  |  Size: 10 KiB

View file

@ -39,8 +39,7 @@ namespace SparkleShare {
SparkleShare.Controller.ShowNoteWindowEvent += OnNoteWindowEvent;
if (SparkleShare.Controller.AvatarsEnabled && !SparkleShare.Controller.FirstRun)
AvatarFilePath = Avatars.GetAvatar (SparkleShare.Controller.CurrentUser.Email,
48, SparkleShare.Controller.Config.DirectoryPath);
AvatarFilePath = Avatars.GetAvatar (SparkleShare.Controller.CurrentUser.Email, 48, SparkleShare.Controller.Config.DirectoryPath, SparkleShare.Controller.AvatarsProvider);
}
@ -73,7 +72,7 @@ namespace SparkleShare {
void ResumeWithNote (string note)
{
{
BaseRepository repo = SparkleShare.Controller.GetRepoByName (CurrentProject);
repo.Resume (note);
}

View file

@ -1,44 +0,0 @@
// SparkleShare, a collaboration and sharing tool.
// Copyright (C) 2010 Hylke Bons <hi@planetpeanut.uk>
//
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU General private License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General private License for more details.
//
// You should have received a copy of the GNU General private License
// along with this program. If not, see <http://www.gnu.org/licenses/>.
using System;
namespace SparkleShare {
public abstract class Page : IDisposable {
protected PageController Controller;
protected PageType? RequestedType;
public string Header;
public string Description;
public object OptionArea;
public object [] Buttons;
public Page (PageType? page_type, PageController controller)
{
RequestedType = page_type;
Controller = controller;
}
public abstract object Render ();
public virtual void Dispose () { }
}
}

View file

@ -1,198 +0,0 @@
// SparkleShare, a collaboration and sharing tool.
// Copyright (C) 2010 Hylke Bons <hi@planetpeanut.uk>
//
// 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
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with this program. If not, see <http://www.gnu.org/licenses/>.
using System;
using System.Collections.Generic;
using System.IO;
using System.Threading;
using Sparkles;
namespace SparkleShare {
public enum PageType {
None,
User,
Privacy,
Host,
Address,
Invite,
Progress,
Storage,
CryptoSetup,
CryptoPassword
}
public partial class PageController {
public bool WindowIsOpen { get; private set; }
public event Action ShowWindowEvent = delegate { };
public event Action HideWindowEvent = delegate { };
PageType current_page;
const int page_delay = 1000;
public event ChangePageEventHandler ChangePageEvent = delegate { };
public delegate void ChangePageEventHandler (PageType page);
public event PageCanContinueEventHandler PageCanContinueEvent = delegate { };
public delegate void PageCanContinueEventHandler (PageType page_type, bool can_continue);
public readonly List<Preset> Presets = new List<Preset> ();
public Preset SelectedPreset;
public Uri FetchAddress { get; private set; }
public double ProgressBarPercentage { get; private set; }
public SparkleInvite PendingInvite { get; private set; }
public PageController ()
{
LoadPresets ();
ChangePageEvent += delegate (PageType page_type) {
this.current_page = page_type;
};
SparkleShare.Controller.InviteReceived += delegate (SparkleInvite invite) {
PendingInvite = invite;
ChangePageEvent (PageType.Invite);
ShowWindowEvent ();
};
SparkleShare.Controller.ShowSetupWindowEvent += ShowSetupWindowEventHandler;
}
void ShowSetupWindowEventHandler (PageType page_type)
{
if (page_type == PageType.Storage ||
page_type == PageType.CryptoSetup ||
page_type == PageType.CryptoPassword) {
ChangePageEvent (page_type);
return;
}
if (PendingInvite != null) {
WindowIsOpen = true;
ShowWindowEvent ();
return;
}
if (this.current_page == PageType.Progress ||
this.current_page == PageType.CryptoSetup ||
this.current_page == PageType.CryptoPassword) {
ShowWindowEvent ();
return;
}
if (page_type == PageType.Host) {
if (WindowIsOpen) {
if (this.current_page == PageType.None)
ChangePageEvent (PageType.Host);
} else if (!SparkleShare.Controller.FirstRun) {
WindowIsOpen = true;
ChangePageEvent (PageType.Host);
}
ShowWindowEvent ();
return;
}
WindowIsOpen = true;
ChangePageEvent (page_type);
ShowWindowEvent ();
}
public void QuitClicked ()
{
SparkleShare.Controller.Quit ();
}
public void CancelClicked (PageType? canceled_page)
{
if (canceled_page == PageType.Progress) {
SparkleShare.Controller.StopFetcher ();
if (PendingInvite != null)
ChangePageEvent (PageType.Invite);
else
ChangePageEvent (PageType.Host);
return;
}
if (canceled_page == PageType.CryptoSetup ||
canceled_page == PageType.CryptoPassword) {
CancelClicked (PageType.Progress);
return;
}
Reset ();
WindowIsOpen = false;
HideWindowEvent ();
}
PageType [] page_order = { PageType.User, PageType.Privacy,
PageType.Host, PageType.Address, PageType.Progress };
public void BackClicked (PageType? page_type)
{
PageType page = (PageType) page_type;
int current_index = Array.IndexOf (page_order, page);
int back_index = current_index - 1;
if (back_index > -1)
ChangePageEvent (page_order [back_index]);
}
public void Reset ()
{
PendingInvite = null;
SelectedPreset = Presets [0];
FetchAddress = null;
}
public void ProgressPageCompleted ()
{
this.current_page = PageType.None;
Reset ();
WindowIsOpen = false;
HideWindowEvent ();
}
}
}

View file

@ -1,76 +0,0 @@
// SparkleShare, a collaboration and sharing tool.
// Copyright (C) 2010 Hylke Bons <hi@planetpeanut.uk>
//
// 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
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with this program. If not, see <http://www.gnu.org/licenses/>.
using System;
using System.Threading;
using Sparkles;
namespace SparkleShare {
public partial class PageController {
public event AddressPagePublicKeyEventHandler AddressPagePublicKeyEvent = delegate { };
public delegate void AddressPagePublicKeyEventHandler (bool has_key, string auth_status, string key_entry_hint);
public void CheckAddressPage (string address, string remote_path)
{
address = address.Trim ();
remote_path = remote_path.Trim ();
bool fields_valid = (!string.IsNullOrEmpty (address) &&
!string.IsNullOrEmpty (remote_path) && !remote_path.Contains ("\""));
PageCanContinueEvent (PageType.Address, fields_valid);
}
public void AddressPageCompleted (string address, string remote_path)
{
ProgressBarPercentage = 1.0;
ChangePageEvent (PageType.Progress);
address = Uri.EscapeUriString (address.Trim ());
remote_path = remote_path.Trim ();
if (SelectedPreset.PathUsesLowerCase)
remote_path = remote_path.ToLower ();
FetchAddress = new Uri (address + remote_path);
SparkleShare.Controller.FolderFetched += ProgressPageFetchedDelegate;
SparkleShare.Controller.FolderFetchError += ProgressPageFetchErrorDelegate;
SparkleShare.Controller.FolderFetching += ProgressPageFetchingDelegate;
var info = new FetcherInfo (FetchAddress) {
Backend = SelectedPreset.Backend,
Fingerprint = SelectedPreset.Fingerprint,
AnnouncementsUrl = SelectedPreset.AnnouncementsUrl
};
new Thread (() => { SparkleShare.Controller.StartFetcher (info); }).Start ();
}
public void CopyToClipboardClicked ()
{
SparkleShare.Controller.CopyToClipboard (SparkleShare.Controller.UserAuthenticationInfo.PublicKey);
}
}
}

View file

@ -1,55 +0,0 @@
// SparkleShare, a collaboration and sharing tool.
// Copyright (C) 2010 Hylke Bons <hi@planetpeanut.uk>
//
// 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
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with this program. If not, see <http://www.gnu.org/licenses/>.
using System;
using System.Threading;
using Sparkles;
namespace SparkleShare {
public partial class PageController {
public void CheckCryptoSetupPage (string password)
{
new Thread (() => {
bool is_valid_password = (password.Length > 0 && !password.StartsWith (" ") && !password.EndsWith (" "));
PageCanContinueEvent (PageType.CryptoSetup, is_valid_password);
}).Start ();
}
public void CheckCryptoPasswordPage (string password)
{
bool is_password_correct = SparkleShare.Controller.CheckPassword (password);
PageCanContinueEvent (PageType.CryptoPassword, is_password_correct);
}
public void CryptoPageCompleted (string password)
{
ProgressBarPercentage = 100.0;
ChangePageEvent (PageType.Progress);
new Thread (() => {
Thread.Sleep (page_delay);
SparkleShare.Controller.FinishFetcher (StorageType.Encrypted, password);
}).Start ();
}
}
}

View file

@ -1,114 +0,0 @@
// SparkleShare, a collaboration and sharing tool.
// Copyright (C) 2010 Hylke Bons <hi@planetpeanut.uk>
//
// 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
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with this program. If not, see <http://www.gnu.org/licenses/>.
using System;
using System.IO;
using System.Threading;
using Sparkles;
namespace SparkleShare {
public partial class PageController {
void LoadPresets ()
{
int local_presets_count = 0;
string local_presets_path = Preset.LocalPresetsPath;
if (Directory.Exists (local_presets_path))
// Local presets go first...
foreach (string xml_file_path in Directory.GetFiles (local_presets_path, "*.xml")) {
Presets.Add (new Preset (xml_file_path));
local_presets_count++;
}
// ...system presets after that...
if (Directory.Exists (SparkleShare.Controller.PresetsPath)) {
foreach (string xml_file_path in Directory.GetFiles (SparkleShare.Controller.PresetsPath, "*.xml")) {
// ...and "Own server" at the very top
if (xml_file_path.EndsWith ("own-server.xml"))
Presets.Insert (0, new Preset (xml_file_path));
else
Presets.Add (new Preset (xml_file_path));
}
}
SelectedPreset = Presets [0];
}
public int SelectedPresetIndex {
get {
return Presets.IndexOf (SelectedPreset);
}
}
public void SelectedPresetChanged (int preset_index)
{
SelectedPreset = Presets [preset_index];
}
public void HostPageCompleted ()
{
ChangePageEvent (PageType.Address);
string host = SelectedPreset.Address;
if (string.IsNullOrEmpty (host)) {
if (string.IsNullOrEmpty (SelectedPreset.Host)) {
new Thread (() => {
Thread.Sleep (page_delay);
AddressPagePublicKeyEvent (false, "", SelectedPreset.KeyEntryHint);
}).Start ();
return;
}
host = "ssh://" + SelectedPreset.Host;
}
new Thread (() => {
bool authenticated = true;
string auth_status = "✓ Authenticated";
try {
authenticated = SSHFetcher.CanAuthenticateTo (
new Uri (host), SparkleShare.Controller.UserAuthenticationInfo);
} catch (NetworkException) {
authenticated = false;
}
if (authenticated) {
if (!string.IsNullOrEmpty (SelectedPreset.Address))
auth_status += string.Format (" to {0}", new Uri (host).Host);
} else {
string public_key = "<tt>" + SparkleShare.Controller.UserAuthenticationInfo.PublicKey.Substring (0, 40) + "…</tt>";
auth_status = public_key;
}
AddressPagePublicKeyEvent (authenticated, auth_status, SelectedPreset.KeyEntryHint);
}).Start ();
}
}
}

View file

@ -1,79 +0,0 @@
// SparkleShare, a collaboration and sharing tool.
// Copyright (C) 2010 Hylke Bons <hi@planetpeanut.uk>
//
// 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
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with this program. If not, see <http://www.gnu.org/licenses/>.
using System;
using System.IO;
using System.Threading;
using Sparkles;
namespace SparkleShare {
public partial class PageController {
public void InvitePageCompleted ()
{
// TODO PreviousAddress = PendingInvite.Address;
ChangePageEvent (PageType.Progress);
new Thread (() => {
if (!PendingInvite.Accept (SparkleShare.Controller.UserAuthenticationInfo.PublicKey)) {
FetchAddress = new Uri (PendingInvite.Address + PendingInvite.RemotePath.TrimStart ('/'));
// TODO ChangePageEvent (PageType.Error, new string [] { "error: Failed to upload the public key" });
return;
}
SparkleShare.Controller.FolderFetched += InvitePageFetchedDelegate;
SparkleShare.Controller.FolderFetchError += InvitePageFetchErrorDelegate;
SparkleShare.Controller.FolderFetching += ProgressPageFetchingDelegate;
var info = new FetcherInfo (new Uri (Path.Combine (PendingInvite.Address, PendingInvite.RemotePath))) {
Fingerprint = PendingInvite.Fingerprint,
AnnouncementsUrl = PendingInvite.AnnouncementsUrl
};
SparkleShare.Controller.StartFetcher (info);
}).Start ();
}
void InvitePageFetchedDelegate (string remote_url)
{
PendingInvite = null;
// TODO success state + warning
SparkleShare.Controller.FolderFetched -= ProgressPageFetchedDelegate;
SparkleShare.Controller.FolderFetchError -= ProgressPageFetchErrorDelegate;
SparkleShare.Controller.FolderFetching -= ProgressPageFetchingDelegate;
}
void InvitePageFetchErrorDelegate (string remote_url, string error, string error_details)
{
FetchAddress = new Uri (remote_url);
//TODO ChangePageEvent (PageType.Error, errors);
SparkleShare.Controller.FolderFetched -= ProgressPageFetchedDelegate;
SparkleShare.Controller.FolderFetchError -= ProgressPageFetchErrorDelegate;
SparkleShare.Controller.FolderFetching -= ProgressPageFetchingDelegate;
}
}
}

View file

@ -1,33 +0,0 @@
// SparkleShare, a collaboration and sharing tool.
// Copyright (C) 2010 Hylke Bons <hi@planetpeanut.uk>
//
// 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
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with this program. If not, see <http://www.gnu.org/licenses/>.
using System;
namespace SparkleShare {
public partial class PageController {
public void PrivacyPageCompleted (bool notification_service, bool crash_reports, bool gravatars)
{
SparkleShare.Controller.Config.SetConfigOption ("notification_service", notification_service.ToString ());
SparkleShare.Controller.Config.SetConfigOption ("crash_reports", crash_reports.ToString ());
SparkleShare.Controller.Config.SetConfigOption ("gravatars", gravatars.ToString ());
ChangePageEvent (PageType.Host);
}
}
}

View file

@ -1,114 +0,0 @@
// SparkleShare, a collaboration and sharing tool.
// Copyright (C) 2010 Hylke Bons <hi@planetpeanut.uk>
//
// 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
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with this program. If not, see <http://www.gnu.org/licenses/>.
using System;
using System.IO;
using Sparkles;
namespace SparkleShare {
public partial class PageController {
public event ProgressPageBarEventHandler ProgressPageBarEvent = delegate { };
public delegate void ProgressPageBarEventHandler (bool? success,
string status, string status_details,
double progress, string progress_details);
void ProgressPageFetchedDelegate (string remote_url)
{
// Create a local preset for succesfully added projects, so
// so the user can easily use the same host again
if (SelectedPresetIndex == 0) {
Preset new_preset;
Uri uri = new Uri (remote_url);
try {
string address = remote_url.Replace (uri.AbsolutePath, "");
new_preset = Preset.Create (uri.Host, address, address, "", "", "/path/to/project");
if (new_preset != null) {
Presets.Insert (1, new_preset);
Logger.LogInfo ("Controller", "Added preset for " + uri.Host);
}
} catch (Exception e) {
Logger.LogInfo ("Controller", "Failed adding preset for " + uri.Host, e);
}
}
SparkleShare.Controller.FolderFetched -= ProgressPageFetchedDelegate;
SparkleShare.Controller.FolderFetchError -= ProgressPageFetchErrorDelegate;
SparkleShare.Controller.FolderFetching -= ProgressPageFetchingDelegate;
ProgressPageBarEvent (
success: true,
status: "Fetched all files from " + FetchAddress, status_details: null,
progress: 100.0, progress_details: null);
}
void ProgressPageFetchErrorDelegate (string remote_url, string error, string error_details)
{
FetchAddress = new Uri (remote_url);
ProgressPageBarEvent (
success: false,
status: error, status_details: error_details,
progress: ProgressBarPercentage, progress_details: "Could not download files from " + remote_url);
SparkleShare.Controller.FolderFetched -= ProgressPageFetchedDelegate;
SparkleShare.Controller.FolderFetchError -= ProgressPageFetchErrorDelegate;
SparkleShare.Controller.FolderFetching -= ProgressPageFetchingDelegate;
}
void ProgressPageFetchingDelegate (double percentage, double speed ,string information)
{
ProgressBarPercentage = percentage;
if (speed > 0)
information = speed.ToSize () + " " + information;
ProgressPageBarEvent (
success: null,
status: "Getting files", status_details: null,
progress: ProgressBarPercentage, progress_details: information);
}
public void ErrorPageCompleted ()
{
if (PendingInvite != null)
ChangePageEvent (PageType.Invite);
else
ChangePageEvent (PageType.Address);
}
public void ShowFilesClicked ()
{
string folder_name = Path.GetFileName (FetchAddress.AbsolutePath);
folder_name = folder_name.ReplaceUnderscoreWithSpace ();
SparkleShare.Controller.OpenSparkleShareFolder (folder_name);
ProgressPageCompleted ();
}
}
}

View file

@ -1,44 +0,0 @@
// SparkleShare, a collaboration and sharing tool.
// Copyright (C) 2010 Hylke Bons <hi@planetpeanut.uk>
//
// 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
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with this program. If not, see <http://www.gnu.org/licenses/>.
using System;
using System.Threading;
using Sparkles;
namespace SparkleShare {
public partial class PageController {
public void StoragePageCompleted (StorageType storage_type)
{
if (storage_type == StorageType.Encrypted) {
ChangePageEvent (PageType.CryptoSetup);
return;
}
ProgressBarPercentage = 100.0;
ChangePageEvent (PageType.Progress);
new Thread (() => {
Thread.Sleep (page_delay);
SparkleShare.Controller.FinishFetcher (storage_type);
}).Start ();
}
}
}

View file

@ -1,45 +0,0 @@
// SparkleShare, a collaboration and sharing tool.
// Copyright (C) 2010 Hylke Bons <hi@planetpeanut.uk>
//
// 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
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with this program. If not, see <http://www.gnu.org/licenses/>.
using System;
using System.Threading;
using Sparkles;
namespace SparkleShare {
public partial class PageController {
public void CheckUserPage (string name, string email)
{
name = name.Trim ();
email = email.Trim ();
bool fields_valid = (!string.IsNullOrEmpty (name) && email.Contains ("@"));
PageCanContinueEvent (PageType.User, fields_valid);
}
public void UserPageCompleted (string full_name, string email)
{
SparkleShare.Controller.CurrentUser = new User (full_name, email);
new Thread (() => SparkleShare.Controller.CreateStartupItem ()).Start ();
ChangePageEvent (PageType.Privacy);
}
}
}

View file

@ -1,23 +1,21 @@
<?xml version="1.0" encoding="UTF-8"?>
<sparkleshare>
<preset>
<info>
<name>Bitbucket</name>
<description>Free code hosting for Git and Mercurial</description>
<icon>bitbucket.png</icon>
<backend>Git</backend>
<host>bitbucket.org</host>
<fingerprint>cf:35:d0:39:74:91:04:48:94:b6:e1:3c:02:29:09:60:ac:1b:1d:ac:6f:49:cd:28:8d:ec:fd:61:76:86:a7:50</fingerprint>
</info>
<address>
<value>ssh://git@bitbucket.org/</value>
<example/>
</address>
<path>
<value/>
<example>/username/project</example>
<uses_lower_case>True</uses_lower_case>
</path>
<key_entry_hint>Go to <b>Settings → SSH Keys</b> on <a href="https://bitbucket.org/">bitbucket.org</a> and add this SSH key:</key_entry_hint>
</preset>
<preset>
<info>
<name>Bitbucket</name>
<description>Free code hosting for Git and Mercurial</description>
<icon>bitbucket.png</icon>
<backend>Git</backend>
<fingerprint>4c:eb:19:11:0d:d6:19:65:7b:6a:40:8a:fb:b7:4d:51:81:a1:7a:07:74:4a:b5:22:0c:91:86:42:74:88:9b:bc</fingerprint>
</info>
<address>
<value>ssh://git@bitbucket.org/</value>
<example/>
</address>
<path>
<value/>
<example>/username/project</example>
<uses_lower_case>True</uses_lower_case>
</path>
</preset>
</sparkleshare>

Binary file not shown.

Before

Width:  |  Height:  |  Size: 3.4 KiB

View file

@ -1,26 +1,21 @@
<?xml version="1.0" encoding="UTF-8"?>
<sparkleshare>
<preset>
<info>
<name>GitHub</name>
<description>The biggest collection of Open Source projects</description>
<icon>github.png</icon>
<logo>github-logo.png</logo>
<backend>Git</backend>
<host>github.com</host>
<fingerprint>9d:38:5b:83:a9:17:52:92:56:1a:5e:c4:d4:81:8e:0a:ca:51:a2:64:f1:74:20:11:2e:f8:8a:c3:a1:39:49:8f</fingerprint>
<storage_type>LargeFiles</storage_type>
</info>
<address>
<value>ssh://git@github.com/</value>
<example/>
</address>
<path>
<value/>
<example>/username/project</example>
</path>
<key>
<hint>Go to <a href="https://github.com/settings/keys">github.com/settings/keys</a> and add this SSH key:</hint>
</key>
</preset>
<preset>
<info>
<name>GitHub</name>
<description>The biggest collection of Open Source projects</description>
<icon>github.png</icon>
<backend>Git</backend>
<storage_type>LargeFiles</storage_type>
<fingerprint>92:a3:7f:bd:5e:21:a5:3a:95:c7:16:e1:14:4f:44:2f:58:2b:94:d0:fa:fc:67:3e:b6:71:7a:4e:b5:1a:88:a7</fingerprint>
</info>
<address>
<value>ssh://git@github.com/</value>
<example/>
</address>
<path>
<value/>
<example>/username/project</example>
</path>
</preset>
</sparkleshare>

Binary file not shown.

Before

Width:  |  Height:  |  Size: 5 KiB

View file

@ -1,25 +1,21 @@
<?xml version="1.0" encoding="UTF-8"?>
<sparkleshare>
<preset>
<info>
<name>GitLab</name>
<description>Open Source alternative to GitHub</description>
<icon>gitlab.png</icon>
<logo>gitlab-logo.png</logo>
<backend>Git</backend>
<host>gitlab.com</host>
<fingerprint>44:e4:05:bc:f4:e1:1a:b5:b8:46:e5:8b:a0:bf:6d:ab:d2:3d:cc:9e:36:7c:ae:17:cb:0c:91:b5:b3:b3:fc:44</fingerprint>
</info>
<address>
<value>ssh://git@gitlab.com/</value>
<example/>
</address>
<path>
<value/>
<example>/username/project</example>
</path>
<key>
<hint>Go to <a href="https://gitlab.com/profile/keys">gitlab.com/profile/keys</a> and add this SSH key:</hint>
</key>
</preset>
<preset>
<info>
<name>GitLab</name>
<description>Open Source alternative to GitHub</description>
<icon>gitlab.png</icon>
<backend>Git</backend>
<fingerprint>44:e4:05:bc:f4:e1:1a:b5:b8:46:e5:8b:a0:bf:6d:ab:d2:3d:cc:9e:36:7c:ae:17:cb:0c:91:b5:b3:b3:fc:44</fingerprint>
</info>
<address>
<value>ssh://git@gitlab.com/</value>
<example/>
</address>
<path>
<value/>
<example>/username/project</example>
</path>
</preset>
</sparkleshare>

View file

@ -1,18 +1,8 @@
# Github
preset_files = ['github.xml', 'github.png', 'github-logo.png']
# GitLab
preset_files += ['gitlab.xml', 'gitlab.png', 'gitlab-logo.png']
# Bitbucket
preset_files += ['bitbucket.xml', 'bitbucket.png']
# Planio
preset_files += ['planio.xml', 'planio.png', 'planio-logo.png']
# Other
preset_files += ['own-server.xml', 'own-server.png']
preset_files = ['github.xml', 'github.png',
'gitlab.xml', 'gitlab.png',
'bitbucket.xml', 'bitbucket.png',
'own-server.xml', 'own-server.png'
]
install_data(
sources: preset_files,

View file

@ -1,20 +1,20 @@
<?xml version="1.0" encoding="UTF-8"?>
<sparkleshare>
<preset>
<info>
<name>Own server</name>
<description>Everything under my control</description>
<key_entry_hint>Ask the person administrating the server to add this SSH key:</key_entry_hint>
<icon>own-server.png</icon>
<backend>Git</backend>
</info>
<address>
<value/>
<example>ssh://[user@]hostname[:port]</example>
</address>
<path>
<value/>
<example>/path/to/project</example>
</path>
</preset>
<preset>
<info>
<name>Own server</name>
<description>Everything under my control</description>
<icon>own-server.png</icon>
<backend>Git</backend>
</info>
<address>
<value/>
<example>ssh://[user@]hostname[:port]</example>
</address>
<path>
<value/>
<example>/path/to/project</example>
</path>
</preset>
</sparkleshare>

Binary file not shown.

Before

Width:  |  Height:  |  Size: 3.9 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.5 KiB

View file

@ -1,26 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<sparkleshare>
<preset>
<info>
<name>Planio</name>
<description>Online project management</description>
<icon>planio.png</icon>
<logo>planio-logo.png</logo>
<backend>Git</backend>
<host>plan.io</host>
<fingerprint>38:29:13:0f:7c:74:67:22:c5:a6:a6:95:b4:b8:e0:ef:3d:e0:9e:87:02:58:ff:37:2c:8b:34:5a:ed:73:5d:81</fingerprint>
<announcements_url>tcp://sparkleshare-notifications.plan.io:443</announcements_url>
</info>
<address>
<value/>
<example>ssh://git@[account].plan.io</example>
</address>
<path>
<value/>
<example>/[account]-[project].git</example>
</path>
<key>
<hint>Go to <b>My account → Public keys</b> on <a href="https://plan.io/">plan.io</a> and add this key:</hint>
</key>
</preset>
</sparkleshare>

Binary file not shown.

Before

Width:  |  Height:  |  Size: 3.6 KiB

View file

@ -0,0 +1,566 @@
// SparkleShare, a collaboration and sharing tool.
// Copyright (C) 2010 Hylke Bons <hi@planetpeanut.uk>
//
// 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
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with this program. If not, see <http://www.gnu.org/licenses/>.
using System;
using System.Collections.Generic;
using System.IO;
using System.Text.RegularExpressions;
using System.Threading;
using Sparkles;
namespace SparkleShare {
public enum PageType {
None,
Setup,
Add,
Invite,
Syncing,
Error,
Finished,
StorageSetup,
CryptoSetup,
CryptoPassword
}
public enum FieldState {
Enabled,
Disabled
}
public class SetupController {
public event Action ShowWindowEvent = delegate { };
public event Action HideWindowEvent = delegate { };
public event ChangePageEventHandler ChangePageEvent = delegate { };
public delegate void ChangePageEventHandler (PageType page, string [] warnings);
public event UpdateProgressBarEventHandler UpdateProgressBarEvent = delegate { };
public delegate void UpdateProgressBarEventHandler (double percentage, string information);
public event UpdateSetupContinueButtonEventHandler UpdateSetupContinueButtonEvent = delegate { };
public delegate void UpdateSetupContinueButtonEventHandler (bool button_enabled);
public event UpdateCryptoSetupContinueButtonEventHandler UpdateCryptoSetupContinueButtonEvent = delegate { };
public delegate void UpdateCryptoSetupContinueButtonEventHandler (bool button_enabled);
public event UpdateCryptoPasswordContinueButtonEventHandler UpdateCryptoPasswordContinueButtonEvent = delegate { };
public delegate void UpdateCryptoPasswordContinueButtonEventHandler (bool button_enabled);
public event UpdateAddProjectButtonEventHandler UpdateAddProjectButtonEvent = delegate { };
public delegate void UpdateAddProjectButtonEventHandler (bool button_enabled);
public event ChangeAddressFieldEventHandler ChangeAddressFieldEvent = delegate { };
public delegate void ChangeAddressFieldEventHandler (string text, string example_text, FieldState state);
public event ChangePathFieldEventHandler ChangePathFieldEvent = delegate { };
public delegate void ChangePathFieldEventHandler (string text, string example_text, FieldState state);
public readonly List<Preset> Presets = new List<Preset> ();
public Preset SelectedPreset;
public bool WindowIsOpen { get; private set; }
public SparkleInvite PendingInvite { get; private set; }
public string PreviousUrl { get; private set; }
public string PreviousAddress { get; private set; }
public string PreviousPath { get; private set; }
public string SyncingFolder { get; private set; }
public double ProgressBarPercentage { get; private set; }
public int SelectedPresetIndex {
get {
return Presets.IndexOf (SelectedPreset);
}
}
public bool FetchPriorHistory {
get {
return this.fetch_prior_history;
}
}
private PageType current_page;
private string saved_address = "";
private string saved_remote_path = "";
private bool fetch_prior_history = false;
public SetupController ()
{
ChangePageEvent += delegate (PageType page_type, string [] warnings) {
this.current_page = page_type;
};
PreviousAddress = "";
PreviousPath = "";
PreviousUrl = "";
SyncingFolder = "";
string local_presets_path = Preset.LocalPresetsPath;
int local_presets_count = 0;
// Import all of the presets
if (Directory.Exists (local_presets_path))
// Local presets go first...
foreach (string xml_file_path in Directory.GetFiles (local_presets_path, "*.xml")) {
Presets.Add (new Preset (xml_file_path));
local_presets_count++;
}
// ...system presets after that...
if (Directory.Exists (SparkleShare.Controller.PresetsPath)) {
foreach (string xml_file_path in Directory.GetFiles (SparkleShare.Controller.PresetsPath, "*.xml")) {
// ...and "Own server" at the very top
if (xml_file_path.EndsWith ("own-server.xml"))
Presets.Insert (0, new Preset (xml_file_path));
else
Presets.Add (new Preset (xml_file_path));
}
}
SelectedPreset = Presets [0];
SparkleShare.Controller.InviteReceived += delegate (SparkleInvite invite) {
PendingInvite = invite;
ChangePageEvent (PageType.Invite, null);
ShowWindowEvent ();
};
SparkleShare.Controller.ShowSetupWindowEvent += delegate (PageType page_type) {
if (page_type == PageType.StorageSetup ||
page_type == PageType.CryptoSetup ||
page_type == PageType.CryptoPassword) {
ChangePageEvent (page_type, null);
return;
}
if (PendingInvite != null) {
WindowIsOpen = true;
ShowWindowEvent ();
return;
}
if (this.current_page == PageType.Syncing ||
this.current_page == PageType.Finished ||
this.current_page == PageType.CryptoSetup ||
this.current_page == PageType.CryptoPassword) {
ShowWindowEvent ();
return;
}
if (page_type == PageType.Add) {
if (WindowIsOpen) {
if (this.current_page == PageType.Error ||
this.current_page == PageType.Finished ||
this.current_page == PageType.None) {
ChangePageEvent (PageType.Add, null);
}
} else if (!SparkleShare.Controller.FirstRun) {
WindowIsOpen = true;
ChangePageEvent (PageType.Add, null);
}
ShowWindowEvent ();
return;
}
WindowIsOpen = true;
ChangePageEvent (page_type, null);
ShowWindowEvent ();
};
}
public void PageCancelled ()
{
PendingInvite = null;
SelectedPreset = Presets [0];
PreviousAddress = "";
PreviousPath = "";
PreviousUrl = "";
this.saved_address = "";
this.saved_remote_path = "";
this.fetch_prior_history = false;
WindowIsOpen = false;
HideWindowEvent ();
}
public void CheckSetupPage (string full_name, string email)
{
full_name = full_name.Trim ();
email = email.Trim ();
bool fields_valid = (!string.IsNullOrEmpty (full_name) && IsValidEmail (email));
UpdateSetupContinueButtonEvent (fields_valid);
}
public void SetupPageCancelled ()
{
SparkleShare.Controller.Quit ();
}
public void SetupPageCompleted (string full_name, string email)
{
SparkleShare.Controller.CurrentUser = new User (full_name, email);
new Thread (() => SparkleShare.Controller.CreateStartupItem ()).Start ();
ChangePageEvent (PageType.Add, null);
}
public void HistoryItemChanged (bool fetch_prior_history)
{
this.fetch_prior_history = fetch_prior_history;
}
public void SelectedPresetChanged (int preset_index)
{
SelectedPreset = Presets [preset_index];
if (SelectedPreset.Address != null) {
ChangeAddressFieldEvent (SelectedPreset.Address, "", FieldState.Disabled);
} else if (SelectedPreset.AddressExample != null) {
ChangeAddressFieldEvent (this.saved_address, SelectedPreset.AddressExample, FieldState.Enabled);
} else {
ChangeAddressFieldEvent (this.saved_address, "", FieldState.Enabled);
}
if (SelectedPreset.Path != null) {
ChangePathFieldEvent (SelectedPreset.Path, "", FieldState.Disabled);
} else if (SelectedPreset.PathExample != null) {
ChangePathFieldEvent (this.saved_remote_path, SelectedPreset.PathExample, FieldState.Enabled);
} else {
ChangePathFieldEvent (this.saved_remote_path, "", FieldState.Enabled);
}
}
public void CheckAddPage (string address, string remote_path, int selected_preset)
{
address = address.Trim ();
remote_path = remote_path.Trim ();
if (selected_preset == 0)
this.saved_address = address;
this.saved_remote_path = remote_path;
bool fields_valid = (!string.IsNullOrEmpty (address) &&
!string.IsNullOrEmpty (remote_path) && !remote_path.Contains ("\""));
UpdateAddProjectButtonEvent (fields_valid);
}
public void AddPageCompleted (string address, string remote_path)
{
SyncingFolder = Path.GetFileName (remote_path);
if (remote_path.EndsWith (".git"))
SyncingFolder = remote_path.Substring (0, remote_path.Length - 4);
SyncingFolder = SyncingFolder.ReplaceUnderscoreWithSpace ();
ProgressBarPercentage = 1.0;
ChangePageEvent (PageType.Syncing, null);
address = Uri.EscapeUriString (address.Trim ());
remote_path = remote_path.Trim ();
remote_path = remote_path.TrimEnd ("/".ToCharArray ());
if (SelectedPreset.PathUsesLowerCase)
remote_path = remote_path.ToLower ();
PreviousAddress = address;
PreviousPath = remote_path;
SparkleShare.Controller.FolderFetched += AddPageFetchedDelegate;
SparkleShare.Controller.FolderFetchError += AddPageFetchErrorDelegate;
SparkleShare.Controller.FolderFetching += SyncingPageFetchingDelegate;
SparkleFetcherInfo info = new SparkleFetcherInfo {
Address = address,
Fingerprint = SelectedPreset.Fingerprint,
RemotePath = remote_path,
FetchPriorHistory = this.fetch_prior_history,
AnnouncementsUrl = SelectedPreset.AnnouncementsUrl,
Backend = SelectedPreset.Backend
};
new Thread (() => { SparkleShare.Controller.StartFetcher (info); }).Start ();
}
// The following private methods are
// delegates used by the previous method
private void AddPageFetchedDelegate (string remote_url, string [] warnings)
{
SyncingFolder = "";
// Create a local preset for succesfully added projects, so
// so the user can easily use the same host again
if (SelectedPresetIndex == 0) {
Preset new_preset;
Uri uri = new Uri (remote_url);
try {
string address = remote_url.Replace (uri.AbsolutePath, "");
new_preset = Preset.Create (uri.Host, address, address, "", "", "/path/to/project");
if (new_preset != null) {
Presets.Insert (1, new_preset);
Logger.LogInfo ("Controller", "Added preset for " + uri.Host);
}
} catch (Exception e) {
Logger.LogInfo ("Controller", "Failed adding preset for " + uri.Host, e);
}
}
ChangePageEvent (PageType.Finished, warnings);
SparkleShare.Controller.FolderFetched -= AddPageFetchedDelegate;
SparkleShare.Controller.FolderFetchError -= AddPageFetchErrorDelegate;
SparkleShare.Controller.FolderFetching -= SyncingPageFetchingDelegate;
}
private void AddPageFetchErrorDelegate (string remote_url, string [] errors)
{
SyncingFolder = "";
PreviousUrl = remote_url;
ChangePageEvent (PageType.Error, errors);
SparkleShare.Controller.FolderFetched -= AddPageFetchedDelegate;
SparkleShare.Controller.FolderFetchError -= AddPageFetchErrorDelegate;
SparkleShare.Controller.FolderFetching -= SyncingPageFetchingDelegate;
}
private void SyncingPageFetchingDelegate (double percentage, double speed ,string information)
{
ProgressBarPercentage = percentage;
if (speed > 0)
information = speed.ToSize () + " " + information;
UpdateProgressBarEvent (ProgressBarPercentage, information);
}
public void InvitePageCompleted ()
{
SyncingFolder = Path.GetFileName (PendingInvite.RemotePath);
if (PendingInvite.RemotePath.EndsWith (".git"))
SyncingFolder = PendingInvite.RemotePath.Substring (0, PendingInvite.RemotePath.Length - 4);
SyncingFolder = SyncingFolder.ReplaceUnderscoreWithSpace ();
PreviousAddress = PendingInvite.Address;
PreviousPath = PendingInvite.RemotePath;
ChangePageEvent (PageType.Syncing, null);
new Thread (() => {
if (!PendingInvite.Accept (SparkleShare.Controller.UserAuthenticationInfo.PublicKey)) {
PreviousUrl = PendingInvite.Address + PendingInvite.RemotePath.TrimStart ("/".ToCharArray ());
ChangePageEvent (PageType.Error, new string [] { "error: Failed to upload the public key" });
return;
}
SparkleShare.Controller.FolderFetched += InvitePageFetchedDelegate;
SparkleShare.Controller.FolderFetchError += InvitePageFetchErrorDelegate;
SparkleShare.Controller.FolderFetching += SyncingPageFetchingDelegate;
SparkleFetcherInfo info = new SparkleFetcherInfo {
Address = PendingInvite.Address,
Fingerprint = PendingInvite.Fingerprint,
RemotePath = PendingInvite.RemotePath,
FetchPriorHistory = false, // TODO: checkbox on invite page
AnnouncementsUrl = PendingInvite.AnnouncementsUrl
};
SparkleShare.Controller.StartFetcher (info);
}).Start ();
}
// The following private methods are
// delegates used by the previous method
private void InvitePageFetchedDelegate (string remote_url, string [] warnings)
{
SyncingFolder = "";
PendingInvite = null;
ChangePageEvent (PageType.Finished, warnings);
SparkleShare.Controller.FolderFetched -= AddPageFetchedDelegate;
SparkleShare.Controller.FolderFetchError -= AddPageFetchErrorDelegate;
SparkleShare.Controller.FolderFetching -= SyncingPageFetchingDelegate;
}
private void InvitePageFetchErrorDelegate (string remote_url, string [] errors)
{
SyncingFolder = "";
PreviousUrl = remote_url;
ChangePageEvent (PageType.Error, errors);
SparkleShare.Controller.FolderFetched -= AddPageFetchedDelegate;
SparkleShare.Controller.FolderFetchError -= AddPageFetchErrorDelegate;
SparkleShare.Controller.FolderFetching -= SyncingPageFetchingDelegate;
}
public void SyncingCancelled ()
{
SparkleShare.Controller.StopFetcher ();
if (PendingInvite != null)
ChangePageEvent (PageType.Invite, null);
else
ChangePageEvent (PageType.Add, null);
}
public void ErrorPageCompleted ()
{
if (PendingInvite != null)
ChangePageEvent (PageType.Invite, null);
else
ChangePageEvent (PageType.Add, null);
}
public void StoragePageCompleted (StorageType storage_type)
{
if (storage_type == StorageType.Encrypted) {
ChangePageEvent (PageType.CryptoSetup, null);
return;
}
ProgressBarPercentage = 100.0;
ChangePageEvent (PageType.Syncing, null);
new Thread (() => {
Thread.Sleep (1000);
SparkleShare.Controller.FinishFetcher (storage_type);
}).Start ();
}
public void CheckCryptoSetupPage (string password)
{
new Thread (() => {
bool is_valid_password = (password.Length > 0 && !password.StartsWith (" ") && !password.EndsWith (" "));
UpdateCryptoSetupContinueButtonEvent (is_valid_password);
}).Start ();
}
public void CheckCryptoPasswordPage (string password)
{
bool is_password_correct = SparkleShare.Controller.CheckPassword (password);
UpdateCryptoPasswordContinueButtonEvent (is_password_correct);
}
public void CryptoPageCancelled ()
{
SyncingCancelled ();
}
public void CryptoSetupPageCompleted (string password)
{
CryptoPasswordPageCompleted (password);
}
public void CryptoPasswordPageCompleted (string password)
{
ProgressBarPercentage = 100.0;
ChangePageEvent (PageType.Syncing, null);
new Thread (() => {
Thread.Sleep (1000);
SparkleShare.Controller.FinishFetcher (StorageType.Encrypted, password);
}).Start ();
}
public void CopyToClipboardClicked ()
{
SparkleShare.Controller.CopyToClipboard (SparkleShare.Controller.UserAuthenticationInfo.PublicKey);
}
public void ShowFilesClicked ()
{
string folder_name = Path.GetFileNameWithoutExtension (PreviousPath);
folder_name = folder_name.ReplaceUnderscoreWithSpace ();
SparkleShare.Controller.OpenSparkleShareFolder (folder_name);
FinishPageCompleted ();
}
public void FinishPageCompleted ()
{
SelectedPreset = Presets [0];
PreviousUrl = "";
PreviousAddress = "";
PreviousPath = "";
this.fetch_prior_history = false;
this.saved_address = "";
this.saved_remote_path = "";
this.current_page = PageType.None;
WindowIsOpen = false;
HideWindowEvent ();
}
private bool IsValidEmail (string email)
{
return email.Contains ("@");
}
}
}

View file

@ -46,14 +46,14 @@ namespace SparkleShare {
public string StatusMessage {
get {
string status_message = "Ready to sync";
if (repo.LastSync > DateTime.MinValue)
string status_message = "Waiting to sync";
if (!repo.LastSync.Equals (DateTime.MinValue))
status_message = string.Format ("✓ Synced Last change {0}", repo.LastSync.ToPrettyDate ());
if (repo.Status == SyncStatus.SyncUp)
status_message = "Sending… " + (int) repo.ProgressPercentage + "%";
if (repo.Status == SyncStatus.SyncDown)
status_message = "Receiving… " + (int) repo.ProgressPercentage + "%";
@ -136,7 +136,7 @@ namespace SparkleShare {
public delegate void UpdateQuitItemEventHandler (bool quit_item_enabled);
public IconState CurrentState = IconState.Idle;
public string StateText = "Welcome to SparkleShare";
public string StateText = "Welcome to SparkleShare!";
public ProjectInfo [] Projects = new ProjectInfo [0];
@ -147,6 +147,11 @@ namespace SparkleShare {
}
}
public bool LinkCodeItemEnabled {
get {
return !string.IsNullOrEmpty (SparkleShare.Controller.UserAuthenticationInfo.PublicKey);
}
}
public bool QuitItemEnabled {
get {
@ -302,9 +307,13 @@ namespace SparkleShare {
public void AddHostedProjectClicked ()
{
new Thread (() => SparkleShare.Controller.ShowSetupWindow (PageType.Host)).Start ();
new Thread (() => SparkleShare.Controller.ShowSetupWindow (PageType.Add)).Start ();
}
public void CopyToClipboardClicked ()
{
SparkleShare.Controller.CopyToClipboard (SparkleShare.Controller.UserAuthenticationInfo.PublicKey);
}
public void AboutClicked ()
{

Binary file not shown.

Before

Width:  |  Height:  |  Size: 2.2 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 879 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 575 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 7.1 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.2 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 24 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 17 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 8.8 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 2 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.6 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.6 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 52 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 44 KiB

View file

@ -0,0 +1,47 @@
<?xml version="1.0" encoding="UTF-8"?>
<svg height="128px" viewBox="0 0 128 128" width="128px" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
<clipPath id="a">
<rect height="128" width="128"/>
</clipPath>
<clipPath id="b">
<rect height="128" width="128"/>
</clipPath>
<filter id="c" height="100%" width="100%" x="0%" y="0%">
<feColorMatrix in="SourceGraphic" type="matrix" values="0 0 0 0 1 0 0 0 0 1 0 0 0 0 1 0 0 0 1 0"/>
</filter>
<mask id="d">
<g clip-path="url(#b)" filter="url(#c)">
<g clip-path="url(#a)">
<path d="m 20.679688 11.867188 c -4.796876 -0.023438 -8.6875 3.890624 -8.6875 8.6875 v 86.890624 h 95.453124 c 4.945313 0 8.6875 -3.441406 8.6875 -8.734374 v -70 c 0 -4.796876 -3.890624 -8.691407 -8.6875 -8.6875 l -51.445312 -0.023438 l -8 -8 z m 0 0" fill="#fb8c14"/>
<path d="m 64 34 l -8.6875 8.277344 h -34.632812 c -4.796876 0 -8.6875 3.890625 -8.6875 8.6875 v 65.167968 h 95.488281 c 4.320312 0 8.652343 -3.59375 8.652343 -8.683593 v -64.734375 c 0 -4.796875 -3.890624 -8.6875 -8.6875 -8.6875 z m 0 0" fill="#fff1db"/>
<path d="m 116.132812 105.273438 v 2.171874 c 0 4.796876 -3.890624 8.6875 -8.6875 8.6875 h -95.578124 v -2.171874 h 95.578124 c 4.796876 0 8.6875 -3.890626 8.6875 -8.6875 z m 0 0" fill="#fb8c14"/>
<path d="m 569.617711 133.878011 c -1.946492 0.248867 -3.661892 1.786506 -4.141849 3.697445 l -8.274809 24.931084 l -1.839834 0.93325 h -25.295497 c -1.413205 0 -2.790859 0.737711 -3.679668 1.848722 c -1.85761 2.0887 -1.395429 5.812809 0.915473 7.386 l 20.700355 15.24307 l 0.435517 2.213133 l -7.812629 24.468905 c -1.084347 3.821877 4.008527 7.661531 7.359336 5.546166 l 20.691467 -15.24307 h 2.64865 l 20.700355 15.24307 c 1.795394 1.182116 4.372939 0.97769 5.972795 -0.462181 c 1.350989 -1.25322 1.919827 -3.306368 1.386542 -5.075097 l -7.821517 -24.477793 c -0.737711 -0.142209 0.293307 -1.475422 0.444404 -2.213133 l 20.691467 -15.24307 c 2.319791 -1.573191 2.773083 -5.288412 0.906585 -7.386 c -0.871032 -1.111011 -2.257574 -1.804282 -3.67078 -1.848722 h -25.757677 l -1.830946 -0.924362 l -7.821516 -24.939972 c -0.231091 -0.871033 -0.719935 -1.688737 -1.386542 -2.310903 c -0.968801 -0.942137 -2.328679 -1.457646 -3.679668 -1.386542 h 0.168874 z m 0 0" fill="none" stroke="#fb8c14" stroke-linecap="round" stroke-linejoin="round" stroke-width="11.3768" transform="matrix(0.439493 0 0 0.439493 -186.44833 -3.03373)"/>
</g>
</g>
</mask>
<mask id="e">
<g filter="url(#c)">
<rect fill-opacity="0.8" height="128" width="128"/>
</g>
</mask>
<linearGradient id="f" gradientTransform="matrix(0 0.37 -0.98462 0 295.38501 -30.360001)" gradientUnits="userSpaceOnUse" x1="300" x2="428" y1="235" y2="235">
<stop offset="0" stop-color="#f9f06b"/>
<stop offset="1" stop-color="#f5c211"/>
</linearGradient>
<clipPath id="g">
<rect height="128" width="128"/>
</clipPath>
<clipPath id="h">
<rect height="128" width="128"/>
</clipPath>
<path d="m 20.679688 11.867188 c -4.796876 -0.023438 -8.6875 3.890624 -8.6875 8.6875 v 86.890624 h 95.453124 c 4.945313 0 8.6875 -3.441406 8.6875 -8.734374 v -70 c 0 -4.796876 -3.890624 -8.691407 -8.6875 -8.6875 l -51.445312 -0.023438 l -8 -8 z m 0 0" fill="#fb8c14"/>
<path d="m 64 34 l -8.6875 8.277344 h -34.632812 c -4.796876 0 -8.6875 3.890625 -8.6875 8.6875 v 65.167968 h 95.488281 c 4.320312 0 8.652343 -3.59375 8.652343 -8.683593 v -64.734375 c 0 -4.796875 -3.890624 -8.6875 -8.6875 -8.6875 z m 0 0" fill="#fff1db"/>
<path d="m 116.132812 105.273438 v 2.171874 c 0 4.796876 -3.890624 8.6875 -8.6875 8.6875 h -95.578124 v -2.171874 h 95.578124 c 4.796876 0 8.6875 -3.890626 8.6875 -8.6875 z m 0 0" fill="#fb8c14"/>
<path d="m 63.89466666052 55.80471868842 c -0.85546960856 0.10937530443 -1.60937590076 0.78515688146 -1.82031364256 1.62500119539 l -3.63672063184 10.95703690041 l -0.80859416416 0.41015684225 h -11.11719386302 c -0.62109370507 0 -1.22656299449 0.32421882052 -1.61718832832 0.81250037795 c -0.81640659173 0.9179690291 -0.6132812775 2.55468886584 0.40234397519 3.246095298 l 9.09766112002 6.69922256351 l 0.19140667288 0.97265646157 l -3.4335957571 10.75391246516 c -0.47656291607 1.67968818836 1.76171955681 3.36718924378 3.23437665665 2.43750113384 l 9.09375490623 -6.69922256351 h 1.16406313445 l 9.09766112002 6.69922256351 c 0.78906309524 0.51953170719 1.92187607993 0.42968791117 2.62500159294 -0.20312531423 c 0.59375020858 -0.55078141746 0.84375052771 -1.45312559142 0.60937550321 -2.23046960582 l -3.43750197088 -10.75781867895 c -0.32421882052 -0.06249986004 0.12890637335 -0.64843764105 0.19531244717 -0.97265646157 l 9.09375490623 -6.69922256351 c 1.01953190596 -0.69140643216 1.21875056692 -2.32422005512 0.39843776141 -3.246095298 c -0.38281246678 -0.48828155742 -0.99218796998 -0.79296930903 -1.61328211454 -0.81250037795 h -11.32031873776 l -0.80468795038 -0.40625062847 l -3.43750153139 -10.9609431142 c -0.10156287686 -0.38281290627 -0.31640639296 -0.74218809034 -0.60937550321 -1.01562569218 c -0.42578125789 -0.41406261654 -1.02343811975 -0.64062521348 -1.61718832832 -0.60937550321 h 0.07421894088 z m 0 0" fill="none" stroke="#fb8c14" stroke-linecap="round" stroke-linejoin="round" stroke-width="5.0000239624"/>
<g clip-path="url(#h)" mask="url(#d)">
<g clip-path="url(#g)" mask="url(#e)">
<path d="m 128 80.640625 v 47.359375 h -128 v -47.359375 z m 0 0" fill="url(#f)"/>
<path d="m 13.308594 80.640625 l 47.355468 47.359375 h 21.214844 l -47.359375 -47.359375 z m 42.421875 0 l 47.363281 47.359375 h 21.214844 l -47.363282 -47.359375 z m 42.429687 0 l 29.839844 29.839844 v -21.210938 l -8.628906 -8.628906 z m -98.160156 7.90625 v 21.214844 l 18.238281 18.238281 h 21.214844 z m 0 0"/>
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 5.8 KiB

View file

@ -0,0 +1,7 @@
<?xml version="1.0" encoding="UTF-8"?>
<svg height="128px" viewBox="0 0 128 128" width="128px" xmlns="http://www.w3.org/2000/svg">
<path d="m 20.679688 11.867188 c -4.796876 -0.023438 -8.6875 3.890624 -8.6875 8.6875 v 86.890624 h 95.453124 c 4.945313 0 8.6875 -3.441406 8.6875 -8.734374 v -70 c 0 -4.796876 -3.890624 -8.691407 -8.6875 -8.6875 l -51.445312 -0.023438 l -8 -8 z m 0 0" fill="#fb8c14"/>
<path d="m 64 34 l -8.6875 8.277344 h -34.632812 c -4.796876 0 -8.6875 3.890625 -8.6875 8.6875 v 65.167968 h 95.488281 c 4.320312 0 8.652343 -3.59375 8.652343 -8.683593 v -64.734375 c 0 -4.796875 -3.890624 -8.6875 -8.6875 -8.6875 z m 0 0" fill="#fff1db"/>
<path d="m 116.132812 105.273438 v 2.171874 c 0 4.796876 -3.890624 8.6875 -8.6875 8.6875 h -95.578124 v -2.171874 h 95.578124 c 4.796876 0 8.6875 -3.890626 8.6875 -8.6875 z m 0 0" fill="#fb8c14"/>
<path d="m 63.89466666052 55.80471868842 c -0.85546960856 0.10937530443 -1.60937590076 0.78515688146 -1.82031364256 1.62500119539 l -3.63672063184 10.95703690041 l -0.80859416416 0.41015684225 h -11.11719386302 c -0.62109370507 0 -1.22656299449 0.32421882052 -1.61718832832 0.81250037795 c -0.81640659173 0.9179690291 -0.6132812775 2.55468886584 0.40234397519 3.246095298 l 9.09766112002 6.69922256351 l 0.19140667288 0.97265646157 l -3.4335957571 10.75391246516 c -0.47656291607 1.67968818836 1.76171955681 3.36718924378 3.23437665665 2.43750113384 l 9.09375490623 -6.69922256351 h 1.16406313445 l 9.09766112002 6.69922256351 c 0.78906309524 0.51953170719 1.92187607993 0.42968791117 2.62500159294 -0.20312531423 c 0.59375020858 -0.55078141746 0.84375052771 -1.45312559142 0.60937550321 -2.23046960582 l -3.43750197088 -10.75781867895 c -0.32421882052 -0.06249986004 0.12890637335 -0.64843764105 0.19531244717 -0.97265646157 l 9.09375490623 -6.69922256351 c 1.01953190596 -0.69140643216 1.21875056692 -2.32422005512 0.39843776141 -3.246095298 c -0.38281246678 -0.48828155742 -0.99218796998 -0.79296930903 -1.61328211454 -0.81250037795 h -11.32031873776 l -0.80468795038 -0.40625062847 l -3.43750153139 -10.9609431142 c -0.10156287686 -0.38281290627 -0.31640639296 -0.74218809034 -0.60937550321 -1.01562569218 c -0.42578125789 -0.41406261654 -1.02343811975 -0.64062521348 -1.61718832832 -0.60937550321 h 0.07421894088 z m 0 0" fill="none" stroke="#fb8c14" stroke-linecap="round" stroke-linejoin="round" stroke-width="5.0000239624"/>
</svg>

After

Width:  |  Height:  |  Size: 2.4 KiB

View file

@ -1,6 +1,6 @@
# Install app icons in system theme
theme_dir = join_paths(get_option('prefix'), 'share', 'icons', 'hicolor')
icon_sizes = ['16', '24', '48', '256', '512']
icon_sizes = ['scalable']
app_icon_name = 'org.sparkleshare.SparkleShare'
source_icon_name = app_icon_name
@ -13,9 +13,9 @@ foreach size : icon_sizes
icon_dir = join_paths(size + 'x' + size, 'apps')
install_data(
sources: join_paths('hicolor', icon_dir, source_icon_name + '.png'),
sources: join_paths('hicolor', icon_dir, source_icon_name + '.svg'),
install_dir: join_paths(theme_dir, icon_dir),
rename: app_icon_name + '.png')
rename: app_icon_name + '.svg')
endforeach
install_data(

704
SparkleShare/Linux/Setup.cs Executable file
View file

@ -0,0 +1,704 @@
// SparkleShare, a collaboration and sharing tool.
// Copyright (C) 2010 Hylke Bons <hi@planetpeanut.uk>
//
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU General private License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General private License for more details.
//
// You should have received a copy of the GNU General private License
// along with this program. If not, see <http://www.gnu.org/licenses/>.
using System;
using Gtk;
using Mono.Unix;
using Sparkles;
namespace SparkleShare {
public class Setup : SetupWindow {
public SetupController Controller = new SetupController ();
public Setup ()
{
Controller.HideWindowEvent += delegate {
Application.Invoke (delegate { Hide (); });
};
Controller.ShowWindowEvent += delegate {
Application.Invoke (delegate {
ShowAll ();
Present ();
});
};
Controller.ChangePageEvent += delegate (PageType type, string [] warnings) {
Application.Invoke (delegate {
Reset ();
ShowPage (type, warnings);
ShowAll ();
});
};
}
public void ShowPage (PageType type, string [] warnings)
{
if (type == PageType.Setup) {
Header = "Welcome to SparkleShare!";
Description = "First off, whats your name and email?\n(visible only to team members)";
Table table = new Table (2, 3, true) {
RowSpacing = 6,
ColumnSpacing = 6
};
Label name_label = new Label ("<b>" + "Your Name:" + "</b>") {
UseMarkup = true,
Xalign = 1
};
Entry name_entry = new Entry () {
Xalign = 0,
ActivatesDefault = true
};
try {
UnixUserInfo user_info = UnixUserInfo.GetRealUser ();
if (user_info != null && user_info.RealName != null)
// Some systems append a series of "," for some reason, TODO: Report upstream
name_entry.Text = user_info.RealName.TrimEnd (",".ToCharArray ());
} catch (ArgumentException) {
// No username, not a big deal
}
Entry email_entry = new Entry () {
Xalign = 0,
ActivatesDefault = true
};
Label email_label = new Label ("<b>" + "Email:" + "</b>") {
UseMarkup = true,
Xalign = 1
};
table.Attach (name_label, 0, 1, 0, 1);
table.Attach (name_entry, 1, 2, 0, 1);
table.Attach (email_label, 0, 1, 1, 2);
table.Attach (email_entry, 1, 2, 1, 2);
VBox wrapper = new VBox (false, 9);
wrapper.PackStart (table, true, false, 0);
Button cancel_button = new Button ("Cancel");
Button continue_button = new Button ("Continue") { Sensitive = false };
Controller.UpdateSetupContinueButtonEvent += delegate (bool button_enabled) {
Application.Invoke (delegate { continue_button.Sensitive = button_enabled; });
};
name_entry.Changed += delegate { Controller.CheckSetupPage (name_entry.Text, email_entry.Text); };
email_entry.Changed += delegate { Controller.CheckSetupPage (name_entry.Text, email_entry.Text); };
cancel_button.Clicked += delegate { Controller.SetupPageCancelled (); };
continue_button.Clicked += delegate {
Controller.SetupPageCompleted (name_entry.Text, email_entry.Text);
};
AddButton (cancel_button);
AddButton (continue_button);
Add (wrapper);
Controller.CheckSetupPage (name_entry.Text, email_entry.Text);
if (name_entry.Text.Equals (""))
name_entry.GrabFocus ();
else
email_entry.GrabFocus ();
}
if (type == PageType.Add) {
Header = "Wheres your project hosted?";
VBox layout_vertical = new VBox (false, 16);
HBox layout_fields = new HBox (true, 32);
VBox layout_address = new VBox (true, 0);
VBox layout_path = new VBox (true, 0);
ListStore store = new ListStore (typeof (string), typeof (Gdk.Pixbuf), typeof (string), typeof (Preset));
SparkleTreeView tree_view = new SparkleTreeView (store) {
HeadersVisible = false,
SearchColumn = -1,
EnableSearch = false
};
ScrolledWindow scrolled_window = new ScrolledWindow () { ShadowType = ShadowType.In };
scrolled_window.SetPolicy (PolicyType.Never, PolicyType.Automatic);
// Padding column
tree_view.AppendColumn ("Padding", new Gtk.CellRendererText (), "text", 0);
tree_view.Columns [0].Cells [0].Xpad = 8;
// Icon column
tree_view.AppendColumn ("Icon", new Gtk.CellRendererPixbuf (), "pixbuf", 1);
tree_view.Columns [1].Cells [0].Xpad = 6;
// Service column
TreeViewColumn service_column = new TreeViewColumn () { Title = "Service" };
CellRendererText service_cell = new CellRendererText () { Ypad = 12 };
service_column.PackStart (service_cell, true);
service_column.SetCellDataFunc (service_cell, new TreeCellDataFunc (RenderServiceColumn));
foreach (Preset preset in Controller.Presets) {
store.AppendValues ("", new Gdk.Pixbuf (preset.ImagePath),
"<span><b>" + preset.Name + "</b>\n" +
"<span size=\"small\" fgcolor=\"" + SparkleShare.UI.SecondaryTextColor + "\">" + preset.Description + "</span>" +
"</span>", preset);
}
tree_view.AppendColumn (service_column);
scrolled_window.Add (tree_view);
Entry address_entry = new Entry () {
Text = Controller.PreviousAddress,
Sensitive = (Controller.SelectedPreset.Address == null),
ActivatesDefault = true
};
Entry path_entry = new Entry () {
Text = Controller.PreviousPath,
Sensitive = (Controller.SelectedPreset.Path == null),
ActivatesDefault = true
};
tree_view.ButtonReleaseEvent += delegate {
path_entry.GrabFocus ();
};
Label address_example = new Label () {
Xalign = 0,
UseMarkup = true,
Markup = "<span size=\"small\" fgcolor=\"" +
SparkleShare.UI.SecondaryTextColor + "\">" + Controller.SelectedPreset.AddressExample + "</span>"
};
Label path_example = new Label () {
Xalign = 0,
UseMarkup = true,
Markup = "<span size=\"small\" fgcolor=\"" +
SparkleShare.UI.SecondaryTextColor + "\">" + Controller.SelectedPreset.PathExample + "</span>"
};
TreeSelection default_selection = tree_view.Selection;
TreePath default_path = new TreePath ("" + Controller.SelectedPresetIndex);
default_selection.SelectPath (default_path);
tree_view.Model.Foreach (new TreeModelForeachFunc (
delegate (ITreeModel model, TreePath path, TreeIter iter) {
string address;
try {
address = (model.GetValue (iter, 2) as Preset).Address;
} catch (NullReferenceException) {
address = "";
}
if (!string.IsNullOrEmpty (address) &&
address.Equals (Controller.PreviousAddress)) {
tree_view.SetCursor (path, service_column, false);
Preset preset = (Preset) model.GetValue (iter, 2);
if (preset.Address != null)
address_entry.Sensitive = false;
if (preset.Path != null)
path_entry.Sensitive = false;
return true;
} else {
return false;
}
}
));
layout_address.PackStart (new Label () {
Markup = "<b>" + "Address" + "</b>",
Xalign = 0
}, true, true, 0);
layout_address.PackStart (address_entry, false, false, 0);
layout_address.PackStart (address_example, false, false, 0);
path_entry.Changed += delegate {
Controller.CheckAddPage (address_entry.Text, path_entry.Text, tree_view.SelectedRow);
};
layout_path.PackStart (new Label () {
Markup = "<b>" + "Remote Path" + "</b>",
Xalign = 0
}, true, true, 0);
layout_path.PackStart (path_entry, false, false, 0);
layout_path.PackStart (path_example, false, false, 0);
layout_fields.PackStart (layout_address, true, true, 0);
layout_fields.PackStart (layout_path, true, true, 0);
layout_vertical.PackStart (scrolled_window, true, true, 0);
layout_vertical.PackStart (layout_fields, false, false, 0);
tree_view.ScrollToCell (new TreePath ("" + Controller.SelectedPresetIndex), null, true, 0, 0);
Add (layout_vertical);
if (string.IsNullOrEmpty (path_entry.Text)) {
address_entry.GrabFocus ();
address_entry.Position = -1;
} else {
path_entry.GrabFocus ();
path_entry.Position = -1;
}
Button cancel_button = new Button ("Cancel");
Button add_button = new Button ("Add") { Sensitive = false };
Controller.ChangeAddressFieldEvent += delegate (string text,
string example_text, FieldState state) {
Application.Invoke (delegate {
address_entry.Text = text;
address_entry.Sensitive = (state == FieldState.Enabled);
address_example.Markup = "<span size=\"small\" fgcolor=\"" +
SparkleShare.UI.SecondaryTextColor + "\">" + example_text + "</span>";
});
};
Controller.ChangePathFieldEvent += delegate (string text,
string example_text, FieldState state) {
Application.Invoke (delegate {
path_entry.Text = text;
path_entry.Sensitive = (state == FieldState.Enabled);
path_example.Markup = "<span size=\"small\" fgcolor=\""
+ SparkleShare.UI.SecondaryTextColor + "\">" + example_text + "</span>";
});
};
Controller.UpdateAddProjectButtonEvent += delegate (bool button_enabled) {
Application.Invoke (delegate { add_button.Sensitive = button_enabled; });
};
tree_view.CursorChanged += delegate (object sender, EventArgs e) {
Controller.SelectedPresetChanged (tree_view.SelectedRow);
};
address_entry.Changed += delegate {
Controller.CheckAddPage (address_entry.Text, path_entry.Text, tree_view.SelectedRow);
};
cancel_button.Clicked += delegate { Controller.PageCancelled (); };
add_button.Clicked += delegate { Controller.AddPageCompleted (address_entry.Text, path_entry.Text); };
CheckButton check_button = new CheckButton ("Fetch prior revisions") { Active = false };
check_button.Toggled += delegate { Controller.HistoryItemChanged (check_button.Active); };
AddOption (check_button);
AddButton (cancel_button);
AddButton (add_button);
Controller.HistoryItemChanged (check_button.Active);
Controller.CheckAddPage (address_entry.Text, path_entry.Text, 1);
}
if (type == PageType.Invite) {
Header = "Youve received an invite!";
Description = "Do you want to add this project to SparkleShare?";
Table table = new Table (2, 3, true) {
RowSpacing = 6,
ColumnSpacing = 6
};
Label address_label = new Label ("Address:") { Xalign = 1 };
Label path_label = new Label ("Remote Path:") { Xalign = 1 };
Label address_value = new Label ("<b>" + Controller.PendingInvite.Address + "</b>") {
UseMarkup = true,
Xalign = 0
};
Label path_value = new Label ("<b>" + Controller.PendingInvite.RemotePath + "</b>") {
UseMarkup = true,
Xalign = 0
};
table.Attach (address_label, 0, 1, 0, 1);
table.Attach (address_value, 1, 2, 0, 1);
table.Attach (path_label, 0, 1, 1, 2);
table.Attach (path_value, 1, 2, 1, 2);
VBox wrapper = new VBox (false, 9);
wrapper.PackStart (table, true, false, 0);
Button cancel_button = new Button ("Cancel");
Button add_button = new Button ("Add");
cancel_button.Clicked += delegate { Controller.PageCancelled (); };
add_button.Clicked += delegate { Controller.InvitePageCompleted (); };
AddButton (cancel_button);
AddButton (add_button);
Add (wrapper);
}
if (type == PageType.Syncing) {
Header = String.Format ("Adding project {0}’…", Controller.SyncingFolder);
Description = "This may take a while for large projects.\nIsnt it coffee-oclock?";
ProgressBar progress_bar = new ProgressBar ();
progress_bar.Fraction = Controller.ProgressBarPercentage / 100;
Button cancel_button = new Button () { Label = "Cancel" };
Button finish_button = new Button ("Finish") { Sensitive = false };
Label progress_label = new Label ("Preparing to fetch files…") {
Justify = Justification.Right,
Xalign = 1
};
Controller.UpdateProgressBarEvent += delegate (double percentage, string speed) {
Application.Invoke (delegate {
progress_bar.Fraction = percentage / 100;
progress_label.Text = speed;
});
};
cancel_button.Clicked += delegate { Controller.SyncingCancelled (); };
VBox bar_wrapper = new VBox (false, 0);
bar_wrapper.PackStart (progress_bar, false, false, 21);
bar_wrapper.PackStart (progress_label, false, true, 0);
Add (bar_wrapper);
AddButton (cancel_button);
AddButton (finish_button);
}
if (type == PageType.Error) {
Header = "Oops! Something went wrong" + "…";
VBox points = new VBox (false, 0);
Image list_point_one = new Image (UserInterfaceHelpers.GetIcon ("list-point", 16));
Image list_point_two = new Image (UserInterfaceHelpers.GetIcon ("list-point", 16));
Image list_point_three = new Image (UserInterfaceHelpers.GetIcon ("list-point", 16));
Label label_one = new Label () {
Markup = "<b>" + Controller.PreviousUrl + "</b> is the address weve compiled. " +
"Does this look alright?",
Wrap = true,
Xalign = 0
};
Label label_two = new Label () {
Text = "Is this computers Client ID known by the host?",
Wrap = true,
Xalign = 0
};
points.PackStart (new Label ("Please check the following:") { Xalign = 0 }, false, false, 6);
HBox point_one = new HBox (false, 0);
point_one.PackStart (list_point_one, false, false, 0);
point_one.PackStart (label_one, true, true, 12);
points.PackStart (point_one, false, false, 12);
HBox point_two = new HBox (false, 0);
point_two.PackStart (list_point_two, false, false, 0);
point_two.PackStart (label_two, true, true, 12);
points.PackStart (point_two, false, false, 12);
if (warnings.Length > 0) {
string warnings_markup = "";
foreach (string warning in warnings)
warnings_markup += "\n<b>" + warning + "</b>";
Label label_three = new Label () {
Markup = "Heres the raw error message:" + warnings_markup,
Wrap = true,
Xalign = 0
};
HBox point_three = new HBox (false, 0);
point_three.PackStart (list_point_three, false, false, 0);
point_three.PackStart (label_three, true, true, 12);
points.PackStart (point_three, false, false, 12);
}
points.PackStart (new Label (""), true, true, 0);
Button cancel_button = new Button ("Cancel");
Button try_again_button = new Button ("Retry") { Sensitive = true };
cancel_button.Clicked += delegate { Controller.PageCancelled (); };
try_again_button.Clicked += delegate { Controller.ErrorPageCompleted (); };
AddButton (cancel_button);
AddButton (try_again_button);
Add (points);
}
if (type == PageType.StorageSetup) {
Header = string.Format ("Storage type for {0}", Controller.SyncingFolder);
Description = "What type of storage would you like to use?";
VBox layout_vertical = new VBox (false, 0);
VBox layout_radio_buttons = new VBox (false, 0) { BorderWidth = 12 };
foreach (StorageTypeInfo storage_type in SparkleShare.Controller.FetcherAvailableStorageTypes) {
RadioButton radio_button = new RadioButton (null,
storage_type.Name + "\n" + storage_type.Description);
(radio_button.Child as Label).Markup = string.Format(
"<b>{0}</b>\n<span fgcolor=\"{1}\">{2}</span>",
storage_type.Name, SparkleShare.UI.SecondaryTextColor, storage_type.Description);
(radio_button.Child as Label).Xpad = 9;
layout_radio_buttons.PackStart (radio_button, false, false, 9);
radio_button.Group = (layout_radio_buttons.Children [0] as RadioButton).Group;
}
layout_vertical.PackStart (new Label (""), true, true, 0);
layout_vertical.PackStart (layout_radio_buttons, false, false, 0);
layout_vertical.PackStart (new Label (""), true, true, 0);
Add (layout_vertical);
Button cancel_button = new Button ("Cancel");
Button continue_button = new Button ("Continue");
continue_button.Clicked += delegate {
int checkbox_index= 0;
foreach (RadioButton radio_button in layout_radio_buttons.Children) {
if (radio_button.Active) {
StorageTypeInfo selected_storage_type = SparkleShare.Controller.FetcherAvailableStorageTypes [checkbox_index];
Controller.StoragePageCompleted (selected_storage_type.Type);
return;
}
checkbox_index++;
}
};
cancel_button.Clicked += delegate {
Controller.SyncingCancelled ();
};
AddButton (cancel_button);
AddButton (continue_button);
}
if (type == PageType.CryptoSetup || type == PageType.CryptoPassword) {
if (type == PageType.CryptoSetup) {
Header = string.Format ("Encryption password for {0}", Controller.SyncingFolder);
Description = "Please a provide a strong password that you dont use elsewhere.";
} else {
Header = string.Format ("{0} contains encrypted files", Controller.SyncingFolder);
Description = "Please enter the password to see their contents.";
}
Label password_label = new Label ("<b>" + "Password" + "</b>") {
UseMarkup = true,
Xalign = 1
};
Entry password_entry = new Entry () {
Xalign = 0,
Visibility = false,
ActivatesDefault = true
};
CheckButton show_password_check_button = new CheckButton ("Make visible") {
Active = false,
Xalign = 0,
};
Table table = new Table (2, 3, true) {
RowSpacing = 6,
ColumnSpacing = 6
};
table.Attach (password_label, 0, 1, 0, 1);
table.Attach (password_entry, 1, 2, 0, 1);
table.Attach (show_password_check_button, 1, 2, 1, 2);
VBox wrapper = new VBox (false, 9);
wrapper.PackStart (table, true, false, 0);
Image warning_image = new Image (
UserInterfaceHelpers.GetIcon ("dialog-information", 24));
Label warning_label = new Label () {
Xalign = 0,
Wrap = true,
Text = "This password cant be changed later, and your files cant be recovered if its forgotten."
};
HBox warning_layout = new HBox (false, 0);
warning_layout.PackStart (warning_image, false, false, 15);
warning_layout.PackStart (warning_label, true, true, 0);
VBox warning_wrapper = new VBox (false, 0);
warning_wrapper.PackStart (warning_layout, false, false, 15);
if (type == PageType.CryptoSetup)
wrapper.PackStart (warning_wrapper, false, false, 0);
Button cancel_button = new Button ("Cancel");
Button continue_button = new Button ("Continue") { Sensitive = false };
Controller.UpdateCryptoSetupContinueButtonEvent += delegate (bool button_enabled) {
Application.Invoke (delegate { continue_button.Sensitive = button_enabled; });
};
Controller.UpdateCryptoPasswordContinueButtonEvent += delegate (bool button_enabled) {
Application.Invoke (delegate { continue_button.Sensitive = button_enabled; });
};
show_password_check_button.Toggled += delegate {
password_entry.Visibility = !password_entry.Visibility;
};
password_entry.Changed += delegate {
if (type == PageType.CryptoSetup)
Controller.CheckCryptoSetupPage (password_entry.Text);
else
Controller.CheckCryptoPasswordPage (password_entry.Text);
};
cancel_button.Clicked += delegate { Controller.CryptoPageCancelled (); };
continue_button.Clicked += delegate {
if (type == PageType.CryptoSetup)
Controller.CryptoSetupPageCompleted (password_entry.Text);
else
Controller.CryptoPasswordPageCompleted (password_entry.Text);
};
Add (wrapper);
AddButton (cancel_button);
AddButton (continue_button);
password_entry.GrabFocus ();
}
if (type == PageType.Finished) {
Header = "Your shared project is ready!";
Description = "You can find the files in your SparkleShare folder.";
UrgencyHint = true;
Button show_files_button = new Button ("Show Files");
Button finish_button = new Button ("Finish");
show_files_button.Clicked += delegate { Controller.ShowFilesClicked (); };
finish_button.Clicked += delegate { Controller.FinishPageCompleted (); };
if (warnings.Length > 0) {
Image warning_image = new Image (UserInterfaceHelpers.GetIcon ("dialog-information", 24));
Label warning_label = new Label (warnings [0]) {
Xalign = 0,
Wrap = true
};
HBox warning_layout = new HBox (false, 0);
warning_layout.PackStart (warning_image, false, false, 15);
warning_layout.PackStart (warning_label, true, true, 0);
VBox warning_wrapper = new VBox (false, 0);
warning_wrapper.PackStart (warning_layout, false, false, 0);
Add (warning_wrapper);
} else {
Add (null);
}
AddButton (show_files_button);
AddButton (finish_button);
}
}
private void RenderServiceColumn (TreeViewColumn column, CellRenderer cell,
ITreeModel model, TreeIter iter)
{
string markup = (string) model.GetValue (iter, 2);
TreeSelection selection = (column.TreeView as TreeView).Selection;
if (selection.IterIsSelected (iter))
markup = markup.Replace (SparkleShare.UI.SecondaryTextColor, SparkleShare.UI.SecondaryTextColorSelected);
else
markup = markup.Replace (SparkleShare.UI.SecondaryTextColorSelected, SparkleShare.UI.SecondaryTextColor);
(cell as CellRendererText).Markup = markup;
}
private class SparkleTreeView : TreeView {
public int SelectedRow
{
get {
TreeIter iter;
ITreeModel model;
Selection.GetSelected (out model, out iter);
return int.Parse (model.GetPath (iter).ToString ());
}
}
public SparkleTreeView (ListStore store) : base (store)
{
}
}
}
}

View file

@ -20,45 +20,90 @@ using Gtk;
namespace SparkleShare {
public class SetupWindow : Window {
public class SetupWindow : Window {
public const int Spacing = 18;
private EventBox content_area;
private EventBox option_area;
private HBox buttons;
public string Header;
public string Description;
EventBox content_area;
HBox buttons;
public SetupWindow () : base ("SparkleShare")
public SetupWindow () : base ("SparkleShare Setup")
{
IconName = "org.sparkleshare.SparkleShare";
Resizable = false;
WindowPosition = WindowPosition.Center;
WindowPosition = WindowPosition.CenterAlways;
Deletable = false;
TypeHint = Gdk.WindowTypeHint.Dialog;
SetSizeRequest (720, 540);
DeleteEvent += delegate (object sender, DeleteEventArgs args) { args.RetVal = true; };
VBox layout_vertical = new VBox (false, 0);
layout_vertical.BorderWidth = Spacing;
layout_vertical.Spacing = Spacing;
VBox layout_vertical = new VBox (false, 16);
layout_vertical.BorderWidth = 16;
this.content_area = new EventBox ();
this.option_area = new EventBox ();
this.buttons = new HBox () {
this.buttons = CreateButtonBox ();
HBox layout_actions = new HBox (false , 16);
layout_actions.PackStart (this.option_area, true, true, 0);
layout_actions.PackStart (this.buttons, false, false, 0);
layout_vertical.PackStart (this.content_area, true, true, 0);
layout_vertical.PackStart (layout_actions, false, false, 0);
base.Add (layout_vertical);
}
private HBox CreateButtonBox ()
{
return new HBox () {
BorderWidth = 0,
Homogeneous = false,
Spacing = 6
};
}
layout_vertical.PackStart (this.content_area, true, true, 0);
layout_vertical.PackStart (this.buttons, false, false, 0);
base.Add (layout_vertical);
public void AddButton (Button button)
{
(button.Child as Label).Xpad = 15;
this.buttons.Add (button);
}
public void AddOption (Widget widget)
{
this.option_area.Add (widget);
}
new public void Add (Widget widget)
{
Title = Header;
VBox layout_vertical = new VBox (false, 0);
if (!string.IsNullOrEmpty (Description)) {
Label description = new Label (Description) {
Xalign = 0,
LineWrap = true,
LineWrapMode = Pango.WrapMode.WordChar
};
layout_vertical.PackStart (description, false, false, 0);
}
if (widget != null)
layout_vertical.PackStart (widget, true, true, 0);
this.content_area.Add (layout_vertical);
}
@ -67,47 +112,28 @@ namespace SparkleShare {
Header = "";
Description = "";
if (this.option_area.Children.Length > 0)
this.option_area.Remove (this.option_area.Children [0]);
if (this.content_area.Children.Length > 0)
this.content_area.Remove (this.content_area.Children [0]);
foreach (Widget button in this.buttons)
foreach (Button button in this.buttons)
this.buttons.Remove (button);
}
public void AddButtons (object [] buttons)
{
if (!Array.Exists (buttons, button => button == null))
this.buttons.PackStart (new Label (""), true, true, 0);
foreach (Button button in buttons) {
if (button == null) {
this.buttons.PackStart (new Label (""), true, true, 0);
} else {
button.WidthRequest = 100;
this.buttons.PackStart (button, false, false, 0);
}
}
var default_button = (Button) buttons [buttons.Length - 1];
default_button.CanDefault = true;
default_button.StyleContext.AddClass ("suggested-action");
Default = default_button;
}
public void Add (object widget)
{
if (widget != null)
this.content_area.Add ((Widget) widget);
}
new public void ShowAll ()
{
Title = Header;
if (this.buttons.Children.Length > 0) {
Button default_button = (Button) this.buttons.Children [this.buttons.Children.Length - 1];
default_button.CanDefault = true;
Default = default_button;
default_button.StyleContext.AddClass ("suggested-action");
}
Present ();
base.ShowAll ();
}
}

View file

@ -5,4 +5,4 @@ Exec=sh -c "type -P sparkleshare &>/dev/null && sparkleshare || flatpak run org.
Icon=org.sparkleshare.SparkleShare
Terminal=false
X-GNOME-Autostart-enabled=true
X-AppStream-Ignore=true

View file

@ -125,15 +125,6 @@
<None Include="..\Common\Presets\own-server%402x.png">
<Link>Presets\own-server%402x.png</Link>
</None>
<None Include="..\Common\Presets\planio.png">
<Link>Presets\planio.png</Link>
</None>
<None Include="..\Common\Presets\planio.xml">
<Link>Presets\planio.xml</Link>
</None>
<None Include="..\Common\Presets\planio%402x.png">
<Link>Presets\planio%402x.png</Link>
</None>
<None Include="org.sparkleshare.SparkleShare.appdata.xml" />
<None Include="org.sparkleshare.SparkleShare.desktop" />
<None Include="org.sparkleshare.SparkleShare.Invites.desktop" />

View file

@ -216,9 +216,34 @@ namespace SparkleShare {
this.recent_events_item = new MenuItem ("Recent Changes…");
this.recent_events_item.Sensitive = Controller.RecentEventsItemEnabled;
if (!use_appindicator)
(folder_item.Submenu as Menu).Add (new SeparatorMenuItem ());
(folder_item.Submenu as Menu).Add (this.recent_events_item);
this.quit_item = new MenuItem ("Quit") { Sensitive = Controller.QuitItemEnabled };
MenuItem add_item = new MenuItem ("Sync Remote Project…");
MenuItem link_code_item = new MenuItem ("Computer ID");
if (Controller.LinkCodeItemEnabled) {
link_code_item.Submenu = new Menu ();
string link_code = SparkleShare.Controller.UserAuthenticationInfo.PublicKey.Substring (0, 20) + "...";
MenuItem code_item = new MenuItem (link_code) { Sensitive = false };
MenuItem copy_item = new MenuItem ("Copy to Clipboard");
copy_item.Activated += delegate { Controller.CopyToClipboardClicked (); };
(link_code_item.Submenu as Menu).Add (code_item);
if (!use_appindicator)
(link_code_item.Submenu as Menu).Add (new SeparatorMenuItem ());
(link_code_item.Submenu as Menu).Add (copy_item);
}
MenuItem about_item = new MenuItem ("About SparkleShare");
about_item.Activated += delegate { Controller.AboutClicked (); };
@ -227,9 +252,9 @@ namespace SparkleShare {
this.quit_item.Activated += delegate { Controller.QuitClicked (); };
this.menu.Add (new SeparatorMenuItem ());
this.menu.Add (this.recent_events_item);
this.menu.Add (add_item);
this.menu.Add (new SeparatorMenuItem ());
this.menu.Add (link_code_item);
this.menu.Add (new SeparatorMenuItem ());
this.menu.Add (about_item);
this.menu.Add (new SeparatorMenuItem ());
this.menu.Add (this.quit_item);
@ -241,7 +266,7 @@ namespace SparkleShare {
#endif
}
}
// Makes the menu visible
void ShowMenu (object o, EventArgs args)

View file

@ -101,7 +101,10 @@ namespace SparkleShare
StatusIcon.use_appindicator = true;
#else
if (StatusIcon.use_appindicator) {
Console.WriteLine ("AppIndicator not installed.");
Console.ForegroundColor = ConsoleColor.Red;
Console.WriteLine ("error: AppIndicator not found. Install AppIndicator or run with --status-icon=gtk");
Console.ResetColor ();
Environment.Exit (-1);
}
#endif
@ -165,43 +168,5 @@ namespace SparkleShare
SecondaryTextColor = UserInterfaceHelpers.ColorToHex (text_color);
SecondaryTextColorSelected = UserInterfaceHelpers.ColorToHex (text_color_selected);
}
// The bindings don't support Gtk.Widget.ScaleFactor yet
public int ScaleFactor {
get {
if (scale_factor > 0)
return scale_factor;
var gsettings = new Command ("gsettings", "get org.gnome.desktop.interface scaling-factor");
string output = gsettings.StartAndReadStandardOutput ();
// Output: "uint32 1"
try {
scale_factor = Int32.Parse (output.Substring (7));
} catch (Exception e) {
scale_factor = 1;
Logger.LogInfo ("UI", "Could not determine screen scale factor: ", e);
}
return scale_factor;
}
}
int scale_factor;
}
public class DescriptionLabel : Label
{
public DescriptionLabel (string text) : base ()
{
Sensitive = false;
Xalign = 0;
Markup = string.Format ("<span size='small'>{0}</span>", text);
}
}
}

View file

@ -1,186 +0,0 @@
// SparkleShare, a collaboration and sharing tool.
// Copyright (C) 2010 Hylke Bons <hi@planetpeanut.uk>
//
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU General private License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General private License for more details.
//
// You should have received a copy of the GNU General private License
// along with this program. If not, see <http://www.gnu.org/licenses/>.
using System;
using Sparkles;
using Gtk;
namespace SparkleShare {
public class AddressPage : Page {
Entry address_entry;
DescriptionLabel address_example;
Entry path_entry;
DescriptionLabel path_example;
Label public_key_label;
Button copy_button;
Button add_button;
public AddressPage (PageType page_type, PageController controller) : base (page_type, controller)
{
Header = "Wheres your project hosted?";
Description = "";
Controller.PageCanContinueEvent += AddressPageCanContinueEventHandler;
Controller.AddressPagePublicKeyEvent += AddressPagePublicKeyEventHandler;
}
public override void Dispose ()
{
Controller.PageCanContinueEvent -= AddressPageCanContinueEventHandler;
Controller.AddressPagePublicKeyEvent -= AddressPagePublicKeyEventHandler;
}
public override object Render ()
{
// Address entry
address_entry = new Entry () {
Text = Controller.SelectedPreset.Address,
ActivatesDefault = true
};
address_example = new DescriptionLabel (Controller.SelectedPreset.AddressExample) { Xalign = 1 };
address_entry.Changed += delegate { Controller.CheckAddressPage (address_entry.Text, path_entry.Text); };
VBox layout_address = new VBox (false, 6);
layout_address.PackStart (new Label () {
Markup = "<b>Address</b>",
Xalign = 0 }, true, true, 0);
layout_address.PackStart (address_entry, false, false, 0);
layout_address.PackStart (address_example, false, false, 0);
path_entry = new Entry () {
Text = Controller.SelectedPreset.Path,
ActivatesDefault = true
};
path_entry.ClipboardPasted += delegate {
try {
path_entry.Text = new Uri (path_entry.Text).AbsolutePath;
path_entry.Position = path_entry.Text.Length;
} catch {
}
};
path_example = new DescriptionLabel (Controller.SelectedPreset.Path) { Xalign = 1 };
path_entry.Changed += delegate { Controller.CheckAddressPage (address_entry.Text, path_entry.Text); };
VBox layout_path = new VBox (false, 6);
layout_path.PackStart (new Label () {
Markup = "<b>Remote Path</b>",
Xalign = 0 }, true, true, 0);
layout_path.PackStart (path_entry, false, false, 0);
layout_path.PackStart (path_example, false, false, 0);
if (string.IsNullOrEmpty (path_entry.Text)) {
address_entry.GrabFocus ();
address_entry.Position = -1;
} else {
path_entry.GrabFocus ();
path_entry.Position = -1;
}
public_key_label = new Label () {
Markup = "Authenticating…\n",
UseMarkup = true,
Xalign = 0,
Yalign = 0
};
copy_button = new Button ("Copy") {
Visible = false,
NoShowAll = true
};
copy_button.Clicked += delegate {
SparkleShare.Controller.CopyToClipboard (SparkleShare.Controller.UserAuthenticationInfo.PublicKey);
};
var copy_layout = new HBox (false, 0);
copy_layout.PackStart (copy_button, false, false, 0);
VBox layout_fields = new VBox (false, 0) { BorderWidth = 24 };
layout_fields.PackStart (layout_address, false, false, 12);
layout_fields.PackStart (layout_path, false, false, 12);
layout_fields.PackStart (new Label () {
Markup = "<b>" + "Public Key" + "</b>",
Xalign = 0,
Yalign = 0
}, false, false, 12);
layout_fields.PackStart (public_key_label, false, false, 0);
layout_fields.PackStart (copy_layout, false, false, 12);
// Buttons
Button cancel_button = new Button ("Cancel");
add_button = new Button ("Add") { Sensitive = false };
cancel_button.Clicked += delegate { Controller.CancelClicked (RequestedType); };
add_button.Clicked += delegate { Controller.AddressPageCompleted ( address_entry.Text, path_entry.Text); };
Button back_button = new Button ("Back");
back_button.Clicked += delegate { Controller.BackClicked (RequestedType); };
Buttons = new Button [] { cancel_button, null, back_button, add_button };
var padding = new HBox (false, 0);
padding.PackStart (layout_fields, true, true, 128);
// Layout
return padding;
}
void AddressPagePublicKeyEventHandler (bool authenticated, string auth_status, string key_entry_hint)
{
Application.Invoke (delegate {
public_key_label.Markup = auth_status;
if (!authenticated) {
public_key_label.Markup = key_entry_hint + "\n" + "<span fgcolor=\"" +
SparkleShare.UI.SecondaryTextColor + "\">" + auth_status + "</span>";
copy_button.Show ();
}
});
}
void AddressPageCanContinueEventHandler (PageType page_type, bool can_continue)
{
if (page_type == RequestedType)
Application.Invoke (delegate { add_button.Sensitive = can_continue; });
}
}
}

View file

@ -1,153 +0,0 @@
// SparkleShare, a collaboration and sharing tool.
// Copyright (C) 2010 Hylke Bons <hi@planetpeanut.uk>
//
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU General private License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General private License for more details.
//
// You should have received a copy of the GNU General private License
// along with this program. If not, see <http://www.gnu.org/licenses/>.
using System;
using Gtk;
namespace SparkleShare {
public class CryptoSetupPage : Page {
Button continue_button;
public CryptoSetupPage (PageType page_type, PageController controller) : base (page_type, controller)
{
if (RequestedType == PageType.CryptoSetup) {
Header = string.Format ("Encryption password for {0}", Controller.FetchAddress.AbsolutePath);
Description = "Please a provide a strong password that you dont use elsewhere.";
} else {
Header = string.Format ("{0} contains encrypted files", Controller.FetchAddress.AbsolutePath);
Description = "Please enter the password to see their contents.";
}
Controller.PageCanContinueEvent += CryptoPageCanContinueEventHandler;
}
public override void Dispose ()
{
Controller.PageCanContinueEvent -= CryptoPageCanContinueEventHandler;
}
public override object Render ()
{
// Password entry
Label password_label = new Label ("<b>" + "Password" + "</b>") {
UseMarkup = true,
Xalign = 1
};
Entry password_entry = new Entry () {
Xalign = 0,
Visibility = false,
ActivatesDefault = true
};
password_entry.Changed += delegate {
if (RequestedType == PageType.CryptoSetup)
Controller.CheckCryptoSetupPage (password_entry.Text);
else
Controller.CheckCryptoPasswordPage (password_entry.Text);
};
password_entry.GrabFocus ();
// Checkbox
CheckButton show_password_check_button = new CheckButton ("Make visible") {
Active = false,
Xalign = 0,
};
show_password_check_button.Toggled += delegate {
password_entry.Visibility = !password_entry.Visibility;
};
// Buttons
Button cancel_button = new Button ("Cancel");
cancel_button.Clicked += delegate { Controller.CancelClicked (RequestedType); };
continue_button = new Button ("Continue") { Sensitive = false };
continue_button.Clicked += delegate { Controller.CryptoPageCompleted (password_entry.Text); };
Buttons = new Button [] { cancel_button, continue_button };
// Layout
Table table = new Table (2, 3, true) {
RowSpacing = 6,
ColumnSpacing = 6
};
table.Attach (password_label, 0, 1, 0, 1);
table.Attach (password_entry, 1, 2, 0, 1);
table.Attach (show_password_check_button, 1, 2, 1, 2);
VBox wrapper = new VBox (false, 9);
wrapper.PackStart (table, true, false, 0);
if (RequestedType == PageType.CryptoSetup)
wrapper.PackStart (RenderWarning (), false, false, 0);
return wrapper;
}
VBox RenderWarning ()
{
var image = new Image (
UserInterfaceHelpers.GetIcon ("dialog-information-symbolic", 24));
Label label = new Label () {
Xalign = 0,
Wrap = true,
Text = "This password cant be changed later, and your files cant be recovered if its forgotten."
};
// Layout
HBox layout = new HBox (false, 0);
layout.PackStart (image, false, false, 16);
layout.PackStart (label, true, true, 0);
VBox wrapper = new VBox (false, 0);
wrapper.PackStart (layout, false, false, 16);
return wrapper;
}
void CryptoPageCanContinueEventHandler (PageType page_type, bool can_continue)
{
if (page_type == RequestedType)
Application.Invoke (delegate { continue_button.Sensitive = can_continue; });
}
}
public class CryptoPasswordPage : CryptoSetupPage {
public CryptoPasswordPage (PageType page_type, PageController controller) : base (page_type, controller)
{
}
}
}

View file

@ -1,169 +0,0 @@
// SparkleShare, a collaboration and sharing tool.
// Copyright (C) 2010 Hylke Bons <hi@planetpeanut.uk>
//
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU General private License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General private License for more details.
//
// You should have received a copy of the GNU General private License
// along with this program. If not, see <http://www.gnu.org/licenses/>.
using System;
using Sparkles;
using Gtk;
namespace SparkleShare {
public class HostPage : Page {
SparkleTreeView tree_view;
TreeViewColumn service_column;
public HostPage (PageType page_type, PageController controller) : base (page_type, controller)
{
Header = "Wheres your project hosted?";
Description = "";
}
public override object Render ()
{
// Host selection
ListStore store = new ListStore (typeof (string), typeof (Gdk.Pixbuf), typeof (string), typeof (Preset));
tree_view = new SparkleTreeView (store) {
HeadersVisible = false,
SearchColumn = -1,
EnableSearch = false
};
tree_view.CursorChanged += delegate { Controller.SelectedPresetChanged (tree_view.SelectedRow); };
// Padding column
tree_view.AppendColumn ("Padding", new Gtk.CellRendererText (), "text", 0);
tree_view.Columns [0].Cells [0].Xpad = 8;
// Icon column
tree_view.AppendColumn ("Icon", new Gtk.CellRendererPixbuf (), "pixbuf", 1);
tree_view.Columns [1].Cells [0].Xpad = 6;
// Service column
service_column = new TreeViewColumn () { Title = "Service" };
CellRendererText service_cell = new CellRendererText () { Ypad = 12 };
service_column.PackStart (service_cell, true);
service_column.SetCellDataFunc (service_cell, new TreeCellDataFunc (RenderServiceColumn));
tree_view.AppendColumn (service_column);
// Fill the list
foreach (Preset preset in Controller.Presets) {
store.AppendValues ("", new Gdk.Pixbuf (preset.IconPath),
string.Format ("<span><b>{0}</b>\n<span size='small' fgcolor='{1}'>{2}</span></span>",
preset.Name, SparkleShare.UI.SecondaryTextColor, preset.Description),
preset);
}
tree_view.Model.Foreach (new TreeModelForeachFunc (TreeModelForeachFuncHandler));
TreeSelection default_selection = tree_view.Selection;
TreePath default_path = new TreePath ("" + Controller.SelectedPresetIndex);
default_selection.SelectPath (default_path);
tree_view.ScrollToCell (new TreePath ("" + Controller.SelectedPresetIndex), null, true, 0, 0);
ScrolledWindow scrolled_window = new ScrolledWindow () { ShadowType = ShadowType.In };
scrolled_window.SetPolicy (PolicyType.Never, PolicyType.Automatic);
scrolled_window.Add (tree_view);
// Buttons
Button cancel_button = new Button ("Cancel");
Button continue_button = new Button ("Continue");
cancel_button.Clicked += delegate { Controller.CancelClicked (RequestedType); };
continue_button.Clicked += delegate { Controller.HostPageCompleted (); };
Button back_button = new Button ("Back");
back_button.Clicked += delegate { Controller.BackClicked (RequestedType); };
Buttons = new Button [] { cancel_button, null, back_button, continue_button };
// Layout
VBox layout_vertical = new VBox (false, 16);
layout_vertical.PackStart (scrolled_window, true, true, 0);
return layout_vertical;
}
void RenderServiceColumn (TreeViewColumn column, CellRenderer cell, ITreeModel model, TreeIter iter)
{
string markup = (string) model.GetValue (iter, 2);
TreeSelection selection = (column.TreeView as TreeView).Selection;
if (selection.IterIsSelected (iter))
markup = markup.Replace (SparkleShare.UI.SecondaryTextColor, SparkleShare.UI.SecondaryTextColorSelected);
else
markup = markup.Replace (SparkleShare.UI.SecondaryTextColorSelected, SparkleShare.UI.SecondaryTextColor);
(cell as CellRendererText).Markup = markup;
}
bool TreeModelForeachFuncHandler (ITreeModel model, TreePath path, TreeIter iter)
{
string address;
try {
address = (model.GetValue (iter, 2) as Preset).Address;
} catch (NullReferenceException) {
address = "";
}
if (!string.IsNullOrEmpty (address) &&
address.Equals (Controller.FetchAddress.Host)) { // TODO Check selection
tree_view.SetCursor (path, service_column, false);
//Preset preset = (Preset) model.GetValue (iter, 2);
return true;
} else {
return false;
}
}
class SparkleTreeView : TreeView {
public int SelectedRow
{
get {
TreeIter iter;
ITreeModel model;
Selection.GetSelected (out model, out iter);
return int.Parse (model.GetPath (iter).ToString ());
}
}
public SparkleTreeView (ListStore store) : base (store)
{
}
}
}
}

View file

@ -1,75 +0,0 @@
// SparkleShare, a collaboration and sharing tool.
// Copyright (C) 2010 Hylke Bons <hi@planetpeanut.uk>
//
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU General private License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General private License for more details.
//
// You should have received a copy of the GNU General private License
// along with this program. If not, see <http://www.gnu.org/licenses/>.
using System;
using Gtk;
namespace SparkleShare {
public class InvitePage : Page {
public InvitePage (PageType page_type, PageController controller) : base (page_type, controller)
{
Header = "Youve received an invite!";
Description = "Do you want to add this project to SparkleShare?";
// Buttons
Button cancel_button = new Button ("Cancel");
Button add_button = new Button ("Add");
cancel_button.Clicked += delegate { Controller.CancelClicked (RequestedType); };
add_button.Clicked += delegate { Controller.InvitePageCompleted (); };
Buttons = new Button [] {cancel_button, add_button };
}
public override object Render ()
{
// Labels
Label address_label = new Label ("Address:") { Xalign = 1 };
Label address_value = new Label ("<b>" + Controller.PendingInvite.Address + "</b>") {
UseMarkup = true,
Xalign = 0
};
Label path_label = new Label ("Remote Path:") { Xalign = 1 };
Label path_value = new Label ("<b>" + Controller.PendingInvite.RemotePath + "</b>") {
UseMarkup = true,
Xalign = 0
};
// Layout
Table table = new Table (2, 3, true) {
RowSpacing = 6,
ColumnSpacing = 6
};
table.Attach (address_label, 0, 1, 0, 1);
table.Attach (address_value, 1, 2, 0, 1);
table.Attach (path_label, 0, 1, 1, 2);
table.Attach (path_value, 1, 2, 1, 2);
VBox wrapper = new VBox (false, 9);
wrapper.PackStart (table, true, false, 0);
return wrapper;
}
}
}

View file

@ -1,143 +0,0 @@
// SparkleShare, a collaboration and sharing tool.
// Copyright (C) 2010 Hylke Bons <hi@planetpeanut.uk>
//
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU General private License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General private License for more details.
//
// You should have received a copy of the GNU General private License
// along with this program. If not, see <http://www.gnu.org/licenses/>.
using System;
using Gtk;
namespace SparkleShare {
public class PrivacyPage : Page {
Switch notification_service_switch;
Switch crash_reports_switch;
Switch gravatars_switch;
public PrivacyPage (PageType page_type, PageController controller) : base (page_type, controller)
{
Header = "Privacy Preferences";
Description = "";
}
public override void Dispose ()
{
}
public override object Render ()
{
var intro_label = new Label () {
Text = "SparkleShare is decentralized, so no account of any sort is created.\n" +
"However, some features can affect your privacy:",
LineWrap = true,
LineWrapMode = Pango.WrapMode.Word,
MaxWidthChars = 48,
Xalign = 0
};
HBox notification_service_layout = SwitchLayout ("Notification Service",
"Instantly syncs when someone makes a change by sending a notification " +
"via <a href='https://www.sparkleshare.org/'>sparkleshare.org</a>. " +
"No personal or usage data is recorded.", recommended: true);
notification_service_switch = (Switch) (notification_service_layout.Children [0] as Box).Children [0];
HBox crash_reports_layout = SwitchLayout ("Crash Reports",
"In the unlikely event of a SparkleShare crash, sends an anonymized report to " +
"the project maintainers to help fix bugs.", recommended: false);
crash_reports_switch = (Switch) (crash_reports_layout.Children [0] as Box).Children [0];
HBox gravatars_layout = SwitchLayout ("Gravatars",
"Uses <a href='https://www.gravatar.com/'>gravatar.com</a> to download " +
"profile pictures.", recommended: false);
gravatars_switch = (Switch) (gravatars_layout.Children [0] as Box).Children [0];
// Tip
var tip_label = new Label ("You will be able to change these preferences later.") { Xalign = 0 };
// Buttons
Button quit_button = new Button ("Quit");
quit_button.Clicked += delegate { Controller.QuitClicked (); };
Button back_button = new Button ("Back");
back_button.Clicked += delegate { Controller.BackClicked (RequestedType); };
Button continue_button = new Button ("Continue");
continue_button.Clicked += ContinueButtonClickedHandler;
Buttons = new Button [] { quit_button, null, back_button, continue_button };
// Layout
var layout = new VBox (false, 0) { MarginLeft = 32, MarginRight = 12 };
layout.PackStart (intro_label, false, false, 32);
layout.PackStart (notification_service_layout, false, false, 12);
layout.PackStart (crash_reports_layout, false, false, 12);
layout.PackStart (gravatars_layout, false, false, 12);
layout.PackStart (tip_label, false, false, 32);
return layout;
}
void ContinueButtonClickedHandler (object sender, EventArgs args)
{
Controller.PrivacyPageCompleted (
notification_service: notification_service_switch.Active,
crash_reports: crash_reports_switch.Active,
gravatars: gravatars_switch.Active);
}
HBox SwitchLayout (string title, string description, bool recommended)
{
var light_switch = new Switch () { Active = recommended, HeightRequest = 36 };
string recommended_text = "";
if (recommended)
recommended_text = " Recommended";
var label = new Label () {
Markup = string.Format ("<b>{0}</b>{1}\n<span fgcolor='{2}'>{3}</span>",
title, recommended_text, SparkleShare.UI.SecondaryTextColor, description),
LineWrap = true,
LineWrapMode = Pango.WrapMode.Word,
MaxWidthChars = 48,
Xalign = 0
};
var box = new VBox (false, 0);
box.PackStart (light_switch, false, false, 6);
var layout = new HBox (false, 0) { MarginLeft = 24 };
layout.PackStart (box, false, false, 0);
layout.PackStart (label, true, true, 24);
return layout;
}
}
}

View file

@ -1,186 +0,0 @@
// SparkleShare, a collaboration and sharing tool.
// Copyright (C) 2010 Hylke Bons <hi@planetpeanut.uk>
//
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU General private License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General private License for more details.
//
// You should have received a copy of the GNU General private License
// along with this program. If not, see <http://www.gnu.org/licenses/>.
using System;
using Sparkles; // TODO: remove
using Gtk;
namespace SparkleShare {
public class ProgressPage : Page {
Image image;
Label status_label;
Label status_details_label;
ProgressBar progress_bar;
Label progress_label;
public ProgressPage (PageType page_type, PageController controller) : base (page_type, controller)
{
Header = String.Format ("Getting files from {0}", Controller.SelectedPreset.Name);
Description = "Depending on its size, it may be a good time to make some tea.";
Controller.ProgressPageBarEvent += ProgressPageBarEventHandler;
}
public override void Dispose ()
{
Controller.ProgressPageBarEvent -= ProgressPageBarEventHandler;
// TODO: State handling
}
public override object Render ()
{
// image = new Image ();
// Progress bar
progress_bar = new ProgressBar ();
progress_bar.Fraction = Controller.ProgressBarPercentage / 100;
progress_label = new Label () {
Markup = string.Format ("Getting files from <b>{0}</b>", Controller.FetchAddress.Authority),
Xalign = 0
};
Buttons = ProgressButtons ();
// UrgencyHint = true; TODO
//VBox wrapper = new VBox (false, 0);
/* TODO
// Buttons
Button show_files_button = new Button ("Show Files");
Button finish_button = new Button ("Finish");
show_files_button.Clicked += delegate { Controller.ShowFilesClicked (); };
finish_button.Clicked += delegate { Controller.FinishPageCompleted (); };
Buttons = new Button [] { show_files_button, finish_button };
if (warnings.Length > 0) {
Image warning_image = new Image (UserInterfaceHelpers.GetIcon ("dialog-information", 24));
Label warning_label = new Label (warnings [0]) {
Xalign = 0,
Wrap = true
};
HBox warning_layout = new HBox (false, 0);
warning_layout.PackStart (warning_image, false, false, 15);
warning_layout.PackStart (warning_label, true, true, 0);
VBox wrapper = new VBox (false, 0);
wrapper.PackStart (warning_layout, false, false, 0);
Add (wrapper);
} else {
Add (null);
}
*/
image = new Image (Controller.SelectedPreset.LogoPath);
image = new Image ("dialog-error-symbolic", (IconSize) 128);
status_label = new Label () { Markup = "<b>" + Header + "</b>" };
status_details_label = new Label ("error goes here");
var status_layout = new VBox (false, 0);
status_layout.PackStart (image, false, false, 12);
status_layout.PackStart (status_label, false, false, 6);
status_layout.PackStart (status_details_label, false, false, 0);
// Layout
VBox layout = new VBox (false, 0) { BorderWidth = 48 };
layout.PackStart (status_layout, true, true, 0);
layout.PackStart (progress_bar, false, false, 24);
layout.PackStart (progress_label, false, false, 0);
return layout;
}
void ProgressPageBarEventHandler (bool? success,
string status, string status_details,
double progress, string progress_details)
{
Application.Invoke (delegate {
status_label.Markup = "<b>" + status + "</b>";
status_details_label.Text = status_details;
progress_bar.Sensitive = success.GetValueOrDefault ();
progress_bar.Fraction = progress / 100;
progress_label.Text = progress_details;
});
}
Button [] ProgressButtons ()
{
var cancel_button = new Button ("Cancel");
cancel_button.Clicked += delegate { Controller.CancelClicked (RequestedType); };
var back_button = new Button ("Back") { Sensitive = false };
var done_button = new Button ("Done") { Sensitive = false };
return new Button [] { cancel_button, null, back_button, done_button };
}
Button [] ErrorButtons ()
{
var cancel_button = new Button ("Cancel");
cancel_button.Clicked += delegate { Controller.CancelClicked (RequestedType); };
var back_button = new Button ("Back");
back_button.Clicked += delegate { Controller.BackClicked (RequestedType); };
var retry_button = new Button ("Retry");
retry_button.Clicked += delegate {
// TODO
};
return new Button [] { cancel_button, null, back_button, retry_button };
}
Button [] SuccessButtons ()
{
var open_files_button = new Button ("Open Files");
open_files_button.Clicked += delegate {
Controller.ShowFilesClicked (); // TODO
};
var done_button = new Button ("Done");
done_button.Clicked += delegate {
Controller.ProgressPageCompleted ();
};
return new Button [] { open_files_button, done_button };
}
}
}

View file

@ -1,85 +0,0 @@
// SparkleShare, a collaboration and sharing tool.
// Copyright (C) 2010 Hylke Bons <hi@planetpeanut.uk>
//
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU General private License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General private License for more details.
//
// You should have received a copy of the GNU General private License
// along with this program. If not, see <http://www.gnu.org/licenses/>.
using System;
using Sparkles;
using Gtk;
namespace SparkleShare {
public class StoragePage : Page {
public StoragePage (PageType page_type, PageController controller) : base (page_type, controller)
{
Header = string.Format ("Storage type for {0}", Controller.FetchAddress.AbsolutePath);
Description = "What type of storage would you like to use?";
}
public override object Render ()
{
// Radio buttons
VBox radio_buttons = new VBox (false, 0) { BorderWidth = 12 };
foreach (StorageTypeInfo storage_type in SparkleShare.Controller.FetcherAvailableStorageTypes) {
RadioButton radio_button = new RadioButton (null,
storage_type.Name + "\n" + storage_type.Description);
(radio_button.Child as Label).Markup =
string.Format("<b>{0}</b>\n<span fgcolor=\"{1}\">{2}</span>",
storage_type.Name, SparkleShare.UI.SecondaryTextColor, storage_type.Description);
(radio_button.Child as Label).Xpad = 9;
radio_buttons.PackStart (radio_button, false, false, 9);
radio_button.Group = (radio_buttons.Children [0] as RadioButton).Group;
}
// Buttons
Button cancel_button = new Button ("Cancel");
cancel_button.Clicked += delegate { Controller.CancelClicked (RequestedType); };
Button continue_button = new Button ("Continue");
continue_button.Clicked += delegate {
int checkbox_index= 0;
foreach (RadioButton radio_button in radio_buttons.Children) {
if (radio_button.Active) {
StorageTypeInfo selected_storage_type = SparkleShare.Controller.FetcherAvailableStorageTypes [checkbox_index];
Controller.StoragePageCompleted (selected_storage_type.Type);
return;
}
checkbox_index++;
}
};
Buttons = new Button [] { cancel_button, continue_button };
// Layout
VBox layout = new VBox (false, 0);
layout.PackStart (new Label (""), true, true, 0);
layout.PackStart (radio_buttons, false, false, 0);
layout.PackStart (new Label (""), true, true, 0);
return layout;
}
}
}

View file

@ -1,145 +0,0 @@
// SparkleShare, a collaboration and sharing tool.
// Copyright (C) 2010 Hylke Bons <hi@planetpeanut.uk>
//
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU General private License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General private License for more details.
//
// You should have received a copy of the GNU General private License
// along with this program. If not, see <http://www.gnu.org/licenses/>.
using System;
using Sparkles;
using Gtk;
using Mono.Unix;
namespace SparkleShare {
public class UserPage : Page {
Entry name_entry;
Entry email_entry;
Button continue_button;
public UserPage (PageType page_type, PageController controller) : base (page_type, controller)
{
Header = "Welcome to SparkleShare";
Description = "Hello. Let's get you set up.";
Controller.PageCanContinueEvent += UserPageCanContinueEventHandler;
}
public override void Dispose ()
{
Controller.PageCanContinueEvent -= UserPageCanContinueEventHandler;
}
public override object Render ()
{
// Name
Label name_label = new Label () {
Markup = "<b>Name</b>",
Xalign = 0
};
name_entry = new Entry ();
name_entry.Changed += delegate { Controller.CheckUserPage (name_entry.Text, email_entry.Text); };
// TODO: fill name and email when Back was pressed on privacy page
/* TODO broken
try {
UnixUserInfo user_info = UnixUserInfo.GetRealUser ();
if (user_info != null && user_info.RealName != null) {
// Some systems append a series of "," for some reason
string name = "" + user_info.RealName;
name_entry.Text = name;
}
} catch (Exception) {
// No username, not a big deal
}
*/
// Email
Label email_label = new Label () {
Markup = "<b>Email</b>",
Xalign = 0
};
email_entry = new Entry () { ActivatesDefault = true };
email_entry.Changed += delegate { Controller.CheckUserPage (name_entry.Text, email_entry.Text); };
var data_hint = new DescriptionLabel (
"The following information is used to mark your changes in a project's history. " +
"It won't be sent anywhere, but will be visible to those working on the same project.") {
LineWrap = true,
LineWrapMode = Pango.WrapMode.Word,
MaxWidthChars = 48
};
// Buttons
Button quit_button = new Button ("Quit");
quit_button.Clicked += delegate { Controller.QuitClicked (); };
continue_button = new Button ("Continue") { Sensitive = false };
continue_button.Clicked += delegate { Controller.UserPageCompleted (name_entry.Text, email_entry.Text); };
Buttons = new Button [] { quit_button, continue_button };
if (name_entry.Text.Equals (""))
name_entry.GrabFocus ();
else
email_entry.GrabFocus ();
Controller.CheckUserPage (name_entry.Text, email_entry.Text);
// Layout
VBox layout = new VBox (false, 9) { BorderWidth = 64 };
layout.PackStart (new Label (Description) { Xalign = 0 }, false, false, 0);
layout.PackStart (data_hint, false, false, 0);
VBox layout_fields = new VBox (false, 0) { BorderWidth = 32 };
VBox layout_name = new VBox (false, 6);
layout_name.PackStart (name_label, false, false, 0);
layout_name.PackStart (name_entry, false, false, 0);
VBox layout_email = new VBox (false, 6);
layout_email.PackStart (email_label, false, false, 0);
layout_email.PackStart (email_entry, false, false, 0);
layout_fields.PackStart (layout_name, false, false, 12);
layout_fields.PackStart (layout_email, false, false, 12);
layout.PackStart (layout_fields, false, false, 0);
return layout;
}
void UserPageCanContinueEventHandler (PageType page_type, bool can_continue)
{
if (page_type == RequestedType)
Application.Invoke (delegate { continue_button.Sensitive = can_continue; });
}
}
}

View file

@ -1,76 +0,0 @@
// SparkleShare, a collaboration and sharing tool.
// Copyright (C) 2010 Hylke Bons <hi@planetpeanut.uk>
//
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU General private License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General private License for more details.
//
// You should have received a copy of the GNU General private License
// along with this program. If not, see <http://www.gnu.org/licenses/>.
using System;
using Gtk;
using Sparkles;
namespace SparkleShare {
public class Setup : SetupWindow {
public PageController Controller = new PageController ();
Page active_page;
public Setup ()
{
Controller.HideWindowEvent += () => {
Application.Invoke (delegate {
Hide ();
if (active_page != null) {
active_page.Dispose ();
active_page = null;
}
});
};
Controller.ShowWindowEvent += () => {
Application.Invoke (delegate {
ShowAll ();
Present ();
});
};
Controller.ChangePageEvent += (PageType type) => {
Application.Invoke (delegate {
Reset ();
ShowPage (type);
ShowAll ();
Present ();
});
};
}
void ShowPage (PageType page_type)
{
System.Type t = System.Type.GetType ("SparkleShare." + page_type + "Page", throwOnError: true);
Page page = (Page) Activator.CreateInstance (t, new object [] { page_type, Controller });
Header = page.Header;
Description = page.Description;
Add (page.Render ());
AddButtons (page.Buttons);
active_page = page;
}
}
}

View file

@ -31,7 +31,7 @@ namespace SparkleShare {
icon_theme.AppendSearchPath (Path.Combine (UserInterface.AssetsPath, "icons"));
foreach (string search_path in IconTheme.Default.SearchPath)
icon_theme.AppendSearchPath (search_path);
icon_theme.AppendSearchPath (search_path);
try {
return icon_theme.LoadIcon (name, size, IconLookupFlags.GenericFallback);
@ -51,9 +51,6 @@ namespace SparkleShare {
public static Image GetImage (string name)
{
// if (SparkleShare.UI.ScaleFactor > 1)
// name += string.Format ("@{0}x", SparkleShare.UI.ScaleFactor);
string image_path = Path.Combine (UserInterface.AssetsPath, "pixmaps", name);
return new Image (image_path);
}

View file

@ -5,35 +5,18 @@ sparkleshare_src = ['../Common/SparkleShare.cs',
'../Common/BaseController.cs',
'../Common/EventLogController.cs',
'../Common/NoteController.cs',
'../Common/Page.cs',
'../Common/PageController.cs',
'../Common/PageControllers/PageController.Address.cs',
'../Common/PageControllers/PageController.Crypto.cs',
'../Common/PageControllers/PageController.Host.cs',
'../Common/PageControllers/PageController.Invite.cs',
'../Common/PageControllers/PageController.Progress.cs',
'../Common/PageControllers/PageController.Privacy.cs',
'../Common/PageControllers/PageController.User.cs',
'../Common/PageControllers/PageController.Storage.cs',
'../Common/SetupController.cs',
'../Common/StatusIconController.cs',
'About.cs',
'Bubbles.cs',
'Controller.cs',
'UserInterface/About.cs',
'UserInterface/Bubbles.cs',
'UserInterface/EventLog.cs',
'UserInterface/Note.cs',
'UserInterface/Setup.cs',
'UserInterface/SetupWindow.cs',
'UserInterface/StatusIcon.cs',
'UserInterface/UserInterface.cs',
'UserInterface/UserInterfaceHelpers.cs',
'UserInterface/Pages/Page.Address.cs',
'UserInterface/Pages/Page.Crypto.cs',
'UserInterface/Pages/Page.Host.cs',
'UserInterface/Pages/Page.Invite.cs',
'UserInterface/Pages/Page.Privacy.cs',
'UserInterface/Pages/Page.Progress.cs',
'UserInterface/Pages/Page.Storage.cs',
'UserInterface/Pages/Page.User.cs']
'EventLog.cs',
'Note.cs',
'Setup.cs',
'SetupWindow.cs',
'StatusIcon.cs',
'UserInterface.cs',
'UserInterfaceHelpers.cs']
# Startup script
@ -47,7 +30,7 @@ configure_file(
apps_dir = join_paths(get_option('prefix'), 'share', 'applications')
install_data(sources: 'org.sparkleshare.SparkleShare.Invites.desktop', install_dir: apps_dir)
install_data(sources: 'SparkleShare.Autostart.desktop', install_dir: apps_dir)
install_data(sources: 'org.sparkleshare.SparkleShare.appdata.xml', install_dir: join_paths(get_option('prefix'), 'share', 'appdata'))
install_data(sources: 'org.sparkleshare.SparkleShare.appdata.xml', install_dir: join_paths(get_option('prefix'), 'share', 'metainfo'))
if get_option('nightly')
install_data(sources: 'org.sparkleshare.SparkleShare.Nightly.desktop',

View file

@ -1,5 +1,5 @@
<?xml version="1.0" encoding="UTF-8"?>
<component type="desktop">
<component type="desktop-application">
<name>SparkleShare</name>
<summary>Magic self hosted Git file sync</summary>
<developer_name>Hylke Bons</developer_name>
@ -64,13 +64,13 @@
</screenshot>
</screenshots>
<id type="desktop">org.sparkleshare.SparkleShare.desktop</id>
<launchable id="desktop-id">org.sparkleshare.SparkleShare.desktop</launchable>
<id>org.sparkleshare.SparkleShare</id>
<launchable type="desktop-id">org.sparkleshare.SparkleShare.desktop</launchable>
<provides>
<binary>sparkleshare</binary>
</provides>
<metadata_licence>CC0-1.0</metadata_licence>
<metadata_license>CC0-1.0</metadata_license>
<update_contact>hi_AT_planetpeanut.uk</update_contact>
<content_rating type="oars-1.0">

View file

@ -51,6 +51,16 @@ namespace SparkleShare {
Path.Combine (GitCommand.ExecPath, "git-lfs"),
Path.Combine (Config.BinPath, "git-lfs"),
overwite);
NSWorkspace.Notifications.ObserveDidWake((object sender, NSNotificationEventArgs e) => {
Console.Write ("Detected wake from sleep, checking for updates\n");
if (SparkleShare.Controller.RepositoriesLoaded) {
foreach (var repo in SparkleShare.Controller.Repositories) {
repo.SyncDown();
repo.SyncUp();
}
}
});
}

View file

@ -9,13 +9,13 @@
<key>CFBundleName</key>
<string>SparkleShare</string>
<key>CFBundleShortVersionString</key>
<string>3.28.0</string>
<string>3.38.0</string>
<key>CFBundleVersion</key>
<string>3.28.0</string>
<string>3.38.0</string>
<key>LSApplicationCategoryType</key>
<string>public.app-category.utilities</string>
<key>LSMinimumSystemVersion</key>
<string>10.7</string>
<string>10.9</string>
<key>LSUIElement</key>
<string>1</string>
<key>NSMainNibFile</key>

View file

@ -13,6 +13,7 @@
<TargetFrameworkVersion>v4.5</TargetFrameworkVersion>
<MonoMacResourcePrefix>Resources</MonoMacResourcePrefix>
<ReleaseVersion></ReleaseVersion>
<UseXamMacFullFramework>true</UseXamMacFullFramework>
</PropertyGroup>
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Release|AnyCPU' ">
<DebugType>none</DebugType>
@ -40,6 +41,8 @@
<TlsProvider>Default</TlsProvider>
<LinkMode>None</LinkMode>
<UseMSBuildEngine>True</UseMSBuildEngine>
<AOTMode>None</AOTMode>
<LangVersion>latest</LangVersion>
</PropertyGroup>
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|AnyCPU' ">
<Optimize>False</Optimize>
@ -67,6 +70,10 @@
<LinkMode>None</LinkMode>
<HttpClientHandler>HttpClientHandler</HttpClientHandler>
<TlsProvider>Default</TlsProvider>
<AOTMode>None</AOTMode>
<CodeSigningKey>Mac Developer</CodeSigningKey>
<PackageSigningKey>3rd Party Mac Developer Installer</PackageSigningKey>
<LangVersion>latest</LangVersion>
</PropertyGroup>
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'ReleaseDist|AnyCPU' ">
<Optimize>false</Optimize>
@ -93,7 +100,9 @@
<Profiling>false</Profiling>
<HttpClientHandler>HttpClientHandler</HttpClientHandler>
<TlsProvider>Default</TlsProvider>
<LinkMode>None</LinkMode>
<LinkMode>Platform</LinkMode>
<AOTMode>None</AOTMode>
<LangVersion>latest</LangVersion>
</PropertyGroup>
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'ReleaseMac|AnyCPU' ">
<DebugType>none</DebugType>
@ -119,9 +128,11 @@
<Profiling>false</Profiling>
<HttpClientHandler>HttpClientHandler</HttpClientHandler>
<TlsProvider>Default</TlsProvider>
<LinkMode>None</LinkMode>
<LinkMode>Platform</LinkMode>
<CodeSigningKey>Mac Developer</CodeSigningKey>
<PackageSigningKey>3rd Party Mac Developer Installer</PackageSigningKey>
<AOTMode>None</AOTMode>
<LangVersion>latest</LangVersion>
</PropertyGroup>
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'DebugMac|AnyCPU' ">
<Optimize>False</Optimize>
@ -146,9 +157,11 @@
<UseSGen>false</UseSGen>
<UseRefCounting>false</UseRefCounting>
<Profiling>false</Profiling>
<LinkMode>None</LinkMode>
<LinkMode>Platform</LinkMode>
<HttpClientHandler>HttpClientHandler</HttpClientHandler>
<TlsProvider>Default</TlsProvider>
<AOTMode>None</AOTMode>
<LangVersion>latest</LangVersion>
</PropertyGroup>
<ItemGroup>
<Reference Include="System" />
@ -268,12 +281,6 @@
<BundleResource Include="..\Common\Presets\own-server%402x.png">
<Link>Presets\own-server%402x.png</Link>
</BundleResource>
<BundleResource Include="..\Common\Presets\planio.png">
<Link>Presets\planio.png</Link>
</BundleResource>
<BundleResource Include="..\Common\Presets\planio%402x.png">
<Link>Presets\planio%402x.png</Link>
</BundleResource>
<BundleResource Include="..\Common\Presets\bitbucket.xml">
<Link>Presets\bitbucket.xml</Link>
</BundleResource>
@ -286,9 +293,6 @@
<BundleResource Include="..\Common\Presets\own-server.xml">
<Link>Presets\own-server.xml</Link>
</BundleResource>
<BundleResource Include="..\Common\Presets\planio.xml">
<Link>Presets\planio.xml</Link>
</BundleResource>
<BundleResource Include="..\Common\HTML\day-entry.html">
<Link>HTML\day-entry.html</Link>
</BundleResource>

2
SparkleShare/Mac/UserInterface/Bubbles.cs Executable file → Normal file
View file

@ -22,7 +22,7 @@ namespace SparkleShare {
public class Bubbles : NSObject {
public BubblesController Controller = new BubblesController ();
public BubblesController Controller = new BubblesController (false);
public Bubbles ()

View file

@ -27,7 +27,7 @@ namespace SparkleShare {
public class EventLog : NSWindow {
public EventLogController Controller = new EventLogController ();
public EventLogController Controller = new EventLogController (false);
public float TitlebarHeight;
WebView web_view;

4
SparkleShare/Mac/Watcher.cs Executable file → Normal file
View file

@ -149,6 +149,10 @@ namespace SparkleShare {
if (handler != null) {
List<string> filtered_paths = new List<string> ();
foreach (var path in paths) {
if (path.EndsWith(".git")
|| path.Contains ("/.git/"))
continue;
if (path.Length > BasePath.Length) {
var t = path.Substring (BasePath.Length);
t = t.Trim ("/".ToCharArray ());

View file

@ -1,4 +1,4 @@
#!/bin/sh
#!/bin/sh
function abspath()
{
case "${1}" in
@ -11,6 +11,8 @@ function abspath()
esac
}
export projectFolder=$(dirname $0)
export projectFolder=$(abspath ${projectFolder})
LINE=$(cat ${projectFolder}/git.download)
TMP=()
@ -19,23 +21,22 @@ for val in $LINE ; do
TMP+=("$val")
done
export projectFolder=$(dirname $0)
export projectFolder=$(abspath ${projectFolder})
export gitDownload="${TMP[0]}"
export gitName=${gitDownload##*/}
export gitSHA256="${TMP[1]}"
set -e
if [ ! -f ${projectFolder}/git.tar.gz ]
if [[ ! -f ${projectFolder}/${gitName} ]];
then
curl --silent --location ${gitDownload} > git.tar.gz
test -e git.tar.gz || { echo "Failed to download git"; exit 1; }
curl --silent --location ${gitDownload} > ${projectFolder}/${gitName}
test -e ${projectFolder}/${gitName} || { echo "Failed to download git"; exit 1; }
printf "${gitSHA256} git.tar.gz" | shasum --check --algorithm 256
printf "${gitSHA256} ${projectFolder}/${gitName}" | shasum --check --algorithm 256
mkdir git/
tar xzf git.tar.gz --directory git/
tar czf git.tar.gz git/
rm -rf git/
fi
rm -f ${projectFolder}/git.tar.gz
ln -s ${projectFolder}/$gitName ${projectFolder}/git.tar.gz

View file

@ -1,2 +0,0 @@
<configuration>
</configuration>

View file

@ -1 +1 @@
https://github.com/desktop/dugite-native/releases/download/v2.16.2/dugite-native-v2.16.2-macOS-119.tar.gz 65d608eb16e0e262bae6bd7828b28cf640455e949003fec94c1233e084b9ccde
https://github.com/desktop/dugite-native/releases/download/v2.29.2-2/dugite-native-v2.29.2-f9ceb12-macOS.tar.gz ff16488ebbb3a0000fac34c8afc01bc4e839ad478717fbcbbe0c207642b5872c

View file

@ -8,12 +8,21 @@ echo packing ${bundle} for release without Mono framework dependency
export MONO_PATH=`readlink /Library/Frameworks/Mono.framework/Versions/Current`
export PKG_CONFIG_PATH=/usr/lib/pkgconfig:${MONO_PATH}/lib/pkgconfig
export AS="as -arch i386"
export CC="cc -arch i386 -lobjc -liconv -framework Foundation"
export PATH=/usr/local/bin:/opt/local/bin:/Library/Frameworks/Mono.framework/Versions/Current/bin:/usr/bin:/bin
mkdir -p cd ${bundle}/Contents/MonoBundle/
cd ${bundle}/Contents/MonoBundle/
assemblyPath=$(dirname $(dirname $(dirname $(pwd))))
echo ${projectFolder}
pwd
echo "x"
echo ${assemblyPath}
# merge all Assemblies into one Mac binary
mkbundle --static --deps --config ./config -o ../MacOS/SparkleShare SparkleShare.exe Sparkles.dll Xamarin.Mac.dll Sparkles.Git.dll
mkbundle \
--simple \
-v \
--config ./config \
-o ../MacOS/SparkleShare \
${assemblyPath}/SparkleShare.exe ${assemblyPath}/Sparkles.dll ${assemblyPath}/Sparkles.Git.dll
rm *.dll *.exe

View file

@ -9,6 +9,7 @@ echo Postprocessing ${bundle}...
export PATH=/usr/local/bin:/opt/local/bin:/Library/Frameworks/Mono.framework/Versions/Current/bin:/usr/bin:/bin
${projectFolder}/checkGit.sh
tar -x -f ${projectFolder}/git.tar.gz --directory ${bundle}/Contents/Resources
cp -R SparkleShareInviteOpener.app ${bundle}/Contents/Resources
cp config ${bundle}/Contents/MonoBundle
rm -rf ${bundle}/Contents/Resources/git
mkdir -p ${bundle}/Contents/Resources/git
tar -x -f ${projectFolder}/git.tar.gz --directory ${bundle}/Contents/Resources/git
cp -R ${projectFolder}/SparkleShareInviteOpener.app ${bundle}/Contents/Resources

View file

@ -265,10 +265,6 @@
<Link>Presets\bitbucket.png</Link>
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
</None>
<None Include="..\Common\Presets\planio.png">
<Link>Presets\planio.png</Link>
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
</None>
<None Include="app.config" />
<None Include="packages.config" />
</ItemGroup>
@ -285,10 +281,6 @@
<Link>Presets\own-server.xml</Link>
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
</None>
<None Include="..\Common\Presets\planio.xml">
<Link>Presets\planio.xml</Link>
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
</None>
</ItemGroup>
<ItemGroup>
<EmbeddedResource Include="Images\folder.png">

View file

@ -2,7 +2,7 @@
<Wix xmlns='http://schemas.microsoft.com/wix/2006/wi' xmlns:util="http://schemas.microsoft.com/wix/UtilExtension">
<Product Name='SparkleShare' Id='184950D5-67F6-4D06-9717-7E2F1607A7B0' UpgradeCode='D3DF1D99-87F5-47A7-A349-863DD6E4B73A'
Language='1033' Codepage='1252' Version='3.28.0' Manufacturer='SparkleShare'>
Language='1033' Codepage='1252' Version='3.38.0' Manufacturer='SparkleShare'>
<Package Id='*' Keywords='Installer' Description="SparkleShare Setup" Manufacturer='SparkleShare'
InstallerVersion='100' Languages='1033' Compressed='yes' SummaryCodepage='1252' />

View file

@ -0,0 +1,23 @@
// SparkleShare, a collaboration and sharing tool.
// Copyright (C) 2010 Hylke Bons <hi@planetpeanut.uk>
//
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU Lesser General Public License as
// published by the Free Software Foundation, either version 3 of the
// License, or (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with this program. If not, see <http://www.gnu.org/licenses/>.
namespace Sparkles {
public abstract class AuthenticationInfo
{
}
}

View file

@ -22,8 +22,9 @@ using System.Threading;
namespace Sparkles {
public class FetcherInfo {
public readonly Uri Address;
public class SparkleFetcherInfo {
public string Address; // TODO: Uri object
public string RemotePath;
public string Fingerprint;
@ -32,45 +33,22 @@ namespace Sparkles {
public bool FetchPriorHistory;
public string AnnouncementsUrl; // TODO: Uri object
public FetcherInfo (Uri address)
{
Address = address;
}
}
public enum FetchResult {
Unknown,
BackendMissing,
NoNetwork,
HostNotSupported,
HostChanged,
NotAuthenticated,
UserInterrupted,
Success
}
public class NetworkException : Exception { }
public abstract class BaseFetcher {
public event Action Started = delegate { };
public event FailedEventHandler Failed = delegate { };
public delegate void FailedEventHandler (FetchResult result);
public event Action Failed = delegate { };
public event FinishedEventHandler Finished = delegate { };
public delegate void FinishedEventHandler (StorageType storage_type);
public delegate void FinishedEventHandler (StorageType storage_type, string [] warnings);
public event ProgressChangedEventHandler ProgressChanged = delegate { };
public delegate void ProgressChangedEventHandler (double percentage, double speed, string information);
public abstract FetchResult Fetch ();
public abstract bool Fetch ();
public abstract void Stop ();
public bool IsActive { get; protected set; }
public double ProgressPercentage { get; private set; }
@ -89,10 +67,27 @@ namespace Sparkles {
public string RequiredFingerprint { get; protected set; }
public readonly bool FetchPriorHistory;
public string TargetFolder { get; protected set; }
public FetcherInfo OriginalFetcherInfo;
public SparkleFetcherInfo OriginalFetcherInfo;
protected BaseFetcher (FetcherInfo info)
protected List<string> warnings = new List<string> ();
protected List<string> errors = new List<string> ();
public string [] Warnings {
get {
return warnings.ToArray ();
}
}
public string [] Errors {
get {
return errors.ToArray ();
}
}
protected BaseFetcher (SparkleFetcherInfo info)
{
FetchedRepoStorageType = StorageType.Unknown;
@ -100,12 +95,10 @@ namespace Sparkles {
new StorageTypeInfo (StorageType.Plain, "Plain Storage", "Nothing fancy;\nmaximum compatibility"));
OriginalFetcherInfo = info;
RequiredFingerprint = info.Fingerprint;
FetchPriorHistory = info.FetchPriorHistory;
string remote_path = info.Address.AbsolutePath.Trim ("/".ToCharArray ());
string address = info.Address.ToString ();
string remote_path = info.RemotePath.Trim ("/".ToCharArray ());
string address = info.Address;
if (address.EndsWith ("/", StringComparison.InvariantCulture))
address = address.Substring (0, address.Length - 1);
@ -137,29 +130,30 @@ namespace Sparkles {
Directory.Delete (TargetFolder, recursive: true);
} catch (IOException) {
Failed (FetchResult.Unknown);
errors.Add ("\"" + TargetFolder + "\" is read-only.");
Failed ();
return;
}
thread = new Thread (() => {
FetchResult result = Fetch ();
if (result == FetchResult.Success) {
if (Fetch ()) {
Thread.Sleep (500);
Logger.LogInfo ("Fetcher", "Finished");
IsActive = false;
Finished (FetchedRepoStorageType);
Finished (FetchedRepoStorageType, Warnings);
} else {
Thread.Sleep (500);
if (!IsActive)
result = FetchResult.UserInterrupted;
Failed (result);
Logger.LogInfo ("Fetcher", string.Format ("Failed ({0})", result));
if (IsActive) {
Logger.LogInfo ("Fetcher", "Failed");
Failed ();
} else {
Logger.LogInfo ("Fetcher", "Failed: cancelled by user");
}
IsActive = false;
}

View file

@ -37,18 +37,15 @@ namespace Sparkles {
StartInfo.FileName = path;
StartInfo.Arguments = args;
StartInfo.WorkingDirectory = Path.GetTempPath ();
StartInfo.WorkingDirectory = Path.GetTempPath ();
StartInfo.CreateNoWindow = true;
StartInfo.RedirectStandardOutput = true;
StartInfo.StandardOutputEncoding = System.Text.Encoding.UTF8;
StartInfo.RedirectStandardError = true;
StartInfo.UseShellExecute = false;
StartInfo.RedirectStandardOutput = true;
StartInfo.RedirectStandardError = true;
EnableRaisingEvents = true;
// Force set the language because we do a lot of string parsing
SetEnvironmentVariable ("LANG", "en_US");
}
@ -107,7 +104,8 @@ namespace Sparkles {
return output.TrimEnd ();
}
public void SetEnvironmentVariable (string variable, string content)
public void SetEnvironmentVariable (string variable, string content)
{
if (StartInfo.EnvironmentVariables.ContainsKey (variable))
StartInfo.EnvironmentVariables [variable] = content;

View file

@ -2,8 +2,8 @@
// Copyright (C) 2010 Hylke Bons <hi@planetpeanut.uk>
//
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU Lesser General Public License as
// published by the Free Software Foundation, either version 3 of the
// it under the terms of the GNU Lesser General Public License as
// published by the Free Software Foundation, either version 3 of the
// License, or (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
@ -32,10 +32,10 @@ namespace Sparkles {
app_data_path = Path.Combine (Environment.GetFolderPath (Environment.SpecialFolder.Personal), ".config");
string config_path = Path.Combine (app_data_path, "org.sparkleshare.SparkleShare");
return new Configuration (config_path, "projects.xml");
});
public static Configuration DefaultConfiguration { get { return ConfigLazy.Value; } }
public static bool DebugMode = true;
@ -43,6 +43,7 @@ namespace Sparkles {
public readonly string FilePath;
public readonly string TmpPath;
public readonly string BinPath;
public string AvatarProvider;
public readonly string LogFilePath;
@ -51,7 +52,7 @@ namespace Sparkles {
get {
if (InstallationInfo.OperatingSystem == OS.Windows)
return Environment.GetFolderPath (Environment.SpecialFolder.UserProfile);
return Environment.GetFolderPath (Environment.SpecialFolder.Personal);
}
}
@ -59,9 +60,9 @@ namespace Sparkles {
public string FoldersPath {
get {
if (GetConfigOption ("folders_path") != null)
if (GetConfigOption ("folders_path") != null)
return GetConfigOption ("folders_path");
return Path.Combine (HomePath, "SparkleShare");
}
}
@ -72,7 +73,7 @@ namespace Sparkles {
FilePath = Path.Combine (config_path, config_file_name);
DirectoryPath = config_path;
BinPath = Path.Combine (config_path, "bin");
BinPath = Path.Combine (config_path, "bin");
if (!Directory.Exists (BinPath))
Directory.CreateDirectory (BinPath);
@ -328,7 +329,7 @@ namespace Sparkles {
}
Save ();
Logger.LogInfo ("Config", string.Format ("Set {0} {1}:{2}", FilePath, name, content));
Logger.LogInfo ("Config", "Updated option " + name + ":" + content);
}
@ -336,15 +337,15 @@ namespace Sparkles {
{
return SelectSingleNode (string.Format ("/sparkleshare/folder[name=\"{0}\"]", name));
}
string FolderValueByKey (string name, string key)
{
XmlNode folder = FolderByName(name);
if ((folder != null) && (folder [key] != null))
return folder [key].InnerText;
return null;
}
@ -352,6 +353,7 @@ namespace Sparkles {
void Save ()
{
Save (FilePath);
Logger.LogInfo ("Config", "Wrote to '" + FilePath + "'");
}
}
}

View file

@ -98,6 +98,9 @@ namespace Sparkles.Git {
SetEnvironmentVariable ("GIT_CONFIG_NOSYSTEM", "1");
SetEnvironmentVariable ("PREFIX", "");
SetEnvironmentVariable ("HOME", "");
SetEnvironmentVariable ("LANG", "en_US.UTF8");
SetEnvironmentVariable ("LC_ALL", "en_US.UTF8");
}

View file

@ -39,7 +39,7 @@ namespace Sparkles.Git {
}
public GitFetcher (FetcherInfo fetcher_info, SSHAuthenticationInfo auth_info) : base (fetcher_info, auth_info)
public GitFetcher (SparkleFetcherInfo fetcher_info, SSHAuthenticationInfo auth_info) : base (fetcher_info)
{
this.auth_info = auth_info;
var uri_builder = new UriBuilder (RemoteUrl);
@ -72,17 +72,15 @@ namespace Sparkles.Git {
}
public override FetchResult Fetch ()
public override bool Fetch ()
{
FetchResult result = base.Fetch ();
if (result != FetchResult.Success)
return result;
if (!base.Fetch ())
return false;
StorageType? storage_type = DetermineStorageType ();
if (storage_type == null)
return FetchResult.NoNetwork; // TODO: or HostNotSupported
return false;
FetchedRepoStorageType = (StorageType) storage_type;
@ -113,7 +111,6 @@ namespace Sparkles.Git {
while (!output_stream.EndOfStream) {
string line = output_stream.ReadLine ();
// TODO: Make ParseProgress use FetchResult
ErrorStatus error = GitCommand.ParseProgress (line, out percentage, out speed, out information);
if (error != ErrorStatus.None) {
@ -121,7 +118,7 @@ namespace Sparkles.Git {
git_clone.Kill ();
git_clone.Dispose ();
return FetchResult.Unknown; // TODO
return false;
}
OnProgressChanged (percentage, speed, information);
@ -130,14 +127,13 @@ namespace Sparkles.Git {
git_clone.WaitForExit ();
if (git_clone.ExitCode != 0)
return FetchResult.Unknown; // TODO
return false;
// Smooth out progression
Thread.Sleep (500);
OnProgressChanged (100, 0, "");
Thread.Sleep (500);
return FetchResult.Success;
return true;
}
@ -180,6 +176,13 @@ namespace Sparkles.Git {
File.WriteAllText (identifier_path, identifier);
File.SetAttributes (identifier_path, FileAttributes.Hidden);
// The repo is freshly cloned and no config user.name is set yet, so temporary use SparkleShare
// to avoid error 'TELL ME WHO YOU ARE', later on this will be handled in Commit of Git.Repository
var git_config = new GitCommand(TargetFolder, "config user.name \"SparkleShare\"");
git_config.StartAndWaitForExit();
git_config = new GitCommand(TargetFolder, "config user.email \"info@sparkleshare.org\"");
git_config.StartAndWaitForExit();
// We can't do the "commit --all" shortcut because it doesn't add untracked files
var git_add = new GitCommand (TargetFolder, "add .sparkleshare");
var git_commit = new GitCommand (TargetFolder,

View file

@ -178,7 +178,7 @@ namespace Sparkles.Git {
string remote_revision = "" + output.Substring (0, 40);
if (!remote_revision.Equals (current_revision)) {
git = new GitCommand (LocalPath, "merge-base " + remote_revision + " master");
git = new GitCommand (LocalPath, "merge-base " + remote_revision + " " + this.branch);
git.StartAndWaitForExit ();
if (git.ExitCode != 0) {
@ -434,7 +434,8 @@ namespace Sparkles.Git {
git = new GitCommand (LocalPath, "config core.ignorecase true");
git.StartAndWaitForExit ();
git = new GitCommand (LocalPath, "merge FETCH_HEAD");
git = new GitCommand (LocalPath, "merge --no-edit FETCH_HEAD");
git.StartInfo.StandardOutputEncoding = null;
git.StartInfo.RedirectStandardOutput = false;
string error_output = git.StartAndReadStandardError ();
@ -616,6 +617,7 @@ namespace Sparkles.Git {
var git = new GitCommand (LocalPath,
"commit --message=\"Conflict resolution\" --author=\"SparkleShare <info@sparkleshare.org>\"");
git.StartInfo.StandardOutputEncoding = null;
git.StartInfo.RedirectStandardOutput = false;
git.StartAndWaitForExit ();
@ -934,7 +936,12 @@ namespace Sparkles.Git {
string HEAD_file_path = Path.Combine (child_path, "HEAD");
if (File.Exists (HEAD_file_path)) {
File.Move (HEAD_file_path, HEAD_file_path + ".backup");
string HEAD_file_path_backup = Path.Combine (child_path, "HEAD.backup");
if (File.Exists (HEAD_file_path_backup)) {
File.Delete (HEAD_file_path_backup);
}
File.Move (HEAD_file_path, HEAD_file_path_backup);
Logger.LogInfo ("Git", Name + " | Renamed " + HEAD_file_path);
}

View file

@ -18,7 +18,7 @@
using System.Reflection;
[assembly:AssemblyTitle ("Sparkles")]
[assembly:AssemblyVersion ("3.28.0")]
[assembly:AssemblyVersion ("3.38.0")]
[assembly:AssemblyCopyright ("Copyright (c) 2010 Hylke Bons and others")]
namespace Sparkles {

View file

@ -67,25 +67,37 @@ namespace Sparkles {
get {
if (OperatingSystem == OS.macOS) {
var uname = new Command ("sw_vers", "-productVersion", write_output: false);
string output = uname.StartAndReadStandardOutput ();
string version = output;
string version = uname.StartAndReadStandardOutput ();
//
string[] version_elements= version.Split('.');
// Parse the version number between the periods (e.g. "10.12.1" -> 12)
output = output.Substring (output.IndexOf (".") + 1);
if (output.LastIndexOf (".") != -1) {
output = output.Substring (0, output.LastIndexOf ("."));
}
string release = "Unreleased Version";
switch (int.Parse (output)) {
case 7: release = "Lion"; break;
case 8: release = "Mountain Lion"; break;
case 9: release = "Mavericks"; break;
case 10: release = "Yosemite"; break;
case 11: release = "El Capitan"; break;
case 12: release = "Sierra"; break;
case 13: release = "High Sierra"; break;
case 14: release = "Mojave"; break;
if ((version_elements.Length) >= 2) {
switch (int.Parse (version_elements [0])) {
case 10:
// Parse the version number between the periods (e.g. "10.12.1" -> 12)
switch (int.Parse (version_elements [0])) {
case 7: release = "Lion"; break;
case 8: release = "Mountain Lion"; break;
case 9: release = "Mavericks"; break;
case 10: release = "Yosemite"; break;
case 11: release = "El Capitan"; break;
case 12: release = "Sierra"; break;
case 13: release = "High Sierra"; break;
case 14: release = "Mojave"; break;
case 15: release = "Catalina"; break;
}
break;
case 11:
release = "BigSur"; break;
case 12:
release = "Monterey"; break;
case 13:
release = "Ventura"; break;
}
}
return string.Format ("{0} ({1})", version, release);

View file

@ -25,7 +25,7 @@ namespace Sparkles {
public class SparkleInvite : XmlDocument {
public string Address { get; private set; } // TODO: uri
public string Address { get; private set; }
public string RemotePath { get; private set; }
public string Fingerprint { get; private set; }
public string AcceptUrl { get; private set; }

View file

@ -32,8 +32,6 @@ namespace Sparkles {
new public string Name { get { return GetValue ("info", "name"); } }
public string Description { get { return GetValue ("info", "description"); } }
public string Host { get { return GetValue ("info", "host"); } }
public string KeyEntryHint { get { return GetValue ("key", "hint"); } }
public string Backend { get { return GetValue ("info", "backend"); } }
public string Fingerprint { get { return GetValue ("info", "fingerprint"); } }
public string AnnouncementsUrl { get { return GetValue ("info", "announcements_url"); } }
@ -42,7 +40,7 @@ namespace Sparkles {
public string Path { get { return GetValue ("path", "value"); } }
public string PathExample { get { return GetValue ("path", "example"); } }
public string IconPath {
public string ImagePath {
get {
string image_file_name = GetValue ("info", "icon");
string image_path = IO.Path.Combine (preset_directory, image_file_name);
@ -53,19 +51,7 @@ namespace Sparkles {
return IO.Path.Combine (PresetsPath, image_file_name);
}
}
public string LogoPath {
get {
string image_file_name = GetValue ("info", "logo");
string image_path = IO.Path.Combine (preset_directory, image_file_name);
if (IO.File.Exists (image_path))
return image_path;
return IO.Path.Combine (PresetsPath, image_file_name);
}
}
public bool PathUsesLowerCase {
get {
string uses_lower_case = GetValue ("path", "uses_lower_case");
@ -124,14 +110,14 @@ namespace Sparkles {
}
string GetValue (string a, string b)
private string GetValue (string a, string b)
{
XmlNode node = SelectSingleNode ("/sparkleshare/preset/" + a + "/" + b);
XmlNode node = SelectSingleNode ("/sparkleshare/preset/" + a + "/" + b + "/text()");
if (node == null)
if (node != null && !string.IsNullOrEmpty (node.Value))
return node.Value;
else
return null;
return node.InnerXml;
}
}
}

Some files were not shown because too many files have changed in this diff Show more