/*
 * Copyright 2016 Hippo Seven
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

package com.hippo.ehviewer.gallery;

import android.content.Context;
import android.support.annotation.NonNull;
import android.support.annotation.Nullable;

import com.hippo.ehviewer.client.data.GalleryInfo;
import com.hippo.ehviewer.spider.SpiderQueen;
import com.hippo.image.Image;
import com.hippo.unifile.UniFile;
import com.hippo.yorozuya.SimpleHandler;

import java.util.Locale;

public class EhGalleryProvider extends GalleryProvider implements SpiderQueen.OnSpiderListener {

    private final Context mContext;
    private final GalleryInfo mGalleryInfo;
    @Nullable
    private SpiderQueen mSpiderQueen;

    public EhGalleryProvider(Context context, GalleryInfo galleryInfo) {
        mContext = context;
        mGalleryInfo = galleryInfo;
    }

    @Override
    public void start() {
        super.start();

        mSpiderQueen = SpiderQueen.obtainSpiderQueen(mContext, mGalleryInfo, SpiderQueen.MODE_READ);
        mSpiderQueen.addOnSpiderListener(this);
    }

    @Override
    public void stop() {
        super.stop();

        if (mSpiderQueen != null) {
            mSpiderQueen.removeOnSpiderListener(this);
            final SpiderQueen spiderQueen = mSpiderQueen;
            mSpiderQueen = null;
            // Activity recreate may called
            SimpleHandler.getInstance().postDelayed(new Runnable() {
                @Override
                public void run() {
                    SpiderQueen.releaseSpiderQueen(spiderQueen, SpiderQueen.MODE_READ);
                }
            }, 3000);
        }
    }

    @Override
    public int getStartPage() {
        if (mSpiderQueen != null) {
            return mSpiderQueen.getStartPage();
        } else {
            return super.getStartPage();
        }
    }

    @NonNull
    @Override
    public String getImageFilename(int index) {
        return String.format(Locale.US, "%d-%08d", mGalleryInfo.gid, index + 1);
    }

    @Override
    public boolean save(int index, @NonNull UniFile file) {
        if (null != mSpiderQueen) {
            return mSpiderQueen.save(index, file);
        } else {
            return false;
        }
    }

    @Nullable
    @Override
    public UniFile save(int index, @NonNull UniFile dir, @NonNull String filename) {
        if (null != mSpiderQueen) {
            return mSpiderQueen.save(index, dir, filename);
        } else {
            return null;
        }
    }

    @Override
    public void putStartPage(int page) {
        if (mSpiderQueen != null) {
            mSpiderQueen.putStartPage(page);
        }
    }

    @Override
    public int size() {
        if (mSpiderQueen != null) {
            return mSpiderQueen.size();
        } else {
            return GalleryProvider.STATE_ERROR;
        }
    }

    @Override
    public void request(int index) {
        if (mSpiderQueen != null) {
            Object object = mSpiderQueen.request(index);
            if (object instanceof Float) {
                notifyPagePercent(index, (Float) object);
            } else if (object instanceof String) {
                notifyPageFailed(index, (String) object);
            } else if (object == null) {
                notifyPageWait(index);
            }
        }
    }

    @Override
    public void forceRequest(int index) {
        if (mSpiderQueen != null) {
            Object object = mSpiderQueen.forceRequest(index);
            if (object instanceof Float) {
                notifyPagePercent(index, (Float) object);
            } else if (object instanceof String) {
                notifyPageFailed(index, (String) object);
            } else if (object == null) {
                notifyPageWait(index);
            }
        }
    }

    @Override
    public void cancelRequest(int index) {
        if (mSpiderQueen != null) {
            mSpiderQueen.cancelRequest(index);
        }
    }

    @Override
    public String getError() {
        if (mSpiderQueen != null) {
            return mSpiderQueen.getError();
        } else {
            return "Error"; // TODO
        }
    }

    @Override
    public void onGetPages(int pages) {
        notifyDataChanged();
    }

    @Override
    public void onGet509(int index) {
        // TODO
    }

    @Override
    public void onPageDownload(int index, long contentLength, long receivedSize, int bytesRead) {
        if (contentLength > 0) {
            notifyPagePercent(index, (float) receivedSize / contentLength);
        }
    }

    @Override
    public void onPageSuccess(int index, int finished, int downloaded, int total) {
        notifyDataChanged(index);
    }

    @Override
    public void onPageFailure(int index, String error, int finished, int downloaded, int total) {
        notifyPageFailed(index, error);
    }

    @Override
    public void onFinish(int finished, int downloaded, int total) {
    }

    @Override
    public void onGetImageSuccess(int index, Image image) {
        notifyPageSucceed(index, image);
    }

    @Override
    public void onGetImageFailure(int index, String error) {
        notifyPageFailed(index, error);
    }
}

@@ -1727,99 +1727,8 @@
 s);%0A
-            final SpiderQueen spiderQueen = mSpiderQueen;%0A            mSpiderQueen = null;%0A
     
@@ -1766,16 +1766,31 @@
 y called
+, so wait 3000s
 %0A       
@@ -1843,208 +1843,72 @@
 ew R
-unnable() %7B%0A                @Override%0A                public void run() %7B%0A                    SpiderQueen.releaseSpiderQueen(spiderQueen, SpiderQueen.MODE_READ);%0A                %7D%0A            %7D, 3000)
+eleaseTask(mSpiderQueen), 3000);%0A            mSpiderQueen = null
 ;%0A  
@@ -5452,11 +5452,458 @@
 );%0A    %7D
+%0A%0A    private static class ReleaseTask implements Runnable %7B%0A%0A        private SpiderQueen mSpiderQueen;%0A%0A        public ReleaseTask(SpiderQueen spiderQueen) %7B%0A            mSpiderQueen = spiderQueen;%0A        %7D%0A%0A        @Override%0A        public void run() %7B%0A            if (null != mSpiderQueen) %7B%0A                SpiderQueen.releaseSpiderQueen(mSpiderQueen, SpiderQueen.MODE_READ);%0A                mSpiderQueen = null;%0A            %7D%0A        %7D%0A    %7D
 %0A%7D%0A

Improve EhGalleryProvider