ফ্র্যাগমেন্ট ম্যানেজার

FragmentManager হল আপনার অ্যাপের টুকরোগুলিতে ক্রিয়া সম্পাদনের জন্য দায়ী ক্লাস, যেমন যোগ করা, অপসারণ করা বা প্রতিস্থাপন করা এবং সেগুলিকে ব্যাক স্ট্যাকে যুক্ত করা।

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

এই পৃষ্ঠাটি কভার করে:

  • কিভাবে FragmentManager অ্যাক্সেস করবেন।
  • আপনার ক্রিয়াকলাপ এবং টুকরাগুলির সাথে সম্পর্কযুক্ত FragmentManager ভূমিকা৷
  • FragmentManager দিয়ে কীভাবে ব্যাক স্ট্যাক পরিচালনা করবেন।
  • আপনার টুকরোগুলিতে ডেটা এবং নির্ভরতা কীভাবে সরবরাহ করবেন।

ফ্র্যাগমেন্ট ম্যানেজার অ্যাক্সেস করুন

আপনি একটি কার্যকলাপ বা একটি খণ্ড থেকে FragmentManager অ্যাক্সেস করতে পারেন।

FragmentActivity এবং এর সাবক্লাস, যেমন AppCompatActivity , getSupportFragmentManager() পদ্ধতির মাধ্যমে FragmentManager এ অ্যাক্সেস করতে পারে।

টুকরা এক বা একাধিক শিশু খণ্ড হোস্ট করতে পারে। একটি খণ্ডের ভিতরে, আপনি FragmentManager এর একটি রেফারেন্স পেতে পারেন যা getChildFragmentManager() এর মাধ্যমে খণ্ডের বাচ্চাদের পরিচালনা করে। আপনি যদি এর হোস্ট FragmentManager অ্যাক্সেস করতে চান, তাহলে আপনি getParentFragmentManager() ব্যবহার করতে পারেন।

খণ্ড, তাদের হোস্ট, এবং প্রতিটির সাথে যুক্ত FragmentManager দৃষ্টান্তগুলির মধ্যে সম্পর্ক দেখতে এখানে কয়েকটি উদাহরণ দেওয়া হল।

টুকরো এবং তাদের হোস্ট কার্যকলাপের মধ্যে সম্পর্ক দেখায় দুটি UI লেআউট উদাহরণ
চিত্র 1. টুকরো এবং তাদের হোস্ট কার্যকলাপের মধ্যে সম্পর্ক দেখায় দুটি UI লেআউট উদাহরণ।

চিত্র 1 দুটি উদাহরণ দেখায়, যার প্রতিটিতে একটি একক কার্যকলাপ হোস্ট রয়েছে। এই দুটি উদাহরণে হোস্ট কার্যকলাপ ব্যবহারকারীকে একটি BottomNavigationView হিসাবে শীর্ষ-স্তরের নেভিগেশন প্রদর্শন করে যা অ্যাপের বিভিন্ন স্ক্রীনের সাথে হোস্টের খণ্ডটি অদলবদল করার জন্য দায়ী। প্রতিটি পর্দা একটি পৃথক খণ্ড হিসাবে বাস্তবায়িত হয়.

উদাহরণ 1-এ হোস্ট ফ্র্যাগমেন্ট দুটি চাইল্ড ফ্র্যাগমেন্ট হোস্ট করে যা একটি স্প্লিট-ভিউ স্ক্রিন তৈরি করে। উদাহরণ 2-এর হোস্ট ফ্র্যাগমেন্ট একটি একক চাইল্ড ফ্র্যাগমেন্ট হোস্ট করে যা একটি সোয়াইপ ভিউয়ের ডিসপ্লে ফ্র্যাগমেন্ট তৈরি করে।

এই সেটআপটি দেওয়া হলে, আপনি প্রতিটি হোস্ট সম্পর্কে এটির সাথে যুক্ত একটি FragmentManager হিসাবে ভাবতে পারেন যা তার শিশুর টুকরোগুলি পরিচালনা করে। supportFragmentManager , parentFragmentManager , এবং childFragmentManager এর মধ্যে সম্পত্তি ম্যাপিং সহ চিত্র 2-এ এটি চিত্রিত করা হয়েছে।

প্রতিটি হোস্ট এর সাথে যুক্ত নিজস্ব ফ্র্যাগমেন্ট ম্যানেজার থাকে যা তার চাইল্ড ফ্র্যাগমেন্ট পরিচালনা করে
চিত্র 2. প্রতিটি হোস্টের নিজস্ব FragmentManager সাথে যুক্ত থাকে যা তার শিশুর টুকরোগুলি পরিচালনা করে।

রেফারেন্সের জন্য উপযুক্ত FragmentManager প্রপার্টি নির্ভর করে যেখানে কলসাইটটি ফ্র্যাগমেন্ট হায়ারার্কিতে রয়েছে এবং আপনি কোন ফ্র্যাগমেন্ট ম্যানেজারটি অ্যাক্সেস করার চেষ্টা করছেন তার উপর।

একবার আপনার কাছে FragmentManager এর একটি রেফারেন্স পাওয়া গেলে, আপনি ব্যবহারকারীর কাছে প্রদর্শিত টুকরাগুলিকে ম্যানিপুলেট করতে এটি ব্যবহার করতে পারেন।

শিশুর টুকরো

সাধারণভাবে বলতে গেলে, আপনার অ্যাপ্লিকেশানটি আপনার অ্যাপ্লিকেশন প্রকল্পে একক বা অল্প সংখ্যক ক্রিয়াকলাপ নিয়ে গঠিত, প্রতিটি কার্যকলাপ সম্পর্কিত স্ক্রিনের একটি গোষ্ঠীর প্রতিনিধিত্ব করে। ক্রিয়াকলাপটি শীর্ষ-স্তরের নেভিগেশন স্থাপনের জন্য একটি বিন্দু এবং ViewModel অবজেক্ট এবং খণ্ডগুলির মধ্যে অন্যান্য ভিউ-স্টেটের সুযোগের জন্য একটি জায়গা প্রদান করতে পারে। একটি খণ্ড আপনার অ্যাপে একটি পৃথক গন্তব্য প্রতিনিধিত্ব করে।

আপনি যদি একবারে একাধিক খণ্ড দেখাতে চান, যেমন একটি স্প্লিট-ভিউ বা একটি ড্যাশবোর্ডে, আপনি চাইল্ড ফ্র্যাগমেন্ট ব্যবহার করতে পারেন যা আপনার গন্তব্য খণ্ড এবং এর চাইল্ড ফ্র্যাগমেন্ট ম্যানেজার দ্বারা পরিচালিত হয়।

শিশু খণ্ডের জন্য অন্যান্য ব্যবহারের ক্ষেত্রে নিম্নরূপ:

  • স্ক্রীন স্লাইডগুলি , একটি ViewPager2 ব্যবহার করে একটি প্যারেন্ট ফ্র্যাগমেন্টে চাইল্ড ফ্র্যাগমেন্ট ভিউগুলির একটি সিরিজ পরিচালনা করতে।
  • সম্পর্কিত স্ক্রিনের একটি সেটের মধ্যে সাব-নেভিগেশন।
  • Jetpack নেভিগেশন পৃথক গন্তব্য হিসাবে চাইল্ড টুকরা ব্যবহার করে। একটি অ্যাক্টিভিটি একটি সিঙ্গেল প্যারেন্ট NavHostFragment হোস্ট করে এবং ব্যবহারকারীরা আপনার অ্যাপের মাধ্যমে নেভিগেট করার সাথে সাথে বিভিন্ন চাইল্ড ডেস্টিনেশন ফ্র্যাগমেন্ট দিয়ে এর স্থান পূরণ করে।

ফ্র্যাগমেন্ট ম্যানেজার ব্যবহার করুন

FragmentManager ফ্র্যাগমেন্ট ব্যাক স্ট্যাক পরিচালনা করে। রানটাইমে, FragmentManager ব্যবহারকারীর ইন্টারঅ্যাকশনের প্রতিক্রিয়ায় টুকরো যোগ করা বা অপসারণের মতো ব্যাক স্ট্যাক অপারেশন করতে পারে। পরিবর্তনের প্রতিটি সেটকে একক ইউনিট হিসাবে একত্রে প্রতিশ্রুতিবদ্ধ করা হয় যাকে FragmentTransaction বলা হয়। ফ্র্যাগমেন্ট লেনদেন সম্পর্কে আরও গভীর আলোচনার জন্য, খণ্ড লেনদেন নির্দেশিকা দেখুন।

ব্যবহারকারী যখন তাদের ডিভাইসে ব্যাক বোতামে ট্যাপ করে, অথবা আপনি যখন FragmentManager.popBackStack() কল করেন, তখন স্ট্যাকের থেকে শীর্ষ-সবচেয়ে ফ্র্যাগমেন্ট লেনদেন হয়। যদি স্ট্যাকের উপর আর কোন টুকরো লেনদেন না থাকে এবং আপনি যদি চাইল্ড ফ্র্যাগমেন্ট ব্যবহার না করেন, তাহলে ব্যাক ইভেন্টটি ক্রিয়াকলাপ পর্যন্ত বুদবুদ হয়ে যায়। আপনি যদি শিশুর টুকরো ব্যবহার করেন , তাহলে শিশু এবং ভাইবোনের টুকরোগুলির জন্য বিশেষ বিবেচনা দেখুন।

আপনি যখন একটি লেনদেনে addToBackStack() কল করেন, তখন লেনদেনে যেকোন সংখ্যক ক্রিয়াকলাপ অন্তর্ভুক্ত থাকতে পারে, যেমন একাধিক টুকরা যোগ করা বা একাধিক পাত্রে টুকরো প্রতিস্থাপন করা।

যখন পিছনের স্ট্যাকটি পপ করা হয়, তখন এই সমস্ত ক্রিয়াকলাপগুলি একটি একক পারমাণবিক ক্রিয়া হিসাবে বিপরীত হয়। যাইহোক, যদি আপনি popBackStack() কলের আগে অতিরিক্ত লেনদেন করেন এবং আপনি যদি লেনদেনের জন্য addToBackStack() ব্যবহার না করেন , তাহলে এই অপারেশনগুলি বিপরীত হয় না । অতএব, একটি একক FragmentTransaction মধ্যে, ইন্টারলিভিং লেনদেনগুলি এড়িয়ে চলুন যা ব্যাক স্ট্যাককে প্রভাবিত করে না।

একটি লেনদেন সঞ্চালন

একটি লেআউট কন্টেইনারের মধ্যে একটি খণ্ড প্রদর্শন করতে, একটি FragmentTransaction তৈরি করতে FragmentManager ব্যবহার করুন। লেনদেনের মধ্যে, আপনি তারপর কন্টেইনারে একটি add() বা replace() অপারেশন করতে পারেন।

উদাহরণস্বরূপ, একটি সাধারণ FragmentTransaction এইরকম দেখতে পারে:

কোটলিন

supportFragmentManager.commit {
   replace<ExampleFragment>(R.id.fragment_container)
   setReorderingAllowed(true)
   addToBackStack("name") // Name can be null
}

জাভা

FragmentManager fragmentManager = getSupportFragmentManager();
fragmentManager.beginTransaction()
    .replace(R.id.fragment_container, ExampleFragment.class, null)
    .setReorderingAllowed(true)
    .addToBackStack("name") // Name can be null
    .commit();

এই উদাহরণে, ExampleFragment সেই খণ্ডটিকে প্রতিস্থাপন করে, যদি থাকে, যেটি বর্তমানে R.id.fragment_container ID দ্বারা চিহ্নিত লেআউট কন্টেইনারে রয়েছে। replace() পদ্ধতিতে ফ্র্যাগমেন্টের ক্লাস প্রদান করলে FragmentManager তার FragmentFactory ব্যবহার করে ইনস্ট্যান্টিয়েশন পরিচালনা করতে দেয়। আরও তথ্যের জন্য, আপনার টুকরা বিভাগে নির্ভরতা প্রদান দেখুন।

setReorderingAllowed(true) লেনদেনের সাথে জড়িত অংশগুলির অবস্থার পরিবর্তনগুলিকে অপ্টিমাইজ করে যাতে অ্যানিমেশন এবং রূপান্তরগুলি সঠিকভাবে কাজ করে৷ অ্যানিমেশন এবং ট্রানজিশনের সাথে নেভিগেট করার বিষয়ে আরও তথ্যের জন্য, ফ্র্যাগমেন্ট লেনদেন দেখুন এবং অ্যানিমেশন ব্যবহার করে টুকরোগুলির মধ্যে নেভিগেট করুন

addToBackStack() কল করা ব্যাক স্ট্যাকে লেনদেন করে। ব্যবহারকারী পরবর্তীতে লেনদেনটি উল্টাতে পারে এবং ব্যাক বোতামে ট্যাপ করে পূর্ববর্তী অংশটি ফিরিয়ে আনতে পারে। আপনি যদি একটি একক লেনদেনের মধ্যে একাধিক টুকরো যোগ করেন বা মুছে ফেলেন, ব্যাক স্ট্যাক পপ হয়ে গেলে সেই সমস্ত ক্রিয়াকলাপগুলি পূর্বাবস্থায় ফেরানো হয়৷ addToBackStack() কলে দেওয়া ঐচ্ছিক নামটি আপনাকে popBackStack() ব্যবহার করে একটি নির্দিষ্ট লেনদেনে পপ ব্যাক করার ক্ষমতা দেয়।

যদি আপনি addToBackStack() কে কল না করেন যখন আপনি একটি লেনদেন করেন যা একটি খণ্ডটি সরিয়ে দেয়, তাহলে লেনদেনটি করা হলে সরানো খণ্ডটি ধ্বংস হয়ে যায় এবং ব্যবহারকারী এটিতে ফিরে যেতে পারে না। আপনি যদি একটি খণ্ডটি সরানোর সময় addToBackStack() কল করেন, তাহলে খণ্ডটি শুধুমাত্র STOPPED হয় এবং ব্যবহারকারী যখন ফিরে যান তখন পুনরায় RESUMED হয়। এক্ষেত্রে এর দৃষ্টিভঙ্গি নষ্ট হয়ে যায় । আরও তথ্যের জন্য, ফ্র্যাগমেন্ট লাইফসাইকেল দেখুন।

একটি বিদ্যমান খণ্ড খুঁজুন

আপনি findFragmentById() ব্যবহার করে একটি লেআউট কন্টেইনারের মধ্যে বর্তমান টুকরোটির একটি রেফারেন্স পেতে পারেন। XML থেকে স্ফীত হলে প্রদত্ত আইডি দ্বারা বা FragmentTransaction যোগ করার সময় কন্টেইনার আইডি দ্বারা একটি খণ্ড সন্ধান করতে findFragmentById() ব্যবহার করুন। এখানে একটি উদাহরণ:

কোটলিন

supportFragmentManager.commit {
   replace<ExampleFragment>(R.id.fragment_container)
   setReorderingAllowed(true)
   addToBackStack(null)
}
...
val fragment: ExampleFragment =
        supportFragmentManager.findFragmentById(R.id.fragment_container) as ExampleFragment

জাভা

FragmentManager fragmentManager = getSupportFragmentManager();
fragmentManager.beginTransaction()
    .replace(R.id.fragment_container, ExampleFragment.class, null)
    .setReorderingAllowed(true)
    .addToBackStack(null)
    .commit();
...
ExampleFragment fragment =
        (ExampleFragment) fragmentManager.findFragmentById(R.id.fragment_container);

বিকল্পভাবে, আপনি একটি খণ্ডে একটি অনন্য ট্যাগ বরাদ্দ করতে পারেন এবং findFragmentByTag() ব্যবহার করে একটি রেফারেন্স পেতে পারেন। আপনি android:tag XML অ্যাট্রিবিউট ব্যবহার করে একটি ট্যাগ বরাদ্দ করতে পারেন যেগুলি আপনার লেআউটের মধ্যে সংজ্ঞায়িত করা হয়েছে বা একটি FragmentTransaction মধ্যে একটি add() বা replace() অপারেশনের সময়।

কোটলিন

supportFragmentManager.commit {
   replace<ExampleFragment>(R.id.fragment_container, "tag")
   setReorderingAllowed(true)
   addToBackStack(null)
}
...
val fragment: ExampleFragment =
        supportFragmentManager.findFragmentByTag("tag") as ExampleFragment

জাভা

FragmentManager fragmentManager = getSupportFragmentManager();
fragmentManager.beginTransaction()
    .replace(R.id.fragment_container, ExampleFragment.class, null, "tag")
    .setReorderingAllowed(true)
    .addToBackStack(null)
    .commit();
...
ExampleFragment fragment = (ExampleFragment) fragmentManager.findFragmentByTag("tag");

শিশু এবং ভাইবোন টুকরা জন্য বিশেষ বিবেচনা

শুধুমাত্র একটি FragmentManager যেকোন সময়ে ফ্র্যাগমেন্ট ব্যাক স্ট্যাক নিয়ন্ত্রণ করতে পারে। যদি আপনার অ্যাপটি একই সময়ে স্ক্রিনে একাধিক ভাইবোন খণ্ড দেখায়, বা যদি আপনার অ্যাপ শিশু খণ্ডগুলি ব্যবহার করে, তাহলে আপনার অ্যাপের প্রাথমিক নেভিগেশন পরিচালনা করার জন্য একটি FragmentManager মনোনীত করা হয়েছে।

একটি ফ্র্যাগমেন্ট লেনদেনের ভিতরে প্রাথমিক ন্যাভিগেশন ফ্র্যাগমেন্ট সংজ্ঞায়িত করতে, লেনদেনের উপর setPrimaryNavigationFragment() পদ্ধতিতে কল করুন, সেই টুকরোটির উদাহরণে পাস করে যার childFragmentManager প্রাথমিক নিয়ন্ত্রণ রয়েছে।

নেভিগেশন কাঠামোটিকে স্তরগুলির একটি সিরিজ হিসাবে বিবেচনা করুন, কার্যকলাপটি বাইরেরতম স্তর হিসাবে, প্রতিটি স্তরের নীচে শিশুর টুকরোগুলিকে মোড়ানো। প্রতিটি স্তর একটি একক প্রাথমিক নেভিগেশন খণ্ড আছে.

যখন পিছনের ঘটনা ঘটে, তখন সবচেয়ে ভিতরের স্তরটি নেভিগেশন আচরণ নিয়ন্ত্রণ করে। একবার ভিতরের স্তরটিতে আর কোন টুকরো লেনদেন নেই যা থেকে পপ ব্যাক করা যায়, নিয়ন্ত্রণ পরবর্তী স্তরে ফিরে আসে এবং আপনি কার্যকলাপে না পৌঁছানো পর্যন্ত এই প্রক্রিয়াটি পুনরাবৃত্তি হয়।

যখন দুই বা ততোধিক খণ্ড একই সময়ে প্রদর্শিত হয়, তাদের মধ্যে শুধুমাত্র একটি প্রাথমিক ন্যাভিগেশন খণ্ড। প্রাথমিক নেভিগেশন ফ্র্যাগমেন্ট হিসাবে একটি খণ্ড সেট করা পূর্ববর্তী খণ্ড থেকে উপাধিটি সরিয়ে দেয়। পূর্ববর্তী উদাহরণ ব্যবহার করে, আপনি যদি বিশদ খণ্ডটিকে প্রাথমিক ন্যাভিগেশন খণ্ড হিসাবে সেট করেন, তবে প্রধান খণ্ডটির উপাধি সরানো হয়।

একাধিক ব্যাক স্ট্যাক সমর্থন

কিছু ক্ষেত্রে, আপনার অ্যাপটিকে একাধিক ব্যাক স্ট্যাক সমর্থন করতে হতে পারে। একটি সাধারণ উদাহরণ হল যদি আপনার অ্যাপ নিচের নেভিগেশন বার ব্যবহার করে। FragmentManager আপনাকে saveBackStack() এবং restoreBackStack() পদ্ধতির সাথে একাধিক ব্যাক স্ট্যাক সমর্থন করতে দেয়। এই পদ্ধতিগুলি আপনাকে একটি ব্যাক স্ট্যাক সংরক্ষণ করে এবং অন্য একটি পুনরুদ্ধার করে ব্যাক স্ট্যাকের মধ্যে অদলবদল করতে দেয়।

saveBackStack() ঐচ্ছিক name প্যারামিটার সহ popBackStack() কল করার অনুরূপভাবে কাজ করে: নির্দিষ্ট লেনদেন এবং স্ট্যাকের পরে সমস্ত লেনদেন পপ করা হয়। পার্থক্য হল saveBackStack() পপ করা লেনদেনের সমস্ত অংশের অবস্থা সংরক্ষণ করে

উদাহরণস্বরূপ, ধরুন আপনি পূর্বে addToBackStack() ব্যবহার করে একটি FragmentTransaction কমিট করে ব্যাক স্ট্যাকে একটি খণ্ড যুক্ত করেছেন, যেমনটি নিম্নলিখিত উদাহরণে দেখানো হয়েছে:

কোটলিন

supportFragmentManager.commit {
  replace<ExampleFragment>(R.id.fragment_container)
  setReorderingAllowed(true)
  addToBackStack("replacement")
}

জাভা

supportFragmentManager.beginTransaction()
  .replace(R.id.fragment_container, ExampleFragment.class, null)
  // setReorderingAllowed(true) and the optional string argument for
  // addToBackStack() are both required if you want to use saveBackStack()
  .setReorderingAllowed(true)
  .addToBackStack("replacement")
  .commit();

সেক্ষেত্রে, আপনি saveBackStack() কল করে এই টুকরো লেনদেন এবং ExampleFragment এর অবস্থা সংরক্ষণ করতে পারেন:

কোটলিন

supportFragmentManager.saveBackStack("replacement")

জাভা

supportFragmentManager.saveBackStack("replacement");

আপনি সমস্ত পপ করা লেনদেন এবং সমস্ত সংরক্ষিত খণ্ড অবস্থা পুনরুদ্ধার করতে একই নামের প্যারামিটার সহ restoreBackStack() কল করতে পারেন:

কোটলিন

supportFragmentManager.restoreBackStack("replacement")

জাভা

supportFragmentManager.restoreBackStack("replacement");

আপনার টুকরা নির্ভরতা প্রদান

একটি খণ্ড যোগ করার সময়, আপনি ম্যানুয়ালি খণ্ডটিকে ইনস্ট্যান্টিয়েট করতে পারেন এবং এটিকে FragmentTransaction যোগ করতে পারেন।

কোটলিন

fragmentManager.commit {
    // Instantiate a new instance before adding
    val myFragment = ExampleFragment()
    add(R.id.fragment_view_container, myFragment)
    setReorderingAllowed(true)
}

জাভা

// Instantiate a new instance before adding
ExampleFragment myFragment = new ExampleFragment();
fragmentManager.beginTransaction()
    .add(R.id.fragment_view_container, myFragment)
    .setReorderingAllowed(true)
    .commit();

আপনি যখন ফ্র্যাগমেন্ট লেনদেন করেন, তখন আপনার তৈরি করা টুকরোটির উদাহরণটি ব্যবহৃত উদাহরণ। যাইহোক, একটি কনফিগারেশন পরিবর্তনের সময়, আপনার কার্যকলাপ এবং এর সমস্ত অংশগুলি ধ্বংস হয়ে যায় এবং তারপরে সবচেয়ে প্রযোজ্য Android সংস্থানগুলির সাথে পুনরায় তৈরি করা হয়৷ FragmentManager আপনার জন্য এই সবগুলি পরিচালনা করে: এটি আপনার টুকরোগুলির দৃষ্টান্তগুলি পুনরায় তৈরি করে, সেগুলি হোস্টের সাথে সংযুক্ত করে এবং ব্যাক স্ট্যাকের অবস্থাটি পুনরায় তৈরি করে।

ডিফল্টরূপে, FragmentManager একটি FragmentFactory ব্যবহার করে যা ফ্রেমওয়ার্ক আপনার ফ্র্যাগমেন্টের একটি নতুন দৃষ্টান্ত তৈরি করতে প্রদান করে। এই ডিফল্ট ফ্যাক্টরি আপনার খণ্ডের জন্য একটি নো-আর্গুমেন্ট কনস্ট্রাক্টর খুঁজে পেতে এবং আহ্বান করতে প্রতিফলন ব্যবহার করে। এর মানে হল যে আপনি এই ডিফল্ট ফ্যাক্টরিটি আপনার খণ্ডে নির্ভরতা প্রদান করতে ব্যবহার করতে পারবেন না। এর মানে হল যে কোন কাস্টম কনস্ট্রাক্টর আপনি প্রথমবার আপনার টুকরো তৈরি করতে ব্যবহার করেছেন সেটি ডিফল্টরূপে বিনোদনের সময় ব্যবহার করা হয় না

আপনার ফ্র্যাগমেন্টে নির্ভরতা প্রদান করতে, অথবা কোনো কাস্টম কনস্ট্রাক্টর ব্যবহার করতে, পরিবর্তে একটি কাস্টম FragmentFactory সাবক্লাস তৈরি করুন এবং তারপরে FragmentFactory.instantiate ওভাররাইড করুন। তারপরে আপনি আপনার কাস্টম ফ্যাক্টরির সাথে FragmentManager ডিফল্ট ফ্যাক্টরিকে ওভাররাইড করতে পারেন, যা তারপরে আপনার টুকরোগুলিকে ইনস্ট্যান্টিয়েট করতে ব্যবহৃত হয়।

ধরুন আপনার কাছে একটি DessertsFragment রয়েছে যা আপনার শহরে জনপ্রিয় ডেজার্টগুলি প্রদর্শনের জন্য দায়ী, এবং সেই DessertsFragment একটি DessertsRepository ক্লাসের উপর নির্ভরশীলতা রয়েছে যা এটিকে আপনার ব্যবহারকারীর কাছে সঠিক UI প্রদর্শন করার জন্য প্রয়োজনীয় তথ্য সরবরাহ করে৷

আপনি আপনার DessertsFragment সংজ্ঞায়িত করতে পারেন যাতে এটির কনস্ট্রাক্টরে একটি DessertsRepository উদাহরণ প্রয়োজন।

কোটলিন

class DessertsFragment(val dessertsRepository: DessertsRepository) : Fragment() {
    ...
}

জাভা

public class DessertsFragment extends Fragment {
    private DessertsRepository dessertsRepository;

    public DessertsFragment(DessertsRepository dessertsRepository) {
        super();
        this.dessertsRepository = dessertsRepository;
    }

    // Getter omitted.

    ...
}

আপনার FragmentFactory একটি সাধারণ বাস্তবায়ন নিম্নলিখিতটির মতো দেখতে হতে পারে।

কোটলিন

class MyFragmentFactory(val repository: DessertsRepository) : FragmentFactory() {
    override fun instantiate(classLoader: ClassLoader, className: String): Fragment =
            when (loadFragmentClass(classLoader, className)) {
                DessertsFragment::class.java -> DessertsFragment(repository)
                else -> super.instantiate(classLoader, className)
            }
}

জাভা

public class MyFragmentFactory extends FragmentFactory {
    private DessertsRepository repository;

    public MyFragmentFactory(DessertsRepository repository) {
        super();
        this.repository = repository;
    }

    @NonNull
    @Override
    public Fragment instantiate(@NonNull ClassLoader classLoader, @NonNull String className) {
        Class<? extends Fragment> fragmentClass = loadFragmentClass(classLoader, className);
        if (fragmentClass == DessertsFragment.class) {
            return new DessertsFragment(repository);
        } else {
            return super.instantiate(classLoader, className);
        }
    }
}

এই উদাহরণটি FragmentFactory সাবক্লাস করে, একটি DessertsFragment এর জন্য কাস্টম ফ্র্যাগমেন্ট তৈরির যুক্তি প্রদান করার জন্য instantiate() পদ্ধতিকে ওভাররাইড করে। অন্যান্য ফ্র্যাগমেন্ট ক্লাস super.instantiate() এর মাধ্যমে FragmentFactory এর ডিফল্ট আচরণ দ্বারা পরিচালিত হয়।

আপনি তারপর FragmentManager এ একটি সম্পত্তি সেট করে আপনার অ্যাপের টুকরো তৈরি করার সময় ব্যবহার করার জন্য কারখানা হিসাবে MyFragmentFactory মনোনীত করতে পারেন। আপনার খন্ডগুলি পুনরায় তৈরি করার সময় MyFragmentFactory ব্যবহার করা হয়েছে তা নিশ্চিত করতে আপনাকে অবশ্যই আপনার কার্যকলাপের super.onCreate() এর আগে এই সম্পত্তিটি সেট করতে হবে।

কোটলিন

class MealActivity : AppCompatActivity() {
    override fun onCreate(savedInstanceState: Bundle?) {
        supportFragmentManager.fragmentFactory = MyFragmentFactory(DessertsRepository.getInstance())
        super.onCreate(savedInstanceState)
    }
}

জাভা

public class MealActivity extends AppCompatActivity {
    @Override
    protected void onCreate(@Nullable Bundle savedInstanceState) {
        DessertsRepository repository = DessertsRepository.getInstance();
        getSupportFragmentManager().setFragmentFactory(new MyFragmentFactory(repository));
        super.onCreate(savedInstanceState);
    }
}

ক্রিয়াকলাপে FragmentFactory সেট করা সমস্ত কার্যকলাপের খণ্ডের স্তরবিন্যাস জুড়ে খণ্ড সৃষ্টিকে ওভাররাইড করে। অন্য কথায়, আপনার যোগ করা যেকোনো চাইল্ড ফ্র্যাগমেন্টের childFragmentManager নিম্ন স্তরে ওভাররাইড না করা পর্যন্ত এখানে সেট করা কাস্টম ফ্র্যাগমেন্ট ফ্যাক্টরি ব্যবহার করে।

ফ্র্যাগমেন্ট ফ্যাক্টরি দিয়ে পরীক্ষা করুন

একটি একক অ্যাক্টিভিটি আর্কিটেকচারে, FragmentScenario ক্লাস ব্যবহার করে আপনার টুকরোগুলোকে বিচ্ছিন্নভাবে পরীক্ষা করুন। যেহেতু আপনি আপনার কার্যকলাপের কাস্টম onCreate যুক্তির উপর নির্ভর করতে পারবেন না, আপনি পরিবর্তে আপনার টুকরা পরীক্ষায় একটি যুক্তি হিসাবে FragmentFactory পাস করতে পারেন, যেমনটি নিম্নলিখিত উদাহরণে দেখানো হয়েছে:

// Inside your test
val dessertRepository = mock(DessertsRepository::class.java)
launchFragment<DessertsFragment>(factory = MyFragmentFactory(dessertRepository)).onFragment {
    // Test Fragment logic
}

এই পরীক্ষার প্রক্রিয়া সম্পর্কে বিস্তারিত তথ্যের জন্য এবং সম্পূর্ণ উদাহরণের জন্য, আপনার টুকরা পরীক্ষা করুন দেখুন।