You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
xiaomi_notes_reading/src/notes/ui/NotesPreferenceActivity.java

459 lines
18 KiB

This file contains ambiguous Unicode characters!

This file contains ambiguous Unicode characters that may be confused with others in your current locale. If your use case is intentional and legitimate, you can safely ignore this warning. Use the Escape button to highlight these characters.

/*
* Copyright (c) 2010-2011, The MiCode Open Source Community (www.micode.net)
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package net.micode.notes.ui;
import android.accounts.Account;
import android.accounts.AccountManager;
import android.app.ActionBar;
import android.app.AlertDialog;
import android.content.BroadcastReceiver;
import android.content.ContentValues;
import android.content.Context;
import android.content.DialogInterface;
import android.content.Intent;
import android.content.IntentFilter;
import android.content.SharedPreferences;
import android.os.Bundle;
import android.preference.Preference;
import android.preference.Preference.OnPreferenceClickListener;
import android.preference.PreferenceActivity;
import android.preference.PreferenceCategory;
import android.text.TextUtils;
import android.text.format.DateFormat;
import android.view.LayoutInflater;
import android.view.Menu;
import android.view.MenuItem;
import android.view.View;
import android.widget.Button;
import android.widget.TextView;
import android.widget.Toast;
import net.micode.notes.R;
import net.micode.notes.data.Notes;
import net.micode.notes.data.Notes.NoteColumns;
import net.micode.notes.gtask.remote.GTaskSyncService;
/**
* 笔记应用的设置活动,用于管理同步账户和偏好设置
* 继承自PreferenceActivity提供Google任务同步功能配置
*/
public class NotesPreferenceActivity extends PreferenceActivity {
// 偏好设置文件名
public static final String PREFERENCE_NAME = "notes_preferences";
// 同步账户名称的键
public static final String PREFERENCE_SYNC_ACCOUNT_NAME = "pref_key_account_name";
// 最后同步时间的键
public static final String PREFERENCE_LAST_SYNC_TIME = "pref_last_sync_time";
// 背景颜色设置的键
public static final String PREFERENCE_SET_BG_COLOR_KEY = "pref_key_bg_random_appear";
// 同步账户分类的键
private static final String PREFERENCE_SYNC_ACCOUNT_KEY = "pref_sync_account_key";
// 账户权限过滤器键
private static final String AUTHORITIES_FILTER_KEY = "authorities";
private PreferenceCategory mAccountCategory; // 账户设置分类
private GTaskReceiver mReceiver; // 同步服务广播接收器
private Account[] mOriAccounts; // 原始账户列表
private boolean mHasAddedAccount; // 标记是否添加了新账户
/**
* Activity创建时的初始化方法
*/
@Override
protected void onCreate(Bundle icicle) {
super.onCreate(icicle);
// 在ActionBar中显示返回按钮
getActionBar().setDisplayHomeAsUpEnabled(true);
// 从XML资源加载偏好设置
addPreferencesFromResource(R.xml.preferences);
// 查找账户设置分类
mAccountCategory = (PreferenceCategory) findPreference(PREFERENCE_SYNC_ACCOUNT_KEY);
// 创建广播接收器监听同步状态变化
mReceiver = new GTaskReceiver();
IntentFilter filter = new IntentFilter();
filter.addAction(GTaskSyncService.GTASK_SERVICE_BROADCAST_NAME);
registerReceiver(mReceiver, filter);
mOriAccounts = null;
// 加载设置页面的自定义头部布局
View header = LayoutInflater.from(this).inflate(R.layout.settings_header, null);
getListView().addHeaderView(header, null, true);
}
/**
* Activity恢复时调用处理账户变化
*/
@Override
protected void onResume() {
super.onResume();
// 如果用户添加了新账户,自动设置同步账户
if (mHasAddedAccount) {
Account[] accounts = getGoogleAccounts();
// 比较新旧账户列表,找到新添加的账户
if (mOriAccounts != null && accounts.length > mOriAccounts.length) {
for (Account accountNew : accounts) {
boolean found = false;
for (Account accountOld : mOriAccounts) {
if (TextUtils.equals(accountOld.name, accountNew.name)) {
found = true;
break;
}
}
if (!found) {
// 设置新账户为同步账户
setSyncAccount(accountNew.name);
break;
}
}
}
}
// 刷新界面显示
refreshUI();
}
/**
* Activity销毁时清理资源
*/
@Override
protected void onDestroy() {
if (mReceiver != null) {
unregisterReceiver(mReceiver);
}
super.onDestroy();
}
/**
* 加载账户设置项
*/
private void loadAccountPreference() {
mAccountCategory.removeAll(); // 清空现有设置项
Preference accountPref = new Preference(this);
final String defaultAccount = getSyncAccountName(this);
accountPref.setTitle(getString(R.string.preferences_account_title));
accountPref.setSummary(getString(R.string.preferences_account_summary));
accountPref.setOnPreferenceClickListener(new OnPreferenceClickListener() {
public boolean onPreferenceClick(Preference preference) {
// 检查是否正在同步,同步过程中不允许修改账户
if (!GTaskSyncService.isSyncing()) {
if (TextUtils.isEmpty(defaultAccount)) {
// 首次设置账户,显示选择账户对话框
showSelectAccountAlertDialog();
} else {
// 已设置过账户,显示确认对话框
showChangeAccountConfirmAlertDialog();
}
} else {
Toast.makeText(NotesPreferenceActivity.this,
R.string.preferences_toast_cannot_change_account, Toast.LENGTH_SHORT)
.show();
}
return true;
}
});
mAccountCategory.addPreference(accountPref);
}
/**
* 加载同步按钮状态
*/
private void loadSyncButton() {
Button syncButton = (Button) findViewById(R.id.preference_sync_button);
TextView lastSyncTimeView = (TextView) findViewById(R.id.prefenerece_sync_status_textview);
// 根据同步状态设置按钮文本和点击事件
if (GTaskSyncService.isSyncing()) {
syncButton.setText(getString(R.string.preferences_button_sync_cancel));
syncButton.setOnClickListener(new View.OnClickListener() {
public void onClick(View v) {
GTaskSyncService.cancelSync(NotesPreferenceActivity.this);
}
});
} else {
syncButton.setText(getString(R.string.preferences_button_sync_immediately));
syncButton.setOnClickListener(new View.OnClickListener() {
public void onClick(View v) {
GTaskSyncService.startSync(NotesPreferenceActivity.this);
}
});
}
// 只有设置了同步账户才能启用同步按钮
syncButton.setEnabled(!TextUtils.isEmpty(getSyncAccountName(this)));
// 设置最后同步时间显示
if (GTaskSyncService.isSyncing()) {
// 显示同步进度
lastSyncTimeView.setText(GTaskSyncService.getProgressString());
lastSyncTimeView.setVisibility(View.VISIBLE);
} else {
long lastSyncTime = getLastSyncTime(this);
if (lastSyncTime != 0) {
// 格式化显示最后同步时间
lastSyncTimeView.setText(getString(R.string.preferences_last_sync_time,
DateFormat.format(getString(R.string.preferences_last_sync_time_format),
lastSyncTime)));
lastSyncTimeView.setVisibility(View.VISIBLE);
} else {
// 从未同步过,隐藏时间显示
lastSyncTimeView.setVisibility(View.GONE);
}
}
}
/**
* 刷新整个界面
*/
private void refreshUI() {
loadAccountPreference();
loadSyncButton();
}
/**
* 显示选择账户对话框
*/
private void showSelectAccountAlertDialog() {
AlertDialog.Builder dialogBuilder = new AlertDialog.Builder(this);
// 设置自定义标题布局
View titleView = LayoutInflater.from(this).inflate(R.layout.account_dialog_title, null);
TextView titleTextView = (TextView) titleView.findViewById(R.id.account_dialog_title);
titleTextView.setText(getString(R.string.preferences_dialog_select_account_title));
TextView subtitleTextView = (TextView) titleView.findViewById(R.id.account_dialog_subtitle);
subtitleTextView.setText(getString(R.string.preferences_dialog_select_account_tips));
dialogBuilder.setCustomTitle(titleView);
dialogBuilder.setPositiveButton(null, null); // 不显示确定按钮
Account[] accounts = getGoogleAccounts();
String defAccount = getSyncAccountName(this);
mOriAccounts = accounts; // 保存当前账户列表
mHasAddedAccount = false; // 重置添加账户标记
if (accounts.length > 0) {
// 创建账户选择列表
CharSequence[] items = new CharSequence[accounts.length];
final CharSequence[] itemMapping = items;
int checkedItem = -1;
int index = 0;
for (Account account : accounts) {
if (TextUtils.equals(account.name, defAccount)) {
checkedItem = index; // 标记当前选中的账户
}
items[index++] = account.name;
}
dialogBuilder.setSingleChoiceItems(items, checkedItem,
new DialogInterface.OnClickListener() {
public void onClick(DialogInterface dialog, int which) {
// 用户选择账户后设置同步账户
setSyncAccount(itemMapping[which].toString());
dialog.dismiss();
refreshUI(); // 刷新界面
}
});
}
// 添加"添加账户"选项
View addAccountView = LayoutInflater.from(this).inflate(R.layout.add_account_text, null);
dialogBuilder.setView(addAccountView);
final AlertDialog dialog = dialogBuilder.show();
addAccountView.setOnClickListener(new View.OnClickListener() {
public void onClick(View v) {
mHasAddedAccount = true; // 标记正在添加账户
// 启动系统添加账户界面
Intent intent = new Intent("android.settings.ADD_ACCOUNT_SETTINGS");
intent.putExtra(AUTHORITIES_FILTER_KEY, new String[] {
"gmail-ls" // 限制只显示Gmail账户
});
startActivityForResult(intent, -1);
dialog.dismiss();
}
});
}
/**
* 显示更改账户确认对话框
*/
private void showChangeAccountConfirmAlertDialog() {
AlertDialog.Builder dialogBuilder = new AlertDialog.Builder(this);
View titleView = LayoutInflater.from(this).inflate(R.layout.account_dialog_title, null);
TextView titleTextView = (TextView) titleView.findViewById(R.id.account_dialog_title);
titleTextView.setText(getString(R.string.preferences_dialog_change_account_title,
getSyncAccountName(this))); // 显示当前账户名
TextView subtitleTextView = (TextView) titleView.findViewById(R.id.account_dialog_subtitle);
subtitleTextView.setText(getString(R.string.preferences_dialog_change_account_warn_msg));
dialogBuilder.setCustomTitle(titleView);
// 提供三个操作选项:更改账户、移除账户、取消
CharSequence[] menuItemArray = new CharSequence[] {
getString(R.string.preferences_menu_change_account),
getString(R.string.preferences_menu_remove_account),
getString(R.string.preferences_menu_cancel)
};
dialogBuilder.setItems(menuItemArray, new DialogInterface.OnClickListener() {
public void onClick(DialogInterface dialog, int which) {
if (which == 0) {
// 更改账户
showSelectAccountAlertDialog();
} else if (which == 1) {
// 移除账户
removeSyncAccount();
refreshUI();
}
// which == 2 取消操作,不做任何事
}
});
dialogBuilder.show();
}
/**
* 获取设备上的Google账户列表
*/
private Account[] getGoogleAccounts() {
AccountManager accountManager = AccountManager.get(this);
return accountManager.getAccountsByType("com.google"); // Google账户类型
}
/**
* 设置同步账户
*/
private void setSyncAccount(String account) {
// 只有当账户发生变化时才更新
if (!getSyncAccountName(this).equals(account)) {
SharedPreferences settings = getSharedPreferences(PREFERENCE_NAME, Context.MODE_PRIVATE);
SharedPreferences.Editor editor = settings.edit();
if (account != null) {
editor.putString(PREFERENCE_SYNC_ACCOUNT_NAME, account);
} else {
editor.putString(PREFERENCE_SYNC_ACCOUNT_NAME, "");
}
editor.commit();
// 重置最后同步时间
setLastSyncTime(this, 0);
// 在新线程中清理本地同步信息
new Thread(new Runnable() {
public void run() {
ContentValues values = new ContentValues();
values.put(NoteColumns.GTASK_ID, ""); // 清空任务ID
values.put(NoteColumns.SYNC_ID, 0); // 重置同步ID
getContentResolver().update(Notes.CONTENT_NOTE_URI, values, null, null);
}
}).start();
Toast.makeText(NotesPreferenceActivity.this,
getString(R.string.preferences_toast_success_set_accout, account),
Toast.LENGTH_SHORT).show();
}
}
/**
* 移除同步账户
*/
private void removeSyncAccount() {
SharedPreferences settings = getSharedPreferences(PREFERENCE_NAME, Context.MODE_PRIVATE);
SharedPreferences.Editor editor = settings.edit();
// 移除账户相关设置
if (settings.contains(PREFERENCE_SYNC_ACCOUNT_NAME)) {
editor.remove(PREFERENCE_SYNC_ACCOUNT_NAME);
}
if (settings.contains(PREFERENCE_LAST_SYNC_TIME)) {
editor.remove(PREFERENCE_LAST_SYNC_TIME);
}
editor.commit();
// 在新线程中清理本地同步信息
new Thread(new Runnable() {
public void run() {
ContentValues values = new ContentValues();
values.put(NoteColumns.GTASK_ID, "");
values.put(NoteColumns.SYNC_ID, 0);
getContentResolver().update(Notes.CONTENT_NOTE_URI, values, null, null);
}
}).start();
}
/**
* 静态方法:获取当前同步账户名称
*/
public static String getSyncAccountName(Context context) {
SharedPreferences settings = context.getSharedPreferences(PREFERENCE_NAME,
Context.MODE_PRIVATE);
return settings.getString(PREFERENCE_SYNC_ACCOUNT_NAME, "");
}
/**
* 静态方法:设置最后同步时间
*/
public static void setLastSyncTime(Context context, long time) {
SharedPreferences settings = context.getSharedPreferences(PREFERENCE_NAME,
Context.MODE_PRIVATE);
SharedPreferences.Editor editor = settings.edit();
editor.putLong(PREFERENCE_LAST_SYNC_TIME, time);
editor.commit();
}
/**
* 静态方法:获取最后同步时间
*/
public static long getLastSyncTime(Context context) {
SharedPreferences settings = context.getSharedPreferences(PREFERENCE_NAME,
Context.MODE_PRIVATE);
return settings.getLong(PREFERENCE_LAST_SYNC_TIME, 0);
}
/**
* 同步服务广播接收器,用于监听同步状态变化
*/
private class GTaskReceiver extends BroadcastReceiver {
@Override
public void onReceive(Context context, Intent intent) {
refreshUI(); // 收到广播后刷新界面
if (intent.getBooleanExtra(GTaskSyncService.GTASK_SERVICE_BROADCAST_IS_SYNCING, false)) {
// 更新同步进度显示
TextView syncStatus = (TextView) findViewById(R.id.prefenerece_sync_status_textview);
syncStatus.setText(intent
.getStringExtra(GTaskSyncService.GTASK_SERVICE_BROADCAST_PROGRESS_MSG));
}
}
}
/**
* 选项菜单项选择处理
*/
public boolean onOptionsItemSelected(MenuItem item) {
switch (item.getItemId()) {
case android.R.id.home:
// 点击返回按钮,返回到笔记列表
Intent intent = new Intent(this, NotesListActivity.class);
intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
startActivity(intent);
return true;
default:
return false;
}
}
}