diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000000000000000000000000000000000000..5edb4eeb072097aee30adb329700b7790c26d756 --- /dev/null +++ b/.gitignore @@ -0,0 +1,10 @@ +*.iml +.gradle +/local.properties +/.idea/libraries +/.idea/modules.xml +/.idea/workspace.xml +.DS_Store +/build +/captures +.externalNativeBuild diff --git a/.idea/caches/build_file_checksums.ser b/.idea/caches/build_file_checksums.ser new file mode 100644 index 0000000000000000000000000000000000000000..88f65c5b439d73573b7ca3ec88c0a07afd7e8a4c Binary files /dev/null and b/.idea/caches/build_file_checksums.ser differ diff --git a/.idea/codeStyles/Project.xml b/.idea/codeStyles/Project.xml new file mode 100644 index 0000000000000000000000000000000000000000..30aa626c23142d59e94cc76327172301f159b618 --- /dev/null +++ b/.idea/codeStyles/Project.xml @@ -0,0 +1,29 @@ +<component name="ProjectCodeStyleConfiguration"> + <code_scheme name="Project" version="173"> + <Objective-C-extensions> + <file> + <option name="com.jetbrains.cidr.lang.util.OCDeclarationKind" value="Import" /> + <option name="com.jetbrains.cidr.lang.util.OCDeclarationKind" value="Macro" /> + <option name="com.jetbrains.cidr.lang.util.OCDeclarationKind" value="Typedef" /> + <option name="com.jetbrains.cidr.lang.util.OCDeclarationKind" value="Enum" /> + <option name="com.jetbrains.cidr.lang.util.OCDeclarationKind" value="Constant" /> + <option name="com.jetbrains.cidr.lang.util.OCDeclarationKind" value="Global" /> + <option name="com.jetbrains.cidr.lang.util.OCDeclarationKind" value="Struct" /> + <option name="com.jetbrains.cidr.lang.util.OCDeclarationKind" value="FunctionPredecl" /> + <option name="com.jetbrains.cidr.lang.util.OCDeclarationKind" value="Function" /> + </file> + <class> + <option name="com.jetbrains.cidr.lang.util.OCDeclarationKind" value="Property" /> + <option name="com.jetbrains.cidr.lang.util.OCDeclarationKind" value="Synthesize" /> + <option name="com.jetbrains.cidr.lang.util.OCDeclarationKind" value="InitMethod" /> + <option name="com.jetbrains.cidr.lang.util.OCDeclarationKind" value="StaticMethod" /> + <option name="com.jetbrains.cidr.lang.util.OCDeclarationKind" value="InstanceMethod" /> + <option name="com.jetbrains.cidr.lang.util.OCDeclarationKind" value="DeallocMethod" /> + </class> + <extensions> + <pair source="cpp" header="h" fileNamingConvention="NONE" /> + <pair source="c" header="h" fileNamingConvention="NONE" /> + </extensions> + </Objective-C-extensions> + </code_scheme> +</component> \ No newline at end of file diff --git a/.idea/gradle.xml b/.idea/gradle.xml new file mode 100644 index 0000000000000000000000000000000000000000..7ac24c777f8adde6bd57c01c1bfa1cf0143f3d77 --- /dev/null +++ b/.idea/gradle.xml @@ -0,0 +1,18 @@ +<?xml version="1.0" encoding="UTF-8"?> +<project version="4"> + <component name="GradleSettings"> + <option name="linkedExternalProjectsSettings"> + <GradleProjectSettings> + <option name="distributionType" value="DEFAULT_WRAPPED" /> + <option name="externalProjectPath" value="$PROJECT_DIR$" /> + <option name="modules"> + <set> + <option value="$PROJECT_DIR$" /> + <option value="$PROJECT_DIR$/app" /> + </set> + </option> + <option name="resolveModulePerSourceSet" value="false" /> + </GradleProjectSettings> + </option> + </component> +</project> \ No newline at end of file diff --git a/.idea/misc.xml b/.idea/misc.xml new file mode 100644 index 0000000000000000000000000000000000000000..99202cc2d646ceed792bbfa449bc73a840cd6f95 --- /dev/null +++ b/.idea/misc.xml @@ -0,0 +1,34 @@ +<?xml version="1.0" encoding="UTF-8"?> +<project version="4"> + <component name="NullableNotNullManager"> + <option name="myDefaultNullable" value="android.support.annotation.Nullable" /> + <option name="myDefaultNotNull" value="android.support.annotation.NonNull" /> + <option name="myNullables"> + <value> + <list size="5"> + <item index="0" class="java.lang.String" itemvalue="org.jetbrains.annotations.Nullable" /> + <item index="1" class="java.lang.String" itemvalue="javax.annotation.Nullable" /> + <item index="2" class="java.lang.String" itemvalue="javax.annotation.CheckForNull" /> + <item index="3" class="java.lang.String" itemvalue="edu.umd.cs.findbugs.annotations.Nullable" /> + <item index="4" class="java.lang.String" itemvalue="android.support.annotation.Nullable" /> + </list> + </value> + </option> + <option name="myNotNulls"> + <value> + <list size="4"> + <item index="0" class="java.lang.String" itemvalue="org.jetbrains.annotations.NotNull" /> + <item index="1" class="java.lang.String" itemvalue="javax.annotation.Nonnull" /> + <item index="2" class="java.lang.String" itemvalue="edu.umd.cs.findbugs.annotations.NonNull" /> + <item index="3" class="java.lang.String" itemvalue="android.support.annotation.NonNull" /> + </list> + </value> + </option> + </component> + <component name="ProjectRootManager" version="2" languageLevel="JDK_1_7" project-jdk-name="1.8" project-jdk-type="JavaSDK"> + <output url="file://$PROJECT_DIR$/build/classes" /> + </component> + <component name="ProjectType"> + <option name="id" value="Android" /> + </component> +</project> \ No newline at end of file diff --git a/.idea/runConfigurations.xml b/.idea/runConfigurations.xml new file mode 100644 index 0000000000000000000000000000000000000000..7f68460d8b38ac04e3a3224d7c79ef719b1991a9 --- /dev/null +++ b/.idea/runConfigurations.xml @@ -0,0 +1,12 @@ +<?xml version="1.0" encoding="UTF-8"?> +<project version="4"> + <component name="RunConfigurationProducerService"> + <option name="ignoredProducers"> + <set> + <option value="org.jetbrains.plugins.gradle.execution.test.runner.AllInPackageGradleConfigurationProducer" /> + <option value="org.jetbrains.plugins.gradle.execution.test.runner.TestClassGradleConfigurationProducer" /> + <option value="org.jetbrains.plugins.gradle.execution.test.runner.TestMethodGradleConfigurationProducer" /> + </set> + </option> + </component> +</project> \ No newline at end of file diff --git a/.idea/vcs.xml b/.idea/vcs.xml new file mode 100644 index 0000000000000000000000000000000000000000..94a25f7f4cb416c083d265558da75d457237d671 --- /dev/null +++ b/.idea/vcs.xml @@ -0,0 +1,6 @@ +<?xml version="1.0" encoding="UTF-8"?> +<project version="4"> + <component name="VcsDirectoryMappings"> + <mapping directory="$PROJECT_DIR$" vcs="Git" /> + </component> +</project> \ No newline at end of file diff --git a/app/.gitignore b/app/.gitignore new file mode 100644 index 0000000000000000000000000000000000000000..796b96d1c402326528b4ba3c12ee9d92d0e212e9 --- /dev/null +++ b/app/.gitignore @@ -0,0 +1 @@ +/build diff --git a/app/build.gradle b/app/build.gradle new file mode 100644 index 0000000000000000000000000000000000000000..83de8bceb3ea9521fd64178aeb4424d542e2edbc --- /dev/null +++ b/app/build.gradle @@ -0,0 +1,35 @@ +apply plugin: 'com.android.application' + +android { + compileSdkVersion 28 + defaultConfig { + applicationId "com.example.tesla.myhomelibrary" + minSdkVersion 26 + targetSdkVersion 28 + versionCode 1 + versionName "1.0" + testInstrumentationRunner "android.support.test.runner.AndroidJUnitRunner" + } + buildTypes { + release { + minifyEnabled false + proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro' + } + } +} + +dependencies { + implementation fileTree(dir: 'libs', include: ['*.jar']) + implementation 'com.android.support:appcompat-v7:28.0.0' + implementation 'com.android.support.constraint:constraint-layout:1.1.3' + implementation 'com.google.firebase:firebase-core:16.0.4' + implementation 'com.google.firebase:firebase-database:16.0.3' + testImplementation 'junit:junit:4.12' + testImplementation 'org.mockito:mockito-core:1.10.19' + androidTestImplementation 'com.android.support.test:runner:1.0.2' + implementation 'com.android.support:support-annotations:28.0.0' + androidTestImplementation 'com.android.support.test.espresso:espresso-core:3.0.2' + androidTestImplementation 'com.android.support.test:rules:1.0.2' +} + +apply plugin: 'com.google.gms.google-services' \ No newline at end of file diff --git a/app/google-services.json b/app/google-services.json new file mode 100644 index 0000000000000000000000000000000000000000..989cc27954abb032605e20d34334d419437250f9 --- /dev/null +++ b/app/google-services.json @@ -0,0 +1,42 @@ +{ + "project_info": { + "project_number": "29102789333", + "firebase_url": "https://myhomelibrary-838ac.firebaseio.com", + "project_id": "myhomelibrary-838ac", + "storage_bucket": "myhomelibrary-838ac.appspot.com" + }, + "client": [ + { + "client_info": { + "mobilesdk_app_id": "1:29102789333:android:7f079efdba385b39", + "android_client_info": { + "package_name": "com.example.tesla.myhomelibrary" + } + }, + "oauth_client": [ + { + "client_id": "29102789333-b0jc7do4lghpm5oo3panm8rgcqrco9at.apps.googleusercontent.com", + "client_type": 3 + } + ], + "api_key": [ + { + "current_key": "AIzaSyCYVtTDVxur-80vXj37SRHPAvhQeSX8L6U" + } + ], + "services": { + "analytics_service": { + "status": 1 + }, + "appinvite_service": { + "status": 1, + "other_platform_oauth_client": [] + }, + "ads_service": { + "status": 2 + } + } + } + ], + "configuration_version": "1" +} \ No newline at end of file diff --git a/app/proguard-rules.pro b/app/proguard-rules.pro new file mode 100644 index 0000000000000000000000000000000000000000..f1b424510da51fd82143bc74a0a801ae5a1e2fcd --- /dev/null +++ b/app/proguard-rules.pro @@ -0,0 +1,21 @@ +# Add project specific ProGuard rules here. +# You can control the set of applied configuration files using the +# proguardFiles setting in build.gradle. +# +# For more details, see +# http://developer.android.com/guide/developing/tools/proguard.html + +# If your project uses WebView with JS, uncomment the following +# and specify the fully qualified class name to the JavaScript interface +# class: +#-keepclassmembers class fqcn.of.javascript.interface.for.webview { +# public *; +#} + +# Uncomment this to preserve the line number information for +# debugging stack traces. +#-keepattributes SourceFile,LineNumberTable + +# If you keep the line number information, uncomment this to +# hide the original source file name. +#-renamesourcefileattribute SourceFile diff --git a/app/src/androidTest/java/com/example/tesla/myhomelibrary/MainActivityTest.java b/app/src/androidTest/java/com/example/tesla/myhomelibrary/MainActivityTest.java new file mode 100644 index 0000000000000000000000000000000000000000..d9b3ad79105569ddf3111d0af83ab8f161be805f --- /dev/null +++ b/app/src/androidTest/java/com/example/tesla/myhomelibrary/MainActivityTest.java @@ -0,0 +1,97 @@ +package com.example.tesla.myhomelibrary; + + +import android.support.test.espresso.ViewInteraction; +import android.support.test.filters.LargeTest; +import android.support.test.rule.ActivityTestRule; +import android.support.test.runner.AndroidJUnit4; +import android.view.View; +import android.view.ViewGroup; +import android.view.ViewParent; + +import org.hamcrest.Description; +import org.hamcrest.Matcher; +import org.hamcrest.TypeSafeMatcher; +import org.junit.Rule; +import org.junit.Test; +import org.junit.runner.RunWith; + +import static android.support.test.espresso.Espresso.onView; +import static android.support.test.espresso.assertion.ViewAssertions.matches; +import static android.support.test.espresso.matcher.ViewMatchers.isDisplayed; +import static android.support.test.espresso.matcher.ViewMatchers.withId; +import static android.support.test.espresso.matcher.ViewMatchers.withText; +import static org.hamcrest.Matchers.allOf; + +@LargeTest +@RunWith(AndroidJUnit4.class) +public class MainActivityTest { + + @Rule + public ActivityTestRule<MainActivity> mActivityTestRule = new ActivityTestRule<>(MainActivity.class); + + @Test + public void mainActivityTest() { + // Added a sleep statement to match the app's execution delay. + // The recommended way to handle such scenarios is to use Espresso idling resources: + // https://google.github.io/android-testing-support-library/docs/espresso/idling-resource/index.html + try { + Thread.sleep(30000); + } catch (InterruptedException e) { + e.printStackTrace(); + } + + + ViewInteraction textView = onView( + allOf(withId(R.id.textView), withText("Authors"), + childAtPosition( + allOf(withId(R.id.activity_main), + childAtPosition( + withId(android.R.id.content), + 0)), + 3), + isDisplayed())); + textView.check(matches(withText("Authors"))); + + ViewInteraction button = onView( + allOf(withId(R.id.buttonAddAuthor), + childAtPosition( + allOf(withId(R.id.activity_main), + childAtPosition( + withId(android.R.id.content), + 0)), + 2), + isDisplayed())); + button.check(matches(isDisplayed())); + + ViewInteraction textView2 = onView( + allOf(withId(R.id.textViewName), withText("Ernesto Hemingway"), + childAtPosition( + childAtPosition( + withId(R.id.listViewAuthors), + 0), + 0), + isDisplayed())); + textView2.check(matches(withText("Ernesto Hemingway"))); + + } + + private static Matcher<View> childAtPosition( + final Matcher<View> parentMatcher, final int position) { + + return new TypeSafeMatcher<View>() { + @Override + public void describeTo(Description description) { + description.appendText("Child at position " + position + " in parent "); + parentMatcher.describeTo(description); + } + + @Override + public boolean matchesSafely(View view) { + ViewParent parent = view.getParent(); + return parent instanceof ViewGroup && parentMatcher.matches(parent) + && view.equals(((ViewGroup) parent).getChildAt(position)); + } + }; + } +} diff --git a/app/src/main/AndroidManifest.xml b/app/src/main/AndroidManifest.xml new file mode 100644 index 0000000000000000000000000000000000000000..88defcde1700f11957b8f6bf5ec77bd98127c3f1 --- /dev/null +++ b/app/src/main/AndroidManifest.xml @@ -0,0 +1,22 @@ +<?xml version="1.0" encoding="utf-8"?> +<manifest xmlns:android="http://schemas.android.com/apk/res/android" + package="com.example.tesla.myhomelibrary"> + + <application + android:allowBackup="true" + android:icon="@mipmap/ic_launcher" + android:label="@string/app_name" + android:roundIcon="@mipmap/ic_launcher_round" + android:supportsRtl="true" + android:theme="@style/AppTheme"> + <activity android:name=".MainActivity"> + <intent-filter> + <action android:name="android.intent.action.MAIN" /> + + <category android:name="android.intent.category.LAUNCHER" /> + </intent-filter> + </activity> + <activity android:name=".AuthorActivity"></activity> + </application> + +</manifest> \ No newline at end of file diff --git a/app/src/main/java/com/example/tesla/myhomelibrary/Author.java b/app/src/main/java/com/example/tesla/myhomelibrary/Author.java new file mode 100644 index 0000000000000000000000000000000000000000..fd02dcacdaf4f0dd5e61b3ff69f328fec5a058b7 --- /dev/null +++ b/app/src/main/java/com/example/tesla/myhomelibrary/Author.java @@ -0,0 +1,30 @@ +package com.example.tesla.myhomelibrary; + +import com.google.firebase.database.IgnoreExtraProperties; + +@IgnoreExtraProperties +public class Author { + private String authorId; + private String authorName; + private String authorCountry; + + public Author(){ + //this constructor is required + } + + public Author(String authorId, String authorName, String authorCountry) { + this.authorId = authorId; + this.authorName = authorName; + this.authorCountry = authorCountry; + } + + public String getAuthorId() { + return authorId; + } + + public String getAuthorName() { return authorName; } + + public String getAuthorCountry() { + return authorCountry; + } +} \ No newline at end of file diff --git a/app/src/main/java/com/example/tesla/myhomelibrary/AuthorActivity.java b/app/src/main/java/com/example/tesla/myhomelibrary/AuthorActivity.java new file mode 100644 index 0000000000000000000000000000000000000000..7705aa86058d94c0241fc6b30d6f53ba09200462 --- /dev/null +++ b/app/src/main/java/com/example/tesla/myhomelibrary/AuthorActivity.java @@ -0,0 +1,122 @@ +package com.example.tesla.myhomelibrary; + +import android.content.Intent; +import android.support.v7.app.AppCompatActivity; +import android.os.Bundle; +import android.text.TextUtils; +import android.view.View; +import android.widget.Button; +import android.widget.EditText; +import android.widget.ListView; +import android.widget.SeekBar; +import android.widget.TextView; +import android.widget.Toast; + +import com.google.firebase.database.DataSnapshot; +import com.google.firebase.database.DatabaseError; +import com.google.firebase.database.DatabaseReference; +import com.google.firebase.database.FirebaseDatabase; +import com.google.firebase.database.ValueEventListener; + +import java.util.ArrayList; +import java.util.List; + +public class AuthorActivity extends AppCompatActivity { + Button buttonAddTitle; + EditText editTextTitleName; + SeekBar seekBarRating; + TextView textViewRating, textViewAuthor; + ListView listViewTitles; + + DatabaseReference databaseTitles; + + List<Title> titles; + + @Override + protected void onCreate(Bundle savedInstanceState) { + super.onCreate(savedInstanceState); + setContentView(R.layout.activity_author); + + Intent intent = getIntent(); + + /* + * this line is important + * this time we are not getting the reference of a direct node + * but inside the node track we are creating a new child with the author id + * and inside that node we will store all the titles with unique ids + * */ + databaseTitles = FirebaseDatabase.getInstance().getReference("titles").child(intent.getStringExtra(MainActivity.AUTHOR_ID)); + + buttonAddTitle = (Button) findViewById(R.id.buttonAddTitle); + editTextTitleName = (EditText) findViewById(R.id.editTextName); + seekBarRating = (SeekBar) findViewById(R.id.seekBarRating); + textViewRating = (TextView) findViewById(R.id.textViewRating); + textViewAuthor = (TextView) findViewById(R.id.textViewAuthor); + listViewTitles = (ListView) findViewById(R.id.listViewTitles); + + titles = new ArrayList<Title>(); + + textViewAuthor.setText(intent.getStringExtra(MainActivity.AUTHOR_NAME)); + + seekBarRating.setOnSeekBarChangeListener(new SeekBar.OnSeekBarChangeListener() { + @Override + public void onProgressChanged(SeekBar seekBar, int i, boolean b) { + textViewRating.setText(String.valueOf(i)); + } + + @Override + public void onStartTrackingTouch(SeekBar seekBar) { + + } + + @Override + public void onStopTrackingTouch(SeekBar seekBar) { + + } + }); + + buttonAddTitle.setOnClickListener(new View.OnClickListener() { + @Override + public void onClick(View view) { + saveTitle(); + } + }); + } + + @Override + protected void onStart() { + super.onStart(); + + databaseTitles.addValueEventListener(new ValueEventListener() { + @Override + public void onDataChange(DataSnapshot dataSnapshot) { + titles.clear(); + for (DataSnapshot postSnapshot : dataSnapshot.getChildren()) { + Title title = postSnapshot.getValue(Title.class); + titles.add(title); + } + TitleList titleListAdapter = new TitleList(AuthorActivity.this, titles); + listViewTitles.setAdapter(titleListAdapter); + } + + @Override + public void onCancelled(DatabaseError databaseError) { + + } + }); + } + + private void saveTitle() { + String titleName = editTextTitleName.getText().toString().trim(); + int rating = seekBarRating.getProgress(); + if (!TextUtils.isEmpty(titleName)) { + String id = databaseTitles.push().getKey(); + Title title = new Title(id, titleName, rating); + databaseTitles.child(id).setValue(title); + Toast.makeText(this, "Title saved", Toast.LENGTH_LONG).show(); + editTextTitleName.setText(""); + } else { + Toast.makeText(this, "Please enter title name", Toast.LENGTH_LONG).show(); + } + } +} diff --git a/app/src/main/java/com/example/tesla/myhomelibrary/AuthorList.java b/app/src/main/java/com/example/tesla/myhomelibrary/AuthorList.java new file mode 100644 index 0000000000000000000000000000000000000000..32ce1ea7fd016eaf311ec51d9615ca1e0d0d1a24 --- /dev/null +++ b/app/src/main/java/com/example/tesla/myhomelibrary/AuthorList.java @@ -0,0 +1,39 @@ +package com.example.tesla.myhomelibrary; + +import android.app.Activity; +import android.support.annotation.NonNull; +import android.view.LayoutInflater; +import android.view.View; +import android.view.ViewGroup; +import android.widget.ArrayAdapter; +import android.widget.TextView; + +import java.util.List; + + +public class AuthorList extends ArrayAdapter<Author> { + private Activity context; + List<Author> authors; + + public AuthorList(Activity context, List<Author> authors) { + super(context, R.layout.layout_author_list, authors); + this.context = context; + this.authors = authors; + } + + + @Override + public View getView(int position, View convertView, ViewGroup parent) { + LayoutInflater inflater = context.getLayoutInflater(); + View listViewItem = inflater.inflate(R.layout.layout_author_list, null, true); + + TextView textViewName = (TextView) listViewItem.findViewById(R.id.textViewName); + TextView textViewCountry = (TextView) listViewItem.findViewById(R.id.textViewCountry); + + Author author = authors.get(position); + textViewName.setText(author.getAuthorName()); + textViewCountry.setText(author.getAuthorCountry()); + + return listViewItem; + } +} \ No newline at end of file diff --git a/app/src/main/java/com/example/tesla/myhomelibrary/MainActivity.java b/app/src/main/java/com/example/tesla/myhomelibrary/MainActivity.java new file mode 100644 index 0000000000000000000000000000000000000000..d505991fbdbcd2f865a17e05bb2726f0103e5a06 --- /dev/null +++ b/app/src/main/java/com/example/tesla/myhomelibrary/MainActivity.java @@ -0,0 +1,236 @@ +package com.example.tesla.myhomelibrary; + +import android.content.Intent; +import android.support.v7.app.AlertDialog; +import android.support.v7.app.AppCompatActivity; +import android.os.Bundle; +import android.text.TextUtils; +import android.view.LayoutInflater; +import android.view.View; +import android.widget.AdapterView; +import android.widget.ArrayAdapter; +import android.widget.Button; +import android.widget.EditText; +import android.widget.ListView; +import android.widget.Spinner; +import android.widget.Toast; + +import com.google.firebase.database.DataSnapshot; +import com.google.firebase.database.DatabaseError; +import com.google.firebase.database.DatabaseReference; +import com.google.firebase.database.FirebaseDatabase; +import com.google.firebase.database.ValueEventListener; + +import java.util.ArrayList; +import java.util.List; + +public class MainActivity extends AppCompatActivity { + public static final String AUTHOR_NAME = "com.example.tesla.myhomelibrary.authorname"; + public static final String AUTHOR_ID = "com.example.tesla.myhomelibrary.authorid"; + + EditText editTextName; + Spinner spinnerCountry; + Button buttonAddAuthor; + ListView listViewAuthors; + + //a list to store all the artist from firebase database + List<Author> authors; + + //our database reference object + DatabaseReference databaseAuthors; + + @Override + protected void onCreate(Bundle savedInstanceState) { + super.onCreate(savedInstanceState); + setContentView(R.layout.activity_main); + + //getting the reference of artists node + databaseAuthors = FirebaseDatabase.getInstance().getReference("authors"); + + //getting views + editTextName = (EditText) findViewById(R.id.editTextName); + spinnerCountry = (Spinner) findViewById(R.id.spinnerCountry); + listViewAuthors = (ListView) findViewById(R.id.listViewAuthors); + + buttonAddAuthor = (Button) findViewById(R.id.buttonAddAuthor); + + //list to store authors + authors = new ArrayList<>(); + + + //adding an onclicklistener to button + buttonAddAuthor.setOnClickListener(new View.OnClickListener() { + @Override + public void onClick(View view) { + //calling the method addArtist() + //the method is defined below + //this method is actually performing the write operation + addAuthor(); + } + }); + + //attaching listener to listview + listViewAuthors.setOnItemClickListener(new AdapterView.OnItemClickListener() { + @Override + public void onItemClick(AdapterView<?> adapterView, View view, int i, long l) { + //getting the selected artist + Author author = authors.get(i); + + //creating an intent + Intent intent = new Intent(getApplicationContext(), AuthorActivity.class); + + //putting artist name and id to intent + intent.putExtra(AUTHOR_ID, author.getAuthorId()); + intent.putExtra(AUTHOR_NAME, author.getAuthorName()); + + //starting the activity with intent + startActivity(intent); + } + }); + + listViewAuthors.setOnItemLongClickListener(new AdapterView.OnItemLongClickListener() { + @Override + public boolean onItemLongClick(AdapterView<?> adapterView, View view, int i, long l) { + Author author = authors.get(i); + showUpdateDeleteDialog(author.getAuthorId(), author.getAuthorName()); + return true; + } + }); + } + + private void showUpdateDeleteDialog(final String authorId, String authorName) { + + AlertDialog.Builder dialogBuilder = new AlertDialog.Builder(this); + LayoutInflater inflater = getLayoutInflater(); + final View dialogView = inflater.inflate(R.layout.update_dialog, null); + dialogBuilder.setView(dialogView); + + final EditText editTextName = (EditText) dialogView.findViewById(R.id.editTextName); + final Spinner spinnerCountry = (Spinner) dialogView.findViewById(R.id.spinnerCountry); + final Button buttonUpdate = (Button) dialogView.findViewById(R.id.buttonUpdateAuthor); + final Button buttonDelete = (Button) dialogView.findViewById(R.id.buttonDeleteAuthor); + + dialogBuilder.setTitle(authorName); + final AlertDialog b = dialogBuilder.create(); + b.show(); + + + buttonUpdate.setOnClickListener(new View.OnClickListener() { + @Override + public void onClick(View view) { + String name = editTextName.getText().toString().trim(); + String country = spinnerCountry.getSelectedItem().toString(); + if (!TextUtils.isEmpty(name)) { + updateAuthor(authorId, name, country); + b.dismiss(); + } + } + }); + + + buttonDelete.setOnClickListener(new View.OnClickListener() { + @Override + public void onClick(View view) { + + deleteAuthor(authorId); + b.dismiss(); + } + }); + } + + + private boolean updateAuthor(String id, String name, String country) { + //getting the specified author reference + DatabaseReference dR = FirebaseDatabase.getInstance().getReference("authors").child(id); + + //updating author + Author author = new Author(id, name, country); + dR.setValue(author); + Toast.makeText(getApplicationContext(), "Author Updated", Toast.LENGTH_LONG).show(); + return true; + } + + private boolean deleteAuthor(String id) { + //getting the specified author reference + DatabaseReference dR = FirebaseDatabase.getInstance().getReference("authors").child(id); + + //removing author + dR.removeValue(); + + //getting the titles reference for the specified author + DatabaseReference drTitles = FirebaseDatabase.getInstance().getReference("titles").child(id); + + //removing all titles + drTitles.removeValue(); + Toast.makeText(getApplicationContext(), "Author Deleted", Toast.LENGTH_LONG).show(); + + return true; + } + + @Override + protected void onStart() { + super.onStart(); + //attaching value event listener + databaseAuthors.addValueEventListener(new ValueEventListener() { + @Override + public void onDataChange(DataSnapshot dataSnapshot) { + + //clearing the previous artist list + authors.clear(); + + //iterating through all the nodes + for (DataSnapshot postSnapshot : dataSnapshot.getChildren()) { + //getting artist + Author author = postSnapshot.getValue(Author.class); + //adding author to the list + authors.add(author); + } + + //creating adapter + AuthorList authorAdapter = new AuthorList(MainActivity.this, authors); + //attaching adapter to the listview + listViewAuthors.setAdapter(authorAdapter); + } + + @Override + public void onCancelled(DatabaseError databaseError) { + + } + }); + } + + + /* + * This method is saving a new author to the + * Firebase Realtime Database + * */ + private void addAuthor() { + //getting the values to save + String name = editTextName.getText().toString().trim(); + String country = spinnerCountry.getSelectedItem().toString(); + + //checking if the value is provided + if (!TextUtils.isEmpty(name)) { + + //getting a unique id using push().getKey() method + //it will create a unique id and we will use it as the Primary Key for our Author + String id = databaseAuthors.push().getKey(); + + //creating an Author Object + Author author = new Author(id, name, country); + + //Saving the Author + databaseAuthors.child(id).setValue(author); + + //setting edittext to blank again + editTextName.setText(""); + + //displaying a success toast + Toast.makeText(this, "Author added", Toast.LENGTH_LONG).show(); + } else { + //if the value is not given displaying a toast + Toast.makeText(this, "Please enter a name", Toast.LENGTH_LONG).show(); + } + } +} + diff --git a/app/src/main/java/com/example/tesla/myhomelibrary/Title.java b/app/src/main/java/com/example/tesla/myhomelibrary/Title.java new file mode 100644 index 0000000000000000000000000000000000000000..78ae7c51a914632e1514f301c0be17afb05b1141 --- /dev/null +++ b/app/src/main/java/com/example/tesla/myhomelibrary/Title.java @@ -0,0 +1,28 @@ +package com.example.tesla.myhomelibrary; + +import com.google.firebase.database.IgnoreExtraProperties; + +@IgnoreExtraProperties +public class Title { + private String id; + private String titleName; + private int rating; + + public Title() { + + } + + public Title(String id, String titleName, int rating) { + this.titleName = titleName; + this.rating = rating; + this.id = id; + } + + public String getTitleName() { + return titleName; + } + + public int getRating() { + return rating; + } +} diff --git a/app/src/main/java/com/example/tesla/myhomelibrary/TitleList.java b/app/src/main/java/com/example/tesla/myhomelibrary/TitleList.java new file mode 100644 index 0000000000000000000000000000000000000000..a919804f0f4076de7740882845927401448f63eb --- /dev/null +++ b/app/src/main/java/com/example/tesla/myhomelibrary/TitleList.java @@ -0,0 +1,37 @@ +package com.example.tesla.myhomelibrary; + +import android.app.Activity; +import android.view.LayoutInflater; +import android.view.View; +import android.view.ViewGroup; +import android.widget.ArrayAdapter; +import android.widget.TextView; + +import java.util.List; + +public class TitleList extends ArrayAdapter<Title> { + private Activity context; + List<Title> titles; + + public TitleList(Activity context, List<Title> titles) { + super(context, R.layout.layout_author_list, titles); + this.context = context; + this.titles = titles; + } + + + @Override + public View getView(int position, View convertView, ViewGroup parent) { + LayoutInflater inflater = context.getLayoutInflater(); + View listViewItem = inflater.inflate(R.layout.layout_author_list, null, true); + + TextView textViewName = (TextView) listViewItem.findViewById(R.id.textViewName); + TextView textViewRating = (TextView) listViewItem.findViewById(R.id.textViewCountry); + + Title title = titles.get(position); + textViewName.setText(title.getTitleName()); + textViewRating.setText(String.valueOf(title.getRating())); + + return listViewItem; + } +} diff --git a/app/src/main/res/drawable-v24/ic_launcher_foreground.xml b/app/src/main/res/drawable-v24/ic_launcher_foreground.xml new file mode 100644 index 0000000000000000000000000000000000000000..c7bd21dbd86990cde81fea8abd3bf904b4546749 --- /dev/null +++ b/app/src/main/res/drawable-v24/ic_launcher_foreground.xml @@ -0,0 +1,34 @@ +<vector xmlns:android="http://schemas.android.com/apk/res/android" + xmlns:aapt="http://schemas.android.com/aapt" + android:width="108dp" + android:height="108dp" + android:viewportHeight="108" + android:viewportWidth="108"> + <path + android:fillType="evenOdd" + android:pathData="M32,64C32,64 38.39,52.99 44.13,50.95C51.37,48.37 70.14,49.57 70.14,49.57L108.26,87.69L108,109.01L75.97,107.97L32,64Z" + android:strokeColor="#00000000" + android:strokeWidth="1"> + <aapt:attr name="android:fillColor"> + <gradient + android:endX="78.5885" + android:endY="90.9159" + android:startX="48.7653" + android:startY="61.0927" + android:type="linear"> + <item + android:color="#44000000" + android:offset="0.0" /> + <item + android:color="#00000000" + android:offset="1.0" /> + </gradient> + </aapt:attr> + </path> + <path + android:fillColor="#FFFFFF" + android:fillType="nonZero" + android:pathData="M66.94,46.02L66.94,46.02C72.44,50.07 76,56.61 76,64L32,64C32,56.61 35.56,50.11 40.98,46.06L36.18,41.19C35.45,40.45 35.45,39.3 36.18,38.56C36.91,37.81 38.05,37.81 38.78,38.56L44.25,44.05C47.18,42.57 50.48,41.71 54,41.71C57.48,41.71 60.78,42.57 63.68,44.05L69.11,38.56C69.84,37.81 70.98,37.81 71.71,38.56C72.44,39.3 72.44,40.45 71.71,41.19L66.94,46.02ZM62.94,56.92C64.08,56.92 65,56.01 65,54.88C65,53.76 64.08,52.85 62.94,52.85C61.8,52.85 60.88,53.76 60.88,54.88C60.88,56.01 61.8,56.92 62.94,56.92ZM45.06,56.92C46.2,56.92 47.13,56.01 47.13,54.88C47.13,53.76 46.2,52.85 45.06,52.85C43.92,52.85 43,53.76 43,54.88C43,56.01 43.92,56.92 45.06,56.92Z" + android:strokeColor="#00000000" + android:strokeWidth="1" /> +</vector> diff --git a/app/src/main/res/drawable/ic_launcher_background.xml b/app/src/main/res/drawable/ic_launcher_background.xml new file mode 100644 index 0000000000000000000000000000000000000000..d5fccc538c179838bfdce779c26eebb4fa0b5ce9 --- /dev/null +++ b/app/src/main/res/drawable/ic_launcher_background.xml @@ -0,0 +1,170 @@ +<?xml version="1.0" encoding="utf-8"?> +<vector xmlns:android="http://schemas.android.com/apk/res/android" + android:width="108dp" + android:height="108dp" + android:viewportHeight="108" + android:viewportWidth="108"> + <path + android:fillColor="#26A69A" + android:pathData="M0,0h108v108h-108z" /> + <path + android:fillColor="#00000000" + android:pathData="M9,0L9,108" + android:strokeColor="#33FFFFFF" + android:strokeWidth="0.8" /> + <path + android:fillColor="#00000000" + android:pathData="M19,0L19,108" + android:strokeColor="#33FFFFFF" + android:strokeWidth="0.8" /> + <path + android:fillColor="#00000000" + android:pathData="M29,0L29,108" + android:strokeColor="#33FFFFFF" + android:strokeWidth="0.8" /> + <path + android:fillColor="#00000000" + android:pathData="M39,0L39,108" + android:strokeColor="#33FFFFFF" + android:strokeWidth="0.8" /> + <path + android:fillColor="#00000000" + android:pathData="M49,0L49,108" + android:strokeColor="#33FFFFFF" + android:strokeWidth="0.8" /> + <path + android:fillColor="#00000000" + android:pathData="M59,0L59,108" + android:strokeColor="#33FFFFFF" + android:strokeWidth="0.8" /> + <path + android:fillColor="#00000000" + android:pathData="M69,0L69,108" + android:strokeColor="#33FFFFFF" + android:strokeWidth="0.8" /> + <path + android:fillColor="#00000000" + android:pathData="M79,0L79,108" + android:strokeColor="#33FFFFFF" + android:strokeWidth="0.8" /> + <path + android:fillColor="#00000000" + android:pathData="M89,0L89,108" + android:strokeColor="#33FFFFFF" + android:strokeWidth="0.8" /> + <path + android:fillColor="#00000000" + android:pathData="M99,0L99,108" + android:strokeColor="#33FFFFFF" + android:strokeWidth="0.8" /> + <path + android:fillColor="#00000000" + android:pathData="M0,9L108,9" + android:strokeColor="#33FFFFFF" + android:strokeWidth="0.8" /> + <path + android:fillColor="#00000000" + android:pathData="M0,19L108,19" + android:strokeColor="#33FFFFFF" + android:strokeWidth="0.8" /> + <path + android:fillColor="#00000000" + android:pathData="M0,29L108,29" + android:strokeColor="#33FFFFFF" + android:strokeWidth="0.8" /> + <path + android:fillColor="#00000000" + android:pathData="M0,39L108,39" + android:strokeColor="#33FFFFFF" + android:strokeWidth="0.8" /> + <path + android:fillColor="#00000000" + android:pathData="M0,49L108,49" + android:strokeColor="#33FFFFFF" + android:strokeWidth="0.8" /> + <path + android:fillColor="#00000000" + android:pathData="M0,59L108,59" + android:strokeColor="#33FFFFFF" + android:strokeWidth="0.8" /> + <path + android:fillColor="#00000000" + android:pathData="M0,69L108,69" + android:strokeColor="#33FFFFFF" + android:strokeWidth="0.8" /> + <path + android:fillColor="#00000000" + android:pathData="M0,79L108,79" + android:strokeColor="#33FFFFFF" + android:strokeWidth="0.8" /> + <path + android:fillColor="#00000000" + android:pathData="M0,89L108,89" + android:strokeColor="#33FFFFFF" + android:strokeWidth="0.8" /> + <path + android:fillColor="#00000000" + android:pathData="M0,99L108,99" + android:strokeColor="#33FFFFFF" + android:strokeWidth="0.8" /> + <path + android:fillColor="#00000000" + android:pathData="M19,29L89,29" + android:strokeColor="#33FFFFFF" + android:strokeWidth="0.8" /> + <path + android:fillColor="#00000000" + android:pathData="M19,39L89,39" + android:strokeColor="#33FFFFFF" + android:strokeWidth="0.8" /> + <path + android:fillColor="#00000000" + android:pathData="M19,49L89,49" + android:strokeColor="#33FFFFFF" + android:strokeWidth="0.8" /> + <path + android:fillColor="#00000000" + android:pathData="M19,59L89,59" + android:strokeColor="#33FFFFFF" + android:strokeWidth="0.8" /> + <path + android:fillColor="#00000000" + android:pathData="M19,69L89,69" + android:strokeColor="#33FFFFFF" + android:strokeWidth="0.8" /> + <path + android:fillColor="#00000000" + android:pathData="M19,79L89,79" + android:strokeColor="#33FFFFFF" + android:strokeWidth="0.8" /> + <path + android:fillColor="#00000000" + android:pathData="M29,19L29,89" + android:strokeColor="#33FFFFFF" + android:strokeWidth="0.8" /> + <path + android:fillColor="#00000000" + android:pathData="M39,19L39,89" + android:strokeColor="#33FFFFFF" + android:strokeWidth="0.8" /> + <path + android:fillColor="#00000000" + android:pathData="M49,19L49,89" + android:strokeColor="#33FFFFFF" + android:strokeWidth="0.8" /> + <path + android:fillColor="#00000000" + android:pathData="M59,19L59,89" + android:strokeColor="#33FFFFFF" + android:strokeWidth="0.8" /> + <path + android:fillColor="#00000000" + android:pathData="M69,19L69,89" + android:strokeColor="#33FFFFFF" + android:strokeWidth="0.8" /> + <path + android:fillColor="#00000000" + android:pathData="M79,19L79,89" + android:strokeColor="#33FFFFFF" + android:strokeWidth="0.8" /> +</vector> diff --git a/app/src/main/res/layout/activity_author.xml b/app/src/main/res/layout/activity_author.xml new file mode 100644 index 0000000000000000000000000000000000000000..18b3f85ef375342afa5b90b10d7b1342a8a1efe9 --- /dev/null +++ b/app/src/main/res/layout/activity_author.xml @@ -0,0 +1,75 @@ +<?xml version="1.0" encoding="utf-8"?> +<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" + xmlns:tools="http://schemas.android.com/tools" + android:id="@+id/activity_artist" + android:layout_width="match_parent" + android:layout_height="match_parent" + android:paddingBottom="@dimen/activity_vertical_margin" + android:paddingLeft="@dimen/activity_horizontal_margin" + android:paddingRight="@dimen/activity_horizontal_margin" + android:paddingTop="@dimen/activity_vertical_margin" + tools:context="com.example.tesla.myhomelibrary.AuthorActivity"> + + <TextView + android:id="@+id/textViewAuthor" + android:padding="@dimen/activity_horizontal_margin" + android:textAlignment="center" + android:textAppearance="@style/Base.TextAppearance.AppCompat.Large" + android:textStyle="bold" + android:layout_width="match_parent" + android:layout_height="wrap_content" /> + + <EditText + android:layout_below="@id/textViewAuthor" + android:id="@+id/editTextName" + android:layout_width="match_parent" + android:layout_height="wrap_content" + android:hint="Enter title name" /> + + <LinearLayout + android:orientation="horizontal" + android:id="@+id/linearLayout" + android:layout_width="match_parent" + android:layout_height="wrap_content" + android:layout_below="@id/editTextName"> + + <SeekBar + android:layout_weight="1" + android:id="@+id/seekBarRating" + android:layout_width="match_parent" + android:layout_height="wrap_content" + android:max="5"></SeekBar> + + <TextView + android:text="1" + android:id="@+id/textViewRating" + android:layout_width="wrap_content" + android:layout_height="wrap_content" /> + + </LinearLayout> + + + <Button + android:id="@+id/buttonAddTitle" + android:layout_width="match_parent" + android:layout_height="wrap_content" + android:layout_below="@id/linearLayout" + android:text="Add Title" /> + + <TextView + android:id="@+id/textView" + android:layout_width="match_parent" + android:layout_height="wrap_content" + android:layout_below="@id/buttonAddTitle" + android:padding="@dimen/activity_horizontal_margin" + android:text="Titles" + android:textAlignment="center" + android:textAppearance="@style/Base.TextAppearance.AppCompat.Large" /> + + <ListView + android:id="@+id/listViewTitles" + android:layout_width="match_parent" + android:layout_height="wrap_content" + android:layout_below="@+id/textView"></ListView> + +</RelativeLayout> \ No newline at end of file diff --git a/app/src/main/res/layout/activity_main.xml b/app/src/main/res/layout/activity_main.xml new file mode 100644 index 0000000000000000000000000000000000000000..e45abe1ebdc20381f79a26bed546e10fc464cc2d --- /dev/null +++ b/app/src/main/res/layout/activity_main.xml @@ -0,0 +1,58 @@ +<?xml version="1.0" encoding="utf-8"?> +<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" + xmlns:tools="http://schemas.android.com/tools" + android:id="@+id/activity_main" + android:layout_width="match_parent" + android:layout_height="match_parent" + android:paddingBottom="@dimen/activity_vertical_margin" + android:paddingLeft="@dimen/activity_horizontal_margin" + android:paddingRight="@dimen/activity_horizontal_margin" + android:paddingTop="@dimen/activity_vertical_margin" + tools:context="com.example.tesla.myhomelibrary.MainActivity"> + + + <EditText + android:id="@+id/editTextName" + android:layout_width="match_parent" + android:layout_height="wrap_content" + android:hint="Enter author's name:" /> + + <Spinner + android:id="@+id/spinnerCountry" + android:layout_width="match_parent" + android:layout_height="wrap_content" + android:layout_below="@id/editTextName" + android:entries="@array/countries"></Spinner> + + <Button + android:id="@+id/buttonAddAuthor" + android:layout_width="match_parent" + android:layout_height="wrap_content" + android:layout_below="@id/spinnerCountry" + android:text="Add" /> + + <TextView + android:id="@+id/textView" + android:layout_width="match_parent" + android:layout_height="wrap_content" + android:layout_below="@id/buttonAddAuthor" + android:padding="@dimen/activity_horizontal_margin" + android:text="Authors" + android:textAlignment="center" + android:textAppearance="@style/Base.TextAppearance.AppCompat.Large" /> + + <TextView + android:id="@+id/textView1" + android:layout_width="match_parent" + android:layout_height="wrap_content" + android:layout_below="@id/textView" + android:text="Tap on an Author to add and view titles" + android:textAlignment="center" /> + + <ListView + android:id="@+id/listViewAuthors" + android:layout_width="match_parent" + android:layout_height="wrap_content" + android:layout_below="@+id/textView1"></ListView> + +</RelativeLayout> \ No newline at end of file diff --git a/app/src/main/res/layout/layout_author_list.xml b/app/src/main/res/layout/layout_author_list.xml new file mode 100644 index 0000000000000000000000000000000000000000..d6c0ac01056f08081aa6e57dd05604e237870f3e --- /dev/null +++ b/app/src/main/res/layout/layout_author_list.xml @@ -0,0 +1,21 @@ +<?xml version="1.0" encoding="utf-8"?> +<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" + android:orientation="vertical" android:layout_width="match_parent" + android:layout_height="match_parent"> + + <TextView + android:text="Ivo Andric" + android:textAppearance="@style/Base.TextAppearance.AppCompat.Large" + android:id="@+id/textViewName" + android:layout_width="match_parent" + android:layout_height="wrap_content" /> + + <TextView + android:text="Kingdom of Yugoslavia" + android:textAppearance="@style/Base.TextAppearance.AppCompat.Medium" + android:id="@+id/textViewCountry" + android:layout_width="match_parent" + android:layout_height="wrap_content" /> + +</LinearLayout> + diff --git a/app/src/main/res/layout/update_dialog.xml b/app/src/main/res/layout/update_dialog.xml new file mode 100644 index 0000000000000000000000000000000000000000..e313aed8ff8cefc564577b9e2a9b21afd3bb58b9 --- /dev/null +++ b/app/src/main/res/layout/update_dialog.xml @@ -0,0 +1,44 @@ +<?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:orientation="vertical" + android:padding="@dimen/activity_horizontal_margin"> + + + <EditText + android:id="@+id/editTextName" + android:layout_width="match_parent" + android:layout_height="wrap_content" + android:hint="Enter name" /> + + <Spinner + android:id="@+id/spinnerCountry" + android:layout_width="match_parent" + android:layout_height="wrap_content" + android:layout_below="@id/editTextName" + android:entries="@array/countries"></Spinner> + + <LinearLayout + android:layout_width="match_parent" + android:layout_height="wrap_content" + android:orientation="horizontal"> + + <Button + android:id="@+id/buttonUpdateAuthor" + android:layout_width="wrap_content" + android:layout_height="wrap_content" + android:layout_weight="1" + android:text="Update" /> + + <Button + android:id="@+id/buttonDeleteAuthor" + android:layout_width="wrap_content" + android:layout_height="wrap_content" + android:layout_weight="1" + android:text="Delete" /> + + </LinearLayout> + + +</LinearLayout> \ No newline at end of file diff --git a/app/src/main/res/mipmap-anydpi-v26/ic_launcher.xml b/app/src/main/res/mipmap-anydpi-v26/ic_launcher.xml new file mode 100644 index 0000000000000000000000000000000000000000..eca70cfe52eac1ba66ba280a68ca7be8fcf88a16 --- /dev/null +++ b/app/src/main/res/mipmap-anydpi-v26/ic_launcher.xml @@ -0,0 +1,5 @@ +<?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" /> +</adaptive-icon> \ No newline at end of file diff --git a/app/src/main/res/mipmap-anydpi-v26/ic_launcher_round.xml b/app/src/main/res/mipmap-anydpi-v26/ic_launcher_round.xml new file mode 100644 index 0000000000000000000000000000000000000000..eca70cfe52eac1ba66ba280a68ca7be8fcf88a16 --- /dev/null +++ b/app/src/main/res/mipmap-anydpi-v26/ic_launcher_round.xml @@ -0,0 +1,5 @@ +<?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" /> +</adaptive-icon> \ No newline at end of file diff --git a/app/src/main/res/mipmap-hdpi/ic_launcher.png b/app/src/main/res/mipmap-hdpi/ic_launcher.png new file mode 100644 index 0000000000000000000000000000000000000000..a2f5908281d070150700378b64a84c7db1f97aa1 Binary files /dev/null and b/app/src/main/res/mipmap-hdpi/ic_launcher.png differ diff --git a/app/src/main/res/mipmap-hdpi/ic_launcher_round.png b/app/src/main/res/mipmap-hdpi/ic_launcher_round.png new file mode 100644 index 0000000000000000000000000000000000000000..1b523998081149a985cef0cdf89045b9ed29964a Binary files /dev/null and b/app/src/main/res/mipmap-hdpi/ic_launcher_round.png differ diff --git a/app/src/main/res/mipmap-mdpi/ic_launcher.png b/app/src/main/res/mipmap-mdpi/ic_launcher.png new file mode 100644 index 0000000000000000000000000000000000000000..ff10afd6e182edb2b1a63c8f984e9070d9f950ba Binary files /dev/null and b/app/src/main/res/mipmap-mdpi/ic_launcher.png differ diff --git a/app/src/main/res/mipmap-mdpi/ic_launcher_round.png b/app/src/main/res/mipmap-mdpi/ic_launcher_round.png new file mode 100644 index 0000000000000000000000000000000000000000..115a4c768a20c9e13185c17043f4c4d12dd4632a Binary files /dev/null and b/app/src/main/res/mipmap-mdpi/ic_launcher_round.png differ diff --git a/app/src/main/res/mipmap-xhdpi/ic_launcher.png b/app/src/main/res/mipmap-xhdpi/ic_launcher.png new file mode 100644 index 0000000000000000000000000000000000000000..dcd3cd8083358269d6ed7894726283bb9bcbbfea Binary files /dev/null and b/app/src/main/res/mipmap-xhdpi/ic_launcher.png differ diff --git a/app/src/main/res/mipmap-xhdpi/ic_launcher_round.png b/app/src/main/res/mipmap-xhdpi/ic_launcher_round.png new file mode 100644 index 0000000000000000000000000000000000000000..459ca609d3ae0d3943ab44cdc27feef9256dc6d7 Binary files /dev/null and b/app/src/main/res/mipmap-xhdpi/ic_launcher_round.png differ diff --git a/app/src/main/res/mipmap-xxhdpi/ic_launcher.png b/app/src/main/res/mipmap-xxhdpi/ic_launcher.png new file mode 100644 index 0000000000000000000000000000000000000000..8ca12fe024be86e868d14e91120a6902f8e88ac6 Binary files /dev/null and b/app/src/main/res/mipmap-xxhdpi/ic_launcher.png differ diff --git a/app/src/main/res/mipmap-xxhdpi/ic_launcher_round.png b/app/src/main/res/mipmap-xxhdpi/ic_launcher_round.png new file mode 100644 index 0000000000000000000000000000000000000000..8e19b410a1b15ff180f3dacac19395fe3046cdec Binary files /dev/null and b/app/src/main/res/mipmap-xxhdpi/ic_launcher_round.png differ diff --git a/app/src/main/res/mipmap-xxxhdpi/ic_launcher.png b/app/src/main/res/mipmap-xxxhdpi/ic_launcher.png new file mode 100644 index 0000000000000000000000000000000000000000..b824ebdd48db917eea2e67a82260a100371f8a24 Binary files /dev/null and b/app/src/main/res/mipmap-xxxhdpi/ic_launcher.png differ diff --git a/app/src/main/res/mipmap-xxxhdpi/ic_launcher_round.png b/app/src/main/res/mipmap-xxxhdpi/ic_launcher_round.png new file mode 100644 index 0000000000000000000000000000000000000000..4c19a13c239cb67b8a2134ddd5f325db1d2d5bee Binary files /dev/null and b/app/src/main/res/mipmap-xxxhdpi/ic_launcher_round.png differ diff --git a/app/src/main/res/values/colors.xml b/app/src/main/res/values/colors.xml new file mode 100644 index 0000000000000000000000000000000000000000..3ab3e9cbce07f7cdc941fc8ba424c05e83ed80f0 --- /dev/null +++ b/app/src/main/res/values/colors.xml @@ -0,0 +1,6 @@ +<?xml version="1.0" encoding="utf-8"?> +<resources> + <color name="colorPrimary">#3F51B5</color> + <color name="colorPrimaryDark">#303F9F</color> + <color name="colorAccent">#FF4081</color> +</resources> diff --git a/app/src/main/res/values/dimens.xml b/app/src/main/res/values/dimens.xml new file mode 100644 index 0000000000000000000000000000000000000000..48963b20617f19bb0acd4f8d64652afde649ae52 --- /dev/null +++ b/app/src/main/res/values/dimens.xml @@ -0,0 +1,6 @@ +<?xml version="1.0" encoding="utf-8"?> +<resources> + <!-- Default screen margins, per the Android Design guidelines. --> + <dimen name="activity_horizontal_margin">16dp</dimen> + <dimen name="activity_vertical_margin">16dp</dimen> +</resources> \ No newline at end of file diff --git a/app/src/main/res/values/strings.xml b/app/src/main/res/values/strings.xml new file mode 100644 index 0000000000000000000000000000000000000000..5f6e04f02148eae4b92b0f417921514e301bbd34 --- /dev/null +++ b/app/src/main/res/values/strings.xml @@ -0,0 +1,10 @@ +<resources> + <string name="app_name">MyHomeLibrary</string> + <array name="countries"> + <item name="america">America</item> + <item name="france">France</item> + <item name="spain">Spain</item> + <item name="columbia">Columbia</item> + <item name="russia">Russia</item> + </array> +</resources> diff --git a/app/src/main/res/values/styles.xml b/app/src/main/res/values/styles.xml new file mode 100644 index 0000000000000000000000000000000000000000..5885930df6d10edf3d6df40d6556297d11f953da --- /dev/null +++ b/app/src/main/res/values/styles.xml @@ -0,0 +1,11 @@ +<resources> + + <!-- Base application theme. --> + <style name="AppTheme" parent="Theme.AppCompat.Light.DarkActionBar"> + <!-- Customize your theme here. --> + <item name="colorPrimary">@color/colorPrimary</item> + <item name="colorPrimaryDark">@color/colorPrimaryDark</item> + <item name="colorAccent">@color/colorAccent</item> + </style> + +</resources> diff --git a/app/src/test/java/com/example/tesla/myhomelibrary/AuthorTest.java b/app/src/test/java/com/example/tesla/myhomelibrary/AuthorTest.java new file mode 100644 index 0000000000000000000000000000000000000000..7b547bc945bb58ef869244d78488105d20f698ec --- /dev/null +++ b/app/src/test/java/com/example/tesla/myhomelibrary/AuthorTest.java @@ -0,0 +1,37 @@ +package com.example.tesla.myhomelibrary; + +import org.junit.After; +import org.junit.Before; +import org.junit.Test; + +import static org.junit.Assert.*; + +public class AuthorTest { + + Author author; + + @Before + public void setUp() throws Exception { + author = new Author("foo", "J.D. Salinger", "America"); + } + + @After + public void tearDown() throws Exception { + author = null; + } + + @Test + public void getAuthorId() { + assertTrue(author.getAuthorId().equals("foo")); + } + + @Test + public void getAuthorName() { + assertTrue(author.getAuthorName().equals("J.D. Salinger")); + } + + @Test + public void getAuthorCountry() { + assertTrue(author.getAuthorCountry().equals("America")); + } +} \ No newline at end of file diff --git a/build.gradle b/build.gradle new file mode 100644 index 0000000000000000000000000000000000000000..b02426c99c3488785120111df3ec2296adda1ecb --- /dev/null +++ b/build.gradle @@ -0,0 +1,27 @@ +// Top-level build file where you can add configuration options common to all sub-projects/modules. + +buildscript { + + repositories { + google() + jcenter() + } + dependencies { + classpath 'com.android.tools.build:gradle:3.2.1' + + // NOTE: Do not place your application dependencies here; they belong + // in the individual module build.gradle files + classpath 'com.google.gms:google-services:4.0.1' + } +} + +allprojects { + repositories { + google() + jcenter() + } +} + +task clean(type: Delete) { + delete rootProject.buildDir +} diff --git a/gradle.properties b/gradle.properties new file mode 100644 index 0000000000000000000000000000000000000000..743d692ce151e0dbf591cbbf498164ecc8055439 --- /dev/null +++ b/gradle.properties @@ -0,0 +1,13 @@ +# Project-wide Gradle settings. +# IDE (e.g. Android Studio) users: +# Gradle settings configured through the IDE *will override* +# any settings specified in this file. +# For more details on how to configure your build environment visit +# http://www.gradle.org/docs/current/userguide/build_environment.html +# Specifies the JVM arguments used for the daemon process. +# The setting is particularly useful for tweaking memory settings. +org.gradle.jvmargs=-Xmx1536m +# When configured, Gradle will run in incubating parallel mode. +# This option should only be used with decoupled projects. More details, visit +# http://www.gradle.org/docs/current/userguide/multi_project_builds.html#sec:decoupled_projects +# org.gradle.parallel=true diff --git a/gradle/wrapper/gradle-wrapper.jar b/gradle/wrapper/gradle-wrapper.jar new file mode 100644 index 0000000000000000000000000000000000000000..7a3265ee94c0ab25cf079ac8ccdf87f41d455d42 Binary files /dev/null and b/gradle/wrapper/gradle-wrapper.jar differ diff --git a/gradle/wrapper/gradle-wrapper.properties b/gradle/wrapper/gradle-wrapper.properties new file mode 100644 index 0000000000000000000000000000000000000000..ae8b70930dde7498e1856e105765a2a47ff1d076 --- /dev/null +++ b/gradle/wrapper/gradle-wrapper.properties @@ -0,0 +1,6 @@ +#Tue Oct 16 00:07:50 EDT 2018 +distributionBase=GRADLE_USER_HOME +distributionPath=wrapper/dists +zipStoreBase=GRADLE_USER_HOME +zipStorePath=wrapper/dists +distributionUrl=https\://services.gradle.org/distributions/gradle-4.6-all.zip diff --git a/gradlew b/gradlew new file mode 100755 index 0000000000000000000000000000000000000000..cccdd3d517fc5249beaefa600691cf150f2fa3e6 --- /dev/null +++ b/gradlew @@ -0,0 +1,172 @@ +#!/usr/bin/env sh + +############################################################################## +## +## Gradle start up script for UN*X +## +############################################################################## + +# Attempt to set APP_HOME +# Resolve links: $0 may be a link +PRG="$0" +# Need this for relative symlinks. +while [ -h "$PRG" ] ; do + ls=`ls -ld "$PRG"` + link=`expr "$ls" : '.*-> \(.*\)$'` + if expr "$link" : '/.*' > /dev/null; then + PRG="$link" + else + PRG=`dirname "$PRG"`"/$link" + fi +done +SAVED="`pwd`" +cd "`dirname \"$PRG\"`/" >/dev/null +APP_HOME="`pwd -P`" +cd "$SAVED" >/dev/null + +APP_NAME="Gradle" +APP_BASE_NAME=`basename "$0"` + +# Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script. +DEFAULT_JVM_OPTS="" + +# Use the maximum available, or set MAX_FD != -1 to use that value. +MAX_FD="maximum" + +warn () { + echo "$*" +} + +die () { + echo + echo "$*" + echo + exit 1 +} + +# OS specific support (must be 'true' or 'false'). +cygwin=false +msys=false +darwin=false +nonstop=false +case "`uname`" in + CYGWIN* ) + cygwin=true + ;; + Darwin* ) + darwin=true + ;; + MINGW* ) + msys=true + ;; + NONSTOP* ) + nonstop=true + ;; +esac + +CLASSPATH=$APP_HOME/gradle/wrapper/gradle-wrapper.jar + +# Determine the Java command to use to start the JVM. +if [ -n "$JAVA_HOME" ] ; then + if [ -x "$JAVA_HOME/jre/sh/java" ] ; then + # IBM's JDK on AIX uses strange locations for the executables + JAVACMD="$JAVA_HOME/jre/sh/java" + else + JAVACMD="$JAVA_HOME/bin/java" + fi + if [ ! -x "$JAVACMD" ] ; then + die "ERROR: JAVA_HOME is set to an invalid directory: $JAVA_HOME + +Please set the JAVA_HOME variable in your environment to match the +location of your Java installation." + fi +else + JAVACMD="java" + which java >/dev/null 2>&1 || die "ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH. + +Please set the JAVA_HOME variable in your environment to match the +location of your Java installation." +fi + +# Increase the maximum file descriptors if we can. +if [ "$cygwin" = "false" -a "$darwin" = "false" -a "$nonstop" = "false" ] ; then + MAX_FD_LIMIT=`ulimit -H -n` + if [ $? -eq 0 ] ; then + if [ "$MAX_FD" = "maximum" -o "$MAX_FD" = "max" ] ; then + MAX_FD="$MAX_FD_LIMIT" + fi + ulimit -n $MAX_FD + if [ $? -ne 0 ] ; then + warn "Could not set maximum file descriptor limit: $MAX_FD" + fi + else + warn "Could not query maximum file descriptor limit: $MAX_FD_LIMIT" + fi +fi + +# For Darwin, add options to specify how the application appears in the dock +if $darwin; then + GRADLE_OPTS="$GRADLE_OPTS \"-Xdock:name=$APP_NAME\" \"-Xdock:icon=$APP_HOME/media/gradle.icns\"" +fi + +# For Cygwin, switch paths to Windows format before running java +if $cygwin ; then + APP_HOME=`cygpath --path --mixed "$APP_HOME"` + CLASSPATH=`cygpath --path --mixed "$CLASSPATH"` + JAVACMD=`cygpath --unix "$JAVACMD"` + + # We build the pattern for arguments to be converted via cygpath + ROOTDIRSRAW=`find -L / -maxdepth 1 -mindepth 1 -type d 2>/dev/null` + SEP="" + for dir in $ROOTDIRSRAW ; do + ROOTDIRS="$ROOTDIRS$SEP$dir" + SEP="|" + done + OURCYGPATTERN="(^($ROOTDIRS))" + # Add a user-defined pattern to the cygpath arguments + if [ "$GRADLE_CYGPATTERN" != "" ] ; then + OURCYGPATTERN="$OURCYGPATTERN|($GRADLE_CYGPATTERN)" + fi + # Now convert the arguments - kludge to limit ourselves to /bin/sh + i=0 + for arg in "$@" ; do + CHECK=`echo "$arg"|egrep -c "$OURCYGPATTERN" -` + CHECK2=`echo "$arg"|egrep -c "^-"` ### Determine if an option + + if [ $CHECK -ne 0 ] && [ $CHECK2 -eq 0 ] ; then ### Added a condition + eval `echo args$i`=`cygpath --path --ignore --mixed "$arg"` + else + eval `echo args$i`="\"$arg\"" + fi + i=$((i+1)) + done + case $i in + (0) set -- ;; + (1) set -- "$args0" ;; + (2) set -- "$args0" "$args1" ;; + (3) set -- "$args0" "$args1" "$args2" ;; + (4) set -- "$args0" "$args1" "$args2" "$args3" ;; + (5) set -- "$args0" "$args1" "$args2" "$args3" "$args4" ;; + (6) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" ;; + (7) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" ;; + (8) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" "$args7" ;; + (9) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" "$args7" "$args8" ;; + esac +fi + +# Escape application args +save () { + for i do printf %s\\n "$i" | sed "s/'/'\\\\''/g;1s/^/'/;\$s/\$/' \\\\/" ; done + echo " " +} +APP_ARGS=$(save "$@") + +# Collect all arguments for the java command, following the shell quoting and substitution rules +eval set -- $DEFAULT_JVM_OPTS $JAVA_OPTS $GRADLE_OPTS "\"-Dorg.gradle.appname=$APP_BASE_NAME\"" -classpath "\"$CLASSPATH\"" org.gradle.wrapper.GradleWrapperMain "$APP_ARGS" + +# by default we should be in the correct project dir, but when run from Finder on Mac, the cwd is wrong +if [ "$(uname)" = "Darwin" ] && [ "$HOME" = "$PWD" ]; then + cd "$(dirname "$0")" +fi + +exec "$JAVACMD" "$@" diff --git a/gradlew.bat b/gradlew.bat new file mode 100644 index 0000000000000000000000000000000000000000..e95643d6a2ca62258464e83c72f5156dc941c609 --- /dev/null +++ b/gradlew.bat @@ -0,0 +1,84 @@ +@if "%DEBUG%" == "" @echo off +@rem ########################################################################## +@rem +@rem Gradle startup script for Windows +@rem +@rem ########################################################################## + +@rem Set local scope for the variables with windows NT shell +if "%OS%"=="Windows_NT" setlocal + +set DIRNAME=%~dp0 +if "%DIRNAME%" == "" set DIRNAME=. +set APP_BASE_NAME=%~n0 +set APP_HOME=%DIRNAME% + +@rem Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script. +set DEFAULT_JVM_OPTS= + +@rem Find java.exe +if defined JAVA_HOME goto findJavaFromJavaHome + +set JAVA_EXE=java.exe +%JAVA_EXE% -version >NUL 2>&1 +if "%ERRORLEVEL%" == "0" goto init + +echo. +echo ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH. +echo. +echo Please set the JAVA_HOME variable in your environment to match the +echo location of your Java installation. + +goto fail + +:findJavaFromJavaHome +set JAVA_HOME=%JAVA_HOME:"=% +set JAVA_EXE=%JAVA_HOME%/bin/java.exe + +if exist "%JAVA_EXE%" goto init + +echo. +echo ERROR: JAVA_HOME is set to an invalid directory: %JAVA_HOME% +echo. +echo Please set the JAVA_HOME variable in your environment to match the +echo location of your Java installation. + +goto fail + +:init +@rem Get command-line arguments, handling Windows variants + +if not "%OS%" == "Windows_NT" goto win9xME_args + +:win9xME_args +@rem Slurp the command line arguments. +set CMD_LINE_ARGS= +set _SKIP=2 + +:win9xME_args_slurp +if "x%~1" == "x" goto execute + +set CMD_LINE_ARGS=%* + +:execute +@rem Setup the command line + +set CLASSPATH=%APP_HOME%\gradle\wrapper\gradle-wrapper.jar + +@rem Execute Gradle +"%JAVA_EXE%" %DEFAULT_JVM_OPTS% %JAVA_OPTS% %GRADLE_OPTS% "-Dorg.gradle.appname=%APP_BASE_NAME%" -classpath "%CLASSPATH%" org.gradle.wrapper.GradleWrapperMain %CMD_LINE_ARGS% + +:end +@rem End local scope for the variables with windows NT shell +if "%ERRORLEVEL%"=="0" goto mainEnd + +:fail +rem Set variable GRADLE_EXIT_CONSOLE if you need the _script_ return code instead of +rem the _cmd.exe /c_ return code! +if not "" == "%GRADLE_EXIT_CONSOLE%" exit 1 +exit /b 1 + +:mainEnd +if "%OS%"=="Windows_NT" endlocal + +:omega diff --git a/settings.gradle b/settings.gradle new file mode 100644 index 0000000000000000000000000000000000000000..e7b4def49cb53d9aa04228dd3edb14c9e635e003 --- /dev/null +++ b/settings.gradle @@ -0,0 +1 @@ +include ':app'