2015-12-17 83 views
0

我在我的應用程序中有兩個活動,一個是註冊,另一個是人創建帳戶後使用的活動。我想顯示註冊啓動器活動,直到人員註冊。我的代碼:臨時主要活動android

private static boolean doesDatabaseExist(ContextWrapper context, 
    String dbName) { 
    File dbFile = context.getDatabasePath(dbName); 
    return true; 


    @Override 
    protected void onCreate(Bundle savedInstanceState) { 
    super.onCreate(savedInstanceState); 
    if (doesDatabaseExist == true) { 
    setContentView (R.layout.activity_sign_up) ; } 
    else {setContentView (R.layout.activity_name1); }} 

這是正確的做法嗎?

回答

1

可能不是最好的方法,它會讓你的活動代碼非常混亂。

你有兩個選擇 1-使用片段 - 使用片段 - 而不是兩個活動,使用兩個片段。當你的啓動器活動加載時,你可以檢查你的數據庫是否存在,然後通過編程加載包含所有視圖代碼的正確片段。

FragmentManager fragmentManager = getFragmentManager(); 
FragmentTransaction fragmentTransaction = fragmentManager.beginTransaction(); 

if (doesDatabaseExist()){ 
      Name1Fragment fragment = new Name1Fragment(); 
     fragmentTransaction.add(R.id.fragment_container, fragment); 
     fragmentTransaction.commit(); 
    }else{ 
     SignUpFragment fragment = new SignUpFragment(); 
     fragmentTransaction.add(R.id.fragment_container, fragment); 
     fragmentTransaction.commit(); 

    } 

http://developer.android.com/guide/components/fragments.html

2 - 使用閃屏 - 如果你想保持獨立的活動,你的代碼,而不是將它們移動到片段,您可以設置您的主要啓動加載啓動畫面,並從那裏檢查您的數據庫是否存在,並從該值開始正確的活動。

if (doesDatabaseExist()){ 
     Intent intent = new Intent(this, Name1Activity.class); 
     startActivity(intent); 

    }else{ 
     Intent intent = new Intent(this, SignUpActivity.class); 
     startActivity(intent); 

    } 

http://developer.android.com/training/basics/firstapp/starting-activity.html

+0

它是簡單的樣品AccountLoginActivity。我覺得我好笨。我正在與第二個解決方案,因爲我有兩個活動。 –

+0

哈哈沒問題,很高興幫忙。請接受此爲正確答案:D –

+1

您可能還想查看我的答案,它更全面,因爲它可以指導您編寫更靈活/最佳實踐的應用程序等。儘管您當他們加載應用程序將他們引導到賬戶創建/登錄活動 – mawalker

0

在本質上,你有正確的想法......但這不是「正確」的實施。

'正確'的方法是使用一些事情,看起來你不是。內容提供者(這是'包裝'你的數據庫,並創建一個'簡單'(明確定義的)接口來與你的數據庫進行交互(好'簡單'...使用,寫它,可以是一種痛苦......直到你學會如何使它們變得容易,並且我的提示使它變得容易的是在開始之前製作一個Schema文件,其中包含基礎數據庫的所有結構+我們以前在某些情況下使用的ContentProvider Here is a sample Schema我們的Coursera Android Concurrency/Mobile/Web專業課程。))

2)Android的內置帳戶管理支持。

使用ContentProvider和以下組件的要點是多用途的...您正在遵循最佳實踐......您有明確的「分離問題」......您是「好鄰居」應用程序當用戶不希望應用程序同步時,允許用戶禁用應用程序進行同步......(同時保存電池/帶寬/內存(從應用程序不運行服務24/7進行同步)否則,實際上不得不編寫'sycning'機制或定時器或類似的東西......(你必須爲你的同步過程編寫自定義'邏輯'......這超出了這個問題的範圍......)

當您只使用內置的SyncAdaptor/Account機制時...您可以輕鬆檢查用戶是否擁有「帳戶」當他們打開「主要活動」,然後指示他們在繼續之前創建新帳戶/登錄到現有帳戶。 (下面的代碼實際上並不使用OAuth/Google/Facebook/StackOverflow /等基於Web的賬戶,但如果你沒有一個帶有認證設置的Web服務器......這可能是一個很好的早期測試直到你這樣做,仍然允許你使用賬戶機制/等。一旦你這樣做,你顯然必須改變他們使用正確的信息。)

(有很多原因說明爲什麼這種方法更好,我有點琢磨它們,以節省時間/空間......但我認爲你會得到它的一般'要點'。 )

2.1),擴展服務

2.2),擴展AccountAuthenticatorActivity

這裏有兩個 '樣本' 的文件,應該幫助你寫你自己的版本的活性的AccountAuthenticatorService。這段代碼已經有幾年了,但仍然應該與你所需要的「接近」。我在這段代碼中使用了一些「技巧」(比如:ApplicationConstants),我不會分享它們,因爲它們不是最佳實踐。但是這些文件的大綱應該會讓你有70%〜80%的路程。

如果您在編寫ContentProvider時需要幫助,我個人建議您購買/借用/獲取Professional Android 2 Application Development 2nd Edition的副本,價格約爲5.50美元。這是本教程針對Android 2.0教程編寫的舊版本,但自那時起,您嘗試做的核心部分並沒有改變,並且它大幅降低了新版本的價格。本書是我個人用來學習這些材料的內容,我認爲它是教你如何從頭開始創建一個數據庫和ContentProvider的最佳工作之一。如果你不想購買這本書,你可以隨時下載the Downloadable Code from this book。它有很多(在Chapter_7.txt中)內容提供者不同部分的例子。然而,它並沒有解釋每個人做什麼......所以它不會像兩者一樣有用。

package edu.vuum.mocca.authentication; 

import edu.vuum.mocca.main.ApplicationConstants; 
import android.accounts.AbstractAccountAuthenticator; 
import android.accounts.Account; 
import android.accounts.AccountAuthenticatorResponse; 
import android.accounts.AccountManager; 
import android.accounts.NetworkErrorException; 
import android.app.Service; 
import android.content.Context; 
import android.content.Intent; 
import android.os.Bundle; 
import android.os.IBinder; 
import android.util.Log; 

/** 
* Skeleton example for how a functional SyncAdaptor's 
* AccountAuthenticatorService would be implemented. 
* 
* @author Michael A. Walker 
* 
*/ 
public class AccountAuthenticatorService extends Service { 

    private static final String TAG = AccountAuthenticatorService.class 
      .getCanonicalName(); 
    private static AccountAuthenticatorImpl sAccountAuthenticator = null; 

    private static String ACCOUNT_NAME; 
    private static String ACCOUNT_TYPE; 

    public AccountAuthenticatorService() { 
     super(); 
     ACCOUNT_NAME = ApplicationConstants 
       .getValue(ApplicationConstants.ACCOUNT_NAME); 
     ACCOUNT_TYPE = ApplicationConstants 
       .getValue(ApplicationConstants.ACCOUNT_TYPE); 
    } 

    public static Account GetDefaultSyncAccount() { 
     final String accountName = ACCOUNT_NAME; 
     return new Account(accountName, ACCOUNT_TYPE); 
    } 

    /* 
    * (non-Javadoc) 
    * 
    * @see android.app.Service#onBind(android.content.Intent) 
    */ 
    @Override 
    public IBinder onBind(Intent intent) { 
     IBinder ret = null; 
     if (intent.getAction().equals(
       android.accounts.AccountManager.ACTION_AUTHENTICATOR_INTENT)) 
      ret = getAuthenticator().getIBinder(); 
     return ret; 
    } 

    /** 
    * Creates Singleton AccountAuthenticator Implementation. 
    * @return 
    */ 
    private AccountAuthenticatorImpl getAuthenticator() { 
     if (sAccountAuthenticator == null) 
      sAccountAuthenticator = new AccountAuthenticatorImpl(this); 
     return sAccountAuthenticator; 
    } 

    private static class AccountAuthenticatorImpl extends 
      AbstractAccountAuthenticator { 
     private Context mContext; 

     public AccountAuthenticatorImpl(Context context) { 
      super(context); 
      mContext = context; 
     } 

     /* 
     * (non-Javadoc) 
     * 
     * @see 
     * android.accounts.AbstractAccountAuthenticator#addAccount(android. 
     * accounts.AccountAuthenticatorResponse, java.lang.String, 
     * java.lang.String, java.lang.String[], android.os.Bundle) 
     */ 
     @Override 
     public Bundle addAccount(AccountAuthenticatorResponse response, 
       String accountType, String authTokenType, 
       String[] requiredFeatures, Bundle options) 
       throws NetworkErrorException { 
      Bundle result = new Bundle(); 
      Intent i = new Intent(mContext, AccountLoginActivity.class); 
      i.putExtra(AccountManager.KEY_ACCOUNT_AUTHENTICATOR_RESPONSE, 
        response); 
      result.putParcelable(AccountManager.KEY_INTENT, i); 
      return result; 
     } 

     /* 
     * (non-Javadoc) 
     * 
     * @see 
     * android.accounts.AbstractAccountAuthenticator#confirmCredentials(
     * android.accounts.AccountAuthenticatorResponse, 
     * android.accounts.Account, android.os.Bundle) 
     */ 
     @Override 
     public Bundle confirmCredentials(AccountAuthenticatorResponse response, 
       Account account, Bundle options) { 
      // TODO Auto-generated method stub 
      Log.i(TAG, "confirmCredentials, not supported, exception thrown."); 
      throw new UnsupportedOperationException(); 
     } 

     /* 
     * (non-Javadoc) 
     * 
     * @see 
     * android.accounts.AbstractAccountAuthenticator#editProperties(android 
     * .accounts.AccountAuthenticatorResponse, java.lang.String) 
     */ 
     @Override 
     public Bundle editProperties(AccountAuthenticatorResponse response, 
       String accountType) { 
      // TODO Auto-generated method stub 
      Log.i(TAG, "editProperties, not supported, exception thrown."); 
      throw new UnsupportedOperationException(); 
     } 

     /* 
     * (non-Javadoc) 
     * 
     * @see 
     * android.accounts.AbstractAccountAuthenticator#getAuthToken(android 
     * .accounts.AccountAuthenticatorResponse, android.accounts.Account, 
     * java.lang.String, android.os.Bundle) 
     */ 
     @Override 
     public Bundle getAuthToken(AccountAuthenticatorResponse response, 
       Account account, String authTokenType, Bundle options) 
       throws NetworkErrorException { 
      // TODO Auto-generated method stub 
      Log.i(TAG, "getAuthToken"); 
      Bundle bundle = new Bundle(); 
      // TODO this works, but isn't really doing any valid auth. 
      bundle.putString(AccountManager.KEY_AUTHTOKEN, account.name); 
      return bundle; 
     } 

     /** 
     * Ask for a localized label for the given authTokenType. 
     * <p> 
     * may return null if not known. 
     * 
     * @see android.accounts.AbstractAccountAuthenticator#getAuthTokenLabel(java 
     *  .lang.String) 
     */ 
     @Override 
     public String getAuthTokenLabel(String authTokenType) { 
      // TODO Auto-generated method stub 
      Log.i(TAG, "getAuthTokenLabel, not supported, exception thrown."); 
      throw new UnsupportedOperationException(); 
     } 

     /* 
     * Checking features of the Account Not Supported currently. 
     * 
     * @see 
     * android.accounts.AbstractAccountAuthenticator#hasFeatures(android 
     * .accounts.AccountAuthenticatorResponse, android.accounts.Account, 
     * java.lang.String[]) 
     */ 
     @Override 
     public Bundle hasFeatures(AccountAuthenticatorResponse response, 
       Account account, String[] features) 
       throws NetworkErrorException { 
      Log.i(TAG, "hasFeatures, not supported, exception thrown."); 
      throw new UnsupportedOperationException(); 
     } 

     /* 
     * (non-Javadoc) 
     * 
     * @see 
     * android.accounts.AbstractAccountAuthenticator#updateCredentials(android 
     * .accounts.AccountAuthenticatorResponse, android.accounts.Account, 
     * java.lang.String, android.os.Bundle) 
     */ 
     @Override 
     public Bundle updateCredentials(AccountAuthenticatorResponse response, 
       Account account, String authTokenType, Bundle options) { 
      // TODO Auto-generated method stub 
      Log.i(TAG, "updateCredentials, not supported, exception thrown."); 
      throw new UnsupportedOperationException(); 
     } 
    } 
} 

這裏是延伸AccountAuthenticatorActivity

package edu.vuum.mocca.authentication; 

import java.util.Locale; 

import android.accounts.Account; 
import android.accounts.AccountAuthenticatorActivity; 
import android.accounts.AccountManager; 
import android.app.ProgressDialog; 
import android.content.Context; 
import android.os.AsyncTask; 
import android.os.Bundle; 
import android.util.Log; 
import android.view.View; 
import android.view.View.OnClickListener; 
import android.widget.Button; 
import android.widget.EditText; 
import android.widget.Toast; 
import edu.vanderbilt.mooc.mooc_cp.R; 
import edu.vuum.mocca.main.ApplicationConstants; 

/** 
* Activity that gets Launched when Adding an Account to the SyncManager 
* <p> 
* An Activity to prompt for a Server Address, a UserName, and a Password. Uses 
* these to verify user login credentials and to create a 'token' identifying 
* the user account on the device. 
* 
* @author Michael A. Walker 
* @Date 2012-11-23 
*/ 
public class AccountLoginActivity extends AccountAuthenticatorActivity { 

    public final static String LOG_TAG = AccountLoginActivity.class.getCanonicalName(); 

    /************************************************************** 
    * UI component variables 
    *************************************************************/ 
    EditText mServerIP; 
    EditText mUsername; 
    EditText mPassword; 
    Button mLoginButton; 

    /************************************************************** 
    * Examples of constants for message passing on the AsyncTask 
    *************************************************************/ 
    public final static String PARAM_AUTHTOKEN_TYPE = ""; 
    public final static String PARAM_ACCOUNT_TYPE = ""; 

    /* 
    * Called when the activity is first created. 
    */ 
    @Override 
    public void onCreate(Bundle savedInstanceState) { 
     super.onCreate(savedInstanceState); 
     Log.d(LOG_TAG, "onCreate() called"); 
     setContentView(R.layout.authenticator_layout); 

     mServerIP = (EditText) findViewById(R.id.server); 
     mUsername = (EditText) findViewById(R.id.username); 
     mPassword = (EditText) findViewById(R.id.password); 

     mLoginButton = (Button) findViewById(R.id.login); 

     // might be able to make this go away and be in the XML 
     // just easier to put here for now. 
     mLoginButton.setOnClickListener(new OnClickListener() { 
      public void onClick(View v) { 
       loginButtonPressed(v); 
      } 
     }); 
    } 

    // start the background threaded action to authenticate the user 
    public void loginButtonPressed(View v) { 
     Log.d(LOG_TAG, "onCreate() called"); 
     String user = mUsername.getText().toString().trim() 
       .toLowerCase(Locale.ENGLISH); 
     String password = mPassword.getText().toString().trim() 
       .toLowerCase(Locale.ENGLISH); 

     String testValue = ApplicationConstants 
       .getValue(ApplicationConstants.ACCOUNT_TYPE); 

     if (testValue != null) { 
      Toast.makeText(getApplicationContext(), "testValue: " + testValue, 
        Toast.LENGTH_SHORT).show(); 
     } 

     if (user.length() > 0 && password.length() > 0) { 
      LoginTask t = new LoginTask(AccountLoginActivity.this); 
      t.execute(user, password); 
     } 
    } 

    /** 
    * This is the background logic behind the user login credentials checking 
    * 
    * @author Michael A. Walker 
    * 
    */ 
    private class LoginTask extends AsyncTask<String, Void, Boolean> { 

     Context mContext; 
     ProgressDialog mDialog; 

     // constructor 
     LoginTask(Context c) { 
      Log.d(LOG_TAG, "LoginTask() constructed"); 
      mContext = c; 
      mLoginButton.setEnabled(false); 
      // display a dialog with a spinner showing progress being worked on 
      mDialog = ProgressDialog.show(c, "", 
        getString(R.string.authenticating), true, false); 
      mDialog.setCancelable(true); 
     } 

     // Threaded background work (doesn't block UI) 
     @Override 
     public Boolean doInBackground(String... params) { 
      Log.d(LOG_TAG, "LoginTask.doInBackground() called"); 
      String user = params[0]; 
      String pass = params[1]; 

      // TODO:Do something internetty HERE 
      try { 
       Thread.sleep(2000); 
      } catch (Exception e) { 

       e.printStackTrace(); 
      } 

      Bundle result = null; 
      Account account = new Account(user, 
        mContext.getString(R.string.ACCOUNT_TYPE)); 
      AccountManager am = AccountManager.get(mContext); 
      if (am.addAccountExplicitly(account, pass, null)) { 
       result = new Bundle(); 
       result.putString(AccountManager.KEY_ACCOUNT_NAME, account.name); 
       result.putString(AccountManager.KEY_ACCOUNT_TYPE, account.type); 
       setAccountAuthenticatorResult(result); 
       return true; 
      } else { 
       return false; 
      } 
     } 

     // post processing of login verification 
     @Override 
     public void onPostExecute(Boolean result) { 
      Log.d(LOG_TAG, "LoginTask.onPostExecute() called"); 
      mLoginButton.setEnabled(true); 
      mDialog.dismiss(); 
      if (result) 
       finish(); 
     } 
    } 
} 
+0

我仍不能相信你寫了這個,仍然會使用上面的「啓動畫面」方法。感謝您的解釋。我瞭解一些東西,並會嘗試實施它。 –