Android에서 활동을 다시 시작하는 방법


381

Android를 다시 시작하려면 어떻게합니까 Activity? 나는 다음을 시도했지만 Activity단순히 종료됩니다.

public static void restartActivity(Activity act){

        Intent intent=new Intent();
        intent.setClass(act, act.getClass());
        act.startActivity(intent);
        act.finish();

}

9
u가 "act.finish ();"를 호출했기 때문에 활동이 종료됩니다. 즉시 작업을 만든 후 ...
— Nikhil 네쉬

1
구식 방법
— pedjjj

답변:


623

테마 스위처를 다음과 같이했습니다.

Intent intent = getIntent();
finish();
startActivity(intent);

기본적으로 finish()먼저 전화를 하고이 활동이 시작된 것과 정확히 동일한 의도를 사용하고 있습니다. 그 트릭을하는 것 같아?

업데이트 : 아래 Ralf에서 지적했듯이 Activity.recreate()API 11 이상으로 이동하는 방법입니다. API11 + 환경에있는 경우이 방법이 좋습니다. API 10 이하인 경우 여전히 현재 버전을 확인하고 위의 코드 스 니펫을 호출 할 수 있습니다. (Ralf의 답변을 찬성하는 것을 잊지 마십시오!)


36
그리고 그 가치를 떨어 뜨릴 가치가 있습니까? OP에서 언급 한 요구 사항은 아닙니다. 실제로, 바람직 할 수있다.
— EboMike

9
글쎄, 당신이 애니메이션을 좋아하지 않는다면, 당신은 (당신의 답변에서 입증 된 것처럼) 끌 수 있습니다. 그것은 내 대답 자체를 틀리게 만들지 않으며, 자유롭게 추가 할 수있는 추가 옵션을 보여주지 않습니다 (질문에서 묻지 않은).
— EboMike

28
당신이 잘못 생각합니다. downvote는 오답을 의미하며, upvote는 답이 크다는 의미입니다. 답변이 다른 사람과 비교되는 정도는 공감 횟수로 표시됩니다. 답변을 홍보하려고 노력하고 있지만 해당 목적으로 시스템을 잘못 사용하고 있음을 알 수 있습니다.
— EboMike

8
+1-이것은 나에게 큰 효과가 있었고, 당신이 말했듯이 애니메이션은 내가 원했던 것이므로 사용자는 다시 시작한다는 것을 알고 있습니다. FWIW, 나는 질문에 대한 대체 답변을 제공 할 때 다른 사용자의 답변을 절대로 투표하지 않는 것이 원칙입니다.하지만 답변이 클래스를 벗어날 때 가끔 투표를합니다 (여기서 그런 말을하지 않고 그냥 그렇게합니다) .
— Michael Bray

4
EboMike와 Ben : 두 솔루션 모두 OP의 질문에 답변했습니다. "미적"이유 때문에 누군가의 대답을 순수하게 투표하는 것은 좋지 않습니다. 나는 ... 유래 여기 그 일에서 사람을 낙담 것
— ChuongPham

368

API 레벨 11 (Honeycomb)부터 활동 의 recreate () 메소드를 호출 할 수 있습니다 ( 이 답변 덕분에 ).

recreate () 메소드는 구성 변경과 동일하게 작동하므로 해당되는 경우 onSaveInstanceState () 및 onRestoreInstanceState () 메소드도 호출됩니다.


3
이전 액티비티가 startActivityForResult를 사용하여이 액티비티를 호출 한 경우 어떻게됩니까?
— 안드로이드 개발자

1
API 11보다 낮은 것을 지원할 필요가 없다면 정답입니다.
— Edward Falk

@EdwardFalk 지원 라이브러리에 기능이 있습니까?
— 안드로이드 개발자

2
모든 경우에 작동하지는 않습니다. recreate ()를 호출하는 동안 탐색 드로어가 열려 있으면 다시 작성할 때 계속 열려 있으므로 상태를 저장하므로 바람직하지 않을 수 있습니다.
— Chapz

나는 국가가 구원 받기를 원하지 않는 사람입니다. 때로는 사람들이 완전히 다시 시작하기를 원하는 경우 EboMike의 답변을 사용해야합니다.
— Kimi Chiu

132

SDK 11 이전의 방법은 다음과 같습니다.

public void reload() {
    Intent intent = getIntent();
    overridePendingTransition(0, 0);
    intent.addFlags(Intent.FLAG_ACTIVITY_NO_ANIMATION);
    finish();
    overridePendingTransition(0, 0);
    startActivity(intent);
}

HTC에서 Desire 애니메이션은 여전히 ​​남아 있습니다 (적어도 onConfigurationChanged 메소드에서 사용되는 경우). 항상 발생하는 것은 아니지만 EboMike의 코드를 사용하면 항상 발생하지는 않습니다.
— Juozas Kontvainis

8
런처가 시작한 주요 활동에서는 작동하지 않습니다. 의도에 설정된 일부 플래그로 인해 활동이 숨겨집니다. 그렇지 않으면 잘 작동합니다.
— Thomas Ahle

좋은 지적. 스택의 기본 활동에서 finish ()를 호출하기 때문에 의미가 있습니다.
— Ben

우리가 활동의 주제를 바꾸는 동안 이것을 부르는 것은 애니메이션없이 속도를 이끌어내는 것 같습니다
— Ashok Goli

3
+1 주요 활동으로도 잘 작동합니다. 그러나, 당신은 호출해야합니다 overridePendingTransition(0, 0);후 finish()하고 startActivity()당신이 그것을라는 곳 ... 각각 없습니다
— 까악 까악

115

Ralf와 Ben의 답변 (댓글의 변경 사항 포함)을 결합하기 만하면됩니다.

if (Build.VERSION.SDK_INT >= 11) {
    recreate();
} else {
    Intent intent = getIntent();
    intent.addFlags(Intent.FLAG_ACTIVITY_NO_ANIMATION);
    finish();
    overridePendingTransition(0, 0);

    startActivity(intent);
    overridePendingTransition(0, 0);
}

8
모두의 베스트 답변. 믿거 나 말거나, 여전히 API 3 장치를 지원하고 있으며 VERSION.SDK_INT 값에는 API 4가 필요합니다. :)
— Edward Falk

31

이 코드를 사용하여 여전히 이전 Android 버전을 지원 recreate()하고 최신 Android 버전에서 사용할 수 있습니다.

암호:

public static void restartActivity(Activity activity){
    if (Build.VERSION.SDK_INT >= 11) {
        activity.recreate();
    } else {
        activity.finish();
        activity.startActivity(activity.getIntent());
    }
}

견본:

import android.app.Activity;
import android.os.Build;
import android.os.Bundle;
import android.support.v7.app.AppCompatActivity;
import android.view.View;
import android.widget.Button;

public class MainActivity extends AppCompatActivity {
    private Activity mActivity;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        mActivity = MainActivity.this;

        Button button = (Button) findViewById(R.id.restart_button);
        button.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                restartActivity(mActivity);
            }
        });
    }

    public static void restartActivity(Activity activity) {
        if (Build.VERSION.SDK_INT >= 11) {
            activity.recreate();
        } else {
            activity.finish();
            activity.startActivity(activity.getIntent());
        }
    }
}

나를 위해 큰 일입니다!
— 파포

22

이 솔루션은 저에게 효과적이었습니다.

먼저 활동을 완료 한 후 다시 시작하십시오.

샘플 코드 :

public void restartActivity(){
    Intent mIntent = getIntent();
    finish();
    startActivity(mIntent);
}

20

이것은 현재 활동을 다시 시작하는 가장 쉬운 방법입니다.

finish();
startActivity(getIntent());

19

이 방법을 호출

private void restartFirstActivity()
 {
 Intent i = getApplicationContext().getPackageManager()
 .getLaunchIntentForPackage(getApplicationContext().getPackageName() );

 i.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP | Intent.FLAG_ACTIVITY_NEW_TASK );
 startActivity(i);
 }

감사,


1
OP가 첫 번째 활동뿐만 아니라 모든 활동을 다시 시작하려고한다고 생각하지만 이것은 나에게 도움이되었습니다.
— Kristopher Johnson

1
두 깃발은 알아두면 좋을 것입니다. 제 사건은 그들 없이는 아무것도하지 않는 것 같습니다.
— Owen B

1
그것은 당신 덕분에 일했습니다! 하나님의 축복이 있기를 .
— Vivek

16

이것은 여러 번 답변되었지만.

조각에서 활동을 다시 시작하면 다음과 같이됩니다.

new Handler().post(new Runnable() {

         @Override
         public void run()
         {
            Intent intent = getActivity().getIntent();
            intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP | Intent.FLAG_ACTIVITY_NEW_TASK | Intent.FLAG_ACTIVITY_NO_ANIMATION);
            getActivity().overridePendingTransition(0, 0);
            getActivity().finish();

            getActivity().overridePendingTransition(0, 0);
            startActivity(intent);
        }
    });

그래서 당신은 이것이 약간 과잉이라고 생각할 수 있습니까? 그러나 Handler게시를 통해 수명주기 방식으로이를 호출 할 수 있습니다. 나는 이것을 이것을 onRestart/에 사용했다onResume 사용자가 앱으로 돌아 오는 사이에 상태가 변경되었는지 확인할 때 메소드 . (뭔가 설치).

없이 Handler이상한 곳에서 호출 활동을 종료하고 다시 시작하지 않습니다.

궁금한 점이 있으면 언제든지 문의하십시오.

건배, 크리스


2
핸들러에 대한 훌륭한 솔루션과 매우 좋은 추론 / 설명.
— JRomero

1
"overridePendingTransition"에 두 번 전화하는 이유는 무엇입니까?
— 안드로이드 개발자

1
@androiddeveloper 기억이 안 나는 버그에 대한 해결책이라고 생각합니다. startActivity () 전에 한 번 호출하면 지시대로 수행됩니다.
— Chris.Jenkins

onResume 함수에서이 기능을 구현 한 후 게임이 onStop 메서드에서 중지되고 검은 색 화면이 나타납니다 ... 이유가 확실하지 않음
— Scumble373

1
안녕하세요 크리스, 이걸 좀 더 설명 할 수 있습니까? "홀더를 이상한 곳에서 호출하면 액티비티가 종료되고 다시 시작되지 않습니다." ?
— parvez rafi

15

글쎄, 이것은 나열되지 않았지만 이미 게시 된 일부의 콤보입니다.

if (Build.VERSION.SDK_INT >= 11) {
    recreate();   
} else {
    Intent intent = getIntent();
    finish();
    startActivity(intent);
}

그것은 나를 위해 작동합니다 .. 감사합니다 .. 그러나 당신에게 묻고 싶습니다 : 왜 코드의 첫 부분 (SDK_INT를 확인하는 부분)을 제거하면 내 앱이 상대적으로 느리게 실행됩니까? !! .. 코드를 다시 첨부 할 때 상대적으로 명백하게 훨씬 빠르게 실행됩니다 !!!
— McLan

2
확실하지 않습니다. 글쎄, 당신이> = 11 인 SDK를 사용한다면, recreate ()는 의도를 얻는 것, 끝내고 다시 시작하는 것보다 빠를 것입니다. Finish는 onStop으로 실행되는 코드를 호출하고 방향 변경과 같은 실행 코드를 다시 작성하므로 그렇게 할 일이별로 없습니다.
— Codeversed

4

카메라 와 함께 이상한 SurfaceView 수명주기 동작과 함께 . recreate ()가 SurfaceView의 수명주기와 잘 작동하지 않는다는 것을 알았습니다. 레크리에이션 사이클 동안 surfaceDestroyed가 호출되지 않습니다. onResume (이상) 후에 호출되며,이 시점에서 SurfaceView가 파괴됩니다.

활동을 재현하는 원래 방법은 잘 작동합니다.

Intent intent = getIntent();
finish();
startActivity(intent);

이것이 왜 정확한지 알 수는 없지만 SurfaceViews와 관련된 문제를 해결했기 때문에 앞으로 다른 사람들을 희망적으로 안내 할 수있는 관찰 일뿐입니다.


4

왜 아무도 Intent.makeRestartActivityTask()정확하게이 정확한 목적을 언급하지 않았는지 궁금 합니다.

기본 상태에서 응용 프로그램의 작업을 다시 시작하는 데 사용할 수있는 의도를 만드십시오.

startActivity(Intent.makeRestartActivityTask(getActivity().getIntent().getComponent()));

이 메소드는 Intent.FLAG_ACTIVITY_NEW_TASK | Intent.FLAG_ACTIVITY_CLEAR_TASK기본 플래그로 설정 됩니다.


3

실제로 다음 코드는 API 레벨 5 이상에서 유효하므로 대상 API가 이보다 낮 으면 EboMike의 코드와 매우 유사한 결과가 나타납니다.

intent.addFlags(Intent.FLAG_ACTIVITY_NO_ANIMATION);
overridePendingTransition(0, 0);

3

주요 활동을 포함하여 모든 활동에서 작동해야하는 해키 방법이 하나 있습니다.

setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_NOSENSOR);
setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_SENSOR);

오리엔테이션이 변경되면 Android는 일반적으로 액티비티를 재정의하지 않는 한 액티비티를 다시 만듭니다. 이 방법은 Android가 액티비티를 다시 만들지 않을 때 180도 회전에 유용합니다.


3
public void onRestart() {
    super.onRestart();
    Intent intent=new Intent();
    intent.setClass(act, act.getClass());
    finish();
    act.startActivity(intent);
}

이것을 사용해보십시오 ..


3

귀하의 질문에 대한 해결책은 다음과 같습니다.

public static void restartActivity(Activity act){
    Intent intent=new Intent();
    intent.setClass(act, act.getClass());
    ((Activity)act).startActivity(intent);
    ((Activity)act).finish();
}

새 활동을 시작하고 현재 활동을 완료하려면 활동 컨텍스트로 캐스트해야합니다.

도움이되기를 바랍니다.


1

마지막 줄을 제거하면 새 act활동 이 생성 되지만 이전 인스턴스는 계속 활성화됩니다.

방향이 변경 될 때와 같이 활동을 다시 시작해야합니까 (예 : 상태가 저장되고로 전달됨 onCreate(Bundle))?

그렇지 않은 경우 가능한 한 가지 해결 방법은 첫 번째 활동에서 시작되는 새 더미 활동을 사용하고 새 인스턴스를 시작하는 작업입니다. 아니면 그냥 전화를 지연act.finish() 새 이 시작된 후에 .

대부분의 상태를 저장해야 할 경우, 특히 오래된 컨텍스트 / 활동을 누설하지 않고 상태를 새 인스턴스로 전달하여 상태의 모든 속성을 전달하는 것이 쉽지 않기 때문에 상당히 심해에 빠지게됩니다.

수행하려는 작업을 지정하십시오.


1
앱에 다른 테마를 적용하는 버튼이 있습니다. 테마가 적용된 후 환경 설정에 저장되고 루트 활동이 다시 시작되고 환경 설정에서 테마를 읽고 onCreate ()에 테마를 적용합니다. 활동이 single_instance가 아닌 경우 위의 코드가 제대로 작동하는 것으로 나타났습니다. 이것이 최선의 방법인지 확실하지 않습니다.

현재 액티비티, AFAIK를 다시 시작할 깨끗하고 SDK - 포장 방법이 없다 - 당신이하지 누출 아무것도 할 경우, 당신은 :) 가서 잘 될 수있다
— 디미타르 디미트로프

0

이것이 내가하는 방법입니다.

        val i = Intent(context!!, MainActivity::class.java)
        i.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TASK)
        startActivity(i)

-1

일부 조각에서 호출하는 경우 아래 코드를 수행하십시오.

Intent intent = getActivity().getIntent();
getActivity().finish();
startActivity(intent);

-4

당신은 단순히 사용할 수 있습니다

onRestart ()

다음과 같은 방법

 @Override
    protected void onRestart() {
        super.onRestart();
        setContentView(R.layout.add_entry);
    }

및 onRestart ()를 호출 하면 현재 활동을 다시 시작하려면


-5

onCreate 메소드를 호출하십시오. 예를 들어onCreate(null);

당사 사이트를 사용함과 동시에 당사의 쿠키 정책과 개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.