URL로 Itemid를 가져와 JRoute에 전달하는 방법


14

사용자 컴포넌트에 특정보기에 대한 메뉴 항목이 있습니다. 이 메뉴 항목에 첨부 Template Style된 표준 템플릿이 아닌 다른 메뉴 항목을 선택했습니다. 메뉴를 통해보기에 액세스하면 URL에 첨부되어 있으므로 잘 작동합니다 Itemid.

이제 JRoute를 사용하여 다른 뷰와 링크를 연결하려고하지만 JRoute가 원하는 URL을 생성하지 않습니다.

echo JRoute::_('index.php?option=com_example&view=reporting');

/index.php?option=com_example&view=reporting

JRoute URL에 Itemid를 추가하지 않으므로 메뉴 항목에 대해 선택된 템플릿 스타일이 작동하지 않습니다.

Itemid를 "계산"하고 ( jos_menu열의 테이블 에서 쿼리를 수행하는 것을 제외하고 link) JRoute에 첨부하는 방법이 있습니까?


u보다 itemid를 알고 있으면 report & Itemid = 123입니다. 이 절차는 사용자 지정 구성 요소가 이미 게시 된 경우 자동으로 수행해야하므로 권장하지 않습니다.
Dan

답변:


20

여기 내가 사용한 기술이 있습니다 (어디에서 찾은지를 기억할 수 없습니다).

$app = JFactory::getApplication(); 
$menu = $app->getMenu();
$menuItem = $menu->getItems( 'link', 'index.php?option=com_example&view=reporting', true );
echo JRoute::_('index.php?Itemid='.$menuItem->id);

이것은 나를 위해 놀라운 일을했습니다.


4

JRoute의 출력은 피드에 따라 다릅니다.

JRoute::_("index.php?option=com_content&view=article&id=10"); 

이외의 것을 반환 할 수 있습니다

JRoute::_("index.php?option=com_content&view=article&id=10&catid=5"); 

실제로 catid = 5에 대한 메뉴 항목 범주 블로그 목록이 있으면 후자가 menu-url을 제공 할 수 있습니다 (이 정확한 URL은 테스트하지 않았습니다). 다른 get-parameters를 사용하여 다른 결과를 얻으십시오 (@Fedik이 말한 것처럼 매우 잘못됨)


3

여기서 핵심은 구성 요소 router.php 파일 (프론트 엔드 구성 요소의 루트 폴더에 있음)을 해당 메뉴 항목을 검색하고 선택하는 논리로 설정하는 것입니다. 나는 이것이 자동으로 일어나는 것을보고 싶지만, 내가 아는 한 이것은 사실이 아닙니다.

이 코드 블록을 컨텐츠에 가장 적합한 메뉴 항목을 자동으로 찾는 데 사용할 수있는 일부 유형의 도우미 기능으로 작동하는 것이 가장 좋습니다.

가장 적합한 메뉴 항목을 얻기 위해 여러 사용자 정의 구성 요소에서 사용한 코드는 다음과 같습니다.

// I use this first empty array to avoid having unset properties in my query
$base_array = array('Itemid'=>'', 'option'=>'', 'view'=>'', 'layout'=>'', 'id'=>'');

$app =& JFactory::getApplication();
$menu       = $app->getMenu();
$active = $menu->getActive();

// hack to protect the actual current item as well as the search module or other places that use JRoute::_('index.php');
if (count($query)==2 && isset($query['option']) && isset($query['Itemid']) && $query['option'] && $query['Itemid']) {
    return $segments;
}

// start with no match found
$match = false;
$match_level = 0;

$query += $base_array;

// we want to find a menu item for this if possible. If the active menu item is the current menu item then we should see if there is a better match.
if (empty($query['Itemid']) || ($query['Itemid'] == $active->id && empty($query['task']))) {
    // load all menu items
    $items = $menu->getMenu();

    // use the current item over others if it ties for the best match
    if ($active->query['option'] == $query['option']) {
        $match_level = 1;
        $match = $active;
        if ($active->query['view'] == $query['view']) {
            $match_level = 2;
            if ($active->query['layout'] == $query['layout'] || ($query['layout']=='default' && !$active->query['layout'])) {
                $match_level = 3;
                if ($active->query['id'] == $query['id']) {
                    $match_level = 4;
                }
            }
        }
    }

    // loop through each menu item in order
    foreach ($items as $item) {
        $item->query += $base_array;
        // base check is that it is for this component
        // then cycle through each possibility finding it's match level
        if ($item->query['option'] == $query['option']) {
            $item_match = 1;
            if ($item->query['view'] == $query['view']) {
                $item_match = 2;
                if (!$query['layout'] && $item->query['layout']) {
                    $query['layout'] = 'default';
                }
                if ($item->query['layout'] == $query['layout'] || ($query['layout']=='default' && !$item->query['layout'])) {
                    $item_match = 3;
                    if ($item->query['id'] == $query['id']) {
                        $item_match = 4;
                    }
                }
            }
        }

        // if this item is a better match than our current match, set it as the best match
        if ($item_match > $match_level) {
            $match = $item;
            $match_level = $item_match;
        }

    }

    // if there is a match update Itemid to match that menu item
    if ($match) {
        $query['Itemid'] = $match->id;
        $menuItem = $menu->getItem($match->id);
    } else {
        $menuItem = $menu->getActive();
    }
}

이 모든 것은 일종의 엉망입니다 (그리고 누군가가 있다면 개선을 좋아할 것입니다!).하지만 작업이 완료됩니다. 현재 메뉴 항목이 가장 일치하면 항상 해당 메뉴 항목을 사용합니다.

그렇지 않으면 구성 요소 이름->보기 이름-> 레이아웃 이름-> id 값을 기준으로 가장 일치하는 것을 찾아야합니다. 오른쪽으로 갈수록 더 잘 어울립니다!


2

Afaik JRoute 은 제공되지 않은 경우 활성 Itemid(및 활성 option) 을 가져옵니다 . 그래도 문제가 해결되지 않으면 코드에 대한 호출이 Itemid없이 시작된다는 의미입니다. 그렇다면 가장 쉬운 방법은 초기 호출에 Itemid를 추가하는 것입니다.

메뉴 항목을 찾아야하는 경우 직접 쿼리를 수행하지 않고 JMenu를 대신 사용합니다.


경우에 따라 JRouter가 미친 URL을 반환 할 수 있음을 발견했습니다. 자신의 Itemid를 제공하려고하면 JRoute::_('index.php?option=com_example&view=reporting&Itemid=10')JRouter의 예가 반환 될 수 있습니다 /current-path?view=reporting&Itemid=10... 특정한 것이 있습니까?
Fedik
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.