Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
C
com.ccwangluo.accelerator
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Issues
0
Issues
0
List
Boards
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Analytics
Analytics
CI / CD
Repository
Value Stream
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
sheteng
com.ccwangluo.accelerator
Commits
51e155c9
Commit
51e155c9
authored
Nov 09, 2015
by
Mygod
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
Add more material design (3)
parent
1f695b9c
Changes
26
Expand all
Hide whitespace changes
Inline
Side-by-side
Showing
26 changed files
with
471 additions
and
894 deletions
+471
-894
build.sbt
build.sbt
+1
-8
src/main/AndroidManifest.xml
src/main/AndroidManifest.xml
+15
-4
src/main/jni/shadowsocks-libev
src/main/jni/shadowsocks-libev
+1
-1
src/main/res/layout/layout_profiles.xml
src/main/res/layout/layout_profiles.xml
+11
-0
src/main/res/layout/layout_profiles_item.xml
src/main/res/layout/layout_profiles_item.xml
+34
-0
src/main/res/layout/menu_row_category.xml
src/main/res/layout/menu_row_category.xml
+0
-5
src/main/res/layout/menu_row_item.xml
src/main/res/layout/menu_row_item.xml
+0
-5
src/main/res/layout/toolbar_light_dark.xml
src/main/res/layout/toolbar_light_dark.xml
+0
-1
src/main/res/menu/add_profile_methods.xml
src/main/res/menu/add_profile_methods.xml
+20
-0
src/main/res/values-zh/strings.xml
src/main/res/values-zh/strings.xml
+5
-16
src/main/res/values/strings.xml
src/main/res/values/strings.xml
+9
-18
src/main/res/values/styles.xml
src/main/res/values/styles.xml
+1
-56
src/main/res/xml/pref_all.xml
src/main/res/xml/pref_all.xml
+27
-29
src/main/scala/com/github/shadowsocks/AppManager.scala
src/main/scala/com/github/shadowsocks/AppManager.scala
+11
-17
src/main/scala/com/github/shadowsocks/ParserActivity.scala
src/main/scala/com/github/shadowsocks/ParserActivity.scala
+3
-3
src/main/scala/com/github/shadowsocks/ProfileManagerActivity.scala
...scala/com/github/shadowsocks/ProfileManagerActivity.scala
+176
-0
src/main/scala/com/github/shadowsocks/Shadowsocks.scala
src/main/scala/com/github/shadowsocks/Shadowsocks.scala
+89
-420
src/main/scala/com/github/shadowsocks/ShadowsocksApplication.scala
...scala/com/github/shadowsocks/ShadowsocksApplication.scala
+35
-7
src/main/scala/com/github/shadowsocks/ShadowsocksNatService.scala
.../scala/com/github/shadowsocks/ShadowsocksNatService.scala
+7
-21
src/main/scala/com/github/shadowsocks/ShadowsocksSettings.scala
...in/scala/com/github/shadowsocks/ShadowsocksSettings.scala
+13
-1
src/main/scala/com/github/shadowsocks/ShadowsocksVpnService.scala
.../scala/com/github/shadowsocks/ShadowsocksVpnService.scala
+5
-18
src/main/scala/com/github/shadowsocks/database/MenuAdapter.scala
...n/scala/com/github/shadowsocks/database/MenuAdapter.scala
+0
-179
src/main/scala/com/github/shadowsocks/preferences/ProfileEditTextPreference.scala
...b/shadowsocks/preferences/ProfileEditTextPreference.scala
+0
-78
src/main/scala/com/github/shadowsocks/utils/ConfigUtils.scala
...main/scala/com/github/shadowsocks/utils/ConfigUtils.scala
+5
-5
src/main/scala/com/github/shadowsocks/utils/Constants.scala
src/main/scala/com/github/shadowsocks/utils/Constants.scala
+0
-2
src/main/scala/com/github/shadowsocks/utils/Utils.scala
src/main/scala/com/github/shadowsocks/utils/Utils.scala
+3
-0
No files found.
build.sbt
View file @
51e155c9
...
@@ -29,13 +29,10 @@ libraryDependencies ++= Seq(
...
@@ -29,13 +29,10 @@ libraryDependencies ++= Seq(
"com.github.kevinsawicki"
%
"http-request"
%
"6.0"
,
"com.github.kevinsawicki"
%
"http-request"
%
"6.0"
,
"commons-net"
%
"commons-net"
%
"3.3"
,
"commons-net"
%
"commons-net"
%
"3.3"
,
"com.google.zxing"
%
"android-integration"
%
"3.2.1"
,
"com.google.zxing"
%
"android-integration"
%
"3.2.1"
,
"com.joanzapata.android"
%
"android-iconify"
%
"1.0.11"
,
"net.glxn.qrgen"
%
"android"
%
"2.0"
,
"net.glxn.qrgen"
%
"android"
%
"2.0"
,
"net.simonvt.menudrawer"
%
"menudrawer"
%
"3.0.6"
,
"com.google.android.gms"
%
"play-services-base"
%
"8.1.0"
,
"com.google.android.gms"
%
"play-services-base"
%
"8.1.0"
,
"com.google.android.gms"
%
"play-services-ads"
%
"8.1.0"
,
"com.google.android.gms"
%
"play-services-ads"
%
"8.1.0"
,
"com.google.android.gms"
%
"play-services-analytics"
%
"8.1.0"
,
"com.google.android.gms"
%
"play-services-analytics"
%
"8.1.0"
,
"com.android.support"
%
"support-v4"
%
"23.1.0"
,
"com.android.support"
%
"design"
%
"23.1.0"
,
"com.android.support"
%
"design"
%
"23.1.0"
,
"com.github.jorgecastilloprz"
%
"fabprogresscircle"
%
"1.01"
,
"com.github.jorgecastilloprz"
%
"fabprogresscircle"
%
"1.01"
,
"com.nostra13.universalimageloader"
%
"universal-image-loader"
%
"1.9.4"
,
"com.nostra13.universalimageloader"
%
"universal-image-loader"
%
"1.9.4"
,
...
@@ -46,13 +43,9 @@ libraryDependencies ++= Seq(
...
@@ -46,13 +43,9 @@ libraryDependencies ++= Seq(
proguardOptions
in
Android
++=
Seq
(
"-keep class android.support.v4.app.** { *; }"
,
proguardOptions
in
Android
++=
Seq
(
"-keep class android.support.v4.app.** { *; }"
,
"-keep interface android.support.v4.app.** { *; }"
,
"-keep interface android.support.v4.app.** { *; }"
,
"-keep class android.support.v7.widget.Toolbar { <init>(...); }"
,
"-keep class android.support.v7.widget.Toolbar { <init>(...); }"
,
"-keep class com.actionbarsherlock.** { *; }"
,
"-keep interface com.actionbarsherlock.** { *; }"
,
"-keep class org.jraf.android.backport.** { *; }"
,
"-keep class org.jraf.android.backport.** { *; }"
,
"-keep class com.github.shadowsocks.** { *; }"
,
"-keep class com.github.shadowsocks.** { *; }"
,
"-keep class * extends com.j256.ormlite.** { *; }"
,
"-keep class * extends com.j256.ormlite.** { *; }"
,
"-keep class com.joanzapata.** { *; }"
,
"-keepattributes *Annotation*"
,
"-keepattributes *Annotation*"
,
"-dontwarn com.google.android.gms.internal.zzhu"
,
"-dontwarn com.google.android.gms.internal.zzhu"
,
"-dontwarn org.xbill.**"
,
"-dontwarn org.xbill.**"
)
"-dontwarn com.actionbarsherlock.**"
)
src/main/AndroidManifest.xml
View file @
51e155c9
...
@@ -22,7 +22,8 @@
...
@@ -22,7 +22,8 @@
android:hardwareAccelerated=
"true"
android:hardwareAccelerated=
"true"
android:icon=
"@drawable/ic_launcher"
android:icon=
"@drawable/ic_launcher"
android:backupAgent=
".ShadowsocksBackupAgent"
android:backupAgent=
".ShadowsocksBackupAgent"
android:label=
"@string/app_name"
>
android:label=
"@string/app_name"
android:theme=
"@style/Theme.Material"
>
<meta-data
android:name=
"com.google.android.gms.version"
<meta-data
android:name=
"com.google.android.gms.version"
android:value=
"@integer/google_play_services_version"
/>
android:value=
"@integer/google_play_services_version"
/>
...
@@ -36,7 +37,6 @@
...
@@ -36,7 +37,6 @@
<activity
<activity
android:name=
".Shadowsocks"
android:name=
".Shadowsocks"
android:label=
"@string/app_name"
android:label=
"@string/app_name"
android:theme=
"@style/Theme.Shadowsocks"
android:launchMode=
"singleTask"
>
android:launchMode=
"singleTask"
>
<intent-filter>
<intent-filter>
<action
android:name=
"android.intent.action.MAIN"
/>
<action
android:name=
"android.intent.action.MAIN"
/>
...
@@ -62,11 +62,22 @@
...
@@ -62,11 +62,22 @@
android:launchMode=
"singleTask"
>
android:launchMode=
"singleTask"
>
</activity>
</activity>
<activity
android:name=
".ProfileManagerActivity"
android:label=
"@string/app_name"
android:parentActivityName=
".Shadowsocks"
android:exported=
"false"
>
<intent-filter>
<action
android:name=
"com.github.shadowsocks.ProfileManagerActivity"
/>
<category
android:name=
"android.intent.category.DEFAULT"
/>
</intent-filter>
</activity>
<activity
<activity
android:name=
".AppManager"
android:name=
".AppManager"
android:theme=
"@style/Theme.Material"
android:label=
"@string/app_name"
android:label=
"@string/app_name"
android:parentActivityName=
".Shadowsocks"
>
android:parentActivityName=
".Shadowsocks"
android:exported=
"false"
>
<intent-filter>
<intent-filter>
<action
android:name=
"com.github.shadowsocks.AppManager"
/>
<action
android:name=
"com.github.shadowsocks.AppManager"
/>
<category
android:name=
"android.intent.category.DEFAULT"
/>
<category
android:name=
"android.intent.category.DEFAULT"
/>
...
...
shadowsocks-libev
@
890e880d
Subproject commit
095aa7490cb39d513180d1f756e6751107511f98
Subproject commit
890e880dc61ad4f2e9a340a78c797c4aabee6429
src/main/res/layout/layout_profiles.xml
0 → 100644
View file @
51e155c9
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
xmlns:android=
"http://schemas.android.com/apk/res/android"
android:orientation=
"vertical"
android:layout_width=
"match_parent"
android:layout_height=
"match_parent"
>
<include
layout=
"@layout/toolbar_light_dark"
/>
<android.support.v7.widget.RecyclerView
android:id=
"@+id/profilesList"
android:layout_width=
"match_parent"
android:layout_height=
"0dp"
android:layout_weight=
"1"
/>
</LinearLayout>
src/main/res/layout/layout_profiles_item.xml
0 → 100644
View file @
51e155c9
<?xml version="1.0" encoding="utf-8"?>
<!-- Based on: https://github.com/android/platform_frameworks_base/blob/master/core/res/res/layout/select_dialog_singlechoice_material.xml -->
<LinearLayout
xmlns:android=
"http://schemas.android.com/apk/res/android"
android:layout_width=
"match_parent"
android:layout_height=
"wrap_content"
android:background=
"?android:attr/selectableItemBackground"
android:paddingStart=
"20dp"
android:paddingEnd=
"?attr/dialogPreferredPadding"
android:paddingLeft=
"20dp"
android:paddingRight=
"?attr/dialogPreferredPadding"
>
<CheckedTextView
xmlns:android=
"http://schemas.android.com/apk/res/android"
android:id=
"@android:id/text1"
android:layout_width=
"0dp"
android:layout_height=
"wrap_content"
android:layout_gravity=
"center_vertical"
android:layout_weight=
"1"
android:minHeight=
"?android:attr/listPreferredItemHeightSmall"
android:textAppearance=
"?android:attr/textAppearanceMedium"
android:textColor=
"?android:attr/textColorAlertDialogListItem"
android:gravity=
"center_vertical"
android:drawableStart=
"?android:attr/listChoiceIndicatorSingle"
android:drawableLeft=
"?android:attr/listChoiceIndicatorSingle"
android:drawablePadding=
"20dp"
android:maxLines=
"4"
android:scrollHorizontally=
"false"
/>
<!-- TODO: Replace this view with an ImageView -->
<ImageView
android:id=
"@+id/qrcode"
android:layout_width=
"wrap_content"
android:layout_height=
"wrap_content"
android:layout_gravity=
"center_vertical"
android:src=
"@android:drawable/ic_menu_add"
android:background=
"?attr/selectableItemBackgroundBorderless"
android:contentDescription=
"@string/qrcode"
/>
</LinearLayout>
src/main/res/layout/menu_row_category.xml
deleted
100644 → 0
View file @
1f695b9c
<?xml version="1.0" encoding="utf-8"?>
<TextView
xmlns:android=
"http://schemas.android.com/apk/res/android"
android:layout_width=
"match_parent"
android:layout_height=
"wrap_content"
style=
"@style/MenuDrawer.Widget.Category"
/>
\ No newline at end of file
src/main/res/layout/menu_row_item.xml
deleted
100644 → 0
View file @
1f695b9c
<?xml version="1.0" encoding="utf-8"?>
<TextView
xmlns:android=
"http://schemas.android.com/apk/res/android"
android:layout_width=
"match_parent"
android:layout_height=
"wrap_content"
style=
"@style/MenuDrawer.Widget.Title"
/>
\ No newline at end of file
src/main/res/layout/toolbar_light_dark.xml
View file @
51e155c9
...
@@ -7,6 +7,5 @@
...
@@ -7,6 +7,5 @@
android:background=
"?attr/colorPrimary"
android:background=
"?attr/colorPrimary"
android:elevation=
"4dp"
android:elevation=
"4dp"
android:theme=
"@style/ThemeOverlay.AppCompat.Dark.ActionBar"
android:theme=
"@style/ThemeOverlay.AppCompat.Dark.ActionBar"
app:titleTextAppearance=
"@style/Toolbar.TitleText"
app:popupTheme=
"@style/ThemeOverlay.AppCompat.Light"
app:popupTheme=
"@style/ThemeOverlay.AppCompat.Light"
android:id=
"@+id/toolbar"
/>
android:id=
"@+id/toolbar"
/>
src/main/res/menu/add_profile_methods.xml
0 → 100644
View file @
51e155c9
<?xml version="1.0" encoding="utf-8"?>
<menu
xmlns:android=
"http://schemas.android.com/apk/res/android"
xmlns:app=
"http://schemas.android.com/apk/res-auto"
>
<!-- Todo: replace this placeholder icon with a material one -->
<item
android:title=
"@string/add_profile"
android:icon=
"@android:drawable/ic_menu_add"
android:alphabeticShortcut=
"a"
android:numericShortcut=
"0"
app:showAsAction=
"always"
>
<menu>
<item
android:id=
"@+id/scan_qr_code"
android:title=
"@string/add_profile_methods_scan_qr_code"
android:alphabeticShortcut=
"s"
android:numericShortcut=
"1"
/>
<item
android:id=
"@+id/manual_settings"
android:title=
"@string/add_profile_methods_manual_settings"
android:alphabeticShortcut=
"m"
android:numericShortcut=
"2"
/>
</menu>
</item>
</menu>
src/main/res/values-zh/strings.xml
View file @
51e155c9
...
@@ -3,9 +3,6 @@
...
@@ -3,9 +3,6 @@
<resources>
<resources>
<string
name=
"app_name"
>
影梭
</string>
<string
name=
"app_name"
>
影梭
</string>
<string
name=
"screen_name"
>
shadowsocks
</string>
<string
name=
"screen_name"
>
shadowsocks
</string>
<string
name=
"function_cat"
>
服务控制
</string>
<string
name=
"service_controller"
>
代理开关
</string>
<string
name=
"service_summary"
>
启动/关闭后台服务
</string>
<string
name=
"proxy_cat"
>
服务器设置
</string>
<string
name=
"proxy_cat"
>
服务器设置
</string>
<string
name=
"profile"
>
配置文件
</string>
<string
name=
"profile"
>
配置文件
</string>
<string
name=
"profile_summary"
>
配置文件名称
</string>
<string
name=
"profile_summary"
>
配置文件名称
</string>
...
@@ -39,26 +36,18 @@
...
@@ -39,26 +36,18 @@
<string
name=
"traffic_stat_summary"
>
在通知栏上显示当前上下行速率
</string>
<string
name=
"traffic_stat_summary"
>
在通知栏上显示当前上下行速率
</string>
<string
name=
"forward_success"
>
后台服务已开始运行。
</string>
<string
name=
"forward_success"
>
后台服务已开始运行。
</string>
<string
name=
"service_running"
>
已连接到「%s」
</string>
<string
name=
"service_running"
>
已连接到「%s」
</string>
<string
name=
"service_status"
formatted=
"false"
>
当前速率:%d KB/s
</string>
<string
name=
"forward_fail"
>
后台服务启动失败。
</string>
<string
name=
"service_stopped"
>
后台服务已停止。
</string>
<string
name=
"forward_stop"
>
后台服务已停止。
</string>
<string
name=
"service_failed"
>
无法连接远程服务器
</string>
<string
name=
"service_failed"
>
无法连接远程服务器
</string>
<string
name=
"stop"
>
停止服务
</string>
<string
name=
"stop"
>
停止服务
</string>
<string
name=
"stopping"
>
正在关闭...
</string>
<string
name=
"stopping"
>
正在关闭...
</string>
<string
name=
"vpn_error"
>
后台服务启动失败:%s
</string>
<string
name=
"vpn_error"
>
后台服务启动失败:%s
</string>
<string
name=
"ok_iknow"
>
确定
</string>
<string
name=
"close"
>
关闭
</string>
<string
name=
"close"
>
关闭
</string>
<string
name=
"port_alert"
>
本地端口号应大于1024
</string>
<string
name=
"port_alert"
>
本地端口号应大于1024
</string>
<string
name=
"port_empty"
>
端口号不能为空
</string>
<string
name=
"port_empty"
>
端口号不能为空
</string>
<string
name=
"proxy_empty"
>
代理服务器地址不能为空
</string>
<string
name=
"proxy_empty"
>
代理服务器地址不能为空
</string>
<string
name=
"crash_alert"
>
检测到意外退出,状态已被重置。
</string>
<string
name=
"connect"
>
连接
</string>
<string
name=
"connect"
>
连接
</string>
<string
name=
"initializing"
>
正在初始化...
</string>
<string
name=
"initializing"
>
正在初始化...
</string>
<string
name=
"recovering"
>
重置中...
</string>
<string
name=
"recovering"
>
重置中...
</string>
<string
name=
"loading"
>
正在加载...
</string>
<string
name=
"loading"
>
正在加载...
</string>
<string
name=
"yes"
>
是
</string>
<string
name=
"no"
>
否
</string>
<string
name=
"profiles"
>
配置文件
</string>
<string
name=
"profiles"
>
配置文件
</string>
<string
name=
"settings"
>
设置选项
</string>
<string
name=
"settings"
>
设置选项
</string>
<string
name=
"remove_profile"
>
删除此配置文件「%s」?
</string>
<string
name=
"remove_profile"
>
删除此配置文件「%s」?
</string>
...
@@ -84,10 +73,8 @@
...
@@ -84,10 +73,8 @@
<!-- profile -->
<!-- profile -->
<string
name=
"add_profile_dialog"
>
为影梭添加此配置文件?
</string>
<string
name=
"add_profile_dialog"
>
为影梭添加此配置文件?
</string>
<string-array
name=
"add_profile_methods"
>
<string
name=
"add_profile_methods_scan_qr_code"
>
扫描二维码
</string>
<item>
扫描二维码
</item>
<string
name=
"add_profile_methods_manual_settings"
>
手动设置
</string>
<item>
手动设置
</item>
</string-array>
<string-array
name=
"route_entry"
>
<string-array
name=
"route_entry"
>
<item>
全局
</item>
<item>
全局
</item>
...
@@ -101,6 +88,8 @@
...
@@ -101,6 +88,8 @@
<string
name=
"action_export_err"
>
导出失败
</string>
<string
name=
"action_export_err"
>
导出失败
</string>
<string
name=
"action_import_msg"
>
导入成功
</string>
<string
name=
"action_import_msg"
>
导入成功
</string>
<string
name=
"action_import_err"
>
导入失败
</string>
<string
name=
"action_import_err"
>
导入失败
</string>
<string
name=
"error"
>
错误
</string>
<string
name=
"removed"
>
已删除
</string>
<string
name=
"undo"
>
撤销
</string>
</resources>
</resources>
src/main/res/values/strings.xml
View file @
51e155c9
...
@@ -4,15 +4,14 @@
...
@@ -4,15 +4,14 @@
<string
name=
"app_name"
>
Shadowsocks
</string>
<string
name=
"app_name"
>
Shadowsocks
</string>
<string
name=
"screen_name"
>
shadowsocks
</string>
<string
name=
"screen_name"
>
shadowsocks
</string>
<!--
function
category -->
<!--
global
category -->
<string
name=
"
function_cat"
>
Service Controller
</string>
<string
name=
"
global_cat"
>
Global Settings
</string>
<string
name=
"
service_controller"
>
Proxy Switch
</string>
<string
name=
"
profile"
>
Profile
</string>
<string
name=
"
service_summary"
>
Enable / Disable Proxy
</string>
<string
name=
"
profile_summary"
>
Switch to another profile
</string>
<!-- proxy category -->
<!-- proxy category -->
<string
name=
"proxy_cat"
>
Server Settings
</string>
<string
name=
"proxy_cat"
>
Server Settings
</string>
<string
name=
"profile"
>
Profile
</string>
<string
name=
"profile_name"
>
Profile name
</string>
<string
name=
"profile_summary"
>
Profile name
</string>
<string
name=
"proxy"
>
Server
</string>
<string
name=
"proxy"
>
Server
</string>
<string
name=
"proxy_summary"
>
Hostname or IP of the remote server
</string>
<string
name=
"proxy_summary"
>
Hostname or IP of the remote server
</string>
<string
name=
"remote_port"
>
Remote Port
</string>
<string
name=
"remote_port"
>
Remote Port
</string>
...
@@ -54,26 +53,18 @@
...
@@ -54,26 +53,18 @@
<!-- notification category -->
<!-- notification category -->
<string
name=
"forward_success"
>
Shadowsocks started.
</string>
<string
name=
"forward_success"
>
Shadowsocks started.
</string>
<string
name=
"service_running"
>
Connected to "%s"
</string>
<string
name=
"service_running"
>
Connected to "%s"
</string>
<string
name=
"service_status"
formatted=
"false"
>
Current Rate: %d KB/s
</string>
<string
name=
"forward_fail"
>
Shadowsocks failed to start.
</string>
<string
name=
"service_stopped"
>
Shadowsocks stopped.
</string>
<string
name=
"forward_stop"
>
Shadowsocks stopped.
</string>
<string
name=
"service_failed"
>
Failed to connect the remote server
</string>
<string
name=
"service_failed"
>
Failed to connect the remote server
</string>
<string
name=
"stop"
>
Stop the service
</string>
<string
name=
"stop"
>
Stop the service
</string>
<string
name=
"stopping"
>
Shutting down...
</string>
<string
name=
"stopping"
>
Shutting down...
</string>
<string
name=
"vpn_error"
>
%s
</string>
<string
name=
"vpn_error"
>
%s
</string>
<string
name=
"enable_nat"
>
Turn on NAT mode.
</string>
<string
name=
"enable_nat"
>
Turn on NAT mode.
</string>
<string
name=
"disable_nat"
>
Turn off NAT mode.
</string>
<string
name=
"disable_nat"
>
Turn off NAT mode.
</string>
<string
name=
"error"
>
ERROR
</string>
<!-- alert category -->
<!-- alert category -->
<string
name=
"ok_iknow"
>
OK
</string>
<string
name=
"close"
>
Close
</string>
<string
name=
"close"
>
Close
</string>
<string
name=
"port_alert"
>
The local port number should be greater than 1024
</string>
<string
name=
"port_alert"
>
The local port number should be greater than 1024
</string>
<string
name=
"port_empty"
>
Port should not be empty
</string>
<string
name=
"port_empty"
>
Port should not be empty
</string>
<string
name=
"proxy_empty"
>
Proxy should not be empty
</string>
<string
name=
"proxy_empty"
>
Proxy should not be empty
</string>
<string
name=
"crash_alert"
>
An unexpected exit detected, the context has been reset.
</string>
<string
name=
"connect"
>
Connect
</string>
<string
name=
"connect"
>
Connect
</string>
<string
name=
"initializing"
>
Initializing…
</string>
<string
name=
"initializing"
>
Initializing…
</string>
<string
name=
"recovering"
>
Resetting…
</string>
<string
name=
"recovering"
>
Resetting…
</string>
...
@@ -101,9 +92,9 @@
...
@@ -101,9 +92,9 @@
<!-- profile -->
<!-- profile -->
<string
name=
"add_profile_dialog"
>
Add this Shadowsocks Profile?
</string>
<string
name=
"add_profile_dialog"
>
Add this Shadowsocks Profile?
</string>
<string
-array
name=
"add_profile_methods"
>
<string
name=
"add_profile_methods_scan_qr_code"
>
Scan QR code
</string
>
<item>
Scan QR code
</item
>
<string
name=
"add_profile_methods_manual_settings"
>
Manual Settings
</string
>
<item>
Manual Settings
</item
>
<string
name=
"removed"
>
Removed
</string
>
<
/string-array
>
<
string
name=
"undo"
>
Undo
</string
>
</resources>
</resources>
src/main/res/values/styles.xml
View file @
51e155c9
<?xml version="1.0" encoding="utf-8"?>
<?xml version="1.0" encoding="utf-8"?>
<!--
Zirco Browser for Android
Copyright (C) 2010 - 2011 J. Devauchelle and contributors.
This program is free software; you can redistribute it and/or
modify it under the terms of the GNU General Public License
version 3 as published by the Free Software Foundation.
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.
-->
<resources>
<resources>
<style
name=
"Toolbar.
TitleText
"
parent=
"TextAppearance.Widget.AppCompat.Toolbar.Title"
>
<style
name=
"Toolbar.
Logo
"
parent=
"TextAppearance.Widget.AppCompat.Toolbar.Title"
>
<item
name=
"android:textSize"
>
24sp
</item>
<item
name=
"android:textSize"
>
24sp
</item>
</style>
</style>
<style
name=
"Theme.Material"
parent=
"Theme.AppCompat.Light.NoActionBar"
>
<style
name=
"Theme.Material"
parent=
"Theme.AppCompat.Light.NoActionBar"
>
...
@@ -51,45 +37,4 @@
...
@@ -51,45 +37,4 @@
<item
name=
"android:windowIsTranslucent"
>
true
</item>
<item
name=
"android:windowIsTranslucent"
>
true
</item>
</style>
</style>
<!-- Variation on the Light theme that turns off the title -->
<style
name=
"Theme.Shadowsocks"
parent=
"Theme.Material"
>
<item
name=
"menuDrawerStyle"
>
@style/MenuDrawerStyle
</item>
</style>
<style
name=
"MenuDrawer"
/>
<style
name=
"MenuDrawer.Widget"
/>
<style
name=
"MenuDrawer.Widget.Category"
>
<item
name=
"android:textStyle"
>
bold
</item>
<item
name=
"android:textColor"
>
?android:attr/textColorSecondaryInverse
</item>
<item
name=
"android:textSize"
>
14sp
</item>
<item
name=
"android:textAllCaps"
>
true
</item>
<item
name=
"android:gravity"
>
center_vertical
</item>
<item
name=
"android:paddingLeft"
>
16dp
</item>
<item
name=
"android:background"
>
@drawable/md__category_background
</item>
<item
name=
"android:singleLine"
>
true
</item>
<item
name=
"android:ellipsize"
>
end
</item>
</style>
<style
name=
"MenuDrawer.Widget.Title"
>
<item
name=
"android:background"
>
?android:attr/selectableItemBackground
</item>
<item
name=
"android:textAppearance"
>
?android:attr/textAppearance
</item>
<item
name=
"android:textColor"
>
?android:attr/textColorPrimaryInverse
</item>
<item
name=
"android:textSize"
>
18sp
</item>
<item
name=
"android:paddingLeft"
>
16dp
</item>
<item
name=
"android:paddingRight"
>
32dp
</item>
<item
name=
"android:paddingTop"
>
8dp
</item>
<item
name=
"android:paddingBottom"
>
8dp
</item>
<item
name=
"android:drawablePadding"
>
16dp
</item>
<item
name=
"android:gravity"
>
center_vertical
</item>
</style>
<style
name=
"MenuDrawerStyle"
parent=
"Widget.MenuDrawer"
>
<item
name=
"mdActiveIndicator"
>
@drawable/menu_arrow
</item>
<item
name=
"mdMenuSize"
>
250dp
</item>
</style>
</resources>
</resources>
src/main/res/xml/pref_all.xml
View file @
51e155c9
...
@@ -2,50 +2,58 @@
...
@@ -2,50 +2,58 @@
<PreferenceScreen
xmlns:android=
"http://schemas.android.com/apk/res/android"
<PreferenceScreen
xmlns:android=
"http://schemas.android.com/apk/res/android"
xmlns:app=
"http://schemas.android.com/apk/res/com.github.shadowsocks"
>
xmlns:app=
"http://schemas.android.com/apk/res/com.github.shadowsocks"
>
<PreferenceCategory
android:title=
"@string/global_cat"
>
<Preference
android:summary=
"@string/profile_summary"
android:title=
"@string/profile"
>
<intent
android:action=
"com.github.shadowsocks.ProfileManagerActivity"
/>
</Preference>
<!-- TODO: VPN/NAT SwitchPreference -->
<SwitchPreference
android:key=
"isAutoConnect"
android:summary=
"@string/auto_connect_summary"
android:title=
"@string/auto_connect"
/>
<Preference
android:key=
"recovery"
android:title=
"@string/recovery"
/>
<Preference
android:key=
"flush_dnscache"
android:title=
"@string/flush_dnscache"
/>
</PreferenceCategory>
<PreferenceCategory
<PreferenceCategory
android:title=
"@string/proxy_cat"
>
android:title=
"@string/proxy_cat"
>
<com.github.shadowsocks.preferences.
Profile
EditTextPreference
<com.github.shadowsocks.preferences.
Summary
EditTextPreference
android:defaultValue=
"Default"
android:defaultValue=
"Default"
android:key=
"profileName"
android:key=
"profileName"
android:summary=
"@string/profile_summary"
android:title=
"@string/profile_name"
/>
android:title=
"@string/profile"
>
</com.github.shadowsocks.preferences.ProfileEditTextPreference>
<com.github.shadowsocks.preferences.SummaryEditTextPreference
<com.github.shadowsocks.preferences.SummaryEditTextPreference
android:defaultValue=
"198.199.101.152"
android:defaultValue=
"198.199.101.152"
android:key=
"proxy"
android:key=
"proxy"
android:summary=
"@string/proxy_summary"
android:summary=
"@string/proxy_summary"
android:title=
"@string/proxy"
>
android:title=
"@string/proxy"
/>
</com.github.shadowsocks.preferences.SummaryEditTextPreference>
<com.github.shadowsocks.preferences.SummaryEditTextPreference
<com.github.shadowsocks.preferences.SummaryEditTextPreference
android:inputType=
"number"
android:inputType=
"number"
android:defaultValue=
"443"
android:defaultValue=
"443"
android:key=
"remotePort"
android:key=
"remotePort"
android:summary=
"@string/remote_port_summary"
android:summary=
"@string/remote_port_summary"
android:title=
"@string/remote_port"
>
android:title=
"@string/remote_port"
/>
</com.github.shadowsocks.preferences.SummaryEditTextPreference>
<com.github.shadowsocks.preferences.SummaryEditTextPreference
<com.github.shadowsocks.preferences.SummaryEditTextPreference
android:inputType=
"number"
android:inputType=
"number"
android:defaultValue=
"1080"
android:defaultValue=
"1080"
android:key=
"port"
android:key=
"port"
android:summary=
"@string/port_summary"
android:summary=
"@string/port_summary"
android:title=
"@string/port"
>
android:title=
"@string/port"
/>
</com.github.shadowsocks.preferences.SummaryEditTextPreference>
<com.github.shadowsocks.preferences.PasswordEditTextPreference
<com.github.shadowsocks.preferences.PasswordEditTextPreference
android:inputType=
"textPassword"
android:inputType=
"textPassword"
android:defaultValue=
"u1rRWTssNv0p"
android:defaultValue=
"u1rRWTssNv0p"
android:key=
"sitekey"
android:key=
"sitekey"
android:summary=
"@string/sitekey_summary"
android:summary=
"@string/sitekey_summary"
android:title=
"@string/sitekey"
>
android:title=
"@string/sitekey"
/>
</com.github.shadowsocks.preferences.PasswordEditTextPreference>
<com.github.shadowsocks.preferences.DropDownPreference
<com.github.shadowsocks.preferences.DropDownPreference
android:defaultValue=
"rc4"
android:defaultValue=
"rc4"
android:key=
"encMethod"
android:key=
"encMethod"
app:entries=
"@array/enc_method_entry"
app:entries=
"@array/enc_method_entry"
app:entryValues=
"@array/enc_method_value"
app:entryValues=
"@array/enc_method_value"
app:summary=
"%s"
app:summary=
"%s"
android:title=
"@string/enc_method"
>
android:title=
"@string/enc_method"
/>
</com.github.shadowsocks.preferences.DropDownPreference>
</PreferenceCategory>
</PreferenceCategory>
...
@@ -58,21 +66,18 @@
...
@@ -58,21 +66,18 @@
app:entries=
"@array/route_entry"
app:entries=
"@array/route_entry"
app:entryValues=
"@array/route_value"
app:entryValues=
"@array/route_value"
app:summary=
"%s"
app:summary=
"%s"
android:title=
"@string/route_list"
>
android:title=
"@string/route_list"
/>
</com.github.shadowsocks.preferences.DropDownPreference>
<SwitchPreference
<SwitchPreference
android:key=
"isIpv6"
android:key=
"isIpv6"
android:defaultValue=
"false"
android:defaultValue=
"false"
android:summary=
"@string/ipv6_summary"
android:summary=
"@string/ipv6_summary"
android:title=
"@string/ipv6"
>
android:title=
"@string/ipv6"
/>
</SwitchPreference>
<SwitchPreference
<SwitchPreference
android:defaultValue=
"true"
android:defaultValue=
"true"
android:key=
"isGlobalProxy"
android:key=
"isGlobalProxy"
android:disableDependentsState=
"true"
android:disableDependentsState=
"true"
android:summary=
"@string/auto_set_proxy_summary"
android:summary=
"@string/auto_set_proxy_summary"
android:title=
"@string/auto_set_proxy"
>
android:title=
"@string/auto_set_proxy"
/>
</SwitchPreference>
<Preference
<Preference
android:key=
"proxyedApps"
android:key=
"proxyedApps"
android:dependency=
"isGlobalProxy"
android:dependency=
"isGlobalProxy"
...
@@ -84,19 +89,12 @@
...
@@ -84,19 +89,12 @@
android:key=
"isUdpDns"
android:key=
"isUdpDns"
android:defaultValue=
"false"
android:defaultValue=
"false"
android:summary=
"@string/udp_dns_summary"
android:summary=
"@string/udp_dns_summary"
android:title=
"@string/udp_dns"
>
android:title=
"@string/udp_dns"
/>
</SwitchPreference>
<SwitchPreference
<SwitchPreference
android:key=
"isAuth"
android:key=
"isAuth"
android:defaultValue=
"false"
android:defaultValue=
"false"
android:summary=
"@string/onetime_auth_summary"
android:summary=
"@string/onetime_auth_summary"
android:title=
"@string/onetime_auth"
>
android:title=
"@string/onetime_auth"
/>
</SwitchPreference>
<SwitchPreference
android:key=
"isAutoConnect"
android:summary=
"@string/auto_connect_summary"
android:title=
"@string/auto_connect"
>
</SwitchPreference>
</PreferenceCategory>
</PreferenceCategory>
...
...
src/main/scala/com/github/shadowsocks/AppManager.scala
View file @
51e155c9
...
@@ -39,32 +39,26 @@
...
@@ -39,32 +39,26 @@
package
com.github.shadowsocks
package
com.github.shadowsocks
import
android.app.
{
Activity
,
ProgressDialog
}
import
java.io.
{
ByteArrayInputStream
,
ByteArrayOutputStream
,
InputStream
}
import
android.content.ClipboardManager
import
android.content.ClipData
import
android.app.ProgressDialog
import
android.content.Context
import
android.content.
{
ClipData
,
ClipboardManager
,
Context
,
SharedPreferences
}
import
android.content.SharedPreferences
import
android.content.pm.PackageManager
import
android.content.pm.PackageManager
import
android.graphics.
{
Bitmap
,
PixelFormat
}
import
android.graphics.
{
Bitmap
,
PixelFormat
}
import
android.os.Bundle
import
android.os.
{
Bundle
,
Handler
}
import
android.os.Handler
import
android.preference.PreferenceManager
import
android.preference.PreferenceManager
import
android.support.v7.app.AppCompatActivity
import
android.support.v7.widget.Toolbar
import
android.support.v7.widget.Toolbar
import
android.view.Menu
import
android.view.MenuItem
import
android.view.View
import
android.view.View.OnClickListener
import
android.view.View.OnClickListener
import
android.view.ViewGroup
import
android.view.ViewGroup.LayoutParams
import
android.view.ViewGroup.LayoutParams
import
android.view.WindowManager
import
android.view.
{
Menu
,
MenuItem
,
View
,
ViewGroup
,
WindowManager
}
import
android.widget._
import
android.widget.AbsListView.OnScrollListener
import
android.widget.AbsListView.OnScrollListener
import
android.widget.CompoundButton.OnCheckedChangeListener
import
android.widget.CompoundButton.OnCheckedChangeListener
import
android.widget._
import
com.github.shadowsocks.utils.
{
Key
,
Scheme
,
Utils
}
import
com.nostra13.universalimageloader.core.display.FadeInBitmapDisplayer
import
com.nostra13.universalimageloader.core.download.BaseImageDownloader
import
com.nostra13.universalimageloader.core.download.BaseImageDownloader
import
java.io.
{
ByteArrayOutputStream
,
ByteArrayInputStream
,
InputStream
}
import
com.nostra13.universalimageloader.core.
{
DisplayImageOptions
,
ImageLoader
,
ImageLoaderConfiguration
}
import
com.nostra13.universalimageloader.core.
{
DisplayImageOptions
,
ImageLoader
,
ImageLoaderConfiguration
}
import
com.nostra13.universalimageloader.core.display.FadeInBitmapDisplayer
import
com.github.shadowsocks.utils.
{
Utils
,
Scheme
,
Key
}
import
scala.concurrent.ExecutionContext.Implicits.global
import
scala.concurrent.ExecutionContext.Implicits.global
import
scala.concurrent.Future
import
scala.concurrent.Future
...
@@ -105,7 +99,7 @@ object AppManager {
...
@@ -105,7 +99,7 @@ object AppManager {
}
}
}
}
class
AppManager
extends
Activity
with
OnCheckedChangeListener
with
OnClickListener
{
class
AppManager
extends
A
ppCompatA
ctivity
with
OnCheckedChangeListener
with
OnClickListener
{
val
MSG_LOAD_START
=
1
val
MSG_LOAD_START
=
1
val
MSG_LOAD_FINISH
=
2
val
MSG_LOAD_FINISH
=
2
...
...
src/main/scala/com/github/shadowsocks/ParserActivity.scala
View file @
51e155c9
...
@@ -57,14 +57,14 @@ class ParserActivity extends Activity {
...
@@ -57,14 +57,14 @@ class ParserActivity extends Activity {
new
AlertDialog
.
Builder
(
this
)
new
AlertDialog
.
Builder
(
this
)
.
setTitle
(
R
.
string
.
add_profile_dialog
)
.
setTitle
(
R
.
string
.
add_profile_dialog
)
.
setCancelable
(
false
)
.
setCancelable
(
false
)
.
setPositiveButton
(
R
.
string
.
yes
,
((
dialog
:
DialogInterface
,
id
:
Int
)
=>
{
.
setPositiveButton
(
android
.
R
.
string
.
yes
,
((
dialog
:
DialogInterface
,
id
:
Int
)
=>
{
Parser
.
parse
(
data
)
match
{
Parser
.
parse
(
data
)
match
{
case
Some
(
profile
)
=>
addProfile
(
profile
)
case
Some
(
profile
)
=>
addProfile
(
profile
)
case
_
=>
// ignore
case
_
=>
// ignore
}
}
dialog
.
dismiss
()
dialog
.
dismiss
()
})
:
DialogInterface.OnClickListener
)
})
:
DialogInterface.OnClickListener
)
.
setNegativeButton
(
R
.
string
.
no
,
((
dialog
:
DialogInterface
,
id
:
Int
)
=>
{
.
setNegativeButton
(
android
.
R
.
string
.
no
,
((
dialog
:
DialogInterface
,
id
:
Int
)
=>
{
dialog
.
dismiss
()
dialog
.
dismiss
()
finish
()
finish
()
})
:
DialogInterface.OnClickListener
)
})
:
DialogInterface.OnClickListener
)
...
@@ -90,7 +90,7 @@ class ParserActivity extends Activity {
...
@@ -90,7 +90,7 @@ class ParserActivity extends Activity {
h
.
postDelayed
(()
=>
{
h
.
postDelayed
(()
=>
{
val
profileManager
=
val
profileManager
=
new
ProfileManager
(
PreferenceManager
.
getDefaultSharedPreferences
(
getBaseContext
),
new
ProfileManager
(
PreferenceManager
.
getDefaultSharedPreferences
(
getBaseContext
),
getApplication
.
asInstanceOf
[
ShadowsocksApplication
]
.
dbHelper
)
ShadowsocksApplication
.
dbHelper
)
profileManager
.
createOrUpdateProfile
(
profile
)
profileManager
.
createOrUpdateProfile
(
profile
)
profileManager
.
reload
(
profile
.
id
)
profileManager
.
reload
(
profile
.
id
)
h
.
sendEmptyMessage
(
0
)
h
.
sendEmptyMessage
(
0
)
...
...
src/main/scala/com/github/shadowsocks/ProfileManagerActivity.scala
0 → 100644
View file @
51e155c9
package
com.github.shadowsocks
import
android.app.AlertDialog
import
android.content.
{
DialogInterface
,
Intent
}
import
android.os.Bundle
import
android.support.design.widget.Snackbar
import
android.support.v7.app.AppCompatActivity
import
android.support.v7.widget.RecyclerView.ViewHolder
import
android.support.v7.widget.Toolbar.OnMenuItemClickListener
import
android.support.v7.widget.helper.ItemTouchHelper
import
android.support.v7.widget.helper.ItemTouchHelper.SimpleCallback
import
android.support.v7.widget.
{
DefaultItemAnimator
,
LinearLayoutManager
,
RecyclerView
,
Toolbar
}
import
android.view.View.
{
OnAttachStateChangeListener
,
OnClickListener
}
import
android.view.
{
LayoutInflater
,
MenuItem
,
View
,
ViewGroup
}
import
android.widget.
{
LinearLayout
,
ImageView
,
CheckedTextView
,
Toast
}
import
com.github.shadowsocks.database.Profile
import
com.github.shadowsocks.utils.
{
Parser
,
Utils
}
import
com.google.zxing.integration.android.IntentIntegrator
import
net.glxn.qrgen.android.QRCode
import
scala.collection.mutable.ArrayBuffer
/**
* @author Mygod
*/
class
ProfileManagerActivity
extends
AppCompatActivity
with
OnMenuItemClickListener
{
private
class
ProfileViewHolder
(
val
view
:
View
)
extends
RecyclerView
.
ViewHolder
(
view
)
with
View
.
OnClickListener
{
private
var
item
:
Profile
=
_
private
val
text
=
itemView
.
findViewById
(
android
.
R
.
id
.
text1
).
asInstanceOf
[
CheckedTextView
]
itemView
.
setOnClickListener
(
this
)
{
val
qrcode
=
itemView
.
findViewById
(
R
.
id
.
qrcode
)
qrcode
.
setOnClickListener
((
v
:
View
)
=>
{
val
image
=
new
ImageView
(
ProfileManagerActivity
.
this
)
image
.
setLayoutParams
(
new
LinearLayout
.
LayoutParams
(-
1
,
-
1
))
val
qrcode
=
QRCode
.
from
(
Parser
.
generate
(
item
))
.
withSize
(
Utils
.
dpToPx
(
ProfileManagerActivity
.
this
,
250
),
Utils
.
dpToPx
(
ProfileManagerActivity
.
this
,
250
))
.
asInstanceOf
[
QRCode
]
image
.
setImageBitmap
(
qrcode
.
bitmap
())
new
AlertDialog
.
Builder
(
ProfileManagerActivity
.
this
)
.
setCancelable
(
true
)
.
setNegativeButton
(
getString
(
R
.
string
.
close
),
((
dialog
:
DialogInterface
,
id
:
Int
)
=>
dialog
.
cancel
())
:
DialogInterface.OnClickListener
)
.
setView
(
image
)
.
create
()
.
show
()
})
qrcode
.
setOnLongClickListener
((
v
:
View
)
=>
{
Utils
.
positionToast
(
Toast
.
makeText
(
ProfileManagerActivity
.
this
,
R
.
string
.
qrcode
,
Toast
.
LENGTH_SHORT
),
qrcode
,
getWindow
,
0
,
Utils
.
dpToPx
(
ProfileManagerActivity
.
this
,
8
)).
show
true
})
}
def
bind
(
item
:
Profile
)
{
text
.
setText
(
item
.
name
)
text
.
setChecked
(
item
.
id
==
ShadowsocksApplication
.
profileId
)
this
.
item
=
item
}
def
onClick
(
v
:
View
)
=
{
ShadowsocksApplication
.
profileId
(
item
.
id
)
finish
}
}
private
class
ProfilesAdapter
extends
RecyclerView
.
Adapter
[
ProfileViewHolder
]
{
private
val
recycleBin
=
new
ArrayBuffer
[(
Int
,
Profile
)]
private
var
profiles
=
new
ArrayBuffer
[
Profile
]
profiles
++=
ShadowsocksApplication
.
profileManager
.
getAllProfiles
.
getOrElse
(
List
[
Profile
]())
def
getItemCount
=
profiles
.
length
def
onBindViewHolder
(
vh
:
ProfileViewHolder
,
i
:
Int
)
=
vh
.
bind
(
profiles
(
i
))
def
onCreateViewHolder
(
vg
:
ViewGroup
,
i
:
Int
)
=
new
ProfileViewHolder
(
LayoutInflater
.
from
(
vg
.
getContext
).
inflate
(
R
.
layout
.
layout_profiles_item
,
vg
,
false
))
def
add
(
item
:
Profile
)
{
removedSnackbar
.
dismiss
commitRemoves
val
pos
=
getItemCount
if
(
ShadowsocksApplication
.
profileManager
.
createOrUpdateProfile
(
item
))
{
profiles
+=
item
notifyItemInserted
(
pos
)
}
}
def
remove
(
pos
:
Int
)
{
recycleBin
.
append
((
pos
,
profiles
(
pos
)))
profiles
.
remove
(
pos
)
notifyItemRemoved
(
pos
)
}
def
undoRemoves
{
for
((
index
,
item
)
<-
recycleBin
.
reverseIterator
)
{
profiles
.
insert
(
index
,
item
)
notifyItemInserted
(
index
)
}
recycleBin
.
clear
}
def
commitRemoves
{
for
((
index
,
item
)
<-
recycleBin
)
{
ShadowsocksApplication
.
profileManager
.
delProfile
(
item
.
id
)
if
(
item
.
id
==
ShadowsocksApplication
.
profileId
)
ShadowsocksApplication
.
profileId
(-
1
)
}
recycleBin
.
clear
}
}
private
lazy
val
profilesAdapter
=
new
ProfilesAdapter
private
var
removedSnackbar
:
Snackbar
=
_
override
def
onCreate
(
savedInstanceState
:
Bundle
)
{
super
.
onCreate
(
savedInstanceState
)
setContentView
(
R
.
layout
.
layout_profiles
)
val
toolbar
=
findViewById
(
R
.
id
.
toolbar
).
asInstanceOf
[
Toolbar
]
toolbar
.
setTitle
(
R
.
string
.
profiles
)
toolbar
.
setNavigationIcon
(
R
.
drawable
.
abc_ic_ab_back_mtrl_am_alpha
)
toolbar
.
setNavigationOnClickListener
((
v
:
View
)
=>
{
val
intent
=
getParentActivityIntent
if
(
intent
==
null
)
finish
else
navigateUpTo
(
intent
)
})
toolbar
.
inflateMenu
(
R
.
menu
.
add_profile_methods
)
toolbar
.
setOnMenuItemClickListener
(
this
)
val
profilesList
=
findViewById
(
R
.
id
.
profilesList
).
asInstanceOf
[
RecyclerView
]
profilesList
.
setLayoutManager
(
new
LinearLayoutManager
(
this
))
profilesList
.
setItemAnimator
(
new
DefaultItemAnimator
)
profilesList
.
setAdapter
(
profilesAdapter
)
removedSnackbar
=
Snackbar
.
make
(
findViewById
(
android
.
R
.
id
.
content
),
R
.
string
.
removed
,
Snackbar
.
LENGTH_LONG
)
.
setAction
(
R
.
string
.
undo
,
((
v
:
View
)
=>
profilesAdapter
.
undoRemoves
)
:
OnClickListener
)
removedSnackbar
.
getView
.
addOnAttachStateChangeListener
(
new
OnAttachStateChangeListener
{
def
onViewDetachedFromWindow
(
v
:
View
)
=
profilesAdapter
.
commitRemoves
def
onViewAttachedToWindow
(
v
:
View
)
=
()
})
new
ItemTouchHelper
(
new
SimpleCallback
(
0
,
ItemTouchHelper
.
START
|
ItemTouchHelper
.
END
)
{
def
onSwiped
(
viewHolder
:
ViewHolder
,
direction
:
Int
)
=
{
profilesAdapter
.
remove
(
viewHolder
.
getAdapterPosition
)
removedSnackbar
.
show
}
def
onMove
(
recyclerView
:
RecyclerView
,
viewHolder
:
ViewHolder
,
target
:
ViewHolder
)
=
false
// TODO?
}).
attachToRecyclerView
(
profilesList
)
}
override
def
onDestroy
{
super
.
onDestroy
profilesAdapter
.
commitRemoves
}
override
def
onActivityResult
(
requestCode
:
Int
,
resultCode
:
Int
,
data
:
Intent
)
{
val
scanResult
=
IntentIntegrator
.
parseActivityResult
(
requestCode
,
resultCode
,
data
)
if
(
scanResult
!=
null
)
Parser
.
parse
(
scanResult
.
getContents
)
match
{
case
Some
(
profile
)
=>
profilesAdapter
.
add
(
profile
)
case
_
=>
// ignore
}
}
def
onMenuItemClick
(
item
:
MenuItem
)
=
item
.
getItemId
match
{
case
R
.
id
.
scan_qr_code
=>
val
integrator
=
new
IntentIntegrator
(
this
)
val
list
=
new
java
.
util
.
ArrayList
(
IntentIntegrator
.
TARGET_ALL_KNOWN
)
list
.
add
(
"tw.com.quickmark"
)
integrator
.
setTargetApplications
(
list
)
integrator
.
initiateScan
()
true
case
R
.
id
.
manual_settings
=>
ShadowsocksApplication
.
profileManager
.
reload
(-
1
)
ShadowsocksApplication
.
profileId
(
ShadowsocksApplication
.
profileManager
.
save
.
id
)
finish
true
case
_
=>
false
}
}
src/main/scala/com/github/shadowsocks/Shadowsocks.scala
View file @
51e155c9
This diff is collapsed.
Click to expand it.
src/main/scala/com/github/shadowsocks/ShadowsocksApplication.scala
View file @
51e155c9
...
@@ -43,19 +43,47 @@ import java.util
...
@@ -43,19 +43,47 @@ import java.util
import
java.util.concurrent.TimeUnit
import
java.util.concurrent.TimeUnit
import
android.app.Application
import
android.app.Application
import
com.github.shadowsocks.database.DBHelper
import
android.content.pm.PackageManager
import
com.github.shadowsocks.utils.Utils
import
android.preference.PreferenceManager
import
com.google.android.gms.analytics.GoogleAnalytics
import
com.github.shadowsocks.database.
{
DBHelper
,
ProfileManager
}
import
com.github.shadowsocks.utils.
{
Key
,
Utils
}
import
com.google.android.gms.analytics.
{
HitBuilders
,
GoogleAnalytics
}
import
com.google.android.gms.common.api.ResultCallback
import
com.google.android.gms.common.api.ResultCallback
import
com.google.android.gms.tagmanager.
{
ContainerHolder
,
TagManager
}
import
com.google.android.gms.tagmanager.
{
ContainerHolder
,
TagManager
}
object
ShadowsocksApplication
{
var
instance
:
ShadowsocksApplication
=
_
lazy
val
dbHelper
=
new
DBHelper
(
instance
)
final
val
SIG_FUNC
=
"getSignature"
var
containerHolder
:
ContainerHolder
=
_
lazy
val
tracker
=
GoogleAnalytics
.
getInstance
(
instance
).
newTracker
(
R
.
xml
.
tracker
)
lazy
val
settings
=
PreferenceManager
.
getDefaultSharedPreferences
(
instance
)
lazy
val
profileManager
=
new
ProfileManager
(
settings
,
dbHelper
)
def
getVersionName
=
try
{
instance
.
getPackageManager
.
getPackageInfo
(
instance
.
getPackageName
,
0
).
versionName
}
catch
{
case
_:
PackageManager.NameNotFoundException
=>
"Package name not found"
case
_:
Throwable
=>
null
}
// send event
def
track
(
category
:
String
,
action
:
String
)
=
tracker
.
send
(
new
HitBuilders
.
EventBuilder
()
.
setAction
(
action
)
.
setLabel
(
getVersionName
)
.
build
())
def
profileId
=
settings
.
getInt
(
Key
.
profileId
,
-
1
)
def
profileId
(
i
:
Int
)
=
settings
.
edit
.
putInt
(
Key
.
profileId
,
i
).
apply
def
proxy
=
settings
.
getString
(
Key
.
proxy
,
""
)
def
currentProfile
=
profileManager
.
getProfile
(
profileId
)
}
class
ShadowsocksApplication
extends
Application
{
class
ShadowsocksApplication
extends
Application
{
lazy
val
dbHelper
=
new
DBHelper
(
this
)
import
ShadowsocksApplication._
lazy
val
SIG_FUNC
=
"getSignature"
var
containerHolder
:
ContainerHolder
=
null
lazy
val
tracker
=
GoogleAnalytics
.
getInstance
(
this
).
newTracker
(
R
.
xml
.
tracker
)
override
def
onCreate
()
{
override
def
onCreate
()
{
ShadowsocksApplication
.
instance
=
this
val
tm
=
TagManager
.
getInstance
(
this
)
val
tm
=
TagManager
.
getInstance
(
this
)
val
pending
=
tm
.
loadContainerPreferNonDefault
(
"GTM-NT8WS8"
,
R
.
raw
.
gtm_default_container
)
val
pending
=
tm
.
loadContainerPreferNonDefault
(
"GTM-NT8WS8"
,
R
.
raw
.
gtm_default_container
)
val
callback
=
new
ResultCallback
[
ContainerHolder
]
{
val
callback
=
new
ResultCallback
[
ContainerHolder
]
{
...
...
src/main/scala/com/github/shadowsocks/ShadowsocksNatService.scala
View file @
51e155c9
...
@@ -40,22 +40,20 @@
...
@@ -40,22 +40,20 @@
package
com.github.shadowsocks
package
com.github.shadowsocks
import
java.io.File
import
java.io.File
import
java.lang.reflect.
{
InvocationTargetException
,
Method
}
import
java.net.
{
Inet6Address
,
InetAddress
}
import
java.net.
{
Inet6Address
,
InetAddress
}
import
java.util.Locale
import
java.util.Locale
import
android.app._
import
android.app._
import
android.content._
import
android.content._
import
android.content.pm.
{
PackageInfo
,
PackageManager
}
import
android.content.pm.
{
PackageInfo
,
PackageManager
}
import
android.net.
{
Network
,
ConnectivityManager
}
import
android.net.
{
ConnectivityManager
,
Network
}
import
android.os._
import
android.os._
import
android.support.v4.app.NotificationCompat
import
android.support.v4.app.NotificationCompat
import
android.support.v4.content.ContextCompat
import
android.support.v4.content.ContextCompat
import
android.util.
{
SparseArray
,
Log
}
import
android.util.
{
Log
,
SparseArray
}
import
android.widget.Toast
import
android.widget.Toast
import
com.github.shadowsocks.aidl.Config
import
com.github.shadowsocks.aidl.Config
import
com.github.shadowsocks.utils._
import
com.github.shadowsocks.utils._
import
com.google.android.gms.analytics.HitBuilders
import
scala.collection._
import
scala.collection._
import
scala.collection.mutable.ArrayBuffer
import
scala.collection.mutable.ArrayBuffer
...
@@ -77,8 +75,6 @@ class ShadowsocksNatService extends Service with BaseService {
...
@@ -77,8 +75,6 @@ class ShadowsocksNatService extends Service with BaseService {
var
apps
:
Array
[
ProxiedApp
]
=
null
var
apps
:
Array
[
ProxiedApp
]
=
null
val
myUid
=
Process
.
myUid
()
val
myUid
=
Process
.
myUid
()
private
lazy
val
application
=
getApplication
.
asInstanceOf
[
ShadowsocksApplication
]
private
val
dnsAddressCache
=
new
SparseArray
[
String
]
private
val
dnsAddressCache
=
new
SparseArray
[
String
]
def
getNetId
(
network
:
Network
)
:
Int
=
{
def
getNetId
(
network
:
Network
)
:
Int
=
{
...
@@ -254,8 +250,8 @@ class ShadowsocksNatService extends Service with BaseService {
...
@@ -254,8 +250,8 @@ class ShadowsocksNatService extends Service with BaseService {
def
startDnsDaemon
()
{
def
startDnsDaemon
()
{
val
conf
=
if
(
config
.
route
==
Route
.
BYPASS_CHN
)
{
val
conf
=
if
(
config
.
route
==
Route
.
BYPASS_CHN
)
{
val
reject
=
ConfigUtils
.
getRejectList
(
getContext
,
application
)
val
reject
=
ConfigUtils
.
getRejectList
(
getContext
)
val
blackList
=
ConfigUtils
.
getBlackList
(
getContext
,
application
)
val
blackList
=
ConfigUtils
.
getBlackList
(
getContext
)
ConfigUtils
.
PDNSD_DIRECT
.
formatLocal
(
Locale
.
ENGLISH
,
"127.0.0.1"
,
8153
,
ConfigUtils
.
PDNSD_DIRECT
.
formatLocal
(
Locale
.
ENGLISH
,
"127.0.0.1"
,
8153
,
Path
.
BASE
+
"pdnsd-nat.pid"
,
reject
,
blackList
,
8163
,
""
)
Path
.
BASE
+
"pdnsd-nat.pid"
,
reject
,
blackList
,
8163
,
""
)
}
else
{
}
else
{
...
@@ -457,19 +453,14 @@ class ShadowsocksNatService extends Service with BaseService {
...
@@ -457,19 +453,14 @@ class ShadowsocksNatService extends Service with BaseService {
registerReceiver
(
lockReceiver
,
screenFilter
)
registerReceiver
(
lockReceiver
,
screenFilter
)
}
}
// send event
ShadowsocksApplication
.
track
(
TAG
,
"start"
)
application
.
tracker
.
send
(
new
HitBuilders
.
EventBuilder
()
.
setCategory
(
TAG
)
.
setAction
(
"start"
)
.
setLabel
(
getVersionName
)
.
build
())
changeState
(
State
.
CONNECTING
)
changeState
(
State
.
CONNECTING
)
Future
{
Future
{
if
(
config
.
proxy
==
"198.199.101.152"
)
{
if
(
config
.
proxy
==
"198.199.101.152"
)
{
val
holder
=
a
pplication
.
containerHolder
val
holder
=
ShadowsocksA
pplication
.
containerHolder
try
{
try
{
config
=
ConfigUtils
.
getPublicConfig
(
getBaseContext
,
holder
.
getContainer
,
config
)
config
=
ConfigUtils
.
getPublicConfig
(
getBaseContext
,
holder
.
getContainer
,
config
)
}
catch
{
}
catch
{
...
@@ -531,12 +522,7 @@ class ShadowsocksNatService extends Service with BaseService {
...
@@ -531,12 +522,7 @@ class ShadowsocksNatService extends Service with BaseService {
}
}
}
}
// send event
ShadowsocksApplication
.
track
(
TAG
,
"stop"
)
application
.
tracker
.
send
(
new
HitBuilders
.
EventBuilder
()
.
setCategory
(
TAG
)
.
setAction
(
"stop"
)
.
setLabel
(
getVersionName
)
.
build
())
// reset NAT
// reset NAT
killProcesses
()
killProcesses
()
...
...
src/main/scala/com/github/shadowsocks/ShadowsocksSettings.scala
View file @
51e155c9
package
com.github.shadowsocks
package
com.github.shadowsocks
import
android.os.Bundle
import
android.os.Bundle
import
android.preference.
PreferenceFragment
import
android.preference.
{
Preference
,
PreferenceFragment
}
// TODO: Move related logic here
// TODO: Move related logic here
class
ShadowsocksSettings
extends
PreferenceFragment
{
class
ShadowsocksSettings
extends
PreferenceFragment
{
private
lazy
val
activity
=
getActivity
.
asInstanceOf
[
Shadowsocks
]
override
def
onCreate
(
savedInstanceState
:
Bundle
)
{
override
def
onCreate
(
savedInstanceState
:
Bundle
)
{
super
.
onCreate
(
savedInstanceState
)
super
.
onCreate
(
savedInstanceState
)
addPreferencesFromResource
(
R
.
xml
.
pref_all
)
addPreferencesFromResource
(
R
.
xml
.
pref_all
)
findPreference
(
"recovery"
).
setOnPreferenceClickListener
((
preference
:
Preference
)
=>
{
ShadowsocksApplication
.
track
(
Shadowsocks
.
TAG
,
"reset"
)
activity
.
recovery
()
true
})
findPreference
(
"flush_dnscache"
).
setOnPreferenceClickListener
((
preference
:
Preference
)
=>
{
ShadowsocksApplication
.
track
(
Shadowsocks
.
TAG
,
"flush_dnscache"
)
activity
.
flushDnsCache
()
true
})
}
}
}
}
src/main/scala/com/github/shadowsocks/ShadowsocksVpnService.scala
View file @
51e155c9
...
@@ -53,7 +53,6 @@ import android.util.Log
...
@@ -53,7 +53,6 @@ import android.util.Log
import
android.widget.Toast
import
android.widget.Toast
import
com.github.shadowsocks.aidl.Config
import
com.github.shadowsocks.aidl.Config
import
com.github.shadowsocks.utils._
import
com.github.shadowsocks.utils._
import
com.google.android.gms.analytics.HitBuilders
import
org.apache.commons.net.util.SubnetUtils
import
org.apache.commons.net.util.SubnetUtils
import
scala.collection.mutable
import
scala.collection.mutable
...
@@ -62,8 +61,6 @@ import scala.concurrent.ExecutionContext.Implicits.global
...
@@ -62,8 +61,6 @@ import scala.concurrent.ExecutionContext.Implicits.global
import
scala.concurrent.Future
import
scala.concurrent.Future
class
ShadowsocksVpnService
extends
VpnService
with
BaseService
{
class
ShadowsocksVpnService
extends
VpnService
with
BaseService
{
private
lazy
val
application
=
getApplication
.
asInstanceOf
[
ShadowsocksApplication
]
val
TAG
=
"ShadowsocksVpnService"
val
TAG
=
"ShadowsocksVpnService"
val
VPN_MTU
=
1500
val
VPN_MTU
=
1500
val
PRIVATE_VLAN
=
"26.26.26.%s"
val
PRIVATE_VLAN
=
"26.26.26.%s"
...
@@ -152,12 +149,7 @@ class ShadowsocksVpnService extends VpnService with BaseService {
...
@@ -152,12 +149,7 @@ class ShadowsocksVpnService extends VpnService with BaseService {
// channge the state
// channge the state
changeState
(
State
.
STOPPING
)
changeState
(
State
.
STOPPING
)
// send event
ShadowsocksApplication
.
track
(
TAG
,
"stop"
)
application
.
tracker
.
send
(
new
HitBuilders
.
EventBuilder
()
.
setCategory
(
TAG
)
.
setAction
(
"stop"
)
.
setLabel
(
getVersionName
)
.
build
())
// reset VPN
// reset VPN
killProcesses
()
killProcesses
()
...
@@ -231,18 +223,13 @@ class ShadowsocksVpnService extends VpnService with BaseService {
...
@@ -231,18 +223,13 @@ class ShadowsocksVpnService extends VpnService with BaseService {
return
return
}
}
// send event
ShadowsocksApplication
.
track
(
TAG
,
"start"
)
application
.
tracker
.
send
(
new
HitBuilders
.
EventBuilder
()
.
setCategory
(
TAG
)
.
setAction
(
"start"
)
.
setLabel
(
getVersionName
)
.
build
())
changeState
(
State
.
CONNECTING
)
changeState
(
State
.
CONNECTING
)
Future
{
Future
{
if
(
config
.
proxy
==
"198.199.101.152"
)
{
if
(
config
.
proxy
==
"198.199.101.152"
)
{
val
holder
=
getApplication
.
asInstanceOf
[
ShadowsocksApplication
]
.
containerHolder
val
holder
=
ShadowsocksApplication
.
containerHolder
try
{
try
{
config
=
ConfigUtils
.
getPublicConfig
(
getBaseContext
,
holder
.
getContainer
,
config
)
config
=
ConfigUtils
.
getPublicConfig
(
getBaseContext
,
holder
.
getContainer
,
config
)
}
catch
{
}
catch
{
...
@@ -371,8 +358,8 @@ class ShadowsocksVpnService extends VpnService with BaseService {
...
@@ -371,8 +358,8 @@ class ShadowsocksVpnService extends VpnService with BaseService {
val
ipv6
=
if
(
config
.
isIpv6
)
""
else
"reject = ::/0;"
val
ipv6
=
if
(
config
.
isIpv6
)
""
else
"reject = ::/0;"
val
conf
=
{
val
conf
=
{
if
(
config
.
route
==
Route
.
BYPASS_CHN
)
{
if
(
config
.
route
==
Route
.
BYPASS_CHN
)
{
val
reject
=
ConfigUtils
.
getRejectList
(
getContext
,
application
)
val
reject
=
ConfigUtils
.
getRejectList
(
getContext
)
val
blackList
=
ConfigUtils
.
getBlackList
(
getContext
,
application
)
val
blackList
=
ConfigUtils
.
getBlackList
(
getContext
)
ConfigUtils
.
PDNSD_DIRECT
.
formatLocal
(
Locale
.
ENGLISH
,
"0.0.0.0"
,
8153
,
ConfigUtils
.
PDNSD_DIRECT
.
formatLocal
(
Locale
.
ENGLISH
,
"0.0.0.0"
,
8153
,
Path
.
BASE
+
"pdnsd-vpn.pid"
,
reject
,
blackList
,
8163
,
ipv6
)
Path
.
BASE
+
"pdnsd-vpn.pid"
,
reject
,
blackList
,
8163
,
ipv6
)
}
else
{
}
else
{
...
...
src/main/scala/com/github/shadowsocks/database/MenuAdapter.scala
deleted
100644 → 0
View file @
1f695b9c
/*
* Shadowsocks - A shadowsocks client for Android
* Copyright (C) 2014 <max.c.lv@gmail.com>
*
* 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/>.
*
*
* ___====-_ _-====___
* _--^^^#####// \\#####^^^--_
* _-^##########// ( ) \\##########^-_
* -############// |\^^/| \\############-
* _/############// (@::@) \\############\_
* /#############(( \\// ))#############\
* -###############\\ (oo) //###############-
* -#################\\ / VV \ //#################-
* -###################\\/ \//###################-
* _#/|##########/\######( /\ )######/\##########|\#_
* |/ |#/\#/\#/\/ \#/\##\ | | /##/\#/ \/\#/\#/\#| \|
* ` |/ V V ` V \#\| | | |/#/ V ' V V \| '
* ` ` ` ` / | | | | \ ' ' ' '
* ( | | | | )
* __\ | | | | /__
* (vvv(VVV)(VVV)vvv)
*
* HERE BE DRAGONS
*
*/
package
com.github.shadowsocks.database
import
android.content.Context
import
android.graphics.drawable.Drawable
import
android.view.
{
LayoutInflater
,
View
,
ViewGroup
}
import
android.widget.
{
BaseAdapter
,
TextView
}
import
com.github.shadowsocks.R
abstract
class
Item
{
def
id
:
Int
def
title
:
String
def
click
:
Int
=>
Unit
def
longClick
:
Int
=>
Boolean
}
case
class
IconItem
(
id
:
Int
,
title
:
String
,
iconRes
:
Int
,
click
:
Int
=>
Unit
,
longClick
:
Int
=>
Boolean
=
_
=>
false
)
extends
Item
case
class
DrawableItem
(
id
:
Int
,
title
:
String
,
iconRes
:
Drawable
,
click
:
Int
=>
Unit
,
longClick
:
Int
=>
Boolean
=
_
=>
false
)
extends
Item
case
class
Category
(
title
:
String
)
object
MenuAdapter
{
trait
MenuListener
{
def
onActiveViewChanged
(
v
:
View
,
pos
:
Int
)
}
val
UNDEFINED
=
-
1
val
CATEGORY
=
0
val
ITEM
=
1
}
class
MenuAdapter
(
context
:
Context
,
var
items
:
List
[
Any
])
extends
BaseAdapter
{
def
setListener
(
listener
:
MenuAdapter.MenuListener
)
{
this
.
listener
=
listener
}
def
setActiveId
(
activeId
:
Int
)
{
this
.
activeId
=
activeId
}
@Override
def
getCount
:
Int
=
{
items
.
size
}
@Override
def
getItem
(
position
:
Int
)
:
Object
=
{
items
(
position
).
asInstanceOf
[
Object
]
}
@Override
def
getItemId
(
position
:
Int
)
:
Long
=
{
position
}
@Override
override
def
getItemViewType
(
position
:
Int
)
:
Int
=
{
getItem
(
position
)
match
{
case
Category
=>
MenuAdapter
.
CATEGORY
case
IconItem
=>
MenuAdapter
.
ITEM
case
DrawableItem
=>
MenuAdapter
.
ITEM
case
_
=>
MenuAdapter
.
UNDEFINED
}
}
@Override
override
def
getViewTypeCount
:
Int
=
{
3
}
@Override
override
def
isEnabled
(
position
:
Int
)
:
Boolean
=
{
getItemViewType
(
position
)
!=
MenuAdapter
.
UNDEFINED
}
@Override
override
def
areAllItemsEnabled
:
Boolean
=
{
false
}
@Override
def
getView
(
position
:
Int
,
convertView
:
View
,
parent
:
ViewGroup
)
:
View
=
{
var
v
:
View
=
convertView
val
item
=
getItem
(
position
)
item
match
{
case
value
:
Category
=>
if
(
v
==
null
)
{
v
=
LayoutInflater
.
from
(
context
).
inflate
(
R
.
layout
.
menu_row_category
,
parent
,
false
)
}
v
.
asInstanceOf
[
TextView
].
setText
(
value
.
title
)
case
value
:
Item
=>
if
(
v
==
null
)
{
v
=
LayoutInflater
.
from
(
context
).
inflate
(
R
.
layout
.
menu_row_item
,
parent
,
false
)
}
val
tv
:
TextView
=
v
.
asInstanceOf
[
TextView
]
tv
.
setText
(
value
.
title
)
value
match
{
case
iconItem
:
IconItem
=>
if
(
iconItem
.
iconRes
!=
-
1
)
{
tv
.
setCompoundDrawablesWithIntrinsicBounds
(
iconItem
.
iconRes
,
0
,
0
,
0
)
}
case
drawableItem
:
DrawableItem
=>
if
(
drawableItem
.
iconRes
!=
null
)
{
tv
.
setCompoundDrawablesWithIntrinsicBounds
(
drawableItem
.
iconRes
,
null
,
null
,
null
)
}
}
tv
.
setOnClickListener
((
view
:
View
)
=>
{
val
item
=
view
.
getTag
(
R
.
id
.
mdItem
).
asInstanceOf
[
Item
]
item
.
click
(
item
.
id
)
})
tv
.
setOnLongClickListener
((
view
:
View
)
=>
{
val
item
=
view
.
getTag
(
R
.
id
.
mdItem
).
asInstanceOf
[
Item
]
item
.
longClick
(
item
.
id
)
})
v
.
setTag
(
R
.
id
.
mdItem
,
value
)
if
(
value
.
id
==
activeId
)
{
if
(
listener
!=
null
)
listener
.
onActiveViewChanged
(
v
,
position
)
}
case
_
=>
}
v
.
setTag
(
R
.
id
.
mdActiveViewPosition
,
position
)
v
}
def
updateList
(
list
:
List
[
Any
],
activeId
:
Int
)
{
items
=
list
this
.
activeId
=
activeId
notifyDataSetChanged
()
}
private
var
listener
:
MenuAdapter.MenuListener
=
null
private
var
activeId
:
Int
=
-
1
}
src/main/scala/com/github/shadowsocks/preferences/ProfileEditTextPreference.scala
deleted
100644 → 0
View file @
1f695b9c
/*
* Shadowsocks - A shadowsocks client for Android
* Copyright (C) 2013 <max.c.lv@gmail.com>
*
* 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/>.
*
*
* ___====-_ _-====___
* _--^^^#####// \\#####^^^--_
* _-^##########// ( ) \\##########^-_
* -############// |\^^/| \\############-
* _/############// (@::@) \\############\_
* /#############(( \\// ))#############\
* -###############\\ (oo) //###############-
* -#################\\ / VV \ //#################-
* -###################\\/ \//###################-
* _#/|##########/\######( /\ )######/\##########|\#_
* |/ |#/\#/\#/\/ \#/\##\ | | /##/\#/ \/\#/\#/\#| \|
* ` |/ V V ` V \#\| | | |/#/ V ' V V \| '
* ` ` ` ` / | | | | \ ' ' ' '
* ( | | | | )
* __\ | | | | /__
* (vvv(VVV)(VVV)vvv)
*
* HERE BE DRAGONS
*
*/
package
com.github.shadowsocks.preferences
import
android.content.
{
Intent
,
Context
}
import
android.preference.EditTextPreference
import
android.util.AttributeSet
import
com.github.shadowsocks.utils.Action
class
ProfileEditTextPreference
(
context
:
Context
,
attrs
:
AttributeSet
,
defStyle
:
Int
)
extends
EditTextPreference
(
context
,
attrs
,
defStyle
)
{
def
this
(
context
:
Context
,
attrs
:
AttributeSet
)
=
{
this
(
context
,
attrs
,
android
.
R
.
attr
.
editTextPreferenceStyle
)
mDefaultSummary
=
getSummary
}
override
def
setText
(
text
:
String
)
{
super
.
setText
(
text
)
setSummary
(
text
)
}
override
def
setSummary
(
summary
:
CharSequence
)
{
if
(
summary
.
toString
.
isEmpty
)
{
super
.
setSummary
(
mDefaultSummary
)
}
else
{
super
.
setSummary
(
summary
)
}
context
.
sendBroadcast
(
new
Intent
(
Action
.
UPDATE_PREFS
))
}
def
resetSummary
(
summary
:
CharSequence
)
{
if
(
summary
.
toString
.
isEmpty
)
{
super
.
setSummary
(
mDefaultSummary
)
}
else
{
super
.
setSummary
(
summary
)
}
}
private
var
mDefaultSummary
:
CharSequence
=
getSummary
}
src/main/scala/com/github/shadowsocks/utils/ConfigUtils.scala
View file @
51e155c9
...
@@ -198,14 +198,14 @@ object ConfigUtils {
...
@@ -198,14 +198,14 @@ object ConfigUtils {
}
}
def
refresh
(
context
:
Context
)
{
def
refresh
(
context
:
Context
)
{
val
holder
=
context
.
getApplicationContext
.
asInstanceOf
[
ShadowsocksApplication
]
.
containerHolder
val
holder
=
ShadowsocksApplication
.
containerHolder
if
(
holder
!=
null
)
holder
.
refresh
()
if
(
holder
!=
null
)
holder
.
refresh
()
}
}
def
getRejectList
(
context
:
Context
,
app
:
ShadowsocksApplication
)
:
String
=
{
def
getRejectList
(
context
:
Context
)
:
String
=
{
val
default
=
context
.
getString
(
R
.
string
.
reject
)
val
default
=
context
.
getString
(
R
.
string
.
reject
)
try
{
try
{
val
container
=
app
.
containerHolder
.
getContainer
val
container
=
ShadowsocksApplication
.
containerHolder
.
getContainer
val
update
=
container
.
getString
(
"reject"
)
val
update
=
container
.
getString
(
"reject"
)
if
(
update
==
null
||
update
.
isEmpty
)
default
else
update
if
(
update
==
null
||
update
.
isEmpty
)
default
else
update
}
catch
{
}
catch
{
...
@@ -213,10 +213,10 @@ object ConfigUtils {
...
@@ -213,10 +213,10 @@ object ConfigUtils {
}
}
}
}
def
getBlackList
(
context
:
Context
,
app
:
ShadowsocksApplication
)
:
String
=
{
def
getBlackList
(
context
:
Context
)
:
String
=
{
val
default
=
context
.
getString
(
R
.
string
.
black_list
)
val
default
=
context
.
getString
(
R
.
string
.
black_list
)
try
{
try
{
val
container
=
app
.
containerHolder
.
getContainer
val
container
=
ShadowsocksApplication
.
containerHolder
.
getContainer
val
update
=
container
.
getString
(
"black_list"
)
val
update
=
container
.
getString
(
"black_list"
)
if
(
update
==
null
||
update
.
isEmpty
)
default
else
update
if
(
update
==
null
||
update
.
isEmpty
)
default
else
update
}
catch
{
}
catch
{
...
...
src/main/scala/com/github/shadowsocks/utils/Constants.scala
View file @
51e155c9
...
@@ -111,8 +111,6 @@ object State {
...
@@ -111,8 +111,6 @@ object State {
object
Action
{
object
Action
{
val
SERVICE
=
"com.github.shadowsocks.SERVICE"
val
SERVICE
=
"com.github.shadowsocks.SERVICE"
val
CLOSE
=
"com.github.shadowsocks.CLOSE"
val
CLOSE
=
"com.github.shadowsocks.CLOSE"
val
UPDATE_FRAGMENT
=
"com.github.shadowsocks.ACTION_UPDATE_FRAGMENT"
val
UPDATE_PREFS
=
"com.github.shadowsocks.ACTION_UPDATE_PREFS"
}
}
object
Route
{
object
Route
{
...
...
src/main/scala/com/github/shadowsocks/utils/Utils.scala
View file @
51e155c9
...
@@ -92,6 +92,9 @@ object Utils {
...
@@ -92,6 +92,9 @@ object Utils {
new
String
(
Base64
.
encode
(
mdg
.
digest
,
0
))
new
String
(
Base64
.
encode
(
mdg
.
digest
,
0
))
}
}
def
dpToPx
(
context
:
Context
,
dp
:
Int
)
:
Int
=
Math
.
round
(
dp
*
(
context
.
getResources
.
getDisplayMetrics
.
xdpi
/
DisplayMetrics
.
DENSITY_DEFAULT
))
/*
/*
* round or floor depending on whether you are using offsets(floor) or
* round or floor depending on whether you are using offsets(floor) or
* widths(round)
* widths(round)
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment