একটি নিজস্ব ফিল্ড উইজেট ফর্ম প্রদর্শন করা সম্ভব?


21

আমি পুরো নোড সম্পাদনা ফর্মের প্রসঙ্গে একটি ফিল্ড উইজেট ফর্ম এম্বেড করতে আগ্রহী।

আমি drupal_get_for ব্যবহার করে অতীতে সম্পূর্ণ ফর্মগুলি প্রদর্শিত করেছি তবে এটি একা ফিল্ড ফর্মগুলির জন্য প্রয়োগ বলে মনে হচ্ছে না।

একটি কার্যক্ষেত্র উইজেট ফর্ম প্রদর্শন করা কি সম্ভব? এটি করার সর্বোত্তম উপায় কী হবে?

উভয় ক্ষেত্রের উইজেট এবং "সাধারণ" ফর্মগুলি খুব একইরকম মনে হয়, তাই যদি এটি সম্ভব না হয় তবে উইজেট ফর্মটিকে একটি সাধারণ ফর্ম হিসাবে "পরিবর্তন" করার কী প্রয়োজন হবে?

এই প্রশ্নটি অনুরূপ কিছু চাইছে বলে মনে হচ্ছে তবে আমি উত্তরটি বুঝতে পারি না। এই উত্তরটি hook_field_widget_for_alter ব্যবহার করে নির্দিষ্ট করে ; আমি যা বুঝতে পারি না তা হ'ল ফিল্ড ফর্মটি কীভাবে প্রদর্শিত হবে তা তৈরি হওয়ার পরে এটি কীভাবে হুক হবে না।

উত্তর:


18

ভিবিও মোডিফাই.অ্যাকশন.ইন্সে এই জাতীয় কিছু করে:

$form_key = 'bundle_' . $bundle_name;
$form[$form_key] = array(
  '#type' => 'fieldset',
  '#title' => $label,
  '#parents' => array($form_key),
);  
field_attach_form($context['entity_type'], $entity, $form[$form_key], $form_state, LANGUAGE_NONE);  

সুতরাং, আপনার সত্তার ধরণ, সত্তা (যা কেবলমাত্র বান্ডিল কী সেট সহ একটি ফাঁকা বস্তু হতে পারে, এটিই আসলে ব্যবহার করা হয়), উইজেটগুলি যে ফর্মটি যুক্ত করা হয়েছে তা এবং ভাষা need আপনি যদি উইজেটগুলি ফর্মের মধ্যে আরও গভীরভাবে এম্বেড করতে চান (তবে in ফর্ম নয়, তবে [ফর্ম [$ ফর্ম_কি] যেমন আমি করেছিলেন, এমনকি আরও গভীর), তবে সেই ফর্ম অ্যারেতে # প্যারেন্টস সেট থাকা দরকার।

অবশ্যই, লক্ষ্য করুন যে এটি সত্তা টাইপ এবং বান্ডেলের সমস্ত ক্ষেত্রের উইজেটগুলি এম্বেড করবে। এইভাবে সংযুক্তি ফাংশনগুলি লেখা হয়েছিল। এদিকে ঘুরতে আপনাকে প্রচুর কোড পুনরায় উদ্ভাবন করতে হবে; ভারী উত্তোলন করে এমন আসল কোডটি দেখুন । আমি যা করি তা ক্ষেত্রের দৃষ্টান্তগুলির মধ্য দিয়ে যায়, প্রতিটি $ ক্ষেত্রের নাম পান, এবং যদি ক্ষেত্রের ধরণটি আমাকে আগ্রহী না করে, আমি সেট করেছিলাম $form[$form_key][$field_name]['#access'] = FALSE; যা এই উইজেটগুলিকে দর্শন থেকে আড়াল করে।

সম্পাদনা: ঠিক আছে, টোটুলগুলিতে টোটুল_ফিল্ড_ইনভোক_ফিল্ড রয়েছে () যা তত্ত্ব অনুসারে আপনাকে প্রতি ক্ষেত্রের ভিত্তিতে কাজ করতে দেয়। যদিও আমি এটি কখনও ব্যবহার করি নি। উপরের লেখাটি আমার প্রত্যক্ষ অভিজ্ঞতা।


দুর্দান্ত উত্তর। আমি এটির সাথে কাজ করে দিনের একটি ভাল অংশ ব্যয় করেছি এবং এটি আমার ইচ্ছা মতো কাজ করেছে। অনুগ্রহপূর্বক সম্মানিত, এবং আমি ওপিকে এটির সঠিক উত্তর হিসাবে গ্রহণ করার পরামর্শ দিচ্ছি। আমি একটি ছদ্মবেশী বিষয়বস্তুর প্রকার তৈরি করে শেষ করেছি যাতে আমি অন্য যে কোনও বিষয়বস্তুর প্রকারের মতো আমার ক্ষেত্রগুলিকে নিয়ন্ত্রণ করতে পারি, #access = FALSEসেটাকে পরিবর্তে যা এই প্রসঙ্গে হ্যাকি মনে হয়েছিল।
লেথারিওন

আমি যা ভয় পেয়েছিলাম তা নিশ্চিত করার জন্য ধন্যবাদ: একক ক্ষেত্র উইজেটটি নিজের ব্যবহারিকভাবে ব্যবহারযোগ্য নয়।
এসএমটিএফ

7

আমি ttk দ্বারা প্রস্তাবিত ফাংশনটি নিবিড়ভাবে ব্যবহার করেছিলাম, তবে আমার মনে হয় যে সাম্প্রতিক আপডেটে কিছু গোলমেলে ...

এখানে পূর্ববর্তী সমাধানটির একটি নতুন সংস্করণ রয়েছে যা ড্রুপাল 7.22 এবং সিটিওলস 7.x-1.3 এর সাথে ভালভাবে কাজ করে।

সুতরাং, আগের পোস্টের মতো আপনি নিজের কাস্টম ফাংশনটিকে এভাবে কল করেন:

my_field_attach_form('field_body', 'node', 'blog',  $node, $form, $form_state, LANGUAGE_NONE);

লক্ষ্য করুন যে সত্তার বান্ডিলটি এখন একটি প্যারামিটার। আমি এটি করেছি কারণ আমি ব্যবহারকারীদের সম্পাদনা করার জন্য এই ফাংশনটি ব্যবহার করছিলাম। এইভাবে, এটি ট্যাক্সোনমি শব্দ বা অন্য কোনও সত্তার জন্যও ব্যবহার করা যেতে পারে।

এবং my_field_attach_formহিসাবে সংজ্ঞায়িত করা হয়:

function my_field_attach_form($field_name, $entity_type, $bundle, $entity, &$form, &$form_state, $langcode = NULL) {

  // Set #parents to 'top-level' if it doesn't exist.
  $form += array('#parents' => array());

  // If no language is provided use the default site language.
  $options = array(
    'language' => field_valid_language($langcode),
    'default' => TRUE,
  );

  // Append to the form
  ctools_include('fields');
  $field_instance = field_info_instance($entity_type, $field_name, $bundle);
  $form += (array) ctools_field_invoke_field($field_instance, 'form', $entity_type, $entity, $form, $form_state, $options);
}

এই ফাংশনটি আমাকে অনেক সময় বাঁচিয়েছে, আশা করি এটি আপনার জন্যও হবে!


5

ctools_field_invoke_field()পদ্ধতিটি ব্যবহার করে সমাধানটি এখানে দেওয়া হল । আপনার কাস্টম ফর্ম ফাংশনে, যুক্ত করুন:

$form = array();
$node = new stdClass();
$node->type = 'blog';
my_field_attach_form('field_body', 'node', $node, $form, $form_state, LANGUAGE_NONE);

যেখানে my_field_attach_formফাংশন হিসাবে সংজ্ঞায়িত করা হয়

function my_field_attach_form($field_name, $entity_type, $entity, &$form, &$form_state, $langcode = NULL) {
  // Set #parents to 'top-level' if it doesn't exist.
  $form += array('#parents' => array());

  // If no language is provided use the default site language.
  $options = array(
    'language' => field_valid_language($langcode),
    'default' => TRUE,
  );
  module_load_include("inc","ctools","includes/fields");
  $form += (array) ctools_field_invoke_field($field_name, 'form', $entity_type, $entity, $form, $form_state, $options);
}

দ্রষ্টব্য, আপনার সাইটে সিটিউল সক্ষম হওয়া দরকার। এটি খুব খারাপ যে ড্রুপাল ডিফল্টরূপে কোনও সহায়ক ফাংশন অন্তর্ভুক্ত করে না।


2

আমি সিটিউল পদ্ধতিতে কাজ করতে অক্ষম হয়েছি এবং পরিবর্তে এটি করার সিদ্ধান্ত নিয়েছি।

এই কোডটি কোনও ফর্ম ফাংশনের অভ্যন্তরে থাকবে, সুতরাং $ ফর্ম এবং $ ফর্ম_স্টেটটি ইতিমধ্যে পাস করা হবে।

function form_function($form, &$form_state) {

প্রথমে কোনও ধরণের খালি নোড তৈরি করুন যার ক্ষেত্রটি আপনি রেন্ডার করতে যাচ্ছেন।

    $entity = new stdClass();
    $entity->title = "Temp Object";
    $entity->type = "node_type";
    node_object_prepare($entity);

আমি ফর্ম ভেরিয়েবলগুলি সদৃশ করেছি যাতে আমি মূলটি ক্লোবার না করি।

    $temp_form       = $form;
    $temp_form_state = $form_state;
    field_attach_form("node", $entity, $temp_form, $temp_form_state);

আপনি যে ক্ষেত্রটি সন্ধান করছেন তা টানুন এবং এটিকে ফর্মটিতে যুক্ত করুন।

    $form["field"] = $temp_form["existing_field"];
}

আমি এই পদ্ধতিটি একটি স্বনির্ধারিত ফর্মের উপর বিভাগীয় বাছাই উইজেট, শ্রেণীবদ্ধ চেকবক্স উইজেট এবং হায়ারার্কিকাল সিলেক্ট উইজেটকে রেন্ডার করতে ব্যবহার করেছি । (বিভাগশাসন স্বতঃসমাপ্ত উইজেট রেন্ডার করে তবে জমা দেওয়ার সময় একটি ত্রুটি নিক্ষেপ করে)

শেষ পর্যন্ত রেন্ডার এবং মুদ্রণ

drupal_render(drupal_get_form("form_function"))

এটি কাস্টম আকারে ফিল্ড উইজেট ব্যবহার করার সহজ উপায় বলে মনে হচ্ছে। এটি যদিও বিদ্যমান বান্ডিলের উপর নির্ভর করে। আমার ক্ষেত্রে আমি একটি ডামি কনটেন্ট প্রকার ব্যবহার করি যেখানে আমি প্রয়োজনীয় ক্ষেত্রগুলি তৈরি এবং কনফিগার করি। এটি কিছুটা হ্যাকি তবে অন্যান্য পদ্ধতির জন্যও এটি প্রয়োজনীয়। কেবলমাত্র লক্ষণীয়: ctools_field_invoke_field()উপরে বর্ণিত পদ্ধতিটিও কাজ করে।
বার্নহার্ড ফার্স্ট

0

আমি indivisual ক্ষেত্রগুলি ব্যবহার করে ফর্ম তৈরি করেছি

field_default_form('entity_type', $entity, $field,$field_instance,LANGUAGE_NONE,$default_value, $form, $form_state);

এটির জন্য প্রয়োজনীয় উইজেট ফর্মটি ফিরিয়ে দেওয়া উচিত যা কোনও রূপে যেমন ব্যবহার করা যেতে পারে

 $custom_form['form_element_to_display'] = field_default_form('entity_type', $entity, $field,$field_instance,LANGUAGE_NONE,$default_value, $custom_form, $custom_form_state);

উপরের 2 টি প্যারামিটারের মানগুলি পেতে:

$field = field_info_field($field_name);
$field_instance = field_info_instance('node', $field_name, $node_type);

অন্যান্য পরামিতিগুলির জন্য আপনি এপিআই লিঙ্কটি এখানে পরীক্ষা করতে পারেন

এটি সামগ্রী ধরণের ক্ষেত্রে সংজ্ঞায়িত ডিফল্ট উইজেট ফর্মটি দেয়।

আশা করি এটি কাউকে সাহায্য করবে :)

আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.