Android - 如何让我的按钮更改画布上的绘图

时间:2011-03-29 19:46:05

标签: android button canvas

我的代码在下面。

我真正不了解的是如何使用按钮来更改我正在绘制的图形。我有点希望能够调用类似于重绘图形的方法,但我看不出我会怎么做。

干杯

菲尔

    package com.android.phil.smartphonecharts;

import android.app.Activity;
import android.content.Context;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.graphics.Paint.Style;
import android.os.Bundle;
import android.view.Display;
import android.view.View;
import android.widget.ImageButton;
import android.widget.RelativeLayout;

public class GraphActivity extends Activity 
{
    int[][] graphData =  {{591566,601708,591566,600509},
               {593573,594182,586592,591489},
               {600088,602233,596358,599401},
               {592071,601150,592071,600120},
               {592292,593668,586095,591998},
               {599672,599672,591552,592353},
               {601442,602856,592655,599676},
               {606747,610577,601314,601480},
               {609190,609678,604883,608299},
               {609659,610142,606671,608738},
               {604655,609576,604238,608527},
               {605158,607207,602377,603708},
               {607479,609148,604210,606009},
               {600472,607140,597344,606290},
               {603668,604520,598648,602001},
               {606743,608430,604950,605229},
               {604232,609133,603288,609133},
               {600916,605409,599716,605103},
               {600264,602341,598683,599738},
               {598570,599359,595182,598334},
               {597654,602046,597271,600007},
               {592071,601150,592071,600120},
               };

    int highest = 0;
    int lowest = 0;
    int multiY = 10;
    int multiX = 21;
    int graphToggle = 0;
    int numbPeriods = 22;

    float previous = 0;
    float current = 0;
    float stepX = 0;
    float stepY = 0;
    float stepPercent = 0;
    float topLeftX = 0;
    float topLeftY = 0;
    float bottomRightX = 0;
    float bottomRightY = 0;
    float graphHeight = 0;
    float graphWidth = 0;
    double graphLow = 0;
    double graphHigh = 0;
    double graphRange = 0;
    double n = 0;
    double m = 0;

    public int graph_toggle = 0;
    public int data_toggle=0;

    public float width;
    public float height;

    @Override
    public void onCreate(Bundle savedInstanceState) 
    {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.graph_layout);

        Display display = getWindowManager().getDefaultDisplay();
        width = display.getWidth();
        height = display.getHeight();

        final ImageButton graph_toggle_button = (ImageButton) findViewById(R.id.graph_toggle);
        final ImageButton graph_settings_button = (ImageButton) findViewById(R.id.graph_type);
        final ImageButton data_toggle_button = (ImageButton) findViewById(R.id.data_toggle);
        final ImageButton moving_averages_button = (ImageButton)findViewById(R.id.moving_averages);

        //Define the view into which our canvas will be drawn.
        int graph_display_height = (int)(height*0.75);
        int graph_display_width = (int)width;
        CustomDrawableView mCustomDrawableView = new CustomDrawableView(this);

        RelativeLayout graphLayout = (RelativeLayout)findViewById(R.id.graph_window);

        RelativeLayout.LayoutParams lp = new RelativeLayout.LayoutParams(graph_display_width,graph_display_height);
        lp.addRule(RelativeLayout.ALIGN_PARENT_BOTTOM);

        mCustomDrawableView.setLayoutParams(lp);
        graphLayout.addView(mCustomDrawableView);

        graph_toggle_button.setOnClickListener(new View.OnClickListener() 
        {
            public void onClick(View arg0) 
            {
                if (graph_toggle==2)
                {
                    graph_toggle=0;
                }
                else
                {
                    graph_toggle++;
                }

                if (graph_toggle==0)
                {
                    graph_settings_button.setImageResource(R.drawable.close);
                }
                if (graph_toggle==1)
                {
                    graph_settings_button.setImageResource(R.drawable.ohlc_bars);
                }
                if(graph_toggle==2)
                {
                    graph_settings_button.setImageResource(R.drawable.candles);
                }               
            }         
        });
        data_toggle_button.setOnClickListener(new View.OnClickListener() 
        {
            public void onClick(View arg0) 
            {
                if (data_toggle==2)
                {
                    data_toggle=0;
                }
                else
                {
                    data_toggle++;
                }

                if (data_toggle==0)
                {
                    data_toggle_button.setImageResource(R.drawable.ohlc_bars_daily);
                }
                if (data_toggle==1)
            {
                    data_toggle_button.setImageResource(R.drawable.ohlc_bars_weekly);
                }
                if(data_toggle==2)
                {
                    data_toggle_button.setImageResource(R.drawable.ohlc_bars_monthly);
                }               
            }         
        });          
    }    
    public class CustomDrawableView extends View
    {
        public CustomDrawableView(Context context)
        {
            super(context);
        }
        @Override
        protected void onDraw(Canvas canvas)
        {
            invalidate();
            super.onDraw(canvas);

            // custom drawing code here
            // remember: y increases from top to bottom
            // x increases from left to right

            Paint paint = new Paint();
            paint.setStyle(Paint.Style.FILL);

            // make the entire canvas white
            paint.setColor(Color.TRANSPARENT);
            canvas.drawPaint(paint);

            //Set co-ordinates of display window using half the heigh of the screen and
            //indent the window by 5%
            topLeftX = (float)0;
            topLeftY = (float)(height*0.01);

           bottomRightX = (float)(width*0.80);
           bottomRightY = (float)(height*0.45);

           //Width and height of the window are defined by the X and Y co-ords calculated above.
           graphWidth = bottomRightX-topLeftX;
           graphHeight = bottomRightY-topLeftY;

           //Calculate the HighestHigh and LowestLow of the data set.
           highest = mHighestHigh(graphData,graphToggle);
           lowest = mLowestLow(graphData,graphToggle);

           //Total graph range that we want to display based on the values in data

           //Calculate the Lowest value from the data set drawn on the graph
           graphLow = lowest*0.99;

            //Calculate the highest value from the data set drawn on the graph
            graphHigh = highest*1.01;
            //is equal to the highest value minus lowest value +/-5%
            graphRange = graphHigh-graphLow;

            //stepX = space between vertical bars
            stepX = graphWidth/multiX;
            //stepY = space between horizontal bars
            stepY = graphHeight/multiY;
            //step = 1 hundredth of the total height of the box.
            stepPercent = (graphHeight)/100;

            //draw the outline box
            paint.setStyle(Style.STROKE);
            paint.setColor(Color.WHITE);
            canvas.drawRect(topLeftX, topLeftY, bottomRightX, bottomRightY, paint);

            //draw horizontal lines
            paint.setColor(Color.WHITE);
            paint.setTextSize(10);

            canvas.drawText(mD2S2DP(graphLow/100), (float)(width*0.81), bottomRightY+5, paint);
            for (int i = 1; i < multiY; i++)
            {//canvas.drawLine(startX, startY, stopX, stopY, paint)
                paint.setColor(Color.rgb(255,0,0));
                canvas.drawLine(topLeftX, topLeftY+(stepY*i), bottomRightX, topLeftY+(stepY*i), paint);
                paint.setColor(Color.WHITE);            
                paint.setTextSize(10);
                canvas.drawText("Hello Android!", (float)(width*0.81), topLeftY+(stepY*i)+5,paint);
            }
            paint.setColor(Color.WHITE);
            paint.setTextSize(10);
            canvas.drawText(mD2S2DP(graphHigh/100), (float)(width*0.81), topLeftY+5, paint);


            //draw vertical lines and diagonal random price lines
            for (int i = 1; i < multiX; i++)
            {//canvas.drawLine(startX, startY, stopX, stopY, paint)
                paint.setColor(Color.rgb(255,255,255));
                paint.setStrokeWidth(1);
                canvas.drawLine(topLeftX+(stepX*i), topLeftY, topLeftX+(stepX*i), bottomRightY, paint);
            }

            //Inverts the data set and draws it at the appropriate 
            n = (topLeftY-bottomRightY)/graphRange;
            m = bottomRightY-(n*graphLow);

            //draw close line graph
            for (int i = 1; i < (multiX+1); i++)
            {
                //DashPathEffect dashPath = new DashPathEffect(new float[]{10,10}, 1);
                //paint.setPathEffect(dashPath);
                previous = (float)(n*graphData[i-1][3]+m);
                current = (float)(n*graphData[i][3]+m);

                if(previous>current)
                {
                    paint.setColor(Color.rgb(255,0,0));
                    paint.setStrokeWidth(2);
                }
                else
                {
                    paint.setColor(Color.rgb(0,255,0));
                    paint.setStrokeWidth(2);
                }
                //canvas.drawLine(startX, startY, stopX, stopY, paint)

                canvas.drawLine(topLeftX+(stepX*(i-1)),previous, topLeftX+(stepX*i), current, paint);
            }
        }
    }

    public int mHighestHigh(int[][]data, int graphToggle)
    {//method to calculate the highest high of the data set;
        int highValue = graphToggle==0?data[0][3]:data[0][1];
        for (int i=1; i<data.length; i++)
        {
            if ((graphToggle==0?data[i][3]:data[i][1]) > highValue)
            {
                highValue = graphToggle==0?data[i][3]:data[i][1];   //new maximum
            }
        }
        System.out.println("highValue="+highValue);
        return highValue;
    }

    public int mLowestLow(int[][]data,int graphToggle)
    {//method to calculate the lowest low of the data set;
        int lowValue = graphToggle==0?data[0][3]:data[0][2];
        for (int i=1; i<data.length; i++)
        {
            if ((graphToggle==0?data[i][3]:data[i][2]) < lowValue)
            {
                lowValue = graphToggle==0?data[i][3]:data[i][2];   //new minimum
            }
        }
        System.out.println("lowValue=:"+lowValue);
        return lowValue;
    }
    public String mD2S2DP(double doubleValue)
    {//method to turn a double to a string and return it to two dp

        //Convert the double to a string.
        String tempString = Double.toString(doubleValue);
        //Find the location of the decimal point in the string.
        int index = tempString.indexOf('.');
        //remove anything from the string after 2 characters after the decimal point.
        String returnString = tempString.substring(0, index+3);
        //return the result.
        return returnString;
    }
}

1 个答案:

答案 0 :(得分:2)

该方法是invalidate(),它在主线程循环中安排重新绘制您调用它的视图。实际上,您不应该在自定义视图onDraw()中调用它(除非您需要重复重绘,以执行一些类似帧的动画)。

通常查看更改影响方面的内容的方法(如ImageView.setImageDrawable())也可以调用invalidate()。因此,您可以添加执行更改的CustomDrawableView.setGraphData(data)方法,然后调用invalidate()

当然,您也可以从按钮单击侦听器代码中调用mCustomDrawableView.invalidate()

请注意,如果更改还涉及视图父级的大小或位置,您还可以调用requestLayout()