168043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)// Copyright 2013 The Chromium Authors. All rights reserved.
25821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Use of this source code is governed by a BSD-style license that can be
35821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// found in the LICENSE file.
45821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
568043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)#include "ash/shelf/shelf_navigator.h"
65821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
758537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)#include "ash/ash_switches.h"
85d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#include "ash/shelf/shelf.h"
95d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#include "ash/shelf/shelf_item_types.h"
10f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)#include "ash/shelf/shelf_model.h"
1158537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)#include "base/command_line.h"
125d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#include "base/macros.h"
135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "testing/gtest/include/gtest/gtest.h"
145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)namespace ash {
165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)namespace {
185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
195d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)class ShelfNavigatorTest : public testing::Test {
205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public:
215d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  ShelfNavigatorTest() {}
225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) protected:
242a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  virtual void SetUp() OVERRIDE {
25f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)    model_.reset(new ShelfModel);
2690dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
2758537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)    // Add APP_LIST for test.
285d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    ShelfItem app_list;
2958537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)    app_list.type = TYPE_APP_LIST;
3058537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)    model_->Add(app_list);
3158537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)
3290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    // Initially, applist launcher item is only created.
3390dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    int total_num = model_->item_count();
3490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    EXPECT_EQ(1, total_num);
3590dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    EXPECT_TRUE(model_->items()[0].type == TYPE_APP_LIST);
3690dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
3790dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    // Add BROWSER_SHORTCUT for test.
385d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    ShelfItem browser_shortcut;
3990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    browser_shortcut.type = TYPE_BROWSER_SHORTCUT;
4090dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    model_->Add(browser_shortcut);
415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
435d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  void SetupMockShelfModel(ShelfItemType* types,
445d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)                           int types_length,
455d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)                           int focused_index) {
465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    for (int i = 0; i < types_length; ++i) {
475d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      ShelfItem new_item;
485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      new_item.type = types[i];
495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      new_item.status =
50424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles)          (types[i] == TYPE_PLATFORM_APP) ? STATUS_RUNNING : STATUS_CLOSED;
515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      model_->Add(new_item);
525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    // Set the focused item.
555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (focused_index >= 0) {
565d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      ShelfItem focused_item =model_->items()[focused_index];
57424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles)      if (focused_item.type == TYPE_PLATFORM_APP) {
585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        focused_item.status = STATUS_ACTIVE;
595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        model_->Set(focused_index, focused_item);
605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      }
615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
64f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  const ShelfModel& model() { return *model_.get(); }
655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) private:
67f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  scoped_ptr<ShelfModel> model_;
685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
695d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  DISALLOW_COPY_AND_ASSIGN(ShelfNavigatorTest);
705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)};
715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7258537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)}  // namespace
735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
745d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)TEST_F(ShelfNavigatorTest, BasicCycle) {
75424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles)  // An app shortcut and three platform apps.
765d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  ShelfItemType types[] = {
77424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles)    TYPE_APP_SHORTCUT, TYPE_PLATFORM_APP, TYPE_PLATFORM_APP, TYPE_PLATFORM_APP,
785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  };
79f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  // ShelfModel automatically adds BROWSER_SHORTCUT item at the
8058537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)  // beginning, so '3' refers the first TYPE_PLATFORM_APP item.
81f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  SetupMockShelfModel(types, arraysize(types), 3);
8258537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)
8358537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)  EXPECT_EQ(4, GetNextActivatedItemIndex(model(), CYCLE_FORWARD));
8458537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)
8558537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)  // Fourth one.  It will skip the APP_SHORTCUT at the beginning of the list and
8658537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)  // the APP_LIST item which is automatically added at the end of items.
8758537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)  EXPECT_EQ(5, GetNextActivatedItemIndex(model(), CYCLE_BACKWARD));
8858537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)}
8958537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)
905d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)TEST_F(ShelfNavigatorTest, WrapToBeginning) {
915d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  ShelfItemType types[] = {
92424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles)    TYPE_APP_SHORTCUT, TYPE_PLATFORM_APP, TYPE_PLATFORM_APP, TYPE_PLATFORM_APP,
935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  };
94f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  SetupMockShelfModel(types, arraysize(types), 5);
9558537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)
9658537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)  // Second one.  It skips the APP_LIST item at the end of the list,
9758537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)  // wraps to the beginning, and skips BROWSER_SHORTCUT and APP_SHORTCUT
9858537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)  // at the beginning of the list.
9958537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)  EXPECT_EQ(3, GetNextActivatedItemIndex(model(), CYCLE_FORWARD));
10058537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)}
10158537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)
1025d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)TEST_F(ShelfNavigatorTest, Empty) {
103f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  SetupMockShelfModel(NULL, 0, -1);
1045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(-1, GetNextActivatedItemIndex(model(), CYCLE_FORWARD));
1055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(-1, GetNextActivatedItemIndex(model(), CYCLE_BACKWARD));
1065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
1075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1085d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)TEST_F(ShelfNavigatorTest, SingleEntry) {
1095d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  ShelfItemType type = TYPE_PLATFORM_APP;
110f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  SetupMockShelfModel(&type, 1, 2);
11158537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)
11258537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)  // If there's only one item there and it is already active, there's no item
11358537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)  // to be activated next.
11458537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)  EXPECT_EQ(-1, GetNextActivatedItemIndex(model(), CYCLE_FORWARD));
11558537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)  EXPECT_EQ(-1, GetNextActivatedItemIndex(model(), CYCLE_BACKWARD));
11658537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)}
11758537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)
1185d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)TEST_F(ShelfNavigatorTest, NoActive) {
1195d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  ShelfItemType types[] = {
120424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles)    TYPE_PLATFORM_APP, TYPE_PLATFORM_APP,
1215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  };
1225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Special case: no items are 'STATUS_ACTIVE'.
123f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  SetupMockShelfModel(types, arraysize(types), -1);
1245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // If there are no active status, pick the first running item as a fallback.
12658537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)  EXPECT_EQ(2, GetNextActivatedItemIndex(model(), CYCLE_FORWARD));
12758537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)  EXPECT_EQ(2, GetNextActivatedItemIndex(model(), CYCLE_BACKWARD));
12858537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)}
12958537e28ecd584eab876aee8be7156509866d23aTorne (Richard Coles)
1305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}  // namespace ash
131