Commit 97dd8fa1 authored by Max Lv's avatar Max Lv

fix #132

parent 4b37d88f
...@@ -46,6 +46,7 @@ ...@@ -46,6 +46,7 @@
<string name="forward_stop">后台服务已停止。</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="vpn_error">后台服务启动失败:\"%s\"。</string> <string name="vpn_error">后台服务启动失败:\"%s\"。</string>
<string name="ok_iknow">确定</string> <string name="ok_iknow">确定</string>
<string name="port_alert">端口号应大于1024</string> <string name="port_alert">端口号应大于1024</string>
......
...@@ -57,6 +57,7 @@ ...@@ -57,6 +57,7 @@
<string name="forward_stop">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 Shadowsocks</string>
<string name="vpn_error">Error: \"%s\".</string> <string name="vpn_error">Error: \"%s\".</string>
<!-- alert category --> <!-- alert category -->
......
...@@ -46,7 +46,6 @@ import android.content.pm.PackageManager ...@@ -46,7 +46,6 @@ import android.content.pm.PackageManager
import android.graphics.{Bitmap, PixelFormat} import android.graphics.{Bitmap, PixelFormat}
import android.os.Bundle import android.os.Bundle
import android.os.Handler import android.os.Handler
import android.os.Message
import android.preference.PreferenceManager import android.preference.PreferenceManager
import android.view.View import android.view.View
import android.view.View.OnClickListener import android.view.View.OnClickListener
...@@ -62,7 +61,9 @@ import com.nostra13.universalimageloader.core.{DisplayImageOptions, ImageLoader, ...@@ -62,7 +61,9 @@ import com.nostra13.universalimageloader.core.{DisplayImageOptions, ImageLoader,
import com.nostra13.universalimageloader.core.display.FadeInBitmapDisplayer import com.nostra13.universalimageloader.core.display.FadeInBitmapDisplayer
import com.github.shadowsocks.utils.{Utils, Scheme, Key} import com.github.shadowsocks.utils.{Utils, Scheme, Key}
case class ProxiedApp(uid: Int, name: String, var proxied: Boolean) import scala.language.implicitConversions
case class ProxiedApp(uid: Int, name: String, packageName: String, var proxied: Boolean)
class ObjectArrayTools[T <: AnyRef](a: Array[T]) { class ObjectArrayTools[T <: AnyRef](a: Array[T]) {
def binarySearch(key: T) = { def binarySearch(key: T) = {
...@@ -74,7 +75,7 @@ case class ListEntry(box: CheckBox, text: TextView, icon: ImageView) ...@@ -74,7 +75,7 @@ case class ListEntry(box: CheckBox, text: TextView, icon: ImageView)
object AppManager { object AppManager {
implicit def anyrefarray_tools[T <: AnyRef](a: Array[T]) = new ObjectArrayTools(a) implicit def anyrefarray_tools[T <: AnyRef](a: Array[T]): ObjectArrayTools[T] = new ObjectArrayTools(a)
def getProxiedApps(context: Context, proxiedAppString: String): Array[ProxiedApp] = { def getProxiedApps(context: Context, proxiedAppString: String): Array[ProxiedApp] = {
...@@ -86,13 +87,13 @@ object AppManager { ...@@ -86,13 +87,13 @@ object AppManager {
val appList = packageManager.getInstalledApplications(0) val appList = packageManager.getInstalledApplications(0)
appList.filter(_.uid >= 10000).map { appList.filter(_.uid >= 10000).map {
case a => { case a =>
val uid = a.uid val uid = a.uid
val userName = uid.toString val userName = uid.toString
val name = packageManager.getApplicationLabel(a).toString
val packageName = a.packageName val packageName = a.packageName
val proxied = proxiedApps.binarySearch(userName) >= 0 val proxied = proxiedApps.binarySearch(userName) >= 0
new ProxiedApp(uid, packageName, proxied) new ProxiedApp(uid, name, packageName, proxied)
}
}.toArray }.toArray
} }
} }
...@@ -103,7 +104,7 @@ class AppManager extends Activity with OnCheckedChangeListener with OnClickListe ...@@ -103,7 +104,7 @@ class AppManager extends Activity with OnCheckedChangeListener with OnClickListe
val MSG_LOAD_FINISH = 2 val MSG_LOAD_FINISH = 2
val STUB = android.R.drawable.sym_def_app_icon val STUB = android.R.drawable.sym_def_app_icon
implicit def anyrefarray_tools[T <: AnyRef](a: Array[T]) = new ObjectArrayTools(a) implicit def anyrefarray_tools[T <: AnyRef](a: Array[T]): ObjectArrayTools[T] = new ObjectArrayTools(a)
var apps: Array[ProxiedApp] = null var apps: Array[ProxiedApp] = null
var appListView: ListView = null var appListView: ListView = null
...@@ -129,8 +130,9 @@ class AppManager extends Activity with OnCheckedChangeListener with OnClickListe ...@@ -129,8 +130,9 @@ class AppManager extends Activity with OnCheckedChangeListener with OnClickListe
val uid = a.uid val uid = a.uid
val userName = uid.toString val userName = uid.toString
val name = packageManager.getApplicationLabel(a).toString val name = packageManager.getApplicationLabel(a).toString
val packageName = a.packageName
val proxied = (proxiedApps binarySearch userName) >= 0 val proxied = (proxiedApps binarySearch userName) >= 0
new ProxiedApp(uid, name, proxied) new ProxiedApp(uid, name, packageName, proxied)
}.toArray }.toArray
} }
...@@ -175,7 +177,7 @@ class AppManager extends Activity with OnCheckedChangeListener with OnClickListe ...@@ -175,7 +177,7 @@ class AppManager extends Activity with OnCheckedChangeListener with OnClickListe
.cacheOnDisc() .cacheOnDisc()
.displayer(new FadeInBitmapDisplayer(300)) .displayer(new FadeInBitmapDisplayer(300))
.build() .build()
ImageLoader.getInstance().displayImage(Scheme.APP + app.uid, entry.icon, options) ImageLoader.getInstance().displayImage(Scheme.APP + app.packageName, entry.icon, options)
entry.text.setText(app.name) entry.text.setText(app.name)
val box: CheckBox = entry.box val box: CheckBox = entry.box
...@@ -319,8 +321,8 @@ class AppManager extends Activity with OnCheckedChangeListener with OnClickListe ...@@ -319,8 +321,8 @@ class AppManager extends Activity with OnCheckedChangeListener with OnClickListe
} }
override def getStreamFromOtherSource(imageUri: String, extra: AnyRef): InputStream = { override def getStreamFromOtherSource(imageUri: String, extra: AnyRef): InputStream = {
val uid = imageUri.substring(Scheme.APP.length).toInt val packageName = imageUri.substring(Scheme.APP.length)
val drawable = Utils.getAppIcon(getBaseContext, uid) val drawable = Utils.getAppIcon(getBaseContext, packageName)
val bitmap = Utils.drawableToBitmap(drawable) val bitmap = Utils.drawableToBitmap(drawable)
val os = new ByteArrayOutputStream() val os = new ByteArrayOutputStream()
......
...@@ -81,13 +81,17 @@ trait BaseService { ...@@ -81,13 +81,17 @@ trait BaseService {
} }
override def stop() { override def stop() {
if (state != State.CONNECTING && state != State.STOPPING) {
stopRunner() stopRunner()
} }
}
override def start(config: Config) { override def start(config: Config) {
if (state != State.CONNECTING && state != State.STOPPING) {
startRunner(config) startRunner(config)
} }
} }
}
def stopBackgroundService() def stopBackgroundService()
def startRunner(config: Config) def startRunner(config: Config)
......
...@@ -49,6 +49,7 @@ import android.net.{Network, ConnectivityManager} ...@@ -49,6 +49,7 @@ import android.net.{Network, ConnectivityManager}
import android.os._ import android.os._
import android.support.v4.app.NotificationCompat import android.support.v4.app.NotificationCompat
import android.util.Log import android.util.Log
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 com.google.android.gms.analytics.HitBuilders
...@@ -459,6 +460,7 @@ class ShadowsocksNatService extends Service with BaseService { ...@@ -459,6 +460,7 @@ class ShadowsocksNatService extends Service with BaseService {
filter.addAction(Action.CLOSE) filter.addAction(Action.CLOSE)
closeReceiver = new BroadcastReceiver() { closeReceiver = new BroadcastReceiver() {
def onReceive(p1: Context, p2: Intent) { def onReceive(p1: Context, p2: Intent) {
Toast.makeText(p1, R.string.stopping, Toast.LENGTH_SHORT)
stopRunner() stopRunner()
} }
} }
...@@ -521,6 +523,9 @@ class ShadowsocksNatService extends Service with BaseService { ...@@ -521,6 +523,9 @@ class ShadowsocksNatService extends Service with BaseService {
override def stopRunner() { override def stopRunner() {
// channge the state
changeState(State.STOPPING)
// clean up recevier // clean up recevier
if (closeReceiver != null) { if (closeReceiver != null) {
unregisterReceiver(closeReceiver) unregisterReceiver(closeReceiver)
......
...@@ -47,6 +47,7 @@ import android.content.pm.{PackageInfo, PackageManager} ...@@ -47,6 +47,7 @@ import android.content.pm.{PackageInfo, PackageManager}
import android.net.VpnService import android.net.VpnService
import android.os._ import android.os._
import android.util.Log import android.util.Log
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 com.google.android.gms.analytics.HitBuilders
...@@ -190,7 +191,7 @@ class ShadowsocksVpnService extends VpnService with BaseService { ...@@ -190,7 +191,7 @@ class ShadowsocksVpnService extends VpnService with BaseService {
val pkgSet: mutable.HashSet[String] = new mutable.HashSet[String] val pkgSet: mutable.HashSet[String] = new mutable.HashSet[String]
for (app <- apps) { for (app <- apps) {
if (app.proxied) { if (app.proxied) {
pkgSet.add(app.name) pkgSet.add(app.packageName)
} }
} }
for (pkg <- pkgSet) { for (pkg <- pkgSet) {
...@@ -396,6 +397,7 @@ class ShadowsocksVpnService extends VpnService with BaseService { ...@@ -396,6 +397,7 @@ class ShadowsocksVpnService extends VpnService with BaseService {
filter.addAction(Intent.ACTION_SHUTDOWN) filter.addAction(Intent.ACTION_SHUTDOWN)
receiver = new BroadcastReceiver { receiver = new BroadcastReceiver {
def onReceive(p1: Context, p2: Intent) { def onReceive(p1: Context, p2: Intent) {
Toast.makeText(p1, R.string.stopping, Toast.LENGTH_SHORT)
stopRunner() stopRunner()
} }
} }
...@@ -448,7 +450,7 @@ class ShadowsocksVpnService extends VpnService with BaseService { ...@@ -448,7 +450,7 @@ class ShadowsocksVpnService extends VpnService with BaseService {
override def stopRunner() { override def stopRunner() {
// channge the state // channge the state
changeState(State.STOPPED) changeState(State.STOPPING)
// send event // send event
application.tracker.send(new HitBuilders.EventBuilder() application.tracker.send(new HitBuilders.EventBuilder()
...@@ -476,6 +478,9 @@ class ShadowsocksVpnService extends VpnService with BaseService { ...@@ -476,6 +478,9 @@ class ShadowsocksVpnService extends VpnService with BaseService {
unregisterReceiver(receiver) unregisterReceiver(receiver)
receiver = null receiver = null
} }
// channge the state
changeState(State.STOPPED)
} }
override def stopBackgroundService() { override def stopBackgroundService() {
......
...@@ -101,7 +101,8 @@ object State { ...@@ -101,7 +101,8 @@ object State {
val INIT = 0 val INIT = 0
val CONNECTING = 1 val CONNECTING = 1
val CONNECTED = 2 val CONNECTED = 2
val STOPPED = 3 val STOPPING = 3
val STOPPED = 4
def isAvailable(state: Int): Boolean = state != CONNECTED && state != CONNECTING def isAvailable(state: Int): Boolean = state != CONNECTED && state != CONNECTING
} }
......
...@@ -332,6 +332,16 @@ object Utils { ...@@ -332,6 +332,16 @@ object Utils {
bitmap bitmap
} }
def getAppIcon(c: Context, packageName: String): Drawable = {
val pm: PackageManager = c.getPackageManager
val icon: Drawable = c.getResources.getDrawable(android.R.drawable.sym_def_app_icon)
try {
pm.getApplicationIcon(packageName)
} catch {
case e: PackageManager.NameNotFoundException => icon
}
}
def getAppIcon(c: Context, uid: Int): Drawable = { def getAppIcon(c: Context, uid: Int): Drawable = {
val pm: PackageManager = c.getPackageManager val pm: PackageManager = c.getPackageManager
val icon: Drawable = c.getResources.getDrawable(android.R.drawable.sym_def_app_icon) val icon: Drawable = c.getResources.getDrawable(android.R.drawable.sym_def_app_icon)
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment