2012-01-27 32 views
13

Tôi đang cố gắng để có được chế độ xem sau: Mô tả trên trang web bên trái và giá trị ở bên phải. ví dụ .:Android HorizontalScrollView với layout_gravity đúng cách hoạt động sai

enter image description here


Vấn đề là các văn bản có thể dài vì vậy tôi quấn nó trong HorizontalScrollView. Tôi đang sử dụng sau xml:

<LinearLayout 
    android:layout_width="fill_parent" 
    android:layout_weight="1" 
    android:orientation="horizontal" 
    android:layout_height="wrap_content"> 
    <TextView 
     android:layout_height="wrap_content" 
     android:textColor="#000000" 
     android:layout_width="110dp" 
     android:text="Description:"/> 
    <HorizontalScrollView 
     android:layout_weight="1" 
     android:layout_width="wrap_content" 
     android:layout_height="wrap_content"> 
     <TextView 
      android:layout_height="wrap_content" 
      android:textColor="#000000" 
      android:layout_width="wrap_content" 
      android:layout_gravity="right" 
      android:text="Very1 very2 very3 very4 very5 very6 long text"/> 
    </HorizontalScrollView> 
</LinearLayout> 

Và đây là vấn đề. Sau scroling sang trái góc nhất mà tôi đã xem (thiếu đầu văn bản):

enter image description here


Sau scroling sang phải nhất góc Tôi đã xem (không gian bổ sung sau khi văn bản):

enter image description here


Nếu tôi thay đổi TextView android: layout_gravity thành "left" mọi thứ hoạt động như mong đợi. Sau scroling sang trái góc nhất mà tôi đã xem:

enter image description here


Sau scroling sang phải góc nhất mà tôi đã xem:

enter image description here


có phải là một cách để làm cho nó hoạt động chính xác và căn chỉnh văn bản đến đúng trang khi nó ngắn?

Trả lời

1

Không sử dụng bất kỳ trọng lượng bố cục nào cho TextView, nó sẽ hoạt động như bạn mong đợi.

Như bạn đã nói, có vấn đề ở đó, hành vi của nó sai với trọng lực phải.

+0

Nhưng tôi muốn các văn bản để được ở bên phải, nếu nó là ngắn (xem hình ảnh đầu tiên). Nếu tôi loại bỏ trọng lực - hành vi chính xác như với lực hấp dẫn được đặt sang trái. Câu hỏi đặt ra là: làm thế nào để làm cho nó đúng align hoặc scrollable, tùy thuộc vào độ dài văn bản. – Remi

1

Tôi biết điều này đã không hoạt động trong một năm, nhưng nó vẫn là một vấn đề trong năm 2013. Tạo một lớp mới mở rộng HorizontalScrollView và sao chép/dán mã bên dưới.

@Override 
public boolean onTouchEvent(MotionEvent ev) { 
    autoScrolling = false; 
    return super.onTouchEvent(ev); 
} 

private int getScrollRange() { 
    int scrollRange = 0; 
    if(getChildCount() > 0) { 
     View child = getChildAt(0); 
     scrollRange = Math.max(0, child.getWidth() - (getWidth() - getPaddingLeft() - getPaddingRight())); 
    } 
    return scrollRange; 
} 

private boolean gravityRight = false; 
private boolean autoScrolling = false; 

@Override 
protected void onLayout(boolean changed, int left, int top, int right, int bottom) { 
    // HorizontalScrollView is broken for Gravity.RIGHT. So we're fixing it. 
    if(getChildCount() == 0) return super.onLayout(changed, left, top, right, bottom); 
    int childWidth = getChildAt(0).getWidth(); 
    super.onLayout(changed, left, top, right, bottom); 
    int delta = getChildAt(0).getWidth() - childWidth; 
    AdvancedDisplay view = getView(); 
    ScrollableDisplay.LayoutParams p = (LayoutParams) view.getLayoutParams(); 
    int horizontalGravity = p.gravity & Gravity.HORIZONTAL_GRAVITY_MASK; 
    int verticalGravity = p.gravity & Gravity.VERTICAL_GRAVITY_MASK; 
    if(horizontalGravity == Gravity.RIGHT) { 
     if(getScrollRange() > 0) { 
      gravityRight = true; 
      p.gravity = Gravity.LEFT | verticalGravity; 
      view.setLayoutParams(p); 
      super.onLayout(changed, left, top, right, bottom); 
     } 
    } 
    else if(gravityRight) { 
     if(getScrollRange() == 0) { 
      gravityRight = false; 
      p.gravity = Gravity.RIGHT | verticalGravity; 
      view.setLayoutParams(p); 
      super.onLayout(changed, left, top, right, bottom); 
     } 
    } 
    if(gravityRight && delta > 0) { 
     autoScrolling = false; 
     scrollBy(delta, 0); 
     autoScrolling = true; 
    } 
} 

@Override 
public void computeScroll() { 
    if(autoScrolling) return; 
    super.computeScroll(); 
} 

@Override 
public void scrollTo(int x, int y) { 
    if(autoScrolling) return; 
    super.scrollTo(x, y); 
} 
2

Tôi biết nó được một lúc nhưng đây là một cách giải quyết (thử nghiệm):

public class RightAlignedHorizontalScrollView extends HorizontalScrollView { 
private boolean mGravityRight = false; 
private boolean mAutoScrolling = false; 

public RightAlignedHorizontalScrollView(Context context) { 
    super(context); 
} 

public RightAlignedHorizontalScrollView(Context context, AttributeSet attrs) { 
    super(context, attrs); 
} 

public RightAlignedHorizontalScrollView(Context context, AttributeSet attrs, int defStyle) { 
    super(context, attrs, defStyle); 
} 

public View getChildView() { 
    return getChildAt(0); 
} 

private int getScrollRange() { 
    int scrollRange = 0; 
    if (getChildCount() > 0) { 
     View child = getChildAt(0); 
     scrollRange = Math.max(0, child.getWidth() - (getWidth() - getPaddingLeft() - getPaddingRight())); 
    } 
    return scrollRange; 
} 

@Override 
protected void onLayout(boolean changed, int left, int top, int right, int bottom) { 
    // HorizontalScrollView is broken for Gravity.RIGHT. So we're fixing it. 
    mAutoScrolling = false; 
    int childWidth = getChildView().getWidth(); 
    super.onLayout(changed, left, top, right, bottom); 
    int delta = getChildView().getWidth() - childWidth; 
    View childView = getChildView(); 
    FrameLayout.LayoutParams p = (LayoutParams) childView.getLayoutParams(); 
    int horizontalGravity = p.gravity & Gravity.HORIZONTAL_GRAVITY_MASK; 
    int verticalGravity = p.gravity & Gravity.VERTICAL_GRAVITY_MASK; 
    if (horizontalGravity == Gravity.RIGHT) { 
     if (getScrollRange() > 0) { 
      mGravityRight = true; 
      p.gravity = Gravity.LEFT | verticalGravity; 
      childView.setLayoutParams(p); 
      super.onLayout(changed, left, top, right, bottom); 
     } 
    } else if (mGravityRight) { 
     if (getScrollRange() == 0) { 
      mGravityRight = false; 
      p.gravity = Gravity.RIGHT | verticalGravity; 
      childView.setLayoutParams(p); 
      super.onLayout(changed, left, top, right, bottom); 
     } 
    } 
    if (mGravityRight && delta > 0) { 
     scrollBy(delta, 0); 
     mAutoScrolling = true; 
    } 
} 

@Override 
public void computeScroll() { 
    if (mAutoScrolling) return; 
    super.computeScroll(); 
} 

@Override 
public void scrollTo(int x, int y) { 
    if (mAutoScrolling) return; 
    super.scrollTo(x, y); 
} 

}

Các vấn đề liên quan