1

Accessing Google APIsのガイドにうまく従った後、すべての Google+ 関連コードを自分のコードからMainActivity別のカスタムGoogleFragmentに移動しようとしています。

しかし、私は最後の場所で立ち往生しています - 私のカスタムフラグメントでは、が却下されmResolvingErrorた後にフィールドにアクセスする方法がわかりません:DialogFragment

public class GoogleFragment extends Fragment
        implements GoogleApiClient.OnConnectionFailedListener {

    private boolean mResolvingError = false; // HOW TO ACCESS?

    @Override
    public void onConnectionFailed(ConnectionResult connectionResult) {
        if (mResolvingError) {
            // Already attempting to resolve an error.
            return;
        } else if (connectionResult.hasResolution()) {
            try {
                mResolvingError = true;
                connectionResult.startResolutionForResult(getActivity(), REQUEST_RESOLVE_ERROR);
            } catch (IntentSender.SendIntentException e) {
                // There was an error with the resolution intent. Try again.
                if (mGoogleApiClient != null)
                    mGoogleApiClient.connect();
            }
        } else {
            // Show dialog using GoogleApiAvailability.getErrorDialog()
            showErrorDialog(connectionResult.getErrorCode());
            mResolvingError = true;
        }
    }

    private void showErrorDialog(int errorCode) {
        // Create a fragment for the error dialog
        ErrorDialogFragment dialogFragment = new ErrorDialogFragment();
        // Pass the error that should be displayed
        Bundle args = new Bundle();
        args.putInt(ARGS_DIALOG_ERROR, errorCode);
        dialogFragment.setArguments(args);
        dialogFragment.show(getActivity().getSupportFragmentManager(), TAG_DIALOG_ERROR);
    }

    public static class ErrorDialogFragment extends DialogFragment {
        public ErrorDialogFragment() {
        }

        @Override
        public Dialog onCreateDialog(Bundle savedInstanceState) {
            // Get the error code and retrieve the appropriate dialog
            int errorCode = this.getArguments().getInt(ARGS_DIALOG_ERROR);
            return GoogleApiAvailability.getInstance().getErrorDialog(
                    this.getActivity(),
                    errorCode,
                    REQUEST_RESOLVE_ERROR);
        }

        @Override
        public void onDismiss(DialogInterface dialog) {
            mResolvingError = false; // DOES NOT COMPILE
        }
    }
}

ここで何をすればいいですか?

ErrorDialogFragment非静的にすると、コンパイル エラーが発生します。

このフラグメントの内部クラスは静的である必要があります (GoogleFragment.ErrorDialogFragment)

静的にしておくと、変数にもアクセスできません。

私の問題の2つの回避策を考えています:

  1. カスタムをLocalBroadcastManager送信するために使用するIntentErrorDialogFragmentGoogleFragment
  2. でカスタム メソッドを定義しGoogleFragmentgetSupportFragmentManager().findFragmentByTag()

しかし、もっと簡単な解決策はありますか?

アップデート:

フィールドを publicに変更し、次のmResolvingErrorコードを試しました。

    @Override
    public void onDismiss(DialogInterface dialog) {
        GoogleFragment f = (GoogleFragment) getActivity().getSupportFragmentManager().findFragmentByTag(GoogleFragment.TAG);
        if (f != null && f.isVisible()) {
            f.mResolvingError = false;
        }
    }

しかし、これを適切にテストする方法がわかりませんf.isVisible()。必要な場合は...

更新 2:

たぶん、コードでGoogleApiAvailability.getInstance().getErrorDialogでDialogInterface.OnDismissListenerを使用する必要がありますか?

4

1 に答える 1

1

BladeCoder のコメントは非常に洞察に満ちています。

ただし、 startResolutionForResult()はとにかく別のアクティビティを開始し、アプリを妨害するため、保存と復元に関するすべての手間mResolvingErrorが不要であることに気付きました。そのため、デバイスを回転させるかどうかは問題ではありません。

GCM を開始して Google+ ユーザー データを取得するための最終的なコードを次に示します。

スクリーンショット 1

スクリーンショット 2

MainActivity.java:

public static final int REQUEST_GOOGLE_PLAY_SERVICES = 1972;
public static final int REQUEST_GOOGLE_PLUS_LOGIN = 2015;

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    if (savedInstanceState == null)
        startRegistrationService();
}

private void startRegistrationService() {
    GoogleApiAvailability api = GoogleApiAvailability.getInstance();
    int code = api.isGooglePlayServicesAvailable(this);
    if (code == ConnectionResult.SUCCESS) {
        onActivityResult(REQUEST_GOOGLE_PLAY_SERVICES, Activity.RESULT_OK, null);
    } else if (api.isUserResolvableError(code) &&
        api.showErrorDialogFragment(this, code, REQUEST_GOOGLE_PLAY_SERVICES)) {
        // wait for onActivityResult call (see below)
    } else {
        String str = GoogleApiAvailability.getInstance().getErrorString(code);
        Toast.makeText(this, str, Toast.LENGTH_LONG).show();
    }
}

@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
    switch(requestCode) {
        case REQUEST_GOOGLE_PLAY_SERVICES:
            if (resultCode == Activity.RESULT_OK) {
                Intent i = new Intent(this, RegistrationService.class); 
                startService(i); // OK, init GCM
            }
            break;

        case REQUEST_GOOGLE_PLUS_LOGIN:
            if (resultCode == Activity.RESULT_OK) {
                GoogleFragment f = (GoogleFragment) getSupportFragmentManager().
                    findFragmentByTag(GoogleFragment.TAG);
                if (f != null && f.isVisible())
                    f.onActivityResult(requestCode, resultCode, data);
            }
            break;

        default:
            super.onActivityResult(requestCode, resultCode, data);
    }
}

GoogleFragment.java:

public class GoogleFragment extends Fragment
        implements View.OnClickListener,
        GoogleApiClient.ConnectionCallbacks,
        GoogleApiClient.OnConnectionFailedListener {

    public final static String TAG = "GoogleFragment";

    private GoogleApiClient mGoogleApiClient;

    private ImageButton mLoginButton;
    private ImageButton mLogoutButton;

    public GoogleFragment() {
        // required empty public constructor
    }

    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container,
                             Bundle savedInstanceState) {

        View v = inflater.inflate(R.layout.fragment_google, container, false);

        mGoogleApiClient = new GoogleApiClient.Builder(getContext())
                .addConnectionCallbacks(this)
                .addOnConnectionFailedListener(this)
                .addApi(Plus.API)
                .addScope(Plus.SCOPE_PLUS_PROFILE)
                .build();

        mLoginButton = (ImageButton) v.findViewById(R.id.login_button);
        mLoginButton.setOnClickListener(this);

        mLogoutButton = (ImageButton) v.findViewById(R.id.logout_button);
        mLogoutButton.setOnClickListener(this);

        return v;
    }

    private void googleLogin() {
        mGoogleApiClient.connect();
    }

    private void googleLogout() {
        if (mGoogleApiClient.isConnecting() || mGoogleApiClient.isConnected())
            mGoogleApiClient.disconnect();
    }

    @Override
    public void onActivityResult(int requestCode, int resultCode, Intent data) {
        if (resultCode == Activity.RESULT_OK)
            mGoogleApiClient.connect();
    }

    @Override
    public void onClick(View v) {
        if (v == mLoginButton)
            googleLogin();
        else
            googleLogout();
    }

    @Override
    public void onConnected(Bundle bundle) {
        Person me = Plus.PeopleApi.getCurrentPerson(mGoogleApiClient);
        if (me != null) {
            String id = me.getId();
            Person.Name name = me.getName();
            String given = name.getGivenName();
            String family = name.getFamilyName();
            boolean female = (me.hasGender() && me.getGender() == 1);

            String photo = null;
            if (me.hasImage() && me.getImage().hasUrl()) {
                photo = me.getImage().getUrl();
                photo = photo.replaceFirst("\\bsz=\\d+\\b", "sz=300");
            }

            String city = "Unknown city";
            List<Person.PlacesLived> places = me.getPlacesLived();
            if (places != null) {
                for (Person.PlacesLived place : places) {
                    city = place.getValue();
                    if (place.isPrimary())
                        break;
                }
            }

            Toast.makeText(getContext(), "Given: " + given + ", Family: " + family + ", Female: " + female + ", City: " + city, Toast.LENGTH_LONG).show();
        }
    }

    @Override
    public void onConnectionSuspended(int i) {
        // ignore? don't know what to do here...
    }

    @Override
    public void onConnectionFailed(ConnectionResult connectionResult) {
        if (connectionResult.hasResolution()) {
            try {
                connectionResult.startResolutionForResult(getActivity(), MainActivity.REQUEST_GOOGLE_PLUS_LOGIN);
            } catch (IntentSender.SendIntentException e) {
                mGoogleApiClient.connect();
            }
        } else {
            int code = connectionResult.getErrorCode();
            String str = GoogleApiAvailability.getInstance().getErrorString(code);
            Toast.MakeText(getContext(), str, Toast.LENGTH_LONG).show();
        }
    }
}
于 2015-09-17T17:13:29.587 に答える