0

Mac OSX ドックや Windows のタスクバーと同じように、画面の下部全体を占める LinearLayout があります。コンテンツが動的になるため、xml を使用せずにプログラムで作成しています。ただし、アイコン (ImageView オブジェクト) の配置に問題があります。アイコン間の距離を指定したいのですが(アイコンを互いに近づけたり、離したりします。オプションで、最初または最後にスペースを保持することもできます)、setMargins、setGravityなどはすべて明らかな顕著な視覚的変化なしで失敗しました。

現在の様子はこんな感じです。

LayoutParams で重みが指定されている場合、LinearLayout 全体に均等に分散された 5 つのアイコン

これは LinearLayout に適用されます。

setOrientation( LinearLayout.HORIZONTAL );

これは ImageView (LinearLayout 内のアイコン) に適用されます。

LayoutParams lp = new LayoutParams( LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT, (1) ); // weight has to be specified, otherwise only will show 1 icon
imageIcon.setGravity( Gravity.CENTER_HORIZONTAL );

重量が指定されていない場合:

LayoutParams で重みが指定されていない場合、同じスペースを占める 5 つのアイコン

これは LinearLayout に適用されます。

setOrientation( LinearLayout.HORIZONTAL );

これは ImageView (LinearLayout 内のアイコン) に適用されます。

LayoutParams lp = new LayoutParams( LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT /* , (1)  */); // weight has to be specified, otherwise only will show 1 icon
imageIcon.setGravity( Gravity.CENTER_HORIZONTAL );

質問:

  1. LinearLayout 内の ImageView 間の距離を制御するにはどうすればよいですか? それを制御するために使用されるコードについて説明してください。私は無駄にAndroidのドキュメントを検索してきました...

  2. LayoutParams の「重み」パラメータが行う魔法のことを誰か説明できますか? 欠落している ImageView のデバッグに非常に長い時間を費やし、試行錯誤を通じて魔法の「重み」パラメーターを見つけましたが、ドキュメントに明確な説明がなければ、なぜそのような強力なことを行うのかまだわかりません

編集: LinearLayout (緑のコンテナー) のコードを挿入

public class GameSliderView extends LinearLayout {

    private Context                 mContext;
    private Vector<GameEntryView>   mGameEntries;

    public GameSliderView(Context context) {
        super(context);
        mContext = context;
        mGameEntries = new Vector<GameEntryView>();
        setOrientation( LinearLayout.HORIZONTAL );
    }

    public void addGameEntry( String szIconUrl ) {
        GameEntryView gameEntry = new GameEntryView(mContext);
        LayoutParams lp = new LayoutParams( LayoutParams.MATCH_PARENT, LayoutParams.MATCH_PARENT );
        this.setGravity( Gravity.CENTER_HORIZONTAL );
//      lp.setMargins( 0, 0, 0, 0 );
        gameEntry.setLayoutParams( lp );
        gameEntry.loadIcon( szIconUrl );
        gameEntry.requestLayout();
        mGameEntries.add( gameEntry );
        addView( gameEntry );
    }

}

ゲームのアイコン:

public class GameEntryView extends RelativeLayout {

    private Context         mContext;
    private GameIconView    mGameIcon;
//  private ImageView       mNewIcon;

    private String          mIconUrl;

    public GameEntryView(Context context) {
        super(context);
        mContext = context;
    }

    @Override
    protected void onLayout( boolean changed, int l, int t, int r, int b ) {
        int iChildCount = this.getChildCount();
        for ( int i = 0; i < iChildCount; i++ ) {
            View pChild = this.getChildAt(i);
            pChild.layout(0, 0, pChild.getMeasuredWidth(), pChild.getMeasuredHeight());
        }
    }

    @Override
    protected void onMeasure( int widthMeasureSpec, int heightMeasureSpec ) {
        int iParentWidth = MeasureSpec.getSize( widthMeasureSpec );
        int iParentHeight = MeasureSpec.getSize( heightMeasureSpec );
        this.setMeasuredDimension( iParentWidth, iParentHeight );

        int iChildCount = this.getChildCount();
        for ( int i = 0; i < iChildCount; i++ ) {
            View pChild = this.getChildAt(i);
            this.measureChild( 
                    pChild,
                    MeasureSpec.makeMeasureSpec( iParentWidth, MeasureSpec.EXACTLY),
                    MeasureSpec.makeMeasureSpec( iParentHeight, MeasureSpec.EXACTLY)
            );
        }
    }

    public void loadIcon( String szUrl ) {
        mGameIcon = new GameIconView( mContext );
        addView( mGameIcon );

        ImageManager.getInstance( mContext ).get( szUrl, new OnImageReceivedListener() {

            @Override
            public void onImageReceived(String source, Bitmap bitmap) {
                mGameIcon.setImageBitmap( bitmap );
                mGameIcon.setLayoutParams( new LayoutParams( LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT ) );
                postInvalidate();
            }
        });
    }

    public String getIconUrl() {
        return mIconUrl;
    }

    /**
     *  @author Hakim Hauston
     *  @desc   Resizable ImageView - surprised that Android library did not include this?
     *  @ref    http://stackoverflow.com/questions/5554682/android-imageview-adjusting-parents-height-and-fitting-width
     */
    class GameIconView extends ImageView {

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

        @Override
        protected void onMeasure( int widthMeasureSpec, int heightMeasureSpec ) {
            Drawable d = getDrawable();
            if ( d != null ) {
                float fScale = 0.90f;
                int iHeight = (int) (MeasureSpec.getSize( heightMeasureSpec ) * fScale);
                int iWidth = (int) ((iHeight * d.getIntrinsicWidth() / d.getIntrinsicHeight()) * fScale);
                setMeasuredDimension( iWidth,  iHeight );
                Log.d("GameEntryView", "GameEntryView.onMeasure: measureSpec: (" + widthMeasureSpec + ", " + heightMeasureSpec + ");");
                Log.d("GameEntryView", "GameEntryView.onMeasure: intrinsic: (" + d.getIntrinsicWidth() + ", " + d.getIntrinsicHeight() + ");");
                Log.d("GameEntryView", "GameEntryView.onMeasure: calculated: (" + iWidth + ", " + iHeight + ");");
            } else {
                super.onMeasure(widthMeasureSpec, heightMeasureSpec);
            }
        }

    }

}
4

1 に答える 1