【问题标题】:Binding a Windows Phone 7 button's action to a method in Expression Blend 4将 Windows Phone 7 按钮的操作绑定到 Expression Blend 4 中的方法
【发布时间】:2011-07-22 13:03:58
【问题描述】:

我是第一次试用 Windows Phone 7 开发版。我决定尝试从 Expression Blend 4 中的默认示例移植一个 Silverlight Timer 示例。完整的 silverlight 计时器示例将 TimerModel 类绑定到计时器、启动/停止切换开关等。我已经弄清楚了如何创建数据源/数据上下文并将属性绑定到屏幕上的事物。但是,作为 void 的 Reset() 方法不会出现在 Windows Phone 7 应用程序的可绑定选项中。它在两者中是完全相同的类,但由于某种原因,void 方法不可绑定。我需要在 Windows Phone 7 中没有的完整 Silverlight 应用程序中启用某些功能吗?当它是数据源时,是否有特别的东西使类的属性或方法可绑定?这只是 Windows Phone 7 的 Silverlight 功能子集的限制之一吗?


下面是类,在两个应用程序中都是相同的。我想将按钮的点击绑定到 Reset() 方法。

namespace Time
{
    using System;
    using System.ComponentModel;
    using System.Windows.Threading;
    using System.Windows.Data;

    public class TimerModel : INotifyPropertyChanged
    {
        private bool isRunning;
        private DispatcherTimer timer;
        private TimeSpan time;
        private DateTime lastTick;

        public string FormattedTime
        {
            get 
            {
                return string.Format("{0:#0}:{1:00}:{2:00.00}", this.time.Hours, this.time.Minutes, (this.time.Seconds + (this.time.Milliseconds / 1000.0d)));
            }
        }

        private void UpdateTimes()
        {
            this.NotifyPropertyChanged("FormattedTime");
            this.NotifyPropertyChanged("Hours");
            this.NotifyPropertyChanged("Minutes");
            this.NotifyPropertyChanged("Seconds");
        }

        public bool Increment
        {
            get;
            set;
        }

        public int Hours
        {
            get
            {
                return this.time.Hours;
            }
            set
            {
                this.time = this.time.Add(TimeSpan.FromHours(value - this.time.Hours));
                this.UpdateTimes();
            }
        }

        public int Minutes
        {
            get
            {
                return this.time.Minutes;
            }
            set
            {
                this.time = this.time.Add(TimeSpan.FromMinutes(value - this.time.Minutes));
                this.UpdateTimes();
            }
        }

        public int Seconds
        {
            get
            {
                return this.time.Seconds;
            }
            set
            {
                this.time = this.time.Add(TimeSpan.FromSeconds(value - this.time.Seconds));
                this.UpdateTimes();
            }
        }

        public bool IsRunning
        {
            get { return this.isRunning; }
            set
            {
                if (this.isRunning != value)
                {
                    this.isRunning = value;
                    if (this.isRunning)
                    {
                        this.StartTimer();
                    }
                    else
                    {
                        this.StopTimer();
                    }
                    this.NotifyPropertyChanged("IsRunning");
                }
            }
        }

        private void StartTimer()
        {
            if (this.timer != null)
            {
                this.StopTimer();
            }
            this.timer = new DispatcherTimer();
            this.timer.Interval = TimeSpan.FromMilliseconds(1);
            this.timer.Tick += this.OnTimerTick;
            this.lastTick = DateTime.Now;
            this.timer.Start();
        }

        private void StopTimer()
        {
            if (this.timer != null)
            {
                this.timer.Stop();
                this.timer = null;
            }
        }

        private void OnTimerTick(object sender, EventArgs e)
        {
            DateTime now = DateTime.Now;
            TimeSpan diff = now - this.lastTick;
            this.lastTick = now;

            if (this.Increment)
            {
                this.time = this.time.Add(diff);
            }
            else
            {
                this.time = this.time.Subtract(diff);
            }
            if (this.time.TotalMilliseconds <= 0)
            {
                this.time = TimeSpan.FromMilliseconds(0);
                this.IsRunning = false;
            }
            this.UpdateTimes();
        }

        public void Reset()
        {
            this.time = new TimeSpan();
            this.UpdateTimes();
        }

        public TimerModel()
        {
        }

        public event PropertyChangedEventHandler PropertyChanged;

        private void NotifyPropertyChanged(string propertyName)
        {
            if (this.PropertyChanged != null)
            {
                this.PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
            }
        }
    }

}

【问题讨论】:

    标签: data-binding silverlight-4.0 windows-phone-7 binding expression-blend


    【解决方案1】:

    我使用 Caliburn Micro MVVM 框架。它允许按约定进行绑定,因此如果您调用按钮 RefreshButton 并且您的视图模型中有一个名为 RefreshButton 的方法,它将自动绑定到 Click 事件。非常强大且简单。

    【讨论】:

    • 不错!我最近听到了很多关于 Caliburn 框架的信息,但还没有研究过。看来现在是个好时机。谢谢!
    【解决方案2】:

    我发现 Silverlight 正在使用 stock CallMethodAction 操作,这在 Windows Phone 7 中不可用。看来我有两个选择:

    1. 像传统表单一样使用 onClick 事件,只需使用代码隐藏以编程方式调用方法。
    2. 创建我自己的自定义操作以重新创建CallMethodActionThere is also an open source project which contains a port of the method from full-blown Silverlight, which you can find on Codeplex.

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多