package com.mikepenz.fastadapter.app;

import android.graphics.Color;
import android.os.Bundle;
import android.support.v7.app.AppCompatActivity;
import android.support.v7.widget.DefaultItemAnimator;
import android.support.v7.widget.LinearLayoutManager;
import android.support.v7.widget.RecyclerView;
import android.support.v7.widget.Toolbar;
import android.view.Menu;
import android.view.MenuInflater;
import android.view.MenuItem;
import android.view.View;
import android.widget.Toast;

import com.mikepenz.fastadapter.FastAdapter;
import com.mikepenz.fastadapter.IAdapter;
import com.mikepenz.fastadapter.adapters.FastItemAdapter;
import com.mikepenz.fastadapter.app.items.RealmSampleUserItem;
import com.mikepenz.iconics.IconicsDrawable;
import com.mikepenz.material_design_iconic_typeface_library.MaterialDesignIconic;
import com.mikepenz.materialize.MaterializeBuilder;

import java.util.LinkedList;
import java.util.List;

import io.realm.Realm;
import io.realm.RealmChangeListener;
import io.realm.RealmResults;

public class RealmActivity extends AppCompatActivity {
    //save our FastAdapter
    private FastItemAdapter<RealmSampleUserItem> mFastItemAdapter;
    //save our Realm instance to close it later
    private Realm mRealm;

    @Override
    protected void onCreate(final Bundle savedInstanceState) {
        findViewById(android.R.id.content).setSystemUiVisibility(findViewById(android.R.id.content).getSystemUiVisibility() | View.SYSTEM_UI_FLAG_LIGHT_STATUS_BAR);
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        // Handle Toolbar
        Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar);
        setSupportActionBar(toolbar);
        getSupportActionBar().setTitle(R.string.sample_realm_list);

        //style our ui
        new MaterializeBuilder().withActivity(this).build();

        //create our FastAdapter which will manage everything
        mFastItemAdapter = new FastItemAdapter<>();

        //configure our fastAdapter
        mFastItemAdapter.withOnClickListener(new FastAdapter.OnClickListener<RealmSampleUserItem>() {
            @Override
            public boolean onClick(View v, IAdapter<RealmSampleUserItem> adapter, RealmSampleUserItem item, int position) {
                Toast.makeText(v.getContext(), item.getName(), Toast.LENGTH_SHORT).show();
                return false;
            }
        });

        //get our recyclerView and do basic setup
        RecyclerView rv = (RecyclerView) findViewById(R.id.rv);
        rv.setLayoutManager(new LinearLayoutManager(this));
        rv.setItemAnimator(new DefaultItemAnimator());
        rv.setAdapter(mFastItemAdapter);

        //Get a realm instance for this activity
        mRealm = Realm.getDefaultInstance();

        //Add a realm on change listener (don´t forget to close this realm instance before adding this listener again)
        mRealm.where(RealmSampleUserItem.class).findAllAsync().addChangeListener(new RealmChangeListener<RealmResults<RealmSampleUserItem>>() {
            @Override
            public void onChange(RealmResults<RealmSampleUserItem> userItems) {
                //This will call twice
                //1.) from findAllAsync()
                //2.) from createData()
                mFastItemAdapter.set(userItems);
            }
        });

        //fill with some sample data
        createData();

        //set the back arrow in the toolbar
        getSupportActionBar().setDisplayHomeAsUpEnabled(true);
        getSupportActionBar().setHomeButtonEnabled(false);

        //restore selections (this has to be done after the items were added
        mFastItemAdapter.withSavedInstanceState(savedInstanceState);
    }

    private void createData() {
        //Execute transaction
        mRealm.executeTransactionAsync(new Realm.Transaction() {
            @Override
            public void execute(Realm realm) {
                List<RealmSampleUserItem> users = new LinkedList<>();
                for (int i = 1; i <= 50; i++) {
                    RealmSampleUserItem user = new RealmSampleUserItem();
                    user.withName("Sample Realm Element " + i).withIdentifier(i);
                    users.add(user);
                }
                //insert the created objects to realm
                //a bulk insert has lower object allocations then a copy
                realm.insertOrUpdate(users);
            }
        });
    }

    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
        MenuInflater inflater = getMenuInflater();
        inflater.inflate(R.menu.menu_add, menu);
        menu.findItem(R.id.item_add).setIcon(new IconicsDrawable(this, MaterialDesignIconic.Icon.gmi_plus_square).color(Color.BLACK).actionBar());
        return true;
    }

    @Override
    protected void onSaveInstanceState(Bundle outState) {
        //add the values which need to be saved from the adapter to the bundel
        outState = mFastItemAdapter.saveInstanceState(outState);
        super.onSaveInstanceState(outState);
    }

    @Override
    public boolean onOptionsItemSelected(MenuItem item) {
        //handle the click on the back arrow click
        switch (item.getItemId()) {
            case android.R.id.home:
                onBackPressed();
                return true;
            case R.id.item_add:
                mRealm.where(RealmSampleUserItem.class).findAllAsync().addChangeListener(new RealmChangeListener<RealmResults<RealmSampleUserItem>>() {
                    @Override
                    public void onChange(RealmResults<RealmSampleUserItem> userItems) {
                        //This transaction has to be in the same thread to access the userItems
                        mRealm.beginTransaction();
                        long newPrimaryKey = userItems.last().getIdentifier() + 1;
                        RealmSampleUserItem newUser = mRealm.createObject(RealmSampleUserItem.class);
                        newUser.withName("Sample Realm Element " + newPrimaryKey)
                                .withIdentifier(newPrimaryKey);
                        mRealm.commitTransaction();

                        //Remove the change listener
                        userItems.removeChangeListener(this);
                    }
                });
                return true;
            default:
                return super.onOptionsItemSelected(item);
        }
    }

    //Prevent the realm instance from leaking
    @Override
    protected void onDestroy() {
        super.onDestroy();
        closeRealm();
    }

    private void closeRealm() {
        if (!mRealm.isClosed()) {
            mRealm.close();
        }
    }
}

@@ -5637,128 +5637,178 @@
   //
-This transaction has to be in the same thread to access the userItems%0A                        mRealm.beginTransaction();
+Remove the change listener%0A                        userItems.removeChangeListener(this);%0A                        //Store the primary key to get access from a other thread
 %0A   
@@ -5828,16 +5828,22 @@
         
+final 
 long new
@@ -5893,16 +5893,206 @@
 () + 1;%0A
+                        mRealm.executeTransactionAsync(new Realm.Transaction() %7B%0A                            @Override%0A                            public void execute(Realm realm) %7B%0A        
         
@@ -6137,18 +6137,17 @@
 wUser = 
-mR
+r
 ealm.cre
@@ -6208,16 +6208,24 @@
         
+      
+  
 newUser.
@@ -6306,16 +6306,24 @@
         
+        
 .withIde
@@ -6374,149 +6374,39 @@
     
-mRealm.commitTransaction();%0A%0A                        //Remove the change listener%0A                        userItems.removeChangeListener(this
+    %7D%0A                        %7D
 );%0A 

improve async write