添加评论查看与发送功能,评论按发布时间排序
No files matched your search
|
Before Width: | Height: | Size: 480 B |
|
After Width: | Height: | Size: 735 B |
|
After Width: | Height: | Size: 817 B |
|
Before Width: | Height: | Size: 298 B |
|
After Width: | Height: | Size: 471 B |
|
After Width: | Height: | Size: 532 B |
|
Before Width: | Height: | Size: 587 B |
|
After Width: | Height: | Size: 970 B |
|
After Width: | Height: | Size: 1.1 KiB |
|
Before Width: | Height: | Size: 1002 B |
|
After Width: | Height: | Size: 1.5 KiB |
|
After Width: | Height: | Size: 1.7 KiB |
@@ -1,25 +0,0 @@
|
||||
<LinearLayout
|
||||
xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:id="@+id/search_bar"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="match_parent"
|
||||
android:orientation="horizontal" >
|
||||
|
||||
<AutoCompleteTextView
|
||||
android:id="@+id/autoCompleteTextView1"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_weight="1"
|
||||
android:ems="10"
|
||||
android:singleLine="true"
|
||||
android:background="@android:color/transparent" >
|
||||
</AutoCompleteTextView>
|
||||
|
||||
<ImageView
|
||||
android:id="@+id/remove"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_weight="1"
|
||||
android:src="@drawable/ic_action_remove" />
|
||||
|
||||
</LinearLayout>
|
||||
@@ -11,4 +11,10 @@
|
||||
android:showAsAction="ifRoom"
|
||||
android:icon="@drawable/ic_action_download"
|
||||
android:title="@string/download"/>
|
||||
|
||||
<item
|
||||
android:id="@+id/action_reply"
|
||||
android:showAsAction="ifRoom"
|
||||
android:icon="@drawable/ic_action_reply"
|
||||
android:title="@string/download"/>
|
||||
</menu>
|
||||
@@ -6,6 +6,8 @@ Version 0.4.5 (2014-??-??)
|
||||
* 更规范的界面
|
||||
* 添加评分功能
|
||||
* 添加标签投票功能
|
||||
* 添加评论查看与发送功能
|
||||
* 评论按发布时间排序
|
||||
* 调整下拉刷新控件
|
||||
* 调整部分数据的存储方式
|
||||
* 支持语音搜索
|
||||
|
||||
@@ -185,28 +185,6 @@ public class ListUrls {
|
||||
return numPerPage;
|
||||
}
|
||||
|
||||
public boolean pageUp() {
|
||||
if (page < max - 1) {
|
||||
page++;
|
||||
return true;
|
||||
}
|
||||
else {
|
||||
page = max -1;
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
public boolean pageDown() {
|
||||
if (page > 0) {
|
||||
page--;
|
||||
return true;
|
||||
}
|
||||
else {
|
||||
page = 0;
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
public String getUrl() {
|
||||
StringBuilder url = new StringBuilder(EhClient.listHeader);
|
||||
url.append("?");
|
||||
|
||||
@@ -19,6 +19,7 @@ import android.widget.TextView;
|
||||
|
||||
public class CommentsSectionFragment extends Fragment {
|
||||
|
||||
@SuppressWarnings("unused")
|
||||
private static final String TAG = "CommentsSectionFragment";
|
||||
|
||||
private MangaDetailActivity mActivity;
|
||||
@@ -101,16 +102,34 @@ public class CommentsSectionFragment extends Fragment {
|
||||
public long getItemId(int position) {
|
||||
return position;
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
public View getView(int position, View convertView, ViewGroup parent) {
|
||||
boolean isUserSame = true;
|
||||
boolean isTimeSame = true;
|
||||
|
||||
if (convertView == null)
|
||||
convertView = LayoutInflater.from(mActivity)
|
||||
.inflate(R.layout.comments_item, null);
|
||||
Comment c = mComments.get(position);
|
||||
((TextView)convertView.findViewById(R.id.user)).setText(c.user);
|
||||
((TextView)convertView.findViewById(R.id.time)).setText(c.time);
|
||||
((TextView)convertView.findViewById(R.id.comment)).setText(Html.fromHtml(c.comment));
|
||||
|
||||
TextView user = (TextView)convertView.findViewById(R.id.user);
|
||||
if (!c.user.equals(user.getText())) {
|
||||
isUserSame = false;
|
||||
user.setText(c.user);
|
||||
}
|
||||
|
||||
TextView time = (TextView)convertView.findViewById(R.id.time);
|
||||
if (!c.time.equals(time.getText())) {
|
||||
isTimeSame = false;
|
||||
time.setText(c.time);
|
||||
}
|
||||
|
||||
// No one can post one comment at same this time
|
||||
if (!isUserSame || !isTimeSame)
|
||||
((TextView)convertView.findViewById(R.id.comment))
|
||||
.setText(Html.fromHtml(c.comment));
|
||||
|
||||
return convertView;
|
||||
}
|
||||
};
|
||||
|
||||
@@ -684,10 +684,6 @@ public class DetailSectionFragment extends Fragment
|
||||
public void onSuccess(GalleryDetail md) {
|
||||
Cache.mdCache.put(String.valueOf(mGalleryDetail.gid), md);
|
||||
layout(md);
|
||||
|
||||
for (Comment c : mGalleryDetail.comments) {
|
||||
Log.d(TAG, c.time);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -70,6 +70,7 @@ import android.view.animation.TranslateAnimation;
|
||||
import android.widget.AdapterView;
|
||||
import android.widget.BaseAdapter;
|
||||
import android.widget.Button;
|
||||
import android.widget.EditText;
|
||||
import android.widget.LinearLayout;
|
||||
import android.widget.ProgressBar;
|
||||
import android.widget.RatingBar;
|
||||
@@ -94,6 +95,8 @@ public class MangaDetailActivity extends FragmentActivity
|
||||
private DetailSectionFragment mDetailFragment;
|
||||
private CommentsSectionFragment mCommentsFragment;
|
||||
|
||||
private int mTabIndex;
|
||||
|
||||
private DownloadServiceConnection mServiceConn = new DownloadServiceConnection();
|
||||
|
||||
@Override
|
||||
@@ -162,6 +165,8 @@ public class MangaDetailActivity extends FragmentActivity
|
||||
@Override
|
||||
public void onTabSelected(Tab tab, FragmentTransaction ft) {
|
||||
mViewPager.setCurrentItem(tab.getPosition());
|
||||
mTabIndex = tab.getPosition();
|
||||
invalidateOptionsMenu();
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -192,8 +197,6 @@ public class MangaDetailActivity extends FragmentActivity
|
||||
mCommentsFragment.setComments(comments);
|
||||
}
|
||||
|
||||
/*
|
||||
|
||||
@Override
|
||||
public boolean onOptionsItemSelected(MenuItem item) {
|
||||
// Handle item selection
|
||||
@@ -202,12 +205,13 @@ public class MangaDetailActivity extends FragmentActivity
|
||||
finish();
|
||||
return true;
|
||||
case R.id.action_favourite:
|
||||
mData.addLocalFavourite(mangaDetail);
|
||||
((AppContext)getApplication()).getData().addLocalFavourite(mGalleryInfo);
|
||||
Toast.makeText(MangaDetailActivity.this,
|
||||
getString(R.string.toast_add_favourite),
|
||||
Toast.LENGTH_SHORT).show();
|
||||
return true;
|
||||
case R.id.action_download:
|
||||
/*
|
||||
Intent it = new Intent(MangaDetailActivity.this, DownloadService.class);
|
||||
startService(it);
|
||||
if (mangaDetail.firstPage == null)
|
||||
@@ -222,13 +226,63 @@ public class MangaDetailActivity extends FragmentActivity
|
||||
Toast.makeText(MangaDetailActivity.this,
|
||||
getString(R.string.toast_add_download),
|
||||
Toast.LENGTH_SHORT).show();
|
||||
*/
|
||||
return true;
|
||||
|
||||
case R.id.action_reply:
|
||||
final EditText et = new EditText(this);
|
||||
//et.setMinimumHeight(Ui.dp2pix(64));
|
||||
LinearLayout.LayoutParams lp = new LinearLayout.LayoutParams(
|
||||
LinearLayout.LayoutParams.MATCH_PARENT,
|
||||
LinearLayout.LayoutParams.WRAP_CONTENT);
|
||||
int x = Ui.dp2pix(8);
|
||||
lp.leftMargin = x;
|
||||
lp.rightMargin = x;
|
||||
lp.topMargin = x;
|
||||
lp.bottomMargin = x;
|
||||
new DialogBuilder(this).setView(et, lp)
|
||||
.setTitle("评论")
|
||||
.setPositiveButton("发送", new View.OnClickListener() {
|
||||
@Override
|
||||
public void onClick(View v) {
|
||||
((AlertButton)v).dialog.dismiss();
|
||||
String comment = et.getText().toString();
|
||||
((AppContext)getApplication()).getEhClient()
|
||||
.comment(EhClient.getDetailUrl(mGalleryInfo.gid, mGalleryInfo.token, EhClient.EX),
|
||||
comment, new EhClient.OnCommentListener() {
|
||||
@Override
|
||||
public void onSuccess(List<Comment> comments) {
|
||||
setComments(comments);
|
||||
}
|
||||
@Override
|
||||
public void onFailure(String eMsg) {
|
||||
Toast.makeText(MangaDetailActivity.this, eMsg, Toast.LENGTH_SHORT).show();
|
||||
}
|
||||
});
|
||||
}
|
||||
}).setNegativeButton(android.R.string.cancel,
|
||||
new View.OnClickListener() {
|
||||
@Override
|
||||
public void onClick(View v) {
|
||||
((AlertButton)v).dialog.dismiss();
|
||||
}
|
||||
}).create().show();
|
||||
|
||||
return true;
|
||||
default:
|
||||
return super.onOptionsItemSelected(item);
|
||||
}
|
||||
}
|
||||
|
||||
*/
|
||||
@Override
|
||||
public boolean onPrepareOptionsMenu (Menu menu) {
|
||||
MenuItem reply = menu.findItem(R.id.action_reply);
|
||||
if (mTabIndex == 1)
|
||||
reply.setVisible(true);
|
||||
else
|
||||
reply.setVisible(false);
|
||||
return true;
|
||||
}
|
||||
|
||||
private class SectionsPagerAdapter extends FragmentPagerAdapter {
|
||||
public SectionsPagerAdapter(FragmentManager fm) {
|
||||
|
||||
@@ -1293,7 +1293,7 @@ public class MangaListActivity extends SlidingActivity {
|
||||
mHlv.setOnFooterRefreshListener(new HfListView.OnFooterRefreshListener() {
|
||||
@Override
|
||||
public boolean onFooterRefresh() {
|
||||
if (lus.pageUp()) {
|
||||
if (lus.setPage(lastPage+1)) {
|
||||
mGetMode = NEXT_PAGE;
|
||||
getList();
|
||||
return true;
|
||||
|
||||
@@ -513,7 +513,7 @@ public class Data {
|
||||
public synchronized void addLocalFavourite(GalleryInfo galleryInfo) {
|
||||
int gid = galleryInfo.gid;
|
||||
|
||||
if (containsRead(gid)) {
|
||||
if (containsLocalFavourite(gid)) {
|
||||
updateGallery(galleryInfo);
|
||||
} else {
|
||||
addGallery(galleryInfo);
|
||||
|
||||
@@ -1,5 +1,7 @@
|
||||
package com.hippo.ehviewer.ehclient;
|
||||
|
||||
import java.util.Collections;
|
||||
import java.util.Comparator;
|
||||
import java.util.LinkedHashMap;
|
||||
import java.util.AbstractMap.SimpleEntry;
|
||||
import java.util.LinkedList;
|
||||
@@ -25,6 +27,8 @@ public class DetailParser {
|
||||
public static final int OFFENSIVE = 0x20;
|
||||
public static final int PINING = 0x40;
|
||||
|
||||
private static final CommentSort cs = new CommentSort();
|
||||
|
||||
private int mMode;
|
||||
|
||||
public int category;
|
||||
@@ -141,8 +145,10 @@ public class DetailParser {
|
||||
m = p.matcher(pageContent);
|
||||
comments = new LinkedList<Comment>();
|
||||
while (m.find()) {
|
||||
re |= COMMENT;
|
||||
comments.add(new Comment(m.group(1), m.group(2), m.group(3)));
|
||||
}
|
||||
Collections.sort(comments, cs);
|
||||
}
|
||||
return re;
|
||||
}
|
||||
@@ -188,4 +194,68 @@ public class DetailParser {
|
||||
type = ListUrls.UNKNOWN;
|
||||
return type;
|
||||
}
|
||||
|
||||
static class CommentSort implements Comparator<Comment> {
|
||||
private int compareNum(String n1, String n2, int median) {
|
||||
int re = 0;
|
||||
for (int i = 0; i < median; i++) {
|
||||
re *= 10;
|
||||
re += n1.charAt(i) - n2.charAt(i);
|
||||
}
|
||||
return re;
|
||||
}
|
||||
private int getMonth(String m) {
|
||||
if (m.equals("January"))
|
||||
return 1;
|
||||
else if (m.equals("February"))
|
||||
return 2;
|
||||
else if (m.equals("March"))
|
||||
return 3;
|
||||
else if (m.equals("April"))
|
||||
return 4;
|
||||
else if (m.equals("May"))
|
||||
return 5;
|
||||
else if (m.equals("June"))
|
||||
return 6;
|
||||
else if (m.equals("July"))
|
||||
return 7;
|
||||
else if (m.equals("August"))
|
||||
return 8;
|
||||
else if (m.equals("September"))
|
||||
return 9;
|
||||
else if (m.equals("October"))
|
||||
return 10;
|
||||
else if (m.equals("November"))
|
||||
return 11;
|
||||
else if (m.equals("December"))
|
||||
return 12;
|
||||
else
|
||||
return 0;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int compare(Comment c1, Comment c2) {
|
||||
int re = 0;
|
||||
Pattern p = Pattern.compile("(\\d{2}) (\\w+) (\\d{4}), (\\d{2}):(\\d{2})");
|
||||
Matcher m1 = p.matcher(c1.time);
|
||||
Matcher m2 = p.matcher(c2.time);
|
||||
if (!m1.find() || !m2.find())
|
||||
return 0;
|
||||
// year
|
||||
re += compareNum(m1.group(3), m2.group(3), 4);
|
||||
re <<= 4;
|
||||
// Month
|
||||
re += getMonth(m1.group(2)) - getMonth(m2.group(2));
|
||||
re <<= 5;
|
||||
// Day
|
||||
re += compareNum(m1.group(1), m2.group(1), 2);
|
||||
re <<= 5;
|
||||
// Hour
|
||||
re += compareNum(m1.group(4), m2.group(4), 2);
|
||||
re <<= 6;
|
||||
// Minute
|
||||
re += compareNum(m1.group(5), m2.group(5), 2);
|
||||
return re;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -14,6 +14,7 @@ import java.net.MalformedURLException;
|
||||
import java.net.URL;
|
||||
import java.net.UnknownHostException;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.regex.Matcher;
|
||||
import java.util.regex.Pattern;
|
||||
@@ -1516,6 +1517,44 @@ public class EhClient {
|
||||
|
||||
}
|
||||
|
||||
// Post comment
|
||||
public interface OnCommentListener {
|
||||
void onSuccess(List<Comment> comments);
|
||||
void onFailure(String eMsg);
|
||||
}
|
||||
|
||||
public void comment(final String detailUrl, final String comment,
|
||||
final OnCommentListener listener) {
|
||||
new Thread(new Runnable() {
|
||||
@Override
|
||||
public void run() {
|
||||
HttpHelper hp = new HttpHelper(mAppContext);
|
||||
hp.setOnRespondListener(new HttpHelper.OnRespondListener() {
|
||||
@Override
|
||||
public void onSuccess(String pageContent) {
|
||||
DetailParser parser = new DetailParser();
|
||||
parser.setMode(DetailParser.COMMENT);
|
||||
if (parser.parser(pageContent) == DetailParser.COMMENT) {
|
||||
listener.onSuccess(parser.comments);
|
||||
} else {
|
||||
listener.onFailure("parser error"); // TODO
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onFailure(String eMsg) {
|
||||
listener.onFailure(eMsg); // TODO
|
||||
}
|
||||
});
|
||||
hp.post(detailUrl, new String[][]{
|
||||
new String[]{"commenttext", comment},
|
||||
new String[]{"postcomment", "Post New"}});
|
||||
}
|
||||
}).start();
|
||||
}
|
||||
|
||||
// TODO
|
||||
|
||||
/********** Use E-hentai API ************/
|
||||
|
||||
// rate for gallery
|
||||
|
||||
@@ -336,6 +336,7 @@ public class HttpHelper {
|
||||
return null;
|
||||
}
|
||||
|
||||
/*
|
||||
public String post(String urlStr, String str) {
|
||||
mException = null;
|
||||
|
||||
@@ -420,7 +421,7 @@ public class HttpHelper {
|
||||
mException = new RedirectionException();
|
||||
return null;
|
||||
}
|
||||
|
||||
*/
|
||||
|
||||
public String postJson(String urlStr, JSONObject json) {
|
||||
mException = null;
|
||||
|
||||
@@ -1,24 +0,0 @@
|
||||
package com.hippo.ehviewer.view;
|
||||
|
||||
import com.hippo.ehviewer.R;
|
||||
|
||||
import android.content.Context;
|
||||
import android.util.AttributeSet;
|
||||
import android.view.LayoutInflater;
|
||||
import android.widget.LinearLayout;
|
||||
|
||||
public class SearchView extends LinearLayout {
|
||||
public SearchView(Context context) {
|
||||
super(context, null);
|
||||
}
|
||||
|
||||
public SearchView(Context context, AttributeSet attrs) {
|
||||
super(context, attrs);
|
||||
|
||||
LayoutInflater inflater = (LayoutInflater) context
|
||||
.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
|
||||
inflater.inflate(R.layout.search_view, this, true);
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
@@ -366,12 +366,12 @@ public class TagListView extends ListView {
|
||||
int deltaY = mLastEventY - mDownY;
|
||||
|
||||
if (mCellIsMobile) {
|
||||
if (deltaX < -mHoverCellOriginalBounds.width() / SENSITY)
|
||||
if (deltaX > mHoverCellOriginalBounds.width() / SENSITY)
|
||||
mIsDelete = true;
|
||||
else
|
||||
mIsDelete = false;
|
||||
|
||||
if (deltaX > mHoverCellOriginalBounds.width() / SENSITY)
|
||||
if (deltaX < -mHoverCellOriginalBounds.width() / SENSITY)
|
||||
mIsModify = true;
|
||||
else
|
||||
mIsModify = false;
|
||||
|
||||
@@ -103,20 +103,25 @@ public class DialogBuilder extends AlertDialog.Builder {
|
||||
* @return
|
||||
*/
|
||||
public DialogBuilder setView(View view, boolean center) {
|
||||
LinearLayout.LayoutParams lp;
|
||||
if (center) {
|
||||
lp = new LinearLayout.LayoutParams(
|
||||
LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT);
|
||||
lp.gravity = Gravity.CENTER;
|
||||
} else {
|
||||
lp = new LinearLayout.LayoutParams(
|
||||
LayoutParams.FILL_PARENT, LayoutParams.WRAP_CONTENT);
|
||||
}
|
||||
setView(view, lp);
|
||||
return this;
|
||||
}
|
||||
|
||||
public DialogBuilder setView(View view, LinearLayout.LayoutParams lp) {
|
||||
ScrollView scrollView = (ScrollView)mView.findViewById(R.id.scroll_view);
|
||||
scrollView.setVisibility(View.VISIBLE);
|
||||
LinearLayout customLayout = (LinearLayout)mView.findViewById(R.id.custom);
|
||||
customLayout.setVisibility(View.VISIBLE);
|
||||
if (center) {
|
||||
LinearLayout.LayoutParams lp = new LinearLayout.LayoutParams(
|
||||
LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT);
|
||||
lp.gravity = Gravity.CENTER;
|
||||
customLayout.addView(view, lp);
|
||||
} else {
|
||||
LinearLayout.LayoutParams lp = new LinearLayout.LayoutParams(
|
||||
LayoutParams.FILL_PARENT, LayoutParams.WRAP_CONTENT);
|
||||
customLayout.addView(view, lp);
|
||||
}
|
||||
customLayout.addView(view, lp);
|
||||
return this;
|
||||
}
|
||||
|
||||
|
||||