Commit bae8cc2d authored by Max Lv's avatar Max Lv

fix an UI issue on 4.4

parent 75d9e577
...@@ -5,8 +5,8 @@ import sbtandroid._ ...@@ -5,8 +5,8 @@ import sbtandroid._
import sbtandroid.AndroidPlugin._ import sbtandroid.AndroidPlugin._
object App { object App {
val version = "2.0.5" val version = "2.0.6"
val versionCode = 56 val versionCode = 57
} }
object General { object General {
......
...@@ -65,20 +65,10 @@ import net.simonvt.menudrawer.MenuDrawer ...@@ -65,20 +65,10 @@ import net.simonvt.menudrawer.MenuDrawer
import com.github.shadowsocks.database._ import com.github.shadowsocks.database._
import scala.collection.mutable.ListBuffer import scala.collection.mutable.ListBuffer
import com.github.shadowsocks.database.Profile import com.github.shadowsocks.database.Profile
import com.nostra13.universalimageloader.core.{ImageLoader, ImageLoaderConfiguration}
import com.nostra13.universalimageloader.core.download.BaseImageDownloader import com.nostra13.universalimageloader.core.download.BaseImageDownloader
import com.github.shadowsocks.database.Item
import com.github.shadowsocks.database.Category
import com.actionbarsherlock.view.MenuItem
import com.github.shadowsocks.preferences.{ProfileEditTextPreference, PasswordEditTextPreference, SummaryEditTextPreference} import com.github.shadowsocks.preferences.{ProfileEditTextPreference, PasswordEditTextPreference, SummaryEditTextPreference}
import com.github.shadowsocks.database.Item import com.github.shadowsocks.database.Item
import com.github.shadowsocks.database.Category import com.github.shadowsocks.database.Category
import scala.Option
import android.view.ViewGroup.LayoutParams
import com.github.shadowsocks.database.Item
import com.github.shadowsocks.database.Category
import com.google.tagmanager.{Container, ContainerOpener, TagManager}
import com.google.tagmanager.ContainerOpener.{Notifier, OpenType}
class ProfileIconDownloader(context: Context, connectTimeout: Int, readTimeout: Int) class ProfileIconDownloader(context: Context, connectTimeout: Int, readTimeout: Int)
extends BaseImageDownloader(context, connectTimeout, readTimeout) { extends BaseImageDownloader(context, connectTimeout, readTimeout) {
...@@ -119,22 +109,25 @@ object Typefaces { ...@@ -119,22 +109,25 @@ object Typefaces {
} }
} }
private final val TAG: String = "Typefaces" private final val TAG = "Typefaces"
private final val cache: Hashtable[String, Typeface] = new Hashtable[String, Typeface] private final val cache = new Hashtable[String, Typeface]
} }
object Shadowsocks { object Shadowsocks {
// Constants
val PREFS_NAME = "Shadowsocks" val PREFS_NAME = "Shadowsocks"
val PROXY_PREFS = Array(Key.profileName, Key.proxy, Key.remotePort, Key.localPort, Key.sitekey, Key.encMethod) val PROXY_PREFS = Array(Key.profileName, Key.proxy, Key.remotePort, Key.localPort, Key.sitekey,
Key.encMethod)
val FEATRUE_PREFS = Array(Key.isGFWList, Key.isGlobalProxy, Key.proxyedApps, Key.isTrafficStat, val FEATRUE_PREFS = Array(Key.isGFWList, Key.isGlobalProxy, Key.proxyedApps, Key.isTrafficStat,
Key.isAutoConnect) Key.isAutoConnect)
val TAG = "Shadowsocks" val TAG = "Shadowsocks"
val REQUEST_CONNECT = 1 val REQUEST_CONNECT = 1
private var vpnEnabled = -1 // Flags
var vpnEnabled = -1
var currentProfile: Profile = null // Help functions
def updateListPreference(pref: Preference, value: String) { def updateListPreference(pref: Preference, value: String) {
pref.setSummary(value) pref.setSummary(value)
...@@ -156,7 +149,6 @@ object Shadowsocks { ...@@ -156,7 +149,6 @@ object Shadowsocks {
pref.asInstanceOf[ProfileEditTextPreference].setText(value) pref.asInstanceOf[ProfileEditTextPreference].setText(value)
} }
def updateCheckBoxPreference(pref: Preference, value: Boolean) { def updateCheckBoxPreference(pref: Preference, value: Boolean) {
pref.asInstanceOf[CheckBoxPreference].setChecked(value) pref.asInstanceOf[CheckBoxPreference].setChecked(value)
} }
...@@ -198,7 +190,8 @@ object Shadowsocks { ...@@ -198,7 +190,8 @@ object Shadowsocks {
private def updatePreferenceScreen() { private def updatePreferenceScreen() {
for (name <- Shadowsocks.PROXY_PREFS) { for (name <- Shadowsocks.PROXY_PREFS) {
val pref = findPreference(name) val pref = findPreference(name)
Shadowsocks.updatePreference(pref, name, Shadowsocks.currentProfile) Shadowsocks.updatePreference(pref, name,
getActivity.asInstanceOf[Shadowsocks].currentProfile)
} }
} }
...@@ -255,7 +248,8 @@ object Shadowsocks { ...@@ -255,7 +248,8 @@ object Shadowsocks {
private def updatePreferenceScreen() { private def updatePreferenceScreen() {
for (name <- Shadowsocks.FEATRUE_PREFS) { for (name <- Shadowsocks.FEATRUE_PREFS) {
val pref = findPreference(name) val pref = findPreference(name)
Shadowsocks.updatePreference(pref, name, Shadowsocks.currentProfile) Shadowsocks.updatePreference(pref, name,
getActivity.asInstanceOf[Shadowsocks].currentProfile)
} }
} }
...@@ -292,19 +286,20 @@ object Shadowsocks { ...@@ -292,19 +286,20 @@ object Shadowsocks {
class Shadowsocks class Shadowsocks
extends UnifiedSherlockPreferenceActivity extends UnifiedSherlockPreferenceActivity
with CompoundButton.OnCheckedChangeListener with CompoundButton.OnCheckedChangeListener
with MenuAdapter.MenuListener{ with MenuAdapter.MenuListener {
private val MSG_CRASH_RECOVER: Int = 1
private val MSG_INITIAL_FINISH: Int = 2
private val STATE_MENUDRAWER = "com.github.shadowsocks.menuDrawer" // Flags
private val STATE_ACTIVE_VIEW_ID = "com.github.shadowsocks.activeViewId" val MSG_CRASH_RECOVER: Int = 1
val MSG_INITIAL_FINISH: Int = 2
val STATE_MENUDRAWER = "com.github.shadowsocks.menuDrawer"
val STATE_ACTIVE_VIEW_ID = "com.github.shadowsocks.activeViewId"
private var switchButton: Switch = null // Variables
private var progressDialog: ProgressDialog = null var switchButton: Switch = null
var progressDialog: ProgressDialog = null
private var state = State.INIT var state = State.INIT
private var prepared = false var prepared = false
var currentProfile = new Profile
lazy val settings = PreferenceManager.getDefaultSharedPreferences(this) lazy val settings = PreferenceManager.getDefaultSharedPreferences(this)
lazy val status = getSharedPreferences(Key.status, Context.MODE_PRIVATE) lazy val status = getSharedPreferences(Key.status, Context.MODE_PRIVATE)
...@@ -313,7 +308,8 @@ class Shadowsocks ...@@ -313,7 +308,8 @@ class Shadowsocks
lazy val drawer = MenuDrawer.attach(this) lazy val drawer = MenuDrawer.attach(this)
lazy val menuAdapter = new MenuAdapter(this, getMenuList) lazy val menuAdapter = new MenuAdapter(this, getMenuList)
lazy val listView = new ListView(this) lazy val listView = new ListView(this)
lazy val profileManager = new ProfileManager(settings, getApplication.asInstanceOf[ShadowsocksApplication].dbHelper) lazy val profileManager =
new ProfileManager(settings, getApplication.asInstanceOf[ShadowsocksApplication].dbHelper)
private val handler: Handler = new Handler { private val handler: Handler = new Handler {
override def handleMessage(msg: Message) { override def handleMessage(msg: Message) {
...@@ -495,13 +491,17 @@ class Shadowsocks ...@@ -495,13 +491,17 @@ class Shadowsocks
/** Called when the activity is first created. */ /** Called when the activity is first created. */
override def onCreate(savedInstanceState: Bundle) { override def onCreate(savedInstanceState: Bundle) {
// Initialize preference
setHeaderRes(R.xml.shadowsocks_headers) setHeaderRes(R.xml.shadowsocks_headers)
super.onCreate(savedInstanceState) super.onCreate(savedInstanceState)
Shadowsocks.currentProfile = { // Initialize profile
profileManager.getProfile(settings.getInt(Key.profileId, -1)) getOrElse new Profile() currentProfile = {
profileManager.getProfile(settings.getInt(Key.profileId, -1)) getOrElse currentProfile
} }
// Initialize drawer
menuAdapter.setActiveId(settings.getInt(Key.profileId, -1)) menuAdapter.setActiveId(settings.getInt(Key.profileId, -1))
menuAdapter.setListener(this) menuAdapter.setListener(this)
listView.setAdapter(menuAdapter) listView.setAdapter(menuAdapter)
...@@ -511,35 +511,36 @@ class Shadowsocks ...@@ -511,35 +511,36 @@ class Shadowsocks
// Whether the previous drawable should be shown // Whether the previous drawable should be shown
drawer.setDrawerIndicatorEnabled(true) drawer.setDrawerIndicatorEnabled(true)
// Initialize action bar
val switchLayout = getLayoutInflater val switchLayout = getLayoutInflater
.inflate(R.layout.layout_switch, null) .inflate(R.layout.layout_switch, null)
.asInstanceOf[RelativeLayout] .asInstanceOf[RelativeLayout]
getSupportActionBar.setCustomView(switchLayout)
getSupportActionBar.setDisplayShowTitleEnabled(false)
getSupportActionBar.setDisplayShowCustomEnabled(true)
getSupportActionBar.setIcon(R.drawable.ic_stat_shadowsocks)
val title: TextView = switchLayout.findViewById(R.id.title).asInstanceOf[TextView] val title: TextView = switchLayout.findViewById(R.id.title).asInstanceOf[TextView]
val tf: Typeface = Typefaces.get(this, "fonts/Iceland.ttf") val tf: Typeface = Typefaces.get(this, "fonts/Iceland.ttf")
if (tf != null) title.setTypeface(tf) if (tf != null) title.setTypeface(tf)
switchButton = switchLayout.findViewById(R.id.switchButton).asInstanceOf[Switch] switchButton = switchLayout.findViewById(R.id.switchButton).asInstanceOf[Switch]
getSupportActionBar.setCustomView(switchLayout)
getSupportActionBar.setDisplayShowTitleEnabled(false)
getSupportActionBar.setDisplayShowCustomEnabled(true)
getSupportActionBar.setIcon(R.drawable.ic_stat_shadowsocks)
// Register broadcast receiver
registerReceiver(stateReceiver, new IntentFilter(Action.UPDATE_STATE)) registerReceiver(stateReceiver, new IntentFilter(Action.UPDATE_STATE))
registerReceiver(preferenceReceiver, new IntentFilter(Action.UPDATE_PREFS)) registerReceiver(preferenceReceiver, new IntentFilter(Action.UPDATE_PREFS))
val init: Boolean = !Shadowsocks.isServiceStarted(this) // Update status
if (init) { if (!Shadowsocks.isServiceStarted(this)) {
if (progressDialog == null) {
progressDialog = ProgressDialog.show(this, "", getString(R.string.initializing), true, true)
}
spawn { spawn {
status.edit().putBoolean(Key.isRoot, Utils.getRoot).commit() status.edit.putBoolean(Key.isRoot, Utils.getRoot).apply()
if (!status.getBoolean(getVersionName, false)) { }
status.edit.putBoolean(getVersionName, true).apply() if (!status.getBoolean(getVersionName, false)) {
val h = showProgress(getString(R.string.initializing))
status.edit.putBoolean(getVersionName, true).apply()
spawn {
reset() reset()
Shadowsocks.currentProfile = profileManager.create() currentProfile = profileManager.create()
h.sendEmptyMessage(0)
} }
handler.sendEmptyMessage(MSG_INITIAL_FINISH)
} }
} }
} }
...@@ -552,7 +553,7 @@ class Shadowsocks ...@@ -552,7 +553,7 @@ class Shadowsocks
override def onSaveInstanceState(outState: Bundle) { override def onSaveInstanceState(outState: Bundle) {
super.onSaveInstanceState(outState) super.onSaveInstanceState(outState)
outState.putParcelable(STATE_MENUDRAWER, drawer.saveState()) outState.putParcelable(STATE_MENUDRAWER, drawer.saveState())
outState.putInt(STATE_ACTIVE_VIEW_ID, Shadowsocks.currentProfile.id) outState.putInt(STATE_ACTIVE_VIEW_ID, currentProfile.id)
} }
override def onBackPressed() { override def onBackPressed() {
...@@ -575,9 +576,9 @@ class Shadowsocks ...@@ -575,9 +576,9 @@ class Shadowsocks
handler.postDelayed(new Runnable { handler.postDelayed(new Runnable {
def run() { def run() {
Shadowsocks.currentProfile = profileManager.reload(id) currentProfile = profileManager.reload(id)
profileManager.save() profileManager.save()
menuAdapter.updateList(getMenuList, Shadowsocks.currentProfile.id) menuAdapter.updateList(getMenuList, currentProfile.id)
if (!isSinglePane) { if (!isSinglePane) {
sendBroadcast(new Intent(Action.UPDATE_FRAGMENT)) sendBroadcast(new Intent(Action.UPDATE_FRAGMENT))
...@@ -586,10 +587,8 @@ class Shadowsocks ...@@ -586,10 +587,8 @@ class Shadowsocks
} }
h.sendEmptyMessage(0) h.sendEmptyMessage(0)
} }
}, 600) }, 600)
} }
def updateProfile(id: Int) { def updateProfile(id: Int) {
...@@ -599,7 +598,7 @@ class Shadowsocks ...@@ -599,7 +598,7 @@ class Shadowsocks
handler.postDelayed(new Runnable { handler.postDelayed(new Runnable {
def run() { def run() {
Shadowsocks.currentProfile = profileManager.reload(id) currentProfile = profileManager.reload(id)
menuAdapter.setActiveId(id) menuAdapter.setActiveId(id)
menuAdapter.notifyDataSetChanged() menuAdapter.notifyDataSetChanged()
...@@ -612,7 +611,6 @@ class Shadowsocks ...@@ -612,7 +611,6 @@ class Shadowsocks
h.sendEmptyMessage(0) h.sendEmptyMessage(0)
} }
}, 600) }, 600)
} }
def delProfile(id: Int): Boolean = { def delProfile(id: Int): Boolean = {
...@@ -626,27 +624,29 @@ class Shadowsocks ...@@ -626,27 +624,29 @@ class Shadowsocks
.setMessage(String.format(getString(R.string.remove_profile), profile.get.name)) .setMessage(String.format(getString(R.string.remove_profile), profile.get.name))
.setCancelable(false) .setCancelable(false)
.setNegativeButton(R.string.no, new DialogInterface.OnClickListener() { .setNegativeButton(R.string.no, new DialogInterface.OnClickListener() {
override def onClick(dialog: DialogInterface, i: Int) = dialog.cancel() override def onClick(dialog: DialogInterface, i: Int) = dialog.cancel()
}) })
.setPositiveButton(R.string.yes, new DialogInterface.OnClickListener() { .setPositiveButton(R.string.yes, new DialogInterface.OnClickListener() {
override def onClick(dialog: DialogInterface, i: Int) { override def onClick(dialog: DialogInterface, i: Int) {
profileManager.delProfile(id) profileManager.delProfile(id)
val profileId = { val profileId = {
val profiles = profileManager.getAllProfiles.getOrElse(List[Profile]()) val profiles = profileManager.getAllProfiles.getOrElse(List[Profile]())
if (profiles.isEmpty) -1 else profiles(0).id if (profiles.isEmpty) -1 else profiles(0).id
} }
Shadowsocks.currentProfile = profileManager.load(profileId) currentProfile = profileManager.load(profileId)
menuAdapter.updateList(getMenuList, Shadowsocks.currentProfile.id) menuAdapter.updateList(getMenuList, currentProfile.id)
if (!isSinglePane) {
sendBroadcast(new Intent(Action.UPDATE_FRAGMENT))
} else {
updatePreferenceScreen()
}
dialog.dismiss() if (!isSinglePane) {
sendBroadcast(new Intent(Action.UPDATE_FRAGMENT))
} else {
updatePreferenceScreen()
} }
}).create().show()
dialog.dismiss()
}
})
.create()
.show()
true true
} }
...@@ -664,37 +664,40 @@ class Shadowsocks ...@@ -664,37 +664,40 @@ class Shadowsocks
buf ++= getProfileList buf ++= getProfileList
buf += new Item(-400, getString(R.string.add_profile), android.R.drawable.ic_menu_add, addProfile) buf +=
new Item(-400, getString(R.string.add_profile), android.R.drawable.ic_menu_add, addProfile)
buf += new Category(getString(R.string.settings)) buf += new Category(getString(R.string.settings))
buf += new Item(-100, getString(R.string.recovery), android.R.drawable.ic_menu_revert, _ => { buf += new Item(-100, getString(R.string.recovery), android.R.drawable.ic_menu_revert, _ => {
EasyTracker.getInstance(this).send( EasyTracker
MapBuilder.createEvent(Shadowsocks.TAG, "reset", getVersionName, null).build()) .getInstance(this)
.send(MapBuilder.createEvent(Shadowsocks.TAG, "reset", getVersionName, null).build())
recovery() recovery()
}) })
buf += buf +=
new Item(-200, getString(R.string.flush_dnscache), android.R.drawable.ic_menu_delete, _ => { new Item(-200, getString(R.string.flush_dnscache), android.R.drawable.ic_menu_delete, _ => {
EasyTracker.getInstance(this).send( EasyTracker
.getInstance(this)
.send(
MapBuilder.createEvent(Shadowsocks.TAG, "flush_dnscache", getVersionName, null).build()) MapBuilder.createEvent(Shadowsocks.TAG, "flush_dnscache", getVersionName, null).build())
flushDnsCache() flushDnsCache()
}) })
buf += new Item(-300, getString(R.string.about), android.R.drawable.ic_menu_info_details, _ => { buf += new Item(-300, getString(R.string.about), android.R.drawable.ic_menu_info_details, _ => {
EasyTracker.getInstance(this).send( EasyTracker
MapBuilder.createEvent(Shadowsocks.TAG, "about", getVersionName, null).build()) .getInstance(this)
.send(MapBuilder.createEvent(Shadowsocks.TAG, "about", getVersionName, null).build())
showAbout() showAbout()
}) })
buf.toList buf.toList
} }
override def onOptionsItemSelected(item: MenuItem): Boolean = { override def onOptionsItemSelected(item: com.actionbarsherlock.view.MenuItem): Boolean = {
item.getItemId match { item.getItemId match {
case android.R.id.home => { case android.R.id.home => {
EasyTracker.getInstance(this).send(
MapBuilder.createEvent(Shadowsocks.TAG, "home", getVersionName, null).build())
drawer.toggleMenu() drawer.toggleMenu()
return true return true
} }
...@@ -713,14 +716,11 @@ class Shadowsocks ...@@ -713,14 +716,11 @@ class Shadowsocks
if (Shadowsocks.isServiceStarted(this)) { if (Shadowsocks.isServiceStarted(this)) {
switchButton.setChecked(true) switchButton.setChecked(true)
if (ShadowVpnService.isServiceStarted(this)) { if (ShadowVpnService.isServiceStarted(this)) {
val style = new Style.Builder() val style = new Style.Builder().setBackgroundColorValue(Style.holoBlueLight).build()
.setBackgroundColorValue(Style.holoBlueLight) val config = new Configuration.Builder().setDuration(Configuration.DURATION_LONG).build()
.build()
val config = new Configuration.Builder()
.setDuration(Configuration.DURATION_LONG)
.build()
switchButton.setEnabled(false) switchButton.setEnabled(false)
Crouton.makeText(Shadowsocks.this, R.string.vpn_status, style) Crouton
.makeText(Shadowsocks.this, R.string.vpn_status, style)
.setConfiguration(config) .setConfiguration(config)
.show() .show()
} }
...@@ -744,7 +744,6 @@ class Shadowsocks ...@@ -744,7 +744,6 @@ class Shadowsocks
switchButton.setOnCheckedChangeListener(this) switchButton.setOnCheckedChangeListener(this)
Config.refresh(this) Config.refresh(this)
} }
private def setPreferenceEnabled(enabled: Boolean) { private def setPreferenceEnabled(enabled: Boolean) {
...@@ -769,7 +768,7 @@ class Shadowsocks ...@@ -769,7 +768,7 @@ class Shadowsocks
} }
private def updatePreferenceScreen() { private def updatePreferenceScreen() {
val profile = Shadowsocks.currentProfile val profile = currentProfile
for (name <- Shadowsocks.PROXY_PREFS) { for (name <- Shadowsocks.PROXY_PREFS) {
val pref = findPreference(name) val pref = findPreference(name)
Shadowsocks.updatePreference(pref, name, profile) Shadowsocks.updatePreference(pref, name, profile)
...@@ -883,15 +882,9 @@ class Shadowsocks ...@@ -883,15 +882,9 @@ class Shadowsocks
val intent: Intent = new Intent(this, classOf[ShadowVpnService]) val intent: Intent = new Intent(this, classOf[ShadowVpnService])
Extra.put(settings, intent) Extra.put(settings, intent)
startService(intent) startService(intent)
val style = new Style.Builder() val style = new Style.Builder().setBackgroundColorValue(Style.holoBlueLight).build()
.setBackgroundColorValue(Style.holoBlueLight) val config = new Configuration.Builder().setDuration(Configuration.DURATION_LONG).build()
.build() Crouton.makeText(Shadowsocks.this, R.string.vpn_status, style).setConfiguration(config).show()
val config = new Configuration.Builder()
.setDuration(Configuration.DURATION_LONG)
.build()
Crouton.makeText(Shadowsocks.this, R.string.vpn_status, style)
.setConfiguration(config)
.show()
switchButton.setEnabled(false) switchButton.setEnabled(false)
} else { } else {
if (ShadowsocksService.isServiceStarted(this)) return false if (ShadowsocksService.isServiceStarted(this)) return false
...@@ -981,9 +974,7 @@ class Shadowsocks ...@@ -981,9 +974,7 @@ class Shadowsocks
} }
if (m != null) { if (m != null) {
Crouton.cancelAllCroutons() Crouton.cancelAllCroutons()
val style = new Style.Builder() val style = new Style.Builder().setBackgroundColorValue(Style.holoRedLight).build()
.setBackgroundColorValue(Style.holoRedLight)
.build()
val config = new Configuration.Builder() val config = new Configuration.Builder()
.setDuration(Configuration.DURATION_LONG) .setDuration(Configuration.DURATION_LONG)
.build() .build()
...@@ -1001,8 +992,8 @@ class Shadowsocks ...@@ -1001,8 +992,8 @@ class Shadowsocks
class PreferenceBroadcastReceiver extends BroadcastReceiver { class PreferenceBroadcastReceiver extends BroadcastReceiver {
override def onReceive(context: Context, intent: Intent) { override def onReceive(context: Context, intent: Intent) {
Shadowsocks.currentProfile = profileManager.save() currentProfile = profileManager.save()
menuAdapter.updateList(getMenuList, Shadowsocks.currentProfile.id) menuAdapter.updateList(getMenuList, currentProfile.id)
} }
} }
......
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