private void listAll() {
    ViewGroup root = mList;
    root.removeAllViews();

    // 列出所有已经安装的插件
    Collection<PluginDescriptor> plugins = PluginLoader.getPlugins();
    Iterator<PluginDescriptor> itr = plugins.iterator();
    while (itr.hasNext()) {
      final PluginDescriptor pluginDescriptor = itr.next();
      Button button = new Button(this);
      button.setPadding(10, 10, 10, 10);
      button.setText("插件id:" + pluginDescriptor.getPackageName() + ",点击查看");
      button.setOnClickListener(
          new View.OnClickListener() {

            @Override
            public void onClick(View v) {
              Intent intent = new Intent(PluginListActivity.this, PluginDetailActivity.class);
              intent.putExtra("plugin_id", pluginDescriptor.getPackageName());
              startActivity(intent);
            }
          });

      LayoutParams layoutParam =
          new LayoutParams(LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT);
      layoutParam.topMargin = 10;
      layoutParam.bottomMargin = 10;
      layoutParam.gravity = Gravity.LEFT;
      root.addView(button, layoutParam);
    }
  }
  @Override
  protected void applyTransformation(float interpolatedTime, Transformation t) {
    super.applyTransformation(interpolatedTime, t);

    if (interpolatedTime < 1.0f) {

      // Calculating the new bottom margin, and setting it
      mViewLayoutParams.bottomMargin =
          mMarginStart + (int) ((mMarginEnd - mMarginStart) * interpolatedTime);

      // Invalidating the layout, making us seeing the changes we made
      mAnimatedView.requestLayout();

      // Making sure we didn't run the ending before (it happens!)
    } else if (!mWasEndedAlready) {
      mViewLayoutParams.bottomMargin = mMarginEnd;
      mAnimatedView.requestLayout();

      if (mIsVisibleAfter) {
        mAnimatedView.setVisibility(View.GONE);
      }
      mWasEndedAlready = true;
    }
  }
    @SuppressWarnings("deprecation")
    @Override
    public View getView(int position, View convertView, ViewGroup parent) {
      Message message1 = (Message) this.getItem(position);

      ViewHolder holder;
      if (convertView == null) {
        holder = new ViewHolder();
        convertView = LayoutInflater.from(mContext).inflate(R.layout.sms_row, parent, false);
        holder.message = (EmojiconTextView) convertView.findViewById(R.id.message_text);
        holder.thumb = (FetchableImageView) convertView.findViewById(R.id.thumb);
        holder.message.setPadding(10, 10, 10, 10);
        convertView.setTag(holder);
      } else holder = (ViewHolder) convertView.getTag();
      if (message1.getMsgtype().equalsIgnoreCase("text")) {
        holder.message.setVisibility(View.VISIBLE);
        holder.thumb.setVisibility(View.GONE);

        holder.message.setText(message1.getMessage());
        LayoutParams lp = (LayoutParams) holder.message.getLayoutParams();
        if (message1.getIsmine().equals("yes")) {
          holder.message.setBackgroundResource(R.drawable.message_you);
          holder.message.setPadding(15, 15, 15, 15);
          lp.gravity = Gravity.RIGHT;
          lp.leftMargin = 50;
          lp.rightMargin = 20;
        }
        // If not mine then it is from sender to show orange background and
        // align to left
        else {
          holder.message.setBackgroundResource(R.drawable.message_from);
          holder.message.setPadding(15, 15, 15, 15);
          lp.gravity = Gravity.LEFT;
          lp.rightMargin = 50;
          lp.leftMargin = 20;
        }
        holder.message.setLayoutParams(lp);
        holder.message.setTextColor(mContext.getResources().getColor(R.color.Black));
      } else {
        LayoutParams lp1 = (LayoutParams) holder.thumb.getLayoutParams();
        holder.message.setVisibility(View.GONE);
        holder.thumb.setVisibility(View.VISIBLE);
        holder.thumb.setPadding(15, 15, 15, 15);
        if (message1.getMsgtype().equals("video")) {

          holder.thumb.setImage(message1.getMessage(), R.drawable.placeholder_video);
          final String url = DataManager.FILE_PATH + message1.getMessage().toString();
          holder.thumb.setOnClickListener(
              new View.OnClickListener() {

                @Override
                public void onClick(View v) {
                  // TODO Auto-generated method stub
                  Intent intent = new Intent(Intent.ACTION_VIEW);
                  intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
                  intent.setDataAndType(Uri.parse(url), "video/*");
                  mContext.startActivity(intent);
                }
              });
        } else if (message1.getMsgtype().equals("audio")) {
          holder.thumb.setImage(message1.getMessage(), R.drawable.placeholder_audio);
          final String url = DataManager.FILE_PATH + message1.getMessage();
          holder.thumb.setOnClickListener(
              new View.OnClickListener() {

                @Override
                public void onClick(View v) {
                  // TODO Auto-generated method stub
                  Uri myUri = Uri.parse(url);
                  Intent intent = new Intent(Intent.ACTION_VIEW);
                  intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
                  intent.setDataAndType(myUri, "audio/*");
                  mContext.startActivity(intent);
                }
              });
        } else if (message1.getMsgtype().equals("photo")) {
          holder.thumb.setImage(
              DataManager.FILE_PATH + message1.getMessage(), R.drawable.placeholder_image);
          final String url = DataManager.FILE_PATH + message1.getMessage();
          holder.thumb.setOnClickListener(
              new View.OnClickListener() {

                @Override
                public void onClick(View v) {
                  // TODO Auto-generated method stub
                  Intent intent = new Intent(Intent.ACTION_VIEW);
                  intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
                  intent.setDataAndType(Uri.parse(url), "image/*");
                  mContext.startActivity(intent);
                }
              });
        }
        if (message1.getIsmine().equals("yes")) {
          holder.thumb.setBackgroundResource(R.drawable.message_you);
          holder.thumb.setPadding(15, 15, 15, 15);
          lp1.gravity = Gravity.RIGHT;
          lp1.topMargin = 10;
          lp1.bottomMargin = 10;
          lp1.leftMargin = 50;
          lp1.rightMargin = 20;
        }
        // If not mine then it is from sender to show orange background and
        // align to left
        else {
          holder.thumb.setBackgroundResource(R.drawable.message_from);
          holder.thumb.setPadding(15, 15, 15, 15);
          lp1.gravity = Gravity.LEFT;
          lp1.topMargin = 10;
          lp1.bottomMargin = 10;
          lp1.rightMargin = 50;
          lp1.leftMargin = 20;
        }
        holder.thumb.setLayoutParams(lp1);
      }
      return convertView;
    }
  @Override
  public View getView(int position, View convertView, ViewGroup parent) {
    // TODO Auto-generated method stub
    String rich = Constants.RICH_TEXTS[position];

    // 通过迭代装饰方式构造解析器。
    IParser parser = new SmileyParser(mContext);
    parser = new ImageParser(mContext, parser);
    parser = new HyperlinkParser(mContext, parser);
    parser = new WeburlParser(mContext, parser);

    // 执行解析并返回解析文本段队列。
    ParseManager manager = new ParseManager();
    ArrayList<ParsedSegment> segments = manager.parse(parser, rich);

    // 用 Holder 模式更新列表数据。
    CustomLayout layout = null;
    ViewHolder holder = null;
    if (null == convertView) {
      layout = new CustomLayout(mContext);
      AbsListView.LayoutParams params =
          new AbsListView.LayoutParams(
              AbsListView.LayoutParams.MATCH_PARENT, AbsListView.LayoutParams.WRAP_CONTENT);
      layout.setLayoutParams(params);
      layout.setOrientation(LinearLayout.VERTICAL);
      layout.setBackgroundResource(R.drawable.list_item_background);

      holder = new ViewHolder();
      holder.views = new ArrayList<View>();
      layout.setTag(holder);
    } else {
      layout = (CustomLayout) convertView;
      holder = (ViewHolder) convertView.getTag();
    }

    int i = 0;
    for (ParsedSegment segment : segments) {
      if (TextUtils.isEmpty(segment.text)) {
        continue;
      }

      if (MatchType.None == segment.type) {
        TextView textView = null;
        if (null == convertView) {
          textView = new TextView(mContext);
          LayoutParams p = new LayoutParams(LayoutParams.MATCH_PARENT, LayoutParams.WRAP_CONTENT);
          p.bottomMargin =
              mContext.getResources().getDimensionPixelSize(R.dimen.rich_element_margin);
          textView.setLayoutParams(p);
          textView.setTextSize(TypedValue.COMPLEX_UNIT_SP, 20);

          // 自定义 ClickableSpan 点击背景,有两种方法:
          // 1、自定义 LinkMovementMethod,重写其 onTouchEvent 方法;
          // 2、重写 TextView 的 OnTouchListener。
          // 两种方法的核心思想都是获取 touch event 事件,通过对 TextView 中的 ClickableSpan
          // 文本设置和移除 BackgroundColorSpan 来改变其点击背景。
          if (Constants.USE_CUSTOM_LINK) {
            textView.setMovementMethod(mLinkMovementMethod);
          } else {
            textView.setMovementMethod(LinkMovementMethod.getInstance());
            textView.setOnTouchListener(onTouchListener);
          }

          textView.setClickable(false);

          layout.addView(textView);
          holder.views.add(textView);
        } else {
          textView = (TextView) holder.views.get(i);
        }

        textView.setText(segment.text);

        ++i;

      } else if (MatchType.Image == segment.type) {
        ImageView imgView = null;
        if (null == convertView) {
          imgView = new ImageView(mContext);
          LayoutParams p = new LayoutParams(LayoutParams.MATCH_PARENT, LayoutParams.WRAP_CONTENT);
          p.bottomMargin =
              mContext.getResources().getDimensionPixelSize(R.dimen.rich_element_margin);
          imgView.setMaxHeight(
              mContext.getResources().getDimensionPixelSize(R.dimen.image_max_height));
          imgView.setLayoutParams(p);

          layout.addView(imgView);
          holder.views.add(imgView);
        } else {
          imgView = (ImageView) holder.views.get(i);
        }

        // 异步加载图片。
        mImageLoader.displayImage(
            segment.text.toString(), imgView, mOptions, mAnimateFirstListener);

        ++i;
      }
    }

    return layout;
  }
  @Override
  public View onCreateView() {

    LinearLayout ll_container = new LinearLayout(context);
    ll_container.setOrientation(LinearLayout.VERTICAL);
    ll_container.setBackgroundColor(Color.TRANSPARENT);

    /** title */
    tv_title = new TextView(context);
    tv_title.setGravity(Gravity.CENTER);
    tv_title.setPadding(dp2px(10), dp2px(5), dp2px(10), dp2px(5));

    LayoutParams params = new LayoutParams(LayoutParams.MATCH_PARENT, LayoutParams.WRAP_CONTENT);
    params.topMargin = dp2px(20);

    ll_container.addView(tv_title, params);

    /** title underline */
    v_line_title = new View(context);
    ll_container.addView(v_line_title);

    /** listview */
    lv = new ListView(context);
    lv.setLayoutParams(new LayoutParams(LayoutParams.MATCH_PARENT, LayoutParams.WRAP_CONTENT, 1));
    lv.setCacheColorHint(Color.TRANSPARENT);
    lv.setFadingEdgeLength(0);
    lv.setVerticalScrollBarEnabled(false);
    lv.setSelector(new ColorDrawable(Color.TRANSPARENT));

    ll_container.addView(lv);

    /** cancel btn */
    tv_cancel = new TextView(context);
    tv_cancel.setGravity(Gravity.CENTER);
    LayoutParams lp = new LayoutParams(LayoutParams.MATCH_PARENT, LayoutParams.WRAP_CONTENT);
    lp.topMargin = dp2px(7);
    lp.bottomMargin = dp2px(7);
    tv_cancel.setLayoutParams(lp);

    ll_container.addView(tv_cancel);

    /** LayoutAnimation */
    TranslateAnimation animation =
        new TranslateAnimation(
            Animation.RELATIVE_TO_SELF,
            0f,
            Animation.RELATIVE_TO_SELF,
            0f,
            Animation.RELATIVE_TO_SELF,
            6f,
            Animation.RELATIVE_TO_SELF,
            0);
    animation.setInterpolator(new DecelerateInterpolator());
    animation.setDuration(350);
    animation.setStartOffset(150);

    lac = new LayoutAnimationController(animation, 0.12f);
    lac.setInterpolator(new DecelerateInterpolator());

    return ll_container;
  }
  /** 设置button的 宽度 以及监听 */
  private void setButton() {
    Display display = getWindowManager().getDefaultDisplay();
    int width = display.getWidth();
    int height = display.getHeight();
    int width0 = 2; // 边框宽度
    int width1 = 10; // 外部边框距左右边界距离
    int hight0 = 70; // 外部边框高度
    LinearLayout a_layout = (LinearLayout) findViewById(R.id.a_layout);
    LayoutParams param = (LayoutParams) a_layout.getLayoutParams();
    param.topMargin = 10;
    param.bottomMargin = 10;
    param.leftMargin = width1;
    param.rightMargin = width1;
    if (height == 1280 && width == 720) {
      hight0 = 70;
      width = width + 4;
      param.leftMargin = width1;
      param.rightMargin = width1 + 1;
    } else if (height == 854 && width == 480) {
      hight0 = 45;
      width1 = 18;
      width0 = 2;
      param.leftMargin = width1;
      param.rightMargin = width1 - 1;
    } else if (height == 800 && width == 480) {
      hight0 = 45;
      width1 = 18;
      width0 = 2;
      param.leftMargin = width1;
      param.rightMargin = width1 - 1;
    } else if (height >= 1750 && height <= 1920 && width == 1080) {
      width1 = 40; // 外部边框距左右边界距离
      hight0 = 100;
      param.leftMargin = width1;
      param.rightMargin = width1;
    }
    int hight1 = hight0 - width0 * 2; // button高度
    param.height = hight0;
    // view1 = (Button) findViewById(R.id.view_1);
    // view2 = (Button) findViewById(R.id.view_2);
    // view3 = (Button) findViewById(R.id.view_3);
    // view1.setWidth(width0);
    // view2.setWidth(width0);
    // view3.setWidth(width0);
    // view1.setHeight(hight1);
    // view2.setHeight(hight1);
    // view3.setHeight(hight1);

    int button_width = (width - width1 * 2 - 7 * width0) / 4;
    button_1 = (Button) findViewById(R.id.button_1);
    button_2 = (Button) findViewById(R.id.button_2);
    button_3 = (Button) findViewById(R.id.button_3);
    button_4 = (Button) findViewById(R.id.button_4);
    button_1.setOnClickListener(this);
    button_2.setOnClickListener(this);
    button_3.setOnClickListener(this);
    button_4.setOnClickListener(this);
    btnList.add(button_1);
    btnList.add(button_2);
    btnList.add(button_3);
    btnList.add(button_4);

    for (int i = 0; i < btnList.size(); i++) {
      btnList.get(i).setWidth(button_width);
      btnList.get(i).setHeight(hight1);
    }

    if (version < 4) {
      button_1.setBackgroundResource(R.drawable.left_shape_red2);
      button_4.setBackgroundResource(R.drawable.right_shape_white2);
    }
  }