最新消息:雨落星辰是一个专注网站SEO优化、网站SEO诊断、搜索引擎研究、网络营销推广、网站策划运营及站长类的自媒体原创博客

javascript - Binding a select to an array of objects in Aurelia and matching on ID - Stack Overflow

programmeradmin6浏览0评论

So, I have a list of all users, which populates the options of a select.

<option repeat.for="user of userService.users">
  ${user.firstName} ${user.lastName}
</option>

And I have an ining group record which has a list of users attached to it. I follow the cheat sheat instructions and bind it to a single index of the model.

<select value.bind="group.users[0]">
    <option repeat.for="user of userService.users" model.bind="user">
      ${user.firstName} ${user.lastName}
    </option>
</select>

So, the ining user in the group is identical to one of the users in the list:

{
    id: 123,
    firstName: 'Matt',
    lastName: 'Davis'
}

But when the group is loaded and bound to the view, the correct user is not chosen from the select. Actually, I would expect this as JavaScript would look for referential equality.

Ideally, I'd like Aurelia to find that the ining record is as above and (a) search through the list of options testing equality (b) that I've defined in some extension (maybe a filter?), (c) select it in the list and (d) propagate that selection back into the record so that the record is now referentially in sync.

I would rather not fall back to a trigger that manually does this because I will have lots and lots of these kinds of selects throughout my application.

I would settle, albeit sadly, for (a) and (c).

So, I have a list of all users, which populates the options of a select.

<option repeat.for="user of userService.users">
  ${user.firstName} ${user.lastName}
</option>

And I have an ining group record which has a list of users attached to it. I follow the cheat sheat instructions and bind it to a single index of the model.

<select value.bind="group.users[0]">
    <option repeat.for="user of userService.users" model.bind="user">
      ${user.firstName} ${user.lastName}
    </option>
</select>

So, the ining user in the group is identical to one of the users in the list:

{
    id: 123,
    firstName: 'Matt',
    lastName: 'Davis'
}

But when the group is loaded and bound to the view, the correct user is not chosen from the select. Actually, I would expect this as JavaScript would look for referential equality.

Ideally, I'd like Aurelia to find that the ining record is as above and (a) search through the list of options testing equality (b) that I've defined in some extension (maybe a filter?), (c) select it in the list and (d) propagate that selection back into the record so that the record is now referentially in sync.

I would rather not fall back to a trigger that manually does this because I will have lots and lots of these kinds of selects throughout my application.

I would settle, albeit sadly, for (a) and (c).

Share Improve this question edited Oct 12, 2016 at 22:51 Jeremy Danyow 26.4k12 gold badges90 silver badges135 bronze badges asked Nov 25, 2015 at 15:39 Matthew James DavisMatthew James Davis 12.3k7 gold badges63 silver badges91 bronze badges 1
  • github./aurelia/binding/issues/94 – Jeremy Danyow Commented Nov 25, 2015 at 17:02
Add a ment  | 

1 Answer 1

Reset to default 17

Specify a matcher function (equality parer):

<select value.bind="group.users[0]" matcher.bind="userComparer">
  <option repeat.for="user of userService.users" model.bind="user">
    ${user.firstName} ${user.lastName}
  </option>
</select>
export class Foo {
  ...
  userComparer = (userA, userB) => userA.id === userB.id;
  ...
}

Below is the original answer (before 11/30/2015 release)...

Until this is supported natively by aurelia's select binding I would try something like this:

<select value.bind="group.users[0] | userToId:userService.users">
  <option repeat.for="user of userService.users" model.bind="user.id">
    ${user.firstName} ${user.lastName}
  </option>
</select>
export class UserToIdValueConverter {
  toView(user, users) {
    return user ? user.id : null;
  }

  fromView(id, users) {
    return users.find(u => u.id === id);
  }
}

Here's a plunker: http://plnkr.co/edit/15XHkQ?p=preview

You'll probably want to make the converter generic so you can reuse it throughout your app... maybe something like this:

export class ToIdValueConverter {
  toView(obj, idPropertyName, objs) {
    return obj ? obj[idPropertyName] : null;
  }

  fromView(id, idPropertyName, objs) {
    return objs.find(o => o[idPropertyName] === id);
  }
}
<select value.bind="group.users[0] | toId:'id':userService.users">
  <option repeat.for="user of userService.users" model.bind="user.id">
    ${user.firstName} ${user.lastName}
  </option>
</select>

Keep an eye on this issue for updates on native framework support for this scenario.

发布评论

评论列表(0)

  1. 暂无评论