sunnnl

pull remote/master to local/sumin

Showing 32 changed files with 399 additions and 53 deletions
......@@ -7,6 +7,7 @@
/.idea/workspace.xml
/.idea/navEditor.xml
/.idea/assetWizardSettings.xml
/.idea/.name
.DS_Store
/build
/captures
......
......@@ -11,21 +11,26 @@
android:label="@string/app_name"
android:roundIcon="@mipmap/ic_launcher_round"
android:supportsRtl="true"
android:theme="@style/AppTheme">
android:networkSecurityConfig="@xml/network_security_config"
android:theme="@style/Theme.AppCompat.NoActionBar">
<activity android:name=".ui.VideoCheckActivity"></activity>
<activity android:name=".ui.DeviceManagerActivity" />
<activity android:name=".ui.RemoteControlRecordActivity" />
<activity
android:name=".ui.SplashActivity"
android:noHistory="true"
android:screenOrientation="fullSensor" />
<activity android:name=".ui.MainActivity">
android:screenOrientation="fullSensor" >
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
<activity android:name=".ui.MainActivity">
</activity>
<activity android:name=".ui.SettingActivity" />
</application>
</manifest>
\ No newline at end of file
......
package com.sunnni.smartdoorlock.api;
import android.os.Handler;
import android.util.Log;
import com.google.gson.JsonArray;
import com.google.gson.JsonElement;
import com.google.gson.JsonObject;
import com.google.gson.JsonParser;
import org.json.JSONObject;
import java.io.BufferedInputStream;
import java.io.BufferedReader;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.OutputStream;
import java.net.HttpURLConnection;
import java.net.URL;
import java.util.Iterator;
import java.util.Set;
public class Api {
public interface Callback {
void callbackMethod(Object obj);
}
static private final String DOMAIN = "gateway.bu.to";
static private String accessToken = null;
static private void callApi(final String method, final String endpoint, final JsonObject params, final Callback callback) {
final Handler handler = new Handler();
new Thread() {
public void run() {
ApiResult apiResult;
try {
String queryString = "";
if(("GET".equals(method) || "DELETE".equals(method)) && params != null) {
Set<String> keys = params.keySet();
Iterator<String> iter = keys.iterator();
while(iter.hasNext()) {
String key = iter.next();
queryString += "&" + key + "=" + params.get(key).getAsString();
}
queryString = "?" + queryString.substring(1);
}
URL url = new URL("http://" + Api.DOMAIN + endpoint + queryString);
HttpURLConnection conn = (HttpURLConnection) url.openConnection();
conn.setRequestMethod(method);
if(accessToken != null) {
conn.setRequestProperty("access_token", accessToken);
}
if("POST".equals(method) || "PUT".equals(method)) {
if(params == null) {
throw new Exception("params is null");
}
OutputStream os = conn.getOutputStream();
os.write(params.toString().getBytes());
os.flush();
os.close();
}
int status = conn.getResponseCode();
Log.d("status", String.valueOf(status));
InputStream is = conn.getErrorStream();
if(is == null)
is = conn.getInputStream();
StringBuilder builder = new StringBuilder();
BufferedReader reader = new BufferedReader(new InputStreamReader(is, "UTF-8"));
String line;
while((line = reader.readLine()) != null) {
builder.append(line);
}
Log.d("http result", builder.toString());
JsonElement jsonElement = JsonParser.parseString(builder.toString());
apiResult = new ApiResult(status < 300, status, jsonElement);
} catch (Exception e) {
e.printStackTrace();
apiResult = new ApiResult(false);
}
final ApiResult finalApiResult = apiResult;
handler.post(new Runnable() {
@Override
public void run() {
callback.callbackMethod(finalApiResult);
}
});
}
}.start();
}
static public void setAccessToken(String accessToken) {
Api.accessToken = accessToken;
}
static public void auth(String doorId, final Callback callback) {
if("123123123".equals(doorId)) {
// 테스트를 위한 super pass
callback.callbackMethod(new Auth(true, "superpass"));
return;
}
JsonObject params = new JsonObject();
params.addProperty("door_id", doorId);
callApi("GET", "/api/auth", params, new Callback() {
@Override
public void callbackMethod(Object obj) {
ApiResult apiResult = (ApiResult) obj;
if(apiResult.isSuccess()) {
JsonObject resp = (JsonObject) apiResult.getData();
if(resp.get("is_available").getAsBoolean()) {
callback.callbackMethod(new Auth(true, resp.get("access_token").getAsString()));
} else {
callback.callbackMethod(new Auth(false));
}
} else {
callback.callbackMethod(null);
}
}
});
}
static public void getSetting(final Callback callback) {
callApi("GET", "/api/setting", null, new Callback() {
@Override
public void callbackMethod(Object obj) {
ApiResult apiResult = (ApiResult) obj;
if(apiResult.isSuccess()) {
JsonObject resp = (JsonObject) apiResult.getData();
callback.callbackMethod(new Setting(resp.get("recording").getAsBoolean()));
} else {
callback.callbackMethod(null);
}
}
});
}
static public void setSetting(Setting setting, final Callback callback) {
JsonObject params = new JsonObject();
params.addProperty("recording", setting.getRecording());
callApi("PUT", "/api/setting", params, new Callback() {
@Override
public void callbackMethod(Object obj) {
ApiResult apiResult = (ApiResult) obj;
if(apiResult.isSuccess()) {
callback.callbackMethod(true);
} else {
callback.callbackMethod(null);
}
}
});
}
}
package com.sunnni.smartdoorlock.api;
import com.google.gson.JsonElement;
import com.google.gson.JsonObject;
public class ApiResult {
public boolean isSuccess() {
return this.success;
}
public Object getData() {
return this.data;
}
public int getStatus() {
return this.status;
}
public ApiResult(boolean success, int status, JsonElement obj) {
this.success = success;
this.data = obj;
this.status = status;
}
public ApiResult(boolean success) {
this.success = success;
this.data = null;
this.status = 999;
}
private boolean success;
private JsonElement data;
private int status;
}
package com.sunnni.smartdoorlock.api;
public class Auth {
private boolean isAvailable;
private String accessToken = null;
public Auth(boolean isAvailable, String accessToken) {
this.isAvailable = isAvailable;
this.accessToken = accessToken;
}
public Auth(boolean isAvailable) {
this.isAvailable = isAvailable;
}
public boolean getIsAvailable() {
return this.isAvailable;
}
public String getAccessToken() {
return this.accessToken;
}
}
package com.sunnni.smartdoorlock.api;
public class Setting {
private boolean recording;
public Setting(boolean recording) {
this.recording = recording;
}
public boolean getRecording() {
return recording;
}
}
package com.sunnni.smartdoorlock.ui;
import android.content.Intent;
import android.content.SharedPreferences;
import android.os.Bundle;
import android.view.View;
import android.widget.Button;
import android.widget.CompoundButton;
import android.widget.Switch;
import android.widget.Toast;
import com.sunnni.smartdoorlock.R;
import com.sunnni.smartdoorlock.api.Api;
import com.sunnni.smartdoorlock.api.Setting;
import androidx.appcompat.app.AppCompatActivity;
public class SettingActivity extends AppCompatActivity {
private Switch swcRecording;
private Button btnLogout;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_setting);
btnLogout = (Button) findViewById(R.id.btn_logout);
btnLogout.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
SharedPreferences pref = getSharedPreferences("gateway", MODE_PRIVATE);
SharedPreferences.Editor editor = pref.edit();
editor.remove("accessToken");
editor.commit();
startActivity(new Intent(SettingActivity.this, SplashActivity.class));
}
});
swcRecording = (Switch) findViewById(R.id.swc_recording);
swcRecording.setOnCheckedChangeListener(new CompoundButton.OnCheckedChangeListener() {
@Override
public void onCheckedChanged(CompoundButton compoundButton, boolean b) {
Api.setSetting(new Setting(true), new Api.Callback() {
@Override
public void callbackMethod(Object obj) {
if(obj == null) {
Toast.makeText(getApplicationContext(),"연결 상태가 불안정합니다.",Toast.LENGTH_SHORT).show();
}
}
});
}
});
Api.getSetting(new Api.Callback() {
@Override
public void callbackMethod(Object obj) {
Setting setting = (Setting) obj;
if(setting == null) {
Toast.makeText(getApplicationContext(),"연결 상태가 불안정합니다.",Toast.LENGTH_SHORT).show();
return;
}
swcRecording.setChecked(setting.getRecording());
}
});
}
}
......@@ -5,6 +5,7 @@ import androidx.constraintlayout.widget.ConstraintLayout;
import android.annotation.SuppressLint;
import android.content.Intent;
import android.content.SharedPreferences;
import android.os.Bundle;
import android.os.Handler;
import android.util.Log;
......@@ -20,6 +21,8 @@ import android.widget.Toast;
import com.google.android.material.textfield.TextInputEditText;
import com.google.android.material.textfield.TextInputLayout;
import com.sunnni.smartdoorlock.R;
import com.sunnni.smartdoorlock.api.Api;
import com.sunnni.smartdoorlock.api.Auth;
public class SplashActivity extends AppCompatActivity {
......@@ -27,6 +30,7 @@ public class SplashActivity extends AppCompatActivity {
private TextInputLayout textInputLayout;
private TextInputEditText edtSuperKey;
private ConstraintLayout btnEnter;
private ImageView imgEnter;
private Animation logoAnimation;
......@@ -38,17 +42,23 @@ public class SplashActivity extends AppCompatActivity {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_splash);
logoContainer = findViewById(R.id.ll_logo);
textInputLayout = findViewById(R.id.til_super_key);
btnEnter = findViewById(R.id.cl_enter);
edtSuperKey = findViewById(R.id.edt_super_key);
logoAnimation = AnimationUtils.loadAnimation(this, R.anim.anim_bottom_up);
test = findViewById(R.id.img_test);
splashLoading();
init();
SharedPreferences pref = getSharedPreferences("gateway", MODE_PRIVATE);
String accessToken = pref.getString("accessToken", "");
if(!"".equals(accessToken)) {
Api.setAccessToken(accessToken);
startActivity(new Intent(SplashActivity.this, MainActivity.class));
} else {
logoContainer = findViewById(R.id.ll_logo);
textInputLayout = findViewById(R.id.til_super_key);
btnEnter = findViewById(R.id.cl_enter);
edtSuperKey = findViewById(R.id.edt_super_key);
imgEnter = findViewById((R.id.img_enter));
logoAnimation = AnimationUtils.loadAnimation(this, R.anim.anim_bottom_up);
splashLoading();
init();
}
}
private void splashLoading() {
......@@ -60,49 +70,41 @@ public class SplashActivity extends AppCompatActivity {
textInputLayout.setVisibility(View.VISIBLE);
btnEnter.setVisibility(View.VISIBLE);
btnEnter.bringToFront();
test.setVisibility(View.VISIBLE);
test.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
Log.d("스플래시", "테스트 버튼");
}
});
btnEnter.setOnClickListener(new View.OnClickListener(){
@Override
public void onClick(View v) {
Log.d("스플래시", "버튼");
}
});
}
}, 2000);
}, 3000);
}
private void init() {
btnEnter.setOnClickListener(new View.OnClickListener() {
imgEnter.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
Log.d("스플래시", "edtSuperKey.toString()");
if(edtSuperKey.toString().isEmpty()){
Log.d("스플래시", "true");
String text = edtSuperKey.getText().toString();
if("".equals(text)){
Toast.makeText(getApplicationContext(),"고유번호를 입력해주세요.",Toast.LENGTH_SHORT).show();
} else {
Intent intent = new Intent(SplashActivity.this, MainActivity.class);
startActivity(intent);
finish();
Api.auth(text, new Api.Callback() {
@Override
public void callbackMethod(Object obj) {
Auth auth = (Auth) obj;
if(auth == null) {
Toast.makeText(getApplicationContext(),"연결 상태가 불안정합니다.",Toast.LENGTH_SHORT).show();
return;
}
if(auth.getIsAvailable()) {
SharedPreferences pref = getSharedPreferences("gateway", MODE_PRIVATE);
SharedPreferences.Editor editor = pref.edit();
editor.putString("accessToken", auth.getAccessToken());
Api.setAccessToken(auth.getAccessToken());
editor.commit();
startActivity(new Intent(SplashActivity.this, MainActivity.class));
} else {
Toast.makeText(getApplicationContext(),"고유번호를 확인해주세요.",Toast.LENGTH_SHORT).show();
}
}
});
}
}
});
logoContainer.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
Log.d("스플래시", "edtSuperKey.toString()");
}
});
}
}
......
......@@ -313,4 +313,12 @@
</androidx.constraintlayout.widget.ConstraintLayout>
<Button
android:id="@+id/btn_setting"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="btn_setting"
tools:layout_editor_absoluteX="166dp"
tools:layout_editor_absoluteY="399dp" />
</androidx.constraintlayout.widget.ConstraintLayout>
\ No newline at end of file
......
<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.ConstraintLayout 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">
<Button
android:id="@+id/btn_logout"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginStart="22dp"
android:layout_marginTop="9dp"
android:text="btn_logout"
app:layout_constraintStart_toStartOf="@+id/swc_recording"
app:layout_constraintTop_toBottomOf="@+id/swc_recording" />
<Switch
android:id="@+id/swc_recording"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginEnd="117dp"
android:layout_marginTop="151dp"
android:text="swc_recording"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintTop_toTopOf="parent" />
</androidx.constraintlayout.widget.ConstraintLayout>
\ No newline at end of file
......@@ -94,6 +94,7 @@
app:layout_constraintTop_toTopOf="parent" />
<ImageView
android:id="@+id/img_enter"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:src="@drawable/baseline_send_white_24"
......
<?xml version="1.0" encoding="utf-8"?>
<adaptive-icon xmlns:android="http://schemas.android.com/apk/res/android">
<background android:drawable="@drawable/ic_launcher_background" />
<foreground android:drawable="@drawable/ic_launcher_foreground" />
<background android:drawable="@drawable/ic_launcher_background"/>
<foreground android:drawable="@mipmap/ic_launcher_foreground"/>
</adaptive-icon>
\ No newline at end of file
......
<?xml version="1.0" encoding="utf-8"?>
<adaptive-icon xmlns:android="http://schemas.android.com/apk/res/android">
<background android:drawable="@drawable/ic_launcher_background" />
<foreground android:drawable="@drawable/ic_launcher_foreground" />
<background android:drawable="@drawable/ic_launcher_background"/>
<foreground android:drawable="@mipmap/ic_launcher_foreground"/>
</adaptive-icon>
\ No newline at end of file
......

3.51 KB | W: | H:

1.9 KB | W: | H:

  • 2-up
  • Swipe
  • Onion skin

5.21 KB | W: | H:

3.68 KB | W: | H:

  • 2-up
  • Swipe
  • Onion skin

2.57 KB | W: | H:

1.35 KB | W: | H:

  • 2-up
  • Swipe
  • Onion skin

3.31 KB | W: | H:

2.3 KB | W: | H:

  • 2-up
  • Swipe
  • Onion skin

4.81 KB | W: | H:

2.79 KB | W: | H:

  • 2-up
  • Swipe
  • Onion skin

7.3 KB | W: | H:

5.2 KB | W: | H:

  • 2-up
  • Swipe
  • Onion skin

7.72 KB | W: | H:

4.23 KB | W: | H:

  • 2-up
  • Swipe
  • Onion skin

11.6 KB | W: | H:

8.14 KB | W: | H:

  • 2-up
  • Swipe
  • Onion skin

10.4 KB | W: | H:

6 KB | W: | H:

  • 2-up
  • Swipe
  • Onion skin

16.2 KB | W: | H:

11.7 KB | W: | H:

  • 2-up
  • Swipe
  • Onion skin
<?xml version="1.0" encoding="utf-8"?>
<network-security-config>
<!--Set application-wide security config using base-config tag.-->
<base-config cleartextTrafficPermitted="true"/>
</network-security-config>
\ No newline at end of file
......@@ -8,7 +8,7 @@ buildscript {
}
dependencies {
classpath 'com.android.tools.build:gradle:3.6.1'
classpath 'com.android.tools.build:gradle:3.6.3'
// NOTE: Do not place your application dependencies here; they belong
......