새소식

Daily Record

5월 4주차 학습 내용 정리

 

 

 

Android 

 

1. 레이아웃

 - 레이아웃 : 위젯을 배치하여 안드로이드 화면을 목적에 맞게 배열하도록 함

    (view의 하위 클래스)

 - LinearLayout, RelativeLayout, FrameLayout, TableLayout, GridLayout 등이 있음

 - 레이아웃 내 레이아웃 사용 가능하며 LinearLayout이 가장 많이 쓰임

 - LinearLayout : 레이아웃의 왼쪽 위부터 아래쪽 또는 오른쪽으로 차례로 배치(orientation으로 방향 설정)

 - RelativeLayout : 위젯 자신이 속한 레이아웃의 상하좌우 위치를 지정하여 배치,

    또는 다른 위젯으로부터 상대적인 위치 지정

 - FrameLayout : 위젯을 겹쳐 배치 가능(visibility 설정을 통해 보이고자 하는 위젯 지정 가능)

 - TableLayout : 행과 열의 개수를 지정한 테이블 형태로 위젯 배열(열 확장 불가)

 - GridLayout : 테이블 레이아웃과 비슷하며 행이나 열을 확장하여 다양하게 배치 가능

 

- TableLayout을 활용하여 간단 계산기 앱 만들기

  * activity_main.xml

<TableLayout 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=".MainActivity"
    android:padding="10dp"
    android:stretchColumns="*">

    <TableRow>
        <EditText
            android:id="@+id/edt1"
            android:layout_span="4"
            android:inputType="numberDecimal"/>
    </TableRow>
    <TableRow>
        <EditText
            android:id="@+id/edt2"
            android:layout_span="4"
            android:layout_marginBottom="15dp"
            android:inputType="numberDecimal"/>
    </TableRow>
    <TableRow>
        <Button
            android:id="@+id/btn0"
            android:text="0"
            android:backgroundTint="#E1B6E8"
            android:textColor="@color/black"
            android:layout_marginRight="5dp"/>
        <Button
            android:id="@+id/btn1"
            android:text="1"
            android:backgroundTint="#E1B6E8"
            android:textColor="@color/black"
            android:layout_marginRight="5dp"/>
        <Button
            android:id="@+id/btn2"
            android:text="2"
            android:backgroundTint="#E1B6E8"
            android:textColor="@color/black"
            android:layout_marginRight="5dp"/>
        <Button
            android:id="@+id/btn3"
            android:text="3"
            android:backgroundTint="#E1B6E8"
            android:textColor="@color/black"/>
    </TableRow>
    <TableRow>
        <Button
            android:id="@+id/btn4"
            android:text="4"
            android:backgroundTint="#E1B6E8"
            android:textColor="@color/black"
            android:layout_marginRight="5dp"/>
        <Button
            android:id="@+id/btn5"
            android:text="5"
            android:backgroundTint="#E1B6E8"
            android:textColor="@color/black"
            android:layout_marginRight="5dp"/>
        <Button
            android:id="@+id/btn6"
            android:text="6"
            android:backgroundTint="#E1B6E8"
            android:textColor="@color/black"
            android:layout_marginRight="5dp"/>
        <Button
            android:id="@+id/btn7"
            android:text="7"
            android:backgroundTint="#E1B6E8"
            android:textColor="@color/black"/>
    </TableRow>
    <TableRow>
        <Button
            android:id="@+id/btn8"
            android:text="8"
            android:backgroundTint="#E1B6E8"
            android:textColor="@color/black"
            android:layout_marginRight="5dp"/>
        <Button
            android:id="@+id/btn9"
            android:text="9"
            android:backgroundTint="#E1B6E8"
            android:textColor="@color/black"
            android:layout_marginRight="5dp"/>
        <Button
            android:id="@+id/btnDot"
            android:text="."
            android:backgroundTint="#E1B6E8"
            android:textColor="@color/black"
            android:layout_marginRight="5dp"/>
        <Button
            android:id="@+id/btnC"
            android:text="C"
            android:backgroundTint="#E1B6E8"
            android:textColor="@color/black"
            />
    </TableRow>
    <TableRow>
        <Button
            android:id="@+id/btnAdd"
            android:text="더하기"
            android:backgroundTint="#E1B6E8"
            android:textColor="@color/black"
            android:layout_span="4"
            android:layout_marginTop="20dp"/>
    </TableRow>
    <TableRow>
        <Button
            android:id="@+id/btnSub"
            android:text="빼기"
            android:backgroundTint="#E1B6E8"
            android:textColor="@color/black"
            android:layout_span="4"/>
    </TableRow>
    <TableRow>
        <Button
            android:id="@+id/btnMul"
            android:text="곱하기"
            android:backgroundTint="#E1B6E8"
            android:textColor="@color/black"
            android:layout_span="4"/>
    </TableRow>
    <TableRow>
        <Button
            android:id="@+id/btnDiv"
            android:text="나누기"
            android:backgroundTint="#E1B6E8"
            android:textColor="@color/black"
            android:layout_span="4"/>
    </TableRow>
    <TableRow>
        <TextView
            android:id="@+id/txtResult"
            android:text="계산결과 : 0"
            android:textColor="#DF0101"
            android:textSize="20sp"
            android:layout_marginTop="20dp"
            android:layout_span="4"/>
    </TableRow>
</TableLayout>

 

  * MainActivity.java

public class MainActivity extends AppCompatActivity implements View.OnClickListener {
    EditText edt1, edt2;
    Button[] numButtons = new Button[10];
    Button btnAdd, btnSub, btnMul, btnDiv, btnDot, btnC;
    TextView txtResult;

    View.OnClickListener numButtonListener = new View.OnClickListener() {
        @Override
        public void onClick(View view) {
            Button button = (Button)view;
            String strNum = button.getText().toString();

            EditText edit = null;
            if (edt1.isFocused()) edit = edt1;
            else if (edt2.isFocused()) edit = edt2;

            String eNum = edit.getText().toString();

            if (eNum.equals("0")) edit.setText("");
            edit.append(strNum);

            if (view == btnC) {
                edt1.setText("");
                edt2.setText("");
                return;
            }
        }
    };

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setTitle("계산기");
        setContentView(R.layout.activity_main);
        setUI();
        setListener();
    }

    private void setListener() {
        for (Button aButton : numButtons) {
            aButton.setOnClickListener(numButtonListener);
        }
        btnDot.setOnClickListener(numButtonListener);
        btnC.setOnClickListener(numButtonListener);
        btnAdd.setOnClickListener(this);
        btnSub.setOnClickListener(this);
        btnMul.setOnClickListener(this);
        btnDiv.setOnClickListener(this);
    }

    private void setUI() {
        for (int i = 0; i < numButtons.length; i++) {
            int id = getResources().getIdentifier(
                        "btn" + i, "id", getPackageName());
            Log.d("mytag", String.valueOf(id));
            numButtons[i] = findViewById(id);
        }
        edt1 = findViewById(R.id.edt1);
        edt2 = findViewById(R.id.edt2);
        btnAdd = findViewById(R.id.btnAdd);
        btnSub = findViewById(R.id.btnSub);
        btnMul = findViewById(R.id.btnMul);
        btnDiv = findViewById(R.id.btnDiv);
        btnDot = findViewById(R.id.btnDot);
        btnC = findViewById(R.id.btnC);
        txtResult = findViewById(R.id.txtResult);
    }

    @Override
    public void onClick(View view) {
        String str1 = "";
        String str2 = "";
        double num1 = 0;
        double num2 = 0;
        double result = 0;
        try{
            str1 = edt1.getText().toString();
            str2 = edt2.getText().toString();
            num1 = Double.valueOf(str1);
            num2 = Double.valueOf(str2);
        } catch (Exception e) {
            Toast.makeText(this, "정확한 값을 입력하세요.", Toast.LENGTH_SHORT).show();
            return;
        }

        if (view == btnAdd) {
            result = num1 + num2;
        } else if (view == btnSub) {
            result = num1 - num2;
        } else if (view == btnMul) {
            result = num1 * num2;
        } else if (view == btnDiv) {
            if (num2 == 0) {
                Toast.makeText(
                        this, "0으로 나눌 수 없습니다.", Toast.LENGTH_SHORT).show();
                return;
            }
            result = num1 / num2;
        }
        txtResult.setText("계산결과 : " + result);
    }
}

 

 

2. 다양한 위젯 활용하기

 - 날짜와 시간 관련 위젯 : TimePicker, DatePicker, CalendarView, Chronometer 등

 - TimePicker : 시간 표시 및 조절

 - DatePicker, CalendarView : 날짜 표시 및 조절

 - Chronometer : 타이머 형식의 위젯(시간 측정 시 사용)

 - 날짜 / 시간 선택하여 예약 기능 구현하기

  * activity_main.xml

<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=".MainActivity"
    android:orientation="vertical"
    android:padding="10dp">

    <Chronometer
        android:id="@+id/chronometer"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:format="예약에 걸린 시간  %s"
        android:gravity="center_horizontal"
        android:textSize="22sp"
        android:textStyle="bold"
        android:textColor="#3F51B5"
        android:layout_marginTop="10dp"/>
    <Button
        android:id="@+id/btnStart"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:text="예약 시작"
        android:backgroundTint="#DDDBDB"
        android:textColor="@color/black"
        android:layout_marginTop="10dp"/>
    <RadioGroup
        android:layout_width="wrap_content"
        android:layout_height="wrap_content">
        <RadioButton
            android:id="@+id/rdDate"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:text="날짜 설정 (캘린더뷰)"
            android:checked="true"
            android:layout_marginTop="15dp"/>
        <RadioButton
            android:id="@+id/rdTime"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:text="시간 설정"/>
    </RadioGroup>
    <FrameLayout
        android:layout_width="match_parent"
        android:layout_height="0dp"
        android:layout_weight="1">
        <CalendarView
            android:id="@+id/calendarView"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:layout_gravity="center_vertical"
            />
        <TimePicker
            android:id="@+id/timePicker"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:timePickerMode="spinner"
            android:visibility="invisible"
            android:layout_gravity="center_vertical"/>
    </FrameLayout>
    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:orientation="horizontal"
        android:background="#C5C4C4"
        android:layout_marginBottom="10dp">
        <Button
            android:id="@+id/btnFinish"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:text="예약완료"
            android:backgroundTint="#DDDBDB"
            android:textColor="@color/black"
            android:layout_marginLeft="10dp"/>
        <TextView
            android:id="@+id/txtResult"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_marginLeft="20dp"
            android:text="0000년 00월 00일 00시 00분 예약됨"
            android:textColor="@color/black"/>
    </LinearLayout>
</LinearLayout>

 

  * MainActivity.java

public class MainActivity extends AppCompatActivity implements View.OnClickListener {

    Chronometer chronometer;
    Button btnStart, btnFinish;
    RadioButton rdDate, rdTime;
    CalendarView calendarView;
    TimePicker timePicker;
    TextView txtResult;
    int year, month, day;

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

        setUI();
        setListener();
        setInitDate(); // 날짜 변경이 없으면 오늘 날짜로 설정
    }

    private void setInitDate() {
        Calendar cal = Calendar.getInstance();
        this.year = cal.get(Calendar.YEAR);
        this.month = cal.get(Calendar.MONTH) + 1;
        this.day = cal.get(Calendar.DAY_OF_MONTH);
    }

    private void setListener() {
        btnStart.setOnClickListener(this);
        btnFinish.setOnClickListener(this);
        rdDate.setOnClickListener(this);
        rdTime.setOnClickListener(this);

        calendarView.setOnDateChangeListener(new CalendarView.OnDateChangeListener() {
            @Override
            public void onSelectedDayChange(@NonNull CalendarView calendarView,
                                            int year, int month, int day) {
                MainActivity.this.year = year;
                MainActivity.this.month = month + 1;
                MainActivity.this.day = day;
            }
        });
    }

    private void setUI() {
        chronometer = findViewById(R.id.chronometer);
        btnStart = findViewById(R.id.btnStart);
        btnFinish = findViewById(R.id.btnFinish);
        rdDate = findViewById(R.id.rdDate);
        rdTime = findViewById(R.id.rdTime);
        calendarView = findViewById(R.id.calendarView);
        timePicker = findViewById(R.id.timePicker);
        txtResult = findViewById(R.id.txtResult);
    }

    private String make2digits(int value) {
        if (value < 10) return "0" + value;
        else return value + "";
    }

    private String selectedDate() {
        String result = make2digits(year) + "년 "
                + make2digits(month) + "월 " + make2digits(day) + "일 ";
        return result;
    }

    private String selectedTime() {
        int hour = timePicker.getHour();
        int min = timePicker.getMinute();
        String result = make2digits(hour) + "시 " + make2digits(min) + "분 ";
        return result;
    }

    @Override
    public void onClick(View view) {
        if (view == btnStart) {
            chronometer.setBase(SystemClock.elapsedRealtime()); // 실제 흐른 시간값으로 설정
            chronometer.start();
            chronometer.setTextColor(Color.RED);
        } else if (view == btnFinish) {
            chronometer.stop();
            calendarView.getDate();
            chronometer.setTextColor(Color.BLUE);
            txtResult.setText(selectedDate() + selectedTime() + "예약됨");
        } else if (view == rdDate) {
            calendarView.setVisibility(View.VISIBLE);
            timePicker.setVisibility(View.INVISIBLE);
        } else if (view == rdTime) {
            calendarView.setVisibility(View.INVISIBLE);
            timePicker.setVisibility(View.VISIBLE);
        }
    }
}

 

 - CompoundButton : Button 클래스의 하위 클래스로 체크박스, 라디오버튼, 스위치, 토글버튼의 상위 클래스

 - CheckBox : 클릭할 때마다 체크 또는 언체크로 상태가 변경됨

 - Switch / ToggleButton : 온오프 상태 표시 

 - RadioButton : 여러개 중 하나만 선택해야 하는 경우 사용(RadioGroup과 함께 사용)

  * activity_main.xml

<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=".MainActivity"
    android:orientation="vertical"
    android:padding="20dp">

    <TextView
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="선택을 시작하겠습니까?"
        android:textSize="20dp"/>

    <CheckBox
        android:id="@+id/chkStart"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="시작함"
        android:checked="false"/>

<!--    시작함을 클릭했을 때 보이게 하기-->
    <LinearLayout
        android:id="@+id/innerLayout"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:orientation="vertical"
        android:visibility="invisible">

        <TextView
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:text="좋아하는 동물은?"
            android:textSize="20dp"
            android:layout_marginTop="10dp"/>

        <RadioGroup
            android:id="@+id/rGroup"
            android:layout_width="match_parent"
            android:layout_height="wrap_content" >
            <RadioButton
                android:id="@+id/rdDog"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:text="강아지"
                android:checked="true"/>
            <RadioButton
                android:id="@+id/rdCat"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:text="고양이"/>
            <RadioButton
                android:id="@+id/rdRabbit"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:text="토끼"/>
            <RadioButton
                android:id="@+id/rdFox"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:text="사막여우"/>
        </RadioGroup>

        <Button
            android:id="@+id/btnFinish"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:text="선택완료"
            android:layout_marginTop="10dp"/>

        <ImageView
            android:id="@+id/imgPet"
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            android:scaleType="centerInside"
            android:src="@drawable/dog3"
            android:visibility="invisible"
            android:layout_marginTop="10dp"/>
    </LinearLayout>

</LinearLayout>

 

  * MainActivity.java

public class MainActivity extends AppCompatActivity {

    CheckBox chkStart;
    LinearLayout innerLayout;
    RadioGroup rGroup;
    Button btnFinish;
    ImageView imgPet;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        setTitle("귀여운 동물 보기");
        chkStart = findViewById(R.id.chkStart);
        innerLayout = findViewById(R.id.innerLayout);
        rGroup = findViewById(R.id.rGroup);
        btnFinish = findViewById(R.id.btnFinish);
        imgPet = findViewById(R.id.imgPet);

        chkStart.setOnCheckedChangeListener(new OnCheckedChangeListener() {
            @Override
            public void onCheckedChanged(CompoundButton compoundButton, boolean b) {
                if (b) {
                    innerLayout.setVisibility(View.VISIBLE);
                } else {
                    innerLayout.setVisibility(View.INVISIBLE);
                }
            }
        });

        btnFinish.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View view) {
                int id = rGroup.getCheckedRadioButtonId();
                switch (id) {
                    case R.id.rdDog:
                        imgPet.setImageResource(R.drawable.dog3);
                        break;
                    case R.id.rdCat:
                        imgPet.setImageResource(R.drawable.cat);
                        break;
                    case R.id.rdRabbit:
                        imgPet.setImageResource(R.drawable.rabbit);
                        break;
                    case R.id.rdFox:
                        imgPet.setImageResource(R.drawable.fox2);
                        break;
                }
                imgPet.setVisibility(View.VISIBLE);
            }
        });
    }
}

 

 - ProgressBar, SeekBar, RatingBar : 진행 상태를 표시하는 기능

 - ProgressBar : 작업의 진행 상태를 bar 또는 원 형태로 제공

 - SeekBar : ProgressBar의 하위 클래스로 사용자의 터치로 상태 조절 가능

    ex) 음량 조절, 동영상 재생 위치 지정 등

 - RatingBar : 진행 상태를 별 모양으로 표시

    ex) 별점 평가

 - 활용 연습

  * activity_main.xml

<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=".MainActivity"
    android:orientation="vertical"
    android:padding="20dp">

    <ProgressBar
        android:id="@+id/progressbar"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        style="?android:progressBarStyleHorizontal"
        android:max="100"
        android:progress="50"/>

    <SeekBar
        android:id="@+id/seekbar"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:max="100"
        android:progress="30"
        android:thumb="@mipmap/ic_launcher"/> <!--커서(?) 모양 변경-->

    <RatingBar
        android:id="@+id/ratingBar"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:stepSize="0.5"
        android:rating="2"/> <!-- 사용자와 상호작용. 밑에 두개는 표시용-->
    <RatingBar
        android:id="@+id/ratingBarIndi"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        style="?android:ratingBarStyleIndicator"
        android:rating="5"/>
    <RatingBar
        android:id="@+id/ratingBarSmall"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        style="?android:ratingBarStyleSmall"/>

</LinearLayout>

 

  * MainActivity.java

public class MainActivity extends AppCompatActivity {

    ProgressBar progressBar;
    SeekBar seekbar;
    RatingBar ratingBar, ratingBarIndi, ratingBarSmall;

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

        progressBar = findViewById(R.id.progressbar);
        seekbar = findViewById(R.id.seekbar);
        ratingBar = findViewById(R.id.ratingBar);
        ratingBarIndi = findViewById(R.id.ratingBarIndi);
        ratingBarSmall = findViewById(R.id.ratingBarSmall);
        seekbar.setOnSeekBarChangeListener(new SeekBar.OnSeekBarChangeListener() {
            @Override
            public void onProgressChanged(SeekBar seekBar, int progress, boolean b) { // i 값 : 현재 진행 상태, boolean : 사용자가 변경했는지 여부
                progressBar.setProgress(progress);
            }

            @Override
            public void onStartTrackingTouch(SeekBar seekBar) { // 움직이기 시작할 때 호출
                Log.d("mytag", "seekbar moved");
            }

            @Override
            public void onStopTrackingTouch(SeekBar seekBar) { // 멈출 때 호출
                Log.d("mytag", "seekbar stopped");
            }
        });

        ratingBar.setOnRatingBarChangeListener(new RatingBar.OnRatingBarChangeListener() {
            @Override
            public void onRatingChanged(RatingBar ratingBar, float v, boolean b) {
                ratingBarIndi.setRating(v);
                ratingBarSmall.setRating(v);
            }
        });
    }
}

 

Contents

Copied URL!

Liked this Posting!