2012-03-20 66 views
0

我正在构建“日视图”日历应用程序。我已经创建了带有列表视图的空白日历,现在需要添加我的约会。如何在Android中的ListView上绘制形状

我的光标是全部设置,我能够检索我的约会,只需要在列表视图中绘制它们。棘手的部分是,每个列表行是30分钟,我的一些约会可能会延长,长达几个小时。因此,需要能够指定列表视图上应该绘制约会的位置,即使它当前不在屏幕上。

+0

您是否想在24小时内根据预约时间绘制矩形块? – Pavandroid 2012-03-20 10:09:59

+0

@Pavandroid是的,这是正确的。 – dbDev 2012-03-20 16:40:06

回答

1

我做了同样的观点。我开发了自己的CustomView并将其保存在ScrollView中。这个customView的高度是24 * 60倾角。所以视图的高度会随着我们保持倾角而不是px(我希望你知道px和dip之间的差异)而增加,宽度将是设备屏幕的宽度。

我无法与您分享完整的代码。但是,可以在这里部分粘贴。这会给你一个清晰的画面,处理每一件事。

public class CustomDayView extends View implements OnTouchListener{ 

    private Paint p; 
    private Paint textp; 
    private Paint roundRectP; 
    private int parentWidth = 0; 
    private int parentHeight = 0; 
    private int X_OFFSET = 5; 
    private int Y_OFFSET = 5; 
    private int HOUR_BLOCK_HEIGHT = 60; 
    private int font_max_width; 
    private ScrollView _scrollView; 
    private int least_time_in_hours = 24*60;//6 * 60 
    private RectF _rects[]; 
    private int font_height; 
    private Context context; 


    public CustomDayEmployeeView(Context context) { 
     super(context); 
     this.context = context; 
     init(); 
    } 
    public CustomDayEmployeeView(Context context, AttributeSet attrs) { 
     super(context, attrs); 
     this.context = context; 
     init(); 
    } 
    public CustomDayEmployeeView(Context context, AttributeSet attrs, 
      int defStyle) { 
     super(context, attrs, defStyle); 
     this.context = context; 
     init(); 
    } 
    private void init(){ 
     //Creating Paint Objects 
    //setting color 
     //setting Fonts 
     this.setOnTouchListener(this); 
    calculateRectValues(); 
    } 

    private void calculateRectValues() { 
     // Calculating the Rects to draw in the paint this includes x,y points starting of the rect and width and height of the rectangle. 
    int font_max_width = calculate the width needed to draw the hours from 0 to 24 hours; 
    for(int i=0;i<no of appts;i++) 
     _rects[j] = new RectF(font_max_width, convertTimetoSeconds("09:30"), screenwidth-font_max_width , convertTimetoSeconds("11:30"); 

    } 

    private int convertTimetoSeconds(String _startTime) { 
     // TODO Auto-generated method stub 
     int total = Integer.parseInt(_startTime.substring(0,_startTime.indexOf(":"))) * 60; 
     total += Integer.parseInt(_startTime.substring(_startTime.indexOf(":")+1, _startTime.length())); 
     return total; 
    } 

    protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { 
     // TODO Auto-generated method stub 
     super.onMeasure(widthMeasureSpec, heightMeasureSpec); 
     parentWidth = MeasureSpec.getSize(widthMeasureSpec); 
     parentHeight = MeasureSpec.getSize(heightMeasureSpec); 
     calculateRectValues(); 
     setMeasuredDimension(screenwidth,24 * HOUR_BLOCK_HEIGHT); 
    } 


    public void draw(Canvas canvas) { 
     // TODO Auto-generated method stub 
     super.draw(canvas); 

     for(int i=0;i<25;i++) 
     { 
      String preString = ""; 
      String poststring = ""; 

      if(i == 12) 
      { 
       preString = "Noon"; 
       poststring = ""; 

      } 
      else if(i%12 == 0) 
      { 
       preString = "12"; 
       poststring = " AM"; 
      } 
      else if(i<12) 
      { 
       preString = i+""; 
       poststring = " AM"; 
      } 
      else 
      { 
       preString = i%12+""; 
       poststring = " PM"; 
      } 
      canvas.drawText(preString, X_OFFSET+3, i * HOUR_BLOCK_HEIGHT + font_height, p); 
      canvas.drawText(poststring, X_OFFSET+p.measureText(preString), i * HOUR_BLOCK_HEIGHT + font_height, p); 
      p.setTypeface(Typeface.create(Typeface.DEFAULT, Typeface.NORMAL)); 
      p.setColor(Color.parseColor("#cbcaca")); 
      p.setStrokeWidth(0.2f); 
      p.setPathEffect(new DashPathEffect(new float[] {1,2}, 0)); 
      canvas.drawLine(font_max_width, i * (HOUR_BLOCK_HEIGHT)+ font_height/2+HOUR_BLOCK_HEIGHT/2, parentWidth-8, i * (HOUR_BLOCK_HEIGHT)+ font_height/2+HOUR_BLOCK_HEIGHT/2, p); 
      p.setColor(Color.parseColor("#f1f1f1")); 
      p.setPathEffect(new PathEffect()); 
      p.setStrokeWidth(0.2f); 
      canvas.drawLine(font_max_width, i * HOUR_BLOCK_HEIGHT+ font_height/2, parentWidth-8, i * HOUR_BLOCK_HEIGHT+ font_height/2, p); 

     } 
      for(int j=0;j<no of appts;j++) 
      { 
        canvas.drawRoundRect(_rects[j], 3, 3, roundRectP); 
         canvas.drawText(obj._title, _rects[j].left+X_OFFSET,_rects[j].top + font_height + Y_OFFSET, textp); 
      } 
     } 
    } 


    public boolean onTouch(View v, MotionEvent event) { 
     // TODO Auto-generated method stub 
     int x = (int) event.getX(); 
     int y = (int) event.getY(); 
     for(int j=0;j<no of appts;j++) 
     { 
      if(_rects[j].contains(x, y)) 
      { 
     //Selected J appointmrnt 
     } 
     } 
     return true; 
    } 
} 

我想这会帮助你。只需创建Object并将ArrayList中的约会传递给此对象的init,然后执行所需的调整即可。

+0

非常感谢你的代码,它是帮助。一个问题,我看到你声明了一个ScrollView,但是你什么时候使用它? – dbDev 2012-03-21 15:14:37

+0

其实我的项目有问题。我需要将视图滚动到此视图上可见的第一个约会。所以,为了滚动,我将scrollview的对象从MainActivity发送到这个CustomDayView。之后,我使它成为全局的,以便通过CustomView滚动到任何x,y点。 – Pavandroid 2012-03-21 15:21:48

+0

有没有更新?如果无误,请选择此为正确答案。 – Pavandroid 2012-03-22 01:36:30

-1

如果不在屏幕上,则不需要绘制任何东西。

我会以这种方式实现列表适配器:getItem(int position)方法返回每个列表项代表的时间(实际上是时间间隔)。 getView(int position, View convertView, ViewGroup parent)定义哪些约会在给定位置的相应项目的间隔内,并基于该信息更新项目的视图。您可能还需要an endless adapter