1. java 소스코드에 프래그먼트 추가하기

소스 코드에서 프래그먼트를 추가하기 위해선 프래그먼트 매니저를 사용해야 한다.

프래그먼트 매니저는 getSupportFragmentManager 메소드를 이용하여 참조한다. 



2. 실행 결과 화면

 



3. activity_main.xml

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical"
    android:padding="10dp"
    android:gravity="center">
 
   <LinearLayout
       android:layout_width="match_parent"
       android:layout_height="wrap_content"
       android:orientation="horizontal"
       android:layout_marginTop="50dp"
       android:layout_marginBottom="30dp"
       android:gravity="center">
 
      <Button
          android:id="@+id/button1"
          android:layout_width="150dp"
          android:layout_height="wrap_content"
          android:text="프래그먼트1"/>
 
      <Button
          android:id="@+id/button2"
          android:layout_width="150dp"
          android:layout_height="wrap_content"
          android:text="프래그먼트2" />
   </LinearLayout>
 
   <FrameLayout
       android:id="@+id/frame_layout"
       android:layout_width="match_parent"
       android:layout_height="match_parent">
      <!--<fragment
          android:id="@fragment1main"
          android:nacom.tistory.qlyh8.pracitice.FragmentActivity11vity"
          android:layout_width="match_parent"
          android:layout_height="match_parent"/>-->
   </FrameLayout>
 
</LinearLayout>
 
cs



4. MainActivity.java

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
package com.tistory.qlyh8.pracitice;
 
import android.os.Bundle;
import android.support.v7.app.AppCompatActivity;
import android.view.View;
import android.widget.Button;
 
public class MainActivity extends AppCompatActivity {
 
    Button button1, button2;
    FragmentActivity1 frameLayout1;
    FragmentActivity2 frameLayout2;
 
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
 
        button1 = findViewById(R.id.button1);
        button2 = findViewById(R.id.button2);
        frameLayout1 = new FragmentActivity1();
        frameLayout2 = new FragmentActivity2();
 
        button1.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                // 프래그먼트 매니저가 프래그먼트를 담당하며, 프래그먼트 매니저은 트랜잭션에 기반한다.
                // replace(): 기존에 있는게 있으면 대체한다.
                getSupportFragmentManager().beginTransaction()
                        .replace(R.id.frame_layout, frameLayout1).commit();
            }
        });
 
        button2.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                getSupportFragmentManager().beginTransaction()
                        .replace(R.id.frame_layout, frameLayout2).commit();
            }
        });
    }
}
cs



5. fragment1.xml 

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:background="#aaaaad"
    android:padding="10dp">
 
    <TextView
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:text="Fragment 1"
        android:textSize="30sp"
        android:textAlignment="center"/>
 
</LinearLayout>
 
cs



6.fragment2.xml

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:background="#aaddad"
    android:padding="10dp">
 
    <TextView
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:text="Fragment 2"
        android:textSize="30sp"
        android:textAlignment="center"/>
 
</LinearLayout>
 
cs



7. FragmentActivity1.java

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
package com.tistory.qlyh8.pracitice;
 
import android.os.Bundle;
import android.support.annotation.Nullable;
import android.support.v4.app.Fragment;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
 
public class FragmentActivity1 extends Fragment {
 
    @Nullable
    @Override
    public View onCreateView(LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) {
        ViewGroup rootView = (ViewGroup) inflater.inflate(R.layout.fragment1, container, false);
        return rootView;
    }
}
 
cs



8. FragmentActivity2.java

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
package com.tistory.qlyh8.pracitice;
 
import android.os.Bundle;
import android.support.annotation.Nullable;
import android.support.v4.app.Fragment;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
 
public class FragmentActivity2 extends Fragment {
 
    @Nullable
    @Override
    public View onCreateView(LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) {
        ViewGroup rootView = (ViewGroup) inflater.inflate(R.layout.fragment2, container, false);
        return rootView;
    }
}
 
cs



참고

FragmentManager, FragmentTransaction 에 대해서:

http://www.kmshack.kr/2013/08/fragment-%ED%8C%8C%ED%97%A4%EC%B9%98%EA%B8%B0-3-fragmentmanager-fragmenttransaction%EC%97%90-%EB%8C%80%ED%95%B4%EC%84%9C/





출처: https://www.edwith.org/boostcourse-android/lecture/17074/ 


1. 프래그먼트 (Fragment)


프래그먼트를 이용하면 액티비티로 만든 화면 안에 부분화면을 독립적으로 사용할 수 있다.


프래그먼트는 액티비티가 동작하는 방식과 유사하게 프래그먼트를 위한 XML 레이아웃과 소스 파일이 한 쌍으로 만들어진다. 

프래그먼트 객체를 필요할 때 액티비티에서 사용할 수 있어 독립적으로 사용할 수 있게 된다.


액티비티 위에 올라가도록 만들었기 때문에 액티비티가 시스템 역할을 하게 되고, 액티비티보다 가볍게 화면 구성을 할 수 있다.

하나의 액티비티에 하나의 프래그먼트를 전체화면으로 보여주면 시스템과 관계없이 전체화면을 전환하는 효과를 만들 수 있다.

액티비티가 따로 뜨는 것이 아니기 때문에 시스템에서 접근하지 않아 보안 면에서도 장점이 있다.

그러나 프래그먼트를 사용하면 코드가 복잡해지는 단점도 있다.



2. XML 레이아웃에 프래그먼트 추가하기


XML 레이아웃 파일을 만들고 그 파일을 소스 파일에 설정하려면 

프래그먼트 안에 있는 onCreateView 메소드 안에서 Layout inflater를 이용해 인플레이션을 진행한다.


onCreateView 메소드는 자동으로 호출되는 메소드이며 파라미터로 LayoutInflater 객체를 전달해준다.

이 객체의 inflate 메소드를 이용해 인플레이션을 진행할 수 있다.

XML 레이아웃에 추가할 때는, <fragment> 태그를 사용하고 프래그먼트 클래스를 지정할 때는 name 속성을 사용한다.



실행 결과 화면



Fragment_main.xml
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:background="#aaaaad"
    android:padding="10dp">
 
    <TextView
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:text="Fragment 1"
        android:textSize="30sp"
        android:textAlignment="center"/>
 
</LinearLayout>
cs


FragmentActivity.java

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
package com.tistory.qlyh8.pracitice;
 
import android.os.Bundle;
import android.support.annotation.Nullable;
import android.support.v4.app.Fragment;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
 
public class FragmentActivity extends Fragment {
 
    @Nullable
    @Override
    public View onCreateView(LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) {
        ViewGroup rootView = (ViewGroup) inflater.inflate(R.layout.fragment_main, container, false);
        return rootView;
    }
}
 
cs


activity_main.xml

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    tools:context="com.tistory.qlyh8.pracitice.SmsActivity"
    android:orientation="vertical"
    android:padding="10dp"
    android:gravity="center">
 
   <Button
       android:id="@+id/button"
       android:layout_width="250dp"
       android:layout_height="wrap_content"
       android:layout_marginTop="50dp"
       android:layout_marginBottom="30dp"
       android:text="시작"/>
 
   <FrameLayout
       android:layout_width="match_parent"
       android:layout_height="match_parent">
      <fragment
          android:id="@+id/fragment_main"
          android:name="com.tistory.qlyh8.pracitice.FragmentActivity"
          android:layout_width="match_parent"
          android:layout_height="match_parent"/>
   </FrameLayout>
 
</LinearLayout>
 
cs



참고

프래그먼트란? https://developer.android.com/guide/components/fragments?hl=ko





출처: https://www.edwith.org/boostcourse-android/lecture/17074/

1. 위험권한 (Dangerous Permission)

마시멜로우 버전(22)부터 권한을 일반 권한(Normal Permission)과 위험 권한(Dangerous Permission)으로 나누었다.

위험 권한은 앱이 실행된 후에 사용자에게 권한 허용을 요청해야 한다.



2. 위험 권한의 종류

위험 권한은 개인정보가 담겨있는 정보에 접근하는 경우에 대부분 부여된다.

 권한 이름

세부 권한 

 LOCATION

ACCESS_FINE_LOCATION

ACCESS_COARSE_LOCATION 

 CAMERA

CAMERA 

 MICROPHONE

 RECORD_AUDIO

CONTACTS 

 READ_CONTACTS

WRITE_CONTACTS

GET_ACCOUNTS

PHONE 

READ_PHONE_STATE

CALL_PHONE

READ_CALL_LOG

WRITE_CALL_LOG

ADD_VOICEMAIL

USE_SIP

PROCESS_OUTGOING_CALLS 

SMS 

 SEND_SMS

RECEIVE_SMS

READ_SMS

RECEIVE_WAP_PUSH

RECEIVE_MMS

CALENDAR 

 READ_CALENDAR

WRITE_CALENDAR

SENSORS 

BODY_SENSORS 

STORAGE

READ_EXTERNAL_STORAGE

WRITE_EXTERNAL_STORAGE 



3. 위험 권한 부여

app 수준의 build.gradle 파일에서 targetSdkVersion 값을 23 미만으로 설정하면 위험 권한도 자동으로 부여된다.

그러나 필요 시에 직접 코드에서 앱 실행 시에 위험 권한을 부여해야 한다.


실행 결과 화면

  


app/build.gradle

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
ndroid {
    compileSdkVersion 26
    defaultConfig {
        applicationId "com.tistory.qlyh8.pracitice"
        minSdkVersion 15
        targetSdkVersion 26
        versionCode 1
        versionName "1.0"
        testInstrumentationRunner "android.support.test.runner.AndroidJUnitRunner"
    }
    buildTypes {
        release {
            minifyEnabled false
            proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
        }
    }
}
cs



AndroidManifest.xml

1
2
3
4
5
6
7
8
9
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
    package="com.tistory.qlyh8.pracitice">
 
    <uses-permission android:name="android.permission.RECEIVE_SMS" />
 
    <application
        android:allowBackup="true"
        android:icon="@mipmap/ic_launcher"
        android:label="@string/app_name"
cs



MainActivity.java

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
package com.tistory.qlyh8.pracitice;
 
import android.Manifest;
import android.content.pm.PackageManager;
import android.os.Bundle;
import android.support.annotation.NonNull;
import android.support.v4.app.ActivityCompat;
import android.support.v4.content.ContextCompat;
import android.support.v7.app.AppCompatActivity;
import android.widget.Toast;
 
public class MainActivity extends AppCompatActivity {
 
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_sms);
 
        // "RECEIVE_SMS" 권한 있는지 체크
        int permissionCheck = ContextCompat.checkSelfPermission(this, Manifest.permission.RECEIVE_SMS);
 
        if (permissionCheck == PackageManager.PERMISSION_GRANTED) { // 권한이 주어짐
            Toast.makeText(this"SMS 수신 권한 있음.", Toast.LENGTH_LONG).show();
        }
        else {  // 권한이 주어지지 않음. permissionCheck == PackageManager.PERMISSION_DENIED
            Toast.makeText(this"SMS 수신 권한 없음.", Toast.LENGTH_LONG).show();
 
            // 권한에 대해 설명이 필요한지 체크
            if (ActivityCompat.shouldShowRequestPermissionRationale(this, Manifest.permission.RECEIVE_SMS)) {
                Toast.makeText(this"SMS 권한 설명 필요함.", Toast.LENGTH_LONG).show();
            } else {
                // 권한 부여. 시스템에서 띄어 주기 때문에 시스템쪽으로 요청한다. requestCode 는 임의로 지정험
                ActivityCompat.requestPermissions(thisnew String[] {Manifest.permission.RECEIVE_SMS}, 1);
            }
        }
    }
 
    // 시스템이 권한 부여 과정을 마치고 이를 확인하기 위한 콜백 함수
    @Override
    public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults) {
        switch (requestCode){
            case 1:
                if(grantResults.length > 0){
                    if(grantResults[0== PackageManager.PERMISSION_GRANTED)
                        Toast.makeText(this"SMS 수신 권한을 사용자가 승인함.", Toast.LENGTH_LONG).show();
                    else if(grantResults[0== PackageManager.PERMISSION_DENIED)
                        Toast.makeText(this"SMS 수신 권한을 사용자가 거부함.", Toast.LENGTH_LONG).show();
                }
                else {
                    Toast.makeText(this"SMS 수신 권한을 부여받지 못함.", Toast.LENGTH_LONG).show();
                }
                break;
            default:
                break;
        }
    }
}
cs





출처: https://www.edwith.org/boostcourse-android/lecture/22591/

+ Recent posts